@medplum/react-hooks 5.1.6 → 5.1.7

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.
@@ -1,11 +1,17 @@
1
+ import type { AddFavoriteParams } from '@medplum/core';
2
+ import type { AddPharmacyResponse } from '@medplum/core';
1
3
  import type { Bundle } from '@medplum/fhirtypes';
2
4
  import type { Communication } from '@medplum/fhirtypes';
3
5
  import { Context } from 'react';
4
6
  import type { Encounter } from '@medplum/fhirtypes';
5
7
  import type { ExtractResource } from '@medplum/fhirtypes';
8
+ import type { Identifier } from '@medplum/fhirtypes';
6
9
  import type { JSX } from 'react';
7
10
  import type { MedplumClient } from '@medplum/core';
8
11
  import type { OperationOutcome } from '@medplum/fhirtypes';
12
+ import type { Organization } from '@medplum/fhirtypes';
13
+ import type { Patient } from '@medplum/fhirtypes';
14
+ import type { PharmacySearchParams } from '@medplum/core';
9
15
  import type { ProfileResource } from '@medplum/core';
10
16
  import type { QueryTypes } from '@medplum/core';
11
17
  import type { Questionnaire } from '@medplum/fhirtypes';
@@ -30,6 +36,13 @@ export declare function buildInitialResponse(questionnaire: Questionnaire, quest
30
36
 
31
37
  export declare function buildInitialResponseItem(item: QuestionnaireItem): QuestionnaireResponseItem;
32
38
 
39
+ export declare interface EPrescribingIFrameOptions {
40
+ readonly patientId?: string;
41
+ readonly onPatientSyncSuccess?: () => void;
42
+ readonly onIframeSuccess?: (url: string) => void;
43
+ readonly onError?: (err: unknown) => void;
44
+ }
45
+
33
46
  /**
34
47
  * Evaluates the calculated expressions in a questionnaire.
35
48
  * Updates response item answers in place with the calculated values.
@@ -42,6 +55,20 @@ export declare function buildInitialResponseItem(item: QuestionnaireItem): Quest
42
55
  */
43
56
  export declare function evaluateCalculatedExpressionsInQuestionnaire(items: QuestionnaireItem[], response: QuestionnaireResponse, responseItems?: QuestionnaireResponseItem[] | undefined): void;
44
57
 
58
+ /** Descriptor for a single FHIR search that a section needs. */
59
+ export declare interface FhirSearchDescriptor {
60
+ /** Unique key used to access this search's results via `SectionResults[key]`. */
61
+ readonly key: string;
62
+ readonly resourceType: ResourceType;
63
+ /** Which search param references the patient. Defaults to 'subject'. Examples: 'patient', 'beneficiary'. */
64
+ readonly patientParam?: string;
65
+ /**
66
+ * Additional search params — same format as the 2nd arg to medplum.searchResources().
67
+ * When using a string, do not include _count or _sort; they are appended automatically.
68
+ */
69
+ readonly query?: QueryTypes;
70
+ }
71
+
45
72
  export declare function getItemAnswerOptionValue(option: QuestionnaireItemAnswerOption): TypedValue;
46
73
 
47
74
  export declare function getItemEnableWhenValueAnswer(enableWhen: QuestionnaireItemEnableWhen): TypedValue;
@@ -105,6 +132,13 @@ export declare interface MedplumProviderProps {
105
132
  readonly children: ReactNode;
106
133
  }
107
134
 
135
+ export declare interface PatientSummaryData {
136
+ /** One SectionResults map per section, indexed to match the sections array. */
137
+ readonly sectionData: SectionResults[];
138
+ readonly loading: boolean;
139
+ readonly error: Error | undefined;
140
+ }
141
+
108
142
  export declare const QUESTIONNAIRE_CALCULATED_EXPRESSION_URL = "http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-calculatedExpression";
109
143
 
110
144
  export declare const QUESTIONNAIRE_ENABLED_WHEN_EXPRESSION_URL = "http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-enableWhenExpression";
@@ -217,14 +251,35 @@ export declare const reactContext: Context<MedplumContext | undefined>;
217
251
 
218
252
  export declare type SearchOptions = {
219
253
  debounceMs?: number;
254
+ enabled?: boolean;
220
255
  };
221
256
 
257
+ /** Named map of FHIR results for a section: `results[searchKey]` returns the Resource[] for that search. */
258
+ export declare type SectionResults = Record<string, Resource[]>;
259
+
222
260
  export declare function setQuestionnaireItemReferenceTargetTypes(item: QuestionnaireItem, targetTypes: ResourceType[] | undefined): QuestionnaireItem;
223
261
 
224
262
  export declare function typedValueToResponseItem(item: QuestionnaireItem, value: TypedValue): QuestionnaireResponseItemAnswer | undefined;
225
263
 
226
264
  export declare const useCachedBinaryUrl: (binaryUrl: string | undefined) => string | undefined;
227
265
 
266
+ /**
267
+ * Generic React hook that syncs a patient to an e-prescribing system and
268
+ * returns the iframe URL.
269
+ *
270
+ * Executes the patient-sync bot first (if patientId is provided), then
271
+ * the iframe bot to obtain the prescribing UI URL.
272
+ *
273
+ * Uses an effect cleanup flag so React 18 Strict Mode double-mount does not
274
+ * trigger duplicate bot executions.
275
+ *
276
+ * @param syncBotIdentifier - Bot identifier for the patient sync bot.
277
+ * @param iframeBotIdentifier - Bot identifier for the iframe URL bot.
278
+ * @param options - Configuration and callback options.
279
+ * @returns The e-prescribing iframe URL, or undefined while loading.
280
+ */
281
+ export declare function useEPrescribingIFrame(syncBotIdentifier: Identifier, iframeBotIdentifier: Identifier, options: EPrescribingIFrameOptions): string | undefined;
282
+
228
283
  /**
229
284
  * Returns the MedplumClient instance.
230
285
  * This is a shortcut for useMedplumContext().medplum.
@@ -269,6 +324,38 @@ export declare interface UseNotificationCountOptions {
269
324
  readonly subscriptionCriteria: string;
270
325
  }
271
326
 
327
+ /**
328
+ * Hook that collects all FHIR searches from section configs, deduplicates them,
329
+ * executes them in parallel, and routes results back to each section.
330
+ * Uses Promise.allSettled so a single failing search does not block all sections —
331
+ * sections whose searches fail gracefully receive empty arrays.
332
+ * @param patient - The patient or patient reference to fetch data for.
333
+ * @param sections - The section configs defining which searches to execute.
334
+ * @returns Section data, loading state, and any error.
335
+ */
336
+ export declare function usePatientSummaryData(patient: Patient | Reference<Patient>, sections: {
337
+ readonly key: string;
338
+ readonly searches?: FhirSearchDescriptor[];
339
+ }[]): PatientSummaryData;
340
+
341
+ /**
342
+ * Generic React hook that provides pharmacy search and add-to-favorites
343
+ * functionality for any e-prescribing integration.
344
+ *
345
+ * Encapsulates calls to a search-pharmacy bot and an add-patient-pharmacy bot,
346
+ * and can be composed with the generic `PharmacyDialog` component from `@medplum/react`.
347
+ *
348
+ * @param searchBotIdentifier - Bot identifier for the pharmacy search bot.
349
+ * @param addPharmacyBotIdentifier - Bot identifier for the add-patient-pharmacy bot.
350
+ * @returns An object with `searchPharmacies` and `addToFavorites` callbacks.
351
+ */
352
+ export declare function usePharmacySearch(searchBotIdentifier: Identifier, addPharmacyBotIdentifier: Identifier): UsePharmacySearchReturn;
353
+
354
+ export declare interface UsePharmacySearchReturn {
355
+ searchPharmacies: (params: PharmacySearchParams) => Promise<Organization[]>;
356
+ addToFavorites: (params: AddFavoriteParams) => Promise<AddPharmacyResponse>;
357
+ }
358
+
272
359
  /**
273
360
  * React Hook to keep track of the passed-in value from the previous render of the containing component.
274
361
  * @param value - The value to track.
@@ -1,11 +1,17 @@
1
+ import type { AddFavoriteParams } from '@medplum/core';
2
+ import type { AddPharmacyResponse } from '@medplum/core';
1
3
  import type { Bundle } from '@medplum/fhirtypes';
2
4
  import type { Communication } from '@medplum/fhirtypes';
3
5
  import { Context } from 'react';
4
6
  import type { Encounter } from '@medplum/fhirtypes';
5
7
  import type { ExtractResource } from '@medplum/fhirtypes';
8
+ import type { Identifier } from '@medplum/fhirtypes';
6
9
  import type { JSX } from 'react';
7
10
  import type { MedplumClient } from '@medplum/core';
8
11
  import type { OperationOutcome } from '@medplum/fhirtypes';
12
+ import type { Organization } from '@medplum/fhirtypes';
13
+ import type { Patient } from '@medplum/fhirtypes';
14
+ import type { PharmacySearchParams } from '@medplum/core';
9
15
  import type { ProfileResource } from '@medplum/core';
10
16
  import type { QueryTypes } from '@medplum/core';
11
17
  import type { Questionnaire } from '@medplum/fhirtypes';
@@ -30,6 +36,13 @@ export declare function buildInitialResponse(questionnaire: Questionnaire, quest
30
36
 
31
37
  export declare function buildInitialResponseItem(item: QuestionnaireItem): QuestionnaireResponseItem;
32
38
 
39
+ export declare interface EPrescribingIFrameOptions {
40
+ readonly patientId?: string;
41
+ readonly onPatientSyncSuccess?: () => void;
42
+ readonly onIframeSuccess?: (url: string) => void;
43
+ readonly onError?: (err: unknown) => void;
44
+ }
45
+
33
46
  /**
34
47
  * Evaluates the calculated expressions in a questionnaire.
35
48
  * Updates response item answers in place with the calculated values.
@@ -42,6 +55,20 @@ export declare function buildInitialResponseItem(item: QuestionnaireItem): Quest
42
55
  */
43
56
  export declare function evaluateCalculatedExpressionsInQuestionnaire(items: QuestionnaireItem[], response: QuestionnaireResponse, responseItems?: QuestionnaireResponseItem[] | undefined): void;
44
57
 
58
+ /** Descriptor for a single FHIR search that a section needs. */
59
+ export declare interface FhirSearchDescriptor {
60
+ /** Unique key used to access this search's results via `SectionResults[key]`. */
61
+ readonly key: string;
62
+ readonly resourceType: ResourceType;
63
+ /** Which search param references the patient. Defaults to 'subject'. Examples: 'patient', 'beneficiary'. */
64
+ readonly patientParam?: string;
65
+ /**
66
+ * Additional search params — same format as the 2nd arg to medplum.searchResources().
67
+ * When using a string, do not include _count or _sort; they are appended automatically.
68
+ */
69
+ readonly query?: QueryTypes;
70
+ }
71
+
45
72
  export declare function getItemAnswerOptionValue(option: QuestionnaireItemAnswerOption): TypedValue;
46
73
 
47
74
  export declare function getItemEnableWhenValueAnswer(enableWhen: QuestionnaireItemEnableWhen): TypedValue;
@@ -105,6 +132,13 @@ export declare interface MedplumProviderProps {
105
132
  readonly children: ReactNode;
106
133
  }
107
134
 
135
+ export declare interface PatientSummaryData {
136
+ /** One SectionResults map per section, indexed to match the sections array. */
137
+ readonly sectionData: SectionResults[];
138
+ readonly loading: boolean;
139
+ readonly error: Error | undefined;
140
+ }
141
+
108
142
  export declare const QUESTIONNAIRE_CALCULATED_EXPRESSION_URL = "http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-calculatedExpression";
109
143
 
110
144
  export declare const QUESTIONNAIRE_ENABLED_WHEN_EXPRESSION_URL = "http://hl7.org/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-enableWhenExpression";
@@ -217,14 +251,35 @@ export declare const reactContext: Context<MedplumContext | undefined>;
217
251
 
218
252
  export declare type SearchOptions = {
219
253
  debounceMs?: number;
254
+ enabled?: boolean;
220
255
  };
221
256
 
257
+ /** Named map of FHIR results for a section: `results[searchKey]` returns the Resource[] for that search. */
258
+ export declare type SectionResults = Record<string, Resource[]>;
259
+
222
260
  export declare function setQuestionnaireItemReferenceTargetTypes(item: QuestionnaireItem, targetTypes: ResourceType[] | undefined): QuestionnaireItem;
223
261
 
224
262
  export declare function typedValueToResponseItem(item: QuestionnaireItem, value: TypedValue): QuestionnaireResponseItemAnswer | undefined;
225
263
 
226
264
  export declare const useCachedBinaryUrl: (binaryUrl: string | undefined) => string | undefined;
227
265
 
266
+ /**
267
+ * Generic React hook that syncs a patient to an e-prescribing system and
268
+ * returns the iframe URL.
269
+ *
270
+ * Executes the patient-sync bot first (if patientId is provided), then
271
+ * the iframe bot to obtain the prescribing UI URL.
272
+ *
273
+ * Uses an effect cleanup flag so React 18 Strict Mode double-mount does not
274
+ * trigger duplicate bot executions.
275
+ *
276
+ * @param syncBotIdentifier - Bot identifier for the patient sync bot.
277
+ * @param iframeBotIdentifier - Bot identifier for the iframe URL bot.
278
+ * @param options - Configuration and callback options.
279
+ * @returns The e-prescribing iframe URL, or undefined while loading.
280
+ */
281
+ export declare function useEPrescribingIFrame(syncBotIdentifier: Identifier, iframeBotIdentifier: Identifier, options: EPrescribingIFrameOptions): string | undefined;
282
+
228
283
  /**
229
284
  * Returns the MedplumClient instance.
230
285
  * This is a shortcut for useMedplumContext().medplum.
@@ -269,6 +324,38 @@ export declare interface UseNotificationCountOptions {
269
324
  readonly subscriptionCriteria: string;
270
325
  }
271
326
 
327
+ /**
328
+ * Hook that collects all FHIR searches from section configs, deduplicates them,
329
+ * executes them in parallel, and routes results back to each section.
330
+ * Uses Promise.allSettled so a single failing search does not block all sections —
331
+ * sections whose searches fail gracefully receive empty arrays.
332
+ * @param patient - The patient or patient reference to fetch data for.
333
+ * @param sections - The section configs defining which searches to execute.
334
+ * @returns Section data, loading state, and any error.
335
+ */
336
+ export declare function usePatientSummaryData(patient: Patient | Reference<Patient>, sections: {
337
+ readonly key: string;
338
+ readonly searches?: FhirSearchDescriptor[];
339
+ }[]): PatientSummaryData;
340
+
341
+ /**
342
+ * Generic React hook that provides pharmacy search and add-to-favorites
343
+ * functionality for any e-prescribing integration.
344
+ *
345
+ * Encapsulates calls to a search-pharmacy bot and an add-patient-pharmacy bot,
346
+ * and can be composed with the generic `PharmacyDialog` component from `@medplum/react`.
347
+ *
348
+ * @param searchBotIdentifier - Bot identifier for the pharmacy search bot.
349
+ * @param addPharmacyBotIdentifier - Bot identifier for the add-patient-pharmacy bot.
350
+ * @returns An object with `searchPharmacies` and `addToFavorites` callbacks.
351
+ */
352
+ export declare function usePharmacySearch(searchBotIdentifier: Identifier, addPharmacyBotIdentifier: Identifier): UsePharmacySearchReturn;
353
+
354
+ export declare interface UsePharmacySearchReturn {
355
+ searchPharmacies: (params: PharmacySearchParams) => Promise<Organization[]>;
356
+ addToFavorites: (params: AddFavoriteParams) => Promise<AddPharmacyResponse>;
357
+ }
358
+
272
359
  /**
273
360
  * React Hook to keep track of the passed-in value from the previous render of the containing component.
274
361
  * @param value - The value to track.
@@ -1,8 +1,8 @@
1
- import{useEffect as he,useMemo as ye,useState as xe}from"react";import{createContext as ge,useContext as Ie}from"react";var V=ge(void 0);function F(){return Ie(V)}function S(){return F().medplum}function Qn(){return F().navigate}function En(){return F().profile}import{jsx as Ee}from"react/jsx-runtime";var X=["change","storageInitialized","storageInitFailed","profileRefreshing","profileRefreshed"];function Tn(e){let t=e.medplum,n=e.navigate??Qe,[o,r]=xe({profile:t.getProfile(),loading:t.isLoading()});he(()=>{function s(){r(a=>({...a,profile:t.getProfile(),loading:t.isLoading()}))}for(let a of X)t.addEventListener(a,s);return()=>{for(let a of X)t.removeEventListener(a,s)}},[t]);let i=ye(()=>({...o,medplum:t,navigate:n}),[o,t,n]);return Ee(V.Provider,{value:i,children:e.children})}function Qe(e){window.location.assign(e)}import{useMemo as Se}from"react";var J=new Map,wn=e=>Se(()=>{if(!e)return;let t=e.split("?")[0];if(!t)return e;let n;try{n=new URLSearchParams(new URL(e).search)}catch{return e}if(!n.has("Key-Pair-Id")||!n.has("Signature"))return e;let o=n.get("Expires");if(!o||o.length>13)return e;let r=J.get(t);if(r){let s=new URLSearchParams(new URL(r).search).get("Expires");if(s&&Number.parseInt(s,10)*1e3-5e3>Date.now())return r}return J.set(t,e),e},[e]);import{useCallback as ve,useEffect as Te,useState as Ce}from"react";import{deepEquals as Y}from"@medplum/core";import{useCallback as O,useEffect as q,useRef as b,useState as Z}from"react";var be=3e3;function ee(e,t,n){let o=S(),[r,i]=Z(),[s,a]=Z(n?.subscriptionProps),c=b(!1),R=b(void 0),I=b(void 0),v=b(void 0),C=b(t);C.current=t;let g=b(n?.onWebSocketOpen);g.current=n?.onWebSocketOpen;let p=b(n?.onWebSocketClose);p.current=n?.onWebSocketClose;let d=b(n?.onSubscriptionConnect);d.current=n?.onSubscriptionConnect;let u=b(n?.onSubscriptionDisconnect);u.current=n?.onSubscriptionDisconnect;let l=b(n?.onError);l.current=n?.onError,q(()=>{Y(n?.subscriptionProps,s)||a(n?.subscriptionProps)},[s,n]),q(()=>{R.current&&(clearTimeout(R.current),R.current=void 0);let x=!1;return(I.current!==e||!Y(v.current,s))&&(x=!0),x&&I.current&&o.unsubscribeFromCriteria(I.current,v.current),I.current=e,v.current=s,x&&e?i(o.subscribeToCriteria(e,s)):e||i(void 0),()=>{R.current=setTimeout(()=>{i(void 0),e&&o.unsubscribeFromCriteria(e,s)},be)}},[o,e,s]);let f=O(x=>{C.current?.(x.payload)},[]),Q=O(()=>{g.current?.()},[]),E=O(()=>{p.current?.()},[]),P=O(x=>{d.current?.(x.payload.subscriptionId)},[]),A=O(x=>{u.current?.(x.payload.subscriptionId)},[]),h=O(x=>{l.current?.(x.payload)},[]);q(()=>r?(c.current||(r.addEventListener("message",f),r.addEventListener("open",Q),r.addEventListener("close",E),r.addEventListener("connect",P),r.addEventListener("disconnect",A),r.addEventListener("error",h),c.current=!0),()=>{c.current=!1,r.removeEventListener("message",f),r.removeEventListener("open",Q),r.removeEventListener("close",E),r.removeEventListener("connect",P),r.removeEventListener("disconnect",A),r.removeEventListener("error",h)}):()=>{},[r,f,Q,E,P,A,h])}function qn(e){let t=S(),{resourceType:n,countCriteria:o,subscriptionCriteria:r}=e,[i,s]=Ce(0),a=ve(c=>{t.search(n,o,{cache:c}).then(R=>s(R.total)).catch(console.error)},[t,n,o]);return Te(()=>{a("default")},[a]),ee(r,()=>{a("reload")}),i}import{useEffect as Pe,useRef as Oe}from"react";function Dn(e){let t=Oe(void 0);return Pe(()=>{t.current=e}),t.current}import{getExtension as on}from"@medplum/core";import{useReducer as sn,useRef as un}from"react";import{deepEquals as we,isReference as te,isResource as Ae,normalizeOperationOutcome as Me}from"@medplum/core";import{useCallback as Ne,useEffect as Le,useState as Ue}from"react";function k(e,t){let n=S(),[o,r]=Ue(()=>ne(n,e)),i=Ne(s=>{we(s,o)||r(s)},[o]);return Le(()=>{let s=!0,a=ne(n,e);return!a&&te(e)?n.readReference(e).then(c=>{s&&i(c)}).catch(c=>{s&&(i(void 0),t&&t(Me(c)))}):i(a),(()=>s=!1)},[n,e,i,t]),o}function ne(e,t){if(t){if(Ae(t))return t;if(te(t))return e.getCachedReference(t)}}import{EMPTY as se,HTTP_HL7_ORG as T,PropertyType as y,append as re,capitalize as oe,deepClone as _e,evalFhirPathTyped as D,getExtension as w,getReferenceString as Ve,getTypedPropertyValueWithoutSchema as L,normalizeErrorString as Fe,splitN as qe,toJsBoolean as ke,toTypedValue as ue,typedValueToString as We}from"@medplum/core";var m={group:"group",display:"display",question:"question",boolean:"boolean",decimal:"decimal",integer:"integer",date:"date",dateTime:"dateTime",time:"time",string:"string",text:"text",url:"url",choice:"choice",openChoice:"open-choice",attachment:"attachment",reference:"reference",quantity:"quantity"},ae=`${T}/fhir/StructureDefinition/questionnaire-itemControl`,De=`${T}/fhir/StructureDefinition/questionnaire-referenceFilter`,W=`${T}/fhir/StructureDefinition/questionnaire-referenceResource`,$e=`${T}/fhir/StructureDefinition/questionnaire-validationError`,Ke=`${T}/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-enableWhenExpression`,Be=`${T}/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-calculatedExpression`,Hn=`${T}/fhir/StructureDefinition/questionnaire-signatureRequired`,U=`${T}/fhir/StructureDefinition/questionnaireresponse-signature`,ze=`${T}/fhir/StructureDefinition/questionnaire-hidden`;function Xn(e){return e.type==="choice"||e.type==="open-choice"}function Jn(e,t){if(w(e,ze)?.valueBoolean===!0)return!1;let o=Ge(e,t);return o!==void 0?o:je(e,t)}function Ge(e,t){let n=w(e,Ke);if(t&&n){let o=n.valueExpression?.expression;if(o){let r=ue(t),i=D(o,[r],{"%resource":r});return ke(i)}}}function je(e,t){if(!e.enableWhen)return!0;let n=e.enableBehavior??"any";for(let o of e.enableWhen){let r=ce(t?.item,o.question);if(o.operator==="exists"&&!o.answerBoolean&&!r?.length){if(n==="any")return!0;continue}let{anyMatch:i,allMatch:s}=en(o,r,n);if(n==="any"&&i)return!0;if(n==="all"&&!s)return!1}return n!=="any"}function $(e,t,n=t.item){for(let o of e){let r=n?.find(i=>i.linkId===o.linkId);r&&(He(t,o,r),o.item&&r.item&&$(o.item,t,r.item))}}function He(e,t,n){try{let o=Ye(t,e);if(!o)return;let r=Je(t,o);if(!r)return;n.answer=[r]}catch(o){n.extension=[{url:$e,valueString:`Expression evaluation failed: ${Fe(o)}`}]}}var Xe={[m.boolean]:[y.boolean],[m.date]:[y.date],[m.dateTime]:[y.dateTime],[m.time]:[y.time],[m.url]:[y.string,y.uri,y.url],[m.attachment]:[y.Attachment],[m.reference]:[y.Reference],[m.quantity]:[y.Quantity],[m.decimal]:[y.decimal,y.integer],[m.integer]:[y.decimal,y.integer]};function Je(e,t){if(!e.type)return;if(e.type===m.choice||e.type===m.openChoice)return{[`value${oe(t.type)}`]:t.value};if(e.type===m.string||e.type===m.text)return typeof t.value=="string"?{valueString:t.value}:void 0;if(Xe[e.type]?.includes(t.type))return{[`value${oe(e.type)}`]:t.value}}function Ye(e,t){if(!t)return;let n=w(e,Be);if(n){let o=n.valueExpression?.expression;if(o){let r=ue(t),i=D(o,[r],{"%resource":r});return i.length!==0?i[0]:void 0}}}function Yn(e,t,n){let o=[];for(let r of e){let i=n.answerOption?.find(s=>We(ie(s))===r);if(i){let s=ie(i);s&&o.push({[t]:s.value})}}return o}function ce(e,t){for(let n of e??se){if(n.linkId===t)return n.answer;if(n.item){let o=ce(n.item,t);if(o)return o}}}function Ze(e,t,n){if(n==="exists")return!!e===t.value;if(e){let o=n==="="||n==="!="?n?.replace("=","~"):n,[{value:r}]=D(`%actualAnswer ${o} %expectedAnswer`,[e],{"%actualAnswer":e,"%expectedAnswer":t});return r}else return!1}function en(e,t,n){let o=t||[],r=tn(e),i=!1,s=!0;for(let a of o){let c=rn(a),{operator:R}=e;if(Ze(c,r,R)?i=!0:s=!1,n==="any"&&i)break}return{anyMatch:i,allMatch:s}}function Zn(e){let t=w(e,W);if(t){if(t.valueCode!==void 0)return[t.valueCode];if(t.valueCodeableConcept)return t.valueCodeableConcept?.coding?.map(n=>n.code)}}function et(e,t){let n=_e(e),o=w(n,W);return!t||t.length===0?(o&&(n.extension=n.extension?.filter(r=>r!==o)),n):(o||(n.extension??=[],o={url:W},n.extension.push(o)),t.length===1?(o.valueCode=t[0],delete o.valueCodeableConcept):(o.valueCodeableConcept={coding:t.map(r=>({code:r}))},delete o.valueCode),n)}function nt(e,t,n){let o=w(e,De);if(!o?.valueString)return;let r=o.valueString;t?.reference&&(r=r.replaceAll("$subj",t.reference)),n?.reference&&(r=r.replaceAll("$encounter",n.reference));let i={},s=r.split("&");for(let a of s){let[c,R]=qe(a,"=",2);i[c]=R}return i}function K(e,t){return{resourceType:"QuestionnaireResponse",questionnaire:e.url??Ve(e),item:B(e.item,t?.item),status:"in-progress"}}function B(e,t){let n;for(let o of e??se){if(o.type===m.display)continue;let r=t?.filter(i=>i.linkId===o.linkId);if(r?.length)for(let i of r)i.id=i.id??de(),i.text=i.text??o.text,i.item=B(o.item,i.item),i.answer=pe(o,i),n=re(n,i);else n=re(n,z(o))}return n}function z(e){return{id:de(),linkId:e.linkId,text:e.text,item:B(e.item,void 0),answer:pe(e)}}var nn=1;function de(){return"id-"+nn++}function pe(e,t){if(!(e.type===m.display||e.type===m.group)){if(t?.answer&&t.answer.length>0)return t.answer;if(e.initial&&e.initial.length>0)return e.initial.map(n=>({...n}));if(e.answerOption)return e.answerOption.filter(n=>n.initialSelected).map(n=>({...n,initialSelected:void 0}))}}function tt(e){return L({type:"QuestionnaireItemInitial",value:e},"value")}function ie(e){return L({type:"QuestionnaireItemAnswerOption",value:e},"value")}function tn(e){return L({type:"QuestionnaireItemEnableWhen",value:e},"answer")}function rn(e){return L({type:"QuestionnaireResponseItemAnswer",value:e},"value")}function at(e){let t=k(e.questionnaire),n=k(e.defaultValue),[,o]=sn(p=>p+1,0),r=un({activePage:0});if(!r.current.questionnaire&&t&&(r.current.questionnaire=t,r.current.pages=e.disablePagination?void 0:an(t)),t&&e.defaultValue&&n&&!r.current.questionnaireResponse&&(r.current.questionnaireResponse=K(t,n),g()),t&&!e.defaultValue&&!r.current.questionnaireResponse&&(r.current.questionnaireResponse=K(t),g()),!r.current.questionnaire||!r.current.questionnaireResponse)return{loading:!0};function i(p,d){let u=r.current.questionnaireResponse;for(let l of p)u=u?.item?.find(f=>l.id?f.id===l.id:f.linkId===l.linkId);return d&&(u=u?.item?.find(l=>l.linkId===d.linkId)),u}function s(){r.current.activePage=(r.current.activePage??0)+1,o()}function a(){r.current.activePage=(r.current.activePage??0)-1,o()}function c(p,d){let u=i(p);u&&(u.item??=[],u.item.push(z(d)),g())}function R(p,d){let u=i(p,d);u&&(u.answer??=[],u.answer.push({}),g())}function I(p,d,u){let l=i(p,d);l&&(l.answer=u,g())}function v(p){let d=r.current.questionnaireResponse;d&&(p?(d.extension=d.extension??[],d.extension=d.extension.filter(u=>u.url!==U),d.extension.push({url:U,valueSignature:p})):d.extension=d.extension?.filter(u=>u.url!==U),g())}function C(){let p=r.current.questionnaire;if(p?.item){let d=r.current.questionnaireResponse;$(p.item,d)}}function g(){let p=r.current.questionnaireResponse;p&&(C(),o(),e.onChange?.(p))}return{loading:!1,pagination:!!r.current.pages,questionnaire:r.current.questionnaire,questionnaireResponse:r.current.questionnaireResponse,subject:e.subject,encounter:e.encounter,activePage:r.current.activePage,pages:r.current.pages,items:cn(r.current.questionnaire,r.current.pages,r.current.activePage),responseItems:dn(r.current.questionnaireResponse,r.current.pages,r.current.activePage),onNextPage:s,onPrevPage:a,onAddGroup:c,onAddAnswer:R,onChangeAnswer:I,onChangeSignature:v}}function an(e){if(!(!e?.item||on(e?.item?.[0],ae)?.valueCodeableConcept?.coding?.[0]?.code!=="page"))return e.item.map((n,o)=>({linkId:n.linkId,title:n.text??`Page ${o+1}`,group:n}))}function cn(e,t,n=0){return t&&e?.item?.[n]?[e.item[n]]:e.item??[]}function dn(e,t,n=0){return t&&e?.item?.[n]?[e.item[n]]:e.item??[]}import{allOk as ln,normalizeOperationOutcome as mn}from"@medplum/core";import{useEffect as Rn,useMemo as gn,useState as j}from"react";import{useCallback as pn,useEffect as fe,useRef as G,useState as fn}from"react";function le(e,t,n={leading:!1}){let[o,r]=fn(e),i=G(!1),s=G(void 0),a=G(!1),c=pn(()=>window.clearTimeout(s.current),[]);return fe(()=>{i.current&&(!a.current&&n.leading?(a.current=!0,r(e)):(c(),s.current=setTimeout(()=>{a.current=!1,r(e)},t)))},[e,n.leading,t,c]),fe(()=>(i.current=!0,c),[c]),[o,c]}var In=250;function gt(e,t,n){return H("search",e,t,n)}function It(e,t,n){return H("searchOne",e,t,n)}function ht(e,t,n){return H("searchResources",e,t,n)}function H(e,t,n,o){let r=S(),[i,s]=j(!0),[a,c]=j(),[R,I]=j(),v=r.fhirSearchUrl(t,n).toString(),C=gn(()=>({resourceType:t,query:n}),[v]),g=o?.debounceMs??In,[p]=le(C,g,{leading:!0});return Rn(()=>{let d=!0;return r[e](p.resourceType,p.query).then(u=>{d&&(s(!1),c(u),I(ln))}).catch(u=>{d&&(s(!1),c(void 0),I(mn(u)))}),()=>{d=!1}},[r,e,p]),[a,i,R]}import{getReferenceString as hn}from"@medplum/core";import{useCallback as yn,useEffect as me,useState as N}from"react";function St({query:e,threadId:t}){let n=S(),[o,r]=N(!0),[i,s]=N([]),[a,c]=N(void 0),[R,I]=N(null),[v,C]=N(void 0),g=yn(async()=>{let u=new URLSearchParams(e);u.append("identifier:not","http://medplum.com/ai-message|"),u.append("part-of:missing","true"),u.append("_has:Communication:part-of:_id:not","null");let l=await n.search("Communication",u.toString(),{cache:"no-cache"}),f=l.entry?.map(h=>h.resource).filter(h=>h!==void 0)||[];if(l.total!==void 0&&C(l.total),f.length===0){s([]);return}let E=`
1
+ import{useEffect as be,useMemo as ve,useState as Te}from"react";import{createContext as Ee,useContext as Qe}from"react";var F=Ee(void 0);function q(){return Qe(F)}function b(){return q().medplum}function Nn(){return q().navigate}function Un(){return q().profile}import{jsx as Ce}from"react/jsx-runtime";var Y=["change","storageInitialized","storageInitFailed","profileRefreshing","profileRefreshed"];function qn(e){let t=e.medplum,n=e.navigate??Pe,[o,r]=Te({profile:t.getProfile(),loading:t.isLoading()});be(()=>{function s(){r(c=>({...c,profile:t.getProfile(),loading:t.isLoading()}))}for(let c of Y)t.addEventListener(c,s);return()=>{for(let c of Y)t.removeEventListener(c,s)}},[t]);let i=ve(()=>({...o,medplum:t,navigate:n}),[o,t,n]);return Ce(F.Provider,{value:i,children:e.children})}function Pe(e){window.location.assign(e)}import{useMemo as Oe}from"react";var Z=new Map,Wn=e=>Oe(()=>{if(!e)return;let t=e.split("?")[0];if(!t)return e;let n;try{n=new URLSearchParams(new URL(e).search)}catch{return e}if(!n.has("Key-Pair-Id")||!n.has("Signature"))return e;let o=n.get("Expires");if(!o||o.length>13)return e;let r=Z.get(t);if(r){let s=new URLSearchParams(new URL(r).search).get("Expires");if(s&&Number.parseInt(s,10)*1e3-5e3>Date.now())return r}return Z.set(t,e),e},[e]);import{useEffect as ee,useRef as k,useState as we}from"react";function jn(e,t,n){let o=b(),{patientId:r,onPatientSyncSuccess:i,onIframeSuccess:s,onError:c}=n,[d,S]=we(void 0),h=k(i),Q=k(s),v=k(c);return ee(()=>{h.current=i,Q.current=s,v.current=c},[i,s,c]),ee(()=>{let R=!1;return(async()=>{try{if(r){if(await o.executeBot(e,{patientId:r}),R)return;h.current?.()}let u=await o.executeBot(t,{patientId:r});if(R)return;u.url&&(S(u.url),Q.current?.(u.url))}catch(u){R||v.current?.(u)}})().catch(()=>{}),()=>{R=!0}},[o,e,t,r]),d}import{useCallback as Me,useEffect as Ne,useState as Ue}from"react";import{deepEquals as ne}from"@medplum/core";import{useCallback as A,useEffect as V,useRef as C,useState as te}from"react";var Ae=3e3;function re(e,t,n){let o=b(),[r,i]=te(),[s,c]=te(n?.subscriptionProps),d=C(!1),S=C(void 0),h=C(void 0),Q=C(void 0),v=C(t);v.current=t;let R=C(n?.onWebSocketOpen);R.current=n?.onWebSocketOpen;let m=C(n?.onWebSocketClose);m.current=n?.onWebSocketClose;let u=C(n?.onSubscriptionConnect);u.current=n?.onSubscriptionConnect;let a=C(n?.onSubscriptionDisconnect);a.current=n?.onSubscriptionDisconnect;let l=C(n?.onError);l.current=n?.onError,V(()=>{ne(n?.subscriptionProps,s)||c(n?.subscriptionProps)},[s,n]),V(()=>{S.current&&(clearTimeout(S.current),S.current=void 0);let T=!1;return(h.current!==e||!ne(Q.current,s))&&(T=!0),T&&h.current&&o.unsubscribeFromCriteria(h.current,Q.current),h.current=e,Q.current=s,T&&e?i(o.subscribeToCriteria(e,s)):e||i(void 0),()=>{S.current=setTimeout(()=>{i(void 0),e&&o.unsubscribeFromCriteria(e,s)},Ae)}},[o,e,s]);let y=A(T=>{v.current?.(T.payload)},[]),p=A(()=>{R.current?.()},[]),x=A(()=>{m.current?.()},[]),I=A(T=>{u.current?.(T.payload.subscriptionId)},[]),g=A(T=>{a.current?.(T.payload.subscriptionId)},[]),f=A(T=>{l.current?.(T.payload)},[]);V(()=>r?(d.current||(r.addEventListener("message",y),r.addEventListener("open",p),r.addEventListener("close",x),r.addEventListener("connect",I),r.addEventListener("disconnect",g),r.addEventListener("error",f),d.current=!0),()=>{d.current=!1,r.removeEventListener("message",y),r.removeEventListener("open",p),r.removeEventListener("close",x),r.removeEventListener("connect",I),r.removeEventListener("disconnect",g),r.removeEventListener("error",f)}):()=>{},[r,y,p,x,I,g,f])}function nt(e){let t=b(),{resourceType:n,countCriteria:o,subscriptionCriteria:r}=e,[i,s]=Ue(0),c=Me(d=>{t.search(n,o,{cache:d}).then(S=>s(S.total)).catch(console.error)},[t,n,o]);return Ne(()=>{c("default")},[c]),re(r,()=>{c("reload")}),i}import{resolveId as Le}from"@medplum/core";import{useEffect as _e,useMemo as oe,useState as D}from"react";function ie(e){let t=e.patientParam??"subject",n=e.query,o="";if(n!=null)if(typeof n=="string")o=n;else if(n instanceof URLSearchParams){let r=Array.from(n.entries()).sort((i,s)=>i[0].localeCompare(s[0])||i[1].localeCompare(s[1]));o=JSON.stringify(r)}else if(Array.isArray(n)){let r=[...n].sort((i,s)=>i[0].localeCompare(s[0])||i[1].localeCompare(s[1]));o=JSON.stringify(r)}else{let r=Object.entries(n).filter(([,i])=>i!==void 0).sort(([i],[s])=>i.localeCompare(s));o=JSON.stringify(r)}return`${e.resourceType}:${t}:${o}`}function Fe(e){return e.map(t=>{let n=t.searches?t.searches.map(ie).join(","):"";return`${t.key}:[${n}]`}).join("|")}function st(e,t){let n=b(),[o,r]=D([]),[i,s]=D(!0),[c,d]=D(),S=Fe(t),h=oe(()=>t,[S]),Q=oe(()=>Le(e),[e]);return _e(()=>{if(!Q)return;let v=!1,R=`Patient/${Q}`,m={_count:100,_sort:"-_lastUpdated"},u=[],a=new Map,l=[];for(let p of h){let x=[];if(p.searches)for(let I of p.searches){let g=ie(I),f=a.get(g);f===void 0&&(f=u.length,a.set(g,f),u.push(I)),x.push({searchIdx:f,resultKey:I.key})}l.push(x)}if(u.length===0){r(h.map(()=>({}))),s(!1);return}let y=u.map(p=>{let x=p.patientParam??"subject",I={[x]:R};if(p.query){if(typeof p.query=="string")return n.searchResources(p.resourceType,`${x}=${R}&${p.query}&_count=100&_sort=-_lastUpdated`);if(p.query instanceof URLSearchParams)p.query.forEach((g,f)=>{I[f]=g});else if(Array.isArray(p.query))for(let[g,f]of p.query)I[g]=f;else for(let[g,f]of Object.entries(p.query))f!==void 0&&(I[g]=f)}return n.searchResources(p.resourceType,{...m,...I})});return s(!0),d(void 0),Promise.allSettled(y).then(p=>{if(v)return;let x=l.map(g=>{let f={};for(let{searchIdx:T,resultKey:N}of g){let w=p[T];f[N]=w.status==="fulfilled"?w.value:[]}return f});r(x),s(!1);let I=p.filter(g=>g.status==="rejected");if(I.length>0){console.error("Some patient summary searches failed:",I.map(f=>f.reason));let g=I[0].reason;d(g instanceof Error?g:new Error(String(g)))}}).catch(p=>{v||(d(p instanceof Error?p:new Error(String(p))),s(!1))}),()=>{v=!0}},[n,Q,h]),{sectionData:o,loading:i,error:c}}import{isAddPharmacyResponse as qe,isOrganizationArray as ke}from"@medplum/core";import{useCallback as se}from"react";function pt(e,t){let n=b(),o=se(async i=>{let s=await n.executeBot(e,i);if(!ke(s))throw new Error("Invalid response from pharmacy search");return s},[n,e]),r=se(async i=>{let s=await n.executeBot(t,{patientId:i.patientId,pharmacy:i.pharmacy,setAsPrimary:i.setAsPrimary});if(!qe(s))throw new Error("Invalid response from add pharmacy bot");return s},[n,t]);return{searchPharmacies:o,addToFavorites:r}}import{useEffect as Ve,useRef as De}from"react";function mt(e){let t=De(void 0);return Ve(()=>{t.current=e}),t.current}import{getExtension as hn}from"@medplum/core";import{useReducer as gn,useRef as In}from"react";import{deepEquals as We,isReference as ue,isResource as $e,normalizeOperationOutcome as Ke}from"@medplum/core";import{useCallback as Be,useEffect as je,useState as ze}from"react";function W(e,t){let n=b(),[o,r]=ze(()=>ae(n,e)),i=Be(s=>{We(s,o)||r(s)},[o]);return je(()=>{let s=!0,c=ae(n,e);return!c&&ue(e)?n.readReference(e).then(d=>{s&&i(d)}).catch(d=>{s&&(i(void 0),t&&t(Ke(d)))}):i(c),(()=>s=!1)},[n,e,i,t]),o}function ae(e,t){if(t){if($e(t))return t;if(ue(t))return e.getCachedReference(t)}}import{EMPTY as fe,HTTP_HL7_ORG as O,PropertyType as P,append as ce,capitalize as de,deepClone as Ge,evalFhirPathTyped as K,getExtension as M,getReferenceString as Je,getTypedPropertyValueWithoutSchema as L,normalizeErrorString as He,splitN as Xe,toJsBoolean as Ye,toTypedValue as le,typedValueToString as Ze}from"@medplum/core";var E={group:"group",display:"display",question:"question",boolean:"boolean",decimal:"decimal",integer:"integer",date:"date",dateTime:"dateTime",time:"time",string:"string",text:"text",url:"url",choice:"choice",openChoice:"open-choice",attachment:"attachment",reference:"reference",quantity:"quantity"},me=`${O}/fhir/StructureDefinition/questionnaire-itemControl`,en=`${O}/fhir/StructureDefinition/questionnaire-referenceFilter`,$=`${O}/fhir/StructureDefinition/questionnaire-referenceResource`,nn=`${O}/fhir/StructureDefinition/questionnaire-validationError`,tn=`${O}/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-enableWhenExpression`,rn=`${O}/fhir/uv/sdc/StructureDefinition/sdc-questionnaire-calculatedExpression`,xt=`${O}/fhir/StructureDefinition/questionnaire-signatureRequired`,_=`${O}/fhir/StructureDefinition/questionnaireresponse-signature`,on=`${O}/fhir/StructureDefinition/questionnaire-hidden`;function Et(e){return e.type==="choice"||e.type==="open-choice"}function Qt(e,t){if(M(e,on)?.valueBoolean===!0)return!1;let o=sn(e,t);return o!==void 0?o:an(e,t)}function sn(e,t){let n=M(e,tn);if(t&&n){let o=n.valueExpression?.expression;if(o){let r=le(t),i=K(o,[r],{"%resource":r});return Ye(i)}}}function an(e,t){if(!e.enableWhen)return!0;let n=e.enableBehavior??"any";for(let o of e.enableWhen){let r=ye(t?.item,o.question);if(o.operator==="exists"&&!o.answerBoolean&&!r?.length){if(n==="any")return!0;continue}let{anyMatch:i,allMatch:s}=ln(o,r,n);if(n==="any"&&i)return!0;if(n==="all"&&!s)return!1}return n!=="any"}function B(e,t,n=t.item){for(let o of e){let r=n?.find(i=>i.linkId===o.linkId);r&&(un(t,o,r),o.item&&r.item&&B(o.item,t,r.item))}}function un(e,t,n){try{let o=pn(t,e);if(!o)return;let r=dn(t,o);if(!r)return;n.answer=[r]}catch(o){n.extension=[{url:nn,valueString:`Expression evaluation failed: ${He(o)}`}]}}var cn={[E.boolean]:[P.boolean],[E.date]:[P.date],[E.dateTime]:[P.dateTime],[E.time]:[P.time],[E.url]:[P.string,P.uri,P.url],[E.attachment]:[P.Attachment],[E.reference]:[P.Reference],[E.quantity]:[P.Quantity],[E.decimal]:[P.decimal,P.integer],[E.integer]:[P.decimal,P.integer]};function dn(e,t){if(!e.type)return;if(e.type===E.choice||e.type===E.openChoice)return{[`value${de(t.type)}`]:t.value};if(e.type===E.string||e.type===E.text)return typeof t.value=="string"?{valueString:t.value}:void 0;if(cn[e.type]?.includes(t.type))return{[`value${de(e.type)}`]:t.value}}function pn(e,t){if(!t)return;let n=M(e,rn);if(n){let o=n.valueExpression?.expression;if(o){let r=le(t),i=K(o,[r],{"%resource":r});return i.length!==0?i[0]:void 0}}}function bt(e,t,n){let o=[];for(let r of e){let i=n.answerOption?.find(s=>Ze(pe(s))===r);if(i){let s=pe(i);s&&o.push({[t]:s.value})}}return o}function ye(e,t){for(let n of e??fe){if(n.linkId===t)return n.answer;if(n.item){let o=ye(n.item,t);if(o)return o}}}function fn(e,t,n){if(n==="exists")return!!e===t.value;if(e){let o=n==="="||n==="!="?n?.replace("=","~"):n,[{value:r}]=K(`%actualAnswer ${o} %expectedAnswer`,[e],{"%actualAnswer":e,"%expectedAnswer":t});return r}else return!1}function ln(e,t,n){let o=t||[],r=yn(e),i=!1,s=!0;for(let c of o){let d=Rn(c),{operator:S}=e;if(fn(d,r,S)?i=!0:s=!1,n==="any"&&i)break}return{anyMatch:i,allMatch:s}}function vt(e){let t=M(e,$);if(t){if(t.valueCode!==void 0)return[t.valueCode];if(t.valueCodeableConcept)return t.valueCodeableConcept?.coding?.map(n=>n.code)}}function Tt(e,t){let n=Ge(e),o=M(n,$);return!t||t.length===0?(o&&(n.extension=n.extension?.filter(r=>r!==o)),n):(o||(n.extension??=[],o={url:$},n.extension.push(o)),t.length===1?(o.valueCode=t[0],delete o.valueCodeableConcept):(o.valueCodeableConcept={coding:t.map(r=>({code:r}))},delete o.valueCode),n)}function Pt(e,t,n){let o=M(e,en);if(!o?.valueString)return;let r=o.valueString;t?.reference&&(r=r.replaceAll("$subj",t.reference)),n?.reference&&(r=r.replaceAll("$encounter",n.reference));let i={},s=r.split("&");for(let c of s){let[d,S]=Xe(c,"=",2);i[d]=S}return i}function j(e,t){return{resourceType:"QuestionnaireResponse",questionnaire:e.url??Je(e),item:z(e.item,t?.item),status:"in-progress"}}function z(e,t){let n;for(let o of e??fe){if(o.type===E.display)continue;let r=t?.filter(i=>i.linkId===o.linkId);if(r?.length)for(let i of r)i.id=i.id??Re(),i.text=i.text??o.text,i.item=z(o.item,i.item),i.answer=he(o,i),n=ce(n,i);else n=ce(n,G(o))}return n}function G(e){return{id:Re(),linkId:e.linkId,text:e.text,item:z(e.item,void 0),answer:he(e)}}var mn=1;function Re(){return"id-"+mn++}function he(e,t){if(!(e.type===E.display||e.type===E.group)){if(t?.answer&&t.answer.length>0)return t.answer;if(e.initial&&e.initial.length>0)return e.initial.map(n=>({...n}));if(e.answerOption)return e.answerOption.filter(n=>n.initialSelected).map(n=>({...n,initialSelected:void 0}))}}function Ct(e){return L({type:"QuestionnaireItemInitial",value:e},"value")}function pe(e){return L({type:"QuestionnaireItemAnswerOption",value:e},"value")}function yn(e){return L({type:"QuestionnaireItemEnableWhen",value:e},"answer")}function Rn(e){return L({type:"QuestionnaireResponseItemAnswer",value:e},"value")}function Ut(e){let t=W(e.questionnaire),n=W(e.defaultValue),[,o]=gn(m=>m+1,0),r=In({activePage:0});if(!r.current.questionnaire&&t&&(r.current.questionnaire=t,r.current.pages=e.disablePagination?void 0:Sn(t)),t&&e.defaultValue&&n&&!r.current.questionnaireResponse&&(r.current.questionnaireResponse=j(t,n),R()),t&&!e.defaultValue&&!r.current.questionnaireResponse&&(r.current.questionnaireResponse=j(t),R()),!r.current.questionnaire||!r.current.questionnaireResponse)return{loading:!0};function i(m,u){let a=r.current.questionnaireResponse;for(let l of m)a=a?.item?.find(y=>l.id?y.id===l.id:y.linkId===l.linkId);return u&&(a=a?.item?.find(l=>l.linkId===u.linkId)),a}function s(){r.current.activePage=(r.current.activePage??0)+1,o()}function c(){r.current.activePage=(r.current.activePage??0)-1,o()}function d(m,u){let a=i(m);a&&(a.item??=[],a.item.push(G(u)),R())}function S(m,u){let a=i(m,u);a&&(a.answer??=[],a.answer.push({}),R())}function h(m,u,a){let l=i(m,u);l&&(l.answer=a,R())}function Q(m){let u=r.current.questionnaireResponse;u&&(m?(u.extension=u.extension??[],u.extension=u.extension.filter(a=>a.url!==_),u.extension.push({url:_,valueSignature:m})):u.extension=u.extension?.filter(a=>a.url!==_),R())}function v(){let m=r.current.questionnaire;if(m?.item){let u=r.current.questionnaireResponse;B(m.item,u)}}function R(){let m=r.current.questionnaireResponse;m&&(v(),o(),e.onChange?.(m))}return{loading:!1,pagination:!!r.current.pages,questionnaire:r.current.questionnaire,questionnaireResponse:r.current.questionnaireResponse,subject:e.subject,encounter:e.encounter,activePage:r.current.activePage,pages:r.current.pages,items:xn(r.current.questionnaire,r.current.pages,r.current.activePage),responseItems:En(r.current.questionnaireResponse,r.current.pages,r.current.activePage),onNextPage:s,onPrevPage:c,onAddGroup:d,onAddAnswer:S,onChangeAnswer:h,onChangeSignature:Q}}function Sn(e){if(!(!e?.item||hn(e?.item?.[0],me)?.valueCodeableConcept?.coding?.[0]?.code!=="page"))return e.item.map((n,o)=>({linkId:n.linkId,title:n.text??`Page ${o+1}`,group:n}))}function xn(e,t,n=0){return t&&e?.item?.[n]?[e.item[n]]:e.item??[]}function En(e,t,n=0){return t&&e?.item?.[n]?[e.item[n]]:e.item??[]}import{allOk as vn,normalizeOperationOutcome as Tn}from"@medplum/core";import{useEffect as Pn,useMemo as Cn,useState as H}from"react";import{useCallback as Qn,useEffect as ge,useRef as J,useState as bn}from"react";function Ie(e,t,n={leading:!1}){let[o,r]=bn(e),i=J(!1),s=J(void 0),c=J(!1),d=Qn(()=>window.clearTimeout(s.current),[]);return ge(()=>{i.current&&(!c.current&&n.leading?(c.current=!0,r(e),s.current=setTimeout(()=>{c.current=!1},t)):(d(),s.current=setTimeout(()=>{c.current=!1,r(e)},t)))},[e,n.leading,t,d]),ge(()=>(i.current=!0,d),[d]),[o,d]}var On=250;function Wt(e,t,n){return X("search",e,t,n)}function $t(e,t,n){return X("searchOne",e,t,n)}function Kt(e,t,n){return X("searchResources",e,t,n)}function X(e,t,n,o){let r=b(),[i,s]=H(!1),[c,d]=H(),[S,h]=H(),Q=r.fhirSearchUrl(t,n).toString(),v=Cn(()=>({resourceType:t,query:n}),[Q]),R=o?.enabled??!0,m=o?.debounceMs??On,[u]=Ie(v,m,{leading:!0});return Pn(()=>{if(!R)return()=>{};s(!0);let a=!0;return r[e](u.resourceType,u.query).then(l=>{a&&(s(!1),d(l),h(vn))}).catch(l=>{a&&(s(!1),d(void 0),h(Tn(l)))}),()=>{a=!1}},[r,e,u,R]),[c,i,S]}import{getReferenceString as wn}from"@medplum/core";import{useCallback as An,useEffect as Se,useState as U}from"react";function Jt({query:e,threadId:t}){let n=b(),[o,r]=U(!0),[i,s]=U([]),[c,d]=U(void 0),[S,h]=U(null),[Q,v]=U(void 0),R=An(async()=>{let a=new URLSearchParams(e);a.append("identifier:not","http://medplum.com/ai-message|"),a.append("part-of:missing","true"),a.append("_has:Communication:part-of:_id:not","null");let l=await n.search("Communication",a.toString(),{cache:"no-cache"}),y=l.entry?.map(f=>f.resource).filter(f=>f!==void 0)||[];if(l.total!==void 0&&v(l.total),y.length===0){s([]);return}let x=`
2
2
  query {
3
- ${f.map(h=>{let _=`thread_${h.id?.replaceAll("-","")||""}`,M=hn(h);return`
4
- ${_}: CommunicationList(
5
- part_of: "${M}"
3
+ ${y.map(f=>{let N=`thread_${f.id?.replaceAll("-","")||""}`,w=wn(f);return`
4
+ ${N}: CommunicationList(
5
+ part_of: "${w}"
6
6
  _sort: "-sent"
7
7
  _count: 1
8
8
  ) {
@@ -26,5 +26,5 @@ import{useEffect as he,useMemo as ye,useState as xe}from"react";import{createCon
26
26
  `}).join(`
27
27
  `)}
28
28
  }
29
- `,P=await n.graphql(E),A=f.map(h=>{let _=`thread_${h.id?.replaceAll("-","")||""}`,M=P.data[_],Re=M&&M.length>0?M[0]:void 0;return[h,Re]}).filter(h=>h[1]!==void 0);s(A)},[n,e]);return me(()=>{r(!0),g().catch(u=>{I(u)}).finally(()=>{r(!1)})},[g]),me(()=>{(async()=>{if(!t){c(void 0);return}let l=i.find(Q=>Q[0].id===t);if(l){c(l[0]);return}let f=await n.readResource("Communication",t);if(f.partOf===void 0)c(f);else{let Q=f.partOf[0].reference;if(Q){let E=await n.readReference({reference:Q});c(E)}}})().catch(l=>{I(l)})},[t,i,n]),{loading:o,error:R,threadMessages:i,selectedThread:a,total:v,addThreadMessage:u=>{(async()=>{await g(),s(f=>[[u,void 0],...f])})().catch(f=>I(f))},handleThreadStatusChange:u=>{if(!a)return;(async()=>{let f=await n.updateResource({...a,status:u});c(f),s(Q=>Q.map(([E,P])=>E.id===f.id?[f,P]:[E,P]))})().catch(f=>I(f))},refreshThreadMessages:g}}export{Tn as MedplumProvider,Be as QUESTIONNAIRE_CALCULATED_EXPRESSION_URL,Ke as QUESTIONNAIRE_ENABLED_WHEN_EXPRESSION_URL,ze as QUESTIONNAIRE_HIDDEN_URL,ae as QUESTIONNAIRE_ITEM_CONTROL_URL,De as QUESTIONNAIRE_REFERENCE_FILTER_URL,W as QUESTIONNAIRE_REFERENCE_RESOURCE_URL,Hn as QUESTIONNAIRE_SIGNATURE_REQUIRED_URL,U as QUESTIONNAIRE_SIGNATURE_RESPONSE_URL,$e as QUESTIONNAIRE_VALIDATION_ERROR_URL,m as QuestionnaireItemType,K as buildInitialResponse,z as buildInitialResponseItem,$ as evaluateCalculatedExpressionsInQuestionnaire,ie as getItemAnswerOptionValue,tn as getItemEnableWhenValueAnswer,tt as getItemInitialValue,Yn as getNewMultiSelectValues,nt as getQuestionnaireItemReferenceFilter,Zn as getQuestionnaireItemReferenceTargetTypes,rn as getResponseItemAnswerValue,Xn as isChoiceQuestion,Jn as isQuestionEnabled,V as reactContext,et as setQuestionnaireItemReferenceTargetTypes,Je as typedValueToResponseItem,wn as useCachedBinaryUrl,S as useMedplum,F as useMedplumContext,Qn as useMedplumNavigate,En as useMedplumProfile,qn as useNotificationCount,Dn as usePrevious,at as useQuestionnaireForm,k as useResource,gt as useSearch,It as useSearchOne,ht as useSearchResources,ee as useSubscription,St as useThreadInbox};
29
+ `,I=await n.graphql(x),g=y.map(f=>{let N=`thread_${f.id?.replaceAll("-","")||""}`,w=I.data[N],xe=w&&w.length>0?w[0]:void 0;return[f,xe]}).filter(f=>f[1]!==void 0);s(g)},[n,e]);return Se(()=>{r(!0),R().catch(a=>{h(a)}).finally(()=>{r(!1)})},[R]),Se(()=>{(async()=>{if(!t){d(void 0);return}let l=i.find(p=>p[0].id===t);if(l){d(l[0]);return}let y=await n.readResource("Communication",t);if(y.partOf===void 0)d(y);else{let p=y.partOf[0].reference;if(p){let x=await n.readReference({reference:p});d(x)}}})().catch(l=>{h(l)})},[t,i,n]),{loading:o,error:S,threadMessages:i,selectedThread:c,total:Q,addThreadMessage:a=>{(async()=>{await R(),s(y=>[[a,void 0],...y])})().catch(y=>h(y))},handleThreadStatusChange:a=>{if(!c)return;(async()=>{let y=await n.updateResource({...c,status:a});d(y),s(p=>p.map(([x,I])=>x.id===y.id?[y,I]:[x,I]))})().catch(y=>h(y))},refreshThreadMessages:R}}export{qn as MedplumProvider,rn as QUESTIONNAIRE_CALCULATED_EXPRESSION_URL,tn as QUESTIONNAIRE_ENABLED_WHEN_EXPRESSION_URL,on as QUESTIONNAIRE_HIDDEN_URL,me as QUESTIONNAIRE_ITEM_CONTROL_URL,en as QUESTIONNAIRE_REFERENCE_FILTER_URL,$ as QUESTIONNAIRE_REFERENCE_RESOURCE_URL,xt as QUESTIONNAIRE_SIGNATURE_REQUIRED_URL,_ as QUESTIONNAIRE_SIGNATURE_RESPONSE_URL,nn as QUESTIONNAIRE_VALIDATION_ERROR_URL,E as QuestionnaireItemType,j as buildInitialResponse,G as buildInitialResponseItem,B as evaluateCalculatedExpressionsInQuestionnaire,pe as getItemAnswerOptionValue,yn as getItemEnableWhenValueAnswer,Ct as getItemInitialValue,bt as getNewMultiSelectValues,Pt as getQuestionnaireItemReferenceFilter,vt as getQuestionnaireItemReferenceTargetTypes,Rn as getResponseItemAnswerValue,Et as isChoiceQuestion,Qt as isQuestionEnabled,F as reactContext,Tt as setQuestionnaireItemReferenceTargetTypes,dn as typedValueToResponseItem,Wn as useCachedBinaryUrl,jn as useEPrescribingIFrame,b as useMedplum,q as useMedplumContext,Nn as useMedplumNavigate,Un as useMedplumProfile,nt as useNotificationCount,st as usePatientSummaryData,pt as usePharmacySearch,mt as usePrevious,Ut as useQuestionnaireForm,W as useResource,Wt as useSearch,$t as useSearchOne,Kt as useSearchResources,re as useSubscription,Jt as useThreadInbox};
30
30
  //# sourceMappingURL=index.mjs.map