@medplum/app 5.0.1 → 5.0.2
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.
|
@@ -88,7 +88,7 @@ ${d}`}function ja({color:e,theme:t,autoContrast:n}){return(typeof n=="boolean"?n
|
|
|
88
88
|
*
|
|
89
89
|
* Copy of "partysocket" from Partykit team, a fork of the original "Reconnecting WebSocket"
|
|
90
90
|
* https://github.com/partykit/partykit/blob/main/packages/partysocket
|
|
91
|
-
*/const Ac={Event:typeof globalThis.Event<"u"?globalThis.Event:void 0,ErrorEvent:void 0,CloseEvent:void 0};let fT=!1;function vV(){if(typeof globalThis.Event>"u")throw new Error("Unable to lazy init events for ReconnectingWebSocket. globalThis.Event is not defined yet");Ac.Event=globalThis.Event,Ac.ErrorEvent=class extends Event{message;error;constructor(t,n){super("error",n),this.message=t.message,this.error=t}},Ac.CloseEvent=class extends Event{code;reason;wasClean=!0;constructor(t=1e3,n="",r){super("close",r),this.code=t,this.reason=n}}}function yV(e,t){if(!e)throw new Error(t)}function Rh(e){return new e.constructor(e.type,e)}const Fs={maxReconnectionDelay:1e4,minReconnectionDelay:1e3+Math.random()*4e3,minUptime:5e3,reconnectionDelayGrowFactor:1.3,connectionTimeout:4e3,maxRetries:1/0,maxEnqueuedMessages:1/0};let hT=!1;class os extends _m{_ws;_retryCount=-1;_uptimeTimeout;_connectTimeout;_shouldReconnect=!0;_connectLock=!1;_binaryType;_closeCalled=!1;_messageQueue=[];_debugLogger=console.log.bind(console);_url;_protocols;_options;constructor(t,n,r={}){fT||(vV(),fT=!0),super(),this._url=t,this._protocols=n,this._options=r,this._options.startClosed&&(this._shouldReconnect=!1),this._options.binaryType?this._binaryType=this._options.binaryType:this._binaryType="blob",this._options.debugLogger&&(this._debugLogger=this._options.debugLogger),this._connect()}static get CONNECTING(){return 0}static get OPEN(){return 1}static get CLOSING(){return 2}static get CLOSED(){return 3}get CONNECTING(){return os.CONNECTING}get OPEN(){return os.OPEN}get CLOSING(){return os.CLOSING}get CLOSED(){return os.CLOSED}get binaryType(){return this._ws?this._ws.binaryType:this._binaryType}set binaryType(t){this._binaryType=t,this._ws&&(this._ws.binaryType=t)}get retryCount(){return Math.max(this._retryCount,0)}get bufferedAmount(){return this._messageQueue.reduce((n,r)=>(typeof r=="string"?n+=r.length:r instanceof Blob?n+=r.size:n+=r.byteLength,n),0)+(this._ws?.bufferedAmount??0)}get extensions(){return this._ws?.extensions??""}get protocol(){return this._ws?.protocol??""}get readyState(){return this._ws?this._ws.readyState:this._options.startClosed?os.CLOSED:os.CONNECTING}get url(){return this._ws?this._ws.url:""}get shouldReconnect(){return this._shouldReconnect}onclose=null;onerror=null;onmessage=null;onopen=null;close(t=1e3,n){if(this._closeCalled=!0,this._shouldReconnect=!1,this._clearTimeouts(),!this._ws){this._debug("close enqueued: no ws instance");return}if(this._ws.readyState===this.CLOSED){this._debug("close: already closed");return}this._ws.close(t,n)}reconnect(t,n){this._shouldReconnect=!0,this._closeCalled=!1,this._retryCount=-1,!this._ws||this._ws.readyState===this.CLOSED?this._connect():(this._disconnect(t,n),this._connect())}send(t){if(this._ws&&this._ws.readyState===this.OPEN)this._debug("send",t),this._ws.send(t);else{const{maxEnqueuedMessages:n=Fs.maxEnqueuedMessages}=this._options;this._messageQueue.length<n&&(this._debug("enqueue",t),this._messageQueue.push(t))}}_debug(...t){this._options.debug&&this._debugLogger("RWS>",...t)}_getNextDelay(){const{reconnectionDelayGrowFactor:t=Fs.reconnectionDelayGrowFactor,minReconnectionDelay:n=Fs.minReconnectionDelay,maxReconnectionDelay:r=Fs.maxReconnectionDelay}=this._options;let o=0;return this._retryCount>0&&(o=n*Math.pow(t,this._retryCount-1),o>r&&(o=r)),this._debug("next delay",o),o}_wait(){return new Promise(t=>{setTimeout(t,this._getNextDelay())})}_connect(){if(this._connectLock||!this._shouldReconnect)return;this._connectLock=!0;const{maxRetries:t=Fs.maxRetries,connectionTimeout:n=Fs.connectionTimeout}=this._options;if(this._retryCount>=t){this._debug("max retries reached",this._retryCount,">=",t);return}this._retryCount++,this._debug("connect",this._retryCount),this._removeListeners(),this._wait().then(()=>{if(this._closeCalled){this._connectLock=!1;return}!this._options.WebSocket&&typeof WebSocket>"u"&&!hT&&(console.error("‼️ No WebSocket implementation available. You should define options.WebSocket."),hT=!0);const r=this._options.WebSocket||WebSocket;this._debug("connect",{url:this._url,protocols:this._protocols}),this._ws=this._protocols?new r(this._url,this._protocols):new r(this._url),this._ws.binaryType=this._binaryType,this._connectLock=!1,this._addListeners(),this._connectTimeout=setTimeout(()=>this._handleTimeout(),n)}).catch(r=>{this._connectLock=!1,this._handleError(new Ac.ErrorEvent(Error(r.message),this))})}_handleTimeout(){this._debug("timeout event"),this._handleError(new Ac.ErrorEvent(Error("TIMEOUT"),this))}_disconnect(t=1e3,n){if(this._clearTimeouts(),!!this._ws){this._removeListeners();try{this._ws.close(t,n),this._handleClose(new Ac.CloseEvent(t,n,this))}catch{}}}_acceptOpen(){this._debug("accept open"),this._retryCount=0}_handleOpen=t=>{this._debug("open event");const{minUptime:n=Fs.minUptime}=this._options;clearTimeout(this._connectTimeout),this._uptimeTimeout=setTimeout(()=>this._acceptOpen(),n),yV(this._ws,"WebSocket is not defined"),this._ws.binaryType=this._binaryType,this._messageQueue.forEach(r=>this._ws?.send(r)),this._messageQueue=[],this.onopen&&this.onopen(t),this.dispatchEvent(Rh(t))};_handleMessage=t=>{this._debug("message event"),this.onmessage&&this.onmessage(t),this.dispatchEvent(Rh(t))};_handleError=t=>{this._debug("error event",t.message),this._disconnect(void 0,t.message==="TIMEOUT"?"timeout":void 0),this.onerror&&this.onerror(t),this._debug("exec error listeners"),this.dispatchEvent(Rh(t)),this._connect()};_handleClose=t=>{this._debug("close event"),this._clearTimeouts(),this._shouldReconnect&&this._connect(),this.onclose&&this.onclose(t),this.dispatchEvent(Rh(t))};_removeListeners(){this._ws&&(this._debug("removeListeners"),this._ws.removeEventListener("open",this._handleOpen),this._ws.removeEventListener("close",this._handleClose),this._ws.removeEventListener("message",this._handleMessage),this._ws.removeEventListener("error",this._handleError))}_addListeners(){this._ws&&(this._debug("addListeners"),this._ws.addEventListener("open",this._handleOpen),this._ws.addEventListener("close",this._handleClose),this._ws.addEventListener("message",this._handleMessage),this._ws.addEventListener("error",this._handleError))}_clearTimeouts(){clearTimeout(this._connectTimeout),clearTimeout(this._uptimeTimeout)}}const xV=5e3;class wx extends _m{criteria;constructor(...t){super(),this.criteria=new Set(t)}getCriteria(){return this.criteria}_addCriteria(t){this.criteria.add(t)}_removeCriteria(t){this.criteria.delete(t)}}class bV{criteria;emitter;refCount;subscriptionProps;subscriptionId;token;connecting=!1;constructor(t,n){this.criteria=t,this.emitter=new wx(t),this.refCount=1,this.subscriptionProps=n?{...n}:void 0}clearAttachedSubscription(){this.subscriptionId=void 0,this.token=void 0}}class SV{medplum;ws;masterSubEmitter;criteriaEntries;criteriaEntriesBySubscriptionId;wsClosed;pingTimer=void 0;pingIntervalMs;waitingForPong=!1;currentProfile;constructor(t,n,r){if(!(t instanceof zD))throw new gt(yn("First arg of constructor should be a `MedplumClient`"));let o;try{o=new URL(n).toString()}catch{throw new gt(yn("Not a valid URL"))}const l=r?.ReconnectingWebSocket?new r.ReconnectingWebSocket(o,void 0,{debug:r?.debug,debugLogger:r?.debugLogger}):new os(o,void 0,{debug:r?.debug,debugLogger:r?.debugLogger});this.medplum=t,this.ws=l,this.masterSubEmitter=new wx,this.criteriaEntries=new Map,this.criteriaEntriesBySubscriptionId=new Map,this.wsClosed=!1,this.pingIntervalMs=r?.pingIntervalMs??xV,this.currentProfile=t.getProfile(),this.setupListeners()}setupListeners(){const t=this.ws;t.addEventListener("message",n=>{try{const r=JSON.parse(n.data);if(r.type==="pong"){this.waitingForPong=!1;return}const o=r,l=o?.entry?.[0]?.resource;if(l.type==="heartbeat"){this.masterSubEmitter?.dispatchEvent({type:"heartbeat",payload:o});return}if(l.type==="handshake"){const d=sl(l.subscription),f={type:"connect",payload:{subscriptionId:d}};this.masterSubEmitter?.dispatchEvent(f);const p=this.criteriaEntriesBySubscriptionId.get(d);if(!p){console.warn("Received handshake for criteria the SubscriptionManager is not listening for yet");return}p.connecting=!1,p.emitter.dispatchEvent({...f});return}this.masterSubEmitter?.dispatchEvent({type:"message",payload:o});const c=this.criteriaEntriesBySubscriptionId.get(sl(l.subscription));if(!c){console.warn("Received notification for criteria the SubscriptionManager is not listening for");return}c.emitter.dispatchEvent({type:"message",payload:o})}catch(r){console.error(r);const o={type:"error",payload:r};this.masterSubEmitter?.dispatchEvent(o);for(const l of this.getAllCriteriaEmitters())l.dispatchEvent({...o})}}),t.addEventListener("error",()=>{const n={type:"error",payload:new gt(D8(new Error("WebSocket error")))};this.masterSubEmitter?.dispatchEvent(n);for(const r of this.getAllCriteriaEmitters())r.dispatchEvent({...n})}),t.addEventListener("close",()=>{const n={type:"close"};this.masterSubEmitter?.dispatchEvent(n);for(const r of this.getAllCriteriaEmitters())r.dispatchEvent({...n});this.pingTimer&&(clearInterval(this.pingTimer),this.pingTimer=void 0,this.waitingForPong=!1),this.wsClosed&&(this.criteriaEntries.clear(),this.criteriaEntriesBySubscriptionId.clear(),this.masterSubEmitter?.removeAllListeners())}),t.addEventListener("open",()=>{const n={type:"open"};this.masterSubEmitter?.dispatchEvent(n);for(const r of this.getAllCriteriaEmitters())r.dispatchEvent({...n});this.refreshAllSubscriptions().catch(console.error),this.pingTimer||(this.pingTimer=setInterval(()=>{if(this.waitingForPong){this.waitingForPong=!1,t.reconnect();return}t.send(JSON.stringify({type:"ping"})),this.waitingForPong=!0},this.pingIntervalMs))}),this.medplum.addEventListener("change",()=>{const n=this.medplum.getProfile();this.currentProfile&&n===void 0?this.ws.close():n&&this.currentProfile?.id!==n.id&&this.ws.reconnect(),this.currentProfile=n})}emitError(t,n){const r={type:"error",payload:n};this.masterSubEmitter?.dispatchEvent(r),t.emitter.dispatchEvent({...r})}maybeEmitDisconnect(t){const{subscriptionId:n}=t;if(n){const r={type:"disconnect",payload:{subscriptionId:n}};this.masterSubEmitter?.dispatchEvent(r),t.emitter.dispatchEvent({...r})}else console.warn("Called disconnect for `CriteriaEntry` before `subscriptionId` was present.")}async getTokenForCriteria(t){let n=t?.subscriptionId;n||(n=(await this.medplum.createResource({...t.subscriptionProps,resourceType:"Subscription",status:"active",reason:`WebSocket subscription for ${Nt(this.medplum.getProfile())}`,channel:{type:"websocket"},criteria:t.criteria})).id);const{parameter:r}=await this.medplum.get(`fhir/R4/Subscription/${n}/$get-ws-binding-token`),o=r?.find(c=>c.name==="token")?.valueString,l=r?.find(c=>c.name==="websocket-url")?.valueUrl;if(!o)throw new gt(yn("Failed to get token"));if(!l)throw new gt(yn("Failed to get URL from $get-ws-binding-token"));return[n,o]}maybeGetCriteriaEntry(t,n){const r=this.criteriaEntries.get(t);if(r){if(!n)return r.bareCriteria;for(const o of r.criteriaWithProps)if(Ao(n,o.subscriptionProps))return o}}getAllCriteriaEmitters(){const t=[];for(const n of this.criteriaEntries.values()){n.bareCriteria&&t.push(n.bareCriteria.emitter);for(const r of n.criteriaWithProps)t.push(r.emitter)}return t}addCriteriaEntry(t){const{criteria:n,subscriptionProps:r}=t;let o;this.criteriaEntries.has(n)?o=this.criteriaEntries.get(n):(o={criteriaWithProps:[]},this.criteriaEntries.set(n,o)),r?o.criteriaWithProps.push(t):o.bareCriteria=t}removeCriteriaEntry(t){const{criteria:n,subscriptionProps:r,subscriptionId:o,token:l}=t;if(!this.criteriaEntries.has(n))return;const c=this.criteriaEntries.get(n);r?c.criteriaWithProps=c.criteriaWithProps.filter(d=>{const f=d.subscriptionProps;return!Ao(r,f)}):c.bareCriteria=void 0,!c.bareCriteria&&c.criteriaWithProps.length===0&&(this.criteriaEntries.delete(n),this.masterSubEmitter?._removeCriteria(n)),o&&this.criteriaEntriesBySubscriptionId.delete(o),l&&this.ws.readyState===WebSocket.OPEN&&this.ws.send(JSON.stringify({type:"unbind-from-token",payload:{token:l}}))}async subscribeToCriteria(t){if(!(this.ws.readyState!==WebSocket.OPEN||t.connecting)){t.connecting=!0;try{const[n,r]=await this.getTokenForCriteria(t);t.subscriptionId=n,t.token=r,this.criteriaEntriesBySubscriptionId.set(n,t),this.ws.send(JSON.stringify({type:"bind-with-token",payload:{token:r}}))}catch(n){console.error(Ye(n)),this.emitError(t,n),this.removeCriteriaEntry(t)}}}async refreshAllSubscriptions(){this.criteriaEntriesBySubscriptionId.clear();for(const t of this.criteriaEntries.values())for(const n of[...t.bareCriteria?[t.bareCriteria]:[],...t.criteriaWithProps])n.clearAttachedSubscription(),await this.subscribeToCriteria(n)}addCriteria(t,n){this.masterSubEmitter&&this.masterSubEmitter._addCriteria(t);const r=this.maybeGetCriteriaEntry(t,n);if(r)return r.refCount+=1,r.emitter;const o=new bV(t,n);return this.addCriteriaEntry(o),this.subscribeToCriteria(o).catch(console.error),o.emitter}removeCriteria(t,n){const r=this.maybeGetCriteriaEntry(t,n);if(!r){console.warn("Criteria not known to `SubscriptionManager`. Possibly called remove too many times.");return}r.refCount-=1,!(r.refCount>0)&&(this.maybeEmitDisconnect(r),this.removeCriteriaEntry(r))}getWebSocket(){return this.ws}closeWebSocket(){this.wsClosed||(this.wsClosed=!0,this.ws.close())}reconnectWebSocket(){this.ws.reconnect(),this.wsClosed=!1}getCriteriaCount(){return this.getAllCriteriaEmitters().length}getMasterEmitter(){return this.masterSubEmitter||(this.masterSubEmitter=new wx(...Array.from(this.criteriaEntries.keys()))),this.masterSubEmitter}}const ID="5.0.1-775185f",wV=on.FHIR_JSON+", */*; q=0.1",jV="https://api.medplum.com/",CV=1e3,EV=6e4,TV=0,RV=3e5,_V="Binary/",pT={resourceType:"Device",id:"system",deviceName:[{type:"model-name",name:"System"}]},xc={ClientCredentials:"client_credentials",AuthorizationCode:"authorization_code",RefreshToken:"refresh_token",JwtBearer:"urn:ietf:params:oauth:grant-type:jwt-bearer",TokenExchange:"urn:ietf:params:oauth:grant-type:token-exchange"},AV={AccessToken:"urn:ietf:params:oauth:token-type:access_token"},DV={JwtBearer:"urn:ietf:params:oauth:client-assertion-type:jwt-bearer"};class zD extends _m{options;fetch;createPdfImpl;storage;requestCache;cacheTime;baseUrl;fhirBaseUrl;authorizeUrl;tokenUrl;logoutUrl;fhircastHubUrl;defaultHeaders;onUnauthenticated;autoBatchTime;autoBatchQueue;refreshGracePeriod;subscriptionManager;medplumServer;clientId;clientSecret;credentialsInHeader;autoBatchTimerId;accessToken;accessTokenExpires;refreshToken;refreshPromise;profilePromise;sessionDetails;currentRateLimits;basicAuth;initPromise;initComplete=!0;keyValueClient;constructor(t){if(super(),t?.baseUrl&&!t.baseUrl.startsWith("http"))throw new Error("Base URL must start with http or https");this.options=t??{},this.fetch=t?.fetch??kV(),this.storage=t?.storage??new mV(void 0,t?.storagePrefix),this.createPdfImpl=t?.createPdf,this.baseUrl=I0(t?.baseUrl??jV),this.fhirBaseUrl=mo(this.baseUrl,t?.fhirUrlPath??"fhir/R4"),this.authorizeUrl=mo(this.baseUrl,t?.authorizeUrl??"oauth2/authorize"),this.tokenUrl=mo(this.baseUrl,t?.tokenUrl??"oauth2/token"),this.logoutUrl=mo(this.baseUrl,t?.logoutUrl??"oauth2/logout"),this.fhircastHubUrl=mo(this.baseUrl,t?.fhircastHubUrl??"fhircast/STU3"),this.clientId=t?.clientId??"",this.clientSecret=t?.clientSecret??"",this.credentialsInHeader=t?.authCredentialsMethod==="header",this.defaultHeaders=t?.defaultHeaders??{},this.onUnauthenticated=t?.onUnauthenticated,this.refreshGracePeriod=t?.refreshGracePeriod??RV,this.cacheTime=t?.cacheTime??(vo()?EV:TV),this.cacheTime>0?this.requestCache=new YA(t?.resourceCacheSize??CV):this.requestCache=void 0,t?.autoBatchTime?(this.autoBatchTime=t.autoBatchTime,this.autoBatchQueue=[]):(this.autoBatchTime=0,this.autoBatchQueue=void 0),t?.accessToken&&this.setAccessToken(t.accessToken),this.storage.getInitPromise===void 0?(t?.accessToken||this.attemptResumeActiveLogin().catch(console.error),this.initPromise=Promise.resolve(),this.dispatchEvent({type:"storageInitialized"})):(this.initComplete=!1,this.initPromise=this.storage.getInitPromise(),this.initPromise.then(()=>{t?.accessToken||this.attemptResumeActiveLogin().catch(console.error),this.initComplete=!0,this.dispatchEvent({type:"storageInitialized"})}).catch(n=>{console.error(n),this.initComplete=!0,this.dispatchEvent({type:"storageInitFailed",payload:{error:n}})})),this.setupStorageListener()}get isInitialized(){return this.initComplete}getInitPromise(){return this.initPromise}async attemptResumeActiveLogin(){const t=this.getActiveLogin();t&&(this.setAccessToken(t.accessToken,t.refreshToken),await this.refreshProfile())}getBaseUrl(){return this.baseUrl}getAuthorizeUrl(){return this.authorizeUrl}getTokenUrl(){return this.tokenUrl}getLogoutUrl(){return this.logoutUrl}getFhircastHubUrl(){return this.fhircastHubUrl}getDefaultHeaders(){return this.defaultHeaders}clear(){this.storage.clear(),vo()&&sessionStorage.clear(),this.clearActiveLogin()}clearActiveLogin(){this.storage.setString("activeLogin",void 0),this.requestCache?.clear(),this.accessToken=void 0,this.refreshToken=void 0,this.refreshPromise=void 0,this.accessTokenExpires=void 0,this.sessionDetails=void 0,this.medplumServer=void 0,this.dispatchEvent({type:"change"})}invalidateUrl(t){t=t.toString(),this.requestCache?.delete(t)}invalidateAll(){this.requestCache?.clear()}invalidateSearches(t){const n=mo(this.fhirBaseUrl,t);if(this.requestCache)for(const r of this.requestCache.keys())(r.endsWith(n)||r.includes(n+"?"))&&this.requestCache.delete(r)}get(t,n={}){t=t.toString();const r=this.getCacheEntry(t,n);if(r)return r.value;let o;t.startsWith(this.fhirBaseUrl)&&this.autoBatchQueue&&!n.disableAutoBatch?o=new Promise((c,d)=>{this.autoBatchQueue.push({method:"GET",url:t.replace(this.fhirBaseUrl,""),options:n,resolve:c,reject:d}),this.autoBatchTimerId||(this.autoBatchTimerId=setTimeout(()=>this.executeAutoBatch(),this.autoBatchTime))}):o=this.request("GET",t,n);const l=new Wi(o);return this.setCacheEntry(t,l),l}post(t,n,r,o={}){return t=t.toString(),this.setRequestBody(o,n),r&&this.setRequestContentType(o,r),this.invalidateUrl(t),this.request("POST",t,o)}put(t,n,r,o={}){return t=t.toString(),this.setRequestBody(o,n),r&&this.setRequestContentType(o,r),this.invalidateUrl(t),this.request("PUT",t,o)}patch(t,n,r={}){return t=t.toString(),this.setRequestBody(r,n),this.setRequestContentType(r,on.JSON_PATCH),this.invalidateUrl(t),this.request("PATCH",t,r)}delete(t,n){return t=t.toString(),this.invalidateUrl(t),this.request("DELETE",t,n)}async startNewUser(t,n){const{codeChallengeMethod:r,codeChallenge:o}=await this.startPkce();return this.post("auth/newuser",{...t,clientId:t.clientId??this.clientId,codeChallengeMethod:r,codeChallenge:o},void 0,n)}async startNewProject(t,n){return this.post("auth/newproject",t,void 0,n)}async startNewPatient(t,n){return this.post("auth/newpatient",t,void 0,n)}async startLogin(t,n){return this.post("auth/login",{...await this.ensureCodeChallenge(t),clientId:t.clientId??this.clientId,scope:t.scope},void 0,n)}async startGoogleLogin(t,n){return this.post("auth/google",{...await this.ensureCodeChallenge(t),clientId:t.clientId??this.clientId,scope:t.scope},void 0,n)}async ensureCodeChallenge(t){return t.codeChallenge?t:{...t,...await this.startPkce()}}async signOut(){await this.post(this.logoutUrl,{}),this.clear()}async signInWithRedirect(t){const r=new URLSearchParams(rr.getSearch()).get("code");if(!r){await this.requestAuthorization(t);return}return this.processCode(r)}signOutWithRedirect(){rr.assign(this.logoutUrl)}async signInWithExternalAuth(t,n,r,o,l=!0){let c=o;l&&(c=await this.ensureCodeChallenge(o)),rr.assign(this.getExternalAuthRedirectUri(t,n,r,c,l))}async exchangeExternalAccessToken(t,n){if(n=n??this.clientId,!n)throw new Error("MedplumClient is missing clientId");return this.fetchTokens({grant_type:xc.TokenExchange,subject_token_type:AV.AccessToken,client_id:n,subject_token:t})}getExternalAuthRedirectUri(t,n,r,o,l=!0){const c=new URL(t);if(c.searchParams.set("response_type","code"),c.searchParams.set("client_id",n),c.searchParams.set("redirect_uri",r),c.searchParams.set("scope",o.scope??"openid profile email"),c.searchParams.set("state",JSON.stringify(o)),l){const{codeChallenge:d,codeChallengeMethod:f}=o;if(!f)throw new Error("`LoginRequest` for external auth must include a `codeChallengeMethod`.");if(!d)throw new Error("`LoginRequest` for external auth must include a `codeChallenge`.");c.searchParams.set("code_challenge_method",f),c.searchParams.set("code_challenge",d)}return c.toString()}fhirUrl(...t){return new URL(mo(this.fhirBaseUrl,t.join("/")))}fhirSearchUrl(t,n){const r=this.fhirUrl(t);return n&&(r.search=wU(n)),r}search(t,n,r){const o=this.fhirSearchUrl(t,n),l="search-"+o.toString(),c=this.getCacheEntry(l,r);if(c)return c.value;const d=this.getBundle(o,r);return this.setCacheEntry(l,d),d}searchOne(t,n,r){const o=this.fhirSearchUrl(t,n);o.searchParams.set("_count","1"),o.searchParams.sort();const l="searchOne-"+o.toString(),c=this.getCacheEntry(l,r);if(c)return c.value;const d=new Wi(this.search(t,o.searchParams,r).then(f=>f.entry?.[0]?.resource));return this.setCacheEntry(l,d),d}searchResources(t,n,r){const l="searchResources-"+this.fhirSearchUrl(t,n).toString(),c=this.getCacheEntry(l,r);if(c)return c.value;const d=new Wi(this.search(t,n,r).then(gT));return this.setCacheEntry(l,d),d}async*searchResourcePages(t,n,r){let o=this.fhirSearchUrl(t,n);for(;o;){const l=new URL(o).searchParams;l.has("_count")||l.set("_count","1000");const c=await this.search(t,l,r),d=c.link?.find(f=>f.relation==="next");if(!c.entry?.length&&!d)break;yield gT(c),o=d?.url?new URL(d.url):void 0}}valueSetExpand(t,n){const r=this.fhirUrl("ValueSet","$expand");return r.search=new URLSearchParams(t).toString(),this.get(r.toString(),n)}getCached(t,n){const r=this.requestCache?.get(this.fhirUrl(t,n).toString())?.value;return r?.isOk()?r.read():void 0}getCachedReference(t){const n=t.reference;if(!n)return;if(n==="system")return pT;const[r,o]=n.split("/");if(!(!r||!o))return this.getCached(r,o)}readResource(t,n,r){if(!n)throw new Error('The "id" parameter cannot be null, undefined, or an empty string.');return this.get(this.fhirUrl(t,n),r)}readReference(t,n){const r=t.reference;if(!r)return new Wi(Promise.reject(new Error("Missing reference")));if(r==="system")return new Wi(Promise.resolve(pT));const[o,l]=r.split("/");return!o||!l?new Wi(Promise.reject(new Error("Invalid reference"))):this.readResource(o,l,n)}requestSchema(t){if(nD(t))return Promise.resolve();const n=t+"-requestSchema",r=this.getCacheEntry(n,void 0);if(r)return r.value;const o=new Wi((async()=>{const l=`{
|
|
91
|
+
*/const Ac={Event:typeof globalThis.Event<"u"?globalThis.Event:void 0,ErrorEvent:void 0,CloseEvent:void 0};let fT=!1;function vV(){if(typeof globalThis.Event>"u")throw new Error("Unable to lazy init events for ReconnectingWebSocket. globalThis.Event is not defined yet");Ac.Event=globalThis.Event,Ac.ErrorEvent=class extends Event{message;error;constructor(t,n){super("error",n),this.message=t.message,this.error=t}},Ac.CloseEvent=class extends Event{code;reason;wasClean=!0;constructor(t=1e3,n="",r){super("close",r),this.code=t,this.reason=n}}}function yV(e,t){if(!e)throw new Error(t)}function Rh(e){return new e.constructor(e.type,e)}const Fs={maxReconnectionDelay:1e4,minReconnectionDelay:1e3+Math.random()*4e3,minUptime:5e3,reconnectionDelayGrowFactor:1.3,connectionTimeout:4e3,maxRetries:1/0,maxEnqueuedMessages:1/0};let hT=!1;class os extends _m{_ws;_retryCount=-1;_uptimeTimeout;_connectTimeout;_shouldReconnect=!0;_connectLock=!1;_binaryType;_closeCalled=!1;_messageQueue=[];_debugLogger=console.log.bind(console);_url;_protocols;_options;constructor(t,n,r={}){fT||(vV(),fT=!0),super(),this._url=t,this._protocols=n,this._options=r,this._options.startClosed&&(this._shouldReconnect=!1),this._options.binaryType?this._binaryType=this._options.binaryType:this._binaryType="blob",this._options.debugLogger&&(this._debugLogger=this._options.debugLogger),this._connect()}static get CONNECTING(){return 0}static get OPEN(){return 1}static get CLOSING(){return 2}static get CLOSED(){return 3}get CONNECTING(){return os.CONNECTING}get OPEN(){return os.OPEN}get CLOSING(){return os.CLOSING}get CLOSED(){return os.CLOSED}get binaryType(){return this._ws?this._ws.binaryType:this._binaryType}set binaryType(t){this._binaryType=t,this._ws&&(this._ws.binaryType=t)}get retryCount(){return Math.max(this._retryCount,0)}get bufferedAmount(){return this._messageQueue.reduce((n,r)=>(typeof r=="string"?n+=r.length:r instanceof Blob?n+=r.size:n+=r.byteLength,n),0)+(this._ws?.bufferedAmount??0)}get extensions(){return this._ws?.extensions??""}get protocol(){return this._ws?.protocol??""}get readyState(){return this._ws?this._ws.readyState:this._options.startClosed?os.CLOSED:os.CONNECTING}get url(){return this._ws?this._ws.url:""}get shouldReconnect(){return this._shouldReconnect}onclose=null;onerror=null;onmessage=null;onopen=null;close(t=1e3,n){if(this._closeCalled=!0,this._shouldReconnect=!1,this._clearTimeouts(),!this._ws){this._debug("close enqueued: no ws instance");return}if(this._ws.readyState===this.CLOSED){this._debug("close: already closed");return}this._ws.close(t,n)}reconnect(t,n){this._shouldReconnect=!0,this._closeCalled=!1,this._retryCount=-1,!this._ws||this._ws.readyState===this.CLOSED?this._connect():(this._disconnect(t,n),this._connect())}send(t){if(this._ws&&this._ws.readyState===this.OPEN)this._debug("send",t),this._ws.send(t);else{const{maxEnqueuedMessages:n=Fs.maxEnqueuedMessages}=this._options;this._messageQueue.length<n&&(this._debug("enqueue",t),this._messageQueue.push(t))}}_debug(...t){this._options.debug&&this._debugLogger("RWS>",...t)}_getNextDelay(){const{reconnectionDelayGrowFactor:t=Fs.reconnectionDelayGrowFactor,minReconnectionDelay:n=Fs.minReconnectionDelay,maxReconnectionDelay:r=Fs.maxReconnectionDelay}=this._options;let o=0;return this._retryCount>0&&(o=n*Math.pow(t,this._retryCount-1),o>r&&(o=r)),this._debug("next delay",o),o}_wait(){return new Promise(t=>{setTimeout(t,this._getNextDelay())})}_connect(){if(this._connectLock||!this._shouldReconnect)return;this._connectLock=!0;const{maxRetries:t=Fs.maxRetries,connectionTimeout:n=Fs.connectionTimeout}=this._options;if(this._retryCount>=t){this._debug("max retries reached",this._retryCount,">=",t);return}this._retryCount++,this._debug("connect",this._retryCount),this._removeListeners(),this._wait().then(()=>{if(this._closeCalled){this._connectLock=!1;return}!this._options.WebSocket&&typeof WebSocket>"u"&&!hT&&(console.error("‼️ No WebSocket implementation available. You should define options.WebSocket."),hT=!0);const r=this._options.WebSocket||WebSocket;this._debug("connect",{url:this._url,protocols:this._protocols}),this._ws=this._protocols?new r(this._url,this._protocols):new r(this._url),this._ws.binaryType=this._binaryType,this._connectLock=!1,this._addListeners(),this._connectTimeout=setTimeout(()=>this._handleTimeout(),n)}).catch(r=>{this._connectLock=!1,this._handleError(new Ac.ErrorEvent(Error(r.message),this))})}_handleTimeout(){this._debug("timeout event"),this._handleError(new Ac.ErrorEvent(Error("TIMEOUT"),this))}_disconnect(t=1e3,n){if(this._clearTimeouts(),!!this._ws){this._removeListeners();try{this._ws.close(t,n),this._handleClose(new Ac.CloseEvent(t,n,this))}catch{}}}_acceptOpen(){this._debug("accept open"),this._retryCount=0}_handleOpen=t=>{this._debug("open event");const{minUptime:n=Fs.minUptime}=this._options;clearTimeout(this._connectTimeout),this._uptimeTimeout=setTimeout(()=>this._acceptOpen(),n),yV(this._ws,"WebSocket is not defined"),this._ws.binaryType=this._binaryType,this._messageQueue.forEach(r=>this._ws?.send(r)),this._messageQueue=[],this.onopen&&this.onopen(t),this.dispatchEvent(Rh(t))};_handleMessage=t=>{this._debug("message event"),this.onmessage&&this.onmessage(t),this.dispatchEvent(Rh(t))};_handleError=t=>{this._debug("error event",t.message),this._disconnect(void 0,t.message==="TIMEOUT"?"timeout":void 0),this.onerror&&this.onerror(t),this._debug("exec error listeners"),this.dispatchEvent(Rh(t)),this._connect()};_handleClose=t=>{this._debug("close event"),this._clearTimeouts(),this._shouldReconnect&&this._connect(),this.onclose&&this.onclose(t),this.dispatchEvent(Rh(t))};_removeListeners(){this._ws&&(this._debug("removeListeners"),this._ws.removeEventListener("open",this._handleOpen),this._ws.removeEventListener("close",this._handleClose),this._ws.removeEventListener("message",this._handleMessage),this._ws.removeEventListener("error",this._handleError))}_addListeners(){this._ws&&(this._debug("addListeners"),this._ws.addEventListener("open",this._handleOpen),this._ws.addEventListener("close",this._handleClose),this._ws.addEventListener("message",this._handleMessage),this._ws.addEventListener("error",this._handleError))}_clearTimeouts(){clearTimeout(this._connectTimeout),clearTimeout(this._uptimeTimeout)}}const xV=5e3;class wx extends _m{criteria;constructor(...t){super(),this.criteria=new Set(t)}getCriteria(){return this.criteria}_addCriteria(t){this.criteria.add(t)}_removeCriteria(t){this.criteria.delete(t)}}class bV{criteria;emitter;refCount;subscriptionProps;subscriptionId;token;connecting=!1;constructor(t,n){this.criteria=t,this.emitter=new wx(t),this.refCount=1,this.subscriptionProps=n?{...n}:void 0}clearAttachedSubscription(){this.subscriptionId=void 0,this.token=void 0}}class SV{medplum;ws;masterSubEmitter;criteriaEntries;criteriaEntriesBySubscriptionId;wsClosed;pingTimer=void 0;pingIntervalMs;waitingForPong=!1;currentProfile;constructor(t,n,r){if(!(t instanceof zD))throw new gt(yn("First arg of constructor should be a `MedplumClient`"));let o;try{o=new URL(n).toString()}catch{throw new gt(yn("Not a valid URL"))}const l=r?.ReconnectingWebSocket?new r.ReconnectingWebSocket(o,void 0,{debug:r?.debug,debugLogger:r?.debugLogger}):new os(o,void 0,{debug:r?.debug,debugLogger:r?.debugLogger});this.medplum=t,this.ws=l,this.masterSubEmitter=new wx,this.criteriaEntries=new Map,this.criteriaEntriesBySubscriptionId=new Map,this.wsClosed=!1,this.pingIntervalMs=r?.pingIntervalMs??xV,this.currentProfile=t.getProfile(),this.setupListeners()}setupListeners(){const t=this.ws;t.addEventListener("message",n=>{try{const r=JSON.parse(n.data);if(r.type==="pong"){this.waitingForPong=!1;return}const o=r,l=o?.entry?.[0]?.resource;if(l.type==="heartbeat"){this.masterSubEmitter?.dispatchEvent({type:"heartbeat",payload:o});return}if(l.type==="handshake"){const d=sl(l.subscription),f={type:"connect",payload:{subscriptionId:d}};this.masterSubEmitter?.dispatchEvent(f);const p=this.criteriaEntriesBySubscriptionId.get(d);if(!p){console.warn("Received handshake for criteria the SubscriptionManager is not listening for yet");return}p.connecting=!1,p.emitter.dispatchEvent({...f});return}this.masterSubEmitter?.dispatchEvent({type:"message",payload:o});const c=this.criteriaEntriesBySubscriptionId.get(sl(l.subscription));if(!c){console.warn("Received notification for criteria the SubscriptionManager is not listening for");return}c.emitter.dispatchEvent({type:"message",payload:o})}catch(r){console.error(r);const o={type:"error",payload:r};this.masterSubEmitter?.dispatchEvent(o);for(const l of this.getAllCriteriaEmitters())l.dispatchEvent({...o})}}),t.addEventListener("error",()=>{const n={type:"error",payload:new gt(D8(new Error("WebSocket error")))};this.masterSubEmitter?.dispatchEvent(n);for(const r of this.getAllCriteriaEmitters())r.dispatchEvent({...n})}),t.addEventListener("close",()=>{const n={type:"close"};this.masterSubEmitter?.dispatchEvent(n);for(const r of this.getAllCriteriaEmitters())r.dispatchEvent({...n});this.pingTimer&&(clearInterval(this.pingTimer),this.pingTimer=void 0,this.waitingForPong=!1),this.wsClosed&&(this.criteriaEntries.clear(),this.criteriaEntriesBySubscriptionId.clear(),this.masterSubEmitter?.removeAllListeners())}),t.addEventListener("open",()=>{const n={type:"open"};this.masterSubEmitter?.dispatchEvent(n);for(const r of this.getAllCriteriaEmitters())r.dispatchEvent({...n});this.refreshAllSubscriptions().catch(console.error),this.pingTimer||(this.pingTimer=setInterval(()=>{if(this.waitingForPong){this.waitingForPong=!1,t.reconnect();return}t.send(JSON.stringify({type:"ping"})),this.waitingForPong=!0},this.pingIntervalMs))}),this.medplum.addEventListener("change",()=>{const n=this.medplum.getProfile();this.currentProfile&&n===void 0?this.ws.close():n&&this.currentProfile?.id!==n.id&&this.ws.reconnect(),this.currentProfile=n})}emitError(t,n){const r={type:"error",payload:n};this.masterSubEmitter?.dispatchEvent(r),t.emitter.dispatchEvent({...r})}maybeEmitDisconnect(t){const{subscriptionId:n}=t;if(n){const r={type:"disconnect",payload:{subscriptionId:n}};this.masterSubEmitter?.dispatchEvent(r),t.emitter.dispatchEvent({...r})}else console.warn("Called disconnect for `CriteriaEntry` before `subscriptionId` was present.")}async getTokenForCriteria(t){let n=t?.subscriptionId;n||(n=(await this.medplum.createResource({...t.subscriptionProps,resourceType:"Subscription",status:"active",reason:`WebSocket subscription for ${Nt(this.medplum.getProfile())}`,channel:{type:"websocket"},criteria:t.criteria})).id);const{parameter:r}=await this.medplum.get(`fhir/R4/Subscription/${n}/$get-ws-binding-token`),o=r?.find(c=>c.name==="token")?.valueString,l=r?.find(c=>c.name==="websocket-url")?.valueUrl;if(!o)throw new gt(yn("Failed to get token"));if(!l)throw new gt(yn("Failed to get URL from $get-ws-binding-token"));return[n,o]}maybeGetCriteriaEntry(t,n){const r=this.criteriaEntries.get(t);if(r){if(!n)return r.bareCriteria;for(const o of r.criteriaWithProps)if(Ao(n,o.subscriptionProps))return o}}getAllCriteriaEmitters(){const t=[];for(const n of this.criteriaEntries.values()){n.bareCriteria&&t.push(n.bareCriteria.emitter);for(const r of n.criteriaWithProps)t.push(r.emitter)}return t}addCriteriaEntry(t){const{criteria:n,subscriptionProps:r}=t;let o;this.criteriaEntries.has(n)?o=this.criteriaEntries.get(n):(o={criteriaWithProps:[]},this.criteriaEntries.set(n,o)),r?o.criteriaWithProps.push(t):o.bareCriteria=t}removeCriteriaEntry(t){const{criteria:n,subscriptionProps:r,subscriptionId:o,token:l}=t;if(!this.criteriaEntries.has(n))return;const c=this.criteriaEntries.get(n);r?c.criteriaWithProps=c.criteriaWithProps.filter(d=>{const f=d.subscriptionProps;return!Ao(r,f)}):c.bareCriteria=void 0,!c.bareCriteria&&c.criteriaWithProps.length===0&&(this.criteriaEntries.delete(n),this.masterSubEmitter?._removeCriteria(n)),o&&this.criteriaEntriesBySubscriptionId.delete(o),l&&this.ws.readyState===WebSocket.OPEN&&this.ws.send(JSON.stringify({type:"unbind-from-token",payload:{token:l}}))}async subscribeToCriteria(t){if(!(this.ws.readyState!==WebSocket.OPEN||t.connecting)){t.connecting=!0;try{const[n,r]=await this.getTokenForCriteria(t);t.subscriptionId=n,t.token=r,this.criteriaEntriesBySubscriptionId.set(n,t),this.ws.send(JSON.stringify({type:"bind-with-token",payload:{token:r}}))}catch(n){console.error(Ye(n)),this.emitError(t,n),this.removeCriteriaEntry(t)}}}async refreshAllSubscriptions(){this.criteriaEntriesBySubscriptionId.clear();for(const t of this.criteriaEntries.values())for(const n of[...t.bareCriteria?[t.bareCriteria]:[],...t.criteriaWithProps])n.clearAttachedSubscription(),await this.subscribeToCriteria(n)}addCriteria(t,n){this.masterSubEmitter&&this.masterSubEmitter._addCriteria(t);const r=this.maybeGetCriteriaEntry(t,n);if(r)return r.refCount+=1,r.emitter;const o=new bV(t,n);return this.addCriteriaEntry(o),this.subscribeToCriteria(o).catch(console.error),o.emitter}removeCriteria(t,n){const r=this.maybeGetCriteriaEntry(t,n);if(!r){console.warn("Criteria not known to `SubscriptionManager`. Possibly called remove too many times.");return}r.refCount-=1,!(r.refCount>0)&&(this.maybeEmitDisconnect(r),this.removeCriteriaEntry(r))}getWebSocket(){return this.ws}closeWebSocket(){this.wsClosed||(this.wsClosed=!0,this.ws.close())}reconnectWebSocket(){this.ws.reconnect(),this.wsClosed=!1}getCriteriaCount(){return this.getAllCriteriaEmitters().length}getMasterEmitter(){return this.masterSubEmitter||(this.masterSubEmitter=new wx(...Array.from(this.criteriaEntries.keys()))),this.masterSubEmitter}}const ID="5.0.2-fa3244d",wV=on.FHIR_JSON+", */*; q=0.1",jV="https://api.medplum.com/",CV=1e3,EV=6e4,TV=0,RV=3e5,_V="Binary/",pT={resourceType:"Device",id:"system",deviceName:[{type:"model-name",name:"System"}]},xc={ClientCredentials:"client_credentials",AuthorizationCode:"authorization_code",RefreshToken:"refresh_token",JwtBearer:"urn:ietf:params:oauth:grant-type:jwt-bearer",TokenExchange:"urn:ietf:params:oauth:grant-type:token-exchange"},AV={AccessToken:"urn:ietf:params:oauth:token-type:access_token"},DV={JwtBearer:"urn:ietf:params:oauth:client-assertion-type:jwt-bearer"};class zD extends _m{options;fetch;createPdfImpl;storage;requestCache;cacheTime;baseUrl;fhirBaseUrl;authorizeUrl;tokenUrl;logoutUrl;fhircastHubUrl;defaultHeaders;onUnauthenticated;autoBatchTime;autoBatchQueue;refreshGracePeriod;subscriptionManager;medplumServer;clientId;clientSecret;credentialsInHeader;autoBatchTimerId;accessToken;accessTokenExpires;refreshToken;refreshPromise;profilePromise;sessionDetails;currentRateLimits;basicAuth;initPromise;initComplete=!0;keyValueClient;constructor(t){if(super(),t?.baseUrl&&!t.baseUrl.startsWith("http"))throw new Error("Base URL must start with http or https");this.options=t??{},this.fetch=t?.fetch??kV(),this.storage=t?.storage??new mV(void 0,t?.storagePrefix),this.createPdfImpl=t?.createPdf,this.baseUrl=I0(t?.baseUrl??jV),this.fhirBaseUrl=mo(this.baseUrl,t?.fhirUrlPath??"fhir/R4"),this.authorizeUrl=mo(this.baseUrl,t?.authorizeUrl??"oauth2/authorize"),this.tokenUrl=mo(this.baseUrl,t?.tokenUrl??"oauth2/token"),this.logoutUrl=mo(this.baseUrl,t?.logoutUrl??"oauth2/logout"),this.fhircastHubUrl=mo(this.baseUrl,t?.fhircastHubUrl??"fhircast/STU3"),this.clientId=t?.clientId??"",this.clientSecret=t?.clientSecret??"",this.credentialsInHeader=t?.authCredentialsMethod==="header",this.defaultHeaders=t?.defaultHeaders??{},this.onUnauthenticated=t?.onUnauthenticated,this.refreshGracePeriod=t?.refreshGracePeriod??RV,this.cacheTime=t?.cacheTime??(vo()?EV:TV),this.cacheTime>0?this.requestCache=new YA(t?.resourceCacheSize??CV):this.requestCache=void 0,t?.autoBatchTime?(this.autoBatchTime=t.autoBatchTime,this.autoBatchQueue=[]):(this.autoBatchTime=0,this.autoBatchQueue=void 0),t?.accessToken&&this.setAccessToken(t.accessToken),this.storage.getInitPromise===void 0?(t?.accessToken||this.attemptResumeActiveLogin().catch(console.error),this.initPromise=Promise.resolve(),this.dispatchEvent({type:"storageInitialized"})):(this.initComplete=!1,this.initPromise=this.storage.getInitPromise(),this.initPromise.then(()=>{t?.accessToken||this.attemptResumeActiveLogin().catch(console.error),this.initComplete=!0,this.dispatchEvent({type:"storageInitialized"})}).catch(n=>{console.error(n),this.initComplete=!0,this.dispatchEvent({type:"storageInitFailed",payload:{error:n}})})),this.setupStorageListener()}get isInitialized(){return this.initComplete}getInitPromise(){return this.initPromise}async attemptResumeActiveLogin(){const t=this.getActiveLogin();t&&(this.setAccessToken(t.accessToken,t.refreshToken),await this.refreshProfile())}getBaseUrl(){return this.baseUrl}getAuthorizeUrl(){return this.authorizeUrl}getTokenUrl(){return this.tokenUrl}getLogoutUrl(){return this.logoutUrl}getFhircastHubUrl(){return this.fhircastHubUrl}getDefaultHeaders(){return this.defaultHeaders}clear(){this.storage.clear(),vo()&&sessionStorage.clear(),this.clearActiveLogin()}clearActiveLogin(){this.storage.setString("activeLogin",void 0),this.requestCache?.clear(),this.accessToken=void 0,this.refreshToken=void 0,this.refreshPromise=void 0,this.accessTokenExpires=void 0,this.sessionDetails=void 0,this.medplumServer=void 0,this.dispatchEvent({type:"change"})}invalidateUrl(t){t=t.toString(),this.requestCache?.delete(t)}invalidateAll(){this.requestCache?.clear()}invalidateSearches(t){const n=mo(this.fhirBaseUrl,t);if(this.requestCache)for(const r of this.requestCache.keys())(r.endsWith(n)||r.includes(n+"?"))&&this.requestCache.delete(r)}get(t,n={}){t=t.toString();const r=this.getCacheEntry(t,n);if(r)return r.value;let o;t.startsWith(this.fhirBaseUrl)&&this.autoBatchQueue&&!n.disableAutoBatch?o=new Promise((c,d)=>{this.autoBatchQueue.push({method:"GET",url:t.replace(this.fhirBaseUrl,""),options:n,resolve:c,reject:d}),this.autoBatchTimerId||(this.autoBatchTimerId=setTimeout(()=>this.executeAutoBatch(),this.autoBatchTime))}):o=this.request("GET",t,n);const l=new Wi(o);return this.setCacheEntry(t,l),l}post(t,n,r,o={}){return t=t.toString(),this.setRequestBody(o,n),r&&this.setRequestContentType(o,r),this.invalidateUrl(t),this.request("POST",t,o)}put(t,n,r,o={}){return t=t.toString(),this.setRequestBody(o,n),r&&this.setRequestContentType(o,r),this.invalidateUrl(t),this.request("PUT",t,o)}patch(t,n,r={}){return t=t.toString(),this.setRequestBody(r,n),this.setRequestContentType(r,on.JSON_PATCH),this.invalidateUrl(t),this.request("PATCH",t,r)}delete(t,n){return t=t.toString(),this.invalidateUrl(t),this.request("DELETE",t,n)}async startNewUser(t,n){const{codeChallengeMethod:r,codeChallenge:o}=await this.startPkce();return this.post("auth/newuser",{...t,clientId:t.clientId??this.clientId,codeChallengeMethod:r,codeChallenge:o},void 0,n)}async startNewProject(t,n){return this.post("auth/newproject",t,void 0,n)}async startNewPatient(t,n){return this.post("auth/newpatient",t,void 0,n)}async startLogin(t,n){return this.post("auth/login",{...await this.ensureCodeChallenge(t),clientId:t.clientId??this.clientId,scope:t.scope},void 0,n)}async startGoogleLogin(t,n){return this.post("auth/google",{...await this.ensureCodeChallenge(t),clientId:t.clientId??this.clientId,scope:t.scope},void 0,n)}async ensureCodeChallenge(t){return t.codeChallenge?t:{...t,...await this.startPkce()}}async signOut(){await this.post(this.logoutUrl,{}),this.clear()}async signInWithRedirect(t){const r=new URLSearchParams(rr.getSearch()).get("code");if(!r){await this.requestAuthorization(t);return}return this.processCode(r)}signOutWithRedirect(){rr.assign(this.logoutUrl)}async signInWithExternalAuth(t,n,r,o,l=!0){let c=o;l&&(c=await this.ensureCodeChallenge(o)),rr.assign(this.getExternalAuthRedirectUri(t,n,r,c,l))}async exchangeExternalAccessToken(t,n){if(n=n??this.clientId,!n)throw new Error("MedplumClient is missing clientId");return this.fetchTokens({grant_type:xc.TokenExchange,subject_token_type:AV.AccessToken,client_id:n,subject_token:t})}getExternalAuthRedirectUri(t,n,r,o,l=!0){const c=new URL(t);if(c.searchParams.set("response_type","code"),c.searchParams.set("client_id",n),c.searchParams.set("redirect_uri",r),c.searchParams.set("scope",o.scope??"openid profile email"),c.searchParams.set("state",JSON.stringify(o)),l){const{codeChallenge:d,codeChallengeMethod:f}=o;if(!f)throw new Error("`LoginRequest` for external auth must include a `codeChallengeMethod`.");if(!d)throw new Error("`LoginRequest` for external auth must include a `codeChallenge`.");c.searchParams.set("code_challenge_method",f),c.searchParams.set("code_challenge",d)}return c.toString()}fhirUrl(...t){return new URL(mo(this.fhirBaseUrl,t.join("/")))}fhirSearchUrl(t,n){const r=this.fhirUrl(t);return n&&(r.search=wU(n)),r}search(t,n,r){const o=this.fhirSearchUrl(t,n),l="search-"+o.toString(),c=this.getCacheEntry(l,r);if(c)return c.value;const d=this.getBundle(o,r);return this.setCacheEntry(l,d),d}searchOne(t,n,r){const o=this.fhirSearchUrl(t,n);o.searchParams.set("_count","1"),o.searchParams.sort();const l="searchOne-"+o.toString(),c=this.getCacheEntry(l,r);if(c)return c.value;const d=new Wi(this.search(t,o.searchParams,r).then(f=>f.entry?.[0]?.resource));return this.setCacheEntry(l,d),d}searchResources(t,n,r){const l="searchResources-"+this.fhirSearchUrl(t,n).toString(),c=this.getCacheEntry(l,r);if(c)return c.value;const d=new Wi(this.search(t,n,r).then(gT));return this.setCacheEntry(l,d),d}async*searchResourcePages(t,n,r){let o=this.fhirSearchUrl(t,n);for(;o;){const l=new URL(o).searchParams;l.has("_count")||l.set("_count","1000");const c=await this.search(t,l,r),d=c.link?.find(f=>f.relation==="next");if(!c.entry?.length&&!d)break;yield gT(c),o=d?.url?new URL(d.url):void 0}}valueSetExpand(t,n){const r=this.fhirUrl("ValueSet","$expand");return r.search=new URLSearchParams(t).toString(),this.get(r.toString(),n)}getCached(t,n){const r=this.requestCache?.get(this.fhirUrl(t,n).toString())?.value;return r?.isOk()?r.read():void 0}getCachedReference(t){const n=t.reference;if(!n)return;if(n==="system")return pT;const[r,o]=n.split("/");if(!(!r||!o))return this.getCached(r,o)}readResource(t,n,r){if(!n)throw new Error('The "id" parameter cannot be null, undefined, or an empty string.');return this.get(this.fhirUrl(t,n),r)}readReference(t,n){const r=t.reference;if(!r)return new Wi(Promise.reject(new Error("Missing reference")));if(r==="system")return new Wi(Promise.resolve(pT));const[o,l]=r.split("/");return!o||!l?new Wi(Promise.reject(new Error("Invalid reference"))):this.readResource(o,l,n)}requestSchema(t){if(nD(t))return Promise.resolve();const n=t+"-requestSchema",r=this.getCacheEntry(n,void 0);if(r)return r.value;const o=new Wi((async()=>{const l=`{
|
|
92
92
|
StructureDefinitionList(_filter: "name eq ${t}") {
|
|
93
93
|
resourceType,
|
|
94
94
|
name,
|
|
@@ -612,4 +612,4 @@ In order to be iterable, non-array objects must have a [Symbol.iterator]() metho
|
|
|
612
612
|
}
|
|
613
613
|
]
|
|
614
614
|
}`,_ne="MSH|^~\\&|ADT1|MCM|LABADT|MCM|198808181126|SECURITY|ADT|MSG00001|P|2.1\rPID|||PATID1234^5^M11||JONES^WILLIAM^A^III||19610615|M-||C|1200 N ELM STREET^^GREENSBORO^NC^27401-1020|GL|(919)379-1212|(919)271-3434||S||PATID12345001^2^M10|123456789|987654^NC\rNK1|1|JONES^BARBARA^K|SPO|||||20011105\rPV1|1|I|2000^2012^01||||004777^LEBAUER^SIDNEY^J.|||SUR||-||1|A0-";function Ane(){const e=_e(),{id:t}=Ft(),[n,r]=v.useState(),[o,l]=v.useState(),[c,d]=v.useState(),[f,p]=v.useState(Rne),[m,g]=v.useState(_ne),[y,b]=v.useState(on.FHIR_JSON),w=v.useRef(null),j=v.useRef(null),[C,T]=v.useState(!1);v.useEffect(()=>{e.readResource("Bot",t).then(async P=>{r(P),l(P.runtimeVersion==="vmcontext"?"commonjs":"esnext"),d(await Dne(e,P))}).catch(P=>ke({color:"red",message:Ye(P),autoClose:!1}))},[e,t]);const E=v.useCallback(async()=>cd(w.current,{command:"getValue"}),[]),R=v.useCallback(async()=>cd(w.current,{command:"getOutput"}),[]),_=v.useCallback(async()=>y===on.FHIR_JSON?JSON.parse(f):m,[y,f,m]),k=v.useCallback(async P=>{P.preventDefault(),P.stopPropagation(),T(!0);try{const U=await E(),B=await R(),Y=await e.createAttachment({data:U,filename:"index.ts",contentType:on.TYPESCRIPT}),X=await e.createAttachment({data:B,filename:o==="commonjs"?"index.cjs":"index.mjs",contentType:on.JAVASCRIPT}),te=[{op:"add",path:"/sourceCode",value:Y},{op:"add",path:"/executableCode",value:X}];await e.patchResource("Bot",t,te),ke({color:"green",message:"Saved"})}catch(U){ke({color:"red",message:Ye(U),autoClose:!1})}finally{T(!1)}},[e,t,o,E,R]),L=v.useCallback(async P=>{P.preventDefault(),P.stopPropagation(),T(!0);try{await e.post(e.fhirUrl("Bot",t,"$deploy")),ke({color:"green",message:"Deployed"})}catch(U){ke({color:"red",message:Ye(U),autoClose:!1})}finally{T(!1)}},[e,t]),D=v.useCallback(async P=>{P.preventDefault(),P.stopPropagation(),T(!0);try{const U=await _(),B=await e.post(e.fhirUrl("Bot",t,"$execute"),U,y);await cd(j.current,{command:"setValue",value:B}),ke({color:"green",message:"Success"})}catch(U){ke({color:"red",message:Ye(U),autoClose:!1})}finally{T(!1)}},[e,t,_,y]);return!n||c===void 0?null:a.jsxs(Sr,{m:0,gutter:0,style:{overflow:"hidden"},children:[a.jsx(Sr.Col,{span:8,children:a.jsxs(Dr,{m:2,pb:"xs",pr:"xs",pt:"xs",shadow:"md",mih:400,children:[a.jsx(Tne,{iframeRef:w,language:"typescript",module:o,testId:"code-frame",defaultValue:c,minHeight:"528px"}),a.jsxs(xe,{justify:"flex-end",gap:"xs",children:[a.jsx(De,{type:"button",onClick:k,loading:C,leftSection:a.jsx(jH,{size:"1rem"}),children:"Save"}),a.jsx(De,{type:"button",onClick:L,loading:C,leftSection:a.jsx(eS,{size:"1rem"}),children:"Deploy"}),a.jsx(De,{type:"button",onClick:D,loading:C,leftSection:a.jsx(uq,{size:"1rem"}),children:"Execute"})]})]})}),a.jsxs(Sr.Col,{span:4,children:[a.jsxs(Dr,{m:2,pb:"xs",pr:"xs",pt:"xs",shadow:"md",children:[a.jsx(cn,{data:[{label:"FHIR",value:on.FHIR_JSON},{label:"HL7",value:on.HL7_V2}],onChange:P=>b(P.currentTarget.value)}),y===on.FHIR_JSON?a.jsx(Zc,{value:f,onChange:P=>p(P),autosize:!0,minRows:15}):a.jsx("textarea",{className:Cne.hl7Input,value:m,onChange:P=>g(P.currentTarget.value),rows:15})]}),a.jsx(Dr,{m:2,p:"xs",shadow:"md",children:a.jsx(Ene,{iframeRef:j,className:"medplum-bot-output-frame",testId:"output-frame",minHeight:"200px"})})]})]})}async function Dne(e,t){if(t.sourceCode?.url){const n=t.sourceCode.url?.split("/")?.find(mD);return(await e.download(e.fhirUrl("Binary",n))).text()}return t.code??""}function Al(e){let t=e.meta;return t&&(t={...t,lastUpdated:void 0,versionId:void 0,author:void 0}),{...e,meta:t}}function kne(){const e=_e(),{resourceType:t,id:n}=Ft(),r={reference:t+"/"+n},o=v.useCallback(l=>{e.updateResource(Al(l)).then(()=>{ke({color:"green",message:"Success"})}).catch(c=>{ke({color:"red",message:Ye(c),autoClose:!1})})},[e]);switch(t){case"PlanDefinition":return a.jsx(dt,{children:a.jsx(dK,{value:r,onSubmit:o})});case"Questionnaire":return a.jsx(dt,{children:a.jsx($K,{questionnaire:r,onSubmit:o})});default:return null}}function Pne(){const{resourceType:e,id:t}=Ft(),n=Kt({reference:e+"/"+t}),r=Tn();return n?a.jsx(dt,{children:a.jsx(hX,{value:n,onStart:(o,l)=>r(`/forms/${sl(l)}`)?.catch(console.error),onEdit:(o,l,c)=>r(`/${c.reference}}`)?.catch(console.error)})}):null}function One(){const e=_e(),{resourceType:t,id:n}=Ft(),r=Tn();return a.jsxs(dt,{children:[a.jsxs("p",{children:["Are you sure you want to delete this ",t,"?"]}),a.jsx(De,{color:"red",onClick:()=>{e.deleteResource(t,n).then(()=>r(`/${t}`)?.catch(console.error)).catch(o=>ke({color:"red",message:Ye(o),autoClose:!1}))},children:"Delete"})]})}const Nne="_selectProfileBtn_tbaz6_1",Mne="_chevron_tbaz6_13",qR={selectProfileBtn:Nne,chevron:Mne};function Lne(){const{resourceType:e,id:t}=Ft(),n=Kt({reference:e+"/"+t}),[r,o]=v.useState(),l=bl({onDropdownClose:()=>l.resetSelectedOption()}),c=v.useMemo(()=>{if(Dn(n?.meta?.profile))return[a.jsx(Ke.Option,{value:"",children:"None"},""),...n.meta.profile.map(f=>a.jsx(Ke.Option,{value:f,children:f},f))]},[n?.meta?.profile]);if(v.useEffect(()=>{n?.meta?.profile?.length===1&&o(n.meta.profile[0])},[n?.meta?.profile]),!n)return null;let d;return Dn(c)&&(d=a.jsx(xe,{justify:"flex-end",children:a.jsxs(Ue,{align:"flex-end",gap:"xs",children:[a.jsxs(Ke,{store:l,width:250,position:"bottom-end",withinPortal:!1,onOptionSubmit:f=>{o(f),l.closeDropdown()},children:[a.jsx(Ke.Target,{children:a.jsx(ar,{onClick:()=>l.toggleDropdown(),children:a.jsxs(Id,{fw:"bold",fs:"sm",className:qR.selectProfileBtn,children:[a.jsx("span",{children:"Pick profile"}),a.jsx(Z0,{stroke:1.5,className:qR.chevron})]})})}),a.jsx(Ke.Dropdown,{w:"max-content",children:a.jsx(Ke.Options,{children:c})})]}),a.jsx(ue,{children:r?a.jsxs(a.Fragment,{children:[a.jsx(Re,{span:!0,size:"sm",c:"dimmed",children:"Displaying profile: "}),a.jsx(Re,{span:!0,size:"sm",children:r||"Nothing selected"})]}):a.jsx(Re,{span:!0,size:"sm",c:"dimmed",children:"No profile displayed"})})]})})),a.jsx(dt,{children:a.jsxs(Ue,{gap:"xl",children:[d,a.jsx(gS,{value:n,profileUrl:r})]})})}function Ine(){const e=_e(),{resourceType:t,id:n}=Ft(),[r,o]=v.useState(),[l,c]=v.useState(),d=Tn(),[f,p]=v.useState();v.useEffect(()=>{e.readResource(t,n).then(b=>{o(ui(b)),c(ui(b))}).catch(b=>{p(Yt(b)),ke({color:"red",message:Ye(b),autoClose:!1})})},[e,t,n]);const m=v.useCallback(b=>{p(void 0),e.updateResource(Al(b)).then(()=>{d(`/${t}/${n}/details`)?.catch(console.error),ke({id:"succes",color:"green",message:"Success"})}).catch(w=>{p(Yt(w)),ke({color:"red",message:Ye(w),autoClose:!1})})},[e,t,n,d]),g=v.useCallback(b=>{p(void 0);const w=zk.createPatch(r,b);e.patchResource(t,n,w).then(()=>{d(`/${t}/${n}/details`)?.catch(console.error),ke({id:"succes",color:"green",message:"Success"})}).catch(j=>{p(Yt(j)),ke({color:"red",message:Ye(j),autoClose:!1})})},[e,t,n,r,d]),y=v.useCallback(()=>d(`/${t}/${n}/delete`)?.catch(console.error),[d,t,n]);return l?a.jsx(dt,{children:a.jsx(Tp,{defaultValue:l,onSubmit:m,onPatch:g,onDelete:y,outcome:f})}):null}function zne(){const{resourceType:e,id:t}=Ft(),n=Kt({reference:e+"/"+t});return n?a.jsx(dt,{maw:700,children:n.resourceType==="Patient"?a.jsx(oK,{patient:n}):a.jsx(Ta,{icon:a.jsx(Cl,{size:16}),title:"Unsupported export type",color:"red",children:"This page is only supported for Patient resources"})}):null}function XP({resource:e,currentProfile:t,onChange:n}){const r=e.resourceType,o=_e(),[l,c]=v.useState();return v.useEffect(()=>{o.searchResources("StructureDefinition",{type:r,derivation:"constraint",_count:50}).then(d=>{c(d.filter(RW))}).catch(console.error)},[o,n,r]),a.jsx(kt,{value:t?.url,onChange:d=>{const f=l?.find(p=>p.url===d);f&&n(f)},children:a.jsx(kt.List,{children:l?.map(d=>{const f=e.meta?.profile?.includes(d.url),p=f?"This profile is present in this resource's meta.profile property.":"This profile is not included in this resource's meta.profile property.";return a.jsx(kt.Tab,{value:d.url,title:p,rightSection:f&&a.jsx(A0,{variant:"outline",color:"green",size:"xs",style:{borderStyle:"none"},children:a.jsx(Vq,{size:"90%"})}),children:d.title||d.name},d.url)})})})}function JP(e,t){const n=_e(),r=Tn();return{defaultValue:{resourceType:e},handleSubmit:c=>{t&&t(void 0),n.createResource(c).then(d=>r("/"+d.resourceType+"/"+d.id)).catch(d=>{t&&t(Yt(d)),ke({color:"red",message:Ye(d),autoClose:!1,styles:{description:{whiteSpace:"pre-line"}}})})}}}function Xy(){const{resourceType:e}=Ft(),t=Kr(),[n,r]=v.useState(),{defaultValue:o,handleSubmit:l}=JP(e,r),[c,d]=v.useState(),f=t.pathname.toLowerCase().endsWith("profiles"),p=v.useCallback(m=>{const g=Al(m);c&&bD(g,c.url),l(g)},[c,l]);return f?a.jsx(dt,{children:a.jsxs(Ue,{children:[a.jsx(XP,{resource:o,currentProfile:c,onChange:d}),c?a.jsx(Tp,{defaultValue:o,onSubmit:p,outcome:n,profileUrl:c.url},c.url):a.jsx(Re,{my:"lg",fz:"lg",fs:"italic",ta:"center",children:"Select a profile above"})]})}):a.jsx(dt,{children:a.jsx(Tp,{defaultValue:o,onSubmit:l,outcome:n})})}function GR(){const e=_e(),{resourceType:t,id:n}=Ft(),r=e.readHistory(t,n).read();return a.jsx(dt,{children:a.jsx(zX,{history:r})})}function $ne(){const{resourceType:e}=Ft(),[t,n]=v.useState(),{defaultValue:r,handleSubmit:o}=JP(e,n),l=v.useCallback(c=>{o(JSON.parse(c["new-resource"]))},[o]);return a.jsxs(dt,{children:[t&&a.jsx(Cr,{outcome:t}),a.jsxs(pt,{onSubmit:l,children:[a.jsx(Zc,{name:"new-resource","data-testid":"create-resource-json",autosize:!0,minRows:24,defaultValue:to(r,!0),formatOnBlur:!0,deserialize:JSON.parse}),a.jsx(xe,{justify:"flex-end",mt:"xl",wrap:"nowrap",children:a.jsx(De,{type:"submit",children:"OK"})})]})]})}function Une(){const e=_e(),{resourceType:t,id:n}=Ft(),r=Kt({reference:t+"/"+n}),o=Tn(),[l,c]=v.useState(),d=v.useCallback(f=>{e.updateResource(Al(JSON.parse(f.resource))).then(()=>{c(void 0),o(`/${t}/${n}/details`)?.catch(console.error),ke({color:"green",message:"Success"})}).catch(p=>{ke({color:"red",message:Ye(p),autoClose:!1})})},[e,t,n,o]);return r?a.jsxs(dt,{children:[l&&a.jsx(Cr,{outcome:l}),a.jsxs(pt,{onSubmit:d,children:[a.jsx(Zc,{name:"resource","data-testid":"resource-json",autosize:!0,minRows:24,defaultValue:to(r,!0),formatOnBlur:!0,deserialize:JSON.parse}),a.jsx(xe,{justify:"flex-end",mt:"xl",wrap:"nowrap",children:a.jsx(De,{type:"submit",children:"OK"})})]})]}):null}function Bne(){const{resourceType:e,id:t}=Ft();return Kt({reference:e+"/"+t})?a.jsxs(dt,{children:[a.jsxs(Ta,{icon:a.jsx(Cl,{size:16}),mb:"xl",children:["This is just a preview! Access your form here:",a.jsx("br",{}),a.jsx(Mt,{href:`/forms/${t}`,children:`/forms/${t}`})]}),a.jsx(iP,{questionnaire:{reference:e+"/"+t},onSubmit:()=>alert("You submitted the preview")})]}):null}function Vne(){const e=_e(),{resourceType:t,id:n}=Ft(),[r,o]=v.useState(),[l,c]=v.useState();return v.useEffect(()=>{e.readResource(t,n).then(d=>o(ui(d))).catch(d=>{ke({color:"red",message:Ye(d)})})},[e,t,n]),r?a.jsxs(dt,{children:[a.jsxs(Le,{order:2,children:["Available ",t," profiles"]}),a.jsx(Ue,{children:a.jsxs(a.Fragment,{children:[a.jsx(XP,{resource:r,currentProfile:l,onChange:c}),l?a.jsx(Fne,{profile:l,resource:r,onResourceUpdated:d=>o(d)},l.url):a.jsx(Re,{my:"lg",fz:"lg",fs:"italic",ta:"center",children:"Select a profile above"})]})})]}):null}const Fne=({profile:e,resource:t,onResourceUpdated:n})=>{const r=_e(),[o,l]=v.useState(),[c,d]=v.useState(()=>t.meta?.profile?.includes(e.url)),f=v.useCallback(p=>{l(void 0);const m=Al(p);c?bD(m,e.url):jU(m,e.url),r.updateResource(m).then(g=>{n(g),ke({color:"green",message:"Success"})}).catch(g=>{l(Yt(g)),ke({color:"red",message:Ye(g),autoClose:!1})})},[r,e.url,n,c]);return a.jsxs(Ue,{children:[a.jsx(Fd,{size:"md",checked:c,label:`Conform resource to ${e.title}`,onChange:p=>d(p.currentTarget.checked),"data-testid":"profile-toggle"}),c?a.jsx(Tp,{profileUrl:e.url,defaultValue:t,onSubmit:f,outcome:o}):a.jsx("form",{noValidate:!0,onSubmit:p=>{p.preventDefault(),f(t)},children:a.jsx(xe,{justify:"flex-end",mt:"xl",children:a.jsx(De,{type:"submit",children:"OK"})})})]})},ZP={"Create Only":"create","Update Only":"update","Delete Only":"delete","All Interactions":void 0},Hne=Object.keys(ZP);function qne(){const e=_e(),{id:t}=Ft(),n=Kt({reference:`Questionnaire/${t}`}),[r,o]=v.useState(),[l,c]=v.useState("create"),[d,f]=v.useState(0),p=e.searchResources("Subscription","status=active&_count=100").read().filter(g=>Gne(g,n));function m(){r&&n&&e.createResource({resourceType:"Subscription",status:"active",reason:`Connect bot ${r.name} to questionnaire responses`,criteria:`QuestionnaireResponse?questionnaire=${n.url?`${n.url},${Nt(n)}`:Nt(n)}`,channel:{type:"rest-hook",endpoint:Nt(r)},...l?{extension:[{url:"https://medplum.com/fhir/StructureDefinition/subscription-supported-interaction",valueCode:l}]}:void 0}).then(()=>{o(void 0),f(Date.now()),e.invalidateSearches("Subscription"),ke({color:"green",message:"Success"})}).catch(g=>ke({color:"red",message:Ye(g),autoClose:!1}))}return a.jsxs(dt,{children:[a.jsx(Le,{children:"Bots"}),a.jsxs(Ue,{children:[p.length===0&&a.jsx("p",{children:"No bots found."}),p.map(g=>a.jsxs("div",{children:[a.jsx("h3",{children:a.jsx(Rl,{value:{reference:g.channel?.endpoint},link:!0})}),a.jsxs("p",{children:["Criteria: ",g.criteria]})]},g.id))]}),a.jsx(Cn,{}),a.jsxs(Ue,{mt:10,children:[a.jsx(kd,{size:"lg",htmlFor:"bot",children:"Connect to bot"}),a.jsxs(xe,{children:[a.jsx(Tl,{name:"bot",resourceType:"Bot",onChange:g=>o(g)}),a.jsx(De,{onClick:m,children:"Connect"})]}),a.jsx(xe,{children:a.jsx(cn,{name:"subscription-trigger-event",defaultValue:"Create Only",label:"Subscription Trigger Event",data:Hne,onChange:g=>c(ZP[g.target.value])})})]}),a.jsx("div",{style:{display:"none"},children:d})]})}function Gne(e,t){if(!t)return!1;const n=e.criteria||"",r=e.channel?.endpoint||"";return n.startsWith("QuestionnaireResponse?")&&r.startsWith("Bot/")&&(n.includes(Nt(t))||(t.url?n.includes(t.url):!1))}function Wne(){const{id:e}=Ft(),t=Tn(),r=_e().readReference({reference:`Questionnaire/${e}`}).read(),[o,l]=v.useState({resourceType:"QuestionnaireResponse",filters:[{code:"questionnaire",operator:fe.EQUALS,value:r.url?`${r.url},Questionnaire/${e}`:`Questionnaire/${e}`}],fields:["id","_lastUpdated"]});return a.jsx(dt,{children:a.jsx(su,{search:o,onClick:c=>t(`/${c.resource.resourceType}/${c.resource.id}`)?.catch(console.error),onChange:c=>l(c.definition),hideFilters:!0,hideToolbar:!0})})}function Qne(){const e=_e(),{resourceType:t,id:n}=Ft(),r=Kt({reference:t+"/"+n}),o=v.useCallback(l=>{e.updateResource(Al(l)).then(()=>{ke({color:"green",message:"Success"})}).catch(c=>{ke({color:"red",message:Ye(c),autoClose:!1})})},[e]);return r?a.jsx(dt,{children:a.jsx(oX,{onSubmit:o,definition:r})}):null}function Yne(){const{resourceType:e,id:t}=Ft(),n=Kt({reference:e+"/"+t});return n?a.jsx(dt,{children:e==="MeasureReport"?a.jsx(rK,{measureReport:n}):a.jsx(mS,{value:n})}):null}const Kne="_container_1ue98_1",Xne="_entry_1ue98_14",Jne="_active_1ue98_21",Jy={container:Kne,entry:Xne,active:Jne};function Zne(e){const t=_e(),n=Kt(e.value),[r,o]=v.useState();return v.useEffect(()=>{if(!n)return;const l=LS(n);if(!l)return;const c="reference"in l?l.reference:Nt(l);t.search("ServiceRequest","subject="+c).then(d=>{const p=(d.entry??[]).map(m=>m.resource);$k(p),p.reverse(),o(p)}).catch(d=>ke({color:"red",message:Ye(d),autoClose:!1}))},[t,n]),r?a.jsx("div",{"data-testid":"quick-service-requests",className:Jy.container,children:r.map(l=>a.jsxs("div",{className:$t(Jy.entry,{[Jy.active]:l.id===n?.id}),children:[a.jsx("p",{children:a.jsx(St,{to:l,children:ere(l)})}),l.category?.[0]?.text&&a.jsx("p",{children:l.category[0]?.text}),l.code?.coding?.[0]?.code&&a.jsx("p",{children:l.code.coding[0]?.code}),a.jsx("p",{children:tre(l)})]},l.id))}):null}function ere(e){if(e.identifier){for(const t of e.identifier)if(t.value)return t.value}return e.id||""}function tre(e){return e.authoredOn?e.authoredOn.substring(0,10):e.meta?.lastUpdated?e.meta.lastUpdated.substring(0,10):""}const nre="_container_1l2dh_1",rre={container:nre};function ire(e){const t=Kt(e.valueSet);if(!t)return null;const n=[""],r=t.compose?.include?.[0]?.concept?.map(o=>o.code);return r&&n.push(...r),e.defaultValue&&!n.includes(e.defaultValue)&&n.push(e.defaultValue),a.jsx("div",{className:rre.container,children:a.jsx(cn,{defaultValue:e.defaultValue,onChange:o=>e.onChange(o.currentTarget.value),data:n})})}function ore(e){const t=Kt(e.specimen);return t?a.jsxs(yt,{children:[a.jsxs(yt.Entry,{children:[a.jsx(yt.Key,{children:"Type"}),a.jsx(yt.Value,{children:"Specimen"})]}),a.jsxs(yt.Entry,{children:[a.jsx(yt.Key,{children:"Collected"}),a.jsx(yt.Value,{children:wr(t.collection?.collectedDateTime)})]}),a.jsxs(yt.Entry,{children:[a.jsx(yt.Key,{children:"Specimen Age"}),a.jsx(yt.Value,{children:are(t)})]}),t.collection?.collectedDateTime&&t.receivedTime?a.jsxs(yt.Entry,{children:[a.jsx(yt.Key,{children:"Specimen Stability"}),a.jsx(yt.Value,{children:sre(t)})]}):a.jsx(a.Fragment,{})]}):null}function are(e){const t=e.collection?.collectedDateTime;if(!t)return;const n=new Date(t);return eO(tO(n,new Date))}function sre(e){if(!e.collection?.collectedDateTime||!e.receivedTime)return;const t=new Date(e.collection.collectedDateTime),n=new Date(e.receivedTime);return eO(tO(t,n))}function eO(e){return e.toString().padStart(3,"0")+"D"}function tO(e,t){const n=t.getTime()-e.getTime();return Math.floor(n/(1e3*3600*24))}function lre(e){const t=["Timeline"];return e==="Bot"&&t.push("Editor","Subscriptions"),e==="PlanDefinition"&&t.push("Apply","Builder"),e==="Questionnaire"&&t.push("Preview","Builder","Bots","Responses"),(e==="DiagnosticReport"||e==="MeasureReport")&&t.push("Report"),e==="RequestGroup"&&t.push("Checklist"),e==="ObservationDefinition"&&t.push("Ranges"),e==="Agent"&&t.push("Tools"),t.push("Details","Edit","Event","History","Blame","JSON","Apps","Profiles"),e==="Patient"&&t.push("Export"),t}function cre(){const e=_e(),{resourceType:t,id:n}=Ft(),r={reference:t+"/"+n},o=Tn(),[l,c]=v.useState(),d=Kt(r,c),f=lre(t),[p,m]=v.useState(()=>{const E=window.location.pathname.split("/").pop();return E&&f.map(R=>R.toLowerCase()).includes(E)?E:f[0].toLowerCase()});async function g(){const R=(await e.readHistory(t,n)).entry?.find(_=>!!_.resource)?.resource;R?y(R):ke({color:"red",message:"No history to restore",autoClose:!1})}function y(E){e.updateResource(Al(E)).then(()=>{c(void 0),ke({color:"green",message:"Success"})}).catch(R=>{ke({color:"red",message:Ye(R),autoClose:!1})})}if(l)return P8(l)?a.jsxs(dt,{children:[a.jsx(Le,{children:"Deleted"}),a.jsx("p",{children:"The resource was deleted."}),a.jsx(De,{color:"red",onClick:g,children:"Restore"})]}):a.jsx(Cr,{outcome:l});function b(E){E||(E=f[0].toLowerCase()),m(E),o(`/${t}/${n}/${E}`)?.catch(console.error)}function w(E){const R=d,_=R.orderDetail||[];_.length===0&&_.push({}),_[0].text!==E&&(_[0].text=E,y({...R,orderDetail:_}))}const j=d&&LS(d),C=d&&fee(d),T=e.getUserConfiguration()?.option?.find(E=>E.id==="statusValueSet")?.valueString;return a.jsxs(a.Fragment,{children:[d?.resourceType==="ServiceRequest"&&T&&a.jsx(ire,{valueSet:{reference:T},defaultValue:d.orderDetail?.[0]?.text,onChange:w},Nt(d)+"-"+d.orderDetail?.[0]?.text),d&&a.jsx(Zne,{value:d}),d&&a.jsxs(Dr,{children:[j&&a.jsx(Qk,{patient:j}),C&&a.jsx(ore,{specimen:C}),t!=="Patient"&&a.jsx(WP,{resource:r}),a.jsx(fi,{children:a.jsx(kt,{value:p.toLowerCase(),onChange:b,children:a.jsx(kt.List,{style:{whiteSpace:"nowrap",flexWrap:"nowrap"},children:f.map(E=>a.jsx(kt.Tab,{value:E.toLowerCase(),children:E},E))})})})]}),a.jsx(PS,{})]})}function Ih(){const e=Tn(),{resourceType:t,id:n,versionId:r,tab:o}=Ft(),l=_e(),[c,d]=v.useState(!0),[f,p]=v.useState(),[m,g]=v.useState();if(v.useEffect(()=>{g(void 0),d(!0),l.readHistory(t,n).then(R=>p(R)).then(()=>d(!1)).catch(R=>{g(R),d(!1)})},[l,t,n]),c)return a.jsx(Oi,{});const y=f?.entry??[],b=y.findIndex(R=>R.resource?.meta?.versionId===r);if(b===-1)return a.jsxs(dt,{children:[a.jsx(Le,{children:"Version not found"}),a.jsx(St,{to:`/${t}/${n}`,children:"Return to resource"})]});const w=y[b].resource,j=b<y.length-1?y[b+1].resource:void 0,C="diff",T=o||C,E=y.length-b;return a.jsx(zd,{maw:1200,children:a.jsx(El,{children:a.jsxs(Ue,{gap:"lg",children:[m&&a.jsx("pre",{"data-testid":"error",children:JSON.stringify(m,void 0,2)}),a.jsxs(xm,{cols:2,mb:"lg",children:[a.jsx(zi,{total:y.length,value:E,getControlProps:Hk,onChange:R=>e(`/${t}/${n}/_history/${y[y.length-R]?.resource?.meta?.versionId}/${T}`)?.catch(console.error)}),a.jsx(xe,{justify:"right",children:a.jsx(Vd,{data:[{value:"diff",label:"Diff"},{value:"raw",label:"Raw"}],value:T,onChange:R=>e(`/${t}/${n}/_history/${r}/${R||C}`)?.catch(console.error)})})]}),a.jsx(ue,{mb:"lg",children:a.jsxs(Mm,{compact:!0,children:[a.jsx(ki,{term:"Version ID",children:w.meta?.versionId}),a.jsx(ki,{term:"Author",children:a.jsx(Dc,{value:w.meta?.author,link:!0},w.meta?.author?.reference)}),a.jsx(ki,{term:"Date/Time",children:wr(w.meta?.lastUpdated)})]})}),T==="diff"&&a.jsx(NX,{original:j??{resourceType:t,id:n},revised:w}),T==="raw"&&a.jsx("pre",{style:{fontSize:"9pt"},children:JSON.stringify(w,void 0,2)})]})})})}function ure(){const{resourceType:e,id:t}=Ft(),n=Tn(),[r,o]=v.useState({resourceType:"Subscription",filters:[{code:"url",operator:fe.EQUALS,value:`${e}/${t}`}],fields:["id","criteria","status","_lastUpdated"]});return a.jsx(dt,{children:a.jsx(su,{search:r,onClick:l=>n(`/${l.resource.resourceType}/${l.resource.id}`)?.catch(console.error),onChange:l=>o(l.definition),hideFilters:!0})})}function dre(e){const t=_e(),{resource:n,opened:r,onClose:o}=e,[l,c]=v.useState(!1),[d,f]=v.useState(),[p,m]=v.useState(!1),g=v.useCallback(async()=>{if(n?.id)try{await t.post(t.fhirUrl(n.resourceType,n.id,"$resend"),{subscription:l&&d?Nt(d):void 0,verbose:p}),ke({color:"green",message:"Done"}),o()}catch(y){ke({color:"red",message:Ye(y),autoClose:!1})}},[t,n,o,l,d,p]);return a.jsx(Gn,{opened:r,onClose:o,title:"Resend Subscriptions",children:a.jsx(pt,{onSubmit:g,children:a.jsxs(Ue,{children:[a.jsx(Ln,{label:"Choose subscription (all subscriptions by default)",onChange:y=>c(y.currentTarget.checked)}),l&&a.jsx(Tl,{name:"subscription",resourceType:"Subscription",placeholder:"Subscription",onChange:f}),a.jsx(Ln,{label:"Verbose mode",onChange:y=>m(y.currentTarget.checked)}),a.jsx(xe,{justify:"flex-end",children:a.jsx(De,{type:"submit",children:"Resend"})})]})})})}function WR(){const e=_e(),t=km(),{resourceType:n,id:r}=Ft(),o={reference:n+"/"+r},[l,c]=v.useState(),d=Gc(!1);function f(E,R){return e.updateResource({...E,priority:R})}function p(E,R){f(E,"stat").then(R).catch(console.error)}function m(E,R){f(E,"routine").then(R).catch(console.error)}function g(E){t(`/${E.resourceType}/${E.id}`)}function y(E){t(`/${E.resourceType}/${E.id}/edit`)}function b(E){t(`/${E.resourceType}/${E.id}/delete`)}function w(E){c(E),d[1].open()}function j(E){t(`/${E.resourceType}/${E.id}/_history/${E.meta?.versionId}`)}function C(E,R){const _="aws-textract";ke({id:_,title:"AWS Textract in Progress",message:"Extracting text... This may take a moment...",loading:!0,autoClose:!1}),e.post(e.fhirUrl(E.resourceType,E.id,"$aws-textract"),{}).then(()=>{R(),Ks({id:_,title:"AWS Textract Successful",message:"Text successfully extracted.",color:"green",icon:a.jsx(zo,{size:"1rem"}),loading:!1,withCloseButton:!0})}).catch(k=>Ks({id:_,title:"AWS Textract Error",color:"red",message:Ye(k),icon:a.jsx(dl,{size:"1rem"}),loading:!1,withCloseButton:!0}))}function T(E){const{primaryResource:R,currentResource:_,reloadTimeline:k}=E,L=_.resourceType===R.resourceType&&_.id===R.id,D=_.resourceType==="Communication"&&_.priority!=="stat",P=_.resourceType==="Communication"&&_.priority==="stat",U=L,B=!L,Y=!L,X=!L,te=e.getProjectMembership()?.admin,$=te,W=hne()&&(_.resourceType==="DocumentReference"||_.resourceType==="Media");return a.jsxs(we.Dropdown,{children:[a.jsx(we.Label,{children:"Resource"}),D&&a.jsx(we.Item,{leftSection:a.jsx(aq,{size:14}),onClick:()=>p(_,k),"aria-label":`Pin ${Nt(_)}`,children:"Pin"}),P&&a.jsx(we.Item,{leftSection:a.jsx(lq,{size:14}),onClick:()=>m(_,k),"aria-label":`Unpin ${Nt(_)}`,children:"Unpin"}),B&&a.jsx(we.Item,{leftSection:a.jsx(TT,{size:14}),onClick:()=>g(_),"aria-label":`Details ${Nt(_)}`,children:"Details"}),U&&a.jsx(we.Item,{leftSection:a.jsx(TT,{size:14}),onClick:()=>j(_),"aria-label":`Details ${Nt(_)}`,children:"Details"}),Y&&a.jsx(we.Item,{leftSection:a.jsx(tk,{size:14}),onClick:()=>y(_),"aria-label":`Edit ${Nt(_)}`,children:"Edit"}),te&&a.jsxs(a.Fragment,{children:[a.jsx(we.Divider,{}),a.jsx(we.Label,{children:"Admin"}),$&&a.jsx(we.Item,{leftSection:a.jsx(gq,{size:14}),onClick:()=>w(_),"aria-label":`Resend Subscriptions ${Nt(_)}`,children:"Resend Subscriptions"})]}),W&&a.jsxs(a.Fragment,{children:[a.jsx(we.Divider,{}),a.jsx(we.Label,{children:"AWS AI"}),a.jsx(we.Item,{leftSection:a.jsx(Mq,{size:14}),onClick:()=>C(_,k),"aria-label":`AWS Textract ${Nt(_)}`,children:"AWS Textract"})]}),X&&a.jsxs(a.Fragment,{children:[a.jsx(we.Divider,{}),a.jsx(we.Label,{children:"Danger zone"}),a.jsx(we.Item,{color:"red",leftSection:a.jsx(Om,{size:14}),onClick:()=>b(_),"aria-label":`Delete ${Nt(_)}`,children:"Delete"})]})]})}return a.jsxs(a.Fragment,{children:[n==="Encounter"&&a.jsx(KQ,{encounter:o,getMenu:T}),n==="Patient"&&a.jsx(lK,{patient:o,getMenu:T}),n==="ServiceRequest"&&a.jsx(BX,{serviceRequest:o,getMenu:T}),n!=="Encounter"&&n!=="Patient"&&n!=="ServiceRequest"&&a.jsx(YQ,{resource:o,getMenu:T}),a.jsx(dre,{resource:l,opened:d[0],onClose:d[1].close},`resend-subscriptions-${l?.id}`)]})}function fre(e){const{opened:t,close:n,version:r,loadingStatus:o,handleStatus:l,handleUpgrade:c}=e,[d,f]=v.useState(),[p,m]=v.useState(!1);return v.useEffect(()=>{t&&(d||tF("app-tools-page").then(f).catch(console.error),l())},[t,d,l]),d&&r&&!o?r==="unknown"?a.jsx("p",{children:"Unable to determine the current version of the agent. Check the network connectivity of the agent."}):r.startsWith(d)?a.jsxs("p",{children:["This agent is already on the latest version (",d,")."]}):a.jsxs(a.Fragment,{children:[a.jsxs("p",{children:["Are you sure you want to upgrade this agent from version ",r," to version ",d,"?"]}),a.jsxs(xe,{children:[a.jsx(De,{onClick:()=>{c(p),n()},"aria-label":"Confirm upgrade",children:"Confirm Upgrade"}),a.jsx(Ln,{label:"Force",onChange:g=>m(g.currentTarget.checked)})]})]}):a.jsx(Oi,{})}function hre(){const e=_e(),{id:t}=Ft(),n=v.useMemo(()=>({reference:"Agent/"+t}),[t]),[r,o]=v.useState(!1),[l,c]=v.useState(!1),[d,f]=v.useState(!1),[p,m]=v.useState(!1),[g,y]=v.useState(),[b,w]=v.useState(),[j,C]=v.useState(),[T,E]=v.useState(),[R,_]=v.useState(!1),[k,L]=v.useState(!1),[D,P]=v.useState(),[U,{open:B,close:Y}]=Gc(!1);v.useEffect(()=>{if(r||l||d||R){L(!0);return}L(!1)},[r,l,d,R]);const X=v.useCallback(()=>{o(!0),e.get(e.fhirUrl("Agent",t,"$status"),{cache:"reload"}).then(V=>{y(V.parameter?.find(J=>J.name==="status")?.valueCode),w(V.parameter?.find(J=>J.name==="version")?.valueString),C(V.parameter?.find(J=>J.name==="lastUpdated")?.valueInstant)}).catch(V=>z(Ye(V))).finally(()=>o(!1))},[e,t]),te=v.useCallback(V=>{const J=V.host,N=V.pingCount||1;J&&(_(!0),e.pushToAgent(n,J,`PING ${N}`,on.PING,!0).then(F=>E(F)).catch(F=>z(Ye(F))).finally(()=>_(!1)))},[e,n]),$=v.useCallback(()=>{c(!0),e.get(e.fhirUrl("Agent",t,"$reload-config"),{cache:"reload"}).then(V=>{I("Agent config reloaded successfully.")}).catch(V=>z(Ye(V))).finally(()=>c(!1))},[e,t]),W=v.useCallback(V=>{f(!0);const J=e.fhirUrl("Agent",t,"$upgrade");J.searchParams.set("force",String(V)),e.get(J,{cache:"reload"}).then(N=>{I("Agent upgraded successfully.")}).catch(N=>z(Ye(N))).finally(()=>f(!1))},[e,t]),M=v.useCallback(V=>{m(!0);const J=V.logLimit||20;e.get(e.fhirUrl("Agent",t,`$fetch-logs${J!==void 0?`?limit=${J}`:""}`),{cache:"reload"}).then(N=>{const F=N?.parameter?.find(oe=>oe.name==="logs");F&&P(F?.valueString)}).catch(N=>z(Ye(N))).finally(()=>m(!1))},[e,t]);function I(V){ke({color:"green",title:"Success",icon:a.jsx(zo,{size:"1rem"}),message:V})}function z(V){ke({color:"red",title:"Error",message:V,autoClose:!1})}return a.jsxs(dt,{children:[a.jsx(Gn,{opened:U,onClose:Y,title:"Upgrade Agent",centered:!0,children:a.jsx(fre,{opened:U,close:Y,version:b,loadingStatus:r,handleStatus:X,handleUpgrade:W})}),a.jsx(Le,{order:1,children:"Agent Tools"}),a.jsxs("div",{style:{marginBottom:10},children:["Agent: ",a.jsx(Rl,{value:n,link:!0})]}),a.jsx(Cn,{my:"lg"}),a.jsx(Le,{order:2,children:"Agent Status"}),a.jsx("p",{children:"Retrieve the status of the agent. This tests whether the agent is connected to the Medplum server, and the last time it was able to communicate."}),a.jsx(De,{onClick:X,loading:r,disabled:k&&!r,children:"Get Status"}),!r&&g&&a.jsx(he,{children:a.jsxs(he.Tbody,{children:[a.jsxs(he.Tr,{children:[a.jsx(he.Td,{children:"Status"}),a.jsx(he.Td,{children:a.jsx(zm,{status:g})})]}),a.jsxs(he.Tr,{children:[a.jsx(he.Td,{children:"Version"}),a.jsx(he.Td,{children:b})]}),a.jsxs(he.Tr,{children:[a.jsx(he.Td,{children:"Last Updated"}),a.jsx(he.Td,{children:wr(j,void 0,{timeZoneName:"longOffset"})})]})]})}),a.jsx(Cn,{my:"lg"}),a.jsx(Le,{order:2,children:"Reload Config"}),a.jsx("p",{children:"Reload the configuration of this agent, syncing it with the current version of the Agent resource on the Medplum server."}),a.jsx(De,{onClick:$,loading:l,disabled:k&&!l,"aria-label":"Reload config",children:"Reload Config"}),a.jsx(Cn,{my:"lg"}),a.jsx(Le,{order:2,children:"Upgrade Agent"}),a.jsx("p",{children:"Upgrade the version of this agent, to either the latest (default) or a specified version."}),a.jsx(De,{onClick:B,loading:d,disabled:k&&!d,"aria-label":"Upgrade agent",children:"Upgrade"}),a.jsx(Cn,{my:"lg"}),a.jsxs(pt,{onSubmit:M,children:[a.jsx(Le,{order:2,children:"Fetch Logs"}),a.jsx("p",{children:"Fetch logs from the agent."}),D?.length?a.jsx(Id,{block:!0,mb:15,children:D}):null,a.jsxs(xe,{children:[a.jsx(zc,{w:100,id:"logLimit",name:"logLimit",placeholder:"20",label:"Log Limit"}),a.jsx(De,{mt:22,loading:p,disabled:k&&!p,"aria-label":"Fetch logs",type:"submit",children:"Fetch Logs"})]})]}),a.jsx(Cn,{my:"lg"}),a.jsx(Le,{order:2,children:"Ping from Agent"}),a.jsx("p",{children:"Send a ping command from the agent to a valid IP address or hostname. Use this tool to troubleshoot local network connectivity."}),a.jsx(pt,{onSubmit:te,children:a.jsxs(xe,{children:[a.jsx(Be,{id:"host",name:"host",placeholder:"ex. 127.0.0.1",label:"IP Address / Hostname",rightSection:a.jsx(En,{size:24,radius:"xl",variant:"filled",type:"submit","aria-label":"Ping",loading:R,disabled:k&&!R,children:a.jsx(bq,{style:{width:"1rem",height:"1rem"},stroke:1.5})})}),a.jsx(zc,{id:"pingCount",name:"pingCount",placeholder:"1",label:"Ping Count"})]})}),!R&&T&&a.jsxs(a.Fragment,{children:[a.jsx(Le,{order:5,mt:"sm",mb:0,children:"Last Ping"}),a.jsx("pre",{children:T})]})]})}function pre(){const e=Tn(),t=_e(),[n,r]=v.useState();v.useEffect(()=>{t.get("auth/me",{cache:"no-cache"}).then(r).catch(l=>ke({color:"red",message:Ye(l),autoClose:!1}))},[t]);function o(l){t.post("auth/revoke",{loginId:l}).then(()=>t.get("auth/me",{cache:"no-cache"})).then(r).then(()=>ke({color:"green",message:"Login revoked"})).catch(c=>ke({color:"red",message:Ye(c),autoClose:!1}))}return n?a.jsxs(a.Fragment,{children:[a.jsxs(dt,{children:[a.jsx(Le,{children:"Security"}),a.jsxs(Mm,{children:[a.jsx(ki,{term:"ID",children:a.jsx(Mt,{href:`/${Nt(n.profile)}`,children:n.profile.id})}),a.jsx(ki,{term:"Resource Type",children:n.profile.resourceType}),a.jsx(ki,{term:"Name",children:iu(n.profile.name?.[0])})]})]}),a.jsxs(dt,{children:[a.jsx(Le,{children:"Sessions"}),a.jsxs(he,{children:[a.jsx("thead",{children:a.jsxs("tr",{children:[a.jsx("th",{children:"OS"}),a.jsx("th",{children:"Browser"}),a.jsx("th",{children:"IP Address"}),a.jsx("th",{children:"Auth Method"}),a.jsx("th",{children:"Last Updated"}),a.jsx("th",{})]})}),a.jsx("tbody",{children:n.security.sessions.map(l=>a.jsxs("tr",{children:[a.jsx("td",{children:l.os}),a.jsx("td",{children:l.browser}),a.jsx("td",{children:l.remoteAddress}),a.jsx("td",{children:l.authMethod}),a.jsx("td",{children:wr(l.lastUpdated)}),a.jsx("td",{children:a.jsx(Mt,{href:"#",onClick:()=>o(l.id),children:"Revoke"})})]},l.id))})]})]}),a.jsxs(dt,{children:[a.jsx(Le,{children:"Password"}),a.jsx(De,{onClick:()=>e("/changepassword")?.catch(console.error),children:"Change password"})]}),a.jsxs(dt,{children:[a.jsx(Le,{children:"Multi Factor Auth"}),a.jsxs("p",{children:["Enrolled: ",n.security.mfaEnrolled.toString()]}),!n.security.mfaEnrolled&&a.jsx(De,{onClick:()=>e("/mfa")?.catch(console.error),children:"Enroll"})]})]}):null}function mre(){const{id:e,secret:t}=Ft(),n=_e(),[r,o]=v.useState(),[l,c]=v.useState(!1),d=au(r,void 0);return a.jsxs(dt,{width:450,children:[a.jsx(Cr,{issues:d}),a.jsxs(pt,{onSubmit:f=>{if(f.password!==f.confirmPassword){o(jo("Passwords do not match","confirmPassword"));return}o(void 0);const p={id:e,secret:t,password:f.password};n.post("auth/setpassword",p).then(()=>c(!0)).catch(m=>o(Yt(m)))},children:[a.jsxs(fr,{style:{flexDirection:"column"},children:[a.jsx($i,{size:32}),a.jsx(Le,{children:"Set password"})]}),!l&&a.jsxs(Ue,{children:[a.jsx(Xi,{name:"password",label:"New password",required:!0,error:Lt(r,"password")}),a.jsx(Xi,{name:"confirmPassword",label:"Confirm new password",required:!0,error:Lt(r,"confirmPassword")}),a.jsx(xe,{justify:"flex-end",mt:"xl",children:a.jsx(De,{type:"submit",children:"Set password"})})]}),l&&a.jsxs("div",{"data-testid":"success",children:["Password set. You can now ",a.jsx(St,{to:"/signin",children:"sign in"}),"."]})]})]})}function gre(){const e=Pm(),t=Tn(),[n]=MS(),r=af(),o=v.useCallback(()=>{const l=n.get("next");t(l?.startsWith("/")?l:"/")?.catch(console.error)},[n,t]);return v.useEffect(()=>{e&&n.has("next")&&o()},[e,n,o]),a.jsxs(Sk,{onSuccess:()=>o(),onForgotPassword:()=>t("/resetpassword")?.catch(console.error),onRegister:YP()?()=>t("/register")?.catch(console.error):void 0,googleClientId:r.googleClientId,login:n.get("login")||void 0,projectId:n.get("project")||void 0,children:[a.jsx($i,{size:32}),a.jsxs(Le,{children:["Sign in to ",uk()]}),n.get("project")==="new"&&a.jsx("div",{children:"Sign in again to create a new project"})]})}function vre(){const e=Tn(),t=Kr(),[n,r]=v.useState(),[o,l]=v.useState(),[c,d]=v.useState();return v.useEffect(()=>{const f=Object.fromEntries(new URLSearchParams(t.search).entries());r(f.resourceType),l(f.query),d(JSON.parse(f.fields))},[t]),!n||!o||!c?null:a.jsx(WY,{resourceType:n,checkboxesEnabled:!0,query:o,fields:c,onClick:f=>e(`/${n}/${f.resource.id}`)?.catch(console.error),onAuxClick:f=>window.open(`/${n}/${f.resource.id}`,"_blank"),onBulk:f=>{e(`/bulk/${n}?ids=${f.join(",")}`)?.catch(console.error)}})}function yre(){const{id:e,secret:t}=Ft(),n=_e(),[r,o]=v.useState(),[l,c]=v.useState(!1),d=au(r,void 0);return a.jsxs(dt,{width:450,children:[a.jsx(Cr,{issues:d}),a.jsxs(pt,{onSubmit:()=>{o(void 0);const f={id:e,secret:t};n.post("auth/verifyemail",f).then(()=>c(!0)).catch(p=>o(Yt(p)))},children:[a.jsxs(fr,{style:{flexDirection:"column"},children:[a.jsx($i,{size:32}),a.jsx(Le,{children:"Email address verification required"})]}),!l&&a.jsxs(Ue,{children:[a.jsx("p",{children:"In order to sign in, click the button below to verify your ability to receive email at the address this link was sent to."}),a.jsx(xe,{justify:"flex-end",mt:"xl",children:a.jsx(De,{type:"submit",children:"Verify email"})})]}),l&&a.jsxs("div",{"data-testid":"success",children:["Email verified. You can now ",a.jsx(St,{to:"/signin",children:"sign in"}),"."]})]})]})}function xre(){return a.jsx(DZ,{children:a.jsxs($e,{errorElement:a.jsx(Jte,{}),children:[a.jsx($e,{path:"/signin",element:a.jsx(gre,{})}),a.jsx($e,{path:"/oauth",element:a.jsx(pne,{})}),a.jsx($e,{path:"/resetpassword",element:a.jsx(gne,{})}),a.jsx($e,{path:"/setpassword/:id/:secret",element:a.jsx(mre,{})}),a.jsx($e,{path:"/verifyemail/:id/:secret",element:a.jsx(yre,{})}),a.jsx($e,{path:"/register",element:a.jsx(mne,{})}),a.jsx($e,{path:"/changepassword",element:a.jsx(Yte,{})}),a.jsx($e,{path:"/security",element:a.jsx(pre,{})}),a.jsx($e,{path:"/mfa",element:a.jsx(dne,{})}),a.jsx($e,{path:"/batch",element:a.jsx(Wte,{})}),a.jsx($e,{path:"/bulk/:resourceType",element:a.jsx(Qte,{})}),a.jsx($e,{path:"/smart",element:a.jsx(vre,{})}),a.jsx($e,{path:"/forms/:id",element:a.jsx(Zte,{})}),a.jsx($e,{path:"/admin/super",element:a.jsx($ee,{})}),a.jsx($e,{path:"/admin/super/asyncjob",element:a.jsx(Oee,{})}),a.jsx($e,{path:"/admin/super/db",element:a.jsx(Cee,{})}),a.jsx($e,{path:"/admin/config",element:a.jsx(Aee,{})}),a.jsxs($e,{path:"/admin",element:a.jsx(Dee,{}),children:[a.jsx($e,{path:"patients",element:a.jsx(_ee,{})}),a.jsx($e,{path:"bots/new",element:a.jsx(mee,{})}),a.jsx($e,{path:"bots",element:a.jsx(hee,{})}),a.jsx($e,{path:"clients/new",element:a.jsx(gee,{})}),a.jsx($e,{path:"clients",element:a.jsx(pee,{})}),a.jsx($e,{path:"details",element:a.jsx(RR,{})}),a.jsx($e,{path:"invite",element:a.jsx(Ree,{})}),a.jsx($e,{path:"users",element:a.jsx(Vee,{})}),a.jsx($e,{path:"project",element:a.jsx(RR,{})}),a.jsx($e,{path:"secrets",element:a.jsx(kee,{})}),a.jsx($e,{path:"sites",element:a.jsx(Pee,{})}),a.jsx($e,{path:"members/:membershipId",element:a.jsx(Tee,{})})]}),a.jsx($e,{path:"/lab/assays",element:a.jsx(cne,{})}),a.jsx($e,{path:"/lab/panels",element:a.jsx(une,{})}),a.jsxs($e,{path:"/:resourceType/new",element:a.jsx(Xte,{}),children:[a.jsx($e,{index:!0,element:a.jsx(Xy,{})}),a.jsx($e,{path:"form",element:a.jsx(Xy,{})}),a.jsx($e,{path:"json",element:a.jsx($ne,{})}),a.jsx($e,{path:"profiles",element:a.jsx(Xy,{})})]}),a.jsxs($e,{path:"/:resourceType/:id",element:a.jsx(cre,{}),children:[a.jsx($e,{index:!0,element:a.jsx(WR,{})}),a.jsx($e,{path:"apply",element:a.jsx(yne,{})}),a.jsx($e,{path:"apps",element:a.jsx(xne,{})}),a.jsx($e,{path:"event",element:a.jsx(Sne,{})}),a.jsx($e,{path:"blame",element:a.jsx(wne,{})}),a.jsx($e,{path:"bots",element:a.jsx(qne,{})}),a.jsx($e,{path:"builder",element:a.jsx(kne,{})}),a.jsx($e,{path:"checklist",element:a.jsx(Pne,{})}),a.jsx($e,{path:"delete",element:a.jsx(One,{})}),a.jsx($e,{path:"details",element:a.jsx(Lne,{})}),a.jsx($e,{path:"edit",element:a.jsx(Ine,{})}),a.jsx($e,{path:"editor",element:a.jsx(Ane,{})}),a.jsxs($e,{path:"history",children:[a.jsx($e,{index:!0,element:a.jsx(GR,{})}),a.jsx($e,{path:":versionId/:tab",element:a.jsx(Ih,{})}),a.jsx($e,{path:":versionId",element:a.jsx(Ih,{})})]}),a.jsxs($e,{path:"_history",children:[a.jsx($e,{index:!0,element:a.jsx(GR,{})}),a.jsx($e,{path:":versionId/:tab",element:a.jsx(Ih,{})}),a.jsx($e,{path:":versionId",element:a.jsx(Ih,{})})]}),a.jsx($e,{path:"json",element:a.jsx(Une,{})}),a.jsx($e,{path:"preview",element:a.jsx(Bne,{})}),a.jsx($e,{path:"responses",element:a.jsx(Wne,{})}),a.jsx($e,{path:"report",element:a.jsx(Yne,{})}),a.jsx($e,{path:"ranges",element:a.jsx(Qne,{})}),a.jsx($e,{path:"subscriptions",element:a.jsx(ure,{})}),a.jsx($e,{path:"timeline",element:a.jsx(WR,{})}),a.jsx($e,{path:"tools",element:a.jsx(hre,{})}),a.jsx($e,{path:"profiles",element:a.jsx(Vne,{})}),a.jsx($e,{path:"export",element:a.jsx(zne,{})})]}),a.jsx($e,{path:"/:resourceType",element:a.jsx(FR,{})}),a.jsx($e,{path:"/",element:a.jsx(FR,{})})]})})}function bre(){const e=_e(),t=e.getUserConfiguration(),n=Kr(),[r]=MS();return e.isLoading()?a.jsx(Oi,{}):a.jsx(NG,{logo:a.jsx($i,{size:24}),pathname:n.pathname,searchParams:r,version:ID,menus:Sre(t),displayAddBookmark:!!t?.id,children:a.jsx(v.Suspense,{fallback:a.jsx(Oi,{}),children:a.jsx(xre,{})})})}function Sre(e){const t=e?.menu?.map(n=>({title:n.title,links:n.link?.map(r=>({label:r.name,href:r.target,icon:wre(r.target)}))||[]}))||[];return t.push({title:"Settings",links:[{label:"Security",href:"/security",icon:a.jsx(GH,{})}]}),t}const QR={Patient:Aq,Practitioner:BH,Organization:iH,ServiceRequest:hq,DiagnosticReport:yq,Questionnaire:$H,admin:JF,AccessPolicy:HH,Subscription:$q,batch:iq,Observation:eq};function wre(e){if(e.includes("admin/super/db"))return a.jsx(SH,{});try{const t=new URL(e,"https://app.medplum.com").pathname.split("/")[1];if(t in QR){const n=QR[t];return a.jsx(n,{})}}catch{}return a.jsx(bm,{w:30})}async function jre(){const e=af(),t=new zD({baseUrl:e.baseUrl,clientId:e.clientId,storagePrefix:"@medplum:",cacheTime:6e4,autoBatchTime:100,onUnauthenticated:()=>{window.location.pathname!=="/signin"&&window.location.pathname!=="/oauth"&&(window.location.href="/signin?next="+encodeURIComponent(window.location.pathname+window.location.search))}}),n={headings:{sizes:{h1:{fontSize:"1.125rem",fontWeight:"500",lineHeight:"2.0"}}},fontSizes:{xs:"0.6875rem",sm:"0.875rem",md:"0.875rem",lg:"1.0rem",xl:"1.125rem"}},r=eee([{path:"*",element:a.jsx(bre,{})}]),o=c=>r.navigate(c);WX.createRoot(document.getElementById("root")).render(a.jsx(v.StrictMode,{children:a.jsx(nF,{medplum:t,navigate:o,children:a.jsxs(y2,{theme:n,children:[a.jsx(Aa,{position:"bottom-right"}),a.jsx(TZ,{router:r})]})})}))}jre().catch(console.error);
|
|
615
|
-
//# sourceMappingURL=index-
|
|
615
|
+
//# sourceMappingURL=index-XiTfb9pM.js.map
|