Skip to Content

Client Credentials M2M

Il grant OAuth2 client_credentials consente ai servizi backend, agli script automatizzati e ai job cron di ottenere access token senza interazione umana. Questi token M2M (Machine-to-Machine) vengono usati per autenticare le chiamate API da servizio a servizio.


Come Funziona

  1. Il servizio invia le proprie credenziali (client ID + secret) all’endpoint token di Auris
  2. Auris verifica le credenziali e controlla gli scope richiesti
  3. Auris emette un access token JWT di breve durata con gli scope concessi
  4. Il servizio include il token nell’header Authorization: Bearer nelle chiamate API

Non è coinvolto nessun utente — è il servizio stesso il “principal” autenticato.


Configurazione nella Console

Crea un’Applicazione M2M

Vai su Console → Applicazioni → Nuova Applicazione e seleziona Machine-to-Machine (M2M).

Assegna gli Scope

Nella scheda Permissions, assegna gli scope che questo servizio può richiedere. Usa il principio del minimo privilegio — concedi solo gli scope necessari.

Copia le Credenziali

Dalla scheda Credenziali, copia:

  • Client ID
  • Client Secret (mostrato una sola volta — conservalo in modo sicuro)

Implementazione

const AURIS_DOMAIN = 'https://auth.tuodominio.com' const CLIENT_ID = 'il-tuo-client-id' const CLIENT_SECRET = process.env.AURIS_CLIENT_SECRET async function getM2MToken(scopes = []) { const response = await fetch(`${AURIS_DOMAIN}/api/auth/token`, { method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded' }, body: new URLSearchParams({ grant_type: 'client_credentials', client_id: CLIENT_ID, client_secret: CLIENT_SECRET, scope: scopes.join(' '), }), }) if (!response.ok) { throw new Error(`Token request failed: ${response.status}`) } return response.json() } // Uso const { access_token, expires_in } = await getM2MToken(['read:users', 'write:logs']) // Chiama un'API protetta const users = await fetch('https://api.tuodominio.com/users', { headers: { 'Authorization': `Bearer ${access_token}` }, }).then(r => r.json())

Formato del Token M2M

I token M2M sono JWT standard con questi claim aggiuntivi:

{ "iss": "https://auth.tuodominio.com", "sub": "il-tuo-client-id", "aud": "https://api.tuodominio.com", "exp": 1735689600, "iat": 1735686000, "scope": "read:users manage:billing", "type": "m2m", "tenant_id": "ten_abc123" }

Il campo type: "m2m" distingue i token M2M dai token utente. Puoi controllare questo claim nelle tue API per applicare policy diverse.


Caching dei Token

I token M2M sono validi tipicamente per 1 ora. Per evitare di richiedere un nuovo token ad ogni chiamata API, usa il caching:

Non richiedere un nuovo token M2M per ogni chiamata API. Questo sovraccarica Auris e introduce latenza inutile. Usa sempre il caching con rinnovo basato sulla scadenza, come mostrato nell’esempio Next.js sopra.


Token Binding con DPoP

Per una sicurezza maggiore, puoi legare il token M2M alla chiave del client usando DPoP (Demonstrating Proof of Possession):

import { createDpopProof } from '@auris/js/dpop' // Genera una coppia di chiavi DPoP const { privateKey, publicKey } = await crypto.subtle.generateKey( { name: 'ECDSA', namedCurve: 'P-256' }, true, ['sign', 'verify'] ) // Crea la proof DPoP const dpopProof = await createDpopProof({ method: 'POST', url: `${AURIS_DOMAIN}/api/auth/token`, privateKey, publicKey, }) // Richiedi il token con DPoP const response = await fetch(`${AURIS_DOMAIN}/api/auth/token`, { method: 'POST', headers: { 'Content-Type': 'application/x-www-form-urlencoded', 'DPoP': dpopProof, }, body: new URLSearchParams({ grant_type: 'client_credentials', client_id: CLIENT_ID, client_secret: CLIENT_SECRET, scope: 'read:users', }), })

Consulta la guida DPoP per i dettagli completi.


Proteggere le Proprie API con Token M2M

Per validare i token M2M nelle tue API:

import jwt from 'jsonwebtoken' import jwksClient from 'jwks-rsa' const client = jwksClient({ jwksUri: 'https://auth.tuodominio.com/.well-known/jwks.json', }) async function verifyM2MToken(token) { const decoded = jwt.decode(token, { complete: true }) const key = await client.getSigningKey(decoded.header.kid) const publicKey = key.getPublicKey() const payload = jwt.verify(token, publicKey, { issuer: 'https://auth.tuodominio.com', audience: 'https://api.tuodominio.com', }) // Verifica che sia un token M2M if (payload.type !== 'm2m') { throw new Error('Not an M2M token') } // Verifica gli scope richiesti const scopes = payload.scope?.split(' ') ?? [] if (!scopes.includes('read:users')) { throw new Error('Insufficient scope') } return payload }

Endpoint API

POST/api/auth/token

Token endpoint. Per M2M, imposta grant_type=client_credentials con client_id, client_secret e scope. Restituisce un access token JWT.

GET/api/applications/{id}/scopesRequires: view:applications

Elenca gli scope disponibili per un’applicazione M2M.

PATCH/api/applications/{id}/scopesRequires: manage:applications

Aggiorna gli scope assegnati a un’applicazione M2M.


Guide Correlate