@labyrinthe/otp-widget 0.0.0-stage → 1.2.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/CHANGELOG.md ADDED
@@ -0,0 +1,80 @@
1
+ # Changelog
2
+
3
+ All notable changes to `@labyrinthe/otp-widget` are documented here. This project follows
4
+ [Semantic Versioning](https://semver.org/) and the format of [Keep a Changelog](https://keepachangelog.com/).
5
+
6
+ ## [Unreleased]
7
+
8
+ ## [1.2.0] - 2026-11-06
9
+
10
+ Built against the API specification 1.3.0 and `@labyrinthe/connect` 1.2 (peer dependency now `^1.2.0`).
11
+
12
+ ### Added
13
+ - Labyrinthe maintenance: `503 FEATURE_DISABLED` (whole API or OTP functions shut down by the platform) and
14
+ `OTP_SERVICE_DISABLED` are answered as `service_unavailable` (503) with `admin_message` (the administrator's message,
15
+ meant for end users, the only upstream text forwarded), `until` (ISO 8601) and, when the end is scheduled,
16
+ `retry_after_seconds` and a `Retry-After` header. Reported to `onError`. Also read from an older SDK (details and
17
+ `Retry-After` header of the generic error).
18
+ - The widget shows the administrator's message instead of `errors.service_unavailable` when there is one, followed by
19
+ the new text `retryIn` ("Réessayez dans {time}." / "Try again in {time}.") when the time left is known. The
20
+ `labyrinthe-otp:error` event gains `adminMessage` and `until` (`Date`).
21
+
22
+ ### Changed
23
+ - Durations of one hour or more are shown as `h:mm:ss` (`1:30:00`) instead of `90:00`.
24
+
25
+ ## [1.1.1] - 2026-11-06
26
+
27
+ ### Added
28
+ - Stable error code `send_failed` (502) for `409 IDEMPOTENCY_KEY_UNRESOLVED` (the original send failed unexpectedly on
29
+ the API side and its outcome is unknown: a code may have been sent). Reported to `onError`, never retried; the
30
+ widget shows a French / English message and forgets its `send_id`, so a new code requested by the user is sent with
31
+ a new idempotency key.
32
+
33
+ ### Fixed
34
+ - Short foreign numbers (`+2481234567`, Seychelles, 10 digits) are sent to the API with their country code instead of
35
+ being read as local DRC numbers (`2432481234567`), BACKEND-TODO n° 32. The widget and the server helper already
36
+ sent `+<digits>`, but `@labyrinthe/connect` 1.1.0 dropped the `+` before calling the API: the peer dependency is now
37
+ `^1.1.1` (the release that sends E.164 numbers with `+`). Tests check the number handed to the SDK and the body
38
+ received by a local API.
39
+
40
+ ## [1.1.0] - 2026-11-06
41
+
42
+ Built against the API specification 1.2.0 and `@labyrinthe/connect` 1.1 (peer dependency now `^1.1.0`).
43
+
44
+ ### Added
45
+ - Server option `webOtpDomain`: the API ends the SMS with `@domain #code`, so the Web OTP API of the widget
46
+ (`navigator.credentials.get`, Chrome on Android) can really fill the code. Validated at start-up.
47
+ - Server option `stripAccents` (GSM-7 SMS).
48
+ - Idempotent sends: the widget sends a random `send_id` (kept until the send succeeds, reused after a lost
49
+ response); the helper derives the `Idempotency-Key` from it with an HMAC of `secret`, so a retried click never
50
+ sends a second SMS. Invalid `send_id`: 400 `invalid_request`.
51
+ - Stable error code `account_suspended` (503) for `ACCOUNT_SUSPENDED`, translated in French and English and reported
52
+ to `onError`. `IDEMPOTENCY_REQUEST_IN_PROGRESS` maps to `rate_limited` with `retry_after_seconds`.
53
+
54
+ ### Changed
55
+ - `code_length`, `code_type` and `resend_after_seconds` sent to the widget come from the API response; the
56
+ `codeLength`, `codeType` and `resendAfterSeconds` options remain as overrides (needed only with an older API).
57
+ - `attempts_left` is the API's `attempts_remaining` (estimated locally only with an older SDK).
58
+ - Phone numbers, aligned with the API and the SDK: without "+", 11 digits or more not starting with 0 are already
59
+ international (`33612345678` is kept).
60
+
61
+ ## [1.0.0] - 2026-11-06
62
+
63
+ First stable release, built against the API specification 1.1.0 and `@labyrinthe/connect` 1.0.
64
+
65
+ ### Added
66
+ - `<labyrinthe-otp>` web component (Shadow DOM, zero dependencies, 7.6 kB min+gzip standalone): phone step
67
+ (default country code 243, same normalisation as the SDK), separate code boxes, paste and
68
+ `autocomplete="one-time-code"`, Web OTP API, auto-submit, resend countdown (`resend_after_seconds`,
69
+ `OTP_RESEND_TOO_SOON`), attempts left, localised errors, success state.
70
+ - Events `labyrinthe-otp:sent`, `labyrinthe-otp:verified`, `labyrinthe-otp:error`; properties `texts`,
71
+ `requestHeaders`, `step`, `reset()`.
72
+ - Accessibility: labels, `role="group"` code boxes with accessible names, `role="alert"` errors, polite live region,
73
+ keyboard navigation, focus management.
74
+ - Theming with `--lab-otp-*` CSS variables and `::part()`, light / dark / automatic, French (default) and English.
75
+ - React wrapper `@labyrinthe/otp-widget/react` (`'use client'`, React 18 and 19, SSR-safe).
76
+ - Server helper `@labyrinthe/otp-widget/server`: `createOtpHandlers()` for the Fetch API (Next.js App Router, edge,
77
+ Hono, Bun, Deno) and Express; `otp_id` kept in an AES-256-GCM encrypted httpOnly cookie or in a `store`;
78
+ `beforeSend` / `onVerified` / `onError` hooks; origin and content-type checks; `exposeTestCode` for development
79
+ (refused in production).
80
+ - Standalone `dist/labyrinthe-otp.min.js` for a `<script>` tag (unpkg, jsDelivr).
package/LICENSE ADDED
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2026 Labyrinthe Connect
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.