mirror of
https://github.com/PR0M3TH3AN/bitlogin.git
synced 2026-10-27 08:31:21 +00:00
docs: bring the Integrate page and version references up to date
docs.html was missing everything from this session's work: - The disconnectedCallback/crypto-worker-teardown gotcha (found via the BitRoad integration) -- now a callout right where the element is first mounted, since that's the step where it actually bites. - Talking to the element directly (getPublicKey/signEvent/nip44Encrypt/ nip44Decrypt as instance methods) as an alternative to window.nostr, with BitRoad's adapter as the worked example. - claimSigner() failing gracefully (returns false, doesn't throw) when a NIP-07 extension has locked window.nostr down -- was previously undocumented entirely; this is the exact bug just fixed. - Theming via CSS custom properties, with the full property list and BitRoad's mapping as a real example. Also fixed two stale "(v0.3)" references to docs/spec.md in README.md and CONTRIBUTING.md -- the spec was bumped to v0.4 earlier this session for the rollback-detection changes but these two mentions were missed. Co-Authored-By: Claude Sonnet 5 <[email protected]>
This commit is contained in:
1 parent
1dbb4fca51
commit
ce6ade73b4
3 files changed
+70
-2
No files matched your search
+1
-1
@@ -51,7 +51,7 @@ reachable from most contributor sandboxes either.
|
|||||||
|
|
||||||
## The spec is canonical
|
## The spec is canonical
|
||||||
|
|
||||||
`docs/spec.md` (currently v0.3) is the source of truth for the protocol
|
`docs/spec.md` (currently v0.4) is the source of truth for the protocol
|
||||||
itself — wire formats, KDF parameters, capsule structure, derivation paths,
|
itself — wire formats, KDF parameters, capsule structure, derivation paths,
|
||||||
threat model. Code comments reference it by section (`§11.2`, `§17.4`, …).
|
threat model. Code comments reference it by section (`§11.2`, `§17.4`, …).
|
||||||
|
|
||||||
|
|||||||
@@ -7,7 +7,7 @@ password that unlocks a portable Nostr identity, plus an independent 12-word
|
|||||||
recovery phrase. Encrypted account material lives on public Nostr relays —
|
recovery phrase. Encrypted account material lives on public Nostr relays —
|
||||||
no account server, no password-reset email, no database.
|
no account server, no password-reset email, no database.
|
||||||
|
|
||||||
This repo implements the protocol from `docs/spec.md` (v0.3) as a modular
|
This repo implements the protocol from `docs/spec.md` (v0.4) as a modular
|
||||||
system any static site can embed for login and Nostr signing.
|
system any static site can embed for login and Nostr signing.
|
||||||
|
|
||||||
## Layout
|
## Layout
|
||||||
|
|||||||
@@ -39,6 +39,20 @@
|
|||||||
discovery-relays="wss://discovery-one.example,wss://discovery-two.example">
|
discovery-relays="wss://discovery-one.example,wss://discovery-two.example">
|
||||||
</bitlogin-auth></code></pre>
|
</bitlogin-auth></code></pre>
|
||||||
<p class="section-sub" style="margin:10px 0 0">That's it — the element renders its own sign-in/create/recover UI inside a shadow root, so it won't collide with your site's CSS.</p>
|
<p class="section-sub" style="margin:10px 0 0">That's it — the element renders its own sign-in/create/recover UI inside a shadow root, so it won't collide with your site's CSS.</p>
|
||||||
|
<div class="callout">
|
||||||
|
<strong>Mount it somewhere your own re-renders won't touch.</strong> Removing
|
||||||
|
<code><bitlogin-auth></code> from the DOM (including indirectly, by resetting an
|
||||||
|
ancestor's <code>innerHTML</code> — a common pattern in hand-rolled UI without a
|
||||||
|
framework's reconciler) tears down its crypto Web Worker. If that happens mid-session,
|
||||||
|
every signing call made afterward just hangs forever with no error, because the worker
|
||||||
|
is gone and nothing ever replies — a call already in flight when it happens can even
|
||||||
|
look like it succeeded. If your app re-renders the container this element lives in,
|
||||||
|
give it a container that's never replaced wholesale and toggle the <code>hidden</code>
|
||||||
|
attribute instead of removing the element. See the account manager demo's source for a
|
||||||
|
single-page example, or BitRoad's <code>src/nostr/bitloginAdapter.mjs</code> /
|
||||||
|
<code>#bitloginMount</code> (a sibling Nostr commerce app that embeds BitLogin) for a
|
||||||
|
worked example of keeping the element alive across a host app's own re-renders.
|
||||||
|
</div>
|
||||||
</li>
|
</li>
|
||||||
<li>
|
<li>
|
||||||
<h3>React to sign-in and sign-out</h3>
|
<h3>React to sign-in and sign-out</h3>
|
||||||
@@ -73,6 +87,23 @@ const plain = await window.nostr.nip44.decrypt(peerPubkeyHex, cipher);</code></
|
|||||||
and back.
|
and back.
|
||||||
</div>
|
</div>
|
||||||
</li>
|
</li>
|
||||||
|
<li>
|
||||||
|
<h3>Or talk to the element directly — no <code>window.nostr</code> contention</h3>
|
||||||
|
<p><code><bitlogin-auth></code> mirrors the same four calls as instance methods, scoped to that specific
|
||||||
|
element rather than the single shared <code>window.nostr</code> slot:</p>
|
||||||
|
<pre><code>const bl = document.querySelector('bitlogin-auth');
|
||||||
|
|
||||||
|
const pubkey = await bl.getPublicKey();
|
||||||
|
const signed = await bl.signEvent({ kind: 1, content: 'hello', tags: [] });
|
||||||
|
const cipher = await bl.nip44Encrypt(peerPubkeyHex, 'hi there');
|
||||||
|
const plain = await bl.nip44Decrypt(peerPubkeyHex, cipher);</code></pre>
|
||||||
|
<p>Prefer this if your app already holds a reference to the element — e.g. you built the sign-in UI yourself
|
||||||
|
instead of relying on <code>window.nostr</code>-reading app code. It keeps working even if something else
|
||||||
|
currently owns <code>window.nostr</code> (another extension, a different widget instance), and it's what a host
|
||||||
|
app should use if it wants a specific, known signer rather than "whichever provider is active this moment."
|
||||||
|
BitRoad's <code>src/nostr/bitloginAdapter.mjs</code> is a real example: its signer adapter calls these four
|
||||||
|
methods directly and never touches <code>window.nostr</code> at all.</p>
|
||||||
|
</li>
|
||||||
<li>
|
<li>
|
||||||
<h3>Supporting multiple signing methods (extensions, NIP-46, BitLogin)</h3>
|
<h3>Supporting multiple signing methods (extensions, NIP-46, BitLogin)</h3>
|
||||||
<p><code>window.nostr</code> is a single global slot — only one provider can occupy it at a time. If a user also
|
<p><code>window.nostr</code> is a single global slot — only one provider can occupy it at a time. If a user also
|
||||||
@@ -120,6 +151,16 @@ if (window.bitlogin?.releaseSigner()) {
|
|||||||
<code>window.bitlogin.releaseSigner()</code> also fire <code>bitlogin-signer-claimed</code> /
|
<code>window.bitlogin.releaseSigner()</code> also fire <code>bitlogin-signer-claimed</code> /
|
||||||
<code>bitlogin-signer-released</code> events (on the element and on <code>window</code>, respectively) if you'd
|
<code>bitlogin-signer-released</code> events (on the element and on <code>window</code>, respectively) if you'd
|
||||||
rather react to the change than check a return value.</p>
|
rather react to the change than check a return value.</p>
|
||||||
|
<div class="callout">
|
||||||
|
<strong><code>claimSigner()</code> can fail without breaking anything.</strong> Some NIP-07 extensions
|
||||||
|
install <code>window.nostr</code> as a non-configurable, non-writable property specifically to stop another
|
||||||
|
script from overwriting it. When that happens, <code>claimSigner()</code> returns <code>false</code> instead
|
||||||
|
of throwing (and <code>bitlogin-signer-claimed</code>'s <code>event.detail</code> carries
|
||||||
|
<code>{ windowNostrClaimed: false, error }</code>), and every BitLogin sign-in flow completes normally
|
||||||
|
regardless — the failure only means <code>window.nostr</code> still points at that other extension. If your
|
||||||
|
app talks to the element directly (previous step) this never matters at all; only code that reads
|
||||||
|
<code>window.nostr</code> itself is affected, and only for as long as the other extension holds the slot.
|
||||||
|
</div>
|
||||||
</li>
|
</li>
|
||||||
<li>
|
<li>
|
||||||
<h3>Choose your relays</h3>
|
<h3>Choose your relays</h3>
|
||||||
@@ -127,6 +168,33 @@ if (window.bitlogin?.releaseSigner()) {
|
|||||||
<code>discovery-relays</code> at relays you trust for your users. Use at least three vault relays for
|
<code>discovery-relays</code> at relays you trust for your users. Use at least three vault relays for
|
||||||
redundancy — capsule publication and reads use a quorum, so no single relay is a single point of failure.</p>
|
redundancy — capsule publication and reads use a quorum, so no single relay is a single point of failure.</p>
|
||||||
</li>
|
</li>
|
||||||
|
<li>
|
||||||
|
<h3>Make it look like your site</h3>
|
||||||
|
<p>The widget renders in a shadow root, but every color, radius, font, and its max-width are all read from CSS
|
||||||
|
custom properties on <code>:host</code> — and custom properties inherit through the shadow boundary, so your
|
||||||
|
page's own CSS can override every one of them without touching the widget's internals:</p>
|
||||||
|
<pre><code>bitlogin-auth {
|
||||||
|
--bl-accent: #3d9bff; /* primary button / link / focus ring color */
|
||||||
|
--bl-accent-hover: #2f86e0; /* primary button hover */
|
||||||
|
--bl-accent-fg: #04101f; /* text color on top of --bl-accent */
|
||||||
|
--bl-bg: #12151f; /* card background */
|
||||||
|
--bl-fg: #eaeef6; /* body text */
|
||||||
|
--bl-muted: #98a2b6; /* secondary text */
|
||||||
|
--bl-border: rgba(255, 255, 255, 0.10);
|
||||||
|
--bl-input-bg: #1a1e2b; /* input / credential-box background */
|
||||||
|
--bl-danger: #ff6b6b;
|
||||||
|
--bl-danger-bg: rgba(255, 107, 107, 0.16);
|
||||||
|
--bl-radius: 14px;
|
||||||
|
--bl-font-family: Inter, ui-sans-serif, system-ui, sans-serif;
|
||||||
|
--bl-max-width: none; /* default 380px keeps it a fixed-width card;
|
||||||
|
override to fill a wider container */
|
||||||
|
}</code></pre>
|
||||||
|
<p class="section-sub" style="margin:10px 0 0">Overriding none of these is a valid choice — the widget falls
|
||||||
|
back to its own light theme, a <code>prefers-color-scheme: dark</code> media query, and a
|
||||||
|
<code>data-theme="dark"|"light"</code> attribute override for pages with their own theme toggle. See BitRoad's
|
||||||
|
<code>bitlogin-auth { ... }</code> rule in its <code>src/styles.css</code> for a real integration that maps
|
||||||
|
every one of these onto its own design tokens.</p>
|
||||||
|
</li>
|
||||||
<li>
|
<li>
|
||||||
<h3>That's the whole integration</h3>
|
<h3>That's the whole integration</h3>
|
||||||
<p>No account database, no password-reset email, no server-side session. The <a href="./account.html">account manager demo</a>
|
<p>No account database, no password-reset email, no server-side session. The <a href="./account.html">account manager demo</a>
|
||||||
|
|||||||
Reference in new issue
Block a user