Identiteettivarmistus
Välitä kirjautuneen käyttäjän tiedot palvelimen allekirjoittamina ja valitse oikea varmennustapa keskusteluikkunalle.
Avaa kopiointivalikko
Ilman identiteettivarmistusta kävijä voi antaa identify-kutsussa minkä tahansa käyttäjätunnisteen. Allekirjoita tunnistetiedot omalla palvelimellasi vasta, kun olet tarkistanut kirjautumisen. Aihio tarkistaa allekirjoituksen, ei oman sovelluksesi kirjautumistapaa.
Aihio tukee kahta menetelmää: HMAC-käyttäjätiivistettä ja JWT HS256 -tokenia.
Mistä salaisuus löytyy
Osio nimeltä “Mistä salaisuus löytyy”Avaa Oma Aihio -palvelussa agentin Asetukset → Suojaus. Paina Identiteetin varmennus -osiossa Luo avain ja kopioi arvo heti talteen: se näytetään vain kerran. Salaisuus näyttää esimerkiksi tältä: aihio_idv_….
Tallenna salaisuus palvelimesi ympäristömuuttujaksi (esim. AIHIO_IDENTITY_SECRET). Älä koskaan sisällytä sitä selainpuolen JavaScript-koodiin tai versiohallintaan.
Menetelmä A: HMAC-käyttäjätiiviste
Osio nimeltä “Menetelmä A: HMAC-käyttäjätiiviste”Laske HMAC-SHA256(salaisuus, user_id) palvelimellasi ja välitä tulos user_hash-kentässä. Tulosteen on oltava pienet kirjaimet sisältävä heksadesimaali. Aihio hylkää isolla kirjoitetun heksan.
Kaikki alla olevat esimerkit tuottavat oikean muodon oletuksena.
Node.js
Osio nimeltä “Node.js”const crypto = require('crypto');
function computeUserHash(secret, userId) { return crypto.createHmac('sha256', secret).update(userId).digest('hex');}Python
Osio nimeltä “Python”import hmac, hashlib
def compute_user_hash(secret: str, user_id: str) -> str: return hmac.new( secret.encode('utf-8'), user_id.encode('utf-8'), hashlib.sha256 ).hexdigest()function compute_user_hash(string $secret, string $user_id): string { return hash_hmac('sha256', $user_id, $secret);}require 'openssl'
def compute_user_hash(secret, user_id) OpenSSL::HMAC.hexdigest('SHA256', secret, user_id)endMenetelmä B: JWT HS256 -token
Osio nimeltä “Menetelmä B: JWT HS256 -token”Allekirjoita JWT HS256-algoritmilla chatbotin salaisuudella. exp-väite on pakollinen: Aihio hylkää tokenin ilman sitä. Kellopoikkeama on 30 sekuntia.
Valitse lyhyt, käyttötarkoitukseen sopiva voimassaoloaika, esimerkiksi yksi tunti (exp = iat + 3600). Tämä on esimerkkivalinta, ei palvelun kaikille tokeneille asettama enimmäisaika. Lisää myös iat, jotta asetettu tokenin enimmäisikä voidaan tarkistaa palvelimella.
Tuetut JWT-väitteet
Osio nimeltä “Tuetut JWT-väitteet”| Väite | Tyyppi | Pakollinen | Huomio |
|---|---|---|---|
user_id tai sub | merkkijono | kyllä (jompikumpi) | Käyttäjätunnus omassa järjestelmässäsi |
external_id | merkkijono | ei | user_id/sub-alias |
exp | numero (Unix-aika) | kyllä | Vanheneminen; 30 s poikkeama |
iat | numero (Unix-aika) | Suositeltu | Myöntämisaika tokenin enimmäisiän tarkistusta varten |
nbf | numero (Unix-aika) | ei | Voimassa aikaisintaan; 30 s poikkeama |
email | merkkijono | ei | Esitäyttää esikeskustelulomakkeen |
name | merkkijono | ei | Esitäyttää esikeskustelulomakkeen |
phonenumber | merkkijono | ei | Varmennin hyväksyy kentän; ei lupaus lomakkeen esitäytöstä |
custom_attributes | objekti | ei | Vapaamuotoiset lisätiedot |
stripe_accounts | taulukko | ei | Käyttäjän Stripe-tilit (ks. alla) |
Vain HS256 hyväksytään. RS256-, ES256- tai alg: none -tokeneja ei hyväksytä.
Allekirjoita JWT palvelimella
Osio nimeltä “Allekirjoita JWT palvelimella”Allekirjoita token chatbotin salaisuudella HS256-algoritmilla. Aseta exp (suositus 1 tunti). custom_attributes on vapaaehtoinen.
Node.js (jsonwebtoken)
Osio nimeltä “Node.js (jsonwebtoken)”Asennus: npm install jsonwebtoken
const jwt = require('jsonwebtoken');
function signIdentityToken(secret, user) { return jwt.sign( { user_id: user.id, email: user.email, name: user.name, custom_attributes: { plan: user.plan }, }, secret, { algorithm: 'HS256', expiresIn: '1h' }, );}Ruby on Rails (jwt-kirjasto)
Osio nimeltä “Ruby on Rails (jwt-kirjasto)”Asennus: bundle add jwt
require 'jwt'
def sign_identity_token(secret, user) payload = { user_id: user.id, email: user.email, name: user.name, custom_attributes: { plan: user.plan }, exp: Time.now.to_i + 3600, iat: Time.now.to_i, } JWT.encode(payload, secret, 'HS256')endDjango / Python (PyJWT)
Osio nimeltä “Django / Python (PyJWT)”Asennus: pip install PyJWT
import timeimport jwt
def sign_identity_token(secret: str, user) -> str: payload = { 'user_id': user.id, 'email': user.email, 'name': user.name, 'custom_attributes': {'plan': user.plan}, 'exp': int(time.time()) + 3600, 'iat': int(time.time()), } return jwt.encode(payload, secret, algorithm='HS256')PHP (firebase/php-jwt)
Osio nimeltä “PHP (firebase/php-jwt)”Asennus: composer require firebase/php-jwt
use Firebase\JWT\JWT;
function sign_identity_token(string $secret, $user): string { $payload = [ 'user_id' => $user->id, 'email' => $user->email, 'name' => $user->name, 'custom_attributes' => ['plan' => $user->plan], 'exp' => time() + 3600, 'iat' => time(), ]; return JWT::encode($payload, $secret, 'HS256');}Go (golang-jwt)
Osio nimeltä “Go (golang-jwt)”Asennus: go get github.com/golang-jwt/jwt/v5
import ( "time"
"github.com/golang-jwt/jwt/v5")
func SignIdentityToken(secret string, user User) (string, error) { token := jwt.NewWithClaims(jwt.SigningMethodHS256, jwt.MapClaims{ "user_id": user.ID, "email": user.Email, "name": user.Name, "custom_attributes": map[string]any{"plan": user.Plan}, "exp": time.Now().Add(time.Hour).Unix(), "iat": time.Now().Unix(), }) return token.SignedString([]byte(secret))}Java (jjwt)
Osio nimeltä “Java (jjwt)”Asennus (Maven): io.jsonwebtoken:jjwt-api, jjwt-impl, jjwt-jackson (runtime).
import io.jsonwebtoken.Jwts;import javax.crypto.spec.SecretKeySpec;import java.nio.charset.StandardCharsets;import java.util.Date;import java.util.Map;
String signIdentityToken(String secret, User user) { SecretKeySpec key = new SecretKeySpec( secret.getBytes(StandardCharsets.UTF_8), "HmacSHA256"); return Jwts.builder() .claim("user_id", user.getId()) .claim("email", user.getEmail()) .claim("name", user.getName()) .claim("custom_attributes", Map.of("plan", user.getPlan())) .expiration(new Date(System.currentTimeMillis() + 3_600_000)) .issuedAt(new Date()) .signWith(key) .compact();}Stripe-tilien välittäminen (tuleva ominaisuus)
Osio nimeltä “Stripe-tilien välittäminen (tuleva ominaisuus)”Varmennin hyväksyy stripe_accounts-kentän, mutta se ei ota käyttöön Stripe-tilausten tai laskujen hakua. Älä lähetä näitä tietoja varmuuden vuoksi. Käytä vain nykyisen integraatiosi tarvitsemia kenttiä.
Identiteetin välittäminen widgetille
Osio nimeltä “Identiteetin välittäminen widgetille”Laske arvo palvelimella ja välitä se kirjautuneelle käyttäjälle suojatun vastauksen kautta. Korvaa alla olevat paikkamerkit näillä arvoilla. Älä välitä allekirjoitussalaisuutta. Valitse vain toinen esimerkin menetelmistä:
// Menetelmä A: HMAC-käyttäjätiivistewindow.AihioWidget('identify', { externalId: currentUser.id, // Myös 'user_id' hyväksytään; externalId on ensisijainen. email: currentUser.email, name: currentUser.name, user_hash: '{{ palvelimelta_laskettu_tiiviste }}',});
// Menetelmä B: JWT-tokenwindow.AihioWidget('identify', { token: '{{ palvelimelta_allekirjoitettu_jwt }}',});currentUser tarkoittaa oman sovelluksesi kirjautunutta käyttäjää, ei selaimesta vapaasti valittavaa käyttäjätunnistetta. identify-kutsun voi tehdä init-kutsun jälkeen. Jos keskusteluikkunan koodi ei ole vielä latautunut, upotuskoodin komentojono suorittaa kutsun käynnistyksen yhteydessä.
Tyhjennä identiteetti uloskirjautumisen yhteydessä. Tämä ei poista palveluun tallennettuja keskusteluja:
window.AihioWidget('resetUser');Salaisuuden kierrätys
Osio nimeltä “Salaisuuden kierrätys”Salaisuuden kierrätys ei välittömästi mitätöi vanhaa salaisuutta. Edellinen salaisuus on voimassa 24 tuntia kierrätyksen jälkeen. Päivitä allekirjoituskoodi kaikkiin ympäristöihin ennen vanhan salaisuuden vanhenemista.
Tavallinen kierrätys ilman salaisuuden paljastumista
Osio nimeltä “Tavallinen kierrätys ilman salaisuuden paljastumista”Kierrätä salaisuus
Paina Kierrätä kohdassa Asetukset → Suojaus → Identiteetin varmennus.
Päivitä ympäristömuuttuja
Päivitä
AIHIO_IDENTITY_SECRETpalvelimesi ympäristöön uudella arvolla.Ota muutos käyttöön
Ota uusi ympäristömuuttuja käyttöön. Vanha salaisuus jatkaa istuntojen varmennusta rinnakkain 24 tunnin ajan.
Odota 24 tuntia
24 tunnin kuluttua vanha salaisuus lakkaa toimimasta. Holvimerkintä säilytetään, mutta sitä ei enää käytetä varmennuksessa.
Pakota identiteettivarmistus
Osio nimeltä “Pakota identiteettivarmistus”Oletuksena varmistus on avoin (fail-open). Pakotuksen voi ottaa käyttöön agentin Asetukset → Suojaus -näkymästä.
- Pakota identiteettivarmistus. Pyyntö, joka väittää identiteettiä (
user_id/external_id,email,tokentaiuser_hash) ilman validia allekirjoitusta, hylätään HTTP 403:lla. Anonyymit kävijät voivat silti keskustella. - Vaadi tunnistautuminen (tiukka). Jokainen varmistamaton pyyntö hylätään, myös anonyymit.
Kun pakotus on päällä, keskustelu sidotaan varmennettuun external_id-tunnisteeseen. Uudelleenkäytetty reference_id, jonka tallennettu identiteetti ei vastaa varmennettua tokenia, aloittaa uuden keskustelun sen sijaan että liittyisi vanhaan. Näin yksi kävijä ei voi jatkaa toisen kävijän yksityistä keskustelua.
Ota pakotus käyttöön vasta onnistuneen varmennustestin jälkeen. Testaa erikseen voimassa oleva JWT, vanhentunut JWT ja kävijä ilman tunnistetta. Varmista, että valitsemasi anonyymin käytön raja vastaa tarkoitustasi.
Turvallinen yhteys ja istunnon kesto
Osio nimeltä “Turvallinen yhteys ja istunnon kesto”- Vain turvallinen yhteys. Kun tämä on päällä, keskusteluikkuna välittää ja tallentaa identiteetin vain HTTPS-yhteydellä. HTTP-sivulla identiteetti jää välittämättä; palvelimen pakotusasetukset ratkaisevat, sallitaanko anonyymi keskustelu.
- Istunnon kesto. Aseta tokenin suurin hyväksytty ikä. Palvelin voi tarkistaa iän tokenin numeerisesta
iat-kentästä. Ilman sitä tämä ikäraja ei korvaaexp-vanhenemisaikaa. Sisällytä uusiin tokeneihin sekäiatettäexpja testaa valitsemasi raja.
Käyttöönottotapa: toiminto avoimena (fail-open)
Osio nimeltä “Käyttöönottotapa: toiminto avoimena (fail-open)”Kun pakotus ei ole käytössä, puuttuva tai epäonnistunut varmennus sallii keskustelun jatkumisen identity_verified = false -tilassa. Pakotus ja tiukka tunnistautumisvaatimus muuttavat tämän käytöksen edellä kuvatulla tavalla.
Varmistamaton user_id tai sähköposti on käyttäjän antama näyttövihje. Pelkkä identity_verified-arvo ei kerro, varmennettiinko JWT vai HMAC-tiiviste. Yksityisiä tietoja käsittelevä toiminto edellyttää JWT:tä ja erillistä käyttöoikeuden tarkistusta.
Allekirjoitetut vs allekirjoittamattomat tiedot
Osio nimeltä “Allekirjoitetut vs allekirjoittamattomat tiedot”Vain JWT:n sisällä allekirjoitetut tiedot ovat varmennettuja ja luotettavia. Kaikki muu on näyttövihje, jonka lähettäjä voi väärentää.
| Allekirjoitettu (luotettava) | Allekirjoittamaton (vain vihje) |
|---|---|
user_id / external_id | Prechat-lomakkeen nimi, sähköposti ja suostumus |
email, name, custom_attributes (kun ne ovat JWT:n sisällä) | Mikä tahansa x-identify-otsikko ilman JWT:tä |
HMAC-käyttäjätiiviste (tapa A) varmentaa vain external_id-arvon. Jos haluat luottaa email-, name- tai mukautettuihin kenttiin, allekirjoita ne JWT:n sisällä (tapa B). Lähettäjän antamat kentät hyväksytään näyttövihjeinä. Niitä ei koskaan tallenneta varmennettuina, ja keskustelun identity_verified-lippu pysyy arvossa false, ellei validia allekirjoitusta ole.
Tietoturvatarkistuslista
Osio nimeltä “Tietoturvatarkistuslista”- Tallenna agentin salaisuus yksinomaan palvelimelle. Älä sisällytä sitä selainpuolen JavaScript-koodiin tai versiohallintaan.
- Aseta
iatja lyhytexpjokaiseen JWT-tokeniin. - Jos salaisuus paljastuu, valitse Asetukset → Suojaus → Identiteetin varmennus → Poista, luo uusi avain, ota se käyttöön palvelimella ja varmenna toiminta ennen pakotuksen palauttamista. Älä käytä tavallista kierrätystä salaisuuden mitätöintiin.
- Vaadi yksityisiä tietoja käsittelevältä toiminnolta JWT-varmennus. Tarkista omassa rajapinnassasi lisäksi, että käyttäjällä on oikeus juuri pyydettyyn tietoon.
- Käytä HMAC-funktiosi oletustulosteen pieniä kirjaimia sisältävää heksadesimaalia.