generated from templates/typescript-library
162 lines
3.4 KiB
Markdown
162 lines
3.4 KiB
Markdown
|
|
Utilities for implementing OAuth2 / OpenID Connect based login in Node.js services
|
|
|
|
---
|
|
|
|
## Install
|
|
|
|
```bash
|
|
# Update project npm config to refer to correct registry for the @js scope
|
|
echo '@js:registry=https://gitea.jbrumond.me/api/packages/js/npm/' >> ./.npmrc
|
|
|
|
npm install --save @js/oidc-login
|
|
|
|
# optional - additional supporting typescript definitions
|
|
npm install --save-dev @js/types
|
|
```
|
|
|
|
|
|
|
|
## Usage
|
|
|
|
|
|
|
|
### Setup PKCE Provider
|
|
|
|
```ts
|
|
import { create_pkce_cookie_provider } from '@js/oidc-login';
|
|
|
|
const pkce = create_pkce_cookie_provider({
|
|
// Cookie name
|
|
name: 'pkce_verifier_code',
|
|
|
|
// Use "Secure" cookie directive (only send over HTTPS)?
|
|
secure: true,
|
|
|
|
// Cookie time-to-live (in seconds)
|
|
ttl: 300,
|
|
|
|
// Number of bytes of random data to generate for the verification
|
|
// code (more is stronger, must be in range 32-96)
|
|
code_bytes: 48,
|
|
});
|
|
```
|
|
|
|
|
|
|
|
### Preparing a PKCE Challenge
|
|
|
|
```ts
|
|
const {
|
|
// This is a `Set-Cookie` header value containing the PKCE verifier
|
|
// code that should be sent to the client when redirecting to the
|
|
// OAuth2 provider to start the login process
|
|
set_cookie_header,
|
|
|
|
// This is the PKCE challenge code that should be sent to the OAuth2
|
|
// provider as a parameter in the redirect
|
|
pkce_code_challenge,
|
|
} = await pkce.prepare_pkce_challenge();
|
|
```
|
|
|
|
|
|
|
|
### Verifying a PKCE Challenge
|
|
|
|
```ts
|
|
// Retrieve the PKCE verifier from the cookie sent back by the client.
|
|
// This should be sent to the OAuth2 provider when fetching the token set
|
|
// in the login callback
|
|
const pkce_code_verifier = pkce.read_pkce_code_verifier(req.headers.cookie);
|
|
|
|
// When responding to the login callback request, send the invalidator cookie
|
|
// to delete the previous set PKCE cookie
|
|
res.setHeader('set-cookie', pkce.invalidate_cookie);
|
|
```
|
|
|
|
|
|
|
|
### Setup Session Credentials Provider
|
|
|
|
```ts
|
|
import { create_session_credentials_provider } from '@js/oidc-login';
|
|
|
|
const creds = create_session_credentials_provider({
|
|
// Cookie name
|
|
name: 'session_token',
|
|
|
|
// Use "Secure" cookie directive (only send over HTTPS)?
|
|
secure: true,
|
|
|
|
// Cookie time-to-live (in seconds)
|
|
ttl: 3600,
|
|
|
|
// Cryptographic hashing function to use for stored secrets
|
|
hash(secret: string) {
|
|
// SEE BELOW
|
|
return '<hashed secret>';
|
|
},
|
|
|
|
// Verification function for the hashing function above
|
|
verify_hash(secret: string, hashed_secret: string) {
|
|
// SEE BELOW
|
|
return true;
|
|
},
|
|
});
|
|
```
|
|
|
|
#### Using argon2 hashing
|
|
|
|
```bash
|
|
npm install --save argon2
|
|
```
|
|
|
|
```ts
|
|
import { hash, verify, argon2id } from 'argon2';
|
|
import { create_session_credentials_provider } from '@js/oidc-login';
|
|
|
|
const creds = create_session_credentials_provider({
|
|
name: 'session_token',
|
|
secure: true,
|
|
ttl: 3600,
|
|
hash(secret: string) {
|
|
return hash(password, {
|
|
type: argon2id,
|
|
// hash options...
|
|
});
|
|
},
|
|
verify_hash(secret: string, hashed_secret: string) {
|
|
return verify(hashed_secret, secret);
|
|
},
|
|
});
|
|
```
|
|
|
|
|
|
|
|
### Creating New Sessions
|
|
|
|
```ts
|
|
const {
|
|
// This is a `Set-Cookie` header value containing the new session token
|
|
// that can be sent to a client to finish a web login process
|
|
set_cookie_header,
|
|
|
|
// The hashed secret that should be stored for later verification
|
|
hashed_secret,
|
|
|
|
// The session token details
|
|
session_token: {
|
|
// Unique prefix string that can be used to lookup the session
|
|
// for later verification
|
|
prefix,
|
|
|
|
// The secret value generated for token
|
|
secret,
|
|
|
|
// The complete, raw token string
|
|
token,
|
|
},
|
|
} = await creds.prepare_new_session_credentials();
|
|
```
|
|
|