flowdock 0.1.11 → 0.2.0
Sign up to get free protection for your applications and to get access to all the features.
- data/Gemfile +1 -0
- data/{MIT-LICENSE → LICENSE} +1 -1
- data/README.md +43 -15
- data/VERSION +1 -1
- data/flowdock.gemspec +7 -3
- data/lib/flowdock.rb +65 -19
- data/lib/flowdock/capistrano.rb +8 -6
- data/spec/flowdock_spec.rb +167 -46
- metadata +30 -18
data/Gemfile
CHANGED
data/{MIT-LICENSE → LICENSE}
RENAMED
data/README.md
CHANGED
@@ -1,8 +1,6 @@
|
|
1
1
|
# Flowdock
|
2
2
|
|
3
|
-
Ruby Gem for using the Flowdock API.
|
4
|
-
|
5
|
-
http://www.flowdock.com/api
|
3
|
+
Ruby Gem for using the Flowdock Push API. See [Push API documentation](http://www.flowdock.com/api/push) for details.
|
6
4
|
|
7
5
|
## Build Status
|
8
6
|
|
@@ -10,9 +8,10 @@ http://www.flowdock.com/api
|
|
10
8
|
|
11
9
|
flowdock gem is tested on Ruby 1.8.7, 1.9.3 and JRuby.
|
12
10
|
|
13
|
-
##
|
11
|
+
## Dependencies
|
14
12
|
|
15
13
|
* HTTParty
|
14
|
+
* MultiJson
|
16
15
|
|
17
16
|
## Installing
|
18
17
|
|
@@ -20,28 +19,57 @@ flowdock gem is tested on Ruby 1.8.7, 1.9.3 and JRuby.
|
|
20
19
|
|
21
20
|
If you're using JRuby, you'll also need to install jruby-openssl gem.
|
22
21
|
|
23
|
-
##
|
22
|
+
## Usage
|
23
|
+
|
24
|
+
To post content to Chat or Team Inbox, you need to use the target flow's API token. They can be found from [tokens page](https://www.flowdock.com/account/tokens).
|
25
|
+
|
26
|
+
### Posting to Chat
|
24
27
|
|
25
28
|
require 'rubygems'
|
26
29
|
require 'flowdock'
|
27
30
|
|
28
|
-
# create a new Flow object with target flow's api token and
|
29
|
-
flow = Flowdock::Flow.new(:api_token => "
|
30
|
-
|
31
|
-
|
31
|
+
# create a new Flow object with target flow's api token and external user name (enough for posting to Chat)
|
32
|
+
flow = Flowdock::Flow.new(:api_token => "__FLOW_TOKEN__", :external_user_name => "John")
|
33
|
+
|
34
|
+
# send message to Chat
|
35
|
+
flow.push_to_chat(:content => "Hello!", :tags => ["cool", "stuff"])
|
32
36
|
|
33
|
-
|
34
|
-
|
35
|
-
|
37
|
+
### Posting to Team Inbox
|
38
|
+
|
39
|
+
# create a new Flow object with target flow's api token and sender information for Team Inbox posting
|
40
|
+
flow = Flowdock::Flow.new(:api_token => "__FLOW_TOKEN__",
|
41
|
+
:source => "myapp", :from => {:name => "John Doe", :address => "john.doe@example.com"})
|
42
|
+
|
43
|
+
# send message to Team Inbox
|
44
|
+
flow.push_to_team_inbox(:subject => "Greetings from Flowdock API Gem!",
|
45
|
+
:content => "<h2>It works!</h2><p>Now you can start developing your awesome application for Flowdock.</p>",
|
36
46
|
:tags => ["cool", "stuff"], :link => "http://www.flowdock.com/")
|
37
|
-
|
47
|
+
|
38
48
|
## API methods
|
39
49
|
|
40
50
|
* Flow methods
|
41
51
|
|
42
|
-
*
|
52
|
+
*push_to_team_inbox* - Send message to Team Inbox. See [API documentation](http://www.flowdock.com/api/team-inbox) for details.
|
53
|
+
|
54
|
+
*push_to_chat* - Send message to Chat. See [API documentation](http://www.flowdock.com/api/chat) for details.
|
55
|
+
|
56
|
+
*send_message(params)* - Deprecated. Please use *push_to_team_inbox* instead.
|
57
|
+
|
58
|
+
|
59
|
+
## Capistrano deployment task
|
60
|
+
|
61
|
+
The Flowdock API Ruby Gem includes a ready task for sending deployment notifications with Capistrano (you need to have Grit installed too). Just add the task into your deploy.rb file and configure the settings to match your project and flow:
|
62
|
+
|
63
|
+
```
|
64
|
+
require 'flowdock/capistrano'
|
65
|
+
|
66
|
+
# for Flowdock Gem notifications
|
67
|
+
set :flowdock_project_name, "My project"
|
68
|
+
set :flowdock_deploy_tags, ["frontend"]
|
69
|
+
set :flowdock_api_token, "_YOUR_API_TOKEN_HERE_"
|
70
|
+
```
|
43
71
|
|
44
72
|
|
45
73
|
## Copyright
|
46
74
|
|
47
|
-
Copyright (c)
|
75
|
+
Copyright (c) 2012 Flowdock Ltd. See LICENSE for further details.
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.
|
1
|
+
0.2.0
|
data/flowdock.gemspec
CHANGED
@@ -5,13 +5,14 @@
|
|
5
5
|
|
6
6
|
Gem::Specification.new do |s|
|
7
7
|
s.name = "flowdock"
|
8
|
-
s.version = "0.
|
8
|
+
s.version = "0.2.0"
|
9
9
|
|
10
10
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
11
11
|
s.authors = ["Antti Pitk\u{e4}nen"]
|
12
|
-
s.date = "2012-
|
12
|
+
s.date = "2012-02-20"
|
13
13
|
s.email = "team@flowdock.com"
|
14
14
|
s.extra_rdoc_files = [
|
15
|
+
"LICENSE",
|
15
16
|
"README.md"
|
16
17
|
]
|
17
18
|
s.files = [
|
@@ -19,7 +20,7 @@ Gem::Specification.new do |s|
|
|
19
20
|
".rspec",
|
20
21
|
".travis.yml",
|
21
22
|
"Gemfile",
|
22
|
-
"
|
23
|
+
"LICENSE",
|
23
24
|
"README.md",
|
24
25
|
"Rakefile",
|
25
26
|
"VERSION",
|
@@ -40,6 +41,7 @@ Gem::Specification.new do |s|
|
|
40
41
|
|
41
42
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
42
43
|
s.add_runtime_dependency(%q<httparty>, ["~> 0.7"])
|
44
|
+
s.add_runtime_dependency(%q<multi_json>, [">= 0"])
|
43
45
|
s.add_development_dependency(%q<rdoc>, [">= 2.4.2"])
|
44
46
|
s.add_development_dependency(%q<rspec>, ["~> 2.6"])
|
45
47
|
s.add_development_dependency(%q<webmock>, [">= 0"])
|
@@ -48,6 +50,7 @@ Gem::Specification.new do |s|
|
|
48
50
|
s.add_development_dependency(%q<jruby-openssl>, [">= 0"])
|
49
51
|
else
|
50
52
|
s.add_dependency(%q<httparty>, ["~> 0.7"])
|
53
|
+
s.add_dependency(%q<multi_json>, [">= 0"])
|
51
54
|
s.add_dependency(%q<rdoc>, [">= 2.4.2"])
|
52
55
|
s.add_dependency(%q<rspec>, ["~> 2.6"])
|
53
56
|
s.add_dependency(%q<webmock>, [">= 0"])
|
@@ -57,6 +60,7 @@ Gem::Specification.new do |s|
|
|
57
60
|
end
|
58
61
|
else
|
59
62
|
s.add_dependency(%q<httparty>, ["~> 0.7"])
|
63
|
+
s.add_dependency(%q<multi_json>, [">= 0"])
|
60
64
|
s.add_dependency(%q<rdoc>, [">= 2.4.2"])
|
61
65
|
s.add_dependency(%q<rspec>, ["~> 2.6"])
|
62
66
|
s.add_dependency(%q<webmock>, [">= 0"])
|
data/lib/flowdock.rb
CHANGED
@@ -1,65 +1,111 @@
|
|
1
1
|
require 'rubygems'
|
2
2
|
require 'httparty'
|
3
|
+
require 'multi_json'
|
3
4
|
|
4
5
|
module Flowdock
|
5
|
-
FLOWDOCK_API_URL = "https://api.flowdock.com/v1
|
6
|
+
FLOWDOCK_API_URL = "https://api.flowdock.com/v1"
|
6
7
|
|
7
8
|
class Flow
|
8
9
|
include HTTParty
|
9
10
|
class InvalidParameterError < StandardError; end
|
10
11
|
class ApiError < StandardError; end
|
11
12
|
|
12
|
-
# Required options keys: :api_token, :source, :from => { :name, :address }
|
13
|
+
# Required options keys: :api_token, optional keys: :external_user_name, :source, :from => { :name, :address }
|
13
14
|
def initialize(options = {})
|
14
15
|
@api_token = options[:api_token]
|
15
16
|
raise InvalidParameterError, "Flow must have :api_token attribute" if blank?(@api_token)
|
16
|
-
|
17
|
-
@source = options[:source]
|
18
|
-
raise InvalidParameterError, "Flow must have valid :source attribute, only alphanumeric characters and underscores can be used" if blank?(@source) || !@source.match(/^[a-z0-9\-_ ]+$/i)
|
19
|
-
|
20
|
-
@project = options[:project]
|
21
|
-
raise InvalidParameterError, "Optional attribute :project can only contain alphanumeric characters and underscores" if !blank?(@project) && !@project.match(/^[a-z0-9\-_ ]+$/i)
|
22
17
|
|
18
|
+
@source = options[:source] || nil
|
19
|
+
@project = options[:project] || nil
|
23
20
|
@from = options[:from] || {}
|
21
|
+
@external_user_name = options[:external_user_name] || nil
|
24
22
|
end
|
25
23
|
|
26
|
-
def
|
24
|
+
def push_to_team_inbox(params)
|
25
|
+
@source = params[:source] unless blank?(params[:source])
|
26
|
+
raise InvalidParameterError, "Message must have valid :source attribute, only alphanumeric characters and underscores can be used" if blank?(@source) || !@source.match(/^[a-z0-9\-_ ]+$/i)
|
27
|
+
|
28
|
+
@project = params[:project] unless blank?(params[:project])
|
29
|
+
raise InvalidParameterError, "Optional attribute :project can only contain alphanumeric characters and underscores" if !blank?(@project) && !@project.match(/^[a-z0-9\-_ ]+$/i)
|
30
|
+
|
27
31
|
raise InvalidParameterError, "Message must have both :subject and :content" if blank?(params[:subject]) || blank?(params[:content])
|
28
|
-
|
32
|
+
|
29
33
|
from = (params[:from].kind_of?(Hash)) ? params[:from] : @from
|
30
|
-
raise InvalidParameterError, "
|
34
|
+
raise InvalidParameterError, "Message's :from attribute must have :address attribute" if blank?(from[:address])
|
31
35
|
|
32
36
|
tags = (params[:tags].kind_of?(Array)) ? params[:tags] : []
|
33
37
|
tags.reject! { |tag| !tag.kind_of?(String) || blank?(tag) }
|
34
|
-
|
38
|
+
|
35
39
|
link = (!blank?(params[:link])) ? params[:link] : nil
|
36
40
|
|
37
41
|
params = {
|
38
42
|
:source => @source,
|
39
43
|
:format => 'html', # currently only supported format
|
40
|
-
:from_name => from[:name],
|
41
44
|
:from_address => from[:address],
|
42
45
|
:subject => params[:subject],
|
43
46
|
:content => params[:content],
|
44
47
|
}
|
48
|
+
params[:from_name] = from[:name] unless blank?(from[:name])
|
45
49
|
params[:tags] = tags.join(",") if tags.size > 0
|
46
50
|
params[:project] = @project unless blank?(@project)
|
47
51
|
params[:link] = link unless blank?(link)
|
48
52
|
|
49
53
|
# Send the request
|
50
|
-
resp = self.class.post(get_flowdock_api_url, :body => params)
|
51
|
-
|
54
|
+
resp = self.class.post(get_flowdock_api_url("messages/team_inbox"), :body => params)
|
55
|
+
handle_response(resp)
|
52
56
|
true
|
53
57
|
end
|
54
|
-
|
58
|
+
|
59
|
+
def push_to_chat(params)
|
60
|
+
raise InvalidParameterError, "Message must have :content" if blank?(params[:content])
|
61
|
+
|
62
|
+
@external_user_name = params[:external_user_name] unless blank?(params[:external_user_name])
|
63
|
+
if blank?(@external_user_name) || @external_user_name.match(/^[\S]+$/).nil? || @external_user_name.length > 16
|
64
|
+
raise InvalidParameterError, "Message must have :external_user_name that has no whitespace and maximum of 16 characters"
|
65
|
+
end
|
66
|
+
|
67
|
+
tags = (params[:tags].kind_of?(Array)) ? params[:tags] : []
|
68
|
+
tags.reject! { |tag| !tag.kind_of?(String) || blank?(tag) }
|
69
|
+
|
70
|
+
params = {
|
71
|
+
:content => params[:content],
|
72
|
+
:external_user_name => @external_user_name
|
73
|
+
}
|
74
|
+
params[:tags] = tags.join(",") if tags.size > 0
|
75
|
+
|
76
|
+
# Send the request
|
77
|
+
resp = self.class.post(get_flowdock_api_url("messages/chat"), :body => params)
|
78
|
+
handle_response(resp)
|
79
|
+
true
|
80
|
+
end
|
81
|
+
|
82
|
+
# <b>DEPRECATED:</b> Please use <tt>useful</tt> instead.
|
83
|
+
def send_message(params)
|
84
|
+
warn "[DEPRECATION] `send_message` is deprecated. Please use `push_to_team_inbox` instead."
|
85
|
+
push_to_team_inbox(params)
|
86
|
+
end
|
87
|
+
|
55
88
|
private
|
56
89
|
|
57
90
|
def blank?(var)
|
58
91
|
var.nil? || var.respond_to?(:length) && var.length == 0
|
59
92
|
end
|
60
|
-
|
61
|
-
def
|
62
|
-
|
93
|
+
|
94
|
+
def handle_response(resp)
|
95
|
+
unless resp.code == 200
|
96
|
+
begin
|
97
|
+
# should have JSON response
|
98
|
+
json = MultiJson.decode(resp.body)
|
99
|
+
errors = json["errors"].map {|k,v| "#{k}: #{v.join(',')}"}.join("\n") unless json["errors"].nil?
|
100
|
+
raise ApiError, "Flowdock API returned error:\nStatus: #{resp.code}\n Message: #{json["message"]}\n Errors:\n#{errors}"
|
101
|
+
rescue MultiJson::DecodeError
|
102
|
+
raise ApiError, "Flowdock API returned error:\nStatus: #{resp.code}\nBody: #{resp.body}"
|
103
|
+
end
|
104
|
+
end
|
105
|
+
end
|
106
|
+
|
107
|
+
def get_flowdock_api_url(path)
|
108
|
+
"#{FLOWDOCK_API_URL}/#{path}/#{@api_token}"
|
63
109
|
end
|
64
110
|
end
|
65
111
|
end
|
data/lib/flowdock/capistrano.rb
CHANGED
@@ -1,5 +1,4 @@
|
|
1
1
|
require 'flowdock'
|
2
|
-
require 'grit'
|
3
2
|
require 'digest/md5'
|
4
3
|
require 'cgi'
|
5
4
|
|
@@ -15,17 +14,20 @@ Capistrano::Configuration.instance(:must_exist).load do
|
|
15
14
|
begin
|
16
15
|
run "echo '#{source.head}' > #{current_path}/BRANCH"
|
17
16
|
rescue => e
|
18
|
-
puts "Flowdock: error in saving deployed branch information: "
|
17
|
+
puts "Flowdock: error in saving deployed branch information: #{e.to_s}"
|
19
18
|
end
|
20
19
|
end
|
21
20
|
|
22
21
|
task :set_flowdock_api do
|
23
22
|
set :rails_env, variables.include?(:stage) ? stage : ENV['RAILS_ENV']
|
24
23
|
begin
|
24
|
+
require 'grit'
|
25
25
|
set :repo, Grit::Repo.new(".")
|
26
26
|
config = Grit::Config.new(repo)
|
27
|
+
rescue LoadError
|
28
|
+
puts "Flowdock: you need to have Grit gem installed: #{e.to_s}"
|
27
29
|
rescue => e
|
28
|
-
puts "Flowdock: error in fetching your git repository information: "
|
30
|
+
puts "Flowdock: error in fetching your git repository information: #{e.to_s}"
|
29
31
|
end
|
30
32
|
|
31
33
|
begin
|
@@ -33,19 +35,19 @@ Capistrano::Configuration.instance(:must_exist).load do
|
|
33
35
|
:source => "Capistrano deployment", :project => flowdock_project_name,
|
34
36
|
:from => {:name => config["user.name"], :address => config["user.email"]})
|
35
37
|
rescue => e
|
36
|
-
puts "Flowdock: error in configuring Flowdock API: "
|
38
|
+
puts "Flowdock: error in configuring Flowdock API: #{e.to_s}"
|
37
39
|
end
|
38
40
|
end
|
39
41
|
|
40
42
|
task :notify_deploy_finished do
|
41
43
|
# send message to the flow
|
42
44
|
begin
|
43
|
-
flowdock_api.
|
45
|
+
flowdock_api.push_to_team_inbox(:format => "html",
|
44
46
|
:subject => "#{flowdock_project_name} deployed with branch #{branch} on ##{rails_env}",
|
45
47
|
:content => notification_message,
|
46
48
|
:tags => ["deploy", "#{rails_env}"] | flowdock_deploy_tags)
|
47
49
|
rescue => e
|
48
|
-
puts "Flowdock: error in sending notification to your flow: "
|
50
|
+
puts "Flowdock: error in sending notification to your flow: #{e.to_s}"
|
49
51
|
end
|
50
52
|
end
|
51
53
|
|
data/spec/flowdock_spec.rb
CHANGED
@@ -2,88 +2,132 @@ require 'spec_helper'
|
|
2
2
|
|
3
3
|
describe Flowdock do
|
4
4
|
describe "with initializing flow" do
|
5
|
-
it "should succeed with correct token
|
5
|
+
it "should succeed with correct token" do
|
6
6
|
lambda {
|
7
|
-
@flow = Flowdock::Flow.new(:api_token => "test"
|
7
|
+
@flow = Flowdock::Flow.new(:api_token => "test")
|
8
8
|
}.should_not raise_error
|
9
9
|
end
|
10
10
|
|
11
|
-
it "should
|
11
|
+
it "should fail without token" do
|
12
12
|
lambda {
|
13
|
-
@flow = Flowdock::Flow.new(:api_token => "
|
14
|
-
|
15
|
-
}.should_not raise_error
|
13
|
+
@flow = Flowdock::Flow.new(:api_token => "")
|
14
|
+
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
16
15
|
end
|
16
|
+
end
|
17
17
|
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
18
|
+
describe "with sending Team Inbox messages" do
|
19
|
+
before(:each) do
|
20
|
+
@token = "test"
|
21
|
+
@flow_attributes = {:api_token => @token, :source => "myapp", :project => "myproject",
|
22
|
+
:from => {:name => "Eric Example", :address => "eric@example.com"}}
|
23
|
+
@flow = Flowdock::Flow.new(@flow_attributes)
|
24
|
+
@example_content = "<h1>Hello</h1>\n<p>Let's rock and roll!</p>"
|
25
|
+
@valid_attributes = {:subject => "Hello World", :content => @example_content,
|
26
|
+
:link => "http://www.flowdock.com/", :tags => ["cool", "stuff"]}
|
23
27
|
end
|
24
28
|
|
25
|
-
it "should
|
29
|
+
it "should not send without source" do
|
26
30
|
lambda {
|
27
|
-
@flow = Flowdock::Flow.new(:
|
28
|
-
|
29
|
-
}.
|
31
|
+
@flow = Flowdock::Flow.new(@flow_attributes.merge(:source => ""))
|
32
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
33
|
+
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
30
34
|
end
|
31
35
|
|
32
|
-
it "should
|
36
|
+
it "should not send when source is not alphanumeric" do
|
33
37
|
lambda {
|
34
|
-
@flow = Flowdock::Flow.new(:
|
38
|
+
@flow = Flowdock::Flow.new(@flow_attributes.merge(:source => "$foobar"))
|
39
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
35
40
|
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
36
41
|
end
|
37
42
|
|
38
|
-
it "should
|
43
|
+
it "should not send when project is not alphanumeric" do
|
39
44
|
lambda {
|
40
|
-
@flow = Flowdock::Flow.new(:api_token => "test", :source => "")
|
45
|
+
@flow = Flowdock::Flow.new(:api_token => "test", :source => "myapp", :project => "$foobar")
|
46
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
41
47
|
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
42
48
|
end
|
43
49
|
|
44
|
-
it "should
|
50
|
+
it "should not send without sender information" do
|
45
51
|
lambda {
|
46
|
-
@flow = Flowdock::Flow.new(:
|
52
|
+
@flow = Flowdock::Flow.new(@flow_attributes.merge(:from => nil))
|
53
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
47
54
|
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
48
55
|
end
|
49
56
|
|
50
|
-
it "should
|
57
|
+
it "should not send without subject" do
|
51
58
|
lambda {
|
52
|
-
@flow
|
59
|
+
@flow.push_to_team_inbox(@valid_attributes.merge(:subject => ""))
|
53
60
|
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
54
61
|
end
|
55
|
-
end
|
56
62
|
|
57
|
-
|
58
|
-
|
59
|
-
|
60
|
-
|
61
|
-
:from => {:name => "Eric Example", :address => "eric@example.com"})
|
62
|
-
@example_content = "<h1>Hello</h1>\n<p>Let's rock and roll!</p>"
|
63
|
+
it "should not send without content" do
|
64
|
+
lambda {
|
65
|
+
@flow.push_to_team_inbox(@valid_attributes.merge(:content => ""))
|
66
|
+
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
63
67
|
end
|
64
68
|
|
65
|
-
it "should
|
69
|
+
it "should succeed with correct token, source and sender information" do
|
66
70
|
lambda {
|
67
|
-
|
68
|
-
|
71
|
+
stub_request(:post, push_to_team_inbox_url(@token)).
|
72
|
+
with(:body => {
|
73
|
+
:source => "myapp",
|
74
|
+
:format => "html",
|
75
|
+
:from_name => "Eric Example",
|
76
|
+
:from_address => "eric@example.com",
|
77
|
+
:subject => "Hello World",
|
78
|
+
:content => @example_content,
|
79
|
+
:tags => "cool,stuff",
|
80
|
+
:link => "http://www.flowdock.com/"
|
81
|
+
}).
|
82
|
+
to_return(:body => "", :status => 200)
|
83
|
+
|
84
|
+
@flow = Flowdock::Flow.new(@flow_attributes.merge(:project => ""))
|
85
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
86
|
+
}.should_not raise_error
|
69
87
|
end
|
70
88
|
|
71
|
-
it "should
|
89
|
+
it "should succeed without the optional from-name parameter" do
|
72
90
|
lambda {
|
73
|
-
|
74
|
-
|
91
|
+
stub_request(:post, push_to_team_inbox_url(@token)).
|
92
|
+
with(:body => {
|
93
|
+
:source => "myapp",
|
94
|
+
:project => "myproject",
|
95
|
+
:format => "html",
|
96
|
+
:from_address => "eric@example.com",
|
97
|
+
:subject => "Hello World",
|
98
|
+
:content => @example_content,
|
99
|
+
:tags => "cool,stuff",
|
100
|
+
:link => "http://www.flowdock.com/"
|
101
|
+
}).
|
102
|
+
to_return(:body => "", :status => 200)
|
103
|
+
@flow = Flowdock::Flow.new(@flow_attributes.merge(:from => {:address => "eric@example.com"}))
|
104
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
105
|
+
}.should_not raise_error
|
75
106
|
end
|
76
107
|
|
77
|
-
it "should
|
78
|
-
@flow = Flowdock::Flow.new(:api_token => @token, :source => "myapp")
|
108
|
+
it "should succeed with correct token, sender information, source and project" do
|
79
109
|
lambda {
|
80
|
-
|
81
|
-
|
110
|
+
stub_request(:post, push_to_team_inbox_url(@token)).
|
111
|
+
with(:body => {
|
112
|
+
:source => "myapp",
|
113
|
+
:project => "myproject",
|
114
|
+
:format => "html",
|
115
|
+
:from_name => "Eric Example",
|
116
|
+
:from_address => "eric@example.com",
|
117
|
+
:subject => "Hello World",
|
118
|
+
:content => @example_content,
|
119
|
+
:tags => "cool,stuff",
|
120
|
+
:link => "http://www.flowdock.com/"
|
121
|
+
}).
|
122
|
+
to_return(:body => "", :status => 200)
|
123
|
+
@flow = Flowdock::Flow.new(@flow_attributes)
|
124
|
+
@flow.push_to_team_inbox(@valid_attributes)
|
125
|
+
}.should_not raise_error
|
82
126
|
end
|
83
127
|
|
84
128
|
it "should send with valid parameters and return true" do
|
85
129
|
lambda {
|
86
|
-
stub_request(:post,
|
130
|
+
stub_request(:post, push_to_team_inbox_url(@token)).
|
87
131
|
with(:body => {
|
88
132
|
:source => "myapp",
|
89
133
|
:project => "myproject",
|
@@ -97,14 +141,14 @@ describe Flowdock do
|
|
97
141
|
}).
|
98
142
|
to_return(:body => "", :status => 200)
|
99
143
|
|
100
|
-
@flow.
|
144
|
+
@flow.push_to_team_inbox(:subject => "Hello World", :content => @example_content,
|
101
145
|
:tags => ["cool", "stuff"], :link => "http://www.flowdock.com/").should be_true
|
102
146
|
}.should_not raise_error
|
103
147
|
end
|
104
148
|
|
105
149
|
it "should allow overriding sender information per message" do
|
106
150
|
lambda {
|
107
|
-
stub_request(:post,
|
151
|
+
stub_request(:post, push_to_team_inbox_url(@token)).
|
108
152
|
with(:body => {
|
109
153
|
:source => "myapp",
|
110
154
|
:project => "myproject",
|
@@ -117,14 +161,14 @@ describe Flowdock do
|
|
117
161
|
}).
|
118
162
|
to_return(:body => "", :status => 200)
|
119
163
|
|
120
|
-
@flow.
|
164
|
+
@flow.push_to_team_inbox(:subject => "Hello World", :content => @example_content, :tags => ["cool", "stuff"],
|
121
165
|
:from => {:name => "Test", :address => "invalid@nodeta.fi"}).should be_true
|
122
166
|
}.should_not raise_error
|
123
167
|
end
|
124
168
|
|
125
169
|
it "should raise error if backend returns anything but 200 OK" do
|
126
170
|
lambda {
|
127
|
-
stub_request(:post,
|
171
|
+
stub_request(:post, push_to_team_inbox_url(@token)).
|
128
172
|
with(:body => {
|
129
173
|
:source => "myapp",
|
130
174
|
:project => "myproject",
|
@@ -136,8 +180,85 @@ describe Flowdock do
|
|
136
180
|
}).
|
137
181
|
to_return(:body => "Internal Server Error", :status => 500)
|
138
182
|
|
139
|
-
@flow.
|
183
|
+
@flow.push_to_team_inbox(:subject => "Hello World", :content => @example_content).should be_false
|
184
|
+
}.should raise_error(Flowdock::Flow::ApiError)
|
185
|
+
end
|
186
|
+
end
|
187
|
+
|
188
|
+
describe "with sending Chat messages" do
|
189
|
+
before(:each) do
|
190
|
+
@token = "test"
|
191
|
+
@flow = Flowdock::Flow.new(:api_token => @token)
|
192
|
+
@valid_parameters = {:external_user_name => "foobar", :content => "Hello", :tags => ["cool","stuff"]}
|
193
|
+
end
|
194
|
+
|
195
|
+
it "should not send without content" do
|
196
|
+
lambda {
|
197
|
+
@flow.push_to_chat(@valid_parameters.merge(:content => ""))
|
198
|
+
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
199
|
+
end
|
200
|
+
|
201
|
+
it "should not send without external_user_name" do
|
202
|
+
lambda {
|
203
|
+
@flow.push_to_chat(@valid_parameters.merge(:external_user_name => ""))
|
204
|
+
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
205
|
+
end
|
206
|
+
|
207
|
+
it "should not send with invalid external_user_name" do
|
208
|
+
lambda {
|
209
|
+
@flow.push_to_chat(@valid_parameters.merge(:external_user_name => "foo bar"))
|
210
|
+
}.should raise_error(Flowdock::Flow::InvalidParameterError)
|
211
|
+
end
|
212
|
+
|
213
|
+
it "should send with valid parameters and return true" do
|
214
|
+
lambda {
|
215
|
+
stub_request(:post, push_to_chat_url(@token)).
|
216
|
+
with(:body => @valid_parameters.merge(:tags => "cool,stuff")).
|
217
|
+
to_return(:body => "", :status => 200)
|
218
|
+
|
219
|
+
@flow.push_to_chat(@valid_parameters).should be_true
|
220
|
+
}.should_not raise_error
|
221
|
+
end
|
222
|
+
|
223
|
+
it "should accept external_user_name in init" do
|
224
|
+
lambda {
|
225
|
+
stub_request(:post, push_to_chat_url(@token)).
|
226
|
+
with(:body => @valid_parameters.merge(:tags => "cool,stuff", :external_user_name => "foobar2")).
|
227
|
+
to_return(:body => "", :status => 200)
|
228
|
+
|
229
|
+
@flow = Flowdock::Flow.new(:api_token => @token, :external_user_name => "foobar")
|
230
|
+
@flow.push_to_chat(@valid_parameters.merge(:external_user_name => "foobar2"))
|
231
|
+
}.should_not raise_error
|
232
|
+
end
|
233
|
+
|
234
|
+
it "should allow overriding external_user_name" do
|
235
|
+
lambda {
|
236
|
+
stub_request(:post, push_to_chat_url(@token)).
|
237
|
+
with(:body => @valid_parameters.merge(:tags => "cool,stuff")).
|
238
|
+
to_return(:body => "", :status => 200)
|
239
|
+
|
240
|
+
@flow = Flowdock::Flow.new(:api_token => @token, :external_user_name => "foobar")
|
241
|
+
@flow.push_to_chat(@valid_parameters.merge(:external_user_name => ""))
|
242
|
+
}.should_not raise_error
|
243
|
+
end
|
244
|
+
|
245
|
+
it "should raise error if backend returns anything but 200 OK" do
|
246
|
+
lambda {
|
247
|
+
stub_request(:post, push_to_chat_url(@token)).
|
248
|
+
with(:body => @valid_parameters.merge(:tags => "cool,stuff")).
|
249
|
+
to_return(:body => '{"message":"Validation error","errors":{"content":["can\'t be blank"],"external_user_name":["should not contain whitespace"]}}',
|
250
|
+
:status => 400)
|
251
|
+
|
252
|
+
@flow.push_to_chat(@valid_parameters).should be_false
|
140
253
|
}.should raise_error(Flowdock::Flow::ApiError)
|
141
254
|
end
|
142
255
|
end
|
256
|
+
|
257
|
+
def push_to_chat_url(token)
|
258
|
+
"#{Flowdock::FLOWDOCK_API_URL}/messages/chat/#{token}"
|
259
|
+
end
|
260
|
+
|
261
|
+
def push_to_team_inbox_url(token)
|
262
|
+
"#{Flowdock::FLOWDOCK_API_URL}/messages/team_inbox/#{token}"
|
263
|
+
end
|
143
264
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: flowdock
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,11 +9,11 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-
|
12
|
+
date: 2012-02-20 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: httparty
|
16
|
-
requirement: &
|
16
|
+
requirement: &70199262290500 !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ~>
|
@@ -21,10 +21,21 @@ dependencies:
|
|
21
21
|
version: '0.7'
|
22
22
|
type: :runtime
|
23
23
|
prerelease: false
|
24
|
-
version_requirements: *
|
24
|
+
version_requirements: *70199262290500
|
25
|
+
- !ruby/object:Gem::Dependency
|
26
|
+
name: multi_json
|
27
|
+
requirement: &70199262289920 !ruby/object:Gem::Requirement
|
28
|
+
none: false
|
29
|
+
requirements:
|
30
|
+
- - ! '>='
|
31
|
+
- !ruby/object:Gem::Version
|
32
|
+
version: '0'
|
33
|
+
type: :runtime
|
34
|
+
prerelease: false
|
35
|
+
version_requirements: *70199262289920
|
25
36
|
- !ruby/object:Gem::Dependency
|
26
37
|
name: rdoc
|
27
|
-
requirement: &
|
38
|
+
requirement: &70199262289140 !ruby/object:Gem::Requirement
|
28
39
|
none: false
|
29
40
|
requirements:
|
30
41
|
- - ! '>='
|
@@ -32,10 +43,10 @@ dependencies:
|
|
32
43
|
version: 2.4.2
|
33
44
|
type: :development
|
34
45
|
prerelease: false
|
35
|
-
version_requirements: *
|
46
|
+
version_requirements: *70199262289140
|
36
47
|
- !ruby/object:Gem::Dependency
|
37
48
|
name: rspec
|
38
|
-
requirement: &
|
49
|
+
requirement: &70199262287920 !ruby/object:Gem::Requirement
|
39
50
|
none: false
|
40
51
|
requirements:
|
41
52
|
- - ~>
|
@@ -43,10 +54,10 @@ dependencies:
|
|
43
54
|
version: '2.6'
|
44
55
|
type: :development
|
45
56
|
prerelease: false
|
46
|
-
version_requirements: *
|
57
|
+
version_requirements: *70199262287920
|
47
58
|
- !ruby/object:Gem::Dependency
|
48
59
|
name: webmock
|
49
|
-
requirement: &
|
60
|
+
requirement: &70199262287340 !ruby/object:Gem::Requirement
|
50
61
|
none: false
|
51
62
|
requirements:
|
52
63
|
- - ! '>='
|
@@ -54,10 +65,10 @@ dependencies:
|
|
54
65
|
version: '0'
|
55
66
|
type: :development
|
56
67
|
prerelease: false
|
57
|
-
version_requirements: *
|
68
|
+
version_requirements: *70199262287340
|
58
69
|
- !ruby/object:Gem::Dependency
|
59
70
|
name: bundler
|
60
|
-
requirement: &
|
71
|
+
requirement: &70199262286580 !ruby/object:Gem::Requirement
|
61
72
|
none: false
|
62
73
|
requirements:
|
63
74
|
- - ~>
|
@@ -65,10 +76,10 @@ dependencies:
|
|
65
76
|
version: '1.0'
|
66
77
|
type: :development
|
67
78
|
prerelease: false
|
68
|
-
version_requirements: *
|
79
|
+
version_requirements: *70199262286580
|
69
80
|
- !ruby/object:Gem::Dependency
|
70
81
|
name: jeweler
|
71
|
-
requirement: &
|
82
|
+
requirement: &70199262285720 !ruby/object:Gem::Requirement
|
72
83
|
none: false
|
73
84
|
requirements:
|
74
85
|
- - ~>
|
@@ -76,10 +87,10 @@ dependencies:
|
|
76
87
|
version: 1.6.4
|
77
88
|
type: :development
|
78
89
|
prerelease: false
|
79
|
-
version_requirements: *
|
90
|
+
version_requirements: *70199262285720
|
80
91
|
- !ruby/object:Gem::Dependency
|
81
92
|
name: jruby-openssl
|
82
|
-
requirement: &
|
93
|
+
requirement: &70199262285140 !ruby/object:Gem::Requirement
|
83
94
|
none: false
|
84
95
|
requirements:
|
85
96
|
- - ! '>='
|
@@ -87,19 +98,20 @@ dependencies:
|
|
87
98
|
version: '0'
|
88
99
|
type: :development
|
89
100
|
prerelease: false
|
90
|
-
version_requirements: *
|
101
|
+
version_requirements: *70199262285140
|
91
102
|
description:
|
92
103
|
email: team@flowdock.com
|
93
104
|
executables: []
|
94
105
|
extensions: []
|
95
106
|
extra_rdoc_files:
|
107
|
+
- LICENSE
|
96
108
|
- README.md
|
97
109
|
files:
|
98
110
|
- .document
|
99
111
|
- .rspec
|
100
112
|
- .travis.yml
|
101
113
|
- Gemfile
|
102
|
-
-
|
114
|
+
- LICENSE
|
103
115
|
- README.md
|
104
116
|
- Rakefile
|
105
117
|
- VERSION
|
@@ -123,7 +135,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
123
135
|
version: '0'
|
124
136
|
segments:
|
125
137
|
- 0
|
126
|
-
hash: -
|
138
|
+
hash: -726909784894414112
|
127
139
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
128
140
|
none: false
|
129
141
|
requirements:
|