harvested 1.0.1 → 1.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +15 -0
- data/.ruby-version +1 -1
- data/HISTORY +5 -0
- data/README.md +0 -5
- data/VERSION +1 -1
- data/harvested.gemspec +8 -5
- data/lib/harvest/api/projects.rb +8 -0
- data/lib/harvest/api/time.rb +19 -3
- data/lib/harvest/errors.rb +4 -2
- data/lib/harvest/trackable_project.rb +38 -0
- data/lib/harvested.rb +1 -1
- data/spec/functional/account_spec.rb +1 -1
- data/spec/functional/invoice_spec.rb +4 -4
- data/spec/functional/tasks_spec.rb +3 -3
- data/spec/functional/time_tracking_spec.rb +45 -1
- data/spec/functional/users_spec.rb +1 -1
- data/spec/harvest/trackable_project_spec.rb +8 -0
- data/spec/support/harvested_helpers.rb +1 -1
- metadata +16 -38
checksums.yaml
ADDED
@@ -0,0 +1,15 @@
|
|
1
|
+
---
|
2
|
+
!binary "U0hBMQ==":
|
3
|
+
metadata.gz: !binary |-
|
4
|
+
MGIyYjlkMDdjZWI1MTRlMjZlZTk2MmI1OWVjNGY2ZDkxNDAyMTZjZg==
|
5
|
+
data.tar.gz: !binary |-
|
6
|
+
MDliY2MxNTEwMjFhZmE4NGZhMDJmYzhlNTBjM2JhYzU0MTAxMzAwZA==
|
7
|
+
SHA512:
|
8
|
+
metadata.gz: !binary |-
|
9
|
+
NGM1NmJkOWVmNTVkNTRlMmFjMjY1ZjBkMWY4YzQ4YmNkYzU3M2FlY2JhZGY1
|
10
|
+
ZmVkNWRiMGU5YjI5NmJkZDZiMjk3Yjk1MjFhZmI3ZTVkZTQ0ZTFlZWNjNmVm
|
11
|
+
MGUyZTU5OGNjMGU2MmFiMzBjNTg4NWVmNDA4YjQ4ZGNiMWIyYTA=
|
12
|
+
data.tar.gz: !binary |-
|
13
|
+
MjU1NmUxMTY0M2I4OTgxOThlMzEwMDJkODdlMDQ2NmNhMDBhMWU5Njg4MjEw
|
14
|
+
YTg4MjFhZGE3OGYyNDE2NGViZTczNTZjMzA3N2ExZWU1MDQ4NWY0OWViOTFh
|
15
|
+
NDk4MDQ3NTRkNWQxZDU1M2JlNmZlZDQ3Yjg2NmE3NGExNmZhYjE=
|
data/.ruby-version
CHANGED
@@ -1 +1 @@
|
|
1
|
-
1.9.3
|
1
|
+
1.9.3
|
data/HISTORY
CHANGED
@@ -1,3 +1,8 @@
|
|
1
|
+
1.2.0 - February 21, 2014
|
2
|
+
* Adds time.trackable_projects: projects that the current user can create entries for
|
3
|
+
* Show hint on error for projects.all as unprivileged user
|
4
|
+
1.1.0 - December 13, 2013
|
5
|
+
* Adds ability to toggle timers (thanks Eli Fatsi - @efatsi)
|
1
6
|
1.0.1 - June 21, 2013
|
2
7
|
* Adds ability to pass updated_since paramter to report methods (thanks Pete McWilliams)
|
3
8
|
* Adds ability to create time entries for a given user
|
data/README.md
CHANGED
@@ -87,11 +87,6 @@ Using [rvm](https://rvm.beginrescueend.com/) you can run the tests against the p
|
|
87
87
|
|
88
88
|
Each runtime needs to be installed in rvm along with the bundler gem.
|
89
89
|
|
90
|
-
## TODO
|
91
|
-
|
92
|
-
* Write Documentation
|
93
|
-
* Allow Timer Toggling
|
94
|
-
|
95
90
|
## Notes on Harvest Estimates
|
96
91
|
|
97
92
|
Estimates aren't currently supported due to lack of an API. If this opens up, harvested will include them.
|
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
1.0
|
1
|
+
1.2.0
|
data/harvested.gemspec
CHANGED
@@ -2,14 +2,16 @@
|
|
2
2
|
# DO NOT EDIT THIS FILE DIRECTLY
|
3
3
|
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
4
|
# -*- encoding: utf-8 -*-
|
5
|
+
# stub: harvested 1.2.0 ruby lib
|
5
6
|
|
6
7
|
Gem::Specification.new do |s|
|
7
8
|
s.name = "harvested"
|
8
|
-
s.version = "1.0
|
9
|
+
s.version = "1.2.0"
|
9
10
|
|
10
11
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
12
|
+
s.require_paths = ["lib"]
|
11
13
|
s.authors = ["Zach Moazeni"]
|
12
|
-
s.date = "
|
14
|
+
s.date = "2014-02-21"
|
13
15
|
s.description = "Harvested wraps the Harvest API concisely without the use of Rails dependencies. More information about the Harvest API can be found on their website (http://www.getharvest.com/api). For support hit up the Mailing List (http://groups.google.com/group/harvested)"
|
14
16
|
s.email = "zach.moazeni@gmail.com"
|
15
17
|
s.extra_rdoc_files = [
|
@@ -73,6 +75,7 @@ Gem::Specification.new do |s|
|
|
73
75
|
"lib/harvest/task_assignment.rb",
|
74
76
|
"lib/harvest/time_entry.rb",
|
75
77
|
"lib/harvest/timezones.rb",
|
78
|
+
"lib/harvest/trackable_project.rb",
|
76
79
|
"lib/harvest/user.rb",
|
77
80
|
"lib/harvest/user_assignment.rb",
|
78
81
|
"lib/harvested.rb",
|
@@ -99,6 +102,7 @@ Gem::Specification.new do |s|
|
|
99
102
|
"spec/harvest/task_assignment_spec.rb",
|
100
103
|
"spec/harvest/task_spec.rb",
|
101
104
|
"spec/harvest/time_entry_spec.rb",
|
105
|
+
"spec/harvest/trackable_project_spec.rb",
|
102
106
|
"spec/harvest/user_assignment_spec.rb",
|
103
107
|
"spec/harvest/user_spec.rb",
|
104
108
|
"spec/spec_helper.rb",
|
@@ -108,12 +112,11 @@ Gem::Specification.new do |s|
|
|
108
112
|
"spec/test_rubies"
|
109
113
|
]
|
110
114
|
s.homepage = "http://github.com/zmoazeni/harvested"
|
111
|
-
s.
|
112
|
-
s.rubygems_version = "1.8.25"
|
115
|
+
s.rubygems_version = "2.2.1"
|
113
116
|
s.summary = "A Ruby Wrapper for the Harvest API http://www.getharvest.com/"
|
114
117
|
|
115
118
|
if s.respond_to? :specification_version then
|
116
|
-
s.specification_version =
|
119
|
+
s.specification_version = 4
|
117
120
|
|
118
121
|
if Gem::Version.new(Gem::VERSION) >= Gem::Version.new('1.2.0') then
|
119
122
|
s.add_runtime_dependency(%q<httparty>, [">= 0"])
|
data/lib/harvest/api/projects.rb
CHANGED
@@ -4,6 +4,14 @@ module Harvest
|
|
4
4
|
api_model Harvest::Project
|
5
5
|
|
6
6
|
include Harvest::Behavior::Crud
|
7
|
+
|
8
|
+
# Retrieves all projects. Note: this requires project manager or administrator authorization.
|
9
|
+
# @return [Harvest::Project]
|
10
|
+
def all(*)
|
11
|
+
super
|
12
|
+
rescue NotFound => e
|
13
|
+
raise NotFound.new(e.response, e.params, "Do you have sufficient priveleges? If not, consider using time.trackable_projects instead.")
|
14
|
+
end
|
7
15
|
|
8
16
|
# Creates and Assigns a task to the project
|
9
17
|
#
|
data/lib/harvest/api/time.rb
CHANGED
@@ -8,11 +8,18 @@ module Harvest
|
|
8
8
|
end
|
9
9
|
|
10
10
|
def all(date = ::Time.now, user = nil)
|
11
|
-
|
12
|
-
|
13
|
-
|
11
|
+
Harvest::TimeEntry.parse(daily(date, user)["day_entries"])
|
12
|
+
end
|
13
|
+
|
14
|
+
def trackable_projects(date = ::Time.now, user = nil)
|
15
|
+
Harvest::TrackableProject.parse(daily(date, user)["projects"])
|
14
16
|
end
|
15
17
|
|
18
|
+
def toggle(id, user = nil)
|
19
|
+
response = request(:get, credentials, "/daily/timer/#{id}", :query => of_user_query(user))
|
20
|
+
Harvest::TimeEntry.parse(response.parsed_response).first
|
21
|
+
end
|
22
|
+
|
16
23
|
def create(entry, user = nil)
|
17
24
|
response = request(:post, credentials, '/daily/add', :body => entry.to_json, :query => of_user_query(user))
|
18
25
|
Harvest::TimeEntry.parse(response.parsed_response).first
|
@@ -27,6 +34,15 @@ module Harvest
|
|
27
34
|
request(:delete, credentials, "/daily/delete/#{entry.to_i}", :query => of_user_query(user))
|
28
35
|
entry.id
|
29
36
|
end
|
37
|
+
|
38
|
+
|
39
|
+
private
|
40
|
+
|
41
|
+
def daily(date, user)
|
42
|
+
date = ::Time.parse(date) if String === date
|
43
|
+
response = request(:get, credentials, "/daily/#{date.yday}/#{date.year}", :query => of_user_query(user))
|
44
|
+
JSON.parse(response.body)
|
45
|
+
end
|
30
46
|
end
|
31
47
|
end
|
32
48
|
end
|
data/lib/harvest/errors.rb
CHANGED
@@ -4,15 +4,17 @@ module Harvest
|
|
4
4
|
class HTTPError < StandardError
|
5
5
|
attr_reader :response
|
6
6
|
attr_reader :params
|
7
|
+
attr_reader :hint
|
7
8
|
|
8
|
-
def initialize(response, params = {})
|
9
|
+
def initialize(response, params = {}, hint = nil)
|
9
10
|
@response = response
|
10
11
|
@params = params
|
12
|
+
@hint = hint
|
11
13
|
super(response)
|
12
14
|
end
|
13
15
|
|
14
16
|
def to_s
|
15
|
-
"#{self.class.to_s} : #{response.code} #{response.body}"
|
17
|
+
"#{self.class.to_s} : #{response.code} #{response.body}" + (hint ? "\n#{hint}" : "")
|
16
18
|
end
|
17
19
|
end
|
18
20
|
|
@@ -0,0 +1,38 @@
|
|
1
|
+
module Harvest
|
2
|
+
|
3
|
+
# The model for project-tasks combinations that can be added to the timesheet
|
4
|
+
#
|
5
|
+
# == Fields
|
6
|
+
# [+id+] the id of the project
|
7
|
+
# [+name+] the name of the project
|
8
|
+
# [+client+] the name of the client of the project
|
9
|
+
# [+client_id+] the client id of the project
|
10
|
+
# [+tasks+] trackable tasks for the project
|
11
|
+
class TrackableProject < Hashie::Mash
|
12
|
+
include Harvest::Model
|
13
|
+
|
14
|
+
skip_json_root true
|
15
|
+
|
16
|
+
def initialize(args = {}, _ = nil)
|
17
|
+
args = args.to_hash.stringify_keys
|
18
|
+
self.tasks = args.delete("tasks") if args["tasks"]
|
19
|
+
super
|
20
|
+
end
|
21
|
+
|
22
|
+
def tasks=(tasks)
|
23
|
+
self["tasks"] = Task.parse(tasks)
|
24
|
+
end
|
25
|
+
|
26
|
+
# The model for trackable tasks
|
27
|
+
#
|
28
|
+
# == Fields
|
29
|
+
# [+id+] the id of the task
|
30
|
+
# [+name+] the name of the task
|
31
|
+
# [+billable+] whether the task is billable by default
|
32
|
+
class Task < Hashie::Mash
|
33
|
+
include Harvest::Model
|
34
|
+
|
35
|
+
skip_json_root true
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
data/lib/harvested.rb
CHANGED
@@ -19,7 +19,7 @@ require 'harvest/timezones'
|
|
19
19
|
require 'harvest/base'
|
20
20
|
|
21
21
|
%w(crud activatable).each {|a| require "harvest/behavior/#{a}"}
|
22
|
-
%w(model client contact project task user rate_limit_status task_assignment user_assignment expense_category expense time_entry invoice_category line_item invoice invoice_payment).each {|a| require "harvest/#{a}"}
|
22
|
+
%w(model client contact project task user rate_limit_status task_assignment user_assignment expense_category expense time_entry invoice_category line_item invoice invoice_payment trackable_project).each {|a| require "harvest/#{a}"}
|
23
23
|
%w(base account clients contacts projects tasks users task_assignments user_assignments expense_categories expenses time reports invoice_categories invoices invoice_payments).each {|a| require "harvest/api/#{a}"}
|
24
24
|
|
25
25
|
module Harvest
|
@@ -23,7 +23,7 @@ describe 'harvest invoices' do
|
|
23
23
|
invoice = harvest.invoices.create(invoice)
|
24
24
|
|
25
25
|
invoice.subject.should == "Invoice for Joe's Stream Cleaning"
|
26
|
-
invoice.amount.should ==
|
26
|
+
invoice.amount.should == 2400.0
|
27
27
|
invoice.line_items.size.should == 1
|
28
28
|
|
29
29
|
invoice.subject = "Updated Invoice for Joe"
|
@@ -31,7 +31,7 @@ describe 'harvest invoices' do
|
|
31
31
|
|
32
32
|
invoice = harvest.invoices.update(invoice)
|
33
33
|
invoice.subject.should == "Updated Invoice for Joe"
|
34
|
-
invoice.amount.should ==
|
34
|
+
invoice.amount.should == 4800.0
|
35
35
|
invoice.line_items.size.should == 2
|
36
36
|
|
37
37
|
harvest.invoices.delete(invoice)
|
@@ -75,13 +75,13 @@ describe 'harvest invoices' do
|
|
75
75
|
invoice = harvest.invoices.create(invoice)
|
76
76
|
|
77
77
|
invoice.subject.should == "Invoice for Frannie's Widgets"
|
78
|
-
invoice.amount.should ==
|
78
|
+
invoice.amount.should == 2400.0
|
79
79
|
invoice.line_items.size.should == 1
|
80
80
|
invoice.due_at.should == "2011-05-31"
|
81
81
|
|
82
82
|
invoice = harvest.invoices.find(invoice.id)
|
83
83
|
invoice.subject.should == "Invoice for Frannie's Widgets"
|
84
|
-
invoice.amount.should ==
|
84
|
+
invoice.amount.should == 2400.0
|
85
85
|
invoice.line_items.size.should == 1
|
86
86
|
|
87
87
|
invoices = harvest.invoices.all
|
@@ -8,11 +8,11 @@ describe 'harvest tasks' do
|
|
8
8
|
"billable_by_default" => true,
|
9
9
|
"default_hourly_rate" => 120
|
10
10
|
)
|
11
|
-
task.default_hourly_rate.should ==
|
11
|
+
task.default_hourly_rate.should == 120.0
|
12
12
|
|
13
13
|
task.default_hourly_rate = 140
|
14
14
|
task = harvest.tasks.update(task)
|
15
|
-
task.default_hourly_rate.should ==
|
15
|
+
task.default_hourly_rate.should == 140.0
|
16
16
|
|
17
17
|
harvest.tasks.delete(task)
|
18
18
|
harvest.tasks.all.select {|t| t.name == "A crud task"}.should == []
|
@@ -53,7 +53,7 @@ describe 'harvest tasks' do
|
|
53
53
|
|
54
54
|
assignment1.hourly_rate = 100
|
55
55
|
assignment1 = harvest.task_assignments.update(assignment1)
|
56
|
-
assignment1.hourly_rate.should ==
|
56
|
+
assignment1.hourly_rate.should == 100.0
|
57
57
|
|
58
58
|
harvest.task_assignments.delete(assignment1)
|
59
59
|
all_assignments = harvest.task_assignments.all(project)
|
@@ -49,5 +49,49 @@ describe 'harvest time tracking' do
|
|
49
49
|
end
|
50
50
|
end
|
51
51
|
|
52
|
-
it 'allows toggling of timers'
|
52
|
+
it 'allows toggling of timers' do
|
53
|
+
cassette("time_tracking3") do
|
54
|
+
client = harvest.clients.create("name" => "Jane's Used Car Shop")
|
55
|
+
project = harvest.projects.create("name" => "Tracking Project", "client_id" => client.id)
|
56
|
+
harvest.projects.create_task(project, "A billable task")
|
57
|
+
task = harvest.tasks.all.detect {|t| t.name == "A billable task"}
|
58
|
+
|
59
|
+
entry = harvest.time.create("notes" => "Test api support", "hours" => 3, "spent_at" => "2009/12/28", "task_id" => task.id, "project_id" => project.id)
|
60
|
+
|
61
|
+
# start existing timer
|
62
|
+
started_entry = harvest.time.toggle(entry.id)
|
63
|
+
started_entry.timer_started_at.should_not be_nil
|
64
|
+
|
65
|
+
# stop started timer
|
66
|
+
stopped_entry = harvest.time.toggle(started_entry.id)
|
67
|
+
stopped_entry.timer_started_at.should be_nil
|
68
|
+
end
|
69
|
+
end
|
70
|
+
|
71
|
+
it 'allows retrieving trackable projects and tasks' do
|
72
|
+
cassette("time_tracking4") do
|
73
|
+
client = harvest.clients.create("name" => "Bobby's Coffee Shop")
|
74
|
+
project = harvest.projects.create("name" => "Bobby's Trackable Project", "client_id" => client.id)
|
75
|
+
harvest.projects.create_task(project, "A billable task for Bobby")
|
76
|
+
|
77
|
+
trackable_projects = harvest.time.trackable_projects
|
78
|
+
trackable_project = trackable_projects.find {|p| p.name == "Bobby's Trackable Project" }
|
79
|
+
trackable_projects.first.client.should == "Bobbys Coffee Shop"
|
80
|
+
trackable_projects.first.tasks.first.name.should == "A billable task for Bobby"
|
81
|
+
end
|
82
|
+
end
|
83
|
+
|
84
|
+
it 'allows for absence of trackable projects' do
|
85
|
+
cassette("time_tracking5") do
|
86
|
+
user = harvest.users.create(
|
87
|
+
"email" => "gary@example.com",
|
88
|
+
"first_name" => "Gary",
|
89
|
+
"last_name" => "Doe",
|
90
|
+
"password" => "secure"
|
91
|
+
)
|
92
|
+
|
93
|
+
trackable_projects = harvest.time.trackable_projects(Time.now, user)
|
94
|
+
trackable_projects.should == []
|
95
|
+
end
|
96
|
+
end
|
53
97
|
end
|
@@ -92,7 +92,7 @@ describe 'harvest users' do
|
|
92
92
|
|
93
93
|
assignment.hourly_rate = 100
|
94
94
|
assignment = harvest.user_assignments.update(assignment)
|
95
|
-
assignment.hourly_rate.should ==
|
95
|
+
assignment.hourly_rate.should == 100.0
|
96
96
|
|
97
97
|
harvest.user_assignments.delete(assignment)
|
98
98
|
all_assignments = harvest.user_assignments.all(project)
|
@@ -37,7 +37,7 @@ module HarvestedHelpers
|
|
37
37
|
# we store expenses on this date in the tests
|
38
38
|
harvest.expenses.all(Time.utc(2009, 12, 28)).each {|e| harvest.expenses.delete(e) }
|
39
39
|
|
40
|
-
%w(expense_categories projects invoices contacts clients tasks).each do |collection|
|
40
|
+
%w(expense_categories time projects invoices contacts clients tasks).each do |collection|
|
41
41
|
harvest.send(collection).all.each {|m| harvest.send(collection).delete(m) }
|
42
42
|
end
|
43
43
|
end
|
metadata
CHANGED
@@ -1,20 +1,19 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: harvested
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version:
|
5
|
-
|
4
|
+
version: !binary |-
|
5
|
+
MS4yLjA=
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
8
8
|
- Zach Moazeni
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date:
|
12
|
+
date: 2014-02-21 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: httparty
|
16
16
|
requirement: !ruby/object:Gem::Requirement
|
17
|
-
none: false
|
18
17
|
requirements:
|
19
18
|
- - ! '>='
|
20
19
|
- !ruby/object:Gem::Version
|
@@ -22,7 +21,6 @@ dependencies:
|
|
22
21
|
type: :runtime
|
23
22
|
prerelease: false
|
24
23
|
version_requirements: !ruby/object:Gem::Requirement
|
25
|
-
none: false
|
26
24
|
requirements:
|
27
25
|
- - ! '>='
|
28
26
|
- !ruby/object:Gem::Version
|
@@ -30,23 +28,22 @@ dependencies:
|
|
30
28
|
- !ruby/object:Gem::Dependency
|
31
29
|
name: hashie
|
32
30
|
requirement: !ruby/object:Gem::Requirement
|
33
|
-
none: false
|
34
31
|
requirements:
|
35
32
|
- - ~>
|
36
33
|
- !ruby/object:Gem::Version
|
37
|
-
version:
|
34
|
+
version: !binary |-
|
35
|
+
MQ==
|
38
36
|
type: :runtime
|
39
37
|
prerelease: false
|
40
38
|
version_requirements: !ruby/object:Gem::Requirement
|
41
|
-
none: false
|
42
39
|
requirements:
|
43
40
|
- - ~>
|
44
41
|
- !ruby/object:Gem::Version
|
45
|
-
version:
|
42
|
+
version: !binary |-
|
43
|
+
MQ==
|
46
44
|
- !ruby/object:Gem::Dependency
|
47
45
|
name: json
|
48
46
|
requirement: !ruby/object:Gem::Requirement
|
49
|
-
none: false
|
50
47
|
requirements:
|
51
48
|
- - ! '>='
|
52
49
|
- !ruby/object:Gem::Version
|
@@ -54,7 +51,6 @@ dependencies:
|
|
54
51
|
type: :runtime
|
55
52
|
prerelease: false
|
56
53
|
version_requirements: !ruby/object:Gem::Requirement
|
57
|
-
none: false
|
58
54
|
requirements:
|
59
55
|
- - ! '>='
|
60
56
|
- !ruby/object:Gem::Version
|
@@ -62,23 +58,22 @@ dependencies:
|
|
62
58
|
- !ruby/object:Gem::Dependency
|
63
59
|
name: rspec
|
64
60
|
requirement: !ruby/object:Gem::Requirement
|
65
|
-
none: false
|
66
61
|
requirements:
|
67
62
|
- - ~>
|
68
63
|
- !ruby/object:Gem::Version
|
69
|
-
version:
|
64
|
+
version: !binary |-
|
65
|
+
Mg==
|
70
66
|
type: :development
|
71
67
|
prerelease: false
|
72
68
|
version_requirements: !ruby/object:Gem::Requirement
|
73
|
-
none: false
|
74
69
|
requirements:
|
75
70
|
- - ~>
|
76
71
|
- !ruby/object:Gem::Version
|
77
|
-
version:
|
72
|
+
version: !binary |-
|
73
|
+
Mg==
|
78
74
|
- !ruby/object:Gem::Dependency
|
79
75
|
name: jruby-openssl
|
80
76
|
requirement: !ruby/object:Gem::Requirement
|
81
|
-
none: false
|
82
77
|
requirements:
|
83
78
|
- - ! '>='
|
84
79
|
- !ruby/object:Gem::Version
|
@@ -86,7 +81,6 @@ dependencies:
|
|
86
81
|
type: :development
|
87
82
|
prerelease: false
|
88
83
|
version_requirements: !ruby/object:Gem::Requirement
|
89
|
-
none: false
|
90
84
|
requirements:
|
91
85
|
- - ! '>='
|
92
86
|
- !ruby/object:Gem::Version
|
@@ -94,7 +88,6 @@ dependencies:
|
|
94
88
|
- !ruby/object:Gem::Dependency
|
95
89
|
name: webmock
|
96
90
|
requirement: !ruby/object:Gem::Requirement
|
97
|
-
none: false
|
98
91
|
requirements:
|
99
92
|
- - ! '>='
|
100
93
|
- !ruby/object:Gem::Version
|
@@ -102,7 +95,6 @@ dependencies:
|
|
102
95
|
type: :development
|
103
96
|
prerelease: false
|
104
97
|
version_requirements: !ruby/object:Gem::Requirement
|
105
|
-
none: false
|
106
98
|
requirements:
|
107
99
|
- - ! '>='
|
108
100
|
- !ruby/object:Gem::Version
|
@@ -110,7 +102,6 @@ dependencies:
|
|
110
102
|
- !ruby/object:Gem::Dependency
|
111
103
|
name: vcr
|
112
104
|
requirement: !ruby/object:Gem::Requirement
|
113
|
-
none: false
|
114
105
|
requirements:
|
115
106
|
- - ! '>='
|
116
107
|
- !ruby/object:Gem::Version
|
@@ -118,7 +109,6 @@ dependencies:
|
|
118
109
|
type: :development
|
119
110
|
prerelease: false
|
120
111
|
version_requirements: !ruby/object:Gem::Requirement
|
121
|
-
none: false
|
122
112
|
requirements:
|
123
113
|
- - ! '>='
|
124
114
|
- !ruby/object:Gem::Version
|
@@ -126,7 +116,6 @@ dependencies:
|
|
126
116
|
- !ruby/object:Gem::Dependency
|
127
117
|
name: jeweler
|
128
118
|
requirement: !ruby/object:Gem::Requirement
|
129
|
-
none: false
|
130
119
|
requirements:
|
131
120
|
- - ! '>='
|
132
121
|
- !ruby/object:Gem::Version
|
@@ -134,7 +123,6 @@ dependencies:
|
|
134
123
|
type: :development
|
135
124
|
prerelease: false
|
136
125
|
version_requirements: !ruby/object:Gem::Requirement
|
137
|
-
none: false
|
138
126
|
requirements:
|
139
127
|
- - ! '>='
|
140
128
|
- !ruby/object:Gem::Version
|
@@ -142,7 +130,6 @@ dependencies:
|
|
142
130
|
- !ruby/object:Gem::Dependency
|
143
131
|
name: debugger
|
144
132
|
requirement: !ruby/object:Gem::Requirement
|
145
|
-
none: false
|
146
133
|
requirements:
|
147
134
|
- - ! '>='
|
148
135
|
- !ruby/object:Gem::Version
|
@@ -150,7 +137,6 @@ dependencies:
|
|
150
137
|
type: :development
|
151
138
|
prerelease: false
|
152
139
|
version_requirements: !ruby/object:Gem::Requirement
|
153
|
-
none: false
|
154
140
|
requirements:
|
155
141
|
- - ! '>='
|
156
142
|
- !ruby/object:Gem::Version
|
@@ -158,7 +144,6 @@ dependencies:
|
|
158
144
|
- !ruby/object:Gem::Dependency
|
159
145
|
name: factory_girl
|
160
146
|
requirement: !ruby/object:Gem::Requirement
|
161
|
-
none: false
|
162
147
|
requirements:
|
163
148
|
- - ! '>='
|
164
149
|
- !ruby/object:Gem::Version
|
@@ -166,7 +151,6 @@ dependencies:
|
|
166
151
|
type: :development
|
167
152
|
prerelease: false
|
168
153
|
version_requirements: !ruby/object:Gem::Requirement
|
169
|
-
none: false
|
170
154
|
requirements:
|
171
155
|
- - ! '>='
|
172
156
|
- !ruby/object:Gem::Version
|
@@ -174,7 +158,6 @@ dependencies:
|
|
174
158
|
- !ruby/object:Gem::Dependency
|
175
159
|
name: yard
|
176
160
|
requirement: !ruby/object:Gem::Requirement
|
177
|
-
none: false
|
178
161
|
requirements:
|
179
162
|
- - ! '>='
|
180
163
|
- !ruby/object:Gem::Version
|
@@ -182,7 +165,6 @@ dependencies:
|
|
182
165
|
type: :development
|
183
166
|
prerelease: false
|
184
167
|
version_requirements: !ruby/object:Gem::Requirement
|
185
|
-
none: false
|
186
168
|
requirements:
|
187
169
|
- - ! '>='
|
188
170
|
- !ruby/object:Gem::Version
|
@@ -190,7 +172,6 @@ dependencies:
|
|
190
172
|
- !ruby/object:Gem::Dependency
|
191
173
|
name: redcarpet
|
192
174
|
requirement: !ruby/object:Gem::Requirement
|
193
|
-
none: false
|
194
175
|
requirements:
|
195
176
|
- - ! '>='
|
196
177
|
- !ruby/object:Gem::Version
|
@@ -198,7 +179,6 @@ dependencies:
|
|
198
179
|
type: :development
|
199
180
|
prerelease: false
|
200
181
|
version_requirements: !ruby/object:Gem::Requirement
|
201
|
-
none: false
|
202
182
|
requirements:
|
203
183
|
- - ! '>='
|
204
184
|
- !ruby/object:Gem::Version
|
@@ -269,6 +249,7 @@ files:
|
|
269
249
|
- lib/harvest/task_assignment.rb
|
270
250
|
- lib/harvest/time_entry.rb
|
271
251
|
- lib/harvest/timezones.rb
|
252
|
+
- lib/harvest/trackable_project.rb
|
272
253
|
- lib/harvest/user.rb
|
273
254
|
- lib/harvest/user_assignment.rb
|
274
255
|
- lib/harvested.rb
|
@@ -295,6 +276,7 @@ files:
|
|
295
276
|
- spec/harvest/task_assignment_spec.rb
|
296
277
|
- spec/harvest/task_spec.rb
|
297
278
|
- spec/harvest/time_entry_spec.rb
|
279
|
+
- spec/harvest/trackable_project_spec.rb
|
298
280
|
- spec/harvest/user_assignment_spec.rb
|
299
281
|
- spec/harvest/user_spec.rb
|
300
282
|
- spec/spec_helper.rb
|
@@ -304,29 +286,25 @@ files:
|
|
304
286
|
- spec/test_rubies
|
305
287
|
homepage: http://github.com/zmoazeni/harvested
|
306
288
|
licenses: []
|
289
|
+
metadata: {}
|
307
290
|
post_install_message:
|
308
291
|
rdoc_options: []
|
309
292
|
require_paths:
|
310
293
|
- lib
|
311
294
|
required_ruby_version: !ruby/object:Gem::Requirement
|
312
|
-
none: false
|
313
295
|
requirements:
|
314
296
|
- - ! '>='
|
315
297
|
- !ruby/object:Gem::Version
|
316
298
|
version: '0'
|
317
|
-
segments:
|
318
|
-
- 0
|
319
|
-
hash: -4545923220079875304
|
320
299
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
321
|
-
none: false
|
322
300
|
requirements:
|
323
301
|
- - ! '>='
|
324
302
|
- !ruby/object:Gem::Version
|
325
303
|
version: '0'
|
326
304
|
requirements: []
|
327
305
|
rubyforge_project:
|
328
|
-
rubygems_version:
|
306
|
+
rubygems_version: 2.2.1
|
329
307
|
signing_key:
|
330
|
-
specification_version:
|
308
|
+
specification_version: 4
|
331
309
|
summary: A Ruby Wrapper for the Harvest API http://www.getharvest.com/
|
332
310
|
test_files: []
|