cauthy-auth 0.25.0 → 0.27.0

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/dist/index.js CHANGED
@@ -1243,11 +1243,14 @@ function createCauthy(given = {}) {
1243
1243
  "/me/mfa/phone/remove",
1244
1244
  "/sign-in/mfa/methods",
1245
1245
  "/sign-in/mfa/send",
1246
+ "/sign-in/mfa/email",
1246
1247
  "/sign-in/mfa/push",
1247
1248
  "/sign-in/mfa/push/events",
1248
1249
  "/sign-in/mfa/push/finish",
1249
1250
  "/me/sessions",
1250
1251
  "/me/sessions/end",
1252
+ "/me/legal",
1253
+ "/me/legal/accept",
1251
1254
  "/me/email",
1252
1255
  "/me/identities",
1253
1256
  "/me/identities/unlink",
@@ -1306,6 +1309,8 @@ function createCauthy(given = {}) {
1306
1309
  passkeyOnCauthy: place.error ? true : place.data?.on_cauthy === true,
1307
1310
  // A company's sign-in, found by the person's work address.
1308
1311
  sso: Array.isArray(sso.data) && sso.data.some((c) => c?.discoverable === true),
1312
+ // The terms a sign-up accepts and the consents it answers, when the workspace asks any.
1313
+ ...settings.data?.legal ? { legal: legalOf(settings.data.legal) } : {},
1309
1314
  ...settings.data?.captcha_enabled === true && settings.data?.captcha_site_key ? { captchaSiteKey: String(settings.data.captcha_site_key) } : {}
1310
1315
  });
1311
1316
  }
@@ -1466,11 +1471,15 @@ function createCauthy(given = {}) {
1466
1471
  if (res.error) return problem(res.status, res.error.code, res.error.message, void 0, mine.headers);
1467
1472
  return json(factorsOf(res.data), 200, mine.headers);
1468
1473
  }
1469
- if ((route === "/me" || route === "/me/sessions") && !post) {
1474
+ if ((route === "/me" || route === "/me/sessions" || route === "/me/legal") && !post) {
1470
1475
  const mine = await signedInAs(request);
1471
1476
  if ("response" in mine) return mine.response;
1472
- const res = await ask(request, "GET", route === "/me" ? "/v1/auth/me" : "/v1/auth/me/sessions", void 0, void 0, mine.token);
1477
+ const res = await ask(request, "GET", route === "/me" ? "/v1/auth/me" : route === "/me/legal" ? "/v1/auth/me/legal" : "/v1/auth/me/sessions", void 0, void 0, mine.token);
1473
1478
  if (res.error) return problem(res.status, res.error.code, res.error.message, void 0, mine.headers);
1479
+ if (route === "/me/legal") {
1480
+ const list = Array.isArray(res.data?.pending) ? res.data.pending : [];
1481
+ return json({ pending: list.map((d) => ({ kind: String(d.kind ?? ""), version: String(d.version ?? ""), url: String(d.url ?? "") })) }, 200, mine.headers);
1482
+ }
1474
1483
  if (route === "/me/sessions") {
1475
1484
  const list = Array.isArray(res.data) ? res.data : [];
1476
1485
  return json({ sessions: list.map((x) => ({ device: String(x.device ?? ""), ip: String(x.ip ?? ""), createdAt: String(x.created_at ?? ""), expiresAt: String(x.expires_at ?? "") })) }, 200, mine.headers);
@@ -1536,7 +1545,8 @@ function createCauthy(given = {}) {
1536
1545
  if (res.error) return problem(res.status, res.error.code, res.error.message);
1537
1546
  if (res.data?.mfa_required === true) {
1538
1547
  const step = { kind: "mfa", token: String(res.data.mfa_token ?? ""), returnTo: afterSignIn };
1539
- return json({ status: "mfa_required" }, 200, new Headers({ "set-cookie": writeCookie(stepCookie, await seal(step, await key), attrs(request, STEP_SECONDS)) }));
1548
+ const how = res.data.mfa_method === "email" ? { method: "email" } : {};
1549
+ return json({ status: "mfa_required", ...how }, 200, new Headers({ "set-cookie": writeCookie(stepCookie, await seal(step, await key), attrs(request, STEP_SECONDS)) }));
1540
1550
  }
1541
1551
  return signedIn(request, res.data);
1542
1552
  }
@@ -1563,7 +1573,7 @@ function createCauthy(given = {}) {
1563
1573
  if (res.error) return problem(res.status, res.error.code, res.error.message);
1564
1574
  return signedIn(request, res.data, [writeCookie(stepCookie, "", attrs(request, 0))]);
1565
1575
  }
1566
- if (route === "/sign-in/mfa/methods" || route === "/sign-in/mfa/send") {
1576
+ if (route === "/sign-in/mfa/methods" || route === "/sign-in/mfa/send" || route === "/sign-in/mfa/email") {
1567
1577
  const sealed = readCookies(request.headers.get("cookie")).get(stepCookie);
1568
1578
  const step = sealed ? await unseal(sealed, await key) : null;
1569
1579
  if (step === null || step.kind !== "mfa") return problem(400, "step_expired", "Sign in again: the code was asked for too long ago.");
@@ -1572,13 +1582,20 @@ function createCauthy(given = {}) {
1572
1582
  if (res2.error) return problem(res2.status, res2.error.code, res2.error.message);
1573
1583
  const p = res2.data?.phone;
1574
1584
  const push = res2.data?.push;
1585
+ const mail = res2.data?.email;
1575
1586
  return json({
1576
1587
  status: "ok",
1577
1588
  totp: res2.data?.totp === true,
1578
1589
  phone: p ? { number: String(p.number ?? ""), channel: String(p.channel ?? "sms") } : null,
1579
- push: push ? { devices: Number(push.devices ?? 0) } : null
1590
+ push: push ? { devices: Number(push.devices ?? 0) } : null,
1591
+ email: mail ? { to: String(mail.to ?? "") } : null
1580
1592
  });
1581
1593
  }
1594
+ if (route === "/sign-in/mfa/email") {
1595
+ const res2 = await ask(request, "POST", "/v1/auth/mfa/email", { mfa_token: step.token });
1596
+ if (res2.error) return problem(res2.status, res2.error.code, res2.error.message);
1597
+ return json({ status: "sent", sentTo: String(res2.data?.sent_to ?? "") });
1598
+ }
1582
1599
  const res = await ask(request, "POST", "/v1/auth/mfa/send", { mfa_token: step.token });
1583
1600
  if (res.error) return problem(res.status, res.error.code, res.error.message);
1584
1601
  return json({ status: "sent", sentTo: String(res.data?.sent_to ?? ""), channel: String(res.data?.channel ?? "sms") });
@@ -1588,7 +1605,8 @@ function createCauthy(given = {}) {
1588
1605
  if (bad) return invalid(bad);
1589
1606
  const email = String(b.email).trim();
1590
1607
  const organization = typeof b.organization === "string" && b.organization.trim() !== "" ? { organization: { name: b.organization.trim() } } : {};
1591
- const made = await ask(request, "POST", "/v1/auth/register", { email, password: b.password, display_name: typeof b.name === "string" ? b.name.trim() : "", ...organization }, pages.verifyEmail);
1608
+ const legal = { ...b.acceptLegal === true ? { accept_legal: true } : {}, ...b.consents && typeof b.consents === "object" ? { consents: b.consents } : {} };
1609
+ const made = await ask(request, "POST", "/v1/auth/register", { email, password: b.password, display_name: typeof b.name === "string" ? b.name.trim() : "", ...organization, ...legal }, pages.verifyEmail);
1592
1610
  if (made.error) return problem(made.status, made.error.code, made.error.message);
1593
1611
  if (made.data?.verification_required === true) return json({ status: "verification_required", email });
1594
1612
  const res = await ask(request, "POST", "/v1/auth/login", { email, password: b.password });
@@ -1619,6 +1637,12 @@ function createCauthy(given = {}) {
1619
1637
  }
1620
1638
  return json({ status: "saved", account: accountOf(res.data) }, 200, h);
1621
1639
  }
1640
+ if (route === "/me/legal/accept") {
1641
+ const kinds = Array.isArray(b.kinds) ? b.kinds.filter((k) => typeof k === "string") : [];
1642
+ const res = await as("/v1/auth/me/legal/accept", { kinds });
1643
+ if (res.error) return refused(res);
1644
+ return json({ status: "accepted" }, 200, mine.headers);
1645
+ }
1622
1646
  if (route === "/me/password") {
1623
1647
  const bad = checkNewPassword(b.newPassword);
1624
1648
  if (bad) return problem(400, bad.code, bad.message, "newPassword");
@@ -1918,6 +1942,14 @@ function createCauthy(given = {}) {
1918
1942
  options: { issuer, clientId, basePath, afterSignIn, afterSignOut, cookieName }
1919
1943
  };
1920
1944
  }
1945
+ function legalOf(raw) {
1946
+ const documents = Array.isArray(raw?.documents) ? raw.documents : [];
1947
+ const purposes = Array.isArray(raw?.consent_purposes) ? raw.consent_purposes : [];
1948
+ return {
1949
+ documents: documents.map((d) => ({ kind: String(d.kind ?? ""), version: String(d.version ?? ""), url: String(d.url ?? "") })),
1950
+ consentPurposes: purposes.map((p) => ({ key: String(p.key ?? ""), label: String(p.label ?? ""), required: p.required === true }))
1951
+ };
1952
+ }
1921
1953
 
1922
1954
  // src/permissions.ts
1923
1955
  function matches(entry, resource, action) {