27Sign in
The sign-in card in the .ns-auth shell: password plus a magic-link alternative under one divider. Ghost is passwordless (templates/signin-form.html); the Next.js app renders the password form — same markup, one brand.
Use it for
- The one screen whose single job is signing in
Not for
- In-page account settings — the account panel
- Sign up — its own page, its own promises
Sign-in card
markup
<div class="ns-auth__card" style="max-inline-size:22rem">
<p class="ns-auth__kicker">sign in</p>
<h2 class="ns-auth__title" style="font-size:var(--size-h3)">Welcome back</h2>
<form class="ns-auth__form" onsubmit="return false">
<div class="ns-field">
<label class="ns-field__label" for="au-e">Email address</label>
<input class="ns-input" id="au-e" type="email" autocomplete="email">
</div>
<div class="ns-field">
<label class="ns-field__label" for="au-p">Password</label>
<input class="ns-input" id="au-p" type="password" autocomplete="current-password">
</div>
<div class="ns-auth__meta">
<label class="ns-choice" style="padding:0"><input type="checkbox" class="ns-checkbox" checked>
<span class="ns-choice__text"><span class="ns-choice__label">Remember me</span></span></label>
<a href="#">Forgot password?</a>
</div>
<button class="ns-btn ns-btn--primary ns-btn--block" type="submit">Sign in</button>
<div class="ns-auth__divider" aria-hidden="true">or</div>
<button class="ns-btn ns-btn--outline ns-btn--block" type="button">Email me a sign-in link</button>
</form>
<p class="ns-auth__alt">New here? <a href="#">Create an account</a></p>
</div>Error state
One message above the fields, deliberately vague about which half was wrong.
sign in
Welcome back
That email and password combination did not match. Try again or use a sign-in link.
markup
<div class="ns-auth__card" style="max-inline-size:22rem">
<p class="ns-auth__kicker">sign in</p>
<h2 class="ns-auth__title" style="font-size:var(--size-h3)">Welcome back</h2>
<div class="ns-alert ns-alert--error" role="alert" style="margin-block-end:var(--space-4)">
<i class="ph ph-warning-circle ns-alert__icon" aria-hidden="true"></i>
<div class="ns-alert__body"><p class="ns-alert__text">That email and password combination did not match. Try again or use a sign-in link.</p></div>
</div>
<form class="ns-auth__form" onsubmit="return false">
<div class="ns-field">
<label class="ns-field__label" for="aue-e">Email address</label>
<input class="ns-input" id="aue-e" type="email" value="swarnil@example.com" autocomplete="email">
</div>
<div class="ns-field">
<label class="ns-field__label" for="aue-p">Password</label>
<input class="ns-input" id="aue-p" type="password" autocomplete="current-password">
</div>
<button class="ns-btn ns-btn--primary ns-btn--block" type="submit">Sign in</button>
</form>
</div>Accessibility contract
- Sign-in errors never say WHICH field was wrong — that confirms account existence to a guesser
- autocomplete="current-password" is what makes password managers work