dvd
    • Create new note
    • Create a note from template
      • Sharing URL Link copied
      • /edit
      • View mode
        • Edit mode
        • View mode
        • Book mode
        • Slide mode
        Edit mode View mode Book mode Slide mode
      • Customize slides
      • Note Permission
      • Read
        • Only me
        • Signed-in users
        • Everyone
        Only me Signed-in users Everyone
      • Write
        • Only me
        • Signed-in users
        • Everyone
        Only me Signed-in users Everyone
      • Engagement control Commenting, Suggest edit, Emoji Reply
    • Invite by email
      Invitee

      This note has no invitees

    • Publish Note

      Share your work with the world Congratulations! 🎉 Your note is out in the world Publish Note

      Your note will be visible on your profile and discoverable by anyone.
      Your note is now live.
      This note is visible on your profile and discoverable online.
      Everyone on the web can find and read all notes of this public team.
      See published notes
      Unpublish note
      Please check the box to agree to the Community Guidelines.
      View profile
    • Commenting
      Permission
      Disabled Forbidden Owners Signed-in users Everyone
    • Enable
    • Permission
      • Forbidden
      • Owners
      • Signed-in users
      • Everyone
    • Suggest edit
      Permission
      Disabled Forbidden Owners Signed-in users Everyone
    • Enable
    • Permission
      • Forbidden
      • Owners
      • Signed-in users
    • Emoji Reply
    • Enable
    • Versions and GitHub Sync
    • Note settings
    • Note Insights New
    • Engagement control
    • Make a copy
    • Transfer ownership
    • Delete this note
    • Save as template
    • Insert from template
    • Import from
      • Dropbox
      • Google Drive
      • Gist
      • Clipboard
    • Export to
      • Dropbox
      • Google Drive
      • Gist
    • Download
      • Markdown
      • HTML
      • Raw HTML
Menu Note settings Note Insights Versions and GitHub Sync Sharing URL Create Help
Create Create new note Create a note from template
Menu
Options
Engagement control Make a copy Transfer ownership Delete this note
Import from
Dropbox Google Drive Gist Clipboard
Export to
Dropbox Google Drive Gist
Download
Markdown HTML Raw HTML
Back
Sharing URL Link copied
/edit
View mode
  • Edit mode
  • View mode
  • Book mode
  • Slide mode
Edit mode View mode Book mode Slide mode
Customize slides
Note Permission
Read
Only me
  • Only me
  • Signed-in users
  • Everyone
Only me Signed-in users Everyone
Write
Only me
  • Only me
  • Signed-in users
  • Everyone
Only me Signed-in users Everyone
Engagement control Commenting, Suggest edit, Emoji Reply
  • Invite by email
    Invitee

    This note has no invitees

  • Publish Note

    Share your work with the world Congratulations! 🎉 Your note is out in the world Publish Note

    Your note will be visible on your profile and discoverable by anyone.
    Your note is now live.
    This note is visible on your profile and discoverable online.
    Everyone on the web can find and read all notes of this public team.
    See published notes
    Unpublish note
    Please check the box to agree to the Community Guidelines.
    View profile
    Engagement control
    Commenting
    Permission
    Disabled Forbidden Owners Signed-in users Everyone
    Enable
    Permission
    • Forbidden
    • Owners
    • Signed-in users
    • Everyone
    Suggest edit
    Permission
    Disabled Forbidden Owners Signed-in users Everyone
    Enable
    Permission
    • Forbidden
    • Owners
    • Signed-in users
    Emoji Reply
    Enable
    Import from Dropbox Google Drive Gist Clipboard
       Owned this note    Owned this note      
    Published Linked with GitHub
    • Any changes
      Be notified of any changes
    • Mention me
      Be notified of mention me
    • Unsubscribe
    # Aurelia Autenticazione e licensing ![diagram](https://gnx.it/~dvd/aurelia_cluster.svg) ## legenda In questa rappresentazione di un nodo Aurelia abbiamo: - *Notary*, il servizio in grado di autenticare gli utenti e di gestirne l'anagrafica - *Watchman*, il servizio che autorizza tutte le richieste provenienti dai client esterni - Client di vario tipo, i blocchi azzurri, che accedano dall'esterno del nodo - *Hydra*, il servizio che implementa il protocollo OpenID Connect ## Autenticazione Il protocollo di autorizzazione scelto è OAuth2 (OpenID Connect si basa su quest'ultimo e aggiunge il concetto di *identità dell'utente*). Per implementare il protocollo OAuth2 abbiamo scelto un server open-source già pronto [Hydra](https://www.ory.sh/hydra/) che disaccoppia l'implementazione del protocollo stesso dal flusso di autenticazione che rimane a carico di un software scritto da noi (Notary). Dei vari flussi di autenticazione supportati da OAuth2 implementeremo *Authorization Code Grant with PKCE*. L'Authorization Code Grant è il flusso più sicuro implementato da OAuth2 e permette di ottenere anche i refresh token utili per permettere ad un applicazione di ottenere un nuovo token senza l'intervento dell'utente. L'estensione PKCE permette di utilizzare in maniera sicura l'Authorization Code Grant anche quando l'applicazione è installata in un ambiente fuori dal nostro controllo (come i programmi desktop e le web app). L'autorizzazione viene eseguita da ogni client parlando con il server Hydra (le linee viola nel diagramma) e al termine i client ottengono un token da includere in ogni richiesta verso il nodo Aurelia. ### Autenticazione interattiva La classica autenticazione basata su browser dove l'utente è chiamato a verificare la propria identità inserendo qualcosa (potrebbe essere username + password, barcode + sede + m2fa, etc). La pagina HTML viene generata da *Notary* ed è personalizzata per il singolo cliente. ### Autenticazione interattiva SSO TODO da verificare Un autenticazione che sfrutta il SSO di windows. L'idea è che la pagina di login su *Notary* effettui un redirect sull'Active Directory (ad esempio) del cliente che, grazie all'autenticazione di dominio inviata dai browser, è in grado di autenticare l'utente senza chiedergli nulla (ad eccezione della prima volta dove deve autorizzare Aurelia). Una volta autenticato l'utente viene rediretto su *Notary* che recupera le informazioni sull'utente dal server SSO e completa il login. ### Autenticazione non interattiva Un autenticazione *non interattiva* pensata per i client desktop (come Caligola o il GL) per quei casi dove: - non è detto che il cliente abbia necessità di distinguere tra i vari utenti che usano il software - non si possa/voglia usare il flusso di login basato sui browser L'idea è di salvare localmente (su disco o nel keychain) un token generato da Aurelia e collegato con una certa utenza (ogni utente può avere più token) censita da *Notary*. Il client inizia la sequenza di login e intercetta il redirect dal server hydra (dove c'è l'endpoint OAuth2) al server *Notary* che deve mostrare la UI di login; prima di seguire il redirect aggiunge un header HTTP con il token utente. Se il token è valido *Notary* non mostrerà la UI di login ma completerà immediatamente il login. ## Licensing Una licenza d'uso da la possibilità ad un utente **autorizzato** di utilizzare un determinato software. Il conteggio ed il controllo delle licenze è un problema ortogonale all'autorizzazione ma che può essere risolto sfruttando le garanzie offerte da quest'ultima. In ambito cloud possiamo parlare di API invece che di software quindi, in prima istanza, potremmo dire che per chiamare una qualunque API offerta da Aurelia è necessario disporre di una licenza valida. Purtroppo questo modello, sebbene corretto, non è sufficiente a soddisfare tutti i requisiti: - alcuni software devono poter funzionare, e quindi per definizione avere una licenza valida, anche se sono offline; - alcuni software sono venduti con una licenza di tipo *floating*, che viene conteggiata solo quando il software è in uso. Quando questi due requisiti sono richiesti dallo stesso software le cose si complicano; stiamo parlando di un programma che deve avere una licenza offline per poter essere eseguito anche quando la connessione ad internet manca ma che non deve essere conteggiata quando il software non viene usato. Ricapitolando: - Ogni richiesta API deve essere autenticata. - Ogni richiesta API richiede una licenza. - Ogni software, per poter funzionare, deve avere una licenza. - Alcuni software devono poter funzionare anche scollegati ad internet (ma va bene essere online per ottenere la licenza). > [name=Matteo Bertini] nel senso che almeno la prima volta devono essere online? - Alcuni software conteggiano la propria licenza d'uso sui minuti di effettivo utilizzo. ### Sessioni utente, licenze e token OAuth2 Introduciamo il concetto di sessione utente; una sessione utente viene allocata durante il login se: - le credenziali di login sono corrette - esiste una licenza disponibile Nota: Per il momento, dati i vari casi d'uso per le licenze (vedi "Durata della licenza"), il controllo sulla disponibilità di una licenza non è necessario. Aggiungiamo al token OAuth2, restituito al termine dell'autorizzazione, due campi: `session_id` e `license`. Il primo (`session_id`) è l'identificativo della sessione utente generato dal servizio di login. Il secondo (`license`) è un JWT con i dettagli della licenza in uso. Tra i dettagli (claims) della licenza c'è: - la durata della licenza (claim *exp*) - l'hardware per il quale è stata rilasciata (claim *hw_fingerprint*) La durata della licenza **non è collegata** alla durata del token OAuth2. Con queste modifiche abbiamo collegato ogni richiesta ad una sessione utente (e ad una licenza) e comunicato al client per quanto tempo può continuare a funzionare prima di aver bisogno di una nuova licenza. ### Durata della licenza La durata di una licenza dipende dal tipo del client e dai dettagli dell'utente (come la sede) che la richiede. | tipo | durata di default | connettività | | --------- | ----------------- | -------------- | | hw | unlimited | inaffidabile | | desktop | 1 gg | inaffidabile | | web | 10 minuti | affidabile | | 3rd party | unlimited | non importante | Un client di tipo *hw* (come il GL) può avere una connessione ad internet non affidabile ma è venduto insieme ad una macchina industriale; non ha senso limitare artificialmente la durata della licenza software. Potrebbe aver senso invece, un domani, istituire un'anagrafica delle macchine corredata dai loro numeri di serie (o concetto simile) e impedire il login alle macchine non registrate. > [name=Matteo Bertini] in questo caso quindi quando viene associato il token, al primo avvio o prima di spedire la macchina? Un client di tipo *desktop* (come Caligola) può avere una connessione ad internet non affidabile ma deve poter essere utilizzato anche in assenza di connessione. Il client, a cui viene rilasciata una licenza di lunga durata, verifica in autonomia fino a quando può restare in esecuzione. La licenza può anche essere salvata su disco ed essere utilizzata tra avvii diversi. Un client di tipo *web* ha, per definizione, una connessione affidabile e per questo possiamo fornirgli una licenza con una durata *breve*; possiamo ragionevolmente presumere che sia possibile implementare un meccanismo in background con cui la licenza viene periodicamente *estesa*. Sono due i motivi per cui vogliamo ridurre la durata della licenza ed hanno entrambi a che vedere con il conteggio delle stesse: 1. L'ambiente in cui vengono eseguite le applicazioni web (il browser) permette a qualsiasi utente di manipolare facilmente le applicazioni in esecuzione, per questo non possiamo fidarci e permettere a queste applicazioni di fare il reshaping degli utilizzi (vedi Conteggio delle licenze) 2. Senza la possibilità di fare reshaping la licenza verrebbe conteggiata come in uso dal momento in cui l'utente fa login a quando fa logout (vedi Rilascio della licenza); ma il fare logout è un'operazione che pochissimi utenti eseguono normalmente, anzi il modo standard di utilizzare una qualsiasi applicazione web moderna è di rimanere sempre connessi. Entrambi questi problemi possono essere mitigati da una licenza d'uso con una durata breve. > [name=Matteo Bertini] nel senso che l'app identifica l'utente come idle e non rinnova la licenza? Un client *3rd party* è sviluppato da terzi (quindi per definizione fuori dal nostro controllo) e può svolgere compiti di qualsiasi tipo (integrazione, creazione contenuti, statistiche). Quale che sia il suo compito probabilmente non ci guadagniamo nulla a limitare la licenza d'uso che gli rilasciamo, potrebbe essere più opportuno applicare altri tipo di limitazioni (ad esempio il numero di richieste in un dato tempo). > [name=Matteo Bertini] anche per questi, come ci immaginiamo che vengano attivati? Tipo Foobar prende Aurelia, poi vuole connetterla al suo PLM. Dove si crea e dove si monitora il token che gli assegnamo? ### Rilascio della licenza Una licenza viene considerata in uso finché non scade o fino a quando la sessione utente non viene terminata facendo logout. > [name=Matteo Bertini] oppure immagino chiudendo la finestra del browser ad una mancata richiesta per rinfrescare le credenziali il server lo considera logout. ### Estensione della licenza Una licenza può essere estesa chiamando una API che, se possibile, estenderà la durata della licenza collegata con la sessione utente. ### Conteggio della licenza Ad oggi prevediamo due tipi di licenza: 1. licenze *upfront* 1. licenze *floating* Le licenze di tipo *upfront* sono quelle, ad oggi, con una durata *unlimited* mentre le altre sono *floating*. Il conteggio di una licenza, per fini commerciali, ha senso solo per le licenze *floating*. L'idea di base è che una licenza si intende in uso dal momento in cui viene emessa fino a quando scade o non viene rilasciata. Il problema sorge con i client come Caligola che hanno bisogno di una licenza con durata lunghissima per poter lavorare offline, ma che devono poter conteggiare il tempo effettivo di utilizzo (ad esempio per non considerare la licenza in uso durante la notte). Per risolvere questo problema ad alcuni client sarà permesso di fare *usage reshaping*, tramite un API potranno comunicare gli intervalli di tempo in cui sono stati effettivamente in uso. > [name=Matteo Bertini] il modellista Caio apre il cad, fa login, e comincia a lavorare. La sua connessione viene isolata, e lui lavora per 3h, poi chiude e va a pranzo. Il mattino successivo c'è di nuovo linea, il cad si sincronizza con Aurelia, prende un token "fresco" e manda il reshaping, dicendo: di tutto il tempo che non ci siamo visti Caio ha lavorato dalle 9:00 alle 12:00. > 1. Cosa succede se per qualche ragione Caio disinstalla il Cad prima del reshaping? > 2. Cosa succede se accede ad internet via VPN e l'orologio di sistema va a spasso? (qua si spera che sappia anche in che time zone è... dipenderà dal sistema operativo, ma spero lo facciano tutti) > 3. Cosa succede se Caio si salva il profilo del cad a sessione aperta e lo usa su più macchine? (qua ci dovrebbe pensare `hw_fingerprint`, ma alle macchine virtuali è facile dare lo stesso mac address) > 4. Cosa succede se Caio riesce a cambiare il log dell'uso, o se decidiamo di firmarlo, a forgiarlo recuperando la chiave di calgola da qualche parte? > > Per 4) dicevamo al volo in call che: > - potrebbe essere una strategia commerciale vendere 5 sessioni di Caligola full time, estendibili fino a 20 (5 si pagano sempre, è il minimo uso previsto), > - a posteriori, sarebbe possibile fare anomaly detection sui reshape, e magari investigare sui casi atipici. ### Controllo della licenza Il controllo della licenza viene effettuato dal servizio *Watchmen* ad ogni API grazie al token OAuth2 dal quale viene recuperata la licenza collegata. ### Validità di una licenza Una licenza deve essere validata localmente da ogni client. Una licenza è valida se: 1. è stata emessa da Aurelia (verificata tramite chiave pubblica) 1. non è scaduta 1. è stata emessa per l'hw su cui è in esecuzione il client. ### Formato di una licenza Una licenza è un documento JWT firmato con una chiave pubblica/privata. I claim presenti nel token sono: - exp; (claim standard) la scandenza della licenza - iss; (claim standard) la url del nodo Aurelia che ha emesso il token - license_id; (claim custom) un id univoco e causale per identificare questa licenza - hw_fingerprint; (claim custom) un valore, generato dal client, che identificare uno specifico computer, l'unico che può utilizzare questa licenza. ## Caso d'uso: GL - client: desktop - licenza: upfront - offline: si Appena ne ha bisogno il GL fa login su Aurelia (magari utilizzando il login non interattivo basato su token) e utilizza le sue API senza preoccuparsi di nessun aspetto relativo al licensing. ## Caso d'uso: Caligola - client: desktop - licenza: floating - offline: si All'avvio Caligola controlla se c'è una licenza valida salvata localmente. Se la licenza esiste Caligola può avviarsi, altrimenti prova a fare login su Aurelia (magari utilizzando il login non interattivo basato su token) per ottenerne una e se il login fallisce termina. > [name=Matteo Bertini] non ho capito bene come funziona il token, ma immagino sia astratto a livello di libreria. Ma se ci fossero delle invarianti da rispettare anche a livello di applicazione, magari possiamo anticiparlo qua. Una volta avviato Caligola fa partire un thread in background che ogni 5 minuti prova a contattare Aurelia per estendere la licenza in uso e per fare *usage reshaphing*; un eventuale fallimento (ad esempio perché offline) non diventa un problema fin quando la licenza in uso è valida. > [name=Matteo Bertini] in caso di *usage reshaphing* fallito, Caligola (o la libreriea che esporrà l'API) si salva il log di uso da qualche parte, meglio se firmato o almeno offuscato. L'applicazione può contere una chiave privata, ma in qualche modo è sempre accessibile. Stessa cosa c'è per la chiave con cui è crittato il pacchetto PyInstaller, non sappiamo se qualcuno si è messo a estrarla per modificare il codice. Essendo le due cose di complessità analoga possiamo supporre che chi accede alla chiave privata può a questo punto evitare in toto il controllo della licenza con poco più sforzo. > Però dovremmo essere sicuri almeno che chi rompe la licenza non possa usare a sbafo anche le API. Ogni volta che Caligola riesce ad estendere la licenza la salva localmente. Se la licenza in uso scade e non è possibile estenderla Caligola termina. ## Caso d'uso: WebApp - client: web - licenza: floating - offline: no All'avvio il client web fa login su Aurelia (e grazie ai cookie settati da Hydra non vede ogni volta la pagina di login), ottiene una licenza e fa partire un worker thread che ogni cinque minuti prova ad estenderla. ## Caso d'uso: 3rd Party - client: 3rd party - licenza: upfront Appena ne ha bisogno il servizio 3rd Party fa login su Aurelia e utilizza le sue API senza preoccuparsi di nessun aspetto relativo al licensing. > [name=Matteo Bertini] non doveva avere un token? Vedi domanda sopra di quando lo assegnamo questo token? ## Risorse anonime TODO: Ha senso avere delle API anonime? Ad esempio l'API che genera l'svg di un pezzo può essere memorizzata in un PLM e usata in un secondo momento (magari a distanza di anni)? Meglio avere delle API anonime o aggiungere il supporto per le url *firmate*? > [name=Matteo Bertini] il PLM non dovrebbe già avere accesso via token illimitato? Serve una seconda via? > In pratica quel token è quasi per cliente, a loro la cura di non lasciarlo andare a giro perché è autenticato e concordo sul rate-limited. Poi possono usarlo sul PLM o sul backend del sito, a noi interessa il giusto, no?

    Import from clipboard

    Paste your markdown or webpage here...

    Advanced permission required

    Your current role can only read. Ask the system administrator to acquire write and comment permission.

    This team is disabled

    Sorry, this team is disabled. You can't edit this note.

    This note is locked

    Sorry, only owner can edit this note.

    Reach the limit

    Sorry, you've reached the max length this note can be.
    Please reduce the content or divide it to more notes, thank you!

    Import from Gist

    Import from Snippet

    or

    Export to Snippet

    Are you sure?

    Do you really want to delete this note?
    All users will lose their connection.

    Create a note from template

    Create a note from template

    Oops...
    This template has been removed or transferred.
    Upgrade
    All
    • All
    • Team
    No template.

    Create a template

    Upgrade

    Delete template

    Do you really want to delete this template?
    Turn this template into a regular note and keep its content, versions, and comments.

    This page need refresh

    You have an incompatible client version.
    Refresh to update.
    New version available!
    See releases notes here
    Refresh to enjoy new features.
    Your user state has changed.
    Refresh to load new user state.

    Sign in

    Forgot password

    or

    By clicking below, you agree to our terms of service.

    Sign in via Facebook Sign in via Twitter Sign in via GitHub Sign in via Dropbox Sign in with Wallet
    Wallet ( )
    Connect another wallet

    New to HackMD? Sign up

    Help

    • English
    • 中文
    • Français
    • Deutsch
    • 日本語
    • Español
    • Català
    • Ελληνικά
    • Português
    • italiano
    • Türkçe
    • Русский
    • Nederlands
    • hrvatski jezik
    • język polski
    • Українська
    • हिन्दी
    • svenska
    • Esperanto
    • dansk

    Documents

    Help & Tutorial

    How to use Book mode

    Slide Example

    API Docs

    Edit in VSCode

    Install browser extension

    Contacts

    Feedback

    Discord

    Send us email

    Resources

    Releases

    Pricing

    Blog

    Policy

    Terms

    Privacy

    Cheatsheet

    Syntax Example Reference
    # Header Header 基本排版
    - Unordered List
    • Unordered List
    1. Ordered List
    1. Ordered List
    - [ ] Todo List
    • Todo List
    > Blockquote
    Blockquote
    **Bold font** Bold font
    *Italics font* Italics font
    ~~Strikethrough~~ Strikethrough
    19^th^ 19th
    H~2~O H2O
    ++Inserted text++ Inserted text
    ==Marked text== Marked text
    [link text](https:// "title") Link
    ![image alt](https:// "title") Image
    `Code` Code 在筆記中貼入程式碼
    ```javascript
    var i = 0;
    ```
    var i = 0;
    :smile: :smile: Emoji list
    {%youtube youtube_id %} Externals
    $L^aT_eX$ LaTeX
    :::info
    This is a alert area.
    :::

    This is a alert area.

    Versions and GitHub Sync
    Get Full History Access

    • Edit version name
    • Delete

    revision author avatar     named on  

    More Less

    Note content is identical to the latest version.
    Compare
      Choose a version
      No search result
      Version not found
    Sign in to link this note to GitHub
    Learn more
    This note is not linked with GitHub
     

    Feedback

    Submission failed, please try again

    Thanks for your support.

    On a scale of 0-10, how likely is it that you would recommend HackMD to your friends, family or business associates?

    Please give us some advice and help us improve HackMD.

     

    Thanks for your feedback

    Remove version name

    Do you want to remove this version name and description?

    Transfer ownership

    Transfer to
      Warning: is a public team. If you transfer note to this team, everyone on the web can find and read this note.

        Link with GitHub

        Please authorize HackMD on GitHub
        • Please sign in to GitHub and install the HackMD app on your GitHub repo.
        • HackMD links with GitHub through a GitHub App. You can choose which repo to install our App.
        Learn more  Sign in to GitHub

        Push the note to GitHub Push to GitHub Pull a file from GitHub

          Authorize again
         

        Choose which file to push to

        Select repo
        Refresh Authorize more repos
        Select branch
        Select file
        Select branch
        Choose version(s) to push
        • Save a new version and push
        • Choose from existing versions
        Include title and tags
        Available push count

        Pull from GitHub

         
        File from GitHub
        File from HackMD

        GitHub Link Settings

        File linked

        Linked by
        File path
        Last synced branch
        Available push count

        Danger Zone

        Unlink
        You will no longer receive notification when GitHub file changes after unlink.

        Syncing

        Push failed

        Push successfully