phenoml 0.0.6__py3-none-any.whl → 0.0.8__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 (54) hide show
  1. phenoml/client.py +3 -0
  2. phenoml/core/client_wrapper.py +2 -2
  3. phenoml/summary/__init__.py +39 -0
  4. phenoml/summary/client.py +656 -0
  5. phenoml/summary/errors/__init__.py +11 -0
  6. phenoml/summary/errors/bad_request_error.py +10 -0
  7. phenoml/summary/errors/forbidden_error.py +10 -0
  8. phenoml/summary/errors/internal_server_error.py +10 -0
  9. phenoml/summary/errors/not_found_error.py +10 -0
  10. phenoml/summary/errors/unauthorized_error.py +10 -0
  11. phenoml/{workflows/workflows → summary}/raw_client.py +236 -312
  12. phenoml/summary/types/__init__.py +31 -0
  13. phenoml/summary/types/create_summary_request_fhir_resources.py +8 -0
  14. phenoml/summary/types/create_summary_request_mode.py +5 -0
  15. phenoml/summary/types/create_summary_response.py +29 -0
  16. phenoml/summary/types/create_summary_template_response.py +23 -0
  17. phenoml/summary/types/fhir_bundle.py +23 -0
  18. phenoml/summary/types/fhir_bundle_entry_item.py +20 -0
  19. phenoml/summary/types/fhir_resource.py +24 -0
  20. phenoml/summary/types/summary_delete_template_response.py +20 -0
  21. phenoml/summary/types/summary_get_template_response.py +21 -0
  22. phenoml/summary/types/summary_list_templates_response.py +21 -0
  23. phenoml/summary/types/summary_template.py +41 -0
  24. phenoml/summary/types/summary_update_template_response.py +22 -0
  25. phenoml/workflows/__init__.py +3 -8
  26. phenoml/workflows/client.py +517 -33
  27. phenoml/workflows/raw_client.py +1129 -32
  28. phenoml/workflows/types/__init__.py +10 -0
  29. phenoml/workflows/{workflows/types → types}/workflows_delete_response.py +1 -1
  30. phenoml/workflows/{workflows/types → types}/workflows_get_response.py +3 -3
  31. phenoml/workflows/{workflows/types → types}/workflows_update_response.py +3 -3
  32. {phenoml-0.0.6.dist-info → phenoml-0.0.8.dist-info}/METADATA +1 -1
  33. {phenoml-0.0.6.dist-info → phenoml-0.0.8.dist-info}/RECORD +37 -33
  34. phenoml/types/__init__.py +0 -21
  35. phenoml/types/cohort_response.py +0 -5
  36. phenoml/types/lang2fhir_and_create_response.py +0 -5
  37. phenoml/types/lang2fhir_and_search_response.py +0 -5
  38. phenoml/types/mcp_server_response.py +0 -5
  39. phenoml/types/mcp_server_tool_call_response.py +0 -5
  40. phenoml/types/mcp_server_tool_response.py +0 -5
  41. phenoml/types/search_concept.py +0 -5
  42. phenoml/workflows/mcp_server/__init__.py +0 -7
  43. phenoml/workflows/mcp_server/client.py +0 -274
  44. phenoml/workflows/mcp_server/raw_client.py +0 -226
  45. phenoml/workflows/mcp_server/tools/__init__.py +0 -4
  46. phenoml/workflows/mcp_server/tools/client.py +0 -287
  47. phenoml/workflows/mcp_server/tools/raw_client.py +0 -244
  48. phenoml/workflows/workflows/__init__.py +0 -19
  49. phenoml/workflows/workflows/client.py +0 -694
  50. phenoml/workflows/workflows/types/__init__.py +0 -17
  51. /phenoml/workflows/{workflows/types → types}/create_workflow_request_fhir_provider_id.py +0 -0
  52. /phenoml/workflows/{workflows/types → types}/update_workflow_request_fhir_provider_id.py +0 -0
  53. {phenoml-0.0.6.dist-info → phenoml-0.0.8.dist-info}/LICENSE +0 -0
  54. {phenoml-0.0.6.dist-info → phenoml-0.0.8.dist-info}/WHEEL +0 -0
@@ -3,68 +3,62 @@
3
3
  import typing
4
4
  from json.decoder import JSONDecodeError
5
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.jsonable_encoder import jsonable_encoder
10
- from ...core.pydantic_utilities import parse_obj_as
11
- from ...core.request_options import RequestOptions
12
- from ...core.serialization import convert_and_respect_annotation_metadata
13
- from ..errors.bad_request_error import BadRequestError
14
- from ..errors.forbidden_error import ForbiddenError
15
- from ..errors.internal_server_error import InternalServerError
16
- from ..errors.not_found_error import NotFoundError
17
- from ..errors.unauthorized_error import UnauthorizedError
18
- from ..types.create_workflow_response import CreateWorkflowResponse
19
- from ..types.execute_workflow_response import ExecuteWorkflowResponse
20
- from ..types.list_workflows_response import ListWorkflowsResponse
21
- from .types.create_workflow_request_fhir_provider_id import CreateWorkflowRequestFhirProviderId
22
- from .types.update_workflow_request_fhir_provider_id import UpdateWorkflowRequestFhirProviderId
23
- from .types.workflows_delete_response import WorkflowsDeleteResponse
24
- from .types.workflows_get_response import WorkflowsGetResponse
25
- from .types.workflows_update_response import WorkflowsUpdateResponse
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.jsonable_encoder import jsonable_encoder
10
+ from ..core.pydantic_utilities import parse_obj_as
11
+ from ..core.request_options import RequestOptions
12
+ from ..core.serialization import convert_and_respect_annotation_metadata
13
+ from .errors.bad_request_error import BadRequestError
14
+ from .errors.forbidden_error import ForbiddenError
15
+ from .errors.internal_server_error import InternalServerError
16
+ from .errors.not_found_error import NotFoundError
17
+ from .errors.unauthorized_error import UnauthorizedError
18
+ from .types.create_summary_request_fhir_resources import CreateSummaryRequestFhirResources
19
+ from .types.create_summary_request_mode import CreateSummaryRequestMode
20
+ from .types.create_summary_response import CreateSummaryResponse
21
+ from .types.create_summary_template_response import CreateSummaryTemplateResponse
22
+ from .types.summary_delete_template_response import SummaryDeleteTemplateResponse
23
+ from .types.summary_get_template_response import SummaryGetTemplateResponse
24
+ from .types.summary_list_templates_response import SummaryListTemplatesResponse
25
+ from .types.summary_update_template_response import SummaryUpdateTemplateResponse
26
26
 
27
27
  # this is used as the default value for optional parameters
28
28
  OMIT = typing.cast(typing.Any, ...)
29
29
 
30
30
 
31
- class RawWorkflowsClient:
31
+ class RawSummaryClient:
32
32
  def __init__(self, *, client_wrapper: SyncClientWrapper):
33
33
  self._client_wrapper = client_wrapper
34
34
 
35
- def list(
36
- self, *, verbose: typing.Optional[bool] = None, request_options: typing.Optional[RequestOptions] = None
37
- ) -> HttpResponse[ListWorkflowsResponse]:
35
+ def list_templates(
36
+ self, *, request_options: typing.Optional[RequestOptions] = None
37
+ ) -> HttpResponse[SummaryListTemplatesResponse]:
38
38
  """
39
- Retrieves all workflow definitions for the authenticated user
39
+ Retrieves all summary templates for the authenticated user
40
40
 
41
41
  Parameters
42
42
  ----------
43
- verbose : typing.Optional[bool]
44
- If true, includes full workflow implementation details in workflow_details field
45
-
46
43
  request_options : typing.Optional[RequestOptions]
47
44
  Request-specific configuration.
48
45
 
49
46
  Returns
50
47
  -------
51
- HttpResponse[ListWorkflowsResponse]
52
- Successfully retrieved workflows
48
+ HttpResponse[SummaryListTemplatesResponse]
49
+ Templates retrieved successfully
53
50
  """
54
51
  _response = self._client_wrapper.httpx_client.request(
55
- "workflows",
52
+ "fhir2summary/templates",
56
53
  method="GET",
57
- params={
58
- "verbose": verbose,
59
- },
60
54
  request_options=request_options,
61
55
  )
62
56
  try:
63
57
  if 200 <= _response.status_code < 300:
64
58
  _data = typing.cast(
65
- ListWorkflowsResponse,
59
+ SummaryListTemplatesResponse,
66
60
  parse_obj_as(
67
- type_=ListWorkflowsResponse, # type: ignore
61
+ type_=SummaryListTemplatesResponse, # type: ignore
68
62
  object_=_response.json(),
69
63
  ),
70
64
  )
@@ -80,17 +74,6 @@ class RawWorkflowsClient:
80
74
  ),
81
75
  ),
82
76
  )
83
- if _response.status_code == 403:
84
- raise ForbiddenError(
85
- headers=dict(_response.headers),
86
- body=typing.cast(
87
- typing.Optional[typing.Any],
88
- parse_obj_as(
89
- type_=typing.Optional[typing.Any], # type: ignore
90
- object_=_response.json(),
91
- ),
92
- ),
93
- )
94
77
  if _response.status_code == 500:
95
78
  raise InternalServerError(
96
79
  headers=dict(_response.headers),
@@ -107,62 +90,58 @@ class RawWorkflowsClient:
107
90
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
108
91
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
109
92
 
110
- def create(
93
+ def create_template(
111
94
  self,
112
95
  *,
113
96
  name: str,
114
- workflow_instructions: str,
115
- sample_data: typing.Dict[str, typing.Optional[typing.Any]],
116
- fhir_provider_id: CreateWorkflowRequestFhirProviderId,
117
- verbose: typing.Optional[bool] = None,
118
- dynamic_generation: typing.Optional[bool] = OMIT,
97
+ example_summary: str,
98
+ target_resources: typing.Sequence[str],
99
+ mode: str,
100
+ description: typing.Optional[str] = OMIT,
101
+ example_fhir_data: typing.Optional[typing.Dict[str, typing.Optional[typing.Any]]] = OMIT,
119
102
  request_options: typing.Optional[RequestOptions] = None,
120
- ) -> HttpResponse[CreateWorkflowResponse]:
103
+ ) -> HttpResponse[CreateSummaryTemplateResponse]:
121
104
  """
122
- Creates a new workflow definition with graph generation from workflow instructions
105
+ Creates a summary template from an example using LLM function calling
123
106
 
124
107
  Parameters
125
108
  ----------
126
109
  name : str
127
- Human-readable name for the workflow
110
+ Name of the template
128
111
 
129
- workflow_instructions : str
130
- Natural language instructions that define the workflow logic
112
+ example_summary : str
113
+ Example summary note to generate template from
131
114
 
132
- sample_data : typing.Dict[str, typing.Optional[typing.Any]]
133
- Sample data to use for workflow graph generation
115
+ target_resources : typing.Sequence[str]
116
+ List of target FHIR resources
134
117
 
135
- fhir_provider_id : CreateWorkflowRequestFhirProviderId
136
- FHIR provider ID(s) - must be valid UUID(s) from existing FHIR providers
118
+ mode : str
119
+ Template mode (stored with the template)
137
120
 
138
- verbose : typing.Optional[bool]
139
- If true, includes full workflow implementation details in workflow_details field
121
+ description : typing.Optional[str]
122
+ Description of the template
140
123
 
141
- dynamic_generation : typing.Optional[bool]
142
- Enable dynamic lang2fhir calls instead of pre-populated templates
124
+ example_fhir_data : typing.Optional[typing.Dict[str, typing.Optional[typing.Any]]]
125
+ Optional example FHIR data that corresponds to the example summary
143
126
 
144
127
  request_options : typing.Optional[RequestOptions]
145
128
  Request-specific configuration.
146
129
 
147
130
  Returns
148
131
  -------
149
- HttpResponse[CreateWorkflowResponse]
150
- Successfully created workflow
132
+ HttpResponse[CreateSummaryTemplateResponse]
133
+ Template created successfully
151
134
  """
152
135
  _response = self._client_wrapper.httpx_client.request(
153
- "workflows",
136
+ "fhir2summary/template",
154
137
  method="POST",
155
- params={
156
- "verbose": verbose,
157
- },
158
138
  json={
159
139
  "name": name,
160
- "workflow_instructions": workflow_instructions,
161
- "sample_data": sample_data,
162
- "fhir_provider_id": convert_and_respect_annotation_metadata(
163
- object_=fhir_provider_id, annotation=CreateWorkflowRequestFhirProviderId, direction="write"
164
- ),
165
- "dynamic_generation": dynamic_generation,
140
+ "description": description,
141
+ "example_summary": example_summary,
142
+ "target_resources": target_resources,
143
+ "example_fhir_data": example_fhir_data,
144
+ "mode": mode,
166
145
  },
167
146
  headers={
168
147
  "content-type": "application/json",
@@ -173,9 +152,9 @@ class RawWorkflowsClient:
173
152
  try:
174
153
  if 200 <= _response.status_code < 300:
175
154
  _data = typing.cast(
176
- CreateWorkflowResponse,
155
+ CreateSummaryTemplateResponse,
177
156
  parse_obj_as(
178
- type_=CreateWorkflowResponse, # type: ignore
157
+ type_=CreateSummaryTemplateResponse, # type: ignore
179
158
  object_=_response.json(),
180
159
  ),
181
160
  )
@@ -202,17 +181,6 @@ class RawWorkflowsClient:
202
181
  ),
203
182
  ),
204
183
  )
205
- if _response.status_code == 403:
206
- raise ForbiddenError(
207
- headers=dict(_response.headers),
208
- body=typing.cast(
209
- typing.Optional[typing.Any],
210
- parse_obj_as(
211
- type_=typing.Optional[typing.Any], # type: ignore
212
- object_=_response.json(),
213
- ),
214
- ),
215
- )
216
184
  if _response.status_code == 500:
217
185
  raise InternalServerError(
218
186
  headers=dict(_response.headers),
@@ -229,42 +197,36 @@ class RawWorkflowsClient:
229
197
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
230
198
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
231
199
 
232
- def get(
233
- self, id: str, *, verbose: typing.Optional[bool] = None, request_options: typing.Optional[RequestOptions] = None
234
- ) -> HttpResponse[WorkflowsGetResponse]:
200
+ def get_template(
201
+ self, id: str, *, request_options: typing.Optional[RequestOptions] = None
202
+ ) -> HttpResponse[SummaryGetTemplateResponse]:
235
203
  """
236
- Retrieves a workflow definition by its ID
204
+ Retrieves a specific summary template
237
205
 
238
206
  Parameters
239
207
  ----------
240
208
  id : str
241
- ID of the workflow to retrieve
242
-
243
- verbose : typing.Optional[bool]
244
- If true, includes full workflow implementation details in workflow_details field
209
+ Template ID
245
210
 
246
211
  request_options : typing.Optional[RequestOptions]
247
212
  Request-specific configuration.
248
213
 
249
214
  Returns
250
215
  -------
251
- HttpResponse[WorkflowsGetResponse]
252
- Successfully retrieved workflow
216
+ HttpResponse[SummaryGetTemplateResponse]
217
+ Template retrieved successfully
253
218
  """
254
219
  _response = self._client_wrapper.httpx_client.request(
255
- f"workflows/{jsonable_encoder(id)}",
220
+ f"fhir2summary/template/{jsonable_encoder(id)}",
256
221
  method="GET",
257
- params={
258
- "verbose": verbose,
259
- },
260
222
  request_options=request_options,
261
223
  )
262
224
  try:
263
225
  if 200 <= _response.status_code < 300:
264
226
  _data = typing.cast(
265
- WorkflowsGetResponse,
227
+ SummaryGetTemplateResponse,
266
228
  parse_obj_as(
267
- type_=WorkflowsGetResponse, # type: ignore
229
+ type_=SummaryGetTemplateResponse, # type: ignore
268
230
  object_=_response.json(),
269
231
  ),
270
232
  )
@@ -318,66 +280,54 @@ class RawWorkflowsClient:
318
280
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
319
281
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
320
282
 
321
- def update(
283
+ def update_template(
322
284
  self,
323
285
  id: str,
324
286
  *,
325
287
  name: str,
326
- workflow_instructions: str,
327
- sample_data: typing.Dict[str, typing.Optional[typing.Any]],
328
- fhir_provider_id: UpdateWorkflowRequestFhirProviderId,
329
- verbose: typing.Optional[bool] = None,
330
- dynamic_generation: typing.Optional[bool] = OMIT,
288
+ template: str,
289
+ target_resources: typing.Sequence[str],
290
+ mode: str,
291
+ description: typing.Optional[str] = OMIT,
331
292
  request_options: typing.Optional[RequestOptions] = None,
332
- ) -> HttpResponse[WorkflowsUpdateResponse]:
293
+ ) -> HttpResponse[SummaryUpdateTemplateResponse]:
333
294
  """
334
- Updates an existing workflow definition
295
+ Updates an existing summary template
335
296
 
336
297
  Parameters
337
298
  ----------
338
299
  id : str
339
- ID of the workflow to update
300
+ Template ID
340
301
 
341
302
  name : str
342
- Human-readable name for the workflow
343
-
344
- workflow_instructions : str
345
- Natural language instructions that define the workflow logic
346
303
 
347
- sample_data : typing.Dict[str, typing.Optional[typing.Any]]
348
- Sample data to use for workflow graph generation
304
+ template : str
305
+ Updated template with placeholders
349
306
 
350
- fhir_provider_id : UpdateWorkflowRequestFhirProviderId
351
- FHIR provider ID(s) - must be valid UUID(s) from existing FHIR providers
307
+ target_resources : typing.Sequence[str]
352
308
 
353
- verbose : typing.Optional[bool]
354
- If true, includes full workflow implementation details in workflow_details field
309
+ mode : str
310
+ Template mode
355
311
 
356
- dynamic_generation : typing.Optional[bool]
357
- Enable dynamic lang2fhir calls instead of pre-populated templates
312
+ description : typing.Optional[str]
358
313
 
359
314
  request_options : typing.Optional[RequestOptions]
360
315
  Request-specific configuration.
361
316
 
362
317
  Returns
363
318
  -------
364
- HttpResponse[WorkflowsUpdateResponse]
365
- Successfully updated workflow
319
+ HttpResponse[SummaryUpdateTemplateResponse]
320
+ Template updated successfully
366
321
  """
367
322
  _response = self._client_wrapper.httpx_client.request(
368
- f"workflows/{jsonable_encoder(id)}",
323
+ f"fhir2summary/template/{jsonable_encoder(id)}",
369
324
  method="PUT",
370
- params={
371
- "verbose": verbose,
372
- },
373
325
  json={
374
326
  "name": name,
375
- "workflow_instructions": workflow_instructions,
376
- "sample_data": sample_data,
377
- "fhir_provider_id": convert_and_respect_annotation_metadata(
378
- object_=fhir_provider_id, annotation=UpdateWorkflowRequestFhirProviderId, direction="write"
379
- ),
380
- "dynamic_generation": dynamic_generation,
327
+ "description": description,
328
+ "template": template,
329
+ "target_resources": target_resources,
330
+ "mode": mode,
381
331
  },
382
332
  headers={
383
333
  "content-type": "application/json",
@@ -388,9 +338,9 @@ class RawWorkflowsClient:
388
338
  try:
389
339
  if 200 <= _response.status_code < 300:
390
340
  _data = typing.cast(
391
- WorkflowsUpdateResponse,
341
+ SummaryUpdateTemplateResponse,
392
342
  parse_obj_as(
393
- type_=WorkflowsUpdateResponse, # type: ignore
343
+ type_=SummaryUpdateTemplateResponse, # type: ignore
394
344
  object_=_response.json(),
395
345
  ),
396
346
  )
@@ -455,36 +405,36 @@ class RawWorkflowsClient:
455
405
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
456
406
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
457
407
 
458
- def delete(
408
+ def delete_template(
459
409
  self, id: str, *, request_options: typing.Optional[RequestOptions] = None
460
- ) -> HttpResponse[WorkflowsDeleteResponse]:
410
+ ) -> HttpResponse[SummaryDeleteTemplateResponse]:
461
411
  """
462
- Deletes a workflow definition by its ID
412
+ Deletes a summary template
463
413
 
464
414
  Parameters
465
415
  ----------
466
416
  id : str
467
- ID of the workflow to delete
417
+ Template ID
468
418
 
469
419
  request_options : typing.Optional[RequestOptions]
470
420
  Request-specific configuration.
471
421
 
472
422
  Returns
473
423
  -------
474
- HttpResponse[WorkflowsDeleteResponse]
475
- Successfully deleted workflow
424
+ HttpResponse[SummaryDeleteTemplateResponse]
425
+ Template deleted successfully
476
426
  """
477
427
  _response = self._client_wrapper.httpx_client.request(
478
- f"workflows/{jsonable_encoder(id)}",
428
+ f"fhir2summary/template/{jsonable_encoder(id)}",
479
429
  method="DELETE",
480
430
  request_options=request_options,
481
431
  )
482
432
  try:
483
433
  if 200 <= _response.status_code < 300:
484
434
  _data = typing.cast(
485
- WorkflowsDeleteResponse,
435
+ SummaryDeleteTemplateResponse,
486
436
  parse_obj_as(
487
- type_=WorkflowsDeleteResponse, # type: ignore
437
+ type_=SummaryDeleteTemplateResponse, # type: ignore
488
438
  object_=_response.json(),
489
439
  ),
490
440
  )
@@ -538,37 +488,49 @@ class RawWorkflowsClient:
538
488
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
539
489
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
540
490
 
541
- def execute(
491
+ def create(
542
492
  self,
543
- id: str,
544
493
  *,
545
- input_data: typing.Dict[str, typing.Optional[typing.Any]],
494
+ fhir_resources: CreateSummaryRequestFhirResources,
495
+ mode: typing.Optional[CreateSummaryRequestMode] = OMIT,
496
+ template_id: typing.Optional[str] = OMIT,
546
497
  request_options: typing.Optional[RequestOptions] = None,
547
- ) -> HttpResponse[ExecuteWorkflowResponse]:
498
+ ) -> HttpResponse[CreateSummaryResponse]:
548
499
  """
549
- Executes a workflow with provided input data and returns results
500
+ Creates a summary from FHIR resources using one of two modes:
501
+ - **narrative**: Uses a template to substitute FHIR data into placeholders (requires template_id)
502
+ - **flatten**: Flattens FHIR resources into a searchable format for RAG/search (no template needed)
550
503
 
551
504
  Parameters
552
505
  ----------
553
- id : str
554
- ID of the workflow to execute
506
+ fhir_resources : CreateSummaryRequestFhirResources
507
+ FHIR resources (single resource or Bundle)
555
508
 
556
- input_data : typing.Dict[str, typing.Optional[typing.Any]]
557
- Input data for workflow execution
509
+ mode : typing.Optional[CreateSummaryRequestMode]
510
+ Summary generation mode:
511
+ - narrative: Substitute FHIR data into a template (requires template_id)
512
+ - flatten: Flatten FHIR resources for RAG/search (no template needed)
513
+
514
+ template_id : typing.Optional[str]
515
+ ID of the template to use (required for narrative mode)
558
516
 
559
517
  request_options : typing.Optional[RequestOptions]
560
518
  Request-specific configuration.
561
519
 
562
520
  Returns
563
521
  -------
564
- HttpResponse[ExecuteWorkflowResponse]
565
- Successfully executed workflow
522
+ HttpResponse[CreateSummaryResponse]
523
+ Summary generated successfully
566
524
  """
567
525
  _response = self._client_wrapper.httpx_client.request(
568
- f"workflows/{jsonable_encoder(id)}/execute",
526
+ "fhir2summary/create",
569
527
  method="POST",
570
528
  json={
571
- "input_data": input_data,
529
+ "mode": mode,
530
+ "template_id": template_id,
531
+ "fhir_resources": convert_and_respect_annotation_metadata(
532
+ object_=fhir_resources, annotation=CreateSummaryRequestFhirResources, direction="write"
533
+ ),
572
534
  },
573
535
  headers={
574
536
  "content-type": "application/json",
@@ -579,9 +541,9 @@ class RawWorkflowsClient:
579
541
  try:
580
542
  if 200 <= _response.status_code < 300:
581
543
  _data = typing.cast(
582
- ExecuteWorkflowResponse,
544
+ CreateSummaryResponse,
583
545
  parse_obj_as(
584
- type_=ExecuteWorkflowResponse, # type: ignore
546
+ type_=CreateSummaryResponse, # type: ignore
585
547
  object_=_response.json(),
586
548
  ),
587
549
  )
@@ -647,43 +609,37 @@ class RawWorkflowsClient:
647
609
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
648
610
 
649
611
 
650
- class AsyncRawWorkflowsClient:
612
+ class AsyncRawSummaryClient:
651
613
  def __init__(self, *, client_wrapper: AsyncClientWrapper):
652
614
  self._client_wrapper = client_wrapper
653
615
 
654
- async def list(
655
- self, *, verbose: typing.Optional[bool] = None, request_options: typing.Optional[RequestOptions] = None
656
- ) -> AsyncHttpResponse[ListWorkflowsResponse]:
616
+ async def list_templates(
617
+ self, *, request_options: typing.Optional[RequestOptions] = None
618
+ ) -> AsyncHttpResponse[SummaryListTemplatesResponse]:
657
619
  """
658
- Retrieves all workflow definitions for the authenticated user
620
+ Retrieves all summary templates for the authenticated user
659
621
 
660
622
  Parameters
661
623
  ----------
662
- verbose : typing.Optional[bool]
663
- If true, includes full workflow implementation details in workflow_details field
664
-
665
624
  request_options : typing.Optional[RequestOptions]
666
625
  Request-specific configuration.
667
626
 
668
627
  Returns
669
628
  -------
670
- AsyncHttpResponse[ListWorkflowsResponse]
671
- Successfully retrieved workflows
629
+ AsyncHttpResponse[SummaryListTemplatesResponse]
630
+ Templates retrieved successfully
672
631
  """
673
632
  _response = await self._client_wrapper.httpx_client.request(
674
- "workflows",
633
+ "fhir2summary/templates",
675
634
  method="GET",
676
- params={
677
- "verbose": verbose,
678
- },
679
635
  request_options=request_options,
680
636
  )
681
637
  try:
682
638
  if 200 <= _response.status_code < 300:
683
639
  _data = typing.cast(
684
- ListWorkflowsResponse,
640
+ SummaryListTemplatesResponse,
685
641
  parse_obj_as(
686
- type_=ListWorkflowsResponse, # type: ignore
642
+ type_=SummaryListTemplatesResponse, # type: ignore
687
643
  object_=_response.json(),
688
644
  ),
689
645
  )
@@ -699,17 +655,6 @@ class AsyncRawWorkflowsClient:
699
655
  ),
700
656
  ),
701
657
  )
702
- if _response.status_code == 403:
703
- raise ForbiddenError(
704
- headers=dict(_response.headers),
705
- body=typing.cast(
706
- typing.Optional[typing.Any],
707
- parse_obj_as(
708
- type_=typing.Optional[typing.Any], # type: ignore
709
- object_=_response.json(),
710
- ),
711
- ),
712
- )
713
658
  if _response.status_code == 500:
714
659
  raise InternalServerError(
715
660
  headers=dict(_response.headers),
@@ -726,62 +671,58 @@ class AsyncRawWorkflowsClient:
726
671
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
727
672
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
728
673
 
729
- async def create(
674
+ async def create_template(
730
675
  self,
731
676
  *,
732
677
  name: str,
733
- workflow_instructions: str,
734
- sample_data: typing.Dict[str, typing.Optional[typing.Any]],
735
- fhir_provider_id: CreateWorkflowRequestFhirProviderId,
736
- verbose: typing.Optional[bool] = None,
737
- dynamic_generation: typing.Optional[bool] = OMIT,
678
+ example_summary: str,
679
+ target_resources: typing.Sequence[str],
680
+ mode: str,
681
+ description: typing.Optional[str] = OMIT,
682
+ example_fhir_data: typing.Optional[typing.Dict[str, typing.Optional[typing.Any]]] = OMIT,
738
683
  request_options: typing.Optional[RequestOptions] = None,
739
- ) -> AsyncHttpResponse[CreateWorkflowResponse]:
684
+ ) -> AsyncHttpResponse[CreateSummaryTemplateResponse]:
740
685
  """
741
- Creates a new workflow definition with graph generation from workflow instructions
686
+ Creates a summary template from an example using LLM function calling
742
687
 
743
688
  Parameters
744
689
  ----------
745
690
  name : str
746
- Human-readable name for the workflow
691
+ Name of the template
747
692
 
748
- workflow_instructions : str
749
- Natural language instructions that define the workflow logic
693
+ example_summary : str
694
+ Example summary note to generate template from
750
695
 
751
- sample_data : typing.Dict[str, typing.Optional[typing.Any]]
752
- Sample data to use for workflow graph generation
696
+ target_resources : typing.Sequence[str]
697
+ List of target FHIR resources
753
698
 
754
- fhir_provider_id : CreateWorkflowRequestFhirProviderId
755
- FHIR provider ID(s) - must be valid UUID(s) from existing FHIR providers
699
+ mode : str
700
+ Template mode (stored with the template)
756
701
 
757
- verbose : typing.Optional[bool]
758
- If true, includes full workflow implementation details in workflow_details field
702
+ description : typing.Optional[str]
703
+ Description of the template
759
704
 
760
- dynamic_generation : typing.Optional[bool]
761
- Enable dynamic lang2fhir calls instead of pre-populated templates
705
+ example_fhir_data : typing.Optional[typing.Dict[str, typing.Optional[typing.Any]]]
706
+ Optional example FHIR data that corresponds to the example summary
762
707
 
763
708
  request_options : typing.Optional[RequestOptions]
764
709
  Request-specific configuration.
765
710
 
766
711
  Returns
767
712
  -------
768
- AsyncHttpResponse[CreateWorkflowResponse]
769
- Successfully created workflow
713
+ AsyncHttpResponse[CreateSummaryTemplateResponse]
714
+ Template created successfully
770
715
  """
771
716
  _response = await self._client_wrapper.httpx_client.request(
772
- "workflows",
717
+ "fhir2summary/template",
773
718
  method="POST",
774
- params={
775
- "verbose": verbose,
776
- },
777
719
  json={
778
720
  "name": name,
779
- "workflow_instructions": workflow_instructions,
780
- "sample_data": sample_data,
781
- "fhir_provider_id": convert_and_respect_annotation_metadata(
782
- object_=fhir_provider_id, annotation=CreateWorkflowRequestFhirProviderId, direction="write"
783
- ),
784
- "dynamic_generation": dynamic_generation,
721
+ "description": description,
722
+ "example_summary": example_summary,
723
+ "target_resources": target_resources,
724
+ "example_fhir_data": example_fhir_data,
725
+ "mode": mode,
785
726
  },
786
727
  headers={
787
728
  "content-type": "application/json",
@@ -792,9 +733,9 @@ class AsyncRawWorkflowsClient:
792
733
  try:
793
734
  if 200 <= _response.status_code < 300:
794
735
  _data = typing.cast(
795
- CreateWorkflowResponse,
736
+ CreateSummaryTemplateResponse,
796
737
  parse_obj_as(
797
- type_=CreateWorkflowResponse, # type: ignore
738
+ type_=CreateSummaryTemplateResponse, # type: ignore
798
739
  object_=_response.json(),
799
740
  ),
800
741
  )
@@ -821,17 +762,6 @@ class AsyncRawWorkflowsClient:
821
762
  ),
822
763
  ),
823
764
  )
824
- if _response.status_code == 403:
825
- raise ForbiddenError(
826
- headers=dict(_response.headers),
827
- body=typing.cast(
828
- typing.Optional[typing.Any],
829
- parse_obj_as(
830
- type_=typing.Optional[typing.Any], # type: ignore
831
- object_=_response.json(),
832
- ),
833
- ),
834
- )
835
765
  if _response.status_code == 500:
836
766
  raise InternalServerError(
837
767
  headers=dict(_response.headers),
@@ -848,42 +778,36 @@ class AsyncRawWorkflowsClient:
848
778
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
849
779
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
850
780
 
851
- async def get(
852
- self, id: str, *, verbose: typing.Optional[bool] = None, request_options: typing.Optional[RequestOptions] = None
853
- ) -> AsyncHttpResponse[WorkflowsGetResponse]:
781
+ async def get_template(
782
+ self, id: str, *, request_options: typing.Optional[RequestOptions] = None
783
+ ) -> AsyncHttpResponse[SummaryGetTemplateResponse]:
854
784
  """
855
- Retrieves a workflow definition by its ID
785
+ Retrieves a specific summary template
856
786
 
857
787
  Parameters
858
788
  ----------
859
789
  id : str
860
- ID of the workflow to retrieve
861
-
862
- verbose : typing.Optional[bool]
863
- If true, includes full workflow implementation details in workflow_details field
790
+ Template ID
864
791
 
865
792
  request_options : typing.Optional[RequestOptions]
866
793
  Request-specific configuration.
867
794
 
868
795
  Returns
869
796
  -------
870
- AsyncHttpResponse[WorkflowsGetResponse]
871
- Successfully retrieved workflow
797
+ AsyncHttpResponse[SummaryGetTemplateResponse]
798
+ Template retrieved successfully
872
799
  """
873
800
  _response = await self._client_wrapper.httpx_client.request(
874
- f"workflows/{jsonable_encoder(id)}",
801
+ f"fhir2summary/template/{jsonable_encoder(id)}",
875
802
  method="GET",
876
- params={
877
- "verbose": verbose,
878
- },
879
803
  request_options=request_options,
880
804
  )
881
805
  try:
882
806
  if 200 <= _response.status_code < 300:
883
807
  _data = typing.cast(
884
- WorkflowsGetResponse,
808
+ SummaryGetTemplateResponse,
885
809
  parse_obj_as(
886
- type_=WorkflowsGetResponse, # type: ignore
810
+ type_=SummaryGetTemplateResponse, # type: ignore
887
811
  object_=_response.json(),
888
812
  ),
889
813
  )
@@ -937,66 +861,54 @@ class AsyncRawWorkflowsClient:
937
861
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
938
862
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
939
863
 
940
- async def update(
864
+ async def update_template(
941
865
  self,
942
866
  id: str,
943
867
  *,
944
868
  name: str,
945
- workflow_instructions: str,
946
- sample_data: typing.Dict[str, typing.Optional[typing.Any]],
947
- fhir_provider_id: UpdateWorkflowRequestFhirProviderId,
948
- verbose: typing.Optional[bool] = None,
949
- dynamic_generation: typing.Optional[bool] = OMIT,
869
+ template: str,
870
+ target_resources: typing.Sequence[str],
871
+ mode: str,
872
+ description: typing.Optional[str] = OMIT,
950
873
  request_options: typing.Optional[RequestOptions] = None,
951
- ) -> AsyncHttpResponse[WorkflowsUpdateResponse]:
874
+ ) -> AsyncHttpResponse[SummaryUpdateTemplateResponse]:
952
875
  """
953
- Updates an existing workflow definition
876
+ Updates an existing summary template
954
877
 
955
878
  Parameters
956
879
  ----------
957
880
  id : str
958
- ID of the workflow to update
881
+ Template ID
959
882
 
960
883
  name : str
961
- Human-readable name for the workflow
962
-
963
- workflow_instructions : str
964
- Natural language instructions that define the workflow logic
965
884
 
966
- sample_data : typing.Dict[str, typing.Optional[typing.Any]]
967
- Sample data to use for workflow graph generation
885
+ template : str
886
+ Updated template with placeholders
968
887
 
969
- fhir_provider_id : UpdateWorkflowRequestFhirProviderId
970
- FHIR provider ID(s) - must be valid UUID(s) from existing FHIR providers
888
+ target_resources : typing.Sequence[str]
971
889
 
972
- verbose : typing.Optional[bool]
973
- If true, includes full workflow implementation details in workflow_details field
890
+ mode : str
891
+ Template mode
974
892
 
975
- dynamic_generation : typing.Optional[bool]
976
- Enable dynamic lang2fhir calls instead of pre-populated templates
893
+ description : typing.Optional[str]
977
894
 
978
895
  request_options : typing.Optional[RequestOptions]
979
896
  Request-specific configuration.
980
897
 
981
898
  Returns
982
899
  -------
983
- AsyncHttpResponse[WorkflowsUpdateResponse]
984
- Successfully updated workflow
900
+ AsyncHttpResponse[SummaryUpdateTemplateResponse]
901
+ Template updated successfully
985
902
  """
986
903
  _response = await self._client_wrapper.httpx_client.request(
987
- f"workflows/{jsonable_encoder(id)}",
904
+ f"fhir2summary/template/{jsonable_encoder(id)}",
988
905
  method="PUT",
989
- params={
990
- "verbose": verbose,
991
- },
992
906
  json={
993
907
  "name": name,
994
- "workflow_instructions": workflow_instructions,
995
- "sample_data": sample_data,
996
- "fhir_provider_id": convert_and_respect_annotation_metadata(
997
- object_=fhir_provider_id, annotation=UpdateWorkflowRequestFhirProviderId, direction="write"
998
- ),
999
- "dynamic_generation": dynamic_generation,
908
+ "description": description,
909
+ "template": template,
910
+ "target_resources": target_resources,
911
+ "mode": mode,
1000
912
  },
1001
913
  headers={
1002
914
  "content-type": "application/json",
@@ -1007,9 +919,9 @@ class AsyncRawWorkflowsClient:
1007
919
  try:
1008
920
  if 200 <= _response.status_code < 300:
1009
921
  _data = typing.cast(
1010
- WorkflowsUpdateResponse,
922
+ SummaryUpdateTemplateResponse,
1011
923
  parse_obj_as(
1012
- type_=WorkflowsUpdateResponse, # type: ignore
924
+ type_=SummaryUpdateTemplateResponse, # type: ignore
1013
925
  object_=_response.json(),
1014
926
  ),
1015
927
  )
@@ -1074,36 +986,36 @@ class AsyncRawWorkflowsClient:
1074
986
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
1075
987
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
1076
988
 
1077
- async def delete(
989
+ async def delete_template(
1078
990
  self, id: str, *, request_options: typing.Optional[RequestOptions] = None
1079
- ) -> AsyncHttpResponse[WorkflowsDeleteResponse]:
991
+ ) -> AsyncHttpResponse[SummaryDeleteTemplateResponse]:
1080
992
  """
1081
- Deletes a workflow definition by its ID
993
+ Deletes a summary template
1082
994
 
1083
995
  Parameters
1084
996
  ----------
1085
997
  id : str
1086
- ID of the workflow to delete
998
+ Template ID
1087
999
 
1088
1000
  request_options : typing.Optional[RequestOptions]
1089
1001
  Request-specific configuration.
1090
1002
 
1091
1003
  Returns
1092
1004
  -------
1093
- AsyncHttpResponse[WorkflowsDeleteResponse]
1094
- Successfully deleted workflow
1005
+ AsyncHttpResponse[SummaryDeleteTemplateResponse]
1006
+ Template deleted successfully
1095
1007
  """
1096
1008
  _response = await self._client_wrapper.httpx_client.request(
1097
- f"workflows/{jsonable_encoder(id)}",
1009
+ f"fhir2summary/template/{jsonable_encoder(id)}",
1098
1010
  method="DELETE",
1099
1011
  request_options=request_options,
1100
1012
  )
1101
1013
  try:
1102
1014
  if 200 <= _response.status_code < 300:
1103
1015
  _data = typing.cast(
1104
- WorkflowsDeleteResponse,
1016
+ SummaryDeleteTemplateResponse,
1105
1017
  parse_obj_as(
1106
- type_=WorkflowsDeleteResponse, # type: ignore
1018
+ type_=SummaryDeleteTemplateResponse, # type: ignore
1107
1019
  object_=_response.json(),
1108
1020
  ),
1109
1021
  )
@@ -1157,37 +1069,49 @@ class AsyncRawWorkflowsClient:
1157
1069
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response.text)
1158
1070
  raise ApiError(status_code=_response.status_code, headers=dict(_response.headers), body=_response_json)
1159
1071
 
1160
- async def execute(
1072
+ async def create(
1161
1073
  self,
1162
- id: str,
1163
1074
  *,
1164
- input_data: typing.Dict[str, typing.Optional[typing.Any]],
1075
+ fhir_resources: CreateSummaryRequestFhirResources,
1076
+ mode: typing.Optional[CreateSummaryRequestMode] = OMIT,
1077
+ template_id: typing.Optional[str] = OMIT,
1165
1078
  request_options: typing.Optional[RequestOptions] = None,
1166
- ) -> AsyncHttpResponse[ExecuteWorkflowResponse]:
1079
+ ) -> AsyncHttpResponse[CreateSummaryResponse]:
1167
1080
  """
1168
- Executes a workflow with provided input data and returns results
1081
+ Creates a summary from FHIR resources using one of two modes:
1082
+ - **narrative**: Uses a template to substitute FHIR data into placeholders (requires template_id)
1083
+ - **flatten**: Flattens FHIR resources into a searchable format for RAG/search (no template needed)
1169
1084
 
1170
1085
  Parameters
1171
1086
  ----------
1172
- id : str
1173
- ID of the workflow to execute
1087
+ fhir_resources : CreateSummaryRequestFhirResources
1088
+ FHIR resources (single resource or Bundle)
1174
1089
 
1175
- input_data : typing.Dict[str, typing.Optional[typing.Any]]
1176
- Input data for workflow execution
1090
+ mode : typing.Optional[CreateSummaryRequestMode]
1091
+ Summary generation mode:
1092
+ - narrative: Substitute FHIR data into a template (requires template_id)
1093
+ - flatten: Flatten FHIR resources for RAG/search (no template needed)
1094
+
1095
+ template_id : typing.Optional[str]
1096
+ ID of the template to use (required for narrative mode)
1177
1097
 
1178
1098
  request_options : typing.Optional[RequestOptions]
1179
1099
  Request-specific configuration.
1180
1100
 
1181
1101
  Returns
1182
1102
  -------
1183
- AsyncHttpResponse[ExecuteWorkflowResponse]
1184
- Successfully executed workflow
1103
+ AsyncHttpResponse[CreateSummaryResponse]
1104
+ Summary generated successfully
1185
1105
  """
1186
1106
  _response = await self._client_wrapper.httpx_client.request(
1187
- f"workflows/{jsonable_encoder(id)}/execute",
1107
+ "fhir2summary/create",
1188
1108
  method="POST",
1189
1109
  json={
1190
- "input_data": input_data,
1110
+ "mode": mode,
1111
+ "template_id": template_id,
1112
+ "fhir_resources": convert_and_respect_annotation_metadata(
1113
+ object_=fhir_resources, annotation=CreateSummaryRequestFhirResources, direction="write"
1114
+ ),
1191
1115
  },
1192
1116
  headers={
1193
1117
  "content-type": "application/json",
@@ -1198,9 +1122,9 @@ class AsyncRawWorkflowsClient:
1198
1122
  try:
1199
1123
  if 200 <= _response.status_code < 300:
1200
1124
  _data = typing.cast(
1201
- ExecuteWorkflowResponse,
1125
+ CreateSummaryResponse,
1202
1126
  parse_obj_as(
1203
- type_=ExecuteWorkflowResponse, # type: ignore
1127
+ type_=CreateSummaryResponse, # type: ignore
1204
1128
  object_=_response.json(),
1205
1129
  ),
1206
1130
  )