Mundarija (29)
- Bu darsda
- 1. Nega bu kerak?
- 1.1 Rollar portlashi
- 1.2 Uch model
- 2. ABAC: atributlarga asoslangan ruxsat
- 2.1 To'rt xil atribut
- 2.2 To'rt qoida bitta funksiyada
- 3. ReBAC: munosabatlar
- 3.1 Zanzibar g'oyasi
- 3.2 O'zimizning kichik ReBAC
- 3.3 Tayyor ReBAC xizmatlari
- 4. Policy engine: qoidalar alohida qatlamda
- 4.1 PDP va PEP
- 4.2 CASL: qoidalar ma'lumot sifatida
- 4.3 Qoidalar JSON — frontend bilan ulashish
- 4.4 Narxi: o'lchov
- 4.5 Boshqa engine'lar
- 4.6 Ma'lumotlar bazasi bilan bog'lash
- 4.7 Siyosatni test qilish
- 5. Hujumchi nigohi
- 6. Ko'p uchraydigan xatolar
- 7. Mashqlar
- 1-mashq (oson): qaysi model?
- 2-mashq (o'rta): bo'lim va maxfiylik
- 3-mashq (qiyin): kesh bilan qobiliyat
- 8. Loyiha qadami: nega kanonga kirmadi
- 9. Real ishda
- Xulosa
- Manbalar
ABAC, ReBAC va policy engine'lar: atribut, munosabat va CASL
Qisqacha: RBAC "rol nima qila oladi" degan savolga javob beradi. Lekin "faqat ish vaqtida", "bajarilgan vazifani hech kim o'zgartirmaydi", "menga ulashilgan vazifani o'qiyman" kabi qoidalar rolga sig'maydi. ABAC qarorni atributlar (foydalanuvchi, resurs, muhit) bo'yicha, ReBAC esa munosabatlar ("azo", "ulashilgan", "ota papka") bo'yicha qiladi. Qoidalar ko'paysa, ularni bitta joyga — siyosat (policy) qatlamiga yig'ishadi. Kanon bir xil to'rtta qoidani oddiy funksiya va CASL bilan yozdi: natijalar 9 holatda bir xil, lekin funksiya tezroq va CASL qobiliyatini har so'rovda qurish qimmat.
Bu darsda
- RBAC qayerda yetmasligini va "rollar portlashi" ni tushuntira olasiz.
- ABAC qoidasini (foydalanuvchi, resurs, muhit atributlari) funksiya sifatida yozasiz.
- ReBAC va Zanzibar g'oyasini munosabatlar ro'yxati bilan ko'rsatasiz.
- CASL kabi policy engine nima berishini va nima turishini (tezlik, murakkablik) baholaysiz.
- Bu tajriba nega
vazifalar-apiga kirmaganini tushunasiz.
Oldin bilishingiz kerak: RBAC va resurs egaligi, Row Level Security, Intl.DateTimeFormat.
Oldingi darsda ikkita rol va "o'z vazifasi" qoidasi bilan vazifalar-api ni himoyaladik. Bir kishilik vazifalar ro'yxati uchun bu yetarli. Endi tasavvur qiling: «Bahor» oshxonasida Jasur aka vazifalarni oshpazlar bilan ulashmoqchi, admin Bekzod esa tunda hisoblarni bloklay olmasin. Rollar bilan bu qoidalarni qanday yozasiz?
1. Nega bu kerak?
1.1 Rollar portlashi
Yangi qoidalarni rol bilan yozib ko'ramiz:
- "admin hisoblarni bloklay oladi, lekin faqat 09:00–18:00" →
admin_kunduzgiroli? - "Dilnoza Azizning 10-vazifasini o'qiy oladi" →
vazifa10_oquvchiroli? - "bajarilgan vazifani hech kim tahrirlamaydi" → bu umuman rol emas, vazifaning holati.
Har yangi shart rollar sonini ko'paytiradi. Bu hodisa rollar portlashi (role explosion) deyiladi. Tez orada sizda 200 ta rol bo'ladi va hech kim kimda nima borligini bilmaydi.
Muammo shundaki, bu qoidalar kimga emas, vaziyatga bog'liq: soatga, vazifa holatiga, ikki odam orasidagi munosabatga. Ular uchun boshqa modellar bor.
1.2 Uch model
| Model | Qaror nimaga qarab | Misol |
|---|---|---|
| RBAC | foydalanuvchi roli | "admin bloklaydi" |
| ABAC | atributlar | "admin, 09–18 da, adminni emas" |
| ReBAC | munosabatlar | "ulashilgan vazifani o'qiydi" |
Ular bir-birini inkor qilmaydi. Amalda RBAC asos bo'ladi, ABAC va ReBAC esa uning ustiga qo'shiladi.
2. ABAC: atributlarga asoslangan ruxsat
2.1 To'rt xil atribut
ABAC (Attribute-Based Access Control) qarorni to'rt manbadagi atributlardan chiqaradi:
- subyekt (subject) — kim: id, rol, bo'lim, malaka;
- resurs (resource) — nima: egasi, holati (
bajarildi), maxfiylik darajasi; - amal (action) — nima qilmoqchi:
oqish,yangilash,bloklash; - muhit (environment) — qachon va qayerdan: soat, IP, qurilma.
Qoida — shu atributlar ustidagi mantiqiy ifoda. Oldingi darsdagi egalik ham aslida ABAC: resurs.egasiId === subyekt.id.
2.2 To'rt qoida bitta funksiyada
Kanon tajribasi uchun to'rtta qoida tanlandi — ular kelajakdagi jamoaviy loyihaga ko'prik:
- Egasi o'z vazifasini o'qiydi va yangilaydi (RBAC + egalik).
- Vazifa ulashilgan foydalanuvchi uni faqat o'qiydi (ReBAC — munosabat).
- Admin hisoblarni bloklay oladi, lekin faqat ish vaqtida, 09:00–18:00 Toshkent vaqti bilan, va adminni emas (ABAC — muhit atributi).
- Bajarilgan vazifani hech kim yangilamaydi (ABAC — resurs atributi).
Kanon tajribasidagi funksiya (telefon uchun bo'lingan) va o'sha 9 ta holat:
const toshkentSoati = (d) => Number(new Intl.DateTimeFormat("en-GB", {
timeZone: "Asia/Tashkent", hour: "2-digit", hour12: false,
}).format(d));
function mumkinmi(f, amal, resurs, muhit) {
if (resurs.tur === "Vazifa") {
const v = resurs.v;
if (amal === "yangilash" && v.bajarildi) return false;
if (v.egasiId === f.id) return true;
return amal === "oqish" && v.ulashilgan.includes(f.id);
}
if (resurs.tur === "Hisob" && amal === "bloklash") {
const s = toshkentSoati(muhit.vaqt);
return f.rol === "admin" && s >= 9 && s < 18 &&
resurs.h.rol !== "admin";
}
return false;
}
const aziz = { id: 1, rol: "foydalanuvchi" };
const dilnoza = { id: 2, rol: "foydalanuvchi" };
const bekzod = { id: 3, rol: "admin" };
const v1 = { id: 10, egasiId: 1, bajarildi: false, ulashilgan: [2] };
const v2 = { id: 11, egasiId: 1, bajarildi: true, ulashilgan: [] };
const kun = { vaqt: new Date("2026-10-28T06:00:00Z") }; // 11:00
const tun = { vaqt: new Date("2026-10-28T20:00:00Z") }; // 01:00
const V = (v) => ({ tur: "Vazifa", v });
const H = (id, rol) => ({ tur: "Hisob", h: { id, rol } });
const HOLATLAR = [
["Aziz o'z vazifasini yangilaydi", aziz, "yangilash", V(v1), kun],
["Aziz bajarilganni yangilaydi", aziz, "yangilash", V(v2), kun],
["Dilnoza ulashilganni o'qiydi", dilnoza, "oqish", V(v1), kun],
["Dilnoza ulashilganni yangilaydi", dilnoza, "yangilash", V(v1),
kun],
["Dilnoza ulashilmaganni o'qiydi", dilnoza, "oqish", V(v2), kun],
["Bekzod Azizni bloklaydi, 11:00", bekzod, "bloklash",
H(1, "foydalanuvchi"), kun],
["Bekzod Azizni bloklaydi, 01:00", bekzod, "bloklash",
H(1, "foydalanuvchi"), tun],
["Bekzod adminni bloklaydi", bekzod, "bloklash", H(4, "admin"),
kun],
["Aziz bloklaydi", aziz, "bloklash", H(2, "foydalanuvchi"), kun],
];
for (const [nom, f, amal, r, m] of HOLATLAR) {
console.log(nom.padEnd(34), mumkinmi(f, amal, r, m));
}Konsolda:
Aziz o'z vazifasini yangilaydi true
Aziz bajarilganni yangilaydi false
Dilnoza ulashilganni o'qiydi true
Dilnoza ulashilganni yangilaydi false
Dilnoza ulashilmaganni o'qiydi false
Bekzod Azizni bloklaydi, 11:00 true
Bekzod Azizni bloklaydi, 01:00 false
Bekzod adminni bloklaydi false
Aziz bloklaydi falseUchta narsaga e'tibor bering:
- Sukut — rad. Funksiya oxirida
return false. Qoidada ko'rsatilmagan har narsa taqiqlangan ("deny by default"). Teskarisi — "hamma narsa mumkin, faqat ... dan tashqari" — xavfli: yangi amal qo'shilsa, u avtomatik ochiq bo'ladi. - Taqiq birinchi. "Bajarilgan vazifa" sharti egalikdan oldin tekshiriladi. Aks holda egasi uchun
trueqaytib, taqiq ishlamay qolardi. - Vaqt server soatidan.
muhit.vaqt— serverningnew Date(). Uni mijozdan (sarlavha, so'rov tanasi) olsangiz, hujumchi o'z soatini "11:00" deb yuboradi.
Toshkent soati Intl.DateTimeFormat bilan olinadi (Intl.DateTimeFormat), serverning o'z vaqt mintaqasiga bog'liq emas. 06:00Z — Toshkentda 11:00, 20:00Z — ertasi kuni 01:00.
Tekshirib ko'ring:
if (amal === "yangilash" && v.bajarildi) return false;qatorini egalik tekshiruvidan keyinga ko'chirsak, qaysi holat natijasi o'zgaradi?
Javob
"Aziz bajarilganni yangilaydi" — true bo'lib qoladi: Aziz egasi, funksiya taqiqqa yetmasdan qaytadi. Siyosatda taqiqlar ("hech kim") ruxsatlardan oldin turishi kerak — yoki, CASL kabi kutubxonalardagidek, cannot qoidasi can dan ustun bo'lishi kerak.
3. ReBAC: munosabatlar
3.1 Zanzibar g'oyasi
"Dilnoza ulashilgan vazifani o'qiydi" — bu Dilnozaning xususiyati ham emas, vazifaning xususiyati ham emas. Bu ikkalasi orasidagi munosabat. Google Drive'ni eslang: papka jamoaga ulashilgan, jamoada siz borsiz, papka ichidagi hujjat — demak siz uni ko'rasiz. Bu zanjir.
ReBAC (Relationship-Based Access Control) ruxsatni munosabatlar grafi orqali beradi. Eng mashhur tizim — Google'ning Zanzibari (2019-yilda USENIX ATC konferensiyasida maqola bo'lib chiqqan). Google Drive, YouTube, Calendar kabi xizmatlar ruxsatlarini shu tizim saqlaydi. G'oyasi: hamma ruxsat ko'rinishdagi munosabat yozuvlari (relation tuple):
obyekt#munosabat@subyekt
vazifa:10#oquvchi@foydalanuvchi:dilnozaSubyekt boshqa guruh ham bo'la oladi (jamoa:bahor#azo — "bahor jamoasining hamma a'zosi"). Tekshiruv — grafda yo'l bormi degan savol.
3.2 O'zimizning kichik ReBAC
const MUNOSABATLAR = [
"jamoa:bahor#azo@foydalanuvchi:aziz",
"jamoa:bahor#azo@foydalanuvchi:dilnoza",
"loyiha:menyu#oquvchi@jamoa:bahor#azo",
"loyiha:menyu#muharrir@foydalanuvchi:aziz",
"vazifa:10#ota@loyiha:menyu",
];
function bormi(obyekt, munosabat, subyekt, chuqurlik = 0) {
if (chuqurlik > 5) return false;
for (const qator of MUNOSABATLAR) {
const [chap, kim] = qator.split("@");
const [obj, rel] = chap.split("#");
if (obj !== obyekt) continue;
if (rel === munosabat && kim === subyekt) return true;
if (rel === munosabat && kim.includes("#")) {
const [guruh, gRel] = kim.split("#");
if (bormi(guruh, gRel, subyekt, chuqurlik + 1)) return true;
}
if (rel === "ota") {
if (bormi(kim, munosabat, subyekt, chuqurlik + 1)) return true;
}
}
return false;
}
const oqiydimi = (v, kim) =>
bormi(v, "oquvchi", kim) || bormi(v, "muharrir", kim);
for (const kim of ["aziz", "dilnoza", "sardor"]) {
const s = `foydalanuvchi:${kim}`;
console.log(kim, oqiydimi("vazifa:10", s),
bormi("vazifa:10", "muharrir", s));
}Konsolda:
aziz true true
dilnoza true false
sardor false falseShu besh yozuv graf sifatida:
flowchart LR
V["vazifa:10"] -->|ota| L["loyiha:menyu"]
L -->|oquvchi| J["jamoa:bahor (azo)"]
L -->|muharrir| A["foydalanuvchi:aziz"]
J -->|azo| A
J -->|azo| D["foydalanuvchi:dilnoza"]Zanjirni kuzating. 10-vazifaning o'zida hech kim yozilmagan. Lekin uning otasi — loyiha:menyu. Loyihani bahor jamoasining a'zolari o'qiydi, Dilnoza — a'zo. Demak Dilnoza vazifani o'qiydi, lekin tahrirlay olmaydi. Aziz loyihaning muharriri — tahrirlaydi. Sardor jamoada yo'q — hech narsa.
Bitta qator qo'shsangiz (jamoa:bahor#azo@foydalanuvchi:sardor), Sardor menyu loyihasidagi hamma vazifani o'qiy boshlaydi. Kodda hech narsa o'zgarmaydi — faqat ma'lumot. ReBAC'ning kuchi shunda.
chuqurlik > 5 — himoya: munosabatlarda aylana bo'lsa (A guruh B ning a'zosi, B esa A ning), rekursiya cheksiz bo'lmaydi. Haqiqiy tizimlarda bu chegara ham, kesh ham, "yangi yozuv qachon ko'rinadi" degan izchillik savoli ham bor — Zanzibar maqolasining katta qismi aynan shular haqida.
3.3 Tayyor ReBAC xizmatlari
Bunday tizimni o'zingiz to'liq yozmaysiz. Zanzibar g'oyasidagi ochiq loyihalar:
- OpenFGA — Auth0/Okta boshlagan, CNCF loyihasi; sxema DSL'da yoziladi, alohida server sifatida ishlaydi;
- SpiceDB (AuthZed) — Zanzibar'ning yana bir ochiq talqini;
- Permit.io, Oso — boshqariladigan xizmat va kutubxonalar (RBAC, ABAC, ReBAC).
Bularning hech biri kursda sinalmagan — faqat hujjat bo'yicha, tanishuv uchun (2026-10-28). Ularning umumiy narxi — yana bitta xizmat: ruxsatlar endi asosiy bazangizda emas, alohida tizimda. Munosabatlarni ikki joyda sinxron tutish kerak bo'ladi.
4. Policy engine: qoidalar alohida qatlamda
4.1 PDP va PEP
Qoidalar ko'payganda ular har yo'lga sochilib ketadi. Yechim — ularni bitta joyga yig'ish. Atamalar XACML standartidan qolgan:
- PEP (policy enforcement point) — qarorni bajaradigan joy: middleware, yo'l, ombor;
- PDP (policy decision point) — qarorni chiqaradigan joy: siyosat funksiyasi yoki engine.
flowchart LR
S[So'rov] --> PEP[PEP: middleware yoki yo'l]
PEP -->|kim, amal, resurs, muhit| PDP[PDP: siyosat]
PDP -->|ruxsat yoki rad| PEP
PEP -->|ruxsat| H[Ishlovchi]
PEP -->|rad| X[403 yoki 404]
PDP -.-> Q[(Qoidalar: kod, JSON yoki DSL)]Oldingi darsdagi rolKerak — eng sodda PEP+PDP bitta funksiyada. Policy engine — PDP'ni alohida kutubxona yoki xizmatga chiqarish.
4.2 CASL: qoidalar ma'lumot sifatida
CASL — JavaScript uchun kutubxona: qoidalar can va cannot chaqiruvlari bilan yoziladi, shartlar esa MongoDB so'rovi uslubida. Kanon xuddi shu to'rt qoidani CASL 7 da yozdi (@casl/ability 7.0.2, kanon tajriba kodi, telefon uchun bo'lingan):
import { AbilityBuilder, createMongoAbility, subject }
from "@casl/ability";
function caslQobiliyat(f, muhit) {
const { can, cannot, build } =
new AbilityBuilder(createMongoAbility);
can(["oqish", "yangilash"], "Vazifa", { egasiId: f.id });
// Mongo sintaksisi: massivda bor
can("oqish", "Vazifa", { ulashilgan: f.id });
cannot("yangilash", "Vazifa", { bajarildi: true });
const s = toshkentSoati(muhit.vaqt);
if (f.rol === "admin" && s >= 9 && s < 18) {
can("bloklash", "Hisob", { rol: { $ne: "admin" } });
}
return build();
}
// tekshirish: obyektga tur nomi beriladi
caslQobiliyat(dilnoza, kun).can("oqish", subject("Vazifa", v1));Kanon 9 ta holatni ikkala usulda ishga tushirdi. Chiqishda "funksiya" va "CASL" ustunlarini qatorma-qator solishtiring:
holat funksiya CASL
Aziz o'z vazifasini yangilaydi true true
Aziz bajarilgan vazifani yangilaydi false false
Dilnoza ulashilganni o'qiydi true true
Dilnoza ulashilganni yangilaydi false false
Dilnoza ulashilmaganni o'qiydi false false
Bekzod (admin) Azizni bloklaydi, 11:00 true true
Bekzod (admin) Azizni bloklaydi, 01:00 false false
Bekzod boshqa adminni bloklaydi false false
Aziz (foydalanuvchi) bloklaydi false false
farqlar: 0Farq nol — ikkala usul ham to'g'ri. CASL'da taqiq tartibi o'zi hal bo'ladi: keyin yozilgan cannot oldingi can dan ustun.
4.3 Qoidalar JSON — frontend bilan ulashish
CASL'ning asosiy afzalligi — qoidalar ma'lumot. Dilnozaning qobiliyati JSON'ga aylanadi (kanon chiqishi):
CASL qoidalari JSON (frontend'ga yuborish mumkin): [{"action":["oqish","yangilash"],"subject":"Vazifa","conditions":{"egasiId":2}},{"action":"oqish","subject":"Vazifa","conditions":{"ulashilgan":2}},{"action":"yangilash","inverted":true,"subject":"Vazifa","conditions":{"bajarildi":true}}]Server bu ro'yxatni /men javobida yuborsa, frontend xuddi shu kutubxona bilan "Tahrirlash" tugmasini ko'rsatish yoki yashirishni hal qiladi (@casl/react dagi <Can> komponenti). Qoidalar ikki joyda takrorlanmaydi. Bu imkoniyat kanonda sinalmagan — CASL hujjati bo'yicha.
Lekin oldingi darsdagi qoida o'z kuchida: frontend'dagi tekshiruv — faqat UX. Server qarorini baribir serverdagi qobiliyat chiqaradi.
inverted: true — bu cannot. Uchinchi qoida JSON'da ham taqiq bo'lib qoldi.
4.4 Narxi: o'lchov
Kanon har usulni 10 000 marta, 21 marta takrorlab o'lchadi (mediana, bitta tekshiruv uchun):
- oddiy funksiya18,8 ns
- CASL, qobiliyat bir marta434,3 ns
- CASL, har so'rovda qurish~111 µs111 210,2 ns
Manba: kanon o'lchovi (IlmHamroh, 2026-10): @casl/ability 7.0.2, Node 24.21.0, i5-12500H, Windows 11, 2026-10-28
Raqamlarni o'qiymiz:
- Oddiy funksiya — 18.8 ns. Amalda bepul.
- CASL, qobiliyat oldindan qurilgan — 434 ns, funksiyadan ~23 marta sekin. Lekin bu ham bitta so'rov uchun sezilmaydi: ma'lumotlar bazasiga bitta so'rov millisekundlarda o'lchanadi.
- CASL, har so'rovda
createMongoAbilityqurish + tekshirish — ~111 µs. Bu bitta tekshiruvdan ~250 marta qimmat.
Ustunlar bir xil shkalada: uchinchisi qolgan ikkitasini ko'rinmas qilib qo'ydi. Xulosa: qobiliyatni har tekshiruvda qayta qurmang. Uni so'rov boshida bir marta quring va so'rov davomida ishlating. Yoki — qoidalar rolga bog'liq bo'lsa — rol bo'yicha oldindan qurib, keshlang.
4.5 Boshqa engine'lar
| Engine | Qoidalar qayerda | Izoh |
|---|---|---|
| CASL | JS kod / JSON | kutubxona, frontend bilan ulashadi |
| Casbin | model fayli + siyosat jadvali | ko'p tilli, ACL/RBAC/ABAC |
| OPA (Rego) | alohida til, alohida xizmat | infratuzilmada ko'p (Kubernetes) |
| Cedar | alohida til | AWS ochiq manbali qilgan |
Casbin, OPA va Cedar kursda sinalmagan (hujjat bo'yicha). Ularning umumiy g'oyasi bir: siyosat — koddan alohida, versiyalanadi va o'z testlari bor.
4.6 Ma'lumotlar bazasi bilan bog'lash
Siyosat bitta obyekt uchun "mumkinmi?" deb javob beradi. Lekin ro'yxat-chi? "Dilnoza o'qiy oladigan hamma vazifalar" — 10 000 ta vazifani bazadan olib, har birini filtrlash mumkin emas. Qoida SQL WHERE ga aylanishi kerak.
vazifalar-api da bu muammo yo'q: egalik — oddiy WHERE egasi_id va RLS. CASL uchun @casl/prisma paketi qoidalardan Prisma where shartini yasaydi; ReBAC xizmatlari esa "bu foydalanuvchi uchun obyektlar ro'yxati" so'rovini beradi. Ikkalasi ham kursda sinalmagan. Shuni bilib qo'ying: policy engine tanlaganda "ro'yxatni qanday filtrlaydi?" degan savol birinchi o'rinda.
4.7 Siyosatni test qilish
Siyosat — xavfsizlikning yuragi, shuning uchun u kodning eng yaxshi sinalgan qismi bo'lishi kerak. Kanon tajribasi buning yaxshi shaklini ko'rsatdi: jadvalga asoslangan test (table-driven test). Har qator — "kim, nima, qaysi resurs, qachon, kutilgan javob". Yangi qoida qo'shsangiz, jadvalga yangi qator qo'shasiz.
Uch qoida bunday testni kuchli qiladi:
- har qoida uchun kamida bitta "ha" va bitta "yo'q" holati bo'lsin (masalan, 11:00 va 01:00);
- chegaralar alohida: 08:59, 09:00, 17:59, 18:00 — "≥ 9" va "< 18" xatolari aynan shu yerda;
- engine almashtirilsa (funksiyadan CASL'ga yoki aksincha), o'sha jadval ikkala usulda yurgizilib, farq nol bo'lishi kerak — kanon aynan shunday qildi.
Bunday test siyosatni o'zgartirishdan qo'rqmaslikka yordam beradi: biror qator qizarsa, qaysi qoida buzilgani darhol ko'rinadi.
5. Hujumchi nigohi
Har qatorda: hujum, himoya va siyosat jadvalidagi test qatori.
| Hujum | Himoya | Test (jadval qatori) |
|---|---|---|
| soatni mijozdan yuborish | vaqt — serverdan | 11:00 → ha, 01:00 → yo'q |
| qoidada yo'q amalni chaqirish | sukut — rad | "Aziz bloklaydi" → yo'q |
| taqiqni egalik bilan aylanib o'tish | taqiq oldin / cannot ustun |
"Aziz bajarilganni yangilaydi" → yo'q |
| frontend qoidalarini o'zgartirish | qaror serverda, JSON — faqat UX | server testi, frontend emas |
| rol olinganidan keyin eski qobiliyat | so'rov boshida qurish, kesh kaliti — rol | adminlikdan olingach — 403 |
| ro'yxatda begona obyekt | qoida WHERE ga aylanadi |
ro'yxatda begona yo'q |
6. Ko'p uchraydigan xatolar
| Xato | Nega xavfli | To'g'risi |
|---|---|---|
| har shart uchun yangi rol | rollar portlashi | atribut yoki munosabat |
| qoidalar har yo'lda sochilgan | biri unutiladi | bitta siyosat moduli (PDP) |
| "sukut — ruxsat" | yangi amal ochiq | "sukut — rad" |
| CASL qobiliyatini har tekshiruvda qurish | ~111 µs | so'rovda bir marta |
| ReBAC'da chuqurlik chegarasisiz | aylana — cheksiz rekursiya | chegara, kesh |
| kichik loyihaga policy engine | ortiqcha murakkablik | oddiy funksiya, testlar bilan |
7. Mashqlar
Mashqlar kurs/mashqlar/28/21-abac/ da.
1-mashq (oson): qaysi model?
Har qoidani RBAC, ABAC yoki ReBAC ga ajrating:
- "Faqat adminlar foydalanuvchilar ro'yxatini ko'radi."
- "Hujjatni faqat uning bo'limidagi xodimlar o'qiydi."
- "Papkaga ulashilgan har kim uning ichidagi fayllarni ko'radi."
- "To'lovni faqat Toshkent IP manzillaridan tasdiqlash mumkin."
- "Menejer o'z jamoasi a'zolarining ta'tilini tasdiqlaydi."
Yechim
- RBAC — faqat rol.
- ABAC — subyekt atributi (bo'lim) va resurs atributi (bo'lim) teng.
- ReBAC — munosabat zanjiri: fayl → papka → ulashilgan.
- ABAC — muhit atributi (IP).
- ReBAC — "menejeri" munosabati (atribut bilan ham yozsa bo'ladi:
xodim.menejerId === f.id; chegara aniq emas, bu normal).
2-mashq (o'rta): bo'lim va maxfiylik
«Bahor» hujjatlari uchun siyosat yozing. Hujjatda bolim va maxfiy (true/false), xodimda bolim va daraja (1–3). Qoidalar: xodim faqat o'z bo'limi hujjatini o'qiydi; maxfiy hujjatni faqat daraja >= 3 o'qiydi; rol: "auditor" hamma bo'limni o'qiydi, lekin maxfiy hujjatga daraja qoidasi unga ham amal qiladi. Sukut — rad. To'rt holatni sinang.
Yechim
function oqiyOladimi(xodim, hujjat) {
if (hujjat.maxfiy && xodim.daraja < 3) return false;
if (xodim.rol === "auditor") return true;
return xodim.bolim === hujjat.bolim;
}
const oshxona = { bolim: "oshxona", daraja: 1, rol: "xodim" };
const auditor = { bolim: "moliya", daraja: 2, rol: "auditor" };
const menyu = { bolim: "oshxona", maxfiy: false };
const retsept = { bolim: "oshxona", maxfiy: true };
console.log(oqiyOladimi(oshxona, menyu));
console.log(oqiyOladimi(oshxona, retsept));
console.log(oqiyOladimi(auditor, menyu));
console.log(oqiyOladimi(auditor, retsept));Konsolda:
true
false
true
falseTaqiq (maxfiylik) birinchi turibdi — shuning uchun auditor ham maxfiy retseptni ko'rmaydi. Agar auditor tekshiruvini birinchi qo'ysangiz, to'rtinchi qator true bo'lardi — aynan darsdagi "taqiq birinchi" tuzog'i.
3-mashq (qiyin): kesh bilan qobiliyat
CASL o'lchovidagi saboqni oddiy JS'da takrorlang. qobiliyatQur(rol) funksiyasi qimmat bo'lsin: ichida 200 000 qadamli bo'sh sikl va natija — ruxsatlar Set i. keshli(rol) esa Map da saqlab, har rol uchun faqat bir marta qursin. 1000 ta tekshiruvda nechta qurish bo'lganini sanang: keshsiz va keshli. Rollar: ["admin", "foydalanuvchi"] navbatma-navbat.
Yechim
let qurishlar = 0;
function qobiliyatQur(rol) {
qurishlar++;
let x = 0;
for (let i = 0; i < 200_000; i++) x += i;
return rol === "admin"
? new Set(["oqish", "yozish", "bloklash"])
: new Set(["oqish", "yozish"]);
}
const kesh = new Map();
function keshli(rol) {
if (!kesh.has(rol)) kesh.set(rol, qobiliyatQur(rol));
return kesh.get(rol);
}
const ROLLAR = ["admin", "foydalanuvchi"];
let ruxsat = 0;
for (let i = 0; i < 1000; i++) {
if (qobiliyatQur(ROLLAR[i % 2]).has("bloklash")) ruxsat++;
}
console.log("keshsiz:", qurishlar, ruxsat);
qurishlar = 0;
ruxsat = 0;
for (let i = 0; i < 1000; i++) {
if (keshli(ROLLAR[i % 2]).has("bloklash")) ruxsat++;
}
console.log("keshli:", qurishlar, ruxsat);Konsolda:
keshsiz: 1000 500
keshli: 2 500Natija bir xil (500 ta ruxsat), qurish esa 1000 dan 2 ga tushdi. Vaqtni chiqarmadik — u har mashinada boshqa. Lekin bitta tuzoq bor: rol o'zgarsa, kesh eskiradi. Oldingi darsda rol har so'rovda bazadan olinardi va adminlikdan olingan odam darhol 403 olardi. Kesh kaliti rol bo'lsa, bu xavfsiz: yangi rol — boshqa kalit. Kesh kaliti foydalanuvchi id bo'lsa, eskirgan qobiliyat qolishi mumkin.
8. Loyiha qadami: nega kanonga kirmadi
ABAC va CASL tajribasi vazifalar-api ga qo'shilmadi. Sabablar:
vazifalar-api— bir kishilik ro'yxat. Ulashish yo'q, demak ReBAC qoidasiga ehtiyoj ham yo'q. Ulashish va jamoalar — kursning keyingi qismlaridagi jamoaviy loyihada.- Muhit sharti (ish vaqti) yo'q: admin istalgan payt bloklay oladi. Bu ataylab — xavfsizlik hodisasi tunda ham bo'ladi.
- Mavjud ikki qoida — rol (
rolKerak) va egalik (SQLWHERE+ RLS) — bitta funksiya va bitta siyosatdan iborat. Engine qo'shish — yana bitta bog'liqlik va qoidalarni ikki joyda (CASL va RLS) saqlash.
Halol xulosa: kichik loyihada oddiy funksiya + testlar policy engine'dan yaxshiroq. Engine qoidalar ko'p, o'zgaruvchan va frontend bilan ulashilishi kerak bo'lganda o'zini oqlaydi.
9. Real ishda
- GitHub tashkilot, jamoa, repozitoriy va filial himoyasi bo'yicha ruxsatlarni aralashtiradi — bu RBAC + ReBAC.
- Google Drive, Notion, Figma — "ulashish" bor joyda ReBAC bor.
- Bank va davlat tizimlari ABAC'ni ko'p ishlatadi: lavozim, bo'lim, ish vaqti, IP, maxfiylik darajasi.
- Kubernetes va bulut infratuzilmasida siyosatlar ko'pincha OPA (Rego) bilan yoziladi.
- Intervyuda: "RBAC, ABAC, ReBAC farqi?", "Rollar portlashi nima?", "Policy engine qachon kerak?", "Ruxsatlarni frontend bilan qanday ulashasiz?".
Xulosa
- RBAC — rol; ABAC — atributlar (subyekt, resurs, amal, muhit); ReBAC — munosabatlar grafi.
- Vaziyatga bog'liq qoidalarni rol bilan yozish — rollar portlashi.
- Siyosat: sukut — rad; taqiq birinchi; muhit atributlari (vaqt, IP) — faqat serverdan.
- ReBAC (Zanzibar g'oyasi):
obyekt#munosabat@subyektyozuvlari; ruxsat — grafda yo'l. - CASL qoidalari JSON — frontend bilan ulashiladi; qobiliyatni har tekshiruvda qurish ~111 µs, bir marta qurib ishlating.
- Kichik loyihada oddiy funksiya va testlar yetarli; engine — qoidalar ko'p va o'zgaruvchan bo'lganda.
Keyingi dars: API kalitlar va servislararo autentifikatsiya — foydalanuvchi emas, dastur so'rov yuborganda uni qanday tanish va unga qanday cheklangan ruxsat berish.
Manbalar
- NIST SP 800-162 "Guide to Attribute Based Access Control (ABAC) Definition and Considerations": https://doi.org/10.6028/NIST.SP.800-162
- Zanzibar: Google's Consistent, Global Authorization System (USENIX ATC 2019): https://research.google/pubs/zanzibar-googles-consistent-global-authorization-system/
- CASL hujjati: https://casl.js.org/ (
AbilityBuilder,createMongoAbility,@casl/react,@casl/prisma) - OpenFGA: https://openfga.dev/docs ; Casbin: https://casbin.org/docs/overview ; Open Policy Agent: https://www.openpolicyagent.org/docs ; Cedar: https://www.cedarpolicy.com/
- OWASP Authorization Cheat Sheet ("deny by default"): https://cheatsheetseries.owasp.org/cheatsheets/Authorization_Cheat_Sheet.html
- Kanon o'lchovi (IlmHamroh, 2026-10-28): funksiya va CASL solishtiruvi (@casl/ability 7.0.2, Node 24.21.0, i5-12500H). Darsdagi brauzer misollari — biz ishga tushirdik (2026-10-28).
Izohlar (0)
Izoh yozish uchun kiring.
- Hozircha izoh yo'q. Birinchi bo'ling!