mirror of
https://github.com/zoriya/Kyoo.git
synced 2025-07-09 03:04:20 -04:00
Add auth spec
This commit is contained in:
parent
362b4105c8
commit
73e3c6c64b
141
auth/README.md
Normal file
141
auth/README.md
Normal file
@ -0,0 +1,141 @@
|
|||||||
|
# Auth
|
||||||
|
|
||||||
|
## Features
|
||||||
|
|
||||||
|
- Not an oauth provider/no login page (as in you don't redirect to this, you create your own auth page)
|
||||||
|
- [Phantom tokens](https://curity.io/resources/learn/phantom-token-pattern/)
|
||||||
|
- Session based tokens (valid for 30 days, reset after each use [configurable])
|
||||||
|
- Last online/last connection stored per user (and token)
|
||||||
|
- Device used per session/token
|
||||||
|
- Username/password login
|
||||||
|
- OIDC (login via Google, Discord, Authentik, whatever)
|
||||||
|
- Custom jwt claims (for your role/permissions handling or something else)
|
||||||
|
- Api keys support
|
||||||
|
- Optionally [Federated](#federated)
|
||||||
|
|
||||||
|
## Routes
|
||||||
|
|
||||||
|
### Lifecycle
|
||||||
|
|
||||||
|
```
|
||||||
|
`/login` { login, password } -> token
|
||||||
|
`/login/$provider` { redirectUrl, tenant? } -> redirect
|
||||||
|
`/register` { email, username, password } -> token
|
||||||
|
`/logout` w/ optional `?session=id`
|
||||||
|
`/jwt` retrieve a jwt from an opaque token (also update last online value for session & user)
|
||||||
|
```
|
||||||
|
|
||||||
|
### Profiles
|
||||||
|
|
||||||
|
```
|
||||||
|
Get `/users` -> user[]
|
||||||
|
Get/Put/Patch/Delete `/users/$username` (or /users/me) -> user
|
||||||
|
Get/Post/Delete `/users/$username/logo` (or /users/me/logo) -> png
|
||||||
|
```
|
||||||
|
|
||||||
|
Put/Patch of a user can edit the password if the `oldPassword` value is set and valid (or the user has the `users.password` permission).\
|
||||||
|
Should require an otp from mail if no oldPassword exists (see todo).
|
||||||
|
|
||||||
|
Put/Patch can edit custom claims (roles & permissons for example) if the user has the `users.claims` permission).
|
||||||
|
|
||||||
|
Read others requires `users.read` permission.\
|
||||||
|
Write/Delete requires `users.write` permission (if it's not your account).
|
||||||
|
|
||||||
|
### Sessions
|
||||||
|
|
||||||
|
Get `/sessions` list all of your active sessions (and devices)
|
||||||
|
(can then use `/logout?session=id`)
|
||||||
|
|
||||||
|
### Api keys
|
||||||
|
|
||||||
|
```
|
||||||
|
Get `/apikeys`
|
||||||
|
Post `/apikeys` {...nlaims} Create a new api keys with given claims
|
||||||
|
```
|
||||||
|
|
||||||
|
An api key can be used like an opaque token, calling /jwt with it will return a valid jwt with the claims you specified during the post request to create it.
|
||||||
|
Creating an apikeys requires the `apikey.create` permission, reading them requires the `apikey.read` permission.
|
||||||
|
|
||||||
|
### OIDC
|
||||||
|
|
||||||
|
```
|
||||||
|
`/login/$provider` {redirectUrl, tenant?}
|
||||||
|
`/logged/$provider` {code, state, error} (callback called automatically, don't call it manually)
|
||||||
|
`/callback/$provider` {code, tenant?} (if called with the `Authorization` header, links account w/ provider else create a new account) (see diagram below)
|
||||||
|
`/unlink/$provider` Remove provider from current account
|
||||||
|
`/providers` -> provider[]
|
||||||
|
```
|
||||||
|
|
||||||
|
```mermaid
|
||||||
|
sequenceDiagram
|
||||||
|
participant App
|
||||||
|
participant Browser
|
||||||
|
participant Kyoo
|
||||||
|
participant Google
|
||||||
|
App->>Kyoo: /login/google?redirectUrl=/user-logged
|
||||||
|
Kyoo->>Browser: redirect auth.google.com?state=id=guid,url=/user-logged&redirectUrl=/logged/google
|
||||||
|
Browser-->>Google: Access login page
|
||||||
|
Google->>Browser: redirect /logged/google?code=abc&state=id=guid,url=/user-logged
|
||||||
|
Browser-->>Kyoo: access /logged/google?code=abc&state=id=guid,url=/user-logged
|
||||||
|
Kyoo->>App: redirect /user-logged?token=opaque&error=
|
||||||
|
App->>Kyoo: /callback/google?token=opaque
|
||||||
|
Kyoo->>Google: auth.google.com/token?code=abc
|
||||||
|
Google->>Kyoo: jwt token
|
||||||
|
Kyoo->>Google: auth.google.com/profile (w/ jwt)
|
||||||
|
Google->>Kyoo: profile info
|
||||||
|
Kyoo->>App: Token if user exist/was created
|
||||||
|
```
|
||||||
|
|
||||||
|
In the previous diagram, the code is stored by Kyoo and an opaque token is returned to the client to ensure only Kyoo's auth service can read the oauth code.
|
||||||
|
|
||||||
|
## Federated
|
||||||
|
|
||||||
|
You can use another instance to login via oidc you have not configured. This allows an user to login/create a profile without having an api key for the oidc service.
|
||||||
|
This won't allow you to retrive a provider's jwt token, you only get a profile with basic information from the provider. This can be usefull for self-hosted apps where
|
||||||
|
you don't want to setup ~10 api keys just for login.
|
||||||
|
|
||||||
|
|
||||||
|
```mermaid
|
||||||
|
sequenceDiagram
|
||||||
|
participant App
|
||||||
|
participant Browser
|
||||||
|
participant Kyoo
|
||||||
|
participant Hosted
|
||||||
|
participant Google
|
||||||
|
App->>Kyoo: /login/google?redirectUrl=/user-logged
|
||||||
|
Kyoo->>Hosted: /providers
|
||||||
|
Hosted->>Kyoo: has google = true
|
||||||
|
Kyoo->>Browser: redirect hosted.com/login/google?redirectUrl=/user-logged&tenant=kyoo.com
|
||||||
|
Browser-->>Hosted: access /login/google?redirectUrl=/user-logged&tenant=kyoo.com
|
||||||
|
Hosted->>Browser: redirect auth.google.com?state=id=guid,url=/user-logged,tenant=kyoo.com&redirectUrl=/logged/google
|
||||||
|
Browser-->>Google: Access login page
|
||||||
|
Google->>Browser: redirect hosted.com/logged/google?code=abc&state=id=guid,url=/user-logged,tenant=kyoo.com
|
||||||
|
Browser-->>Hosted: access /logged/google?code=abc&state=id=guid,url=/user-logged,tenant=kyoo.com
|
||||||
|
Hosted->>App: redirect /user-logged?token=opaque&error=
|
||||||
|
App->>Kyoo: /callback/google?token=opaque
|
||||||
|
Kyoo->>Hosted: /callback/google?token=opaque&tenant=kyoo.com
|
||||||
|
Hosted->>Google: auth.google.com/token?code=abc
|
||||||
|
Google->>Hosted: jwt token
|
||||||
|
Hosted->>Google: auth.google.com/profile (w/ jwt)
|
||||||
|
Google->>Hosted: profile info
|
||||||
|
Hosted->>Kyoo: profile info (without a jwt to access the provider)
|
||||||
|
Kyoo->>App: Token if user exist/was created
|
||||||
|
```
|
||||||
|
|
||||||
|
The hosted service does not store any user data during this interaction.
|
||||||
|
A `/login` requests temporally stores an id, the tenant & the redirectUrl to unsure the profile value is not stollen. This is then deleted after a `/callback` call (or on timeout).
|
||||||
|
User profile or jwt is never stored.
|
||||||
|
|
||||||
|
## Permissions
|
||||||
|
|
||||||
|
You might have noticed that some routes requires the user to have some permissions.
|
||||||
|
Kyoo's auth uses the custom `permissions` claim for this.
|
||||||
|
Your application is free to use this or any other way of handling permissions/roles.
|
||||||
|
|
||||||
|
## TODO
|
||||||
|
|
||||||
|
- Reset/forget password
|
||||||
|
- Login via qrcode/code from other device (useful for tv for example)
|
||||||
|
- LDMA?
|
||||||
|
- Mails
|
||||||
|
|
Loading…
x
Reference in New Issue
Block a user