OpenID Connect: autorizacija internih aplikacija od prilagođenih do standardnih

Prije nekoliko mjeseci implementirao sam poslužitelj OpenID Connect za upravljanje pristupom za stotine naših internih aplikacija. Od vlastitog razvoja, prikladnog u manjem opsegu, prešli smo na općeprihvaćeni standard. Pristup preko središnjeg servisa uvelike pojednostavljuje monotone operacije, smanjuje troškove implementacije autorizacija, omogućuje vam da pronađete mnogo gotovih rješenja i ne razbijate glavu s razvojem novih. U ovom članku govorit ću o ovoj tranziciji i neravninama koje smo uspjeli popuniti.

OpenID Connect: autorizacija internih aplikacija od prilagođenih do standardnih

Davno... Kako je sve počelo

Prije nekoliko godina, kada je bilo previše internih aplikacija za ručnu kontrolu, napisali smo aplikaciju za kontrolu pristupa unutar tvrtke. Radilo se o jednostavnoj Rails aplikaciji koja se spajala na bazu s podacima o zaposlenicima, gdje je konfiguriran pristup raznim funkcionalnostima. Istovremeno smo podigli prvi SSO koji se temeljio na provjeri tokena sa strane klijenta i autorizacijskog servera, token se prenosio u kriptiranom obliku s nekoliko parametara i verificirao na autorizacijskom serveru. Ovo nije bila najprikladnija opcija, budući da je svaka interna aplikacija morala opisati značajan sloj logike, a baze podataka zaposlenika bile su potpuno sinkronizirane s autorizacijskim poslužiteljem.

Nakon nekog vremena odlučili smo pojednostaviti zadatak centralizirane autorizacije. SSO je prenesen na balanser. Uz pomoć OpenRestyja, u Luu je dodan predložak koji je provjeravao tokene, znao kojoj aplikaciji ide zahtjev i mogao je provjeriti postoji li tamo pristup. Ovakav pristup uvelike je pojednostavio zadatak kontrole pristupa internim aplikacijama – u kodu svake aplikacije više nije bilo potrebno opisivati ​​dodatnu logiku. Zbog toga smo eksterno zatvorili promet, a sama aplikacija nije znala ništa o autorizaciji.

Međutim, jedan problem je ostao neriješen. Što je s aplikacijama koje trebaju podatke o zaposlenicima? Bilo je moguće napisati API za uslugu autorizacije, ali tada biste morali dodati dodatnu logiku za svaku takvu aplikaciju. Osim toga, htjeli smo se riješiti ovisnosti o jednoj od naših aplikacija koje smo sami napisali, a koja bi kasnije bila prevedena u OpenSource, na našem internom autorizacijskom poslužitelju. O tome ćemo neki drugi put. Rješenje za oba problema bio je OAuth.

zajedničkim standardima

OAuth je razumljiv, općeprihvaćen autorizacijski standard, ali kako samo njegova funkcionalnost nije dovoljna, odmah su počeli razmatrati OpenID Connect (OIDC). Sam OIDC je treća implementacija standarda otvorene provjere autentičnosti, koja je prešla u dodatak preko OAuth 2.0 protokola (otvoreni protokol za autorizaciju). Ovo rješenje rješava problem nedostatka podataka o krajnjem korisniku, a također omogućuje promjenu davatelja autorizacije.

Međutim, nismo odabrali određenog pružatelja usluga i odlučili smo dodati integraciju s OIDC-om za naš postojeći autorizacijski poslužitelj. U prilog ovoj odluci išla je činjenica da je OIDC vrlo fleksibilan u pogledu autorizacije krajnjeg korisnika. Stoga je bilo moguće implementirati OIDC podršku na vašem trenutnom autorizacijskom poslužitelju.

OpenID Connect: autorizacija internih aplikacija od prilagođenih do standardnih

Naš način implementacije vlastitog OIDC poslužitelja

1) Doveo podatke u željeni oblik

Za integraciju OIDC-a potrebno je trenutne korisničke podatke dovesti u oblik razumljiv standardu. U OIDC-u se to zove zahtjevi. Zahtjevi su u biti konačna polja u bazi podataka korisnika (ime, e-mail, telefon, itd.). postoji standardni popis maraka, a sve što nije uključeno u ovaj popis smatra se običajem. Stoga je prva točka na koju morate obratiti pozornost ako želite odabrati postojećeg OIDC pružatelja mogućnost prikladne prilagodbe novih marki.

Grupa žigova kombinirana je u sljedeći podskup - Opseg. Tijekom autorizacije ne traži se pristup određenim markama, već opsezima, čak i ako neki od brendova iz opsega nisu potrebni.

2) Provedena potrebna potpora

Sljedeći dio OIDC integracije je odabir i implementacija tipova autorizacija, tzv. grantova. Daljnji scenarij interakcije između odabrane aplikacije i autorizacijskog poslužitelja ovisit će o odabranoj dodjeli. Primjer sheme za odabir prave potpore prikazan je na donjoj slici.

OpenID Connect: autorizacija internih aplikacija od prilagođenih do standardnih

Za našu prvu prijavu koristili smo najčešće odobrenje, autorizacijski kod. Njegova razlika od ostalih je što je trostepeni, tj. prolazi dodatno ispitivanje. Prvo korisnik postavlja zahtjev za autorizacijskom dozvolom, dobiva token – autorizacijski kod, zatim s tim tokenom, kao s kartom za putovanje, traži pristupni token. Sva glavna interakcija ove autorizacijske skripte temelji se na preusmjeravanjima između aplikacije i autorizacijskog poslužitelja. Više o ovoj potpori možete pročitati здесь.

OAuth se pridržava koncepta da pristupni tokeni dobiveni nakon autorizacije trebaju biti privremeni i da se trebaju mijenjati, po mogućnosti u prosjeku svakih 10 minuta. Dodjela autorizacijskog koda je provjera u tri koraka putem preusmjeravanja, svakih 10 minuta za okretanje takvog koraka, iskreno, nije najugodniji zadatak za oči. Za rješavanje ovog problema postoji još jedan grant - Refresh Token, koji smo također koristili u našoj zemlji. Ovdje je sve lakše. Tijekom verifikacije iz drugog granta, osim glavnog pristupnog tokena, izdaje se još jedan - Refresh Token, koji se može koristiti samo jednom i njegov vijek trajanja je obično mnogo duži. S ovim Tokenom za osvježavanje, kada završi TTL (Time to Live) glavnog pristupnog tokena, zahtjev za novim pristupnim tokenom doći će do krajnje točke drugog odobrenja. Iskorišteni Refresh Token odmah se vraća na nulu. Ova provjera je u dva koraka i može se izvršiti u pozadini, korisniku neprimjetno.

3) Postavite prilagođene formate izlaznih podataka

Nakon što se odabrane potpore implementiraju, autorizacija radi, a vrijedi spomenuti i dobivanje podataka o krajnjem korisniku. OIDC ima zasebnu krajnju točku za to, gdje možete zatražiti korisničke podatke sa svojim trenutnim pristupnim tokenom i ako je ažuran. A ako se korisnički podaci ne mijenjaju tako često, a morate pratiti trenutne mnogo puta, možete doći do takvog rješenja kao što su JWT tokeni. Ove tokene također podržava standard. Sam JWT token sastoji se od tri dijela: zaglavlje (informacije o tokenu), korisni sadržaj (svi potrebni podaci) i potpis (potpis, token je potpisan od strane poslužitelja i kasnije možete provjeriti izvor njegovog potpisa).

U OIDC implementaciji, JWT token se zove id_token. Može se zatražiti zajedno s običnim pristupnim tokenom i sve što preostaje je provjeriti potpis. Poslužitelj za autorizaciju ima zasebnu krajnju točku za to s hrpom javnih ključeva u formatu J.W.K.. A kad smo već kod ovoga, vrijedi spomenuti da postoji još jedna krajnja točka, koja, na temelju standarda RFC5785 odražava trenutnu konfiguraciju OIDC poslužitelja. Sadrži sve adrese krajnjih točaka (uključujući adresu prstena javnih ključeva koji se koristi za potpisivanje), podržane marke i opsege, korištene algoritme šifriranja, podržane dodjele itd.

Na primjer na Googleu:

{
 "issuer": "https://accounts.google.com",
 "authorization_endpoint": "https://accounts.google.com/o/oauth2/v2/auth",
 "device_authorization_endpoint": "https://oauth2.googleapis.com/device/code",
 "token_endpoint": "https://oauth2.googleapis.com/token",
 "userinfo_endpoint": "https://openidconnect.googleapis.com/v1/userinfo",
 "revocation_endpoint": "https://oauth2.googleapis.com/revoke",
 "jwks_uri": "https://www.googleapis.com/oauth2/v3/certs",
 "response_types_supported": [
  "code",
  "token",
  "id_token",
  "code token",
  "code id_token",
  "token id_token",
  "code token id_token",
  "none"
 ],
 "subject_types_supported": [
  "public"
 ],
 "id_token_signing_alg_values_supported": [
  "RS256"
 ],
 "scopes_supported": [
  "openid",
  "email",
  "profile"
 ],
 "token_endpoint_auth_methods_supported": [
  "client_secret_post",
  "client_secret_basic"
 ],
 "claims_supported": [
  "aud",
  "email",
  "email_verified",
  "exp",
  "family_name",
  "given_name",
  "iat",
  "iss",
  "locale",
  "name",
  "picture",
  "sub"
 ],
 "code_challenge_methods_supported": [
  "plain",
  "S256"
 ],
 "grant_types_supported": [
  "authorization_code",
  "refresh_token",
  "urn:ietf:params:oauth:grant-type:device_code",
  "urn:ietf:params:oauth:grant-type:jwt-bearer"
 ]
}

Dakle, koristeći id_token, možete prenijeti sve potrebne oznake u sadržaj tokena i ne kontaktirati autorizacijski poslužitelj svaki put kako biste zatražili korisničke podatke. Nedostatak ovog pristupa je što promjena korisničkih podataka s poslužitelja ne dolazi odmah, već zajedno s novim pristupnim tokenom.

Rezultati provedbe

Dakle, nakon implementacije vlastitog OIDC poslužitelja i konfiguriranja veza s njim na aplikativnoj strani, riješili smo problem prijenosa informacija o korisnicima.
Budući da je OIDC otvoreni standard, imamo mogućnost odabira postojećeg pružatelja ili implementacije poslužitelja. Isprobali smo Keycloak, koji se pokazao vrlo praktičnim za konfiguriranje, nakon postavljanja i promjene konfiguracije veze na strani aplikacije, spreman je za rad. Što se tiče aplikacije, sve što preostaje jest promijeniti konfiguraciju veze.

Govorimo o postojećim rješenjima

Unutar naše organizacije, kao prvi OIDC poslužitelj, sastavili smo vlastitu implementaciju koju smo po potrebi nadopunjavali. Nakon detaljnog pregleda drugih gotovih rješenja, možemo reći da je ovo sporna točka. U prilog odluci o implementaciji vlastitog poslužitelja govorila je zabrinutost pružatelja u nedostatku potrebnih funkcionalnosti, kao i prisutnost starog sustava u kojem su postojala različita prilagođena ovlaštenja za neke usluge i dosta toga. podataka o zaposlenicima već je pohranjeno. Međutim, u gotovim implementacijama postoje pogodnosti za integraciju. Recimo, Keycloak ima svoj sustav za upravljanje korisnicima i podaci se pohranjuju direktno u njemu i tu neće biti teško prestići svoje korisnike. Kako biste to učinili, Keycloak ima API koji će vam omogućiti da u potpunosti izvršite sve potrebne radnje prijenosa.

Još jedan primjer certificirane, zanimljive, po mom mišljenju, implementacije je Ory Hydra. Zanimljiv je jer se sastoji od različitih komponenti. Za integraciju morat ćete povezati svoju uslugu upravljanja korisnicima s njihovom uslugom autorizacije i po potrebi proširiti.

Keycloak i Ory Hydra nisu jedina gotova rješenja. Najbolje je odabrati implementaciju s certifikatom OpenID Foundationa. Ova rješenja obično imaju značku OpenID certifikata.

OpenID Connect: autorizacija internih aplikacija od prilagođenih do standardnih

Također ne zaboravite na postojeće plaćene pružatelje usluga ako ne želite zadržati svoj OIDC poslužitelj. Danas postoji mnogo dobrih opcija.

što dalje

U skoroj budućnosti ćemo na drugačiji način zatvoriti promet prema internim servisima. Planiramo prenijeti naš trenutni SSO na balanseru koristeći OpenResty na proxy koji se temelji na OAuthu. Ovdje već postoji mnogo gotovih rješenja, na primjer:
github.com/bitly/oauth2_proxy
github.com/ory/oathkeeper
github.com/keycloak/keycloak-gatekeeper

Dodatni materijali

jwt.io – dobra usluga za provjeru JWT tokena
openid.net/developers/certified - popis certificiranih OIDC implementacija

Izvor: www.habr.com

Dodajte komentar