@ovok/core 0.4.46 → 0.4.47

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.
package/README.md CHANGED
@@ -628,30 +628,54 @@ turning the feature on; an unmapped email can still produce the uniform 202
628
628
  response without sending a message. `useUpdatePatientSharingSettings()` is the
629
629
  corresponding mutation hook.
630
630
 
631
- `listPatientSharing()` returns `outgoing`, `incoming`, and `practitioners`;
632
- the latter lists active shares of a patient's whole record with practitioners.
633
- For compatibility with older servers, the SDK defaults a missing `practitioners`
634
- array to `[]`. Listing is patient-only (403 for another profile).
631
+ `listPatientSharing()` returns `outgoing`, `incoming`, `practitioners`, and
632
+ `relatedPersons`. `practitioners` lists active shares of a patient's whole record
633
+ with practitioners; `relatedPersons` lists the Observation codes a patient shares
634
+ with carers. For compatibility with older servers, the SDK defaults a missing
635
+ `practitioners` or `relatedPersons` array to `[]`. Listing is patient-only (403 for another profile).
635
636
  `revokePatientSharing(consentId)` uses the existing DELETE route
636
637
  to end a share immediately or decline a pending invite. It returns 204; 404
637
638
  (`Share not found.`) means the caller is not a party, and a code-less 409
638
639
  (`This share kept changing; try again.`) can be retried after reloading. A
639
640
  practitioner's whole-record share has no measurement-code list.
640
641
 
641
- Invitations use four client methods, all backed by `/v1/invites/*`:
642
+ Invitations are named by purpose, all backed by `/v1/invites/*`:
642
643
 
643
644
  ```typescript
644
- await client.invitePractitioner({ email, firstName, lastName }); // patient invites practitioner
645
- await client.invitePatient({ email, firstName, lastName }); // practitioner invites patient
646
- await client.acceptPractitionerInvite({ inviteId, code });
647
- await client.acceptPatientInvite({ inviteId, code });
648
-
649
- // Or dispatch acceptance using the signed-in profile:
645
+ // A patient shares their record with a practitioner…
646
+ await client.shareRecord({ recipient: "practitioner", email, firstName, lastName });
647
+ // …or shares some Observation codes with a carer (a related person).
648
+ await client.shareRecord({ recipient: "related-person", email, firstName, lastName, codes: ["8480-6"] });
649
+ await client.acceptRecordShare({ inviteId, code }); // practitioner or existing carer, signed in
650
+ await client.acceptRecordShare({ inviteId, code, password }); // new carer, signed out
651
+
652
+ // A practitioner invites a patient into their care.
653
+ await client.inviteToCare({ email, firstName, lastName });
654
+ await client.acceptCareInvite({ inviteId, code }); // patient, signed in
655
+
656
+ // Or dispatch acceptance using the signed-in Practitioner or Patient profile:
650
657
  await client.acceptInvite({ inviteId, code });
651
658
  ```
652
659
 
653
- `useInvitePractitioner()`, `useInvitePatient()`, and `useAcceptInvite()` provide
654
- React mutation states. The invite methods always return `{ status: "sent" }`
660
+ `useShareRecord()`, `useAcceptRecordShare()`, `useInviteToCare()`,
661
+ `useAcceptCareInvite()`, and `useAcceptInvite()` provide React mutation states.
662
+
663
+ `invitePractitioner()`, `invitePatient()`, `acceptPractitionerInvite()`,
664
+ `acceptPatientInvite()`, `useInvitePractitioner()`, and `useInvitePatient()` are
665
+ deprecated. Their routes (`/v1/invites/practitioner`, `/v1/invites/patient` and
666
+ their `/accept` routes) sunset on 2026-12-01; move to `shareRecord()`,
667
+ `inviteToCare()`, `acceptRecordShare()`, and `acceptCareInvite()` before then.
668
+
669
+ A carer accepts a record share from the patient app. A carer new to the project
670
+ accepts signed out and sends a `password`; that creates their account, and they
671
+ then sign in with `login({ type: "RelatedPerson", email, password, tenantCode })`.
672
+ There is no carer registration route. A 422 `password_required` means the invite
673
+ needs a password; a 409 `address_has_account` means the address already has an
674
+ account, so the patient must send a new invite. Carer sharing needs patient
675
+ sharing enabled and `RELATED_PERSON_INVITATION_ENABLED` not set to `false`; carer
676
+ sign-in needs `RELATED_PERSON_LOGIN_ENABLED` not set to `false`. Map the
677
+ `RELATED_PERSON_INVITED` and `RELATED_PERSON_RECORD_SHARED` email templates
678
+ before inviting carers. The invite methods always return `{ status: "sent" }`
655
679
  (HTTP 202), whether or not an email is ultimately sent. Show only “If that
656
680
  address can be invited, an email is on its way”; the response must not reveal
657
681
  whether the address has an account. Both names are trimmed by Core, and email
@@ -666,7 +690,9 @@ invite can also fail with 401 (no session), 403 (feature/role gate), 422 (invali
666
690
  body), 409 `invitation_not_configured` (missing default policy),
667
691
  `app_url_not_configured` (missing audience app URL), or
668
692
  `practitioner_without_access_policy` (a full-access practitioner cannot be
669
- narrowed to a share policy). A code-less 409 means another invite for the same
693
+ narrowed to a share policy). Accepting a record share can also return 409
694
+ `related_person_without_access_policy` or `sharing_not_configured` (patient
695
+ sharing lost its template; turn it on again). A code-less 409 means another invite for the same
670
696
  address or practitioner is still being written; offer retry. A 429 means the
671
697
  inviter has 20 pending invites. Use
672
698
  `readOvokError(error)` and `OVOK_INVITE_ERROR_CODES` to branch on stable codes.
@@ -675,7 +701,7 @@ inviter has 20 pending invites. Use
675
701
 
676
702
  Every app that can receive invitations needs a page at
677
703
  `<app URL>/accept-invite?invite=<uuid>&code=<secret>`. Practitioner links use
678
- `PRACTITIONER_APP_URL`; patient links use `PATIENT_APP_URL`. The secret is valid
704
+ `PRACTITIONER_APP_URL`; patient and carer links use `PATIENT_APP_URL`. The secret is valid
679
705
  for seven days. `parseAcceptInviteLink(url)` returns a body only when the UUID and
680
706
  16–128 character code are present and valid; otherwise show “This link is
681
707
  incomplete” and make no request. Once parsed, remove the code from the address
@@ -684,7 +710,8 @@ bar/history and do not send it to logs or analytics.
684
710
  If the visitor is signed out, send them through sign-in and restore the link on
685
711
  return. There is no preview endpoint. Once signed in, call `acceptInvite()`; it
686
712
  chooses the route from the `Patient` or `Practitioner` profile and rejects other
687
- profile types. Never accept on page load. For a patient accepting, explain that
713
+ profile types. Carers call `acceptRecordShare()` directly: signed in when they
714
+ already have an account, otherwise signed out with a new password. Never accept on page load. For a patient accepting, explain that
688
715
  their whole record will be shared and wait for an explicit Accept action. A
689
716
  patient can decline with `revokePatientSharing(inviteId)`; practitioners have no
690
717
  decline route and can ignore the link. After a successful acceptance, show who
@@ -7,7 +7,7 @@ type ExchangeCodeProps = {
7
7
  codeVerifier: string;
8
8
  requestOptions?: MedplumRequestOptions;
9
9
  } & ({
10
- type: "Patient";
10
+ type: "Patient" | "RelatedPerson";
11
11
  } | {
12
12
  type: "Practitioner";
13
13
  tenantCode: string;
@@ -9,7 +9,7 @@ const exchangeCode = async ({ ...props }) => {
9
9
  tenantCode: props.tenantCode,
10
10
  }, undefined, props.requestOptions);
11
11
  }
12
- return props.client.post("auth/tenant/Patient/login/token", {
12
+ return props.client.post(`auth/tenant/${props.type}/login/token`, {
13
13
  sessionCode: props.sessionCode,
14
14
  codeVerifier: props.codeVerifier,
15
15
  }, undefined, props.requestOptions);
@@ -2,5 +2,5 @@ import { StartLoginResponse } from "./types/StartLoginResponse";
2
2
  export declare const handleTenantCode: ({ profiles, tenantCode, type, }: {
3
3
  profiles: StartLoginResponse["profiles"];
4
4
  tenantCode?: string;
5
- type: "Practitioner" | "Patient";
5
+ type: "Practitioner" | "Patient" | "RelatedPerson";
6
6
  }) => string;
@@ -60,7 +60,7 @@ async function login(body, requestOptions) {
60
60
  });
61
61
  const exchange = (sessionCode) => (0, exchange_code_1.exchangeCode)({
62
62
  client: this,
63
- type: "Patient",
63
+ type: body.type,
64
64
  sessionCode,
65
65
  codeVerifier,
66
66
  requestOptions,
@@ -68,6 +68,6 @@ async function login(body, requestOptions) {
68
68
  if (startResponse.nextStep === "mfa") {
69
69
  return mfaStep(this, body.type, startResponse.loginId, exchange, requestOptions);
70
70
  }
71
- (0, handle_tenant_code_1.handleTenantCode)({ profiles: startResponse.profiles, tenantCode: body.tenantCode, type: "Patient" });
71
+ (0, handle_tenant_code_1.handleTenantCode)({ profiles: startResponse.profiles, tenantCode: body.tenantCode, type: body.type });
72
72
  return exchange(startResponse.sessionCode);
73
73
  }
@@ -2,8 +2,8 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.startLogin = void 0;
4
4
  const startLogin = async ({ client, body, codeChallenge, requestOptions, }) => {
5
- if (body.type === "Patient") {
6
- return client.post("auth/tenant/Patient/login/start", {
5
+ if (body.type !== "Practitioner") {
6
+ return client.post(`auth/tenant/${body.type}/login/start`, {
7
7
  email: body.email,
8
8
  password: body.password,
9
9
  codeChallenge,
@@ -12,5 +12,11 @@ export type PractitionerLoginBody = LoginCredentials & {
12
12
  /** Selects a project when the person belongs to multiple projects. */
13
13
  tenantCode?: string;
14
14
  };
15
- export type LoginBody = PatientLoginBody | PractitionerLoginBody;
15
+ /** A carer; their account comes only from accepting a record-share invite. */
16
+ export type RelatedPersonLoginBody = LoginCredentials & {
17
+ type: "RelatedPerson";
18
+ /** The tenant code to log in to. */
19
+ tenantCode: string;
20
+ };
21
+ export type LoginBody = PatientLoginBody | PractitionerLoginBody | RelatedPersonLoginBody;
16
22
  export {};
@@ -6,7 +6,7 @@ export interface ResetPasswordBody {
6
6
  /**
7
7
  * The type of user to reset the password for
8
8
  */
9
- type: "Patient" | "Practitioner";
9
+ type: "Patient" | "Practitioner" | "RelatedPerson";
10
10
  /**
11
11
  * The client ID to use for the request
12
12
  */
@@ -1,9 +1,22 @@
1
1
  import type { MedplumRequestOptions } from "@medplum/core";
2
2
  import { OvokClient } from "../ovok-client";
3
3
  import { PatientSharingPractitionerShare } from "../patient-sharing/types";
4
- import { AcceptInviteBody, InviteBody, InviteSent } from "./types";
4
+ import { AcceptInviteBody, AcceptRecordShareBody, InviteBody, InviteSent, RecordShareAccepted, RecordShareBody } from "./types";
5
+ /** A patient shares their record with a practitioner, or with a carer (a related person) for some codes. */
6
+ export declare function shareRecord(this: OvokClient, body: RecordShareBody, requestOptions?: MedplumRequestOptions): Promise<InviteSent>;
7
+ /** Accepts a record share; a carer new to the project accepts signed out with a `password`. */
8
+ export declare function acceptRecordShare(this: OvokClient, body: AcceptRecordShareBody, requestOptions?: MedplumRequestOptions): Promise<RecordShareAccepted>;
9
+ /** A practitioner invites a patient into their care. */
10
+ export declare function inviteToCare(this: OvokClient, body: InviteBody, requestOptions?: MedplumRequestOptions): Promise<InviteSent>;
11
+ /** The signed-in patient accepts a practitioner's care invite. */
12
+ export declare function acceptCareInvite(this: OvokClient, body: AcceptInviteBody, requestOptions?: MedplumRequestOptions): Promise<PatientSharingPractitionerShare>;
13
+ /** @deprecated Use shareRecord({ recipient: "practitioner", ... }); the route sunsets on 2026-12-01. */
5
14
  export declare function invitePractitioner(this: OvokClient, body: InviteBody, requestOptions?: MedplumRequestOptions): Promise<InviteSent>;
15
+ /** @deprecated Use inviteToCare; the route sunsets on 2026-12-01. */
6
16
  export declare function invitePatient(this: OvokClient, body: InviteBody, requestOptions?: MedplumRequestOptions): Promise<InviteSent>;
17
+ /** @deprecated Use acceptRecordShare; the route sunsets on 2026-12-01. */
7
18
  export declare function acceptPractitionerInvite(this: OvokClient, body: AcceptInviteBody, requestOptions?: MedplumRequestOptions): Promise<PatientSharingPractitionerShare>;
19
+ /** @deprecated Use acceptCareInvite; the route sunsets on 2026-12-01. */
8
20
  export declare function acceptPatientInvite(this: OvokClient, body: AcceptInviteBody, requestOptions?: MedplumRequestOptions): Promise<PatientSharingPractitionerShare>;
21
+ /** Accepts as the signed-in practitioner (a record share) or patient (a care invite). */
9
22
  export declare function acceptInvite(this: OvokClient, body: AcceptInviteBody, requestOptions?: MedplumRequestOptions): Promise<PatientSharingPractitionerShare>;
@@ -1,32 +1,64 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.shareRecord = shareRecord;
4
+ exports.acceptRecordShare = acceptRecordShare;
5
+ exports.inviteToCare = inviteToCare;
6
+ exports.acceptCareInvite = acceptCareInvite;
3
7
  exports.invitePractitioner = invitePractitioner;
4
8
  exports.invitePatient = invitePatient;
5
9
  exports.acceptPractitionerInvite = acceptPractitionerInvite;
6
10
  exports.acceptPatientInvite = acceptPatientInvite;
7
11
  exports.acceptInvite = acceptInvite;
8
12
  const request_options_1 = require("../request-options");
13
+ /** A patient shares their record with a practitioner, or with a carer (a related person) for some codes. */
14
+ function shareRecord(body, requestOptions) {
15
+ return this.post("/v1/invites/record-share", body, undefined, requestOptions);
16
+ }
17
+ /** Accepts a record share; a carer new to the project accepts signed out with a `password`. */
18
+ function acceptRecordShare(body, requestOptions) {
19
+ return this.post("/v1/invites/record-share/accept", body, undefined, requestOptions)
20
+ .then((result) => {
21
+ this.invalidateUrl("/v1/patient-sharing/shares");
22
+ return result;
23
+ });
24
+ }
25
+ /** A practitioner invites a patient into their care. */
26
+ function inviteToCare(body, requestOptions) {
27
+ return this.post("/v1/invites/care", body, undefined, requestOptions);
28
+ }
29
+ /** The signed-in patient accepts a practitioner's care invite. */
30
+ function acceptCareInvite(body, requestOptions) {
31
+ return this.post("/v1/invites/care/accept", body, undefined, requestOptions)
32
+ .then((result) => {
33
+ this.invalidateUrl("/v1/patient-sharing/shares");
34
+ return result;
35
+ });
36
+ }
37
+ /** @deprecated Use shareRecord({ recipient: "practitioner", ... }); the route sunsets on 2026-12-01. */
9
38
  function invitePractitioner(body, requestOptions) {
10
39
  return this.post("/v1/invites/practitioner", body, undefined, requestOptions);
11
40
  }
41
+ /** @deprecated Use inviteToCare; the route sunsets on 2026-12-01. */
12
42
  function invitePatient(body, requestOptions) {
13
43
  return this.post("/v1/invites/patient", body, undefined, requestOptions);
14
44
  }
45
+ /** @deprecated Use acceptRecordShare; the route sunsets on 2026-12-01. */
15
46
  function acceptPractitionerInvite(body, requestOptions) {
16
47
  return this.post("/v1/invites/practitioner/accept", body, undefined, requestOptions);
17
48
  }
49
+ /** @deprecated Use acceptCareInvite; the route sunsets on 2026-12-01. */
18
50
  function acceptPatientInvite(body, requestOptions) {
19
51
  return this.post("/v1/invites/patient/accept", body, undefined, requestOptions);
20
52
  }
53
+ /** Accepts as the signed-in practitioner (a record share) or patient (a care invite). */
21
54
  function acceptInvite(body, requestOptions) {
22
55
  var _a;
23
56
  const resourceType = (_a = this.getProfile()) === null || _a === void 0 ? void 0 : _a.resourceType;
24
- if (resourceType !== "Practitioner" && resourceType !== "Patient") {
25
- throw new Error("Accepting an invite requires a signed-in Patient or Practitioner profile.");
57
+ if (resourceType === "Practitioner") {
58
+ return this.acceptRecordShare(body, ...(0, request_options_1.optionalArg)(requestOptions));
26
59
  }
27
- const accept = resourceType === "Practitioner" ? this.acceptPractitionerInvite : this.acceptPatientInvite;
28
- return accept.call(this, body, ...(0, request_options_1.optionalArg)(requestOptions)).then((result) => {
29
- this.invalidateUrl("/v1/patient-sharing/shares");
30
- return result;
31
- });
60
+ if (resourceType === "Patient") {
61
+ return this.acceptCareInvite(body, ...(0, request_options_1.optionalArg)(requestOptions));
62
+ }
63
+ throw new Error("Accepting an invite requires a signed-in Patient or Practitioner profile.");
32
64
  }
@@ -1,9 +1,16 @@
1
- import { PatientSharingPractitionerShare } from "../patient-sharing/types";
1
+ import { PatientSharingPractitionerShare, PatientSharingRelatedPersonShare } from "../patient-sharing/types";
2
2
  export type InviteBody = {
3
3
  email: string;
4
4
  firstName: string;
5
5
  lastName: string;
6
6
  };
7
+ export type RecordShareBody = (InviteBody & {
8
+ recipient: "practitioner";
9
+ }) | (InviteBody & {
10
+ recipient: "related-person";
11
+ /** The Observation codes the carer may read: 1 to 100. */
12
+ codes: string[];
13
+ });
7
14
  export type InviteSent = {
8
15
  status: "sent";
9
16
  };
@@ -11,9 +18,18 @@ export type AcceptInviteBody = {
11
18
  inviteId: string;
12
19
  code: string;
13
20
  };
21
+ export type AcceptRecordShareBody = AcceptInviteBody & {
22
+ /** Only for a carer whose account the invite creates; they accept signed out. */
23
+ password?: string | null;
24
+ };
14
25
  export type AcceptInviteResult = PatientSharingPractitionerShare;
26
+ export type RecordShareAccepted = PatientSharingPractitionerShare | PatientSharingRelatedPersonShare;
15
27
  export declare const OVOK_INVITE_ERROR_CODES: {
16
28
  readonly invitationNotConfigured: "invitation_not_configured";
17
29
  readonly appUrlNotConfigured: "app_url_not_configured";
18
30
  readonly practitionerWithoutAccessPolicy: "practitioner_without_access_policy";
31
+ readonly relatedPersonWithoutAccessPolicy: "related_person_without_access_policy";
32
+ readonly addressHasAccount: "address_has_account";
33
+ readonly passwordRequired: "password_required";
34
+ readonly sharingNotConfigured: "sharing_not_configured";
19
35
  };
@@ -5,4 +5,8 @@ exports.OVOK_INVITE_ERROR_CODES = {
5
5
  invitationNotConfigured: "invitation_not_configured",
6
6
  appUrlNotConfigured: "app_url_not_configured",
7
7
  practitionerWithoutAccessPolicy: "practitioner_without_access_policy",
8
+ relatedPersonWithoutAccessPolicy: "related_person_without_access_policy",
9
+ addressHasAccount: "address_has_account",
10
+ passwordRequired: "password_required",
11
+ sharingNotConfigured: "sharing_not_configured",
8
12
  };
@@ -18,10 +18,11 @@ function redeemPatientSharingInvite(body, requestOptions) {
18
18
  }
19
19
  function listPatientSharing(requestOptions) {
20
20
  return this.get("/v1/patient-sharing/shares", ...(0, request_options_1.optionalArg)(requestOptions)).then((shares) => {
21
- var _a;
21
+ var _a, _b;
22
22
  return ({
23
23
  ...shares,
24
24
  practitioners: (_a = shares.practitioners) !== null && _a !== void 0 ? _a : [],
25
+ relatedPersons: (_b = shares.relatedPersons) !== null && _b !== void 0 ? _b : [],
25
26
  });
26
27
  });
27
28
  }
@@ -25,10 +25,23 @@ export type PatientSharingPractitionerShare = {
25
25
  startedAt: string | null;
26
26
  endsAt: string | null;
27
27
  };
28
+ /** Observation codes a patient shares with a related person (a carer). */
29
+ export type PatientSharingRelatedPersonShare = {
30
+ consentId: string;
31
+ sharer: PatientSharingParty;
32
+ relatedPerson: {
33
+ relatedPersonId: string;
34
+ name: string | null;
35
+ };
36
+ codes: string[];
37
+ startedAt: string | null;
38
+ endsAt: string | null;
39
+ };
28
40
  export type PatientSharingShares = {
29
41
  outgoing: PatientSharingShare[];
30
42
  incoming: PatientSharingShare[];
31
43
  practitioners: PatientSharingPractitionerShare[];
44
+ relatedPersons: PatientSharingRelatedPersonShare[];
32
45
  };
33
46
  export type CreatePatientSharingInvite = {
34
47
  codes: string[];
@@ -21,6 +21,10 @@ exports.OVOK_CORE_API_REQUIREMENTS = {
21
21
  { method: "POST", path: "/auth/tenant/Patient/login/token", group: "Auth" },
22
22
  { method: "POST", path: "/auth/tenant/Practitioner/login/token", group: "Auth" },
23
23
  { method: "POST", path: "/auth/tenant/Practitioner/login/mfa", group: "Auth" },
24
+ { method: "POST", path: "/auth/tenant/Patient/login/mfa", group: "Auth" },
25
+ { method: "POST", path: "/auth/tenant/RelatedPerson/login/start", group: "Auth" },
26
+ { method: "POST", path: "/auth/tenant/RelatedPerson/login/token", group: "Auth" },
27
+ { method: "POST", path: "/auth/tenant/RelatedPerson/login/mfa", group: "Auth" },
24
28
  { method: "POST", path: "/auth/tenant/Patient/register", group: "Auth" },
25
29
  { method: "POST", path: "/auth/tenant/Practitioner/register", group: "Auth" },
26
30
  { method: "POST", path: "/auth/external/google", group: "Auth" },
@@ -91,6 +95,11 @@ exports.OVOK_CORE_API_REQUIREMENTS = {
91
95
  { method: "DELETE", path: "/v1/patient-sharing/shares/:consentId", group: "PatientSharing" },
92
96
  { method: "POST", path: "/v1/patient-sharing/invites", group: "PatientSharing" },
93
97
  { method: "POST", path: "/v1/patient-sharing/invites/redeem", group: "PatientSharing" },
98
+ { method: "POST", path: "/v1/invites/record-share", group: "Invites" },
99
+ { method: "POST", path: "/v1/invites/record-share/accept", group: "Invites" },
100
+ { method: "POST", path: "/v1/invites/care", group: "Invites" },
101
+ { method: "POST", path: "/v1/invites/care/accept", group: "Invites" },
102
+ // Deprecated: sunset on 2026-12-01, used only by the deprecated invite methods.
94
103
  { method: "POST", path: "/v1/invites/practitioner", group: "Invites" },
95
104
  { method: "POST", path: "/v1/invites/patient", group: "Invites" },
96
105
  { method: "POST", path: "/v1/invites/practitioner/accept", group: "Invites" },
@@ -48,7 +48,7 @@ exports.OVOK_CORE_REQUIREMENTS = {
48
48
  description: "The FHIR surface a server must provide for the @ovok/core client library's own methods to function.",
49
49
  software: {
50
50
  name: "@ovok/core",
51
- version: "0.4.46",
51
+ version: "0.4.47",
52
52
  },
53
53
  fhirVersion: "4.0.1",
54
54
  format: ["json"],
@@ -18,7 +18,7 @@ export { useRecentAlarms, useRecentOutOfBed, useRecentSlimNotifications, useSlim
18
18
  export { useCreateNotificationNote, useCreateSignalsAlertNote, useCreateSignalsRawAlertNote, useDeleteNotificationNote, useDeleteSignalsNote, useNotificationNotes, useSignalsAlertNotes, useSignalsRawAlertNotes, useUpdateNotificationNote, useUpdateSignalsNote, } from "./notification-note-hooks";
19
19
  export { useAcknowledgeSlimAlarm, useAcknowledgeSlimMedicalNotification, } from "./notification-ack-hooks";
20
20
  export { useCmsDocument, useCmsDocuments, useLegalPage, useReleaseNotes, useTranslations, } from "./cms-hooks";
21
- export { useAcceptInvite, useInvitePatient, useInvitePractitioner, } from "./invites-hooks";
21
+ export { useAcceptCareInvite, useAcceptInvite, useAcceptRecordShare, useInvitePatient, useInvitePractitioner, useInviteToCare, useShareRecord, } from "./invites-hooks";
22
22
  export { useCurrentPatientProfile, useExtractQuestionnaireObservations, usePatientAppointments, usePatientCarePlans, usePatientDevices, usePatientMeasurement, usePatientMeasurementHistory, usePatientDashboard, usePatientLatestObservations, usePatientNotifications, usePatientQuestionnaireResponses, usePatientQuestionnaires, usePatientSchedules, usePatientSlots, usePopulateQuestionnaire, useSubmitQuestionnaireResponse, } from "./patient-hooks";
23
23
  export { useCreatePatientSharingInvite, usePatientSharing, usePatientSharingSettings, useRedeemPatientSharingInvite, useRevokePatientSharing, useUpdatePatientSharingSettings, } from "./patient-sharing-hooks";
24
24
  export { useAuthorizeWearableConnection, useCreateWearableProvider, useDeleteWearableConnection, useDeleteWearableProvider, useUpdateWearableProvider, useWearableConnections, useWearableProviders, } from "./wearables-hooks";
@@ -35,8 +35,8 @@ var __importStar = (this && this.__importStar) || (function () {
35
35
  })();
36
36
  Object.defineProperty(exports, "__esModule", { value: true });
37
37
  exports.useSlimPatientThresholdV2 = exports.useSetMedicalConsent = exports.useSetLegalConsent = exports.useRepushUnconfirmedLimits = exports.useMedicalConsent = exports.useLegalConsent = exports.useChangeHistory = exports.useEmailTemplates = exports.useUpdateProjectTextSetting = exports.useUpdateLocalization = exports.useUpdateI18nextDocument = exports.useLocalizations = exports.useLocales = exports.useI18nextDocument = exports.useVideoCallAppointments = exports.useVideoCallAccess = exports.useDocuments = exports.useCreateVideoCallUserAccess = exports.useCreateVideoCallAppointment = exports.useContent = exports.useConsentSignature = exports.useOvokPoll = exports.usePublicApiEndpoints = exports.useProjectSettings = exports.useProjectFeatures = exports.useOvokRequest = exports.useOvokMutation = exports.useCapabilityStatement = exports.useSlimPatients = exports.useSlimDevices = exports.useSlimDeviceTelemetry = exports.useAdministeredProjects = exports.useUrineTests = exports.useSaveMeasurement = exports.useObservations = exports.useEcgRecording = exports.observationsToMeasurements = exports.OvokProvider = exports.useClient = exports.useCachedBinaryUrl = exports.reactContext = exports.useSubscription = exports.useSearchResources = exports.useSearchOne = exports.useSearch = exports.useResource = exports.usePrevious = exports.useMedplumProfile = exports.useMedplumNavigate = exports.useMedplumContext = void 0;
38
- exports.usePatientSharingSettings = exports.usePatientSharing = exports.useCreatePatientSharingInvite = exports.useSubmitQuestionnaireResponse = exports.usePopulateQuestionnaire = exports.usePatientSlots = exports.usePatientSchedules = exports.usePatientQuestionnaires = exports.usePatientQuestionnaireResponses = exports.usePatientNotifications = exports.usePatientLatestObservations = exports.usePatientDashboard = exports.usePatientMeasurementHistory = exports.usePatientMeasurement = exports.usePatientDevices = exports.usePatientCarePlans = exports.usePatientAppointments = exports.useExtractQuestionnaireObservations = exports.useCurrentPatientProfile = exports.useInvitePractitioner = exports.useInvitePatient = exports.useAcceptInvite = exports.useTranslations = exports.useReleaseNotes = exports.useLegalPage = exports.useCmsDocuments = exports.useCmsDocument = exports.useAcknowledgeSlimMedicalNotification = exports.useAcknowledgeSlimAlarm = exports.useUpdateSignalsNote = exports.useUpdateNotificationNote = exports.useSignalsRawAlertNotes = exports.useSignalsAlertNotes = exports.useNotificationNotes = exports.useDeleteSignalsNote = exports.useDeleteNotificationNote = exports.useCreateSignalsRawAlertNote = exports.useCreateSignalsAlertNote = exports.useCreateNotificationNote = exports.useSlimOutOfBedNotifications = exports.useSlimNotifications = exports.useSlimMedicalNotifications = exports.useSlimAlarms = exports.useRecentSlimNotifications = exports.useRecentOutOfBed = exports.useRecentAlarms = exports.useUpdateSlimThresholdV2 = exports.useUpdateSlimPatientThresholdV2 = exports.useUnconfirmedLimits = exports.useSlimThresholdV2 = void 0;
39
- exports.useUpdateSignalsSettings = exports.useSignalsThresholds = exports.useSignalsSettings = exports.useSignalsAlerts = exports.useSignalsAlert = exports.useSetSignalsThreshold = exports.useRemoveSignalsThreshold = exports.useEnableSignalsForPatient = exports.useAcknowledgeSignalsAlert = exports.useWearableProviders = exports.useWearableConnections = exports.useUpdateWearableProvider = exports.useDeleteWearableProvider = exports.useDeleteWearableConnection = exports.useCreateWearableProvider = exports.useAuthorizeWearableConnection = exports.useUpdatePatientSharingSettings = exports.useRevokePatientSharing = exports.useRedeemPatientSharingInvite = void 0;
38
+ exports.usePopulateQuestionnaire = exports.usePatientSlots = exports.usePatientSchedules = exports.usePatientQuestionnaires = exports.usePatientQuestionnaireResponses = exports.usePatientNotifications = exports.usePatientLatestObservations = exports.usePatientDashboard = exports.usePatientMeasurementHistory = exports.usePatientMeasurement = exports.usePatientDevices = exports.usePatientCarePlans = exports.usePatientAppointments = exports.useExtractQuestionnaireObservations = exports.useCurrentPatientProfile = exports.useShareRecord = exports.useInviteToCare = exports.useInvitePractitioner = exports.useInvitePatient = exports.useAcceptRecordShare = exports.useAcceptInvite = exports.useAcceptCareInvite = exports.useTranslations = exports.useReleaseNotes = exports.useLegalPage = exports.useCmsDocuments = exports.useCmsDocument = exports.useAcknowledgeSlimMedicalNotification = exports.useAcknowledgeSlimAlarm = exports.useUpdateSignalsNote = exports.useUpdateNotificationNote = exports.useSignalsRawAlertNotes = exports.useSignalsAlertNotes = exports.useNotificationNotes = exports.useDeleteSignalsNote = exports.useDeleteNotificationNote = exports.useCreateSignalsRawAlertNote = exports.useCreateSignalsAlertNote = exports.useCreateNotificationNote = exports.useSlimOutOfBedNotifications = exports.useSlimNotifications = exports.useSlimMedicalNotifications = exports.useSlimAlarms = exports.useRecentSlimNotifications = exports.useRecentOutOfBed = exports.useRecentAlarms = exports.useUpdateSlimThresholdV2 = exports.useUpdateSlimPatientThresholdV2 = exports.useUnconfirmedLimits = exports.useSlimThresholdV2 = void 0;
39
+ exports.useUpdateSignalsSettings = exports.useSignalsThresholds = exports.useSignalsSettings = exports.useSignalsAlerts = exports.useSignalsAlert = exports.useSetSignalsThreshold = exports.useRemoveSignalsThreshold = exports.useEnableSignalsForPatient = exports.useAcknowledgeSignalsAlert = exports.useWearableProviders = exports.useWearableConnections = exports.useUpdateWearableProvider = exports.useDeleteWearableProvider = exports.useDeleteWearableConnection = exports.useCreateWearableProvider = exports.useAuthorizeWearableConnection = exports.useUpdatePatientSharingSettings = exports.useRevokePatientSharing = exports.useRedeemPatientSharingInvite = exports.usePatientSharingSettings = exports.usePatientSharing = exports.useCreatePatientSharingInvite = exports.useSubmitQuestionnaireResponse = void 0;
40
40
  /*
41
41
  * The only React-dependent module in the package.
42
42
  *
@@ -149,9 +149,13 @@ Object.defineProperty(exports, "useLegalPage", { enumerable: true, get: function
149
149
  Object.defineProperty(exports, "useReleaseNotes", { enumerable: true, get: function () { return cms_hooks_1.useReleaseNotes; } });
150
150
  Object.defineProperty(exports, "useTranslations", { enumerable: true, get: function () { return cms_hooks_1.useTranslations; } });
151
151
  var invites_hooks_1 = require("./invites-hooks");
152
+ Object.defineProperty(exports, "useAcceptCareInvite", { enumerable: true, get: function () { return invites_hooks_1.useAcceptCareInvite; } });
152
153
  Object.defineProperty(exports, "useAcceptInvite", { enumerable: true, get: function () { return invites_hooks_1.useAcceptInvite; } });
154
+ Object.defineProperty(exports, "useAcceptRecordShare", { enumerable: true, get: function () { return invites_hooks_1.useAcceptRecordShare; } });
153
155
  Object.defineProperty(exports, "useInvitePatient", { enumerable: true, get: function () { return invites_hooks_1.useInvitePatient; } });
154
156
  Object.defineProperty(exports, "useInvitePractitioner", { enumerable: true, get: function () { return invites_hooks_1.useInvitePractitioner; } });
157
+ Object.defineProperty(exports, "useInviteToCare", { enumerable: true, get: function () { return invites_hooks_1.useInviteToCare; } });
158
+ Object.defineProperty(exports, "useShareRecord", { enumerable: true, get: function () { return invites_hooks_1.useShareRecord; } });
155
159
  var patient_hooks_1 = require("./patient-hooks");
156
160
  Object.defineProperty(exports, "useCurrentPatientProfile", { enumerable: true, get: function () { return patient_hooks_1.useCurrentPatientProfile; } });
157
161
  Object.defineProperty(exports, "useExtractQuestionnaireObservations", { enumerable: true, get: function () { return patient_hooks_1.useExtractQuestionnaireObservations; } });
@@ -1,5 +1,11 @@
1
- import { AcceptInviteBody, AcceptInviteResult, InviteBody, InviteSent } from "../client/invites";
1
+ import { AcceptInviteBody, AcceptInviteResult, AcceptRecordShareBody, InviteBody, InviteSent, RecordShareAccepted, RecordShareBody } from "../client/invites";
2
2
  import { OvokMutationState } from "./api-hooks";
3
+ export declare const useShareRecord: () => OvokMutationState<RecordShareBody, InviteSent>;
4
+ export declare const useInviteToCare: () => OvokMutationState<InviteBody, InviteSent>;
5
+ export declare const useAcceptRecordShare: () => OvokMutationState<AcceptRecordShareBody, RecordShareAccepted>;
6
+ export declare const useAcceptCareInvite: () => OvokMutationState<AcceptInviteBody, AcceptInviteResult>;
7
+ /** @deprecated Use useShareRecord with `recipient: "practitioner"`; the route sunsets on 2026-12-01. */
3
8
  export declare const useInvitePractitioner: () => OvokMutationState<InviteBody, InviteSent>;
9
+ /** @deprecated Use useInviteToCare; the route sunsets on 2026-12-01. */
4
10
  export declare const useInvitePatient: () => OvokMutationState<InviteBody, InviteSent>;
5
11
  export declare const useAcceptInvite: () => OvokMutationState<AcceptInviteBody, AcceptInviteResult>;
@@ -1,11 +1,29 @@
1
1
  "use strict";
2
2
  "use client";
3
3
  Object.defineProperty(exports, "__esModule", { value: true });
4
- exports.useAcceptInvite = exports.useInvitePatient = exports.useInvitePractitioner = void 0;
4
+ exports.useAcceptInvite = exports.useInvitePatient = exports.useInvitePractitioner = exports.useAcceptCareInvite = exports.useAcceptRecordShare = exports.useInviteToCare = exports.useShareRecord = void 0;
5
5
  const api_hooks_1 = require("./api-hooks");
6
6
  const notification_invalidation_1 = require("./notification-invalidation");
7
+ const useShareRecord = () => (0, api_hooks_1.useOvokMutation)((client, body) => client.shareRecord(body));
8
+ exports.useShareRecord = useShareRecord;
9
+ const useInviteToCare = () => (0, api_hooks_1.useOvokMutation)((client, body) => client.inviteToCare(body));
10
+ exports.useInviteToCare = useInviteToCare;
11
+ const useAcceptRecordShare = () => (0, api_hooks_1.useOvokMutation)(async (client, body) => {
12
+ const result = await client.acceptRecordShare(body);
13
+ (0, notification_invalidation_1.notifyNotificationChanges)(client, { type: "patient-sharing" });
14
+ return result;
15
+ });
16
+ exports.useAcceptRecordShare = useAcceptRecordShare;
17
+ const useAcceptCareInvite = () => (0, api_hooks_1.useOvokMutation)(async (client, body) => {
18
+ const result = await client.acceptCareInvite(body);
19
+ (0, notification_invalidation_1.notifyNotificationChanges)(client, { type: "patient-sharing" });
20
+ return result;
21
+ });
22
+ exports.useAcceptCareInvite = useAcceptCareInvite;
23
+ /** @deprecated Use useShareRecord with `recipient: "practitioner"`; the route sunsets on 2026-12-01. */
7
24
  const useInvitePractitioner = () => (0, api_hooks_1.useOvokMutation)((client, body) => client.invitePractitioner(body));
8
25
  exports.useInvitePractitioner = useInvitePractitioner;
26
+ /** @deprecated Use useInviteToCare; the route sunsets on 2026-12-01. */
9
27
  const useInvitePatient = () => (0, api_hooks_1.useOvokMutation)((client, body) => client.invitePatient(body));
10
28
  exports.useInvitePatient = useInvitePatient;
11
29
  const useAcceptInvite = () => (0, api_hooks_1.useOvokMutation)(async (client, body) => {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@ovok/core",
3
- "version": "0.4.46",
3
+ "version": "0.4.47",
4
4
  "private": false,
5
5
  "main": "dist/index.js",
6
6
  "types": "dist/index.d.ts",