change_health 1.0.3 → 2.2.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (34) hide show
  1. checksums.yaml +4 -4
  2. data/CHANGELOG.md +56 -5
  3. data/README.md +154 -17
  4. data/lib/change_health/connection.rb +1 -1
  5. data/lib/change_health/models/claim/submission/claim_information.rb +31 -0
  6. data/lib/change_health/models/claim/submission/provider.rb +17 -0
  7. data/lib/change_health/models/claim/submission/service_line.rb +12 -0
  8. data/lib/change_health/models/claim/submission/submitter.rb +11 -0
  9. data/lib/change_health/models/claim/submission/subscriber.rb +15 -0
  10. data/lib/change_health/models/eligibility/encounter.rb +22 -0
  11. data/lib/change_health/models/eligibility/provider.rb +23 -0
  12. data/lib/change_health/models/eligibility/subscriber.rb +31 -0
  13. data/lib/change_health/models/error.rb +57 -0
  14. data/lib/change_health/models/model.rb +13 -1
  15. data/lib/change_health/models/{trading_partner.rb → trading_partner/trading_partner.rb} +0 -0
  16. data/lib/change_health/{models → request}/eligibility.rb +5 -5
  17. data/lib/change_health/request/report.rb +52 -0
  18. data/lib/change_health/request/submission.rb +58 -0
  19. data/lib/change_health/response/claim/report/report_data.rb +45 -0
  20. data/lib/change_health/response/claim/report/report_list_data.rb +13 -0
  21. data/lib/change_health/response/claim/submission/submission_data.rb +23 -0
  22. data/lib/change_health/{models → response/eligibility}/eligibility_benefit.rb +6 -6
  23. data/lib/change_health/{models → response/eligibility}/eligibility_benefits.rb +3 -3
  24. data/lib/change_health/response/eligibility/eligibility_data.rb +94 -0
  25. data/lib/change_health/response/response_data.rb +41 -0
  26. data/lib/change_health/response/{trading_partner_data.rb → trading_partner/trading_partner_data.rb} +0 -0
  27. data/lib/change_health/response/{trading_partners_data.rb → trading_partner/trading_partners_data.rb} +0 -0
  28. data/lib/change_health/version.rb +1 -1
  29. data/lib/change_health.rb +23 -11
  30. metadata +24 -12
  31. data/lib/change_health/models/eligibility_data.rb +0 -191
  32. data/lib/change_health/models/encounter.rb +0 -20
  33. data/lib/change_health/models/provider.rb +0 -21
  34. data/lib/change_health/models/subscriber.rb +0 -29
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 69bacf8024e568af3c7dbbdfe638ede842f44392fc870128a7da9242ce7a7094
4
- data.tar.gz: d1e9b4d07f32e0631b75820cfe31e0aa4a6f37f77ccebe8e63cdbf826a29ea90
3
+ metadata.gz: c125bdbe69dd6012d726e7ec54364c9535520520beeb4b7503dfc2b8eaf53a04
4
+ data.tar.gz: 1645afbc96aed15798aab5603445c63892593924ae8fcac0c8490d166fa46919
5
5
  SHA512:
6
- metadata.gz: aa7f24775ab4760c110a0b3977a51170c4d465651753b184c65be967a1d48708d3564b63357db110ea8d538be2bece70bb07282623c85c35dc5d789fa68c0703
7
- data.tar.gz: 8307d1353765e881915c50ee02b3c280c5abb73e42f94f9f814f3089c004b6e7d0c4c70130070f964f9922f5496f5b46a8b582956d945cac2d4ddbb6a561cc0d
6
+ metadata.gz: cb574a463704359781dbddee731ce6f298916bbbb37a95dd1f44790aa56e6ba730e916a67655266f1d80dc6a47924140b3ec53fde6425e982fc000ab2b259765
7
+ data.tar.gz: 63162fe79c441191d1a73ebc3967d66bc9f20d1f7cfae7126771c17c08bed61905933e188a66d527835a32f2192a7d1e7246c220b34b06d043577e4fd6dc1a6e
data/CHANGELOG.md CHANGED
@@ -4,6 +4,54 @@ All notable changes to this project will be documented in this file.
4
4
  The format is based on [Keep a Changelog](http://keepachangelog.com/en/1.0.0/)
5
5
  and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.html).
6
6
 
7
+ ## [2.2.1] - [2021-11-15-21]
8
+ ### Added
9
+ Custom Headers for Reports API and Professional Claims API
10
+ * Report
11
+ * Submission
12
+
13
+ ## [2.2.0] - [2021-11-04-21]
14
+ ### Added
15
+ Ability to hit [Claim Responses and Reports](https://developers.changehealthcare.com/eligibilityandclaims/docs/claims-responses-and-reports-getting-started)
16
+ * Report
17
+ * ReportListData
18
+ * ReportData
19
+
20
+ ## [2.1.0] - [2021-10-12]
21
+ ### Changed
22
+ Model#to_h enhanced to change empty values AKA "" to nil. Reason: If a field is empty, Change Healthcare responds with an error - `Invalid value. Item must not be blank value.`. If the empty field is optional, Change Healthcare will accept the field as nil without error. If the empty field is required, Change Healthcare will return an error if the value is empty or nil.
23
+
24
+ ## [2.0.0] - [2021-10-08]
25
+ ### Added
26
+ #### Models
27
+ * ResponseData - for responses from calling change healthcare api used by EligibilityData and SubmissionData
28
+ #### Claim Submission
29
+ Added the ability to hit professional claim submission API. For more details, see [Change Healthcare documentation here](https://developers.changehealthcare.com/eligibilityandclaims/docs/professional-claims-v3-getting-started)
30
+ * ClaimInformation
31
+ * Provider
32
+ * ServiceLine
33
+ * Submission
34
+ * SubmissionData
35
+ * Submitter
36
+ * Subscriber
37
+ ### Changed
38
+ * Using new Change Healthcare url. From apis to apigw. For more info see [change log here](https://developers.changehealthcare.com/eligibilityandclaims/docs/change-logrelease-notes-1)
39
+ * PARSE_DATE moved from ChangeHealth::Models::EligibilityData to ChangeHealth::Models
40
+ * Moved Error class into its own file
41
+ #### Namespace
42
+ Many classes moved namespaces to be more consistent across the many endpoints in Change Healthcare
43
+ | Previous | Current |
44
+ |-|-|
45
+ |ChangeHealth::Models::Eligibility | ChangeHealth::Request::Eligibility |
46
+ | ChangeHealth::Models::Encounter | ChangeHealth::Models::Eligibility::Encounter|
47
+ | ChangeHealth::Models::Provider | ChangeHealth::Models::Eligibility::Provider|
48
+ | ChangeHealth::Models::Subscriber | ChangeHealth::Models::Eligibility::Subscriber|
49
+ | ChangeHealth::Models::EligibilityBenefit | ChangeHealth::Response::EligibilityBenefit|
50
+ | ChangeHealth::Models::EligibilityBenefits | ChangeHealth::Response::EligibilityBenefits|
51
+ | ChangeHealth::Models::EligibilityData | ChangeHealth::Response::EligibilityData|
52
+ ### Fixed
53
+ * Eligibility#add_dependent actually works
54
+
7
55
  ## [1.0.3] - [2021-04-26]
8
56
  ### Added
9
57
  - Model::Error#represents_down? - adds ability to distinguish error representing down state
@@ -114,7 +162,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
114
162
  ### Added
115
163
  - Production endpoint
116
164
 
117
- ## [0.2.0] - [2020-03-09]
165
+ ## [0.0.2] - [2020-03-09]
118
166
  ### Added
119
167
  - EligibilityData
120
168
  - EligibilityBenefit
@@ -123,7 +171,7 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
123
171
  ### Changed
124
172
  - Eligibility.query returns EligibilityData object
125
173
 
126
- ## [0.1.0] - 2020-03-04
174
+ ## [0.0.1] - 2020-03-04
127
175
  ### Added
128
176
  - Provider
129
177
  - Subscriber
@@ -132,6 +180,9 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
132
180
  - Authentication
133
181
  - Configuration
134
182
 
183
+ [2.2.0]: https://github.com/WeInfuse/change_health/compare/v2.1.0...v2.2.0
184
+ [2.1.0]: https://github.com/WeInfuse/change_health/compare/v2.0.0...v2.1.0
185
+ [2.0.0]: https://github.com/WeInfuse/change_health/compare/v1.0.3...v2.0.0
135
186
  [1.0.3]: https://github.com/WeInfuse/change_health/compare/v1.0.2...v1.0.3
136
187
  [1.0.2]: https://github.com/WeInfuse/change_health/compare/v1.0.1...v1.0.2
137
188
  [1.0.1]: https://github.com/WeInfuse/change_health/compare/v1.0.0...v1.0.1
@@ -148,6 +199,6 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
148
199
  [0.6.0]: https://github.com/WeInfuse/change_health/compare/v0.5.0...v0.6.0
149
200
  [0.5.0]: https://github.com/WeInfuse/change_health/compare/v0.4.0...v0.5.0
150
201
  [0.4.0]: https://github.com/WeInfuse/change_health/compare/v0.3.0...v0.4.0
151
- [0.3.0]: https://github.com/WeInfuse/change_health/compare/v0.2.0...v0.3.0
152
- [0.2.0]: https://github.com/WeInfuse/change_health/compare/v0.1.0...v0.2.0
153
- [0.1.0]: https://github.com/WeInfuse/change_health/compare/v0.1.0
202
+ [0.3.0]: https://github.com/WeInfuse/change_health/compare/v0.0.2...v0.3.0
203
+ [0.0.2]: https://github.com/WeInfuse/change_health/compare/v0.0.1...v0.0.2
204
+ [0.0.1]: https://github.com/WeInfuse/change_health/compare/520a8c54d07...v0.0.1
data/README.md CHANGED
@@ -26,24 +26,25 @@ Or install it yourself as:
26
26
  Make sure you're [configured](#configuration)!
27
27
 
28
28
  ### Eligibility
29
+ [Change Healthcare Eligibility Guide](https://developers.changehealthcare.com/eligibilityandclaims/docs)
29
30
  ```ruby
30
- ChangeHealth::Models::Eligibility.ping # Test your connection
31
+ ChangeHealth::Request::Eligibility.ping # Test your connection
31
32
 
32
- encounter = ChangeHealth::Models::Encounter.new(date_of_service: Date.current, service_type_codes: ['98'])
33
- provider = ChangeHealth::Models::Provider.new(npi: '0123456789', last_name: 'Bobson', first_name: 'Bob')
34
- subscriber = ChangeHealth::Models::Subscriber.new(member_id: '0000000000', first_name: 'johnOne', last_name: 'doeOne', date_of_birth: '18800102')
33
+ encounter = ChangeHealth::Models::Eligibility::Encounter.new(date_of_service: Date.current, service_type_codes: ['98'])
34
+ provider = ChangeHealth::Models::Eligibility::Provider.new(npi: '0123456789', last_name: 'Bobson', first_name: 'Bob')
35
+ subscriber = ChangeHealth::Models::Eligibility::Subscriber.new(member_id: '0000000000', first_name: 'johnOne', last_name: 'doeOne', date_of_birth: '18800102')
35
36
 
36
- edata = ChangeHealth::Models::Eligibility.new(tradingPartnerServiceId: '000050', provider: provider, subscriber: subscriber, encounter: encounter).query
37
+ edata = ChangeHealth::Request::Eligibility.new(tradingPartnerServiceId: '000050', provider: provider, subscriber: subscriber, encounter: encounter).query
37
38
 
38
39
  edata.raw # Raw Hash of JSON response
39
40
  ```
40
41
 
41
- ### Benefit(s) objects
42
+ #### Benefit(s) objects
42
43
  Benefits extends Array and provides a query-like interface.
43
44
 
44
45
  Benefit extends Hash and provides helpers for single-benefit.
45
46
 
46
- ```
47
+ ```ruby
47
48
  edata.benefits # Returns Benefits querying object (extends Array)
48
49
 
49
50
  edata.benefits.individual # Only benefits matching the 'IND' identifier
@@ -57,7 +58,7 @@ edata.benefits.where(name: 'Co-Payment', code: 'B', benefitAmount: '30) # Generi
57
58
  edata.benefits.find_by(name: 'Co-Payment', code: 'B', benefitAmount: '30) # Generic 'find_by' api returns first object found
58
59
  ```
59
60
 
60
- ### Response
61
+ #### Response
61
62
 
62
63
  Response is EligibilityData object
63
64
 
@@ -77,24 +78,160 @@ true
77
78
 
78
79
  ### Trading Partners
79
80
  ```ruby
80
- # Query trading partners using a wildcard search
81
- # Returns Array of ChangeHealth::Models::TradingPartner Objects
82
- trading_partners = ChangeHealth::Request::TradingPartner.query("Aetna")
81
+ # Query trading partners using a wildcard search
82
+ # Returns Array of ChangeHealth::Models::TradingPartner Objects
83
+ trading_partners = ChangeHealth::Request::TradingPartner.query("Aetna")
84
+
85
+ trading_partners.first.name
86
+ # "Aetna"
87
+
88
+ trading_partners.first.service_id
89
+ # "ABC123"
90
+ ```
91
+
92
+ ### Claim Submission
93
+ [Change Healthcare Claim Submission Guide](https://developers.changehealthcare.com/eligibilityandclaims/docs/professional-claims-v3-getting-started)
94
+ ```ruby
95
+ ChangeHealth::Request::Claim::Submission.ping # Test your connection
96
+
97
+ contact_information = { name: "SUBMITTER CONTACT INFO", phoneNumber: "123456789"}
98
+ claim_submitter = ChangeHealth::Models::Claim::Submitter.new(
99
+ organization_name: "REGIONAL PPO NETWORK",
100
+ contact_information: contact_information
101
+ )
102
+
103
+ receiver = { organizationName: "EXTRA HEALTHY INSURANCE"}
104
+ address = {
105
+ "address1": "123 address1",
106
+ "city": "city1",
107
+ "state": "wa",
108
+ "postalCode": "981010000"
109
+ }
110
+ subscriber = ChangeHealth::Models::Claim::Subscriber.new(
111
+ member_id: "0000000001",
112
+ payment_responsibility_level_code: "P",
113
+ first_name: "johnone",
114
+ last_name: "doetwo",
115
+ gender: "M",
116
+ date_of_birth: "02/01/1980",
117
+ address: address
118
+ )
119
+ provider = ChangeHealth::Models::Claim::Provider.new(
120
+ address: address,
121
+ employer_id: "000000000",
122
+ first_name: "johnone",
123
+ last_name: "doetwo",
124
+ npi: "1760854442",
125
+ provider_type: "BillingProvider"
126
+ )
127
+
128
+ health_care_code_information1 = {
129
+ "diagnosisTypeCode": "ABK",
130
+ "diagnosisCode": "S93401A"
131
+ }
132
+ health_care_code_information2 = {
133
+ "diagnosisTypeCode": "ABF",
134
+ "diagnosisCode": "S72044G"
135
+
136
+ }
137
+ service_line1 = ChangeHealth::Models::Claim::ServiceLine.new(
138
+ service_date: "2018-05-14",
139
+ professional_service: {
140
+ "procedureIdentifier": "HC",
141
+ "lineItemChargeAmount": "25",
142
+ "procedureCode": "E0570",
143
+ "measurementUnit": "UN",
144
+ "serviceUnitCount": "1",
145
+ "compositeDiagnosisCodePointers": {
146
+ "diagnosisCodePointers": ["1","2"]
147
+ }
148
+ }
149
+ )
150
+ service_line2 = ChangeHealth::Models::Claim::ServiceLine.new(
151
+ service_date: "20180514",
152
+ professional_service: {
153
+ "procedureIdentifier": "HC",
154
+ "lineItemChargeAmount": "3.75",
155
+ "procedureCode": "A7003",
156
+ "measurementUnit": "UN",
157
+ "serviceUnitCount": "1",
158
+ "compositeDiagnosisCodePointers": {
159
+ "diagnosisCodePointers": ["1"]
160
+ }
161
+ }
162
+ )
163
+ claim_information = ChangeHealth::Models::Claim::ClaimInformation.new(
164
+ benefits_assignment_certification_indicator: "Y",
165
+ claim_charge_amount: "28.75",
166
+ claim_filing_code: "CI",
167
+ claim_frequency_code: "1",
168
+ patient_control_number: "12345",
169
+ place_of_service_code: "11",
170
+ plan_participation_code: "A",
171
+ release_information_code: "Y",
172
+ signature_indicator: "Y",
173
+ health_care_code_information: [health_care_code_information1, health_care_code_information2],
174
+ service_lines: [service_line1, service_line2]
175
+ )
176
+
177
+ professional_headers = {
178
+ submitter_id: '111000',
179
+ biller_id: '000111',
180
+ username: '222333hey',
181
+ password: 'builder1'
182
+ }
183
+
184
+ claim_submission = ChangeHealth::Request::Claim::Submission.new(
185
+ trading_partner_service_id: "9496",
186
+ submitter: claim_submitter,
187
+ receiver: receiver,
188
+ subscriber: subscriber,
189
+ providers: [provider],
190
+ claim_information: claim_information,
191
+ headers: professional_headers
192
+ )
193
+
194
+ claim_submission_data = claim_submission.submission
195
+
196
+ validation = claim_submission.validation
197
+ ```
198
+
199
+ ### Claim Reports
200
+ [Change Healthcare Claim Responses and Reports Guide](https://developers.changehealthcare.com/eligibilityandclaims/docs/claims-responses-and-reports-getting-started)
201
+ ```ruby
202
+ ChangeHealth::Request::Claim::Report.ping # Test your connection
203
+
204
+ report_headers = {
205
+ username: '111000john',
206
+ password: 'WeInfuse1'
207
+ }
208
+
209
+ report_list = ChangeHealth::Request::Claim::Report.report_list(headers: report_headers)
83
210
 
84
- trading_partners.first.name
85
- "Aetna"
211
+ report_list.report_names
212
+ # ["X3000000.XX", "R5000000.XY", "R5000000.XX", "X3000000.AB", "X3000000.AC", "X3000000.ZZ", "R5000000.XZ", "R5000000.YZ", "R5000000.WA", "R5000000.WB", "R5000000.WC"]
86
213
 
87
- trading_partners.first.service_id
88
- "ABC123"
214
+ report1_edi = ChangeHealth::Request::Claim::Report.get_report(report_list.report_names.first, as_json_report: false, headers: report_headers)
215
+ # Report in edi format
216
+
217
+ report1_json = ChangeHealth::Request::Claim::Report.get_report(report_list.report_names.first, as_json_report: true, headers: report_headers)
218
+ # Report in json format
219
+
220
+ reports_json = report_list.report_names.map {|report_name| ChangeHealth::Request::Claim::Report.get_report(report_name, headers: report_headers)}
221
+ # all reports in json format
222
+
223
+ reports_edi = report_list.report_names.map {|report_name| ChangeHealth::Request::Claim::Report.get_report(report_name, as_json_report: false, headers: report_headers)}
224
+ # all reports in edi format
89
225
  ```
226
+
90
227
  ### Configuration
91
228
 
92
229
  ```ruby
93
230
  ChangeHealth.configure do |c|
94
231
  c.client_id = ENV['CHANGE_HEALTH_CLIENT_ID']
95
232
  c.client_secret = ENV['CHANGE_HEALTH_SECRET']
96
- c.grant_type = 'bob' # Defaults to client_credentials
97
- c.api_endpoint = 'http://hello.com' # Defaults to Change Health Sandbox endpoint
233
+ c.grant_type = 'client_credentials' # Defaults to client_credentials
234
+ c.api_endpoint = 'https://sandbox.apigw.changehealthcare.com' # Defaults to Change Health Sandbox endpoint
98
235
  end
99
236
  ```
100
237
 
@@ -1,6 +1,6 @@
1
1
  module ChangeHealth
2
2
  class Connection
3
- URI_BUILDER = ->(host) { "https://#{host}apis.changehealthcare.com/".freeze }
3
+ URI_BUILDER = ->(host) { "https://#{host}apigw.changehealthcare.com/".freeze }
4
4
 
5
5
  QA_ENDPOINT = URI_BUILDER.call('sandbox.')
6
6
  PROD_ENDPOINT = URI_BUILDER.call('')
@@ -0,0 +1,31 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Claim
4
+ class ClaimInformation < Hashie::Trash
5
+ property :benefitsAssignmentCertificationIndicator, from: :benefits_assignment_certification_indicator, required: false
6
+ property :claimChargeAmount, from: :claim_charge_amount, required: false
7
+ property :claimFilingCode, from: :claim_filing_code, required: false
8
+ property :claimFrequencyCode, from: :claim_frequency_code, required: false
9
+ property :claimSupplementalInformation, from: :claim_supplemental_information, required: false
10
+ property :healthCareCodeInformation, from: :health_care_code_information, required: false
11
+ property :patientControlNumber, from: :patient_control_number, required: false
12
+ property :placeOfServiceCode, from: :place_of_service_code, required: false
13
+ property :planParticipationCode, from: :plan_participation_code, required: false
14
+ property :releaseInformationCode, from: :release_information_code, required: false
15
+ property :serviceFacilityLocation, from: :service_facility_location, required: false
16
+ property :serviceLines, from: :service_lines, required: false
17
+ property :signatureIndicator, from: :signature_indicator, required: false
18
+
19
+ def add_service_line(service_line)
20
+ self[:serviceLines] ||= []
21
+ self[:serviceLines] << service_line
22
+ end
23
+
24
+ def add_health_care_code_information(health_care_code_information)
25
+ self[:healthCareCodeInformation] ||= []
26
+ self[:healthCareCodeInformation] << health_care_code_information
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,17 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Claim
4
+ class Provider < Hashie::Trash
5
+ property :address, required: false
6
+ property :contactInformation, from: :contact_information, required: false
7
+ property :employerId, from: :employer_id, required: false # or ssn
8
+ property :firstName, from: :first_name, required: false
9
+ property :lastName, from: :last_name, required: false
10
+ property :organizationName, from: :organization_name, required: false
11
+ property :npi, required: false
12
+ property :providerType, from: :provider_type, required: false
13
+ property :ssn, required: false # or employer id
14
+ end
15
+ end
16
+ end
17
+ end
@@ -0,0 +1,12 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Claim
4
+ class ServiceLine < Model
5
+
6
+ property :serviceDate, from: :service_date, required: false
7
+ property :professionalService, from: :professional_service, required: false
8
+
9
+ end
10
+ end
11
+ end
12
+ end
@@ -0,0 +1,11 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Claim
4
+ class Submitter < Hashie::Trash
5
+ property :organizationName, from: :organization_name, required: false
6
+ # contact information has a name & phone number inside
7
+ property :contactInformation, from: :contact_information, required: false
8
+ end
9
+ end
10
+ end
11
+ end
@@ -0,0 +1,15 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Claim
4
+ class Subscriber < Model
5
+ property :address, required: false
6
+ property :dateOfBirth, from: :date_of_birth, required: false
7
+ property :firstName, from: :first_name, required: false
8
+ property :gender, required: false
9
+ property :lastName, from: :last_name, required: false
10
+ property :memberId, from: :member_id, required: false
11
+ property :paymentResponsibilityLevelCode, from: :payment_responsibility_level_code, required: false
12
+ end
13
+ end
14
+ end
15
+ end
@@ -0,0 +1,22 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Eligibility
4
+ class Encounter < Model
5
+ property :beginningDateOfService, from: :beginning_date_of_service, required: false
6
+ property :dateOfService, from: :date_of_service, required: false
7
+ property :dateRange, from: :date_range, required: false, default: false
8
+ property :endDateOfService, from: :end_date_of_service, required: false
9
+ property :serviceTypeCodes, from: :service_type_codes, required: false
10
+
11
+ alias_method :dateRange?, :dateRange
12
+ alias_method :date_range?, :dateRange
13
+ alias_method :service_type_codes, :serviceTypeCodes
14
+
15
+ def add_service_type_code(code)
16
+ self[:serviceTypeCodes] ||= []
17
+ self[:serviceTypeCodes] << code
18
+ end
19
+ end
20
+ end
21
+ end
22
+ end
@@ -0,0 +1,23 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Eligibility
4
+ class Provider < Hashie::Trash
5
+ property :firstName, from: :first_name, required: false
6
+ property :lastName, from: :last_name, required: false
7
+ property :name, default: true, required: false
8
+ property :npi, required: false
9
+ property :organizationName, from: :organization_name, required: false
10
+ property :payorId, from: :payer_id, required: false
11
+ property :person, default: true, required: false
12
+ property :providerCode, from: :provider_code, required: false
13
+ property :providerName, from: :provider_name, required: false
14
+ property :providerType, from: :provider_type, required: false
15
+ property :referenceIdentification, from: :reference_identification, required: false
16
+ property :serviceProviderNumber, from: :service_provider_number, required: false
17
+ property :taxId, from: :tax_id, required: false
18
+
19
+ alias_method :name?, :name
20
+ end
21
+ end
22
+ end
23
+ end
@@ -0,0 +1,31 @@
1
+ module ChangeHealth
2
+ module Models
3
+ module Eligibility
4
+ class Subscriber < Model
5
+ property :additionalIdentification, required: false
6
+ property :address, required: false
7
+ property :birthSequenceNumber, from: :birth_sequence_number, required: false
8
+ property :caseNumber, from: :case_number, required: false
9
+ property :dateOfBirth, from: :date_of_birth, required: false
10
+ property :firstName, from: :first_name, required: false
11
+ property :gender, required: false
12
+ property :groupNumber, from: :group_number, required: false
13
+ property :healthCareCodeInformation, from: :health_care_code_information, required: false
14
+ property :idCard, from: :id_card, required: false
15
+ property :idCardIssueDate, from: :id_card_issued_date, required: false
16
+ property :lastName, from: :last_name, required: false
17
+ property :medicaidRecipientIdentificationNumber, from: :medicaid_recipient_identification_number, required: false
18
+ property :memberId, from: :member_id, required: false
19
+ property :providerCode, from: :provider_code, required: false
20
+ property :providerIdentifier, from: :provider_identification, required: false
21
+ property :referenceIdentificationQualifier, from: :reference_identification_qualifier, required: false
22
+ property :ssn, required: false
23
+
24
+ def add_health_care_code_information(value)
25
+ self[:healthCareCodeInformation] ||= []
26
+ self[:healthCareCodeInformation] << value
27
+ end
28
+ end
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,57 @@
1
+ module ChangeHealth
2
+ # TODO: This should be the response module/folder... next major release
3
+ module Models
4
+ class Error
5
+ attr_reader :data
6
+
7
+ SIMPLE_RETRY_CODES = %w[
8
+ 42
9
+ 80
10
+ ].freeze
11
+
12
+ NO_RESUBMIT_MESSAGES = [
13
+ 'resubmission not allowed',
14
+ 'do not resubmit'
15
+ ].freeze
16
+
17
+ DOWN_FIELD = 'Http Header'.freeze
18
+
19
+ DOWN_MESSAGE = 'Please review http headers for this API, please contact support if you are unsure how to resolve.'.freeze
20
+
21
+ def initialize(data)
22
+ @data = data
23
+ end
24
+
25
+ def message
26
+ field_message || code_message
27
+ end
28
+
29
+ def field_message
30
+ "#{field}: #{description}" if field?
31
+ end
32
+
33
+ def code_message
34
+ "#{code}: #{description}" if code?
35
+ end
36
+
37
+ def represents_down?
38
+ field == DOWN_FIELD && description == DOWN_MESSAGE
39
+ end
40
+
41
+ def retryable?
42
+ represents_down? ||
43
+ (code? && SIMPLE_RETRY_CODES.include?(code) && followupAction? && NO_RESUBMIT_MESSAGES.none? {|msg| followupAction.downcase.include?(msg) })
44
+ end
45
+
46
+ %w[field description code followupAction location].each do |method_name|
47
+ define_method("#{method_name}?") do
48
+ false == send(method_name).nil?
49
+ end
50
+
51
+ define_method("#{method_name}") do
52
+ @data[method_name]
53
+ end
54
+ end
55
+ end
56
+ end
57
+ end
@@ -12,14 +12,26 @@ module ChangeHealth
12
12
  d
13
13
  }
14
14
 
15
+ PARSE_DATE = ->(d) {
16
+ begin
17
+ d = Date.strptime(d, ChangeHealth::Models::DATE_FORMAT)
18
+ rescue
19
+ end
20
+
21
+ d
22
+ }
23
+
24
+ CONTROL_NUMBER = ->() { '%09d' % rand(1_000_000_000) }
25
+
15
26
  class Model < Hashie::Trash
16
27
  def to_h
17
28
  result = super.to_h
18
29
 
19
- self.class.properties.each do |key|
30
+ self.each_pair do |key, value|
20
31
  if key.to_s.downcase.include?('date')
21
32
  result[key] = ChangeHealth::Models::DATE_FORMATTER.call(result[key])
22
33
  end
34
+ result[key] = nil if value == ""
23
35
  end
24
36
 
25
37
  result
@@ -1,10 +1,10 @@
1
1
  module ChangeHealth
2
- module Models
2
+ module Request
3
3
  class Eligibility < Hashie::Trash
4
4
  ENDPOINT = '/medicalnetwork/eligibility/v3'.freeze
5
5
  HEALTH_CHECK_ENDPOINT = ENDPOINT + '/healthcheck'.freeze
6
6
 
7
- property :controlNumber, from: :control_number, required: true, default: ->() { '%09d' % rand(1_000_000_000) }
7
+ property :controlNumber, from: :control_number, required: true, default: ChangeHealth::Models::CONTROL_NUMBER
8
8
  property :dependents, required: false
9
9
  property :encounter, required: false
10
10
  property :informationReceiverName, from: :information_receiver_name, required: false
@@ -20,12 +20,12 @@ module ChangeHealth
20
20
  alias_method :partner_id?, :partnerId
21
21
 
22
22
  def add_dependent(dependent)
23
- self[:dependent] ||= []
24
- self[:dependent] << dependent
23
+ self[:dependents] ||= []
24
+ self[:dependents] << dependent
25
25
  end
26
26
 
27
27
  def query
28
- ChangeHealth::Models::EligibilityData.new(response: ChangeHealth::Connection.new.request(endpoint: ENDPOINT, body: self.to_h))
28
+ ChangeHealth::Response::EligibilityData.new(response: ChangeHealth::Connection.new.request(endpoint: ENDPOINT, body: self.to_h))
29
29
  end
30
30
 
31
31
  def self.health_check
@@ -0,0 +1,52 @@
1
+ module ChangeHealth
2
+ module Request
3
+ module Claim
4
+ class Report
5
+ ENDPOINT = '/medicalnetwork/reports/v2'.freeze
6
+ HEALTH_CHECK_ENDPOINT = ENDPOINT + '/healthcheck'.freeze
7
+
8
+ def self.report_list(headers: nil)
9
+ final_headers = ChangeHealth::Request::Claim::Report.report_headers(headers)
10
+ ChangeHealth::Response::Claim::ReportListData.new(response: ChangeHealth::Connection.new.request(endpoint: ENDPOINT, verb: :get, headers: final_headers))
11
+ end
12
+
13
+ def self.get_report(report_name, as_json_report: true, headers: nil)
14
+ return if report_name.nil? || report_name.empty?
15
+ final_headers = ChangeHealth::Request::Claim::Report.report_headers(headers)
16
+
17
+ individual_report_endpoint = ENDPOINT + '/' + report_name
18
+ if as_json_report
19
+ # https://developers.changehealthcare.com/eligibilityandclaims/docs/what-file-types-does-this-api-get-from-the-mailbox
20
+ report_type = ChangeHealth::Response::Claim::ReportData.report_type(report_name)
21
+ return if report_type.nil?
22
+
23
+ individual_report_endpoint += '/' + report_type
24
+ end
25
+
26
+ ChangeHealth::Response::Claim::ReportData.new(report_name,
27
+ as_json_report,
28
+ response: ChangeHealth::Connection.new.request(endpoint: individual_report_endpoint, verb: :get, headers: final_headers))
29
+ end
30
+
31
+ def self.health_check
32
+ ChangeHealth::Connection.new.request(endpoint: HEALTH_CHECK_ENDPOINT, verb: :get)
33
+ end
34
+
35
+ def self.ping
36
+ self.health_check
37
+ end
38
+
39
+ def self.report_headers(headers)
40
+ if headers
41
+ extra_headers = {}
42
+ extra_headers["X-CHC-Reports-Username"] = headers[:username]
43
+ extra_headers["X-CHC-Reports-Password"] = headers[:password]
44
+ extra_headers
45
+ else
46
+ nil
47
+ end
48
+ end
49
+ end
50
+ end
51
+ end
52
+ end