phenoml 0.0.6__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (244) hide show
  1. phenoml/__init__.py +30 -0
  2. phenoml/agent/__init__.py +56 -0
  3. phenoml/agent/client.py +939 -0
  4. phenoml/agent/errors/__init__.py +11 -0
  5. phenoml/agent/errors/bad_request_error.py +10 -0
  6. phenoml/agent/errors/forbidden_error.py +10 -0
  7. phenoml/agent/errors/internal_server_error.py +10 -0
  8. phenoml/agent/errors/not_found_error.py +10 -0
  9. phenoml/agent/errors/unauthorized_error.py +10 -0
  10. phenoml/agent/prompts/__init__.py +7 -0
  11. phenoml/agent/prompts/client.py +707 -0
  12. phenoml/agent/prompts/raw_client.py +1345 -0
  13. phenoml/agent/prompts/types/__init__.py +8 -0
  14. phenoml/agent/prompts/types/prompts_delete_response.py +20 -0
  15. phenoml/agent/prompts/types/prompts_list_response.py +22 -0
  16. phenoml/agent/raw_client.py +1668 -0
  17. phenoml/agent/types/__init__.py +43 -0
  18. phenoml/agent/types/agent_chat_response.py +33 -0
  19. phenoml/agent/types/agent_create_request.py +53 -0
  20. phenoml/agent/types/agent_create_request_provider.py +5 -0
  21. phenoml/agent/types/agent_delete_response.py +20 -0
  22. phenoml/agent/types/agent_get_chat_messages_request_order.py +5 -0
  23. phenoml/agent/types/agent_get_chat_messages_response.py +22 -0
  24. phenoml/agent/types/agent_list_response.py +22 -0
  25. phenoml/agent/types/agent_prompts_response.py +22 -0
  26. phenoml/agent/types/agent_response.py +22 -0
  27. phenoml/agent/types/agent_template.py +58 -0
  28. phenoml/agent/types/agent_template_provider.py +5 -0
  29. phenoml/agent/types/chat_message_template.py +72 -0
  30. phenoml/agent/types/chat_session_template.py +67 -0
  31. phenoml/agent/types/json_patch.py +7 -0
  32. phenoml/agent/types/json_patch_operation.py +40 -0
  33. phenoml/agent/types/json_patch_operation_op.py +5 -0
  34. phenoml/agent/types/prompt_template.py +52 -0
  35. phenoml/agent/types/success_response.py +20 -0
  36. phenoml/authtoken/__init__.py +17 -0
  37. phenoml/authtoken/auth/__init__.py +7 -0
  38. phenoml/authtoken/auth/client.py +129 -0
  39. phenoml/authtoken/auth/raw_client.py +173 -0
  40. phenoml/authtoken/auth/types/__init__.py +7 -0
  41. phenoml/authtoken/auth/types/auth_generate_token_response.py +22 -0
  42. phenoml/authtoken/client.py +39 -0
  43. phenoml/authtoken/errors/__init__.py +8 -0
  44. phenoml/authtoken/errors/bad_request_error.py +10 -0
  45. phenoml/authtoken/errors/unauthorized_error.py +10 -0
  46. phenoml/authtoken/raw_client.py +13 -0
  47. phenoml/authtoken/types/__init__.py +8 -0
  48. phenoml/authtoken/types/bad_request_error_body.py +21 -0
  49. phenoml/authtoken/types/unauthorized_error_body.py +21 -0
  50. phenoml/client.py +177 -0
  51. phenoml/cohort/__init__.py +8 -0
  52. phenoml/cohort/client.py +113 -0
  53. phenoml/cohort/errors/__init__.py +9 -0
  54. phenoml/cohort/errors/bad_request_error.py +10 -0
  55. phenoml/cohort/errors/internal_server_error.py +10 -0
  56. phenoml/cohort/errors/unauthorized_error.py +10 -0
  57. phenoml/cohort/raw_client.py +185 -0
  58. phenoml/cohort/types/__init__.py +8 -0
  59. phenoml/cohort/types/cohort_response.py +33 -0
  60. phenoml/cohort/types/search_concept.py +37 -0
  61. phenoml/construe/__init__.py +45 -0
  62. phenoml/construe/client.py +399 -0
  63. phenoml/construe/errors/__init__.py +11 -0
  64. phenoml/construe/errors/bad_request_error.py +10 -0
  65. phenoml/construe/errors/conflict_error.py +10 -0
  66. phenoml/construe/errors/failed_dependency_error.py +10 -0
  67. phenoml/construe/errors/internal_server_error.py +10 -0
  68. phenoml/construe/errors/unauthorized_error.py +10 -0
  69. phenoml/construe/raw_client.py +706 -0
  70. phenoml/construe/types/__init__.py +41 -0
  71. phenoml/construe/types/bad_request_error_body.py +27 -0
  72. phenoml/construe/types/construe_cohort_request_config.py +37 -0
  73. phenoml/construe/types/construe_cohort_response.py +33 -0
  74. phenoml/construe/types/construe_cohort_response_queries_item.py +49 -0
  75. phenoml/construe/types/construe_cohort_response_queries_item_code_extract_results_item.py +31 -0
  76. phenoml/construe/types/construe_cohort_response_queries_item_code_extract_results_item_codes_item.py +32 -0
  77. phenoml/construe/types/construe_upload_code_system_response.py +19 -0
  78. phenoml/construe/types/extract_codes_result.py +22 -0
  79. phenoml/construe/types/extract_request_config.py +23 -0
  80. phenoml/construe/types/extract_request_config_chunking_method.py +5 -0
  81. phenoml/construe/types/extract_request_system.py +37 -0
  82. phenoml/construe/types/extracted_code_result.py +41 -0
  83. phenoml/construe/types/internal_server_error_body.py +27 -0
  84. phenoml/construe/types/unauthorized_error_body.py +27 -0
  85. phenoml/construe/types/upload_request_format.py +5 -0
  86. phenoml/core/__init__.py +52 -0
  87. phenoml/core/api_error.py +23 -0
  88. phenoml/core/client_wrapper.py +87 -0
  89. phenoml/core/datetime_utils.py +28 -0
  90. phenoml/core/file.py +67 -0
  91. phenoml/core/force_multipart.py +16 -0
  92. phenoml/core/http_client.py +543 -0
  93. phenoml/core/http_response.py +55 -0
  94. phenoml/core/jsonable_encoder.py +100 -0
  95. phenoml/core/pydantic_utilities.py +255 -0
  96. phenoml/core/query_encoder.py +58 -0
  97. phenoml/core/remove_none_from_dict.py +11 -0
  98. phenoml/core/request_options.py +35 -0
  99. phenoml/core/serialization.py +276 -0
  100. phenoml/environment.py +7 -0
  101. phenoml/fhir/__init__.py +36 -0
  102. phenoml/fhir/client.py +970 -0
  103. phenoml/fhir/errors/__init__.py +10 -0
  104. phenoml/fhir/errors/bad_request_error.py +10 -0
  105. phenoml/fhir/errors/internal_server_error.py +10 -0
  106. phenoml/fhir/errors/not_found_error.py +10 -0
  107. phenoml/fhir/errors/unauthorized_error.py +10 -0
  108. phenoml/fhir/raw_client.py +1385 -0
  109. phenoml/fhir/types/__init__.py +29 -0
  110. phenoml/fhir/types/error_response.py +36 -0
  111. phenoml/fhir/types/fhir_bundle.py +43 -0
  112. phenoml/fhir/types/fhir_bundle_entry_item.py +34 -0
  113. phenoml/fhir/types/fhir_bundle_entry_item_request.py +25 -0
  114. phenoml/fhir/types/fhir_bundle_entry_item_request_method.py +5 -0
  115. phenoml/fhir/types/fhir_bundle_entry_item_response.py +24 -0
  116. phenoml/fhir/types/fhir_patch_request_body_item.py +40 -0
  117. phenoml/fhir/types/fhir_patch_request_body_item_op.py +7 -0
  118. phenoml/fhir/types/fhir_resource.py +40 -0
  119. phenoml/fhir/types/fhir_resource_meta.py +28 -0
  120. phenoml/fhir/types/fhir_search_response.py +8 -0
  121. phenoml/fhir_provider/__init__.py +43 -0
  122. phenoml/fhir_provider/client.py +731 -0
  123. phenoml/fhir_provider/errors/__init__.py +11 -0
  124. phenoml/fhir_provider/errors/bad_request_error.py +10 -0
  125. phenoml/fhir_provider/errors/forbidden_error.py +10 -0
  126. phenoml/fhir_provider/errors/internal_server_error.py +10 -0
  127. phenoml/fhir_provider/errors/not_found_error.py +10 -0
  128. phenoml/fhir_provider/errors/unauthorized_error.py +10 -0
  129. phenoml/fhir_provider/raw_client.py +1445 -0
  130. phenoml/fhir_provider/types/__init__.py +35 -0
  131. phenoml/fhir_provider/types/auth_method.py +7 -0
  132. phenoml/fhir_provider/types/fhir_provider_auth_config.py +53 -0
  133. phenoml/fhir_provider/types/fhir_provider_delete_response.py +20 -0
  134. phenoml/fhir_provider/types/fhir_provider_list_response.py +22 -0
  135. phenoml/fhir_provider/types/fhir_provider_remove_auth_config_response.py +22 -0
  136. phenoml/fhir_provider/types/fhir_provider_response.py +22 -0
  137. phenoml/fhir_provider/types/fhir_provider_set_active_auth_config_response.py +22 -0
  138. phenoml/fhir_provider/types/fhir_provider_template.py +66 -0
  139. phenoml/fhir_provider/types/fhir_query_response.py +27 -0
  140. phenoml/fhir_provider/types/fhir_query_response_data.py +5 -0
  141. phenoml/fhir_provider/types/json_web_key.py +51 -0
  142. phenoml/fhir_provider/types/provider.py +8 -0
  143. phenoml/fhir_provider/types/service_account_key.py +35 -0
  144. phenoml/fhir_provider/types/smart_configuration.py +46 -0
  145. phenoml/lang2fhir/__init__.py +27 -0
  146. phenoml/lang2fhir/client.py +430 -0
  147. phenoml/lang2fhir/errors/__init__.py +11 -0
  148. phenoml/lang2fhir/errors/bad_request_error.py +10 -0
  149. phenoml/lang2fhir/errors/failed_dependency_error.py +10 -0
  150. phenoml/lang2fhir/errors/forbidden_error.py +10 -0
  151. phenoml/lang2fhir/errors/internal_server_error.py +10 -0
  152. phenoml/lang2fhir/errors/unauthorized_error.py +10 -0
  153. phenoml/lang2fhir/raw_client.py +788 -0
  154. phenoml/lang2fhir/types/__init__.py +19 -0
  155. phenoml/lang2fhir/types/create_request_resource.py +25 -0
  156. phenoml/lang2fhir/types/document_request_file_type.py +7 -0
  157. phenoml/lang2fhir/types/document_request_resource.py +5 -0
  158. phenoml/lang2fhir/types/fhir_resource.py +5 -0
  159. phenoml/lang2fhir/types/lang2fhir_upload_profile_response.py +23 -0
  160. phenoml/lang2fhir/types/search_response.py +33 -0
  161. phenoml/py.typed +0 -0
  162. phenoml/tools/__init__.py +37 -0
  163. phenoml/tools/client.py +359 -0
  164. phenoml/tools/errors/__init__.py +11 -0
  165. phenoml/tools/errors/bad_request_error.py +10 -0
  166. phenoml/tools/errors/failed_dependency_error.py +10 -0
  167. phenoml/tools/errors/forbidden_error.py +10 -0
  168. phenoml/tools/errors/internal_server_error.py +10 -0
  169. phenoml/tools/errors/unauthorized_error.py +10 -0
  170. phenoml/tools/mcp_server/__init__.py +7 -0
  171. phenoml/tools/mcp_server/client.py +336 -0
  172. phenoml/tools/mcp_server/raw_client.py +641 -0
  173. phenoml/tools/mcp_server/tools/__init__.py +4 -0
  174. phenoml/tools/mcp_server/tools/client.py +358 -0
  175. phenoml/tools/mcp_server/tools/raw_client.py +656 -0
  176. phenoml/tools/raw_client.py +696 -0
  177. phenoml/tools/types/__init__.py +27 -0
  178. phenoml/tools/types/cohort_response.py +49 -0
  179. phenoml/tools/types/lang2fhir_and_create_request_resource.py +25 -0
  180. phenoml/tools/types/lang2fhir_and_create_response.py +33 -0
  181. phenoml/tools/types/lang2fhir_and_search_response.py +40 -0
  182. phenoml/tools/types/mcp_server_response.py +33 -0
  183. phenoml/tools/types/mcp_server_response_data.py +51 -0
  184. phenoml/tools/types/mcp_server_tool_call_response.py +37 -0
  185. phenoml/tools/types/mcp_server_tool_response.py +33 -0
  186. phenoml/tools/types/mcp_server_tool_response_data.py +61 -0
  187. phenoml/tools/types/search_concept.py +41 -0
  188. phenoml/types/__init__.py +21 -0
  189. phenoml/types/cohort_response.py +5 -0
  190. phenoml/types/lang2fhir_and_create_response.py +5 -0
  191. phenoml/types/lang2fhir_and_search_response.py +5 -0
  192. phenoml/types/mcp_server_response.py +5 -0
  193. phenoml/types/mcp_server_tool_call_response.py +5 -0
  194. phenoml/types/mcp_server_tool_response.py +5 -0
  195. phenoml/types/search_concept.py +5 -0
  196. phenoml/version.py +3 -0
  197. phenoml/workflows/__init__.py +66 -0
  198. phenoml/workflows/client.py +210 -0
  199. phenoml/workflows/errors/__init__.py +11 -0
  200. phenoml/workflows/errors/bad_request_error.py +10 -0
  201. phenoml/workflows/errors/forbidden_error.py +10 -0
  202. phenoml/workflows/errors/internal_server_error.py +10 -0
  203. phenoml/workflows/errors/not_found_error.py +10 -0
  204. phenoml/workflows/errors/unauthorized_error.py +10 -0
  205. phenoml/workflows/mcp_server/__init__.py +7 -0
  206. phenoml/workflows/mcp_server/client.py +274 -0
  207. phenoml/workflows/mcp_server/raw_client.py +226 -0
  208. phenoml/workflows/mcp_server/tools/__init__.py +4 -0
  209. phenoml/workflows/mcp_server/tools/client.py +287 -0
  210. phenoml/workflows/mcp_server/tools/raw_client.py +244 -0
  211. phenoml/workflows/raw_client.py +169 -0
  212. phenoml/workflows/types/__init__.py +43 -0
  213. phenoml/workflows/types/create_workflow_response.py +44 -0
  214. phenoml/workflows/types/decision_node_definition.py +32 -0
  215. phenoml/workflows/types/execute_workflow_response.py +30 -0
  216. phenoml/workflows/types/execute_workflow_response_results.py +22 -0
  217. phenoml/workflows/types/lang2fhir_create_definition.py +37 -0
  218. phenoml/workflows/types/lang2fhir_search_definition.py +42 -0
  219. phenoml/workflows/types/list_workflows_response.py +39 -0
  220. phenoml/workflows/types/step_operation.py +26 -0
  221. phenoml/workflows/types/sub_workflow_definition.py +32 -0
  222. phenoml/workflows/types/workflow_config.py +27 -0
  223. phenoml/workflows/types/workflow_definition.py +57 -0
  224. phenoml/workflows/types/workflow_graph.py +23 -0
  225. phenoml/workflows/types/workflow_response.py +61 -0
  226. phenoml/workflows/types/workflow_response_graph.py +23 -0
  227. phenoml/workflows/types/workflow_step.py +55 -0
  228. phenoml/workflows/types/workflow_step_summary.py +47 -0
  229. phenoml/workflows/types/workflow_step_summary_type.py +5 -0
  230. phenoml/workflows/types/workflow_step_type.py +5 -0
  231. phenoml/workflows/workflows/__init__.py +19 -0
  232. phenoml/workflows/workflows/client.py +694 -0
  233. phenoml/workflows/workflows/raw_client.py +1266 -0
  234. phenoml/workflows/workflows/types/__init__.py +17 -0
  235. phenoml/workflows/workflows/types/create_workflow_request_fhir_provider_id.py +5 -0
  236. phenoml/workflows/workflows/types/update_workflow_request_fhir_provider_id.py +5 -0
  237. phenoml/workflows/workflows/types/workflows_delete_response.py +20 -0
  238. phenoml/workflows/workflows/types/workflows_get_response.py +26 -0
  239. phenoml/workflows/workflows/types/workflows_update_response.py +31 -0
  240. phenoml/wrapper_client.py +123 -0
  241. phenoml-0.0.6.dist-info/LICENSE +21 -0
  242. phenoml-0.0.6.dist-info/METADATA +192 -0
  243. phenoml-0.0.6.dist-info/RECORD +244 -0
  244. phenoml-0.0.6.dist-info/WHEEL +4 -0
@@ -0,0 +1,706 @@
1
+ # This file was auto-generated by Fern from our API Definition.
2
+
3
+ import typing
4
+ from json.decoder import JSONDecodeError
5
+
6
+ from ..core.api_error import ApiError
7
+ from ..core.client_wrapper import AsyncClientWrapper, SyncClientWrapper
8
+ from ..core.http_response import AsyncHttpResponse, HttpResponse
9
+ from ..core.pydantic_utilities import parse_obj_as
10
+ from ..core.request_options import RequestOptions
11
+ from ..core.serialization import convert_and_respect_annotation_metadata
12
+ from .errors.bad_request_error import BadRequestError
13
+ from .errors.conflict_error import ConflictError
14
+ from .errors.failed_dependency_error import FailedDependencyError
15
+ from .errors.internal_server_error import InternalServerError
16
+ from .errors.unauthorized_error import UnauthorizedError
17
+ from .types.construe_cohort_request_config import ConstrueCohortRequestConfig
18
+ from .types.construe_cohort_response import ConstrueCohortResponse
19
+ from .types.construe_upload_code_system_response import ConstrueUploadCodeSystemResponse
20
+ from .types.extract_codes_result import ExtractCodesResult
21
+ from .types.extract_request_config import ExtractRequestConfig
22
+ from .types.extract_request_system import ExtractRequestSystem
23
+ from .types.upload_request_format import UploadRequestFormat
24
+
25
+ # this is used as the default value for optional parameters
26
+ OMIT = typing.cast(typing.Any, ...)
27
+
28
+
29
+ class RawConstrueClient:
30
+ def __init__(self, *, client_wrapper: SyncClientWrapper):
31
+ self._client_wrapper = client_wrapper
32
+
33
+ def upload_code_system(
34
+ self,
35
+ *,
36
+ name: str,
37
+ version: str,
38
+ format: UploadRequestFormat,
39
+ file: str,
40
+ revision: typing.Optional[float] = OMIT,
41
+ code_col: typing.Optional[str] = OMIT,
42
+ desc_col: typing.Optional[str] = OMIT,
43
+ defn_col: typing.Optional[str] = OMIT,
44
+ request_options: typing.Optional[RequestOptions] = None,
45
+ ) -> HttpResponse[ConstrueUploadCodeSystemResponse]:
46
+ """
47
+ Upload a custom medical code system with codes and descriptions for use in code extraction.
48
+ Upon upload, construe generates embeddings for all of the codes in the code system and stores them in the vector database so you can
49
+ subsequently use the code system for construe/extract and lang2fhir/create (coming soon!)
50
+
51
+ Parameters
52
+ ----------
53
+ name : str
54
+ Name of the code system
55
+
56
+ version : str
57
+ Version of the code system
58
+
59
+ format : UploadRequestFormat
60
+ Format of the uploaded file
61
+
62
+ file : str
63
+ The file contents as a base64-encoded string
64
+
65
+ revision : typing.Optional[float]
66
+ Optional revision number
67
+
68
+ code_col : typing.Optional[str]
69
+ Column name containing codes (required for CSV format)
70
+
71
+ desc_col : typing.Optional[str]
72
+ Column name containing descriptions (required for CSV format)
73
+
74
+ defn_col : typing.Optional[str]
75
+ Optional column name containing long definitions (for CSV format)
76
+
77
+ request_options : typing.Optional[RequestOptions]
78
+ Request-specific configuration.
79
+
80
+ Returns
81
+ -------
82
+ HttpResponse[ConstrueUploadCodeSystemResponse]
83
+ Successfully uploaded code system
84
+ """
85
+ _response = self._client_wrapper.httpx_client.request(
86
+ "construe/upload",
87
+ method="POST",
88
+ json={
89
+ "name": name,
90
+ "version": version,
91
+ "revision": revision,
92
+ "format": format,
93
+ "file": file,
94
+ "code_col": code_col,
95
+ "desc_col": desc_col,
96
+ "defn_col": defn_col,
97
+ },
98
+ headers={
99
+ "content-type": "application/json",
100
+ },
101
+ request_options=request_options,
102
+ omit=OMIT,
103
+ )
104
+ try:
105
+ if 200 <= _response.status_code < 300:
106
+ _data = typing.cast(
107
+ ConstrueUploadCodeSystemResponse,
108
+ parse_obj_as(
109
+ type_=ConstrueUploadCodeSystemResponse, # type: ignore
110
+ object_=_response.json(),
111
+ ),
112
+ )
113
+ return HttpResponse(response=_response, data=_data)
114
+ if _response.status_code == 400:
115
+ raise BadRequestError(
116
+ headers=dict(_response.headers),
117
+ body=typing.cast(
118
+ typing.Optional[typing.Any],
119
+ parse_obj_as(
120
+ type_=typing.Optional[typing.Any], # type: ignore
121
+ object_=_response.json(),
122
+ ),
123
+ ),
124
+ )
125
+ if _response.status_code == 401:
126
+ raise UnauthorizedError(
127
+ headers=dict(_response.headers),
128
+ body=typing.cast(
129
+ typing.Optional[typing.Any],
130
+ parse_obj_as(
131
+ type_=typing.Optional[typing.Any], # type: ignore
132
+ object_=_response.json(),
133
+ ),
134
+ ),
135
+ )
136
+ if _response.status_code == 409:
137
+ raise ConflictError(
138
+ headers=dict(_response.headers),
139
+ body=typing.cast(
140
+ typing.Optional[typing.Any],
141
+ parse_obj_as(
142
+ type_=typing.Optional[typing.Any], # type: ignore
143
+ object_=_response.json(),
144
+ ),
145
+ ),
146
+ )
147
+ if _response.status_code == 424:
148
+ raise FailedDependencyError(
149
+ headers=dict(_response.headers),
150
+ body=typing.cast(
151
+ typing.Optional[typing.Any],
152
+ parse_obj_as(
153
+ type_=typing.Optional[typing.Any], # type: ignore
154
+ object_=_response.json(),
155
+ ),
156
+ ),
157
+ )
158
+ if _response.status_code == 500:
159
+ raise InternalServerError(
160
+ headers=dict(_response.headers),
161
+ body=typing.cast(
162
+ typing.Optional[typing.Any],
163
+ parse_obj_as(
164
+ type_=typing.Optional[typing.Any], # type: ignore
165
+ object_=_response.json(),
166
+ ),
167
+ ),
168
+ )
169
+ _response_json = _response.json()
170
+ except JSONDecodeError:
171
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
172
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
173
+
174
+ def extract_codes(
175
+ self,
176
+ *,
177
+ text: str,
178
+ system: typing.Optional[ExtractRequestSystem] = OMIT,
179
+ config: typing.Optional[ExtractRequestConfig] = OMIT,
180
+ request_options: typing.Optional[RequestOptions] = None,
181
+ ) -> HttpResponse[ExtractCodesResult]:
182
+ """
183
+ Converts natural language text into structured medical codes
184
+
185
+ Parameters
186
+ ----------
187
+ text : str
188
+ Natural language text to extract codes from
189
+
190
+ system : typing.Optional[ExtractRequestSystem]
191
+
192
+ config : typing.Optional[ExtractRequestConfig]
193
+
194
+ request_options : typing.Optional[RequestOptions]
195
+ Request-specific configuration.
196
+
197
+ Returns
198
+ -------
199
+ HttpResponse[ExtractCodesResult]
200
+ Successfully extracted codes
201
+ """
202
+ _response = self._client_wrapper.httpx_client.request(
203
+ "construe/extract",
204
+ method="POST",
205
+ json={
206
+ "text": text,
207
+ "system": convert_and_respect_annotation_metadata(
208
+ object_=system, annotation=ExtractRequestSystem, direction="write"
209
+ ),
210
+ "config": convert_and_respect_annotation_metadata(
211
+ object_=config, annotation=ExtractRequestConfig, direction="write"
212
+ ),
213
+ },
214
+ headers={
215
+ "content-type": "application/json",
216
+ },
217
+ request_options=request_options,
218
+ omit=OMIT,
219
+ )
220
+ try:
221
+ if 200 <= _response.status_code < 300:
222
+ _data = typing.cast(
223
+ ExtractCodesResult,
224
+ parse_obj_as(
225
+ type_=ExtractCodesResult, # type: ignore
226
+ object_=_response.json(),
227
+ ),
228
+ )
229
+ return HttpResponse(response=_response, data=_data)
230
+ if _response.status_code == 400:
231
+ raise BadRequestError(
232
+ headers=dict(_response.headers),
233
+ body=typing.cast(
234
+ typing.Optional[typing.Any],
235
+ parse_obj_as(
236
+ type_=typing.Optional[typing.Any], # type: ignore
237
+ object_=_response.json(),
238
+ ),
239
+ ),
240
+ )
241
+ if _response.status_code == 401:
242
+ raise UnauthorizedError(
243
+ headers=dict(_response.headers),
244
+ body=typing.cast(
245
+ typing.Optional[typing.Any],
246
+ parse_obj_as(
247
+ type_=typing.Optional[typing.Any], # type: ignore
248
+ object_=_response.json(),
249
+ ),
250
+ ),
251
+ )
252
+ if _response.status_code == 424:
253
+ raise FailedDependencyError(
254
+ headers=dict(_response.headers),
255
+ body=typing.cast(
256
+ typing.Optional[typing.Any],
257
+ parse_obj_as(
258
+ type_=typing.Optional[typing.Any], # type: ignore
259
+ object_=_response.json(),
260
+ ),
261
+ ),
262
+ )
263
+ if _response.status_code == 500:
264
+ raise InternalServerError(
265
+ headers=dict(_response.headers),
266
+ body=typing.cast(
267
+ typing.Optional[typing.Any],
268
+ parse_obj_as(
269
+ type_=typing.Optional[typing.Any], # type: ignore
270
+ object_=_response.json(),
271
+ ),
272
+ ),
273
+ )
274
+ _response_json = _response.json()
275
+ except JSONDecodeError:
276
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
277
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
278
+
279
+ def cohort(
280
+ self,
281
+ *,
282
+ text: str,
283
+ config: typing.Optional[ConstrueCohortRequestConfig] = OMIT,
284
+ request_options: typing.Optional[RequestOptions] = None,
285
+ ) -> HttpResponse[ConstrueCohortResponse]:
286
+ """
287
+ Creates a patient cohort based on a natural language description.
288
+ Translates the description into FHIR search queries and optional SQL queries.
289
+
290
+ Parameters
291
+ ----------
292
+ text : str
293
+ Natural language description of the desired patient cohort.
294
+
295
+ config : typing.Optional[ConstrueCohortRequestConfig]
296
+
297
+ request_options : typing.Optional[RequestOptions]
298
+ Request-specific configuration.
299
+
300
+ Returns
301
+ -------
302
+ HttpResponse[ConstrueCohortResponse]
303
+ Cohort creation successful
304
+ """
305
+ _response = self._client_wrapper.httpx_client.request(
306
+ "construe/cohort",
307
+ method="POST",
308
+ json={
309
+ "config": convert_and_respect_annotation_metadata(
310
+ object_=config, annotation=ConstrueCohortRequestConfig, direction="write"
311
+ ),
312
+ "text": text,
313
+ },
314
+ headers={
315
+ "content-type": "application/json",
316
+ },
317
+ request_options=request_options,
318
+ omit=OMIT,
319
+ )
320
+ try:
321
+ if 200 <= _response.status_code < 300:
322
+ _data = typing.cast(
323
+ ConstrueCohortResponse,
324
+ parse_obj_as(
325
+ type_=ConstrueCohortResponse, # type: ignore
326
+ object_=_response.json(),
327
+ ),
328
+ )
329
+ return HttpResponse(response=_response, data=_data)
330
+ if _response.status_code == 400:
331
+ raise BadRequestError(
332
+ headers=dict(_response.headers),
333
+ body=typing.cast(
334
+ typing.Optional[typing.Any],
335
+ parse_obj_as(
336
+ type_=typing.Optional[typing.Any], # type: ignore
337
+ object_=_response.json(),
338
+ ),
339
+ ),
340
+ )
341
+ if _response.status_code == 401:
342
+ raise UnauthorizedError(
343
+ headers=dict(_response.headers),
344
+ body=typing.cast(
345
+ typing.Optional[typing.Any],
346
+ parse_obj_as(
347
+ type_=typing.Optional[typing.Any], # type: ignore
348
+ object_=_response.json(),
349
+ ),
350
+ ),
351
+ )
352
+ if _response.status_code == 500:
353
+ raise InternalServerError(
354
+ headers=dict(_response.headers),
355
+ body=typing.cast(
356
+ typing.Optional[typing.Any],
357
+ parse_obj_as(
358
+ type_=typing.Optional[typing.Any], # type: ignore
359
+ object_=_response.json(),
360
+ ),
361
+ ),
362
+ )
363
+ _response_json = _response.json()
364
+ except JSONDecodeError:
365
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
366
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
367
+
368
+
369
+ class AsyncRawConstrueClient:
370
+ def __init__(self, *, client_wrapper: AsyncClientWrapper):
371
+ self._client_wrapper = client_wrapper
372
+
373
+ async def upload_code_system(
374
+ self,
375
+ *,
376
+ name: str,
377
+ version: str,
378
+ format: UploadRequestFormat,
379
+ file: str,
380
+ revision: typing.Optional[float] = OMIT,
381
+ code_col: typing.Optional[str] = OMIT,
382
+ desc_col: typing.Optional[str] = OMIT,
383
+ defn_col: typing.Optional[str] = OMIT,
384
+ request_options: typing.Optional[RequestOptions] = None,
385
+ ) -> AsyncHttpResponse[ConstrueUploadCodeSystemResponse]:
386
+ """
387
+ Upload a custom medical code system with codes and descriptions for use in code extraction.
388
+ Upon upload, construe generates embeddings for all of the codes in the code system and stores them in the vector database so you can
389
+ subsequently use the code system for construe/extract and lang2fhir/create (coming soon!)
390
+
391
+ Parameters
392
+ ----------
393
+ name : str
394
+ Name of the code system
395
+
396
+ version : str
397
+ Version of the code system
398
+
399
+ format : UploadRequestFormat
400
+ Format of the uploaded file
401
+
402
+ file : str
403
+ The file contents as a base64-encoded string
404
+
405
+ revision : typing.Optional[float]
406
+ Optional revision number
407
+
408
+ code_col : typing.Optional[str]
409
+ Column name containing codes (required for CSV format)
410
+
411
+ desc_col : typing.Optional[str]
412
+ Column name containing descriptions (required for CSV format)
413
+
414
+ defn_col : typing.Optional[str]
415
+ Optional column name containing long definitions (for CSV format)
416
+
417
+ request_options : typing.Optional[RequestOptions]
418
+ Request-specific configuration.
419
+
420
+ Returns
421
+ -------
422
+ AsyncHttpResponse[ConstrueUploadCodeSystemResponse]
423
+ Successfully uploaded code system
424
+ """
425
+ _response = await self._client_wrapper.httpx_client.request(
426
+ "construe/upload",
427
+ method="POST",
428
+ json={
429
+ "name": name,
430
+ "version": version,
431
+ "revision": revision,
432
+ "format": format,
433
+ "file": file,
434
+ "code_col": code_col,
435
+ "desc_col": desc_col,
436
+ "defn_col": defn_col,
437
+ },
438
+ headers={
439
+ "content-type": "application/json",
440
+ },
441
+ request_options=request_options,
442
+ omit=OMIT,
443
+ )
444
+ try:
445
+ if 200 <= _response.status_code < 300:
446
+ _data = typing.cast(
447
+ ConstrueUploadCodeSystemResponse,
448
+ parse_obj_as(
449
+ type_=ConstrueUploadCodeSystemResponse, # type: ignore
450
+ object_=_response.json(),
451
+ ),
452
+ )
453
+ return AsyncHttpResponse(response=_response, data=_data)
454
+ if _response.status_code == 400:
455
+ raise BadRequestError(
456
+ headers=dict(_response.headers),
457
+ body=typing.cast(
458
+ typing.Optional[typing.Any],
459
+ parse_obj_as(
460
+ type_=typing.Optional[typing.Any], # type: ignore
461
+ object_=_response.json(),
462
+ ),
463
+ ),
464
+ )
465
+ if _response.status_code == 401:
466
+ raise UnauthorizedError(
467
+ headers=dict(_response.headers),
468
+ body=typing.cast(
469
+ typing.Optional[typing.Any],
470
+ parse_obj_as(
471
+ type_=typing.Optional[typing.Any], # type: ignore
472
+ object_=_response.json(),
473
+ ),
474
+ ),
475
+ )
476
+ if _response.status_code == 409:
477
+ raise ConflictError(
478
+ headers=dict(_response.headers),
479
+ body=typing.cast(
480
+ typing.Optional[typing.Any],
481
+ parse_obj_as(
482
+ type_=typing.Optional[typing.Any], # type: ignore
483
+ object_=_response.json(),
484
+ ),
485
+ ),
486
+ )
487
+ if _response.status_code == 424:
488
+ raise FailedDependencyError(
489
+ headers=dict(_response.headers),
490
+ body=typing.cast(
491
+ typing.Optional[typing.Any],
492
+ parse_obj_as(
493
+ type_=typing.Optional[typing.Any], # type: ignore
494
+ object_=_response.json(),
495
+ ),
496
+ ),
497
+ )
498
+ if _response.status_code == 500:
499
+ raise InternalServerError(
500
+ headers=dict(_response.headers),
501
+ body=typing.cast(
502
+ typing.Optional[typing.Any],
503
+ parse_obj_as(
504
+ type_=typing.Optional[typing.Any], # type: ignore
505
+ object_=_response.json(),
506
+ ),
507
+ ),
508
+ )
509
+ _response_json = _response.json()
510
+ except JSONDecodeError:
511
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
512
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
513
+
514
+ async def extract_codes(
515
+ self,
516
+ *,
517
+ text: str,
518
+ system: typing.Optional[ExtractRequestSystem] = OMIT,
519
+ config: typing.Optional[ExtractRequestConfig] = OMIT,
520
+ request_options: typing.Optional[RequestOptions] = None,
521
+ ) -> AsyncHttpResponse[ExtractCodesResult]:
522
+ """
523
+ Converts natural language text into structured medical codes
524
+
525
+ Parameters
526
+ ----------
527
+ text : str
528
+ Natural language text to extract codes from
529
+
530
+ system : typing.Optional[ExtractRequestSystem]
531
+
532
+ config : typing.Optional[ExtractRequestConfig]
533
+
534
+ request_options : typing.Optional[RequestOptions]
535
+ Request-specific configuration.
536
+
537
+ Returns
538
+ -------
539
+ AsyncHttpResponse[ExtractCodesResult]
540
+ Successfully extracted codes
541
+ """
542
+ _response = await self._client_wrapper.httpx_client.request(
543
+ "construe/extract",
544
+ method="POST",
545
+ json={
546
+ "text": text,
547
+ "system": convert_and_respect_annotation_metadata(
548
+ object_=system, annotation=ExtractRequestSystem, direction="write"
549
+ ),
550
+ "config": convert_and_respect_annotation_metadata(
551
+ object_=config, annotation=ExtractRequestConfig, direction="write"
552
+ ),
553
+ },
554
+ headers={
555
+ "content-type": "application/json",
556
+ },
557
+ request_options=request_options,
558
+ omit=OMIT,
559
+ )
560
+ try:
561
+ if 200 <= _response.status_code < 300:
562
+ _data = typing.cast(
563
+ ExtractCodesResult,
564
+ parse_obj_as(
565
+ type_=ExtractCodesResult, # type: ignore
566
+ object_=_response.json(),
567
+ ),
568
+ )
569
+ return AsyncHttpResponse(response=_response, data=_data)
570
+ if _response.status_code == 400:
571
+ raise BadRequestError(
572
+ headers=dict(_response.headers),
573
+ body=typing.cast(
574
+ typing.Optional[typing.Any],
575
+ parse_obj_as(
576
+ type_=typing.Optional[typing.Any], # type: ignore
577
+ object_=_response.json(),
578
+ ),
579
+ ),
580
+ )
581
+ if _response.status_code == 401:
582
+ raise UnauthorizedError(
583
+ headers=dict(_response.headers),
584
+ body=typing.cast(
585
+ typing.Optional[typing.Any],
586
+ parse_obj_as(
587
+ type_=typing.Optional[typing.Any], # type: ignore
588
+ object_=_response.json(),
589
+ ),
590
+ ),
591
+ )
592
+ if _response.status_code == 424:
593
+ raise FailedDependencyError(
594
+ headers=dict(_response.headers),
595
+ body=typing.cast(
596
+ typing.Optional[typing.Any],
597
+ parse_obj_as(
598
+ type_=typing.Optional[typing.Any], # type: ignore
599
+ object_=_response.json(),
600
+ ),
601
+ ),
602
+ )
603
+ if _response.status_code == 500:
604
+ raise InternalServerError(
605
+ headers=dict(_response.headers),
606
+ body=typing.cast(
607
+ typing.Optional[typing.Any],
608
+ parse_obj_as(
609
+ type_=typing.Optional[typing.Any], # type: ignore
610
+ object_=_response.json(),
611
+ ),
612
+ ),
613
+ )
614
+ _response_json = _response.json()
615
+ except JSONDecodeError:
616
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
617
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
618
+
619
+ async def cohort(
620
+ self,
621
+ *,
622
+ text: str,
623
+ config: typing.Optional[ConstrueCohortRequestConfig] = OMIT,
624
+ request_options: typing.Optional[RequestOptions] = None,
625
+ ) -> AsyncHttpResponse[ConstrueCohortResponse]:
626
+ """
627
+ Creates a patient cohort based on a natural language description.
628
+ Translates the description into FHIR search queries and optional SQL queries.
629
+
630
+ Parameters
631
+ ----------
632
+ text : str
633
+ Natural language description of the desired patient cohort.
634
+
635
+ config : typing.Optional[ConstrueCohortRequestConfig]
636
+
637
+ request_options : typing.Optional[RequestOptions]
638
+ Request-specific configuration.
639
+
640
+ Returns
641
+ -------
642
+ AsyncHttpResponse[ConstrueCohortResponse]
643
+ Cohort creation successful
644
+ """
645
+ _response = await self._client_wrapper.httpx_client.request(
646
+ "construe/cohort",
647
+ method="POST",
648
+ json={
649
+ "config": convert_and_respect_annotation_metadata(
650
+ object_=config, annotation=ConstrueCohortRequestConfig, direction="write"
651
+ ),
652
+ "text": text,
653
+ },
654
+ headers={
655
+ "content-type": "application/json",
656
+ },
657
+ request_options=request_options,
658
+ omit=OMIT,
659
+ )
660
+ try:
661
+ if 200 <= _response.status_code < 300:
662
+ _data = typing.cast(
663
+ ConstrueCohortResponse,
664
+ parse_obj_as(
665
+ type_=ConstrueCohortResponse, # type: ignore
666
+ object_=_response.json(),
667
+ ),
668
+ )
669
+ return AsyncHttpResponse(response=_response, data=_data)
670
+ if _response.status_code == 400:
671
+ raise BadRequestError(
672
+ headers=dict(_response.headers),
673
+ body=typing.cast(
674
+ typing.Optional[typing.Any],
675
+ parse_obj_as(
676
+ type_=typing.Optional[typing.Any], # type: ignore
677
+ object_=_response.json(),
678
+ ),
679
+ ),
680
+ )
681
+ if _response.status_code == 401:
682
+ raise UnauthorizedError(
683
+ headers=dict(_response.headers),
684
+ body=typing.cast(
685
+ typing.Optional[typing.Any],
686
+ parse_obj_as(
687
+ type_=typing.Optional[typing.Any], # type: ignore
688
+ object_=_response.json(),
689
+ ),
690
+ ),
691
+ )
692
+ if _response.status_code == 500:
693
+ raise InternalServerError(
694
+ headers=dict(_response.headers),
695
+ body=typing.cast(
696
+ typing.Optional[typing.Any],
697
+ parse_obj_as(
698
+ type_=typing.Optional[typing.Any], # type: ignore
699
+ object_=_response.json(),
700
+ ),
701
+ ),
702
+ )
703
+ _response_json = _response.json()
704
+ except JSONDecodeError:
705
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
706
+ raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)