mirah-ruby 0.1.0

Sign up to get free protection for your applications and to get access to all the features.
Files changed (49) hide show
  1. checksums.yaml +7 -0
  2. data/.circleci/config.yml +93 -0
  3. data/.gitignore +14 -0
  4. data/.overcommit.yml +48 -0
  5. data/.overcommit_gems.rb +9 -0
  6. data/.rspec +3 -0
  7. data/.rubocop.yml +54 -0
  8. data/.yardopts +1 -0
  9. data/CODE_OF_CONDUCT.md +74 -0
  10. data/Gemfile +6 -0
  11. data/LICENSE.txt +21 -0
  12. data/README.md +187 -0
  13. data/Rakefile +24 -0
  14. data/bin/autocorrect +28 -0
  15. data/bin/console +14 -0
  16. data/bin/setup +8 -0
  17. data/bin/setup_overcommit +12 -0
  18. data/lib/mirah.rb +44 -0
  19. data/lib/mirah/base_input_object.rb +65 -0
  20. data/lib/mirah/base_object.rb +98 -0
  21. data/lib/mirah/client.rb +420 -0
  22. data/lib/mirah/collection.rb +98 -0
  23. data/lib/mirah/data/appointment.rb +65 -0
  24. data/lib/mirah/data/organization.rb +31 -0
  25. data/lib/mirah/data/page_info.rb +40 -0
  26. data/lib/mirah/data/patient.rb +46 -0
  27. data/lib/mirah/data/practitioner.rb +53 -0
  28. data/lib/mirah/errors.rb +39 -0
  29. data/lib/mirah/filters.rb +7 -0
  30. data/lib/mirah/filters/appointment_filters.rb +16 -0
  31. data/lib/mirah/filters/organization_filters.rb +16 -0
  32. data/lib/mirah/filters/paging.rb +33 -0
  33. data/lib/mirah/filters/patient_filters.rb +16 -0
  34. data/lib/mirah/filters/practitioner_filters.rb +16 -0
  35. data/lib/mirah/graphql.rb +33 -0
  36. data/lib/mirah/graphql/fragments.rb +97 -0
  37. data/lib/mirah/graphql/mutations.rb +72 -0
  38. data/lib/mirah/graphql/queries.rb +196 -0
  39. data/lib/mirah/inputs.rb +7 -0
  40. data/lib/mirah/inputs/appointment_input.rb +40 -0
  41. data/lib/mirah/inputs/organization_input.rb +20 -0
  42. data/lib/mirah/inputs/patient_input.rb +40 -0
  43. data/lib/mirah/inputs/practitioner_input.rb +44 -0
  44. data/lib/mirah/push_result.rb +40 -0
  45. data/lib/mirah/serializers.rb +57 -0
  46. data/lib/mirah/version.rb +5 -0
  47. data/mirah-ruby.gemspec +41 -0
  48. data/schema.json +8936 -0
  49. metadata +221 -0
@@ -0,0 +1,98 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ # Collections represent a pageable view into a given collection. They automatically let you iterate through
5
+ # record sets in a stable manner.
6
+ #
7
+ # @example Iterate through a collection of multiple pages
8
+ # while(collection.next_page?)
9
+ # collection = collection.next_page
10
+ # collection.records.each do |record|
11
+ # # process record
12
+ # end
13
+ # end
14
+ class Collection
15
+ def initialize(results:, page_info:, client:, query:)
16
+ @results = results
17
+ @page_info = page_info
18
+ @client = client
19
+ @query = query
20
+ end
21
+
22
+ # The Mirah client, used for sending additional paged requests.
23
+ attr_reader :client
24
+
25
+ # The current results of the query
26
+ attr_reader :results
27
+
28
+ # The information on the current page as returned by the server
29
+ attr_reader :page_info
30
+
31
+ # The current set of paging parameters
32
+ attr_reader :paging
33
+
34
+ # The original query, stored to allow us to retrigger a query with a new page.
35
+ attr_reader :query
36
+
37
+ def length
38
+ results&.length
39
+ end
40
+
41
+ def next_page?
42
+ page_info.next_page?
43
+ end
44
+
45
+ def prev_page?
46
+ page_info.prev_page?
47
+ end
48
+
49
+ def refresh_with_new_paging(paging)
50
+ # Update everything as before, but set the new paging.
51
+ client.query_connection(
52
+ query[:query],
53
+ query[:input],
54
+ paging,
55
+ query[:data_klass],
56
+ query[:path]
57
+ )
58
+ end
59
+
60
+ def next_page
61
+ raise Errors::InvalidPage, 'This collection does not have a next page' unless next_page?
62
+
63
+ return @next_page if @next_page
64
+
65
+ @next_page = refresh_with_new_paging(next_page_params)
66
+ end
67
+
68
+ def prev_page
69
+ raise Errors::InvalidPage, 'This collection does not have a previous page' unless prev_page?
70
+
71
+ return @prev_page if @prev_page
72
+
73
+ @prev_page = refresh_with_new_paging(prev_page_params)
74
+ end
75
+
76
+ private
77
+
78
+ def next_page_params
79
+ last = query[:paging]
80
+ Filters::Paging.new(
81
+ after: page_info.end_cursor,
82
+ before: nil,
83
+ first: last.first || last.last,
84
+ last: nil
85
+ )
86
+ end
87
+
88
+ def prev_page_params
89
+ last = query[:paging]
90
+ Filters::Paging.new(
91
+ before: page_info.start_cursor,
92
+ after: nil,
93
+ last: last.last || last.first,
94
+ first: nil
95
+ )
96
+ end
97
+ end
98
+ end
@@ -0,0 +1,65 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Data
5
+ # Appointments represent a planned or past meeting between a patient and a practitioner. This is based
6
+ # on https://www.hl7.org/fhir/appointment.html
7
+ # As part of the integration flow, Mirah will work out whether this appointments needs an accompanying measurement
8
+ # encounter and automatically create one as appropriate. Mirah's ETL will generally make a best effort to estimate
9
+ # where and what context the measurement should be taken. The more information (Episode of Care, Organization,
10
+ # etc) that you supply, the more likely it is to be correct.
11
+ # Note that as part of this processing, Mirah may immediately choose to create assessments and trigger
12
+ # communications with the patient or other participants, for example by text message or email.
13
+ # In order to keep adherence statistics up to date, Mirah also requires that updates on past
14
+ # appointments are sent, so that we can calculate whether e.g. the appointment was a no-show.
15
+ class Appointment < BaseObject
16
+ # @!attribute [r] id
17
+ # @return [string] The internal Mirah identifier
18
+ attribute :id
19
+
20
+ # @!attribute [r] external_id
21
+ # @return [string] The identifier provided by your system
22
+ attribute :external_id
23
+
24
+ # @!attribute [r] start_date
25
+ # @return [Date] The appointment start date
26
+ attribute :start_date, serializer: Serializers::DateTimeSerializer
27
+
28
+ # @!attribute [r] end_date
29
+ # @return [Date] The appointment end date
30
+ attribute :end_date, serializer: Serializers::DateTimeSerializer
31
+
32
+ # @!attribute [r] minutes_duration
33
+ # @return [Integer] The legnth of this appointment in minutes
34
+ attribute :minutes_duration
35
+
36
+ # @!attribute [r] status
37
+ # @return [string] The appointment status
38
+ attribute :status
39
+
40
+ # @!attribute [r] patient_id
41
+ # @return [string] The internal mirah id of the patient
42
+ attribute :patient_id, path: %w[patient], target: 'id'
43
+
44
+ # @!attribute [r] external_patient_id
45
+ # @return [string] Your system identifier for the patient
46
+ attribute :external_patient_id, path: %w[patient], target: 'externalId'
47
+
48
+ # @!attribute [r] practitioner_id
49
+ # @return [string] The internal mirah id of the practitioner this appointment is with
50
+ attribute :practitioner_id, path: %w[practitioner], target: 'id'
51
+
52
+ # @!attribute [r] external_practitioner_id
53
+ # @return [string] Your system identifier for the practitioner this appointment is with
54
+ attribute :external_practitioner_id, path: %w[practitioner], target: 'externalId'
55
+
56
+ # @!attribute [r] organization_id
57
+ # @return [string] The internal mirah id of the organization this appointment is with
58
+ attribute :organization_id, path: %w[organization], target: 'id'
59
+
60
+ # @!attribute [r] external_organization_id
61
+ # @return [string] Your system identifier for the organization this appointment is with
62
+ attribute :external_organization_id, path: %w[organization], target: 'externalId'
63
+ end
64
+ end
65
+ end
@@ -0,0 +1,31 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Data
5
+ # Organizations in the Mirah system currently represent a hierarchy of units/facilities
6
+ # requiring either different treatment configurations (e.g. inpatient facilities require different
7
+ # measurement protocols to outpatient) or useful for the purpose of analytics. It is roughly based on
8
+ # https://www.hl7.org/fhir/organization.html
9
+ class Organization < BaseObject
10
+ # @!attribute [r] id
11
+ # @return [string] The internal Mirah identifier
12
+ attribute :id
13
+
14
+ # @!attribute [r] external_id
15
+ # @return [string] The identifier provided by your system
16
+ attribute :external_id
17
+
18
+ # @!attribute [r] name
19
+ # @return [string] The organization's name
20
+ attribute :name
21
+
22
+ # @!attribute [r] part_of_id
23
+ # @return [string] The internal mirah id of the organization this organization is a child of
24
+ attribute :part_of_id, path: %w[partOf], target: 'id'
25
+
26
+ # @!attribute [r] external_part_of_id
27
+ # @return [string] Your system identifier for the organization this organization is a child of
28
+ attribute :external_part_of_id, path: %w[partOf], target: 'externalId'
29
+ end
30
+ end
31
+ end
@@ -0,0 +1,40 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Data
5
+ # PageInfo gives information on the current state of paging as returned by the server. This includes information
6
+ # about the start and the end cursors of the result set, and whether or not there are additiona pages.
7
+ # This can be used in combination with {Mirah::Filters::Paging} to make a stable cursor-based pagination call.
8
+ class PageInfo < BaseObject
9
+ # @!attribute [r] end_cursor
10
+ # @return [string] The cursor of the last record of the current set.
11
+ # This can be used as a starting point for the next page of the query.
12
+ attribute :end_cursor
13
+
14
+ # @!attribute [r] start_cursor
15
+ # @return [string] The cursor of the first record of the current set.
16
+ # This can be used to get the previous page.
17
+ attribute :start_cursor
18
+
19
+ # @!attribute [r] has_next_page
20
+ # @return [Boolean] Whether the data set has a next page
21
+ attribute :has_next_page
22
+
23
+ # @!attribute [r] has_previous_page
24
+ # @return [Boolean] Whether the data set has a next page
25
+ attribute :has_previous_page
26
+
27
+ # @see has_next_page
28
+ # @return [Boolean]
29
+ def next_page?
30
+ has_next_page
31
+ end
32
+
33
+ # @see has_previous_page
34
+ # @return [Boolean]
35
+ def prev_page?
36
+ has_previous_page
37
+ end
38
+ end
39
+ end
40
+ end
@@ -0,0 +1,46 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Data
5
+ # Patients represent people who are in treatment. They can have appointments, and be the target of assessments.
6
+ # Patients are only treated in the context of an episode of care.
7
+ class Patient < BaseObject
8
+ # @!attribute [r] id
9
+ # @return [string] The internal Mirah identifier
10
+ attribute :id
11
+
12
+ # @!attribute [r] external_id
13
+ # @return [string] The identifier provided by your system
14
+ attribute :external_id
15
+
16
+ # @!attribute [r] given_name
17
+ # @return [string] The patient's first or given name
18
+ attribute :given_name
19
+
20
+ # @!attribute [r] family_name
21
+ # @return [string] The patient's last or family name
22
+ attribute :family_name
23
+
24
+ # @!attribute [r] birth_date
25
+ # @return [Date] The patient's date of birth.
26
+ attribute :birth_date, serializer: Serializers::DateSerializer
27
+
28
+ # @!attribute [r] gender
29
+ # @return [string] The patient's gender
30
+ attribute :gender
31
+
32
+ # @!attribute [r] primary_language
33
+ # @return [string] The patient's primary language
34
+ attribute :primary_language
35
+
36
+ # @!attribute [r] email
37
+ # @return [string] The patient's primary email address
38
+ attribute :email
39
+
40
+ # @!attribute [r] phone_number
41
+ # @return [string] The patient's primary phone number that is suitable for receiving text messages.
42
+ # Please do not use a phone number which corresponds to a landline as text messages will not be received.
43
+ attribute :phone_number
44
+ end
45
+ end
46
+ end
@@ -0,0 +1,53 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Data
5
+ # FHIR Practitioners represent people directly involved in the provision of care.
6
+ # See https://www.hl7.org/fhir/practitioner.html for more details.
7
+ class Practitioner < BaseObject
8
+ # @!attribute [r] id
9
+ # @return [string] The internal Mirah identifier
10
+ attribute :id
11
+
12
+ # @!attribute [r] external_id
13
+ # @return [string] The identifier provided by your system
14
+ attribute :external_id
15
+
16
+ # @!attribute [r] given_name
17
+ # @return [string] The practitioner's first or given name
18
+ attribute :given_name
19
+
20
+ # @!attribute [r] family_name
21
+ # @return [string] The practitioner's last or family name
22
+ attribute :family_name
23
+
24
+ # @!attribute [r] title
25
+ # @return [string] The practitioner's title, e.g. 'Dr'
26
+ attribute :title
27
+
28
+ # @!attribute [r] suffix
29
+ # @return [string] The practitioner's suffix, e.g. 'MD'
30
+ attribute :suffix
31
+
32
+ # @!attribute [r] email
33
+ # @return [string] The practitioner's primary email address
34
+ attribute :email
35
+
36
+ # @!attribute [r] default_practitioner_role
37
+ # @return [string] The clinical role for this practitioner
38
+ attribute :default_practitioner_role
39
+
40
+ # @!attribute [r] sso_username
41
+ # @return [string] The username (nameid) used for single sign on by this practitioner.
42
+ attribute :sso_username
43
+
44
+ # @!attribute [r] organization_ids
45
+ # @return [Array<string>] The internal mirah organization ids this practitioner has a role in
46
+ attribute :organization_ids, path: %w[organization], target: 'id'
47
+
48
+ # @!attribute [r] external_organization_ids
49
+ # @return [Array<string>] The identifiers from your system of the organizations this practitioner has a role in
50
+ attribute :external_organization_ids, path: %w[organizations], target: 'externalId'
51
+ end
52
+ end
53
+ end
@@ -0,0 +1,39 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ # A top level error from the Mirah system. It is implemented in multiple places with a
5
+ class Error < StandardError; end
6
+
7
+ module Errors
8
+ # This exception is thrown when the credentials you have specified for the service are invalid.
9
+ class InvalidCredentials < Error; end
10
+
11
+ # This exception is thrown when an unknown error occurs on the server side.
12
+ class ServerError < Error; end
13
+
14
+ # This exception is thrown when an error happens in this process rather than on the server side.
15
+ class ClientError < Error; end
16
+
17
+ # A parameter you supplied as an input was not valid for the query.
18
+ # An error class that shows the record was invalid
19
+ class InvalidParameter < Error
20
+ def initialize(param)
21
+ @param = param
22
+ end
23
+
24
+ attr_reader :param
25
+ end
26
+
27
+ # A required parameter was not passed in
28
+ class MissingParameter < Error
29
+ def initialize(param)
30
+ @param = param
31
+ end
32
+
33
+ attr_reader :param
34
+ end
35
+
36
+ # You attempted to fetch a page that was not valid - you probably called `next_page` on the end of the collection.
37
+ class InvalidPage < Error; end
38
+ end
39
+ end
@@ -0,0 +1,7 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ # These filters represent ways of querying data. Each endpoint has a set of filters that you can apply.
5
+ module Filters
6
+ end
7
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Filters
5
+ # Input parameters and filters for queries returning {Data::Appointment} objects.
6
+ class AppointmentFilters < BaseObject
7
+ # @!attribute [r] external_id
8
+ # @return [Array<string>] An array of external identifiers to match.
9
+ attribute :external_id
10
+
11
+ # @!attribute [r] status
12
+ # @return [string] The appointment status
13
+ attribute :status
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,16 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Filters
5
+ # Input parameters and filters for queries returning {Data::Organization} objects.
6
+ class OrganizationFilters < BaseObject
7
+ # @!attribute [r] external_id
8
+ # @return [Array<string>] An array of external identifiers to match.
9
+ attribute :external_id
10
+
11
+ # @!attribute [r] search
12
+ # @return [string] Smart search by name and other fields where appropriate
13
+ attribute :search
14
+ end
15
+ end
16
+ end
@@ -0,0 +1,33 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Mirah
4
+ module Filters
5
+ # A set of input parameters designed to let you select how many and which records you want from a pagination cursor.
6
+ # It is based on Graphql's Relay specification.
7
+ # This can be used with {Data::PageInfo}, which will be provided by the results of a server query, to provide
8
+ # stable pagination framework.
9
+ class Paging < BaseObject
10
+ # @!attribute [r] first
11
+ # @return [string] Return the first N rows from either the start, or the current cursor position.
12
+ # Cannot be used at the same time as #last
13
+ attribute :first
14
+
15
+ # @!attribute [r] last
16
+ # @return [string] Return the last N rows from either the end, or the current cursor position.
17
+ # Cannot be used at the same time as #first
18
+ attribute :last
19
+
20
+ # @!attribute [r] before
21
+ # @return [string] Return rows before the given cursor position
22
+ attribute :before
23
+
24
+ # @!attribute [r] after
25
+ # @return [string] Return rows after the given cursor position
26
+ attribute :after
27
+
28
+ def self.default
29
+ new(first: 100)
30
+ end
31
+ end
32
+ end
33
+ end