carin_for_blue_button_test_kit 0.13.3 → 0.14.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.
- checksums.yaml +4 -4
- data/config/presets/carin_cpcds_client_ri.json +12 -0
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/c4bb_client_test_suite.rb +17 -4
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/coverage_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/eob_inpatient_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/eob_oral_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/eob_outpatient_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/eob_pharmacy_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/eob_professional_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/organization_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/patient_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/practitioner_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/claim_data_request_tests/relatedperson_claims_data_request_test.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/endpoints/authorize_endpoint.rb +32 -0
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/endpoints/next_page_endpoint.rb +3 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/endpoints/resource_api_endpoint.rb +3 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/endpoints/resource_id_endpoint.rb +3 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/endpoints/token_endpoint.rb +69 -13
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/initial_wait_test.rb +35 -4
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/metadata/{mock_capability_statement.json → mock_capability_statement.json.erb} +28 -0
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/mock_authorization.rb +35 -0
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/mock_server.rb +43 -9
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/required_searches_tests/coverage_required_searches.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/required_searches_tests/eob_required_searches.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/required_searches_tests/organization_required_searches.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/required_searches_tests/patient_required_searches.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/required_searches_tests/practitioner_required_searches.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/required_searches_tests/relatedperson_required_searches.rb +0 -1
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/tags.rb +2 -0
- data/lib/carin_for_blue_button_test_kit/client/v2.0.0/urls.rb +25 -10
- data/lib/carin_for_blue_button_test_kit/docs/carin_for_blue_button_v2.0.0_client_suite_description.md +7 -4
- data/lib/carin_for_blue_button_test_kit/generated/v1.1.0/c4bb_test_suite.rb +9 -1
- data/lib/carin_for_blue_button_test_kit/generated/v2.0.0/c4bb_test_suite.rb +9 -1
- data/lib/carin_for_blue_button_test_kit/generated/v2.0.0-dev-nonfinancial/c4bb_test_suite.rb +9 -1
- data/lib/carin_for_blue_button_test_kit/generator/templates/group.rb.erb +24 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/include_search.rb.erb +37 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/must_support.rb.erb +44 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/read.rb.erb +38 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/resource_list.rb.erb +9 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/search.rb.erb +43 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/suite.rb.erb +92 -0
- data/lib/carin_for_blue_button_test_kit/generator/templates/validation.rb.erb +34 -0
- data/lib/carin_for_blue_button_test_kit/metadata.rb +70 -0
- data/lib/carin_for_blue_button_test_kit/requirements/carin-for-blue-button-test-kit_out_of_scope_requirements.csv +53 -0
- data/lib/carin_for_blue_button_test_kit/requirements/carin-for-blue-button-test-kit_requirements.csv +335 -0
- data/lib/carin_for_blue_button_test_kit/requirements/generated/carin-for-blue-button-test-kit_requirements_coverage.csv +335 -0
- data/lib/carin_for_blue_button_test_kit/version.rb +2 -1
- data/lib/carin_for_blue_button_test_kit.rb +1 -0
- data/lib/inferno_requirements_tools/rake/rakefile_template +31 -0
- data/lib/requirements_config.yaml +14 -0
- metadata +27 -9
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA256:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: ea990f355ce17cde4cd012adc06141cb44bf6c3c70a8bc73de0faa9d3f3c2102
|
4
|
+
data.tar.gz: 58e4f6efca2020589024a8cbb11959ed159f58ff00690a3d85f57fd9fea6f7c3
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 22e6ea91cf9494db944a339344b23c80386bbe6ccfb2ef085264467a334c98eca1905acf8ab9d9b5c604b89379816ef8f867bfaf65b62f7ba5ffd838eada51f1
|
7
|
+
data.tar.gz: 23fd00d94577114d623bbeef68b15ff2e121de486b24082a66eace0cb915eee51b1d34215582cfa1aad39236aff17fab4af21959532199b266ff7d65351415fb
|
@@ -1,6 +1,7 @@
|
|
1
1
|
require 'inferno/dsl/oauth_credentials'
|
2
2
|
require_relative 'endpoints/resource_api_endpoint'
|
3
3
|
require_relative 'endpoints/token_endpoint'
|
4
|
+
require_relative 'endpoints/authorize_endpoint'
|
4
5
|
require_relative 'endpoints/next_page_endpoint'
|
5
6
|
require_relative 'endpoints/resource_id_endpoint'
|
6
7
|
|
@@ -77,7 +78,9 @@ module CarinForBlueButtonTestKit
|
|
77
78
|
end
|
78
79
|
end
|
79
80
|
|
80
|
-
suite_endpoint :post, TOKEN_PATH, TokenEndpoint
|
81
|
+
suite_endpoint :post, TOKEN_PATH, MockAuthorization::TokenEndpoint
|
82
|
+
suite_endpoint :get, AUTH_PATH, MockAuthorization::AuthorizeEndpoint
|
83
|
+
suite_endpoint :post, AUTH_PATH, MockAuthorization::AuthorizeEndpoint
|
81
84
|
|
82
85
|
suite_endpoint :get, PATIENT_PATH, ResourceAPIEndpoint
|
83
86
|
|
@@ -87,11 +90,11 @@ module CarinForBlueButtonTestKit
|
|
87
90
|
|
88
91
|
suite_endpoint :get, BASE_FHIR_PATH, NextPageEndpoint
|
89
92
|
|
90
|
-
resume_test_route :get,
|
91
|
-
C4BBV200ClientSuite.
|
93
|
+
resume_test_route :get, RESUME_CLAIMS_DATA_PATH do |request|
|
94
|
+
C4BBV200ClientSuite.extract_test_run_identifier_from_query_params(request)
|
92
95
|
end
|
93
96
|
|
94
|
-
resume_test_route :get,
|
97
|
+
resume_test_route :get, RESUME_PASS_PATH do |request|
|
95
98
|
C4BBV200ClientSuite.extract_token_from_query_params(request)
|
96
99
|
end
|
97
100
|
|
@@ -100,6 +103,8 @@ module CarinForBlueButtonTestKit
|
|
100
103
|
end
|
101
104
|
|
102
105
|
route(:get, METADATA_PATH, get_metadata)
|
106
|
+
route(:get, SMART_CONFIG_PATH, carin_smart_config)
|
107
|
+
route(:get, JKWS_PATH, MockAuthorization.method(:jwks))
|
103
108
|
|
104
109
|
group do
|
105
110
|
run_as_group
|
@@ -111,6 +116,7 @@ module CarinForBlueButtonTestKit
|
|
111
116
|
[C4BB CapabilityStatement](https://hl7.org/fhir/us/carin-bb/STU2/CapabilityStatement-c4bb.html) and the
|
112
117
|
[US Core Client CapabilityStatement](https://hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html).
|
113
118
|
)
|
119
|
+
id :c4bb_claims_data_wait_test_group
|
114
120
|
|
115
121
|
test from: :c4bb_v200_initial_wait_test
|
116
122
|
end
|
@@ -125,6 +131,7 @@ module CarinForBlueButtonTestKit
|
|
125
131
|
and the [US Core Client](https://www.hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html#patient)
|
126
132
|
Capability Statements.
|
127
133
|
)
|
134
|
+
id :c4bb_patient_profile_test_group
|
128
135
|
|
129
136
|
test from: :patient_claims_data_request_test
|
130
137
|
test from: :patient_required_searches
|
@@ -140,6 +147,7 @@ module CarinForBlueButtonTestKit
|
|
140
147
|
and the [US Core Client](https://www.hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html)
|
141
148
|
Capability Statements.
|
142
149
|
)
|
150
|
+
id :c4bb_coverage_profile_test_group
|
143
151
|
|
144
152
|
test from: :coverage_claims_data_request_test
|
145
153
|
test from: :coverage_required_searches
|
@@ -155,6 +163,7 @@ module CarinForBlueButtonTestKit
|
|
155
163
|
and the [US Core Client](https://www.hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html#organization)
|
156
164
|
Capability Statements.
|
157
165
|
)
|
166
|
+
id :c4bb_organization_profile_test_group
|
158
167
|
optional
|
159
168
|
|
160
169
|
test from: :organization_claims_data_request_test
|
@@ -171,6 +180,7 @@ module CarinForBlueButtonTestKit
|
|
171
180
|
and the [US Core Client](https://www.hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html#practitioner)
|
172
181
|
Capability Statements.
|
173
182
|
)
|
183
|
+
id :c4bb_practitioner_profile_test_group
|
174
184
|
optional
|
175
185
|
|
176
186
|
test from: :practitioner_claims_data_request_test
|
@@ -187,6 +197,7 @@ module CarinForBlueButtonTestKit
|
|
187
197
|
and the [US Core Client](https://www.hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html)
|
188
198
|
Capability Statements.
|
189
199
|
)
|
200
|
+
id :c4bb_relatedperson_profile_test_group
|
190
201
|
optional
|
191
202
|
|
192
203
|
test from: :relatedperson_claims_data_request_test
|
@@ -204,6 +215,7 @@ module CarinForBlueButtonTestKit
|
|
204
215
|
and the [US Core Client](https://www.hl7.org/fhir/us/core/STU3.1.1/CapabilityStatement-us-core-client.html)
|
205
216
|
Capability Statements.
|
206
217
|
)
|
218
|
+
id :c4bb_explanationofbenefit_profiles_test_group
|
207
219
|
|
208
220
|
test from: :eob_inpatient_claims_data_request_test
|
209
221
|
test from: :eob_outpatient_claims_data_request_test
|
@@ -220,6 +232,7 @@ module CarinForBlueButtonTestKit
|
|
220
232
|
Attest that the client system under test was able to sucessfully process all of the requested resources for
|
221
233
|
each of the CARIN for Blue Button profiles.
|
222
234
|
)
|
235
|
+
id :c4bb_client_attestation_test_group
|
223
236
|
|
224
237
|
test from: :client_claims_data_attestation
|
225
238
|
end
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is a Coverage resource
|
13
13
|
that conforms to the CARIN for Blue Button [Coverage profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-Coverage.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:Coverage)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is an ExplanationOfBenefit resource
|
13
13
|
that conforms to the CARIN for Blue Button [Outpatient Institutional ExplanationOfBenefit profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-ExplanationOfBenefit-Outpatient-Institutional.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:ExplanationOfBenefit_Inpatient_Institutional)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is an ExplanationOfBenefit resource
|
13
13
|
that conforms to the CARIN for Blue Button [Oral ExplanationOfBenefit profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-ExplanationOfBenefit-Oral.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:ExplanationOfBenefit_Oral)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is an ExplanationOfBenefit resource
|
13
13
|
that conforms to the CARIN for Blue Button [Outpatient Institutional ExplanationOfBenefit profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-ExplanationOfBenefit-Outpatient-Institutional.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:ExplanationOfBenefit_Outpatient_Institutional)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is an ExplanationOfBenefit resource
|
13
13
|
that conforms to the CARIN for Blue Button [Pharmacy ExplanationOfBenefit profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-ExplanationOfBenefit-Pharmacy.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:ExplanationOfBenefit_Pharmacy)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is an ExplanationOfBenefit resource
|
13
13
|
that conforms to the CARIN for Blue Button [Professional NonClinician ExplanationOfBenefit profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-ExplanationOfBenefit-Professional-NonClinician.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:ExplanationOfBenefit_Professional_NonClinician)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is an Organization resource
|
13
13
|
that conforms to the CARIN for Blue Button [Organization profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-Organization.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:Organization)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is a Patient resource
|
13
13
|
that conforms to the CARIN for Blue Button [Patient profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-Patient.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:Patient)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is a Practitioner resource
|
13
13
|
that conforms to the CARIN for Blue Button [Practitioner profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-Practitioner.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:Practitioner)
|
@@ -12,7 +12,6 @@ module CarinForBlueButtonTestKit
|
|
12
12
|
This test verifies that an instance returned by requests made by the client is a RelatedPerson resource
|
13
13
|
that conforms to the CARIN for Blue Button [RelatedPerson profile](https://hl7.org/fhir/us/carin-bb/STU2/StructureDefinition-C4BB-RelatedPerson.html).
|
14
14
|
)
|
15
|
-
input :access_token
|
16
15
|
|
17
16
|
run do
|
18
17
|
resources = previous_resource_requests(:RelatedPerson)
|
@@ -0,0 +1,32 @@
|
|
1
|
+
module CarinForBlueButtonTestKit
|
2
|
+
module MockAuthorization
|
3
|
+
class AuthorizeEndpoint < Inferno::DSL::SuiteEndpoint
|
4
|
+
def test_run_identifier
|
5
|
+
request.params[:client_id]
|
6
|
+
end
|
7
|
+
|
8
|
+
def tags
|
9
|
+
[AUTHORIZE_TAG]
|
10
|
+
end
|
11
|
+
|
12
|
+
def make_response
|
13
|
+
if request.params[:redirect_uri].present?
|
14
|
+
redirect_uri = "#{request.params[:redirect_uri]}?" \
|
15
|
+
"code=#{SecureRandom.hex}&" \
|
16
|
+
"state=#{request.params[:state]}"
|
17
|
+
response.status = 302
|
18
|
+
response.headers['Location'] = redirect_uri
|
19
|
+
else
|
20
|
+
response.status = 400
|
21
|
+
response.format = 'application/fhir+json'
|
22
|
+
response.body = FHIR::OperationOutcome.new(
|
23
|
+
issue: FHIR::OperationOutcome::Issue.new(severity: 'fatal', code: 'required',
|
24
|
+
details: FHIR::CodeableConcept.new(
|
25
|
+
text: 'No redirect_uri provided'
|
26
|
+
))
|
27
|
+
).to_json
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
@@ -1,12 +1,14 @@
|
|
1
1
|
require_relative '../tags'
|
2
2
|
require_relative '../mock_server'
|
3
|
+
require_relative '../mock_authorization'
|
3
4
|
|
4
5
|
module CarinForBlueButtonTestKit
|
5
6
|
class NextPageEndpoint < Inferno::DSL::SuiteEndpoint
|
6
7
|
include CarinForBlueButtonTestKit::MockServer
|
8
|
+
include CarinForBlueButtonTestKit::MockAuthorization
|
7
9
|
|
8
10
|
def test_run_identifier
|
9
|
-
|
11
|
+
extract_client_id_from_bearer_token(request)
|
10
12
|
end
|
11
13
|
|
12
14
|
def make_response
|
@@ -1,14 +1,16 @@
|
|
1
1
|
require_relative '../tags'
|
2
2
|
require_relative '../mock_server'
|
3
|
+
require_relative '../mock_authorization'
|
3
4
|
require_relative '../client_validation_test'
|
4
5
|
|
5
6
|
module CarinForBlueButtonTestKit
|
6
7
|
class ResourceAPIEndpoint < Inferno::DSL::SuiteEndpoint
|
7
8
|
include CarinForBlueButtonTestKit::MockServer
|
9
|
+
include CarinForBlueButtonTestKit::MockAuthorization
|
8
10
|
include CarinForBlueButtonTestKit::ClientValidationTest
|
9
11
|
|
10
12
|
def test_run_identifier
|
11
|
-
|
13
|
+
extract_client_id_from_bearer_token(request)
|
12
14
|
end
|
13
15
|
|
14
16
|
def make_response
|
@@ -1,12 +1,14 @@
|
|
1
1
|
require_relative '../tags'
|
2
2
|
require_relative '../mock_server'
|
3
|
+
require_relative '../mock_authorization'
|
3
4
|
|
4
5
|
module CarinForBlueButtonTestKit
|
5
6
|
class ResourceIDEndpoint < Inferno::DSL::SuiteEndpoint
|
6
7
|
include CarinForBlueButtonTestKit::MockServer
|
8
|
+
include CarinForBlueButtonTestKit::MockAuthorization
|
7
9
|
|
8
10
|
def test_run_identifier
|
9
|
-
|
11
|
+
extract_client_id_from_bearer_token(request)
|
10
12
|
end
|
11
13
|
|
12
14
|
def make_response
|
@@ -1,24 +1,80 @@
|
|
1
1
|
require_relative '../tags'
|
2
|
+
require_relative '../urls'
|
2
3
|
require_relative '../mock_server'
|
4
|
+
require_relative '../mock_authorization'
|
3
5
|
|
4
6
|
module CarinForBlueButtonTestKit
|
5
|
-
|
6
|
-
|
7
|
+
module MockAuthorization
|
8
|
+
CARIN_PATIENT_ID = '888'.freeze # Must exist on the FHIR_REFERENCE_SERVER (env var)
|
7
9
|
|
8
|
-
|
9
|
-
|
10
|
-
end
|
10
|
+
class TokenEndpoint < Inferno::DSL::SuiteEndpoint
|
11
|
+
include CarinForBlueButtonTestKit::MockServer
|
11
12
|
|
12
|
-
|
13
|
-
|
14
|
-
|
13
|
+
def test_run_identifier
|
14
|
+
extract_client_id
|
15
|
+
end
|
15
16
|
|
16
|
-
|
17
|
-
|
18
|
-
|
17
|
+
def tags
|
18
|
+
[TOKEN_TAG]
|
19
|
+
end
|
20
|
+
|
21
|
+
def make_response
|
22
|
+
client_id = extract_client_id
|
23
|
+
access_token = JWT.encode({ inferno_client_id: client_id }, nil, 'none')
|
24
|
+
granted_scopes = SUPPORTED_SCOPES & requested_scopes
|
25
|
+
|
26
|
+
response_hash = { access_token:, scope: granted_scopes.join(' '), token_type: 'bearer',
|
27
|
+
expires_in: 3600 }
|
28
|
+
|
29
|
+
response_hash.merge!(patient: CARIN_PATIENT_ID)
|
30
|
+
|
31
|
+
response.body = response_hash.to_json
|
32
|
+
response.headers['Cache-Control'] = 'no-store'
|
33
|
+
response.headers['Pragma'] = 'no-cache'
|
34
|
+
response.status = 200
|
35
|
+
end
|
36
|
+
|
37
|
+
private
|
38
|
+
|
39
|
+
def extract_client_id
|
40
|
+
# Public client || confidential client asymmetric || confidential client symmetric
|
41
|
+
request.params[:client_id] || extract_client_id_from_client_assertion || extract_client_id_from_basic_auth
|
42
|
+
end
|
43
|
+
|
44
|
+
def extract_client_id_from_client_assertion
|
45
|
+
encoded_jwt = request.params[:client_assertion]
|
46
|
+
return unless encoded_jwt.present?
|
47
|
+
|
48
|
+
jwt_payload =
|
49
|
+
begin
|
50
|
+
JWT.decode(encoded_jwt, nil, false)&.first # skip signature verification
|
51
|
+
rescue StandardError
|
52
|
+
nil
|
53
|
+
end
|
54
|
+
|
55
|
+
jwt_payload['iss'] || jwt_payload['sub'] if jwt_payload.present?
|
56
|
+
end
|
57
|
+
|
58
|
+
def extract_client_id_from_basic_auth
|
59
|
+
encoded_credentials = request.headers['authorization']&.delete_prefix('Basic ')
|
60
|
+
return unless encoded_credentials.present?
|
61
|
+
|
62
|
+
decoded_credentials = Base64.decode64(encoded_credentials)
|
63
|
+
decoded_credentials&.split(':')&.first
|
64
|
+
end
|
65
|
+
|
66
|
+
def requested_scopes
|
67
|
+
auth_request = requests_repo.tagged_requests(result.test_session_id, [AUTHORIZE_TAG]).last
|
68
|
+
return [] unless auth_request
|
19
69
|
|
20
|
-
|
21
|
-
|
70
|
+
auth_params = if auth_request.verb.downcase == 'get'
|
71
|
+
auth_request.query_parameters
|
72
|
+
else
|
73
|
+
URI.decode_www_form(auth_request.request_body)&.to_h
|
74
|
+
end
|
75
|
+
scope_str = auth_params&.dig('scope')
|
76
|
+
scope_str ? URI.decode_www_form_component(scope_str).split : []
|
77
|
+
end
|
22
78
|
end
|
23
79
|
end
|
24
80
|
end
|
@@ -8,14 +8,44 @@ module CarinForBlueButtonTestKit
|
|
8
8
|
description %(
|
9
9
|
This test will receive claims data requests and search requests until the user confirms they are done.
|
10
10
|
)
|
11
|
-
input :
|
11
|
+
input :client_id,
|
12
|
+
title: 'Client ID',
|
13
|
+
description: %(
|
14
|
+
Enter the client ID you will use to connect to this CARIN server via a SMART launch.
|
15
|
+
)
|
16
|
+
|
12
17
|
config options: { accepts_multiple_requests: true }
|
13
18
|
|
19
|
+
def example_client_jwt_payload_part
|
20
|
+
Base64.strict_encode64({ inferno_client_id: client_id }.to_json).delete('=')
|
21
|
+
end
|
22
|
+
|
14
23
|
run do
|
15
24
|
wait(
|
16
|
-
identifier:
|
25
|
+
identifier: client_id,
|
17
26
|
message: %(
|
18
|
-
|
27
|
+
### SMART App Launch
|
28
|
+
|
29
|
+
You may connect to the Inferno CARIN client test server via
|
30
|
+
[SMART App Launch](https://hl7.org/fhir/smart-app-launch/STU2/app-launch.html).
|
31
|
+
Perform the following steps:
|
32
|
+
1. Perform a [Standalone Launch](https://hl7.org/fhir/smart-app-launch/STU2/app-launch.html#step-2-launch-standalone)
|
33
|
+
2. Retrieve .well-known/smart-configuration: `#{smart_configuration_url}`
|
34
|
+
3. Obtain authorization code: `#{authorization_url}`
|
35
|
+
4. Obtain access token: `#{token_url}`
|
36
|
+
5. Access FHIR API
|
37
|
+
|
38
|
+
### Request Identification
|
39
|
+
|
40
|
+
In order to identify requests for this session, Inferno will look for
|
41
|
+
an `Authorization` header with value:
|
42
|
+
|
43
|
+
```
|
44
|
+
Bearer eyJhbGciOiJub25lIn0.#{example_client_jwt_payload_part}.
|
45
|
+
```
|
46
|
+
|
47
|
+
### FHIR API
|
48
|
+
|
19
49
|
Submit CARIN requests via the following method:
|
20
50
|
* Single Resource API: `#{submit_url}?:search_params`, with `:endpoint` replaced with the endpoint you want
|
21
51
|
to reach and `:search_params` replaced with the search parameters for the request.
|
@@ -67,7 +97,8 @@ module CarinForBlueButtonTestKit
|
|
67
97
|
* ExplanationOfBenefit:payee
|
68
98
|
* ExplanationOfBenefit:*
|
69
99
|
|
70
|
-
|
100
|
+
|
101
|
+
[Click here](#{resume_claims_data_url}?test_run_identifier=#{client_id}) when done.
|
71
102
|
),
|
72
103
|
timeout: 900
|
73
104
|
)
|
@@ -23,6 +23,34 @@
|
|
23
23
|
{
|
24
24
|
"mode": "server",
|
25
25
|
"documentation": "The C4BB Server **SHALL**:\n\n1. Support all profiles defined in this Implementation Guide..\n2. Implement the RESTful behavior according to the FHIR specification.\n3. Return the following response classes:\n - (Status 400): invalid parameter\n - (Status 401/4xx): unauthorized request\n - (Status 403): insufficient scope\n - (Status 404): unknown resource\n - (Status 410): deleted resource.\n4. Support json source formats for all CARIN-BB interactions.\n5. Identify the CARIN-BB profiles supported as part of the FHIR `meta.profile` attribute for each instance.\n6. Support the searchParameters on each profile individually and in combination.\n\nThe C4BB Server **SHOULD**:\n\n1. Support xml source formats for all C4BB interactions.\n",
|
26
|
+
"security": {
|
27
|
+
"extension": [
|
28
|
+
{
|
29
|
+
"url": "http://fhir-registry.smarthealthit.org/StructureDefinition/oauth-uris",
|
30
|
+
"extension": [
|
31
|
+
{
|
32
|
+
"url": "token",
|
33
|
+
"valueUri": "<%= Inferno::Application['base_url'] %>/custom/c4bb_v200_client/mock_auth/token"
|
34
|
+
},
|
35
|
+
{
|
36
|
+
"url": "authorize",
|
37
|
+
"valueUri": "<%= Inferno::Application['base_url'] %>/custom/c4bb_v200_client/mock_auth/authorization"
|
38
|
+
}
|
39
|
+
]
|
40
|
+
}
|
41
|
+
],
|
42
|
+
"service": [
|
43
|
+
{
|
44
|
+
"coding": [
|
45
|
+
{
|
46
|
+
"system": "http://terminology.hl7.org/CodeSystem/restful-security-service",
|
47
|
+
"code": "SMART-on-FHIR"
|
48
|
+
}
|
49
|
+
],
|
50
|
+
"text": "OAuth2 using SMART-on-FHIR profile (see http://docs.smarthealthit.org)"
|
51
|
+
}
|
52
|
+
]
|
53
|
+
},
|
26
54
|
"resource": [
|
27
55
|
{
|
28
56
|
"extension": [
|
@@ -0,0 +1,35 @@
|
|
1
|
+
module CarinForBlueButtonTestKit
|
2
|
+
module MockAuthorization
|
3
|
+
RSA_PRIVATE_KEY = OpenSSL::PKey::RSA.generate(2048)
|
4
|
+
RSA_PUBLIC_KEY = RSA_PRIVATE_KEY.public_key
|
5
|
+
|
6
|
+
module_function
|
7
|
+
|
8
|
+
def extract_client_id_from_bearer_token(request)
|
9
|
+
token = request.headers['authorization']&.delete_prefix('Bearer ')
|
10
|
+
jwt =
|
11
|
+
begin
|
12
|
+
JWT.decode(token, nil, false)
|
13
|
+
rescue StandardError
|
14
|
+
nil
|
15
|
+
end
|
16
|
+
jwt&.first&.dig('inferno_client_id')
|
17
|
+
end
|
18
|
+
|
19
|
+
def jwks(_env)
|
20
|
+
response_body = {
|
21
|
+
keys: [
|
22
|
+
{
|
23
|
+
kty: 'RSA',
|
24
|
+
alg: 'RS256',
|
25
|
+
n: Base64.urlsafe_encode64(RSA_PUBLIC_KEY.n.to_s(2), padding: false),
|
26
|
+
e: Base64.urlsafe_encode64(RSA_PUBLIC_KEY.e.to_s(2), padding: false),
|
27
|
+
use: 'sig'
|
28
|
+
}
|
29
|
+
]
|
30
|
+
}.to_json
|
31
|
+
|
32
|
+
[200, { 'Content-Type' => 'application/json' }, [response_body]]
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
@@ -2,7 +2,6 @@ require_relative 'user_input_response'
|
|
2
2
|
require_relative 'urls'
|
3
3
|
require_relative 'collection'
|
4
4
|
require_relative 'client_validation_test'
|
5
|
-
# require_relative 'metadata/mock_capability_statement'
|
6
5
|
|
7
6
|
module CarinForBlueButtonTestKit
|
8
7
|
# Serve responses to CARIN requests
|
@@ -13,6 +12,8 @@ module CarinForBlueButtonTestKit
|
|
13
12
|
module MockServer
|
14
13
|
include URLs
|
15
14
|
|
15
|
+
SUPPORTED_SCOPES = ['launch', 'patient/*.rs', 'user/*.rs', 'offline_access'].freeze
|
16
|
+
|
16
17
|
def server_proxy
|
17
18
|
@server_proxy ||= Faraday.new(
|
18
19
|
url: ENV.fetch('FHIR_REFERENCE_SERVER'),
|
@@ -25,12 +26,6 @@ module CarinForBlueButtonTestKit
|
|
25
26
|
end
|
26
27
|
end
|
27
28
|
|
28
|
-
def token_response(request, _test = nil, _test_result = nil)
|
29
|
-
# Placeholder for a more complete mock token endpoint
|
30
|
-
response.body = { access_token: SecureRandom.hex, token_type: 'bearer', expires_in: 300 }.to_json
|
31
|
-
response.status = 200
|
32
|
-
end
|
33
|
-
|
34
29
|
def error_response_resource(request)
|
35
30
|
server_response = server_proxy.get('Patient', { _id: 888 })
|
36
31
|
response_resource = FHIR.from_contents(server_response.body)
|
@@ -97,9 +92,43 @@ module CarinForBlueButtonTestKit
|
|
97
92
|
end
|
98
93
|
|
99
94
|
def get_metadata
|
95
|
+
erb_template = ERB.new(
|
96
|
+
File.read(
|
97
|
+
File.join(__dir__,
|
98
|
+
'metadata/mock_capability_statement.json.erb')
|
99
|
+
)
|
100
|
+
)
|
101
|
+
capability_statement = JSON.parse(erb_template.result).to_json
|
102
|
+
|
100
103
|
proc {
|
101
104
|
[200, { 'Content-Type' => 'application/fhir+json;charset=utf-8' },
|
102
|
-
[
|
105
|
+
[capability_statement]]
|
106
|
+
}
|
107
|
+
end
|
108
|
+
|
109
|
+
def carin_smart_config
|
110
|
+
response_body =
|
111
|
+
{
|
112
|
+
authorization_endpoint: authorization_url,
|
113
|
+
token_endpoint: token_url,
|
114
|
+
token_endpoint_auth_methods_supported: ['private_key_jwt'],
|
115
|
+
token_endpoint_auth_signing_alg_values_supported: ['RS256'],
|
116
|
+
grant_types_supported: ['authorization_code'],
|
117
|
+
scopes_supported: SUPPORTED_SCOPES,
|
118
|
+
response_types_supported: ['code'],
|
119
|
+
code_challenge_methods_supported: ['S256'],
|
120
|
+
capabilities: [
|
121
|
+
'launch-ehr',
|
122
|
+
'permission-patient',
|
123
|
+
'permission-user',
|
124
|
+
'client-public',
|
125
|
+
'client-confidential-symmetric',
|
126
|
+
'client-confidential-asymmetric'
|
127
|
+
]
|
128
|
+
}.to_json
|
129
|
+
|
130
|
+
proc {
|
131
|
+
[200, { 'Content-Type' => 'application/json' }, [response_body]]
|
103
132
|
}
|
104
133
|
end
|
105
134
|
|
@@ -137,6 +166,10 @@ module CarinForBlueButtonTestKit
|
|
137
166
|
request.query_parameters['token']
|
138
167
|
end
|
139
168
|
|
169
|
+
def extract_test_run_identifier_from_query_params(request)
|
170
|
+
request.query_parameters['test_run_identifier']
|
171
|
+
end
|
172
|
+
|
140
173
|
# Pull resource type from url
|
141
174
|
# e.g. http://example.org/fhir/Patient?_id=123 -> Patient
|
142
175
|
# @private
|
@@ -156,7 +189,8 @@ module CarinForBlueButtonTestKit
|
|
156
189
|
|
157
190
|
def mock_operation_outcome_resource
|
158
191
|
FHIR.from_contents(File.read(
|
159
|
-
|
192
|
+
File.join(__dir__,
|
193
|
+
'metadata/mock_operation_outcome_resource.json')
|
160
194
|
))
|
161
195
|
end
|
162
196
|
|