erp_work_effort 4.0.0 → 4.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (84) hide show
  1. checksums.yaml +4 -4
  2. data/app/controllers/api/v1/projects_controller.rb +25 -0
  3. data/app/controllers/api/v1/time_entries_controller.rb +313 -0
  4. data/app/controllers/api/v1/transportation_routes_controller.rb +9 -0
  5. data/app/controllers/api/v1/work_effort_associations_controller.rb +102 -0
  6. data/app/controllers/api/v1/work_effort_party_assignments_controller.rb +136 -0
  7. data/app/controllers/api/v1/work_effort_types_controller.rb +120 -0
  8. data/app/controllers/api/v1/work_efforts_controller.rb +284 -0
  9. data/app/models/associated_transportation_route.rb +8 -5
  10. data/app/models/cal_evt_party_role.rb +9 -0
  11. data/app/models/calendar_event.rb +46 -0
  12. data/app/models/calendar_invite.rb +10 -0
  13. data/app/models/candidate_submission.rb +37 -0
  14. data/app/models/experience.rb +11 -0
  15. data/app/models/extensions/biz_txn_events.rb +35 -0
  16. data/app/models/extensions/finacial_txns.rb +27 -0
  17. data/app/models/extensions/order_line_item.rb +12 -0
  18. data/app/models/extensions/party.rb +204 -0
  19. data/app/models/party_skill.rb +2 -0
  20. data/app/models/pay_period.rb +59 -0
  21. data/app/models/position.rb +8 -0
  22. data/app/models/position_fulfillment.rb +8 -0
  23. data/app/models/position_type.rb +12 -0
  24. data/app/models/project.rb +59 -0
  25. data/app/models/requirement.rb +2 -0
  26. data/app/models/resume.rb +11 -0
  27. data/app/models/shift.rb +22 -0
  28. data/app/models/skill_type.rb +8 -0
  29. data/app/models/staffing_position.rb +9 -0
  30. data/app/models/time_entry.rb +260 -0
  31. data/app/models/timesheet.rb +194 -0
  32. data/app/models/timesheet_party_role.rb +21 -0
  33. data/app/models/transportation_route.rb +103 -18
  34. data/app/models/transportation_route_segment.rb +44 -0
  35. data/app/models/transportation_route_stop.rb +19 -0
  36. data/app/models/wc_code.rb +7 -0
  37. data/app/models/work_effort.rb +512 -30
  38. data/app/models/work_effort_association.rb +7 -0
  39. data/app/models/work_effort_association_type.rb +5 -0
  40. data/app/models/work_effort_biz_txn_event.rb +22 -0
  41. data/app/models/work_effort_party_assignment.rb +140 -3
  42. data/app/models/work_effort_type.rb +5 -0
  43. data/config/routes.rb +54 -11
  44. data/db/data_migrations/20150709053041_add_skill_types.rb +27 -0
  45. data/db/data_migrations/20150709055922_add_position_types.rb +27 -0
  46. data/db/data_migrations/20150711220000_add_task_tracked_statuses.rb +25 -0
  47. data/db/data_migrations/20150712081804_add_work_effort_types.rb +23 -0
  48. data/db/data_migrations/20150718052204_add_project_tracked_statuses.rb +24 -0
  49. data/db/data_migrations/20150718054404_add_project_party_role_types.rb +14 -0
  50. data/db/data_migrations/20150812150320_add_work_effort_dependency_types.rb +35 -0
  51. data/db/migrate/20100220000000_base_work_efforts.rb +310 -89
  52. data/db/migrate/20150227174108_create_staffing_positions.rb +11 -0
  53. data/db/migrate/20150305194158_create_wc_codes.rb +24 -0
  54. data/db/migrate/20150313134411_create_shifts.rb +28 -0
  55. data/db/migrate/20150325195749_create_candidate_submissions.rb +22 -0
  56. data/db/migrate/20150327115910_resumes.rb +15 -0
  57. data/db/migrate/20150401060938_add_resume_parser_statuses.rb +14 -0
  58. data/db/migrate/20150607181734_create_calendar_events.rb +24 -0
  59. data/db/migrate/20150616174228_create_cal_evt_party_roles.rb +19 -0
  60. data/db/migrate/20150707164520_create_calendar_invites.rb +21 -0
  61. data/db/migrate/20150718052404_create_projects.rb +20 -0
  62. data/db/migrate/20150812191812_update_work_efforts.rb +59 -0
  63. data/db/migrate/20150824152639_add_sequence_to_work_effort.rb +9 -0
  64. data/db/migrate/20150830133951_add_work_effort_biz_txn_events.rb +21 -0
  65. data/db/migrate/20150908200612_update_time_entries.rb +70 -0
  66. data/db/migrate/20151115180427_add_defaults_for_work_effort.rb +36 -0
  67. data/db/migrate/20151218195330_update_transportation_routes.rb +72 -0
  68. data/db/migrate/20160310163052_add_created_by_updated_by_to_erp_work_effort.rb +63 -0
  69. data/db/migrate/20160418115227_add_created_by_updated_by_to_skill_type.rb +34 -0
  70. data/lib/erp_work_effort.rb +3 -0
  71. data/lib/erp_work_effort/config.rb +33 -0
  72. data/lib/erp_work_effort/engine.rb +0 -4
  73. data/lib/erp_work_effort/services/unit_converter.rb +284 -0
  74. data/lib/erp_work_effort/version.rb +1 -1
  75. data/lib/tasks/populate_model_data.rake +19 -0
  76. data/lib/tasks/resume_parser.rake +18 -0
  77. metadata +80 -16
  78. data/app/controllers/erp_work_effort/erp_app/organizer/tasks/base_controller.rb +0 -13
  79. data/app/controllers/erp_work_effort/erp_app/organizer/tasks/work_efforts_controller.rb +0 -128
  80. data/db/data_migrations/20131213151309_create_tasks_organizer_application.rb +0 -14
  81. data/db/migrate/20130829153419_base_routes.rb +0 -93
  82. data/db/migrate/20131213140617_add_work_effort_role_assignments.rb +0 -16
  83. data/db/migrate/20131213144223_add_work_item_to_work_effort.rb +0 -8
  84. data/db/migrate/20140106184615_update_work_effort_item_id_to_int.rb +0 -27
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: ad5d23963efb2e5067ac139ef8d7886811a058d1
4
- data.tar.gz: 0d51e61b9b9b83fe5d6080a4a543cffa27bc9c8f
3
+ metadata.gz: b58acc4d8a198a71e9c42ac9daa6b9d977aa5fef
4
+ data.tar.gz: f7b3fb86a17d31ac9b3dde1e428140c5e2ec1449
5
5
  SHA512:
6
- metadata.gz: 7f7a8b18fa29c8584836be2c62a412575163c2ea82acb3d9c8d5106a507efbe704c32ae7b46968949fbbcd765fc7235ab3f5e08ac41fb8a759655cda9a1ad0e3
7
- data.tar.gz: d775e88305f33b49f9e54e0520638cf70b6bc408606f89acb994449f0204c55e6eaaf8260c3df506540434270c1bf2e6069e5e0dbc542a54f39fd52958d769f6
6
+ metadata.gz: c132f84cd49fa0c36acd5b11731e542007f7f9dc2bee440a685d91753b35210cd7a78a7d23fd8b7cccb8695d91d27bd126805465accbfa0e751bb7d8bae9c9b9
7
+ data.tar.gz: b9789ee3069d3201144cce1a6419ad7ec2c287475d22fa8f0f7cc8b105c156ede8b98022f40692a2534ba10c254456f9414ac3dba3bdc896652e46f6bed27ba6
@@ -0,0 +1,25 @@
1
+ module Api
2
+ module V1
3
+ class ProjectsController < BaseController
4
+
5
+ def index
6
+ # check if we are scoping by current user
7
+ if params[:scope_by_user].present? and params[:scope_by_user].to_bool
8
+ party = current_user.party
9
+ projects = Project.scope_by_party(party,
10
+ {role_types: RoleType.find_child_role_types(party.party_roles.collect { |party_role| party_role.role_type })})
11
+ else
12
+ # scope by dba organization
13
+ projects = Project.scope_by_dba_organization(current_user.party.dba_organization)
14
+ end
15
+
16
+ if params[:query]
17
+ projects = projects.where(projects.arel_table[:description].matches("%#{params[:query]}%"))
18
+ end
19
+
20
+ render :json => {success: true, projects: projects.all.map { |project| project.to_data_hash }}
21
+ end
22
+
23
+ end # ProjectsController
24
+ end # V1
25
+ end # Api
@@ -0,0 +1,313 @@
1
+ module Api
2
+ module V1
3
+ class TimeEntriesController < BaseController
4
+
5
+ def create
6
+ begin
7
+ ActiveRecord::Base.connection.transaction do
8
+ party = current_user.party
9
+
10
+ time_entry = TimeEntry.new(
11
+ manual_entry: true
12
+ )
13
+
14
+ if params[:from_datetime]
15
+ time_entry.from_datetime = params[:from_datetime].to_time
16
+ end
17
+
18
+ if params[:thru_datetime]
19
+ time_entry.from_datetime = params[:thru_datetime].to_time
20
+ end
21
+
22
+ if params[:comment]
23
+ time_entry.comment = params[:comment].strip
24
+ end
25
+
26
+ if params[:regular_hours_in_seconds]
27
+ time_entry.regular_hours_in_seconds = params[:regular_hours_in_seconds].to_i
28
+ end
29
+
30
+ if params[:overtime_hours_in_seconds]
31
+ time_entry.overtime_hours_in_seconds = params[:regular_hours_in_seconds].to_i
32
+ end
33
+
34
+ if params[:work_effort_id]
35
+ time_entry.work_effort = params[:work_effort_id]
36
+ end
37
+
38
+ # if a timesheet id is passed assoicate to that timesheet if not associate to
39
+ # the current user's timesheet
40
+ if params[:timesheet_id]
41
+ time_entry.timesheet_id = params[:timesheet_id]
42
+ else
43
+ time_sheet = party.timesheets.current!(current_user.party, RoleType.iid('work_resource'))
44
+ time_entry.timesheet_id = time_sheet.id
45
+ end
46
+
47
+ render json: {
48
+ success: true,
49
+ time_entry: time_entry.to_data_hash,
50
+ }
51
+
52
+ end
53
+ rescue ActiveRecord::RecordInvalid => invalid
54
+ Rails.logger.error invalid.record.errors
55
+
56
+ render :json => {:success => false, :message => invalid.record.errors}
57
+ rescue StandardError => ex
58
+ Rails.logger.error ex.message
59
+ Rails.logger.error ex.backtrace.join("\n")
60
+
61
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
62
+
63
+ render json: {success: false, message: 'Error creating Time Entry'}
64
+ end
65
+ end
66
+
67
+ def update
68
+ begin
69
+ ActiveRecord::Base.connection.transaction do
70
+
71
+ time_entry = TimeEntry.find(params[:id])
72
+
73
+ if params[:from_datetime]
74
+ time_entry.from_datetime = params[:from_datetime].to_time
75
+ end
76
+
77
+ if params[:thru_datetime]
78
+ time_entry.from_datetime = params[:thru_datetime].to_time
79
+ end
80
+
81
+ if params[:comment]
82
+ time_entry.comment = params[:comment].strip
83
+ end
84
+
85
+ if params[:regular_hours_in_seconds]
86
+ time_entry.regular_hours_in_seconds = params[:regular_hours_in_seconds].to_i
87
+ end
88
+
89
+ if params[:overtime_hours_in_seconds]
90
+ time_entry.overtime_hours_in_seconds = params[:regular_hours_in_seconds].to_i
91
+ end
92
+
93
+ # update to manual entry
94
+ time_entry.manual_entry = true
95
+
96
+ render json: {
97
+ success: time_entry.save!,
98
+ time_entry: time_entry.to_data_hash,
99
+ }
100
+
101
+ end
102
+ rescue ActiveRecord::RecordInvalid => invalid
103
+ Rails.logger.error invalid.record.errors
104
+
105
+ render :json => {:success => false, :message => invalid.record.errors}
106
+ rescue StandardError => ex
107
+ Rails.logger.error ex.message
108
+ Rails.logger.error ex.backtrace.join("\n")
109
+
110
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
111
+
112
+ render json: {success: false, message: 'Error updating Time Entry'}
113
+ end
114
+ end
115
+
116
+ def show
117
+ time_entry = TimeEntry.find(params[:id])
118
+
119
+ render :json => {success: true, time_entry: time_entry.to_data_hash}
120
+ end
121
+
122
+ # start TimeEntry by setting the from_datetime but not the thru_datetime
123
+ # if there is already an open time_entry do not let another one be started
124
+ # It is assumed that a TimeEntry is always logged against a work effort so
125
+ # a WorkEffort id should be passed.
126
+ #
127
+ def start
128
+ begin
129
+ ActiveRecord::Base.connection.transaction do
130
+
131
+ party = current_user.party
132
+ work_effort = WorkEffort.find(params[:work_effort_id])
133
+
134
+ # check for an open TimeEntry
135
+ open_time_entry = party.open_time_entry
136
+
137
+ # if there is an open TimeEntry stop it and start a new one
138
+ if open_time_entry
139
+ open_time_entry.thru_datetime = Time.now
140
+
141
+ open_time_entry.calculate_regular_hours_in_seconds!
142
+ end
143
+
144
+ time_entry = TimeEntry.create(
145
+ from_datetime: params[:start_at].to_time
146
+ )
147
+
148
+ time_entry.work_effort = work_effort
149
+
150
+ # associate to a timesheet
151
+ time_sheet = party.timesheets.current!(RoleType.iid('work_resource'))
152
+ time_sheet.time_entries << time_entry
153
+
154
+ # update task statuses
155
+ time_entry.update_task_status('task_status_in_progress')
156
+ time_entry.update_task_assignment_status('task_resource_status_in_progress')
157
+
158
+ render json: {
159
+ success: true,
160
+ time_entry: time_entry.to_data_hash,
161
+ }
162
+ end
163
+ rescue ActiveRecord::RecordInvalid => invalid
164
+ Rails.logger.error invalid.record.errors
165
+
166
+ render :json => {:success => false, :message => invalid.record.errors}
167
+ rescue StandardError => ex
168
+ Rails.logger.error ex.message
169
+ Rails.logger.error ex.backtrace.join("\n")
170
+
171
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
172
+
173
+ render json: {success: false, message: 'Error starting Time Entry'}
174
+ end
175
+ end
176
+
177
+ # stop TimeEntry by setting the thru_datetime and calculating the hours in seconds
178
+ # it returns the TimeEntry record as well as formatted totals for the day and week
179
+ #
180
+ def stop
181
+ begin
182
+ ActiveRecord::Base.connection.transaction do
183
+ party = current_user.party
184
+ work_effort = WorkEffort.find(params[:work_effort_id])
185
+ time_entry = TimeEntry.find(params[:id])
186
+
187
+ time_entry.thru_datetime = params[:end_at].to_time
188
+ time_entry.comment = params[:comment].present? ? params[:comment].strip : nil
189
+
190
+ time_entry.calculate_regular_hours_in_seconds!
191
+
192
+ time_entry.update_task_assignment_status('task_resource_status_hold')
193
+
194
+ result = {
195
+ success: true,
196
+ time_entry: time_entry.to_data_hash,
197
+ }
198
+
199
+ time_helper = ErpBaseErpSvcs::Helpers::Time::Client.new(params[:client_utc_offset])
200
+
201
+ result[:day_total_formatted] = TimeEntry.total_formatted(work_effort: work_effort,
202
+ party: party,
203
+ start: time_helper.beginning_of_day,
204
+ end: time_helper.end_of_day
205
+ )
206
+ result[:week_total_formatted] = TimeEntry.total_formatted(work_effort: work_effort,
207
+ party: party,
208
+ start: time_helper.beginning_of_week,
209
+ end: time_helper.end_of_week
210
+ )
211
+
212
+ render json: result
213
+ end
214
+ rescue ActiveRecord::RecordInvalid => invalid
215
+ Rails.logger.error invalid.record.errors
216
+
217
+ render :json => {:success => false, :message => invalid.record.errors}
218
+ rescue StandardError => ex
219
+ Rails.logger.error ex.message
220
+ Rails.logger.error ex.backtrace.join("\n")
221
+
222
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
223
+
224
+ render json: {success: false, message: 'Error stopping Time Entry'}
225
+ end
226
+ end
227
+
228
+ # if a work effort id is passed get the last open time_entry for that work_effort
229
+ # for the current user if there are no open time entries then return only the totals
230
+ #
231
+ def open
232
+ if params[:work_effort_id]
233
+ work_effort = WorkEffort.find(params[:work_effort_id])
234
+ party = current_user.party
235
+
236
+ open_time_entry = work_effort.time_entries.scope_by_party(current_user.party).open_entries.first
237
+ time_helper = ErpBaseErpSvcs::Helpers::Time::Client.new(params[:client_utc_offset])
238
+
239
+ render :json => {success: true,
240
+ time_entry: open_time_entry.nil? ? nil : open_time_entry.to_data_hash,
241
+ day_total_formatted: TimeEntry.total_formatted(work_effort: work_effort,
242
+ party: party,
243
+ start: time_helper.beginning_of_day,
244
+ end: time_helper.end_of_day),
245
+ week_total_formatted: TimeEntry.total_formatted(work_effort: work_effort,
246
+ party: party,
247
+ start: time_helper.beginning_of_week,
248
+ end: time_helper.end_of_week)
249
+ }
250
+ else
251
+ render :json => {success: true, time_entries: TimeEntry.open_entries.collect { |time_entry| time_entry.to_data_hash }}
252
+ end
253
+ end
254
+
255
+ # returns totals for time entries. If a work effort id is passed it will get totals for the
256
+ # passed work effort. If no work effort id is passed it will get totals for the current user
257
+ # passed on their timesheet
258
+ #
259
+ def totals
260
+ result = {
261
+ success: true,
262
+ day_total_seconds: 0,
263
+ week_total_seconds: 0,
264
+ day_total_formatted: '00:00:00',
265
+ week_total_formatted: '00:00:00',
266
+ total_formatted: '00:00:00'
267
+ }
268
+
269
+ work_effort = nil
270
+ party = nil
271
+ time_helper = ErpBaseErpSvcs::Helpers::Time::Client.new(params[:client_utc_offset])
272
+
273
+ if params[:work_effort_id]
274
+ work_effort = WorkEffort.find(params[:work_effort_id])
275
+ end
276
+
277
+ if params[:party_id]
278
+ party = Party.find(params[:party_id])
279
+ end
280
+
281
+ result[:day_total_seconds] = TimeEntry.total_seconds(work_effort: work_effort,
282
+ party: party,
283
+ start: time_helper.beginning_of_day,
284
+ end: time_helper.end_of_day
285
+ )
286
+ result[:week_total_seconds] = TimeEntry.total_seconds(work_effort: work_effort,
287
+ party: party,
288
+ start: time_helper.beginning_of_week,
289
+ end: time_helper.end_of_week
290
+ )
291
+ result[:total_seconds] = TimeEntry.total_seconds(work_effort: work_effort,
292
+ party: party
293
+ )
294
+ result[:day_total_formatted] = TimeEntry.total_formatted(work_effort: work_effort,
295
+ party: party,
296
+ start: time_helper.beginning_of_day,
297
+ end: time_helper.end_of_day
298
+ )
299
+ result[:week_total_formatted] = TimeEntry.total_formatted(work_effort: work_effort,
300
+ party: party,
301
+ start: time_helper.beginning_of_week,
302
+ end: time_helper.end_of_week
303
+ )
304
+ result[:total_formatted] = TimeEntry.total_formatted(work_effort: work_effort,
305
+ party: party
306
+ )
307
+
308
+ render json: result
309
+ end
310
+
311
+ end # TimeEntriesController
312
+ end # V1
313
+ end # Api
@@ -0,0 +1,9 @@
1
+ module Api
2
+ module V1
3
+ class TransportationRoutesController < BaseController
4
+
5
+ # TODO implement CRUD operations
6
+
7
+ end # TransportationRoutesController
8
+ end # V1
9
+ end # Api
@@ -0,0 +1,102 @@
1
+ module Api
2
+ module V1
3
+ class WorkEffortAssociationsController < BaseController
4
+
5
+ def index
6
+ work_effort_associations = WorkEffortAssociation
7
+
8
+ if params[:project_id]
9
+ work_effort_associations = work_effort_associations.joins('inner join work_efforts on work_efforts.id = work_effort_associations.work_effort_id_to')
10
+ .where('work_efforts.project_id = ?', params[:project_id])
11
+ else
12
+ # scope by dba organization
13
+ work_effort_associations = work_effort_associations.joins('inner join work_efforts on work_efforts.id = work_effort_associations.work_effort_id_to')
14
+ .joins("inner join entity_party_roles on entity_party_roles.entity_record_type = 'WorkEffort' and entity_party_roles.entity_record_id = work_efforts.id")
15
+ .where('entity_party_roles.party_id = ? and entity_party_roles.role_type_id = ?', current_user.party.dba_organization.id, RoleType.iid('dba_org').id)
16
+ end
17
+
18
+ render :json => {success: true, work_effort_associations: work_effort_associations.all.map { |work_effort| work_effort.to_data_hash }}
19
+ end
20
+
21
+ def show
22
+ render :json => {success: true, work_effort_association: WorkEffortAssociation.find(params[:id]).to_data_hash}
23
+ end
24
+
25
+ def create
26
+ begin
27
+ ActiveRecord::Base.connection.transaction do
28
+
29
+ work_effort_association = WorkEffortAssociation.new
30
+ work_effort_association.work_effort_id_from = params[:work_effort_id_from]
31
+ work_effort_association.work_effort_id_to = params[:work_effort_id_to]
32
+ work_effort_association.work_effort_association_type = WorkEffortAssociationType.where('external_identifier = ?', params['work_effort_association_type.external_identifier'].to_s).first
33
+
34
+ work_effort_association.save!
35
+
36
+ render :json => {success: true, work_effort_association: work_effort_association.to_data_hash}
37
+
38
+ end
39
+ rescue ActiveRecord::RecordInvalid => invalid
40
+ Rails.logger.error invalid.record.errors
41
+
42
+ render :json => {:success => false, :message => invalid.record.errors}
43
+ rescue StandardError => ex
44
+ Rails.logger.error ex.message
45
+ Rails.logger.error ex.backtrace.join("\n")
46
+
47
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
48
+
49
+ render json: {success: false, message: 'Error creating Work Effort Association'}
50
+ end
51
+ end
52
+
53
+ def update
54
+ begin
55
+ ActiveRecord::Base.connection.transaction do
56
+
57
+ work_effort_association = WorkEffortAssociation.find(params[:id])
58
+ work_effort_association.work_effort_id_from = params[:work_effort_id_from]
59
+ work_effort_association.work_effort_id_to = params[:work_effort_id_to]
60
+ work_effort_association.work_effort_association_type = WorkEffortAssociationType.where('external_identifier = ?', params[:work_effort_association_type_external_id].to_s).first
61
+
62
+ work_effort_association.save!
63
+
64
+ render :json => {success: true, work_effort_association: work_effort_association.to_data_hash}
65
+
66
+ end
67
+ rescue ActiveRecord::RecordInvalid => invalid
68
+ Rails.logger.error invalid.record.errors
69
+
70
+ render :json => {:success => false, :message => invalid.record.errors}
71
+ rescue StandardError => ex
72
+ Rails.logger.error ex.message
73
+ Rails.logger.error ex.backtrace.join("\n")
74
+
75
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
76
+
77
+ render json: {success: false, message: 'Error updating Work Effort Association'}
78
+ end
79
+ end
80
+
81
+ def destroy
82
+ work_effort_association = WorkEffortAssociation.find(params[:id])
83
+
84
+ begin
85
+ ActiveRecord::Base.connection.transaction do
86
+
87
+ render json: {success: work_effort_association.destroy}
88
+
89
+ end
90
+ rescue StandardError => ex
91
+ Rails.logger.error ex.message
92
+ Rails.logger.error ex.backtrace.join("\n")
93
+
94
+ ExceptionNotifier.notify_exception(ex) if defined? ExceptionNotifier
95
+
96
+ render json: {success: false, message: 'Error destroying Work Effort Association'}
97
+ end
98
+ end
99
+
100
+ end # WorkEffortAssociationsController
101
+ end # V1
102
+ end # Api