davinci_dtr_test_kit 0.16.0 → 0.16.1
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/full_ehr_postman_dinner_order_example.json.erb +41 -0
- data/config/presets/full_ehr_postman_respiratory_device_example.json +1 -1
- data/config/presets/smart_app_postman_dinner_order_example.json +8 -1
- data/config/presets/smart_app_postman_respiratory_device_example.json +1 -1
- data/lib/davinci_dtr_test_kit/certs/InfernoCA.key +52 -0
- data/lib/davinci_dtr_test_kit/certs/InfernoCA.pem +35 -0
- data/lib/davinci_dtr_test_kit/certs/TestKit.pem +32 -0
- data/lib/davinci_dtr_test_kit/certs/TestKitPrivateKey.key +28 -0
- data/lib/davinci_dtr_test_kit/client_groups/adaptive_questionnaire/custom/dtr_custom_next_question_response_validation_test.rb +95 -0
- data/lib/davinci_dtr_test_kit/client_groups/adaptive_questionnaire/custom/dtr_full_ehr_custom_adaptive_request_test.rb +87 -0
- data/lib/davinci_dtr_test_kit/client_groups/adaptive_questionnaire/custom/dtr_full_ehr_custom_adaptive_workflow_group.rb +136 -0
- data/lib/davinci_dtr_test_kit/client_groups/adaptive_questionnaire/custom/dtr_smart_app_custom_adaptive_request_test.rb +171 -0
- data/lib/davinci_dtr_test_kit/client_groups/adaptive_questionnaire/custom/dtr_smart_app_custom_adaptive_workflow_group.rb +146 -0
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_adaptive_next_question_retrieval_group.rb +3 -3
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_full_ehr_adaptive_dinner_workflow_group.rb +21 -11
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_full_ehr_adaptive_initial_retrieval_group.rb +6 -6
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_smart_app_adaptive_dinner_workflow_group.rb +5 -5
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_smart_app_adaptive_initial_retrieval_group.rb +5 -5
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire}/dtr_adaptive_next_question_request_test.rb +9 -24
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire}/dtr_adaptive_next_question_request_validation_test.rb +36 -17
- data/lib/davinci_dtr_test_kit/client_groups/adaptive_questionnaire/dtr_adaptive_response_validation_test.rb +130 -0
- data/lib/davinci_dtr_test_kit/client_groups/auth/dtr_client_payer_auth_smart_group.rb +29 -0
- data/lib/davinci_dtr_test_kit/client_groups/auth/dtr_client_payer_auth_udap_group.rb +29 -0
- data/lib/davinci_dtr_test_kit/client_groups/custom_static/dtr_full_ehr_custom_static_workflow_group.rb +15 -14
- data/lib/davinci_dtr_test_kit/client_groups/custom_static/dtr_smart_app_custom_static_workflow_group.rb +5 -5
- data/lib/davinci_dtr_test_kit/client_groups/dinner_static/dtr_full_ehr_static_dinner_workflow_group.rb +14 -10
- data/lib/davinci_dtr_test_kit/client_groups/dinner_static/dtr_smart_app_static_dinner_workflow_group.rb +1 -1
- data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → full_ehr}/dtr_full_ehr_adaptive_request_test.rb +11 -14
- data/lib/davinci_dtr_test_kit/client_groups/full_ehr/dtr_full_ehr_questionnaire_package_request_test.rb +9 -17
- data/lib/davinci_dtr_test_kit/client_groups/full_ehr/dtr_full_ehr_questionnaire_response_correctness_test.rb +10 -1
- data/lib/davinci_dtr_test_kit/client_groups/full_ehr/dtr_full_ehr_store_attestation_test.rb +3 -3
- data/lib/davinci_dtr_test_kit/client_groups/light_ehr/fhir_context_references_test.rb +4 -5
- data/lib/davinci_dtr_test_kit/client_groups/must_support/dtr_full_ehr_ms_questionnaire_package_request_test.rb +75 -0
- data/lib/davinci_dtr_test_kit/client_groups/must_support/dtr_full_ehr_questionnaire_must_support_group.rb +85 -0
- data/lib/davinci_dtr_test_kit/client_groups/must_support/dtr_must_support_attestation_test.rb +39 -0
- data/lib/davinci_dtr_test_kit/client_groups/must_support/dtr_questionnaire_must_support_test.rb +42 -0
- data/lib/davinci_dtr_test_kit/client_groups/must_support/dtr_smart_app_ms_questionnaire_package_request_test.rb +148 -0
- data/lib/davinci_dtr_test_kit/client_groups/must_support/dtr_smart_app_questionnaire_must_support_group.rb +85 -0
- data/lib/davinci_dtr_test_kit/client_groups/must_support/questionnaire_must_support_elements.rb +55 -0
- data/lib/davinci_dtr_test_kit/client_groups/payer_registration/configuration_display_smart_test.rb +35 -0
- data/lib/davinci_dtr_test_kit/client_groups/payer_registration/configuration_display_udap_test.rb +35 -0
- data/lib/davinci_dtr_test_kit/client_groups/payer_registration/dtr_client_registration_group.rb +48 -0
- data/lib/davinci_dtr_test_kit/client_groups/shared/dtr_custom_questionnaire_expressions_test.rb +36 -0
- data/lib/davinci_dtr_test_kit/client_groups/shared/dtr_custom_questionnaire_extensions_test.rb +32 -0
- data/lib/davinci_dtr_test_kit/client_groups/{custom_static → shared}/dtr_custom_questionnaire_libraries_test.rb +7 -2
- data/lib/davinci_dtr_test_kit/client_groups/{custom_static → shared}/dtr_custom_questionnaire_package_validation_test.rb +6 -2
- data/lib/davinci_dtr_test_kit/client_groups/shared/dtr_questionnaire_package_request_validation_test.rb +6 -2
- data/lib/davinci_dtr_test_kit/client_groups/shared/dtr_questionnaire_response_prepopulation_test.rb +7 -1
- data/lib/davinci_dtr_test_kit/client_groups/smart_app/dtr_smart_app_questionnaire_response_correctness_test.rb +4 -3
- data/lib/davinci_dtr_test_kit/descriptions.rb +8 -0
- data/lib/davinci_dtr_test_kit/docs/dtr_full_ehr_suite_description_v201.md +145 -78
- data/lib/davinci_dtr_test_kit/docs/dtr_smart_app_suite_description_v201.md +4 -3
- data/lib/davinci_dtr_test_kit/dtr_client_options.rb +13 -0
- data/lib/davinci_dtr_test_kit/dtr_full_ehr_suite.rb +47 -7
- data/lib/davinci_dtr_test_kit/dtr_questionnaire_response_validation.rb +33 -21
- data/lib/davinci_dtr_test_kit/dtr_smart_app_suite.rb +7 -4
- data/lib/davinci_dtr_test_kit/endpoints/mock_ehr.rb +1 -1
- data/lib/davinci_dtr_test_kit/endpoints/mock_payer/full_ehr_next_question_endpoint.rb +20 -1
- data/lib/davinci_dtr_test_kit/endpoints/mock_payer/full_ehr_questionnaire_package_endpoint.rb +21 -1
- data/lib/davinci_dtr_test_kit/endpoints/mock_payer/next_question_endpoint.rb +29 -4
- data/lib/davinci_dtr_test_kit/endpoints/mock_payer/questionnaire_package_endpoint.rb +1 -1
- data/lib/davinci_dtr_test_kit/endpoints/mock_udap_smart_server/token_endpoint.rb +36 -0
- data/lib/davinci_dtr_test_kit/requirements/davinci-dtr-test-kit_out_of_scope_requirements.csv +6 -5
- data/lib/davinci_dtr_test_kit/requirements/davinci-dtr-test-kit_requirements.csv +10 -9
- data/lib/davinci_dtr_test_kit/requirements/generated/davinci-dtr-test-kit_requirements_coverage.csv +21 -21
- data/lib/davinci_dtr_test_kit/urls.rb +21 -4
- data/lib/davinci_dtr_test_kit/version.rb +2 -2
- metadata +59 -21
- data/config/presets/full_ehr_postman_dinner_order_example_postman.json +0 -19
- data/lib/davinci_dtr_test_kit/client_groups/custom_static/dtr_custom_questionnaire_expressions_test.rb +0 -22
- data/lib/davinci_dtr_test_kit/client_groups/custom_static/dtr_custom_questionnaire_extensions_test.rb +0 -19
- data/lib/davinci_dtr_test_kit/client_groups/dinner_adaptive/dtr_adaptive_response_validation_test.rb +0 -68
- /data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_adaptive_completion_group.rb +0 -0
- /data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → adaptive_questionnaire/dinner_order}/dtr_adaptive_followup_questions_group.rb +0 -0
- /data/lib/davinci_dtr_test_kit/client_groups/{dinner_adaptive → smart_app}/dtr_smart_app_adaptive_request_test.rb +0 -0
@@ -0,0 +1,95 @@
|
|
1
|
+
module DaVinciDTRTestKit
|
2
|
+
class DTRCustomNextQuestionResponseValidationTest < Inferno::Test
|
3
|
+
id :dtr_custom_next_questionnaire_validation
|
4
|
+
title '[USER INPUT VERIFICATION] Custom Questionnaires for $next-question Responses are valid for this workflow'
|
5
|
+
description %(
|
6
|
+
Inferno will validate that the user-provided Questionnaire resources to be included in
|
7
|
+
each `$next-question` response are correct for this workflow.
|
8
|
+
|
9
|
+
The test verifies that:
|
10
|
+
1. All provided Questionnaires have the same ID as the contained Questionnaire in the
|
11
|
+
`QuestionnaireResponse` of the `$next-question` request.
|
12
|
+
2. Each provided Questionnaire includes all previously presented questions along with
|
13
|
+
the next question or set of questions.
|
14
|
+
|
15
|
+
If any of these conditions are not met, the test will fail.
|
16
|
+
)
|
17
|
+
|
18
|
+
input :custom_next_question_questionnaires,
|
19
|
+
title: 'Custom Questionnaire resources to include in each $next-question Response',
|
20
|
+
description: %(
|
21
|
+
Provide a JSON list of Questionnaire resources for Inferno to use when updating
|
22
|
+
the contained Questionnaire in the `QuestionnaireResponse` received in each
|
23
|
+
`$next-question` request.
|
24
|
+
|
25
|
+
Each `$next-question` request will correspond to the next item in the provided list,
|
26
|
+
and Inferno will replace the contained Questionnaire with the corresponding resource
|
27
|
+
before returning the updated `QuestionnaireResponse`.
|
28
|
+
|
29
|
+
The provided Questionnaires must contain the next question or set of questions in
|
30
|
+
sequence, ensuring a proper progression of the adaptive questionnaire workflow.
|
31
|
+
),
|
32
|
+
type: 'textarea'
|
33
|
+
|
34
|
+
def next_request_tag
|
35
|
+
config.options[:next_tag]
|
36
|
+
end
|
37
|
+
|
38
|
+
def extract_link_ids(questionnaire_items)
|
39
|
+
questionnaire_items&.each_with_object([]) do |item, link_ids|
|
40
|
+
link_ids << item.linkId
|
41
|
+
|
42
|
+
link_ids.concat(extract_link_ids(item.item)) if item.item.present?
|
43
|
+
end
|
44
|
+
end
|
45
|
+
|
46
|
+
def validate_correctness_of_custom_next_questionnaire(custom_questionnaire, contained_questionnaire)
|
47
|
+
custom_items_link_ids = extract_link_ids(custom_questionnaire.item) || []
|
48
|
+
contained_items_link_ids = extract_link_ids(contained_questionnaire.item) || []
|
49
|
+
missing_items_ids = contained_items_link_ids - custom_items_link_ids
|
50
|
+
|
51
|
+
error_msg = %(
|
52
|
+
Custom Questionnaire must include all previous questions along with the next question or set of questions.
|
53
|
+
)
|
54
|
+
add_message('error', error_msg) if custom_items_link_ids.length <= contained_items_link_ids.length
|
55
|
+
|
56
|
+
error_msg = %(
|
57
|
+
Custom Questionnaire must include all previous questions. The following items are missing:
|
58
|
+
questions with Link ID `#{missing_items_ids.to_sentence}`.
|
59
|
+
)
|
60
|
+
add_message('error', error_msg) if missing_items_ids.present?
|
61
|
+
end
|
62
|
+
|
63
|
+
run do
|
64
|
+
load_tagged_requests next_request_tag
|
65
|
+
skip_if requests.blank?, 'A $next-question request must be made prior to running this test'
|
66
|
+
assert_valid_json custom_next_question_questionnaires, 'Custom $next-question Questionnaires is not valid JSON'
|
67
|
+
|
68
|
+
skip_if scratch[:contained_questionnaires].nil?, %(
|
69
|
+
Unable to validate user-provided Questionnaires: no valid `$next-question` requests
|
70
|
+
containing a Questionnaire were received.
|
71
|
+
)
|
72
|
+
|
73
|
+
custom_questionnaires = [JSON.parse(custom_next_question_questionnaires)].flatten
|
74
|
+
custom_questionnaires.each do |q|
|
75
|
+
custom_questionnaire = FHIR.from_contents(q.to_json)
|
76
|
+
assert custom_questionnaire, "The custom Questionnaire #{q[:id]} provided is not a valid FHIR resource"
|
77
|
+
assert_resource_type(:questionnaire, resource: custom_questionnaire)
|
78
|
+
|
79
|
+
contained_questionnaire = scratch[:contained_questionnaires].find { |cq| cq.id == custom_questionnaire.id }
|
80
|
+
assert contained_questionnaire, %(
|
81
|
+
Unable to validate the provided custom Questionnaire `#{q[:id]}`: no valid `$next-question` request
|
82
|
+
was found containing a Questionnaire with a matching ID.
|
83
|
+
)
|
84
|
+
|
85
|
+
validate_correctness_of_custom_next_questionnaire(custom_questionnaire, contained_questionnaire)
|
86
|
+
rescue Inferno::Exceptions::AssertionException => e
|
87
|
+
add_message('error', "Questionnaire `#{q[:id]}`: #{e.message}")
|
88
|
+
next
|
89
|
+
end
|
90
|
+
|
91
|
+
assert messages.none? { |message| message[:type] == 'error' },
|
92
|
+
'Custom Questionnaire provided is not valid for this workflow'
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
@@ -0,0 +1,87 @@
|
|
1
|
+
require_relative '../../../descriptions'
|
2
|
+
require_relative '../../../urls'
|
3
|
+
|
4
|
+
module DaVinciDTRTestKit
|
5
|
+
class DTRFullEHRCustomAdaptiveRequestTest < Inferno::Test
|
6
|
+
include URLs
|
7
|
+
|
8
|
+
id :dtr_full_ehr_custom_adative_request
|
9
|
+
title 'Client can complete the DTR Adaptive Questionnaire workflow'
|
10
|
+
description %(
|
11
|
+
This test waits for client requests to retrieve and progress through an adaptive questionnaire workflow.
|
12
|
+
|
13
|
+
1. **Questionnaire Package Request**: The client should invoke the `$questionnaire-package` operation
|
14
|
+
to retrieve the adaptive questionnaire package. Inferno will respond with the user-provided
|
15
|
+
empty adaptive questionnaire.
|
16
|
+
|
17
|
+
2. **Next Question Requests**: The client should invoke the `$next-question` operation to request
|
18
|
+
the next set of questions. Inferno will respond sequentially with the next Questionnaire from
|
19
|
+
the user-provided list. If a `$next-question` request is received when the list is empty,
|
20
|
+
Inferno will mark the `QuestionnaireResponse` as completed.
|
21
|
+
)
|
22
|
+
verifies_requirements 'hl7.fhir.us.davinci-dtr_2.0.1@165', 'hl7.fhir.us.davinci-dtr_2.0.1@262',
|
23
|
+
'hl7.fhir.us.davinci-dtr_2.0.1@264'
|
24
|
+
|
25
|
+
config options: { accepts_multiple_requests: true }
|
26
|
+
|
27
|
+
input :custom_questionnaire_package_response, :custom_next_question_questionnaires
|
28
|
+
input :client_id,
|
29
|
+
title: 'Client Id',
|
30
|
+
type: 'text',
|
31
|
+
optional: true,
|
32
|
+
locked: true,
|
33
|
+
description: INPUT_CLIENT_ID_LOCKED
|
34
|
+
|
35
|
+
run do
|
36
|
+
assert_valid_json(
|
37
|
+
custom_questionnaire_package_response,
|
38
|
+
'Custom questionnaire package response is not a valid json'
|
39
|
+
)
|
40
|
+
assert_valid_json(custom_next_question_questionnaires, 'Custom next questionnaires input is not a valid json')
|
41
|
+
|
42
|
+
custom_qp = JSON.parse(custom_questionnaire_package_response)
|
43
|
+
custom_questionnaires = JSON.parse(custom_next_question_questionnaires)
|
44
|
+
assert custom_qp.present?, %(
|
45
|
+
Custom questionnaire package response is empty, please provide a custom questionnaire package response
|
46
|
+
for the $questionnaire-package request
|
47
|
+
)
|
48
|
+
assert custom_questionnaires.present?, %(
|
49
|
+
'Custom questionnaires list is empty, please provide a list of Custom Questionnaire resources
|
50
|
+
to include in each $next-question Response.
|
51
|
+
)
|
52
|
+
|
53
|
+
wait(
|
54
|
+
identifier: client_id,
|
55
|
+
message: %(
|
56
|
+
### Adaptive Questionnaire Workflow
|
57
|
+
|
58
|
+
1. **Questionnaire Package Request**:
|
59
|
+
- Invoke the `$questionnaire-package` operation by sending a POST request to the following endpoint
|
60
|
+
to retrieve the adaptive questionnaire package:
|
61
|
+
|
62
|
+
`#{questionnaire_package_url}`
|
63
|
+
|
64
|
+
- Inferno will respond with the user-provided empty adaptive questionnaire.
|
65
|
+
|
66
|
+
2. **Next Question Requests**:
|
67
|
+
- After receiving the questionnaire package, invoke the `$next-question` operation by sending
|
68
|
+
a POST request to the following endpoint:
|
69
|
+
|
70
|
+
`#{next_url}`
|
71
|
+
|
72
|
+
- Repeat this request **multiple times**, once for each Questionnaire provided in the user-supplied list.
|
73
|
+
- Inferno will sequentially respond with the corresponding Questionnaire from the list.
|
74
|
+
- If a `$next-question` request is received when the list is empty, Inferno will mark
|
75
|
+
the `QuestionnaireResponse` as completed.
|
76
|
+
|
77
|
+
Inferno will wait for all expected requests to be made.
|
78
|
+
|
79
|
+
### Continuing the Tests
|
80
|
+
|
81
|
+
Once all required `$next-question` requests have been made,
|
82
|
+
[Click here](#{resume_pass_url}?token=#{client_id}) to continue.
|
83
|
+
)
|
84
|
+
)
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
@@ -0,0 +1,136 @@
|
|
1
|
+
require_relative '../../../tags'
|
2
|
+
require_relative '../../full_ehr/dtr_full_ehr_launch_attestation_test'
|
3
|
+
require_relative 'dtr_full_ehr_custom_adaptive_request_test'
|
4
|
+
require_relative '../../shared/dtr_questionnaire_package_request_validation_test'
|
5
|
+
require_relative '../dtr_adaptive_next_question_request_validation_test'
|
6
|
+
require_relative '../dtr_adaptive_response_validation_test'
|
7
|
+
require_relative '../../shared/dtr_custom_questionnaire_package_validation_test'
|
8
|
+
require_relative '../../shared/dtr_custom_questionnaire_libraries_test'
|
9
|
+
require_relative 'dtr_custom_next_question_response_validation_test'
|
10
|
+
require_relative '../../shared/dtr_custom_questionnaire_extensions_test'
|
11
|
+
require_relative '../../shared/dtr_custom_questionnaire_expressions_test'
|
12
|
+
require_relative '../../shared/dtr_prepopulation_attestation_test'
|
13
|
+
require_relative '../../shared/dtr_prepopulation_override_attestation_test'
|
14
|
+
require_relative '../../full_ehr/dtr_full_ehr_store_attestation_test'
|
15
|
+
|
16
|
+
module DaVinciDTRTestKit
|
17
|
+
class DTRFullEHRCustomAdaptiveWorkflowGroup < Inferno::TestGroup
|
18
|
+
id :dtr_full_ehr_custom_adaptive_workflow
|
19
|
+
title 'Adaptive Questionnaire Workflow'
|
20
|
+
description %(
|
21
|
+
This group validates that a DTR Full EHR client can perform a full DTR Adaptive Questionnaire workflow.
|
22
|
+
Testers will provide a custom adaptive Questionnaire package for the test, along with a list
|
23
|
+
(JSON array) of Questionnaires to be included in each `$next-question` response.
|
24
|
+
|
25
|
+
As part of this workflow, the Full EHR system must demonstrate its ability to:
|
26
|
+
|
27
|
+
1. Request the Questionnaire using the `$questionnaire-package` operation.
|
28
|
+
2. Support the tester in completing the questionnaire through multiple `$next-question` interactions, including:
|
29
|
+
- Rendering the questionnaire.
|
30
|
+
- Pre-populating answers into the questionnaire.
|
31
|
+
- Allowing the tester to manually enter responses, including overriding pre-populated answers.
|
32
|
+
3. Complete and store the `QuestionnaireResponse` for future use.
|
33
|
+
|
34
|
+
Inferno will process `$next-question` requests dynamically:
|
35
|
+
- Each request will receive the next Questionnaire from the provided list.
|
36
|
+
- If a `$next-question` request is received when the list is empty, Inferno will mark
|
37
|
+
the `QuestionnaireResponse` as completed.
|
38
|
+
|
39
|
+
At least two answers should be pre-populated across all sets of questions.
|
40
|
+
)
|
41
|
+
run_as_group
|
42
|
+
config(
|
43
|
+
options: { form_type: 'adaptive', next_tag: "custom_#{CLIENT_NEXT_TAG}" },
|
44
|
+
inputs: {
|
45
|
+
custom_questionnaire_package_response: {
|
46
|
+
name: 'adaptive_custom_questionnaire_package_response',
|
47
|
+
title: 'Custom Questionnaire Package Response JSON for Adaptive form',
|
48
|
+
description: %(
|
49
|
+
A JSON PackageBundle may be provided here to replace Inferno's response to
|
50
|
+
the $questionnaire-package request. Note: Ensure that the questionnaire package
|
51
|
+
has an empty Adaptive Questionnaire.
|
52
|
+
)
|
53
|
+
}
|
54
|
+
}
|
55
|
+
)
|
56
|
+
|
57
|
+
group do
|
58
|
+
id :dtr_full_ehr_custom_adaptive_retrieval
|
59
|
+
title 'Retrieving the Adaptive Questionnaire'
|
60
|
+
|
61
|
+
# Test 0: attest to launch
|
62
|
+
test from: :dtr_full_ehr_launch_attest,
|
63
|
+
config: {
|
64
|
+
options: {
|
65
|
+
attestation_message: 'I attest that DTR has been launched in the context of a patient with data that will exercise pre-population logic in the provided static questionnaire resulting in at least 2 pre-populated answers.' # rubocop:disable Layout/LineLength
|
66
|
+
}
|
67
|
+
},
|
68
|
+
title: 'Launch DTR (Attestation)'
|
69
|
+
# Test 1: Recieve questionnaire-package and next-question requests
|
70
|
+
test from: :dtr_full_ehr_custom_adative_request
|
71
|
+
# Test 2: validate the $questionnaire-package request body
|
72
|
+
test from: :dtr_qp_request_validation
|
73
|
+
# Test 3: validate the $next-question requests body
|
74
|
+
test from: :dtr_adaptive_next_question_request_validation
|
75
|
+
# Test 4: validate the QuestionnaireResponse in the input parameter
|
76
|
+
test from: :dtr_adaptive_response_validation do
|
77
|
+
description %(
|
78
|
+
Verify that all submitted QuestionnaireResponse resources meet the following criteria:
|
79
|
+
- Conform to the [SDCQuestionnaireResponseAdapt](http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaireresponse-adapt).
|
80
|
+
- Include source extensions indicating whether answers were manually entered,
|
81
|
+
automatically pre-populated, or manually overridden (for `completed` QuestionnaireResponse).
|
82
|
+
- Provide answers for all required items in their contained Questionnaire.
|
83
|
+
)
|
84
|
+
input :custom_next_question_questionnaires
|
85
|
+
end
|
86
|
+
# Test 5: validate the user provided $questionnaire-package response
|
87
|
+
test from: :dtr_custom_qp_validation
|
88
|
+
# Test 6: verify the custom response has the necessary libraries for pre-population
|
89
|
+
test from: :dtr_custom_questionnaire_libraries
|
90
|
+
# Test 7: validate the user provided $next-question questionnaires
|
91
|
+
test from: :dtr_custom_next_questionnaire_validation
|
92
|
+
# Test 8: verify the custom responses has the necessary extensions for pre-population
|
93
|
+
test from: :dtr_custom_questionnaire_extensions do
|
94
|
+
title %(
|
95
|
+
[USER INPUT VERIFICATION] Custom Questionnaires for $next-question Responses contain extensions
|
96
|
+
necessary for pre-population
|
97
|
+
)
|
98
|
+
input :custom_next_question_questionnaires
|
99
|
+
end
|
100
|
+
# Test 9: verify custom responses has necessary expressions for pre-population
|
101
|
+
test from: :dtr_custom_questionnaire_expressions do
|
102
|
+
title %(
|
103
|
+
[USER INPUT VERIFICATION] Custom Questionnaires for $next-question Responses contain items with
|
104
|
+
expressions necessary for pre-population
|
105
|
+
)
|
106
|
+
input :custom_next_question_questionnaires
|
107
|
+
end
|
108
|
+
end
|
109
|
+
|
110
|
+
group do
|
111
|
+
title 'Attestation: Questionnaire Pre-Population and Rendering'
|
112
|
+
description %(
|
113
|
+
This group verifies that the tester has properly followed pre-population and rendering
|
114
|
+
directives while interacting with and filling out the questionnaire.
|
115
|
+
|
116
|
+
After retrieving and completing the questionnaire in their client system, the tester will
|
117
|
+
attest that:
|
118
|
+
1. The questionnaire was pre-populated as expected, with at least two answers pre-populated
|
119
|
+
across all sets of questions.
|
120
|
+
2. The questionnaire was rendered correctly according to its defined structure.
|
121
|
+
3. They were able to manually enter responses, including overriding pre-populated answers.
|
122
|
+
)
|
123
|
+
test from: :dtr_prepopulation_attest
|
124
|
+
test from: :dtr_prepopulation_override_attest
|
125
|
+
end
|
126
|
+
|
127
|
+
group do
|
128
|
+
title 'Attestation: QuestionnaireResponse Completion and Storage'
|
129
|
+
description %(
|
130
|
+
The tester will attest to the completion of the questionnaire such that the results are stored for later use.
|
131
|
+
)
|
132
|
+
|
133
|
+
test from: :dtr_full_ehr_store_attest
|
134
|
+
end
|
135
|
+
end
|
136
|
+
end
|
@@ -0,0 +1,171 @@
|
|
1
|
+
require_relative '../../../urls'
|
2
|
+
|
3
|
+
module DaVinciDTRTestKit
|
4
|
+
class DTRSmartAppCustomAdaptiveRequestTest < Inferno::Test
|
5
|
+
include URLs
|
6
|
+
|
7
|
+
id :dtr_smart_app_custom_adative_request
|
8
|
+
title 'Client can complete the DTR Adaptive Questionnaire workflow'
|
9
|
+
description %(
|
10
|
+
This test waits for client requests to retrieve and progress through an adaptive questionnaire workflow.
|
11
|
+
|
12
|
+
1. **Questionnaire Package Request**: The client should invoke the `$questionnaire-package` operation
|
13
|
+
to retrieve the adaptive questionnaire package. Inferno will respond with the user-provided
|
14
|
+
empty adaptive questionnaire.
|
15
|
+
|
16
|
+
2. **Next Question Requests**: The client should invoke the `$next-question` operation to request
|
17
|
+
the next set of questions. Inferno will respond sequentially with the next Questionnaire from
|
18
|
+
the user-provided list. If a `$next-question` request is received when the list is empty,
|
19
|
+
Inferno will mark the `QuestionnaireResponse` as completed.
|
20
|
+
)
|
21
|
+
config options: { accepts_multiple_requests: true }
|
22
|
+
input :smart_app_launch,
|
23
|
+
type: 'radio',
|
24
|
+
title: 'SMART App Launch',
|
25
|
+
description: 'How will the DTR SMART App launch?',
|
26
|
+
options: { list_options: [{ label: 'EHR Launch from Inferno', value: 'ehr' },
|
27
|
+
{ label: 'Standalone Launch', value: 'standalone' }] }
|
28
|
+
input :client_id
|
29
|
+
input :launch_uri,
|
30
|
+
optional: true,
|
31
|
+
description: 'Required if "Launch from Inferno" is selected'
|
32
|
+
input :adaptive_smart_patient_id,
|
33
|
+
optional: true,
|
34
|
+
title: 'SMART App Launch Patient ID (Custom Adaptive)',
|
35
|
+
type: 'text',
|
36
|
+
description: %(
|
37
|
+
Patient instance ID to be provided by Inferno as the patient as a part of the SMART App Launch.
|
38
|
+
),
|
39
|
+
default: 'pat015'
|
40
|
+
input :adaptive_smart_fhir_context,
|
41
|
+
optional: true,
|
42
|
+
title: 'SMART App Launch fhirContext (Custom Adaptive)',
|
43
|
+
type: 'textarea',
|
44
|
+
description: %(
|
45
|
+
References to be provided by Inferno as the fhirContext as a part of the SMART App
|
46
|
+
Launch. These references help determine the behavior of the app. Referenced instances
|
47
|
+
may be provided in the "EHR-available resources" input.
|
48
|
+
),
|
49
|
+
default: JSON.pretty_generate([{ reference: 'Coverage/cov015' },
|
50
|
+
{ reference: 'DeviceRequest/devreqe0470' }])
|
51
|
+
input :adaptive_ehr_bundle,
|
52
|
+
optional: true,
|
53
|
+
title: 'EHR-available resources (Custom Adaptive)',
|
54
|
+
type: 'textarea',
|
55
|
+
description: %(
|
56
|
+
Resources available from the EHR needed to drive the custom adaptive workflow.
|
57
|
+
Formatted as a FHIR bundle that contains resources, each with an ID property populated. Each
|
58
|
+
instance present will be available for retrieval from Inferno at the endpoint:
|
59
|
+
<fhir-base>/<resource type>/<instance id>
|
60
|
+
)
|
61
|
+
input :custom_questionnaire_package_response, :custom_next_question_questionnaires
|
62
|
+
|
63
|
+
def example_client_jwt_payload_part
|
64
|
+
Base64.strict_encode64({ inferno_client_id: client_id }.to_json).delete('=')
|
65
|
+
end
|
66
|
+
|
67
|
+
run do
|
68
|
+
assert_valid_json(
|
69
|
+
custom_questionnaire_package_response,
|
70
|
+
'Custom questionnaire package response is not a valid json'
|
71
|
+
)
|
72
|
+
assert_valid_json(custom_next_question_questionnaires, 'Custom next questionnaires input is not a valid json')
|
73
|
+
|
74
|
+
custom_qp = JSON.parse(custom_questionnaire_package_response)
|
75
|
+
custom_questionnaires = JSON.parse(custom_next_question_questionnaires)
|
76
|
+
assert custom_qp.present?, %(
|
77
|
+
Custom questionnaire package response is empty, please provide a custom questionnaire package response
|
78
|
+
for the $questionnaire-package request
|
79
|
+
)
|
80
|
+
assert custom_questionnaires.present?, %(
|
81
|
+
'Custom questionnaires list is empty, please provide a list of Custom Questionnaire resources
|
82
|
+
to include in each $next-question Response.
|
83
|
+
)
|
84
|
+
# validate relevant inputs and provide warnings if they are bad
|
85
|
+
warning do
|
86
|
+
if adaptive_smart_fhir_context
|
87
|
+
assert_valid_json(adaptive_smart_fhir_context,
|
88
|
+
'The **SMART App Launch fhirContext** input is not valid JSON, so it will not be included in
|
89
|
+
the access token response.')
|
90
|
+
end
|
91
|
+
end
|
92
|
+
|
93
|
+
warning do
|
94
|
+
if adaptive_ehr_bundle
|
95
|
+
assert_valid_json(adaptive_ehr_bundle,
|
96
|
+
'The **EHR-available resources** input is not valid JSON, so no tester-specified instances
|
97
|
+
will be available to access from Inferno.')
|
98
|
+
assert(FHIR.from_contents(adaptive_ehr_bundle).is_a?(FHIR::Bundle),
|
99
|
+
'The **EHR-available resources** input does not contain a FHIR Bundle, so no tester-specified instances
|
100
|
+
will be available to access from Inferno.')
|
101
|
+
end
|
102
|
+
end
|
103
|
+
|
104
|
+
launch_prompt = if smart_app_launch == 'ehr'
|
105
|
+
%(Launch the DTR SMART App from Inferno by right clicking
|
106
|
+
[this link](#{launch_uri}?iss=#{fhir_base_url}&launch=#{launch_uri})
|
107
|
+
and selecting "Open in new window" or "Open in new tab".)
|
108
|
+
else
|
109
|
+
%(Launch the SMART App from your EHR.)
|
110
|
+
end
|
111
|
+
inferno_prompt_cont = %(As the DTR app steps through the launch steps, Inferno will wait and respond to the app's
|
112
|
+
requests for SMART configuration, authorization and access token.)
|
113
|
+
|
114
|
+
wait(
|
115
|
+
identifier: client_id,
|
116
|
+
message: %(
|
117
|
+
### SMART App Launch
|
118
|
+
|
119
|
+
#{launch_prompt}
|
120
|
+
|
121
|
+
#{inferno_prompt_cont if smart_app_launch == 'ehr'}
|
122
|
+
|
123
|
+
### Adaptive Questionnaire Workflow
|
124
|
+
|
125
|
+
1. **Questionnaire Package Request**:
|
126
|
+
- Invoke the `$questionnaire-package` operation by sending a POST request to the following endpoint
|
127
|
+
to retrieve the adaptive questionnaire package:
|
128
|
+
|
129
|
+
`#{questionnaire_package_url}`
|
130
|
+
|
131
|
+
- Inferno will respond with the user-provided empty adaptive questionnaire.
|
132
|
+
|
133
|
+
2. **Next Question Requests**:
|
134
|
+
- After receiving the questionnaire package, invoke the `$next-question` operation by sending
|
135
|
+
a POST request to the following endpoint:
|
136
|
+
|
137
|
+
`#{next_url}`
|
138
|
+
|
139
|
+
- Repeat this request **multiple times**, once for each Questionnaire provided in the user-supplied list.
|
140
|
+
- Inferno will sequentially respond with the corresponding Questionnaire from the list.
|
141
|
+
- If a `$next-question` request is received when the list is empty, Inferno will mark
|
142
|
+
the `QuestionnaireResponse` as completed.
|
143
|
+
|
144
|
+
Inferno will wait for all expected requests to be made.
|
145
|
+
|
146
|
+
### Pre-population
|
147
|
+
|
148
|
+
Inferno will then wait for the client to complete Questionnaire pre-population. The client should make FHIR
|
149
|
+
GET requests using service base path:
|
150
|
+
|
151
|
+
`#{fhir_base_url}`
|
152
|
+
|
153
|
+
### Request Identification
|
154
|
+
|
155
|
+
In order to identify requests for this session, Inferno will look for
|
156
|
+
an `Authorization` header with value:
|
157
|
+
|
158
|
+
```
|
159
|
+
Bearer eyJhbGciOiJub25lIn0.#{example_client_jwt_payload_part}.
|
160
|
+
```
|
161
|
+
|
162
|
+
### Continuing the Tests
|
163
|
+
|
164
|
+
When the DTR application has finished loading the Questionnaire,
|
165
|
+
including any clinical data requests to support pre-population,
|
166
|
+
[Click here](#{resume_pass_url}?client_id=#{client_id}) to continue.
|
167
|
+
)
|
168
|
+
)
|
169
|
+
end
|
170
|
+
end
|
171
|
+
end
|
@@ -0,0 +1,146 @@
|
|
1
|
+
require_relative '../../../tags'
|
2
|
+
require_relative 'dtr_smart_app_custom_adaptive_request_test'
|
3
|
+
require_relative '../../shared/dtr_questionnaire_package_request_validation_test'
|
4
|
+
require_relative '../dtr_adaptive_next_question_request_validation_test'
|
5
|
+
require_relative '../dtr_adaptive_response_validation_test'
|
6
|
+
require_relative '../../shared/dtr_custom_questionnaire_package_validation_test'
|
7
|
+
require_relative '../../shared/dtr_custom_questionnaire_libraries_test'
|
8
|
+
require_relative '../../shared/dtr_custom_questionnaire_extensions_test'
|
9
|
+
require_relative '../../shared/dtr_custom_questionnaire_expressions_test'
|
10
|
+
require_relative 'dtr_custom_next_question_response_validation_test'
|
11
|
+
require_relative '../../shared/dtr_prepopulation_attestation_test'
|
12
|
+
require_relative '../../shared/dtr_prepopulation_override_attestation_test'
|
13
|
+
require_relative '../../smart_app/dtr_smart_app_saving_questionnaire_response_group'
|
14
|
+
require_relative '../../shared/dtr_questionnaire_response_prepopulation_test'
|
15
|
+
|
16
|
+
module DaVinciDTRTestKit
|
17
|
+
class DTRSmartAppCustomAdaptiveWorkflowGroup < Inferno::TestGroup
|
18
|
+
id :dtr_smart_app_custom_adaptive_workflow
|
19
|
+
title 'Adaptive Questionnaire Workflow'
|
20
|
+
description %(
|
21
|
+
This group validates that a DTR SMART App client can perform a full DTR Adaptive Questionnaire workflow.
|
22
|
+
Testers will provide a custom adaptive Questionnaire package for the test, along with a list
|
23
|
+
(JSON array) of Questionnaires to be included in each `$next-question` response.
|
24
|
+
|
25
|
+
As part of this workflow, the SMART App system must demonstrate its ability to:
|
26
|
+
|
27
|
+
1. Request the Questionnaire using the `$questionnaire-package` operation.
|
28
|
+
2. Support the tester in completing the questionnaire through multiple `$next-question` interactions, including:
|
29
|
+
- Rendering the questionnaire.
|
30
|
+
- Pre-populating answers into the questionnaire.
|
31
|
+
- Allowing the tester to manually enter responses, including overriding pre-populated answers.
|
32
|
+
3. Provide the completed `QuestionnaireResponse` with appropriate indicators for pre-populated
|
33
|
+
and manually-entered data.
|
34
|
+
|
35
|
+
Inferno will process `$next-question` requests dynamically:
|
36
|
+
- Each `$next-question` request will correspond to the next item in the provided list.
|
37
|
+
- Inferno will sequentially return the corresponding Questionnaire from the list.
|
38
|
+
- If a `$next-question` request is received when the list is empty, Inferno will mark
|
39
|
+
the `QuestionnaireResponse` as completed.
|
40
|
+
|
41
|
+
At least two answers should be pre-populated across all sets of questions.
|
42
|
+
)
|
43
|
+
run_as_group
|
44
|
+
|
45
|
+
config(
|
46
|
+
options: {
|
47
|
+
smart_app: true,
|
48
|
+
form_type: 'adaptive',
|
49
|
+
next_tag: "custom_#{CLIENT_NEXT_TAG}"
|
50
|
+
},
|
51
|
+
inputs: {
|
52
|
+
custom_questionnaire_package_response: {
|
53
|
+
name: 'adaptive_custom_questionnaire_package_response',
|
54
|
+
title: 'Custom Questionnaire Package Response JSON for Adaptive form',
|
55
|
+
description: %(
|
56
|
+
A JSON PackageBundle may be provided here to replace Inferno's response to
|
57
|
+
the $questionnaire-package request. Note: Ensure that the questionnaire package
|
58
|
+
has an empty Adaptive Questionnaire.
|
59
|
+
)
|
60
|
+
}
|
61
|
+
}
|
62
|
+
)
|
63
|
+
|
64
|
+
group do
|
65
|
+
id :dtr_smart_app_custom_adaptive_retrieval
|
66
|
+
title 'Retrieving the Adaptive Questionnaire'
|
67
|
+
|
68
|
+
# Test 1: wait for the $questionnaire-package request and initial $next-question request
|
69
|
+
test from: :dtr_smart_app_custom_adative_request
|
70
|
+
# Test 2: validate the $questionnaire-package request body
|
71
|
+
test from: :dtr_qp_request_validation
|
72
|
+
# Test 3: validate the $next-question request body
|
73
|
+
test from: :dtr_adaptive_next_question_request_validation
|
74
|
+
# Test 4: validate the QuestionnaireResponse in the input parameter
|
75
|
+
test from: :dtr_adaptive_response_validation do
|
76
|
+
description %(
|
77
|
+
Verify that all submitted QuestionnaireResponse resources meet the following criteria:
|
78
|
+
- Conform to the [SDCQuestionnaireResponseAdapt](http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaireresponse-adapt).
|
79
|
+
- Include source extensions indicating whether answers were manually entered,
|
80
|
+
automatically pre-populated, or manually overridden (for `completed` QuestionnaireResponse).
|
81
|
+
- Provide answers for all required items in their contained Questionnaire.
|
82
|
+
)
|
83
|
+
input :custom_next_question_questionnaires
|
84
|
+
end
|
85
|
+
# Test 5: validate the user provided $questionnaire-package response
|
86
|
+
test from: :dtr_custom_qp_validation
|
87
|
+
# Test 6: verify the custom response has the necessary libraries for pre-population
|
88
|
+
test from: :dtr_custom_questionnaire_libraries
|
89
|
+
# Test 7: validate the user provided $next-question questionnaire
|
90
|
+
test from: :dtr_custom_next_questionnaire_validation
|
91
|
+
# Test 8: verify the custom response has the necessaru extensions for pre-population
|
92
|
+
test from: :dtr_custom_questionnaire_extensions do
|
93
|
+
title %(
|
94
|
+
[USER INPUT VERIFICATION] Custom Questionnaires for $next-question Responses contain extensions
|
95
|
+
necessary for pre-population
|
96
|
+
)
|
97
|
+
input :custom_next_question_questionnaires
|
98
|
+
end
|
99
|
+
# Test 9: verify custom response has necessary expressions for pre-population
|
100
|
+
test from: :dtr_custom_questionnaire_expressions do
|
101
|
+
title %(
|
102
|
+
[USER INPUT VERIFICATION] Custom Questionnaires for $next-question Responses contain items with
|
103
|
+
expressions necessary for pre-population
|
104
|
+
)
|
105
|
+
input :custom_next_question_questionnaires
|
106
|
+
end
|
107
|
+
end
|
108
|
+
|
109
|
+
group do
|
110
|
+
title 'Attestation: Questionnaire Pre-Population and Rendering'
|
111
|
+
description %(
|
112
|
+
This group verifies that the tester has properly followed pre-population and rendering
|
113
|
+
directives while interacting with and filling out the questionnaire.
|
114
|
+
|
115
|
+
After retrieving and completing the questionnaire in their client system, the tester will
|
116
|
+
attest that:
|
117
|
+
1. The questionnaire was pre-populated as expected, with at least two answers pre-populated
|
118
|
+
across all sets of questions.
|
119
|
+
2. The questionnaire was rendered correctly according to its defined structure.
|
120
|
+
3. They were able to manually enter responses, including overriding pre-populated answers.
|
121
|
+
)
|
122
|
+
test from: :dtr_prepopulation_attest
|
123
|
+
test from: :dtr_prepopulation_override_attest
|
124
|
+
end
|
125
|
+
|
126
|
+
group from: :dtr_smart_app_saving_qr do
|
127
|
+
config(
|
128
|
+
options: {
|
129
|
+
custom: true,
|
130
|
+
adaptive: true,
|
131
|
+
qr_profile_url: 'http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaireresponse-adapt'
|
132
|
+
}
|
133
|
+
)
|
134
|
+
|
135
|
+
test from: :dtr_qr_prepopulation,
|
136
|
+
uses_request: :questionnaire_response_save,
|
137
|
+
description: %(
|
138
|
+
The tester will complete the questionnaire such that a QuestionnaireResponse is
|
139
|
+
stored back into Inferno's EHR endpoint. The stored QuestionnaireResponse will be evaluated for:
|
140
|
+
- Has source extensions demonstrating answers that are manually entered,
|
141
|
+
automatically pre-populated, and manually overridden.
|
142
|
+
- Contains answers for all required items.
|
143
|
+
)
|
144
|
+
end
|
145
|
+
end
|
146
|
+
end
|
@@ -1,6 +1,6 @@
|
|
1
|
-
require_relative 'dtr_adaptive_next_question_request_test'
|
2
|
-
require_relative 'dtr_adaptive_next_question_request_validation_test'
|
3
|
-
require_relative 'dtr_adaptive_response_validation_test'
|
1
|
+
require_relative '../dtr_adaptive_next_question_request_test'
|
2
|
+
require_relative '../dtr_adaptive_next_question_request_validation_test'
|
3
|
+
require_relative '../dtr_adaptive_response_validation_test'
|
4
4
|
|
5
5
|
module DaVinciDTRTestKit
|
6
6
|
class DTRAdaptiveNextQuestionRetrievalGroup < Inferno::TestGroup
|