@awell-health/awell-extensions 2.0.177 → 2.0.179

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.
@@ -50,7 +50,10 @@ export declare const settings: {
50
50
  required: false;
51
51
  };
52
52
  };
53
- export declare const rateLimitDurationSchema: z.ZodOptional<z.ZodEffects<z.ZodString, Duration, string>>;
53
+ export declare const rateLimitDurationSchema: z.ZodOptional<z.ZodEffects<z.ZodEffects<z.ZodString, string, string>, {
54
+ value: number;
55
+ unit: "seconds" | "minutes" | "hours" | "days";
56
+ }, string>>;
54
57
  export declare const SettingsValidationSchema: z.ZodObject<{
55
58
  base_url: z.ZodString;
56
59
  auth_url: z.ZodString;
@@ -63,7 +66,10 @@ export declare const SettingsValidationSchema: z.ZodObject<{
63
66
  */
64
67
  username: z.ZodOptional<z.ZodString>;
65
68
  password: z.ZodOptional<z.ZodString>;
66
- rateLimitDuration: z.ZodOptional<z.ZodEffects<z.ZodString, Duration, string>>;
69
+ rateLimitDuration: z.ZodOptional<z.ZodEffects<z.ZodEffects<z.ZodString, string, string>, {
70
+ value: number;
71
+ unit: "seconds" | "minutes" | "hours" | "days";
72
+ }, string>>;
67
73
  }, "strip", z.ZodTypeAny, {
68
74
  auth_url: string;
69
75
  client_id: string;
@@ -71,7 +77,10 @@ export declare const SettingsValidationSchema: z.ZodObject<{
71
77
  base_url: string;
72
78
  username?: string | undefined;
73
79
  password?: string | undefined;
74
- rateLimitDuration?: Duration | undefined;
80
+ rateLimitDuration?: {
81
+ value: number;
82
+ unit: "seconds" | "minutes" | "hours" | "days";
83
+ } | undefined;
75
84
  }, {
76
85
  auth_url: string;
77
86
  client_id: string;
@@ -1,6 +1,7 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.SettingsValidationSchema = exports.rateLimitDurationSchema = exports.settings = void 0;
4
+ const lodash_1 = require("lodash");
4
5
  const zod_1 = require("zod");
5
6
  exports.settings = {
6
7
  base_url: {
@@ -55,10 +56,25 @@ exports.settings = {
55
56
  };
56
57
  exports.rateLimitDurationSchema = zod_1.z
57
58
  .string()
58
- .regex(/^\d+\s+[smhd]$/, 'Duration must be in format {number} {unit} where unit is s,m,h,d')
59
+ .refine((val) => {
60
+ try {
61
+ const [number, unit] = val.split(' ');
62
+ const parsedUnit = parseDurationUnit(unit);
63
+ return (0, lodash_1.isFinite)(Number(number)) && !(0, lodash_1.isNil)(parsedUnit);
64
+ }
65
+ catch (error) {
66
+ return false;
67
+ }
68
+ }, {
69
+ message: 'Duration must be in format {number} {unit} where unit is seconds, minutes, hours or days',
70
+ })
59
71
  .transform((val) => {
60
72
  const [number, unit] = val.split(' ');
61
- return `${number}${unit}`;
73
+ const parsedUnit = parseDurationUnit(unit);
74
+ return {
75
+ value: Number(number),
76
+ unit: parsedUnit,
77
+ };
62
78
  })
63
79
  .optional();
64
80
  exports.SettingsValidationSchema = zod_1.z.object({
@@ -75,4 +91,30 @@ exports.SettingsValidationSchema = zod_1.z.object({
75
91
  password: zod_1.z.string().optional(),
76
92
  rateLimitDuration: exports.rateLimitDurationSchema,
77
93
  });
94
+ const parseDurationUnit = (unit) => {
95
+ if (!unit)
96
+ throw new Error('Duration unit is required');
97
+ const normalized = unit.toLowerCase().trim();
98
+ switch (normalized) {
99
+ case 's':
100
+ case 'second':
101
+ case 'seconds':
102
+ return 'seconds';
103
+ case 'm':
104
+ case 'min':
105
+ case 'minute':
106
+ case 'minutes':
107
+ return 'minutes';
108
+ case 'h':
109
+ case 'hour':
110
+ case 'hours':
111
+ return 'hours';
112
+ case 'd':
113
+ case 'day':
114
+ case 'days':
115
+ return 'days';
116
+ default:
117
+ throw new Error(`Invalid duration unit: ${unit}. Valid units are: s, m, h, d`);
118
+ }
119
+ };
78
120
  //# sourceMappingURL=settings.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"settings.js","sourceRoot":"","sources":["../../../extensions/elation/settings.ts"],"names":[],"mappings":";;;AACA,6BAAwC;AAE3B,QAAA,QAAQ,GAAG;IACtB,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,KAAK,EAAE,UAAU;QACjB,UAAU,EAAE,KAAK;QACjB,WAAW,EAAE,8BAA8B;QAC3C,QAAQ,EAAE,IAAI;KACf;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,KAAK,EAAE,mBAAmB;QAC1B,UAAU,EAAE,KAAK;QACjB,WAAW,EAAE,sDAAsD;QACnE,QAAQ,EAAE,IAAI;KACf;IACD,SAAS,EAAE;QACT,GAAG,EAAE,WAAW;QAChB,KAAK,EAAE,WAAW;QAClB,UAAU,EAAE,KAAK;QACjB,WAAW,EAAE,mDAAmD;QAChE,QAAQ,EAAE,IAAI;KACf;IACD,aAAa,EAAE;QACb,GAAG,EAAE,eAAe;QACpB,KAAK,EAAE,eAAe;QACtB,UAAU,EAAE,IAAI;QAChB,WAAW,EAAE,uDAAuD;QACpE,QAAQ,EAAE,IAAI;KACf;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,KAAK,EAAE,UAAU;QACjB,UAAU,EAAE,KAAK;QACjB,WAAW,EACT,iJAAiJ;QACnJ,QAAQ,EAAE,KAAK;KAChB;IACD,QAAQ,EAAE;QACR,GAAG,EAAE,UAAU;QACf,KAAK,EAAE,UAAU;QACjB,UAAU,EAAE,IAAI;QAChB,WAAW,EACT,iJAAiJ;QACnJ,QAAQ,EAAE,KAAK;KAChB;IACD,iBAAiB,EAAE;QACjB,GAAG,EAAE,mBAAmB;QACxB,KAAK,EAAE,qBAAqB;QAC5B,UAAU,EAAE,KAAK;QACjB,WAAW,EACT,wKAAwK;QAC1K,QAAQ,EAAE,KAAK;KAChB;CACgC,CAAA;AAEtB,QAAA,uBAAuB,GAAG,OAAC;KACrC,MAAM,EAAE;KACR,KAAK,CACJ,gBAAgB,EAChB,kEAAkE,CACnE;KACA,SAAS,CAAC,CAAC,GAAG,EAAY,EAAE;IAC3B,MAAM,CAAC,MAAM,EAAE,IAAI,CAAC,GAAG,GAAG,CAAC,KAAK,CAAC,GAAG,CAAC,CAAA;IACrC,OAAO,GAAG,MAAM,GAAG,IAAI,EAAc,CAAA;AACvC,CAAC,CAAC;KACD,QAAQ,EAAE,CAAA;AAEA,QAAA,wBAAwB,GAAG,OAAC,CAAC,MAAM,CAAC;IAC/C,QAAQ,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC3B,QAAQ,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC3B,SAAS,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAC5B,aAAa,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,GAAG,CAAC,CAAC,CAAC;IAChC;;;;OAIG;IACH,QAAQ,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IAC/B,QAAQ,EAAE,OAAC,CAAC,MAAM,EAAE,CAAC,QAAQ,EAAE;IAC/B,iBAAiB,EAAE,+BAAuB;CACS,CAAC,CAAA"}
1
+ {"version":3,"file":"settings.js","sourceRoot":"","sources":["../../../extensions/elation/settings.ts"],"names":[],"mappings":"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"}
@@ -2,6 +2,8 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.appointmentCreatedOrUpdated = void 0;
4
4
  const constants_1 = require("../constants");
5
+ const settings_1 = require("../settings");
6
+ const lodash_1 = require("lodash");
5
7
  const dataPoints = {
6
8
  appointmentId: {
7
9
  key: 'appointmentId',
@@ -15,13 +17,38 @@ const dataPoints = {
15
17
  exports.appointmentCreatedOrUpdated = {
16
18
  key: 'appointmentCreatedOrUpdated',
17
19
  dataPoints,
18
- onEvent: async ({ payload: { payload, settings }, onSuccess, onError }) => {
20
+ onEvent: async ({ payload: { payload, settings }, onSuccess, onError, helpers: { rateLimiter }, }) => {
19
21
  const { action, resource, data } = payload;
20
22
  const { id: appointmentId, patient: patientId } = data;
21
23
  // skip non 'saved' actions for that webhook
22
24
  if (action !== 'saved') {
23
25
  return;
24
26
  }
27
+ // rate limiting
28
+ const { success, data: duration } = settings_1.rateLimitDurationSchema.safeParse(settings.rateLimitDuration);
29
+ if (success === true && !(0, lodash_1.isNil)(duration)) {
30
+ const limiter = rateLimiter('elation-appointment', {
31
+ requests: 1,
32
+ duration,
33
+ });
34
+ const { success } = await limiter.limit(appointmentId.toString());
35
+ if (!success) {
36
+ console.warn({
37
+ data,
38
+ resource,
39
+ action,
40
+ message: 'Rate limit exceeded. 200 OK response sent to Elation to prevent further requests.',
41
+ });
42
+ await onError({
43
+ response: {
44
+ statusCode: 200,
45
+ message: 'Rate limit exceeded. 200 OK response sent to Elation to prevent further requests.',
46
+ },
47
+ });
48
+ return;
49
+ }
50
+ console.log(`Rate limit success for appointment_id=${appointmentId}`);
51
+ }
25
52
  if (resource !== 'appointments') {
26
53
  await onError({
27
54
  response: {
@@ -1 +1 @@
1
- {"version":3,"file":"appointmentCreatedOrUpdated.js","sourceRoot":"","sources":["../../../../extensions/elation/webhooks/appointmentCreatedOrUpdated.ts"],"names":[],"mappings":";;;AAIA,4CAA6C;AAG7C,MAAM,UAAU,GAAG;IACjB,aAAa,EAAE;QACb,GAAG,EAAE,eAAe;QACpB,SAAS,EAAE,QAAQ;KACpB;IACD,WAAW,EAAE;QACX,GAAG,EAAE,aAAa;QAClB,SAAS,EAAE,MAAM;KAClB;CAC4C,CAAA;AAElC,QAAA,2BAA2B,GAGpC;IACF,GAAG,EAAE,6BAA6B;IAClC,UAAU;IACV,OAAO,EAAE,KAAK,EAAE,EAAE,OAAO,EAAE,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE,SAAS,EAAE,OAAO,EAAE,EAAE,EAAE;QACxE,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,IAAI,EAAE,GAAG,OAAO,CAAA;QAC1C,MAAM,EAAE,EAAE,EAAE,aAAa,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,IAAI,CAAA;QAEtD,6CAA6C;QAC7C,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;YACvB,OAAM;QACR,CAAC;QAED,IAAI,QAAQ,KAAK,cAAc,EAAE,CAAC;YAChC,MAAM,OAAO,CAAC;gBACZ,QAAQ,EAAE;oBACR,UAAU,EAAE,GAAG;oBACf,OAAO,EAAE,gCAAgC;iBAC1C;aACF,CAAC,CAAA;QACJ,CAAC;aAAM,CAAC;YACN,MAAM,SAAS,CAAC;gBACd,WAAW,EAAE;oBACX,aAAa,EAAE,MAAM,CAAC,aAAa,CAAC;oBACpC,WAAW,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;iBAClC;gBACD,kBAAkB,EAAE;oBAClB,MAAM,EAAE,0BAAc;oBACtB,KAAK,EAAE,MAAM,CAAC,SAAS,CAAC;iBACzB;aACF,CAAC,CAAA;QACJ,CAAC;IACH,CAAC;CACF,CAAA"}
1
+ {"version":3,"file":"appointmentCreatedOrUpdated.js","sourceRoot":"","sources":["../../../../extensions/elation/webhooks/appointmentCreatedOrUpdated.ts"],"names":[],"mappings":";;;AAIA,4CAA6C;AAE7C,0CAAqD;AACrD,mCAA8B;AAE9B,MAAM,UAAU,GAAG;IACjB,aAAa,EAAE;QACb,GAAG,EAAE,eAAe;QACpB,SAAS,EAAE,QAAQ;KACpB;IACD,WAAW,EAAE;QACX,GAAG,EAAE,aAAa;QAClB,SAAS,EAAE,MAAM;KAClB;CAC4C,CAAA;AAElC,QAAA,2BAA2B,GAGpC;IACF,GAAG,EAAE,6BAA6B;IAClC,UAAU;IACV,OAAO,EAAE,KAAK,EAAE,EACd,OAAO,EAAE,EAAE,OAAO,EAAE,QAAQ,EAAE,EAC9B,SAAS,EACT,OAAO,EACP,OAAO,EAAE,EAAE,WAAW,EAAE,GACzB,EAAE,EAAE;QACH,MAAM,EAAE,MAAM,EAAE,QAAQ,EAAE,IAAI,EAAE,GAAG,OAAO,CAAA;QAC1C,MAAM,EAAE,EAAE,EAAE,aAAa,EAAE,OAAO,EAAE,SAAS,EAAE,GAAG,IAAI,CAAA;QAEtD,6CAA6C;QAC7C,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;YACvB,OAAM;QACR,CAAC;QAED,gBAAgB;QAChB,MAAM,EAAE,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,GAAG,kCAAuB,CAAC,SAAS,CACnE,QAAQ,CAAC,iBAAiB,CAC3B,CAAA;QACD,IAAI,OAAO,KAAK,IAAI,IAAI,CAAC,IAAA,cAAK,EAAC,QAAQ,CAAC,EAAE,CAAC;YACzC,MAAM,OAAO,GAAG,WAAW,CAAC,qBAAqB,EAAE;gBACjD,QAAQ,EAAE,CAAC;gBACX,QAAQ;aACT,CAAC,CAAA;YACF,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,OAAO,CAAC,KAAK,CAAC,aAAa,CAAC,QAAQ,EAAE,CAAC,CAAA;YACjE,IAAI,CAAC,OAAO,EAAE,CAAC;gBACb,OAAO,CAAC,IAAI,CAAC;oBACX,IAAI;oBACJ,QAAQ;oBACR,MAAM;oBACN,OAAO,EACL,mFAAmF;iBACtF,CAAC,CAAA;gBACF,MAAM,OAAO,CAAC;oBACZ,QAAQ,EAAE;wBACR,UAAU,EAAE,GAAG;wBACf,OAAO,EACL,mFAAmF;qBACtF;iBACF,CAAC,CAAA;gBACF,OAAM;YACR,CAAC;YACD,OAAO,CAAC,GAAG,CAAC,yCAAyC,aAAa,EAAE,CAAC,CAAA;QACvE,CAAC;QAED,IAAI,QAAQ,KAAK,cAAc,EAAE,CAAC;YAChC,MAAM,OAAO,CAAC;gBACZ,QAAQ,EAAE;oBACR,UAAU,EAAE,GAAG;oBACf,OAAO,EAAE,gCAAgC;iBAC1C;aACF,CAAC,CAAA;QACJ,CAAC;aAAM,CAAC;YACN,MAAM,SAAS,CAAC;gBACd,WAAW,EAAE;oBACX,aAAa,EAAE,MAAM,CAAC,aAAa,CAAC;oBACpC,WAAW,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;iBAClC;gBACD,kBAAkB,EAAE;oBAClB,MAAM,EAAE,0BAAc;oBACtB,KAAK,EAAE,MAAM,CAAC,SAAS,CAAC;iBACzB;aACF,CAAC,CAAA;QACJ,CAAC;IACH,CAAC;CACF,CAAA"}
@@ -1,6 +1,8 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.patientCreatedOrUpdated = void 0;
4
+ const settings_1 = require("../settings");
5
+ const lodash_1 = require("lodash");
4
6
  const dataPoints = {
5
7
  patientId: {
6
8
  key: 'patientId',
@@ -14,13 +16,38 @@ const dataPoints = {
14
16
  exports.patientCreatedOrUpdated = {
15
17
  key: 'patientCreatedOrUpdated',
16
18
  dataPoints,
17
- onEvent: async ({ payload: { payload, settings }, onSuccess, onError }) => {
19
+ onEvent: async ({ payload: { payload, settings }, onSuccess, onError, helpers: { rateLimiter }, }) => {
18
20
  const { data, resource, action } = payload;
19
21
  const { id: patientId } = data;
20
22
  // skip non 'saved' actions for that webhook
21
23
  if (action !== 'saved') {
22
24
  return;
23
25
  }
26
+ // rate limiting
27
+ const { success, data: duration } = settings_1.rateLimitDurationSchema.safeParse(settings.rateLimitDuration);
28
+ if (success === true && !(0, lodash_1.isNil)(duration)) {
29
+ const limiter = rateLimiter('elation-patient', {
30
+ requests: 1,
31
+ duration,
32
+ });
33
+ const { success } = await limiter.limit(patientId.toString());
34
+ if (!success) {
35
+ console.warn({
36
+ data,
37
+ resource,
38
+ action,
39
+ message: 'Rate limit exceeded. 200 OK response sent to Elation to prevent further requests.',
40
+ });
41
+ await onError({
42
+ response: {
43
+ statusCode: 200,
44
+ message: 'Rate limit exceeded. 200 OK response sent to Elation to prevent further requests.',
45
+ },
46
+ });
47
+ return;
48
+ }
49
+ console.log(`Rate limit success for patient_id=${patientId}`);
50
+ }
24
51
  if (resource !== 'patients') {
25
52
  await onError({
26
53
  response: {
@@ -1 +1 @@
1
- {"version":3,"file":"patientCreatedOrUpdated.js","sourceRoot":"","sources":["../../../../extensions/elation/webhooks/patientCreatedOrUpdated.ts"],"names":[],"mappings":";;;AAMA,MAAM,UAAU,GAAG;IACjB,SAAS,EAAE;QACT,GAAG,EAAE,WAAW;QAChB,SAAS,EAAE,QAAQ;KACpB;IACD,OAAO,EAAE;QACP,GAAG,EAAE,SAAS;QACd,SAAS,EAAE,MAAM;KAClB;CAC4C,CAAA;AAElC,QAAA,uBAAuB,GAGhC;IACF,GAAG,EAAE,yBAAyB;IAC9B,UAAU;IACV,OAAO,EAAE,KAAK,EAAE,EAAE,OAAO,EAAE,EAAE,OAAO,EAAE,QAAQ,EAAE,EAAE,SAAS,EAAE,OAAO,EAAE,EAAE,EAAE;QACxE,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,GAAG,OAAO,CAAA;QAC1C,MAAM,EAAE,EAAE,EAAE,SAAS,EAAE,GAAG,IAAI,CAAA;QAE9B,4CAA4C;QAC5C,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;YACvB,OAAM;QACR,CAAC;QAED,IAAI,QAAQ,KAAK,UAAU,EAAE,CAAC;YAC5B,MAAM,OAAO,CAAC;gBACZ,QAAQ,EAAE;oBACR,UAAU,EAAE,GAAG;oBACf,OAAO,EAAE,2BAA2B;iBACrC;aACF,CAAC,CAAA;QACJ,CAAC;aAAM,CAAC;YACN,MAAM,SAAS,CAAC;gBACd,WAAW,EAAE;oBACX,SAAS,EAAE,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC;oBAC1B,OAAO,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;iBAC9B;gBACD,iDAAiD;gBACjD,kBAAkB,EAAE;oBAClB,MAAM,EAAE,gCAAgC;oBACxC,KAAK,EAAE,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC;iBACvB;aACF,CAAC,CAAA;QACJ,CAAC;IACH,CAAC;CACF,CAAA"}
1
+ {"version":3,"file":"patientCreatedOrUpdated.js","sourceRoot":"","sources":["../../../../extensions/elation/webhooks/patientCreatedOrUpdated.ts"],"names":[],"mappings":";;;AAKA,0CAAqD;AACrD,mCAA8B;AAE9B,MAAM,UAAU,GAAG;IACjB,SAAS,EAAE;QACT,GAAG,EAAE,WAAW;QAChB,SAAS,EAAE,QAAQ;KACpB;IACD,OAAO,EAAE;QACP,GAAG,EAAE,SAAS;QACd,SAAS,EAAE,MAAM;KAClB;CAC4C,CAAA;AAElC,QAAA,uBAAuB,GAGhC;IACF,GAAG,EAAE,yBAAyB;IAC9B,UAAU;IACV,OAAO,EAAE,KAAK,EAAE,EACd,OAAO,EAAE,EAAE,OAAO,EAAE,QAAQ,EAAE,EAC9B,SAAS,EACT,OAAO,EACP,OAAO,EAAE,EAAE,WAAW,EAAE,GACzB,EAAE,EAAE;QACH,MAAM,EAAE,IAAI,EAAE,QAAQ,EAAE,MAAM,EAAE,GAAG,OAAO,CAAA;QAC1C,MAAM,EAAE,EAAE,EAAE,SAAS,EAAE,GAAG,IAAI,CAAA;QAC9B,4CAA4C;QAC5C,IAAI,MAAM,KAAK,OAAO,EAAE,CAAC;YACvB,OAAM;QACR,CAAC;QAED,gBAAgB;QAChB,MAAM,EAAE,OAAO,EAAE,IAAI,EAAE,QAAQ,EAAE,GAAG,kCAAuB,CAAC,SAAS,CACnE,QAAQ,CAAC,iBAAiB,CAC3B,CAAA;QACD,IAAI,OAAO,KAAK,IAAI,IAAI,CAAC,IAAA,cAAK,EAAC,QAAQ,CAAC,EAAE,CAAC;YACzC,MAAM,OAAO,GAAG,WAAW,CAAC,iBAAiB,EAAE;gBAC7C,QAAQ,EAAE,CAAC;gBACX,QAAQ;aACT,CAAC,CAAA;YACF,MAAM,EAAE,OAAO,EAAE,GAAG,MAAM,OAAO,CAAC,KAAK,CAAC,SAAS,CAAC,QAAQ,EAAE,CAAC,CAAA;YAC7D,IAAI,CAAC,OAAO,EAAE,CAAC;gBACb,OAAO,CAAC,IAAI,CAAC;oBACX,IAAI;oBACJ,QAAQ;oBACR,MAAM;oBACN,OAAO,EACL,mFAAmF;iBACtF,CAAC,CAAA;gBACF,MAAM,OAAO,CAAC;oBACZ,QAAQ,EAAE;wBACR,UAAU,EAAE,GAAG;wBACf,OAAO,EACL,mFAAmF;qBACtF;iBACF,CAAC,CAAA;gBACF,OAAM;YACR,CAAC;YACD,OAAO,CAAC,GAAG,CAAC,qCAAqC,SAAS,EAAE,CAAC,CAAA;QAC/D,CAAC;QAED,IAAI,QAAQ,KAAK,UAAU,EAAE,CAAC;YAC5B,MAAM,OAAO,CAAC;gBACZ,QAAQ,EAAE;oBACR,UAAU,EAAE,GAAG;oBACf,OAAO,EAAE,2BAA2B;iBACrC;aACF,CAAC,CAAA;QACJ,CAAC;aAAM,CAAC;YACN,MAAM,SAAS,CAAC;gBACd,WAAW,EAAE;oBACX,SAAS,EAAE,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC;oBAC1B,OAAO,EAAE,IAAI,CAAC,SAAS,CAAC,IAAI,CAAC;iBAC9B;gBACD,iDAAiD;gBACjD,kBAAkB,EAAE;oBAClB,MAAM,EAAE,gCAAgC;oBACxC,KAAK,EAAE,MAAM,CAAC,IAAI,CAAC,EAAE,CAAC;iBACvB;aACF,CAAC,CAAA;QACJ,CAAC;IACH,CAAC;CACF,CAAA"}
@@ -14,9 +14,9 @@ export declare const FieldsSchema: z.ZodEffects<z.ZodObject<{
14
14
  healthie_patient_id: string;
15
15
  form_id: string;
16
16
  period?: string | undefined;
17
- frequency?: string | undefined;
18
- hour?: string | undefined;
19
17
  minute?: string | undefined;
18
+ hour?: string | undefined;
19
+ frequency?: string | undefined;
20
20
  weekday?: string | undefined;
21
21
  monthday?: string | undefined;
22
22
  is_recurring?: boolean | undefined;
@@ -25,9 +25,9 @@ export declare const FieldsSchema: z.ZodEffects<z.ZodObject<{
25
25
  healthie_patient_id: string;
26
26
  form_id: string;
27
27
  period?: string | undefined;
28
- frequency?: string | undefined;
29
- hour?: string | undefined;
30
28
  minute?: string | undefined;
29
+ hour?: string | undefined;
30
+ frequency?: string | undefined;
31
31
  weekday?: string | undefined;
32
32
  monthday?: string | undefined;
33
33
  is_recurring?: boolean | undefined;
@@ -36,9 +36,9 @@ export declare const FieldsSchema: z.ZodEffects<z.ZodObject<{
36
36
  healthie_patient_id: string;
37
37
  form_id: string;
38
38
  period?: string | undefined;
39
- frequency?: string | undefined;
40
- hour?: string | undefined;
41
39
  minute?: string | undefined;
40
+ hour?: string | undefined;
41
+ frequency?: string | undefined;
42
42
  weekday?: string | undefined;
43
43
  monthday?: string | undefined;
44
44
  is_recurring?: boolean | undefined;
@@ -47,9 +47,9 @@ export declare const FieldsSchema: z.ZodEffects<z.ZodObject<{
47
47
  healthie_patient_id: string;
48
48
  form_id: string;
49
49
  period?: string | undefined;
50
- frequency?: string | undefined;
51
- hour?: string | undefined;
52
50
  minute?: string | undefined;
51
+ hour?: string | undefined;
52
+ frequency?: string | undefined;
53
53
  weekday?: string | undefined;
54
54
  monthday?: string | undefined;
55
55
  is_recurring?: boolean | undefined;
@@ -7,7 +7,20 @@ export declare const simpleFormMockResponse: {
7
7
  release_id: string;
8
8
  key: string;
9
9
  metadata: string;
10
- questions: {
10
+ questions: ({
11
+ id: string;
12
+ definition_id: string;
13
+ title: string;
14
+ key: string;
15
+ dataPointValueType: null;
16
+ questionType: "NO_INPUT";
17
+ userQuestionType: "DESCRIPTION";
18
+ metadata: null;
19
+ options: never[];
20
+ rule: null;
21
+ questionConfig: null;
22
+ __typename: "Question";
23
+ } | {
11
24
  id: string;
12
25
  definition_id: string;
13
26
  title: string;
@@ -22,7 +35,11 @@ export declare const simpleFormMockResponse: {
22
35
  label: string;
23
36
  __typename: "Option";
24
37
  }[];
25
- }[];
38
+ metadata?: undefined;
39
+ rule?: undefined;
40
+ questionConfig?: undefined;
41
+ __typename?: undefined;
42
+ })[];
26
43
  };
27
44
  };
28
45
  export declare const simpleFormResponseMockResponse: {
@@ -11,6 +11,20 @@ exports.simpleFormMockResponse = {
11
11
  key: 'simple-form',
12
12
  metadata: '{"form": "metadata"}',
13
13
  questions: [
14
+ {
15
+ id: 'description-question-id',
16
+ definition_id: 'description-question-definition-id',
17
+ title: '<p class="slate-p">Description content</p>',
18
+ key: 'description',
19
+ dataPointValueType: null,
20
+ questionType: 'NO_INPUT',
21
+ userQuestionType: 'DESCRIPTION',
22
+ metadata: null,
23
+ options: [],
24
+ rule: null,
25
+ questionConfig: null,
26
+ __typename: 'Question',
27
+ },
14
28
  {
15
29
  id: 'question-id',
16
30
  definition_id: 'question-definition-id',
@@ -1 +1 @@
1
- {"version":3,"file":"submitQuestionnaireResponse.mocks.js","sourceRoot":"","sources":["../../../../../../extensions/medplum/actions/submitQuestionnaireResponse/__testdata__/submitQuestionnaireResponse.mocks.ts"],"names":[],"mappings":";;;AAMa,QAAA,sBAAsB,GAAG;IACpC,OAAO,EAAE,IAAI;IACb,IAAI,EAAE;QACJ,EAAE,EAAE,mBAAmB;QACvB,aAAa,EAAE,oBAAoB;QACnC,KAAK,EAAE,aAAa;QACpB,UAAU,EAAE,iBAAiB;QAC7B,GAAG,EAAE,aAAa;QAClB,QAAQ,EAAE,sBAAsB;QAChC,SAAS,EAAE;YACT;gBACE,EAAE,EAAE,aAAa;gBACjB,aAAa,EAAE,wBAAwB;gBACvC,KAAK,EAAE,wBAAwB;gBAC/B,GAAG,EAAE,oBAAoB;gBACzB,kBAAkB,EAAE,QAAQ;gBAC5B,YAAY,EAAE,iBAAiB;gBAC/B,gBAAgB,EAAE,iBAAiB;gBACnC,OAAO,EAAE;oBACP;wBACE,EAAE,EAAE,cAAc;wBAClB,KAAK,EAAE,CAAC;wBACR,YAAY,EAAE,GAAG;wBACjB,KAAK,EAAE,UAAU;wBACjB,UAAU,EAAE,QAAQ;qBACrB;oBACD;wBACE,EAAE,EAAE,cAAc;wBAClB,KAAK,EAAE,CAAC;wBACR,YAAY,EAAE,GAAG;wBACjB,KAAK,EAAE,UAAU;wBACjB,UAAU,EAAE,QAAQ;qBACrB;oBACD;wBACE,EAAE,EAAE,cAAc;wBAClB,KAAK,EAAE,CAAC;wBACR,YAAY,EAAE,GAAG;wBACjB,KAAK,EAAE,UAAU;wBACjB,UAAU,EAAE,QAAQ;qBACrB;iBACF;aACF;SACF;KACF;CACiC,CAAA;AAEvB,QAAA,8BAA8B,GAAG;IAC5C,OAAO,EAAE,IAAI;IACb,QAAQ,EAAE;QACR,OAAO,EAAE;YACP;gBACE,WAAW,EAAE,aAAa;gBAC1B,KAAK,EAAE,GAAG;gBACV,KAAK,EAAE,UAAU;gBACjB,UAAU,EAAE,QAAQ;aACrB;SACF;KACF;CACyC,CAAA"}
1
+ {"version":3,"file":"submitQuestionnaireResponse.mocks.js","sourceRoot":"","sources":["../../../../../../extensions/medplum/actions/submitQuestionnaireResponse/__testdata__/submitQuestionnaireResponse.mocks.ts"],"names":[],"mappings":";;;AAMa,QAAA,sBAAsB,GAAG;IACpC,OAAO,EAAE,IAAI;IACb,IAAI,EAAE;QACJ,EAAE,EAAE,mBAAmB;QACvB,aAAa,EAAE,oBAAoB;QACnC,KAAK,EAAE,aAAa;QACpB,UAAU,EAAE,iBAAiB;QAC7B,GAAG,EAAE,aAAa;QAClB,QAAQ,EAAE,sBAAsB;QAChC,SAAS,EAAE;YACT;gBACE,EAAE,EAAE,yBAAyB;gBAC7B,aAAa,EAAE,oCAAoC;gBACnD,KAAK,EAAE,4CAA4C;gBACnD,GAAG,EAAE,aAAa;gBAClB,kBAAkB,EAAE,IAAI;gBACxB,YAAY,EAAE,UAAU;gBACxB,gBAAgB,EAAE,aAAa;gBAC/B,QAAQ,EAAE,IAAI;gBACd,OAAO,EAAE,EAAE;gBACX,IAAI,EAAE,IAAI;gBACV,cAAc,EAAE,IAAI;gBACpB,UAAU,EAAE,UAAU;aACvB;YACD;gBACE,EAAE,EAAE,aAAa;gBACjB,aAAa,EAAE,wBAAwB;gBACvC,KAAK,EAAE,wBAAwB;gBAC/B,GAAG,EAAE,oBAAoB;gBACzB,kBAAkB,EAAE,QAAQ;gBAC5B,YAAY,EAAE,iBAAiB;gBAC/B,gBAAgB,EAAE,iBAAiB;gBACnC,OAAO,EAAE;oBACP;wBACE,EAAE,EAAE,cAAc;wBAClB,KAAK,EAAE,CAAC;wBACR,YAAY,EAAE,GAAG;wBACjB,KAAK,EAAE,UAAU;wBACjB,UAAU,EAAE,QAAQ;qBACrB;oBACD;wBACE,EAAE,EAAE,cAAc;wBAClB,KAAK,EAAE,CAAC;wBACR,YAAY,EAAE,GAAG;wBACjB,KAAK,EAAE,UAAU;wBACjB,UAAU,EAAE,QAAQ;qBACrB;oBACD;wBACE,EAAE,EAAE,cAAc;wBAClB,KAAK,EAAE,CAAC;wBACR,YAAY,EAAE,GAAG;wBACjB,KAAK,EAAE,UAAU;wBACjB,UAAU,EAAE,QAAQ;qBACrB;iBACF;aACF;SACF;KACF;CACiC,CAAA;AAEvB,QAAA,8BAA8B,GAAG;IAC5C,OAAO,EAAE,IAAI;IACb,QAAQ,EAAE;QACR,OAAO,EAAE;YACP;gBACE,WAAW,EAAE,aAAa;gBAC1B,KAAK,EAAE,GAAG;gBACV,KAAK,EAAE,UAAU;gBACjB,UAAU,EAAE,QAAQ;aACrB;SACF;KACF;CACyC,CAAA"}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@awell-health/awell-extensions",
3
- "version": "2.0.177",
3
+ "version": "2.0.179",
4
4
  "packageManager": "yarn@4.5.3",
5
5
  "main": "dist/src/index.js",
6
6
  "repository": {
@@ -78,8 +78,8 @@
78
78
  "typescript": "5.7.2"
79
79
  },
80
80
  "dependencies": {
81
- "@awell-health/awell-sdk": "^0.1.20",
82
- "@awell-health/extensions-core": "1.0.18",
81
+ "@awell-health/awell-sdk": "^0.1.21",
82
+ "@awell-health/extensions-core": "1.0.21",
83
83
  "@awell-health/healthie-sdk": "^0.1.1",
84
84
  "@dropbox/sign": "^1.8.0",
85
85
  "@hubspot/api-client": "^11.2.0",