VPN ulanishidan keyingi amalni daemon sifatida emas, foydalanuvchi sifatida ishga tushiring
USER=alice deb ko'rsatadigan muhit o'zgaruvchisi hook qaysi hisobda ishlashini o'zgartirmaydi. Hodisa, trigger va amalni ajratib, so'ngra UIDni isbotlang.
VPN daemonidagi ulanish hooklari daemon sifatida ishlaydi, bu esa odatda ular root sifatida ishlashini anglatadi. O'sha hooklardan biri kimningdir uy katalogiga yozganda yoki ish stoli yordamchisini qayta ishga tushirganda, siz tarmoq hodisasiga har qanday mahalliy foydalanuvchi sifatida harakat qilish qobiliyatini bergansiz. Odatiy qisqa yo'l, ya'ni muhit o'zgaruvchisidan foydalanuvchi nomini o'qib, uni uzatish, buni tuzatmaydi. U faqat amalni qayta belgilaydi, ammo uni qaysi hisob bajarishini o'zgartirmaydi. Ishlaydigan narsa uch qismli topshirish: imtiyozli qadam nima bo'lganini aytadi, alohida birlik esa amalni to'g'ri shaxsiyat ostida bajaradi.
Muhitdagi foydalanuvchi nomi shaxsiyat kaliti emas
Unix jarayon nimaga tegishi mumkinligini uning samarali foydalanuvchi IDsi bo'yicha hal qiladi, muhitidagi satrlar bo'yicha emas. USER=alice ni o'rnatish yoki LOGNAME ni eksport qilish beparvo dastur o'z chiqishida nima chop etishini o'zgartiradi; fayl egaligini tekshirishlarda hech narsani o'zgartirmaydi. Shu o'zgaruvchi bilan root sifatida ishlaydigan hook baribir Alice fayllarini root sifatida ochadi.
Nomlar ham bir xil nom emas. Masofaviy kirish logini, mahalliy Unix hisobi va sertifikatning umumiy nomi ko'pincha mos keladigan, ba'zan esa kelmaydigan uchta identifikator. a.smith sifatida autentifikatsiyadan o'tadigan foydalanuvchining mahalliy hisobi umuman bo'lmasligi yoki katalog xizmati orqali asmith ga xaritalanishi mumkin. Bitta satr uch rolning barchasini bajaradi deb hisoblaydigan har qanday dizayn birinchi pudratchida buziladi.
Shuning uchun birinchi savol «qaysi foydalanuvchi ulangan» emas, balki «qaysi mahalliy hisobga bu amalni bajarishga ruxsat bor». Bunga o'z hisoblar bazangizdan javob bering, klient yuborgan narsadan emas:
id -u alice
getent passwd alice | cut -d: -f1,3,6
stat -c '%U:%G %a %n' /home/alice/.local/state/vpn-status.json
Uchinchi buyruq odamlar tashlab ketadigan buyruqdir. Agar maqsadli fayl rootga tegishli bo'lsa, chunki uni oldingi hook yaratgan, to'g'ri sozlangan foydalanuvchi amali systemd muammosiga o'xshaydigan, ammo unday bo'lmagan ruxsat xatosi bilan muvaffaqiyatsiz bo'ladi.
Daemon o'z joyida qoladi
VPN xizmatining o'z User= qiymatini Alicega almashtirish noto'g'ri dastakdir. Bu daemon interfeyslarni qanday bog'lashini, kalitlarni qanday o'qishini, holat faylini qanday yozishini va marshrutlarni qanday boshqarishini o'zgartiradi va bu butun xavfni ishlab turgan birlikka ko'chiradi. Daemonga o'z imtiyozlari kerak; keyingi amalga kerak emas.
Birlikka tegishdan oldin uning aslida nima qilayotganini ko'ring. Ikki buyruq sizga bajarish shaxsiyatini va amaldagi aniq buyruq satrlarini aytadi, qayta belgilash qo'shgan hamma narsani ham qo'shib:
systemctl show -p User -p Group -p ExecStart openvpn-server@server
systemctl cat openvpn-server@server
Odatiy paket o'rnatishida daemon root, --up skripti esa buni meros oladi. Taxmin qilish o'rniga buni tasdiqlang, chunki qattiqlashtirilgan distributiv uni alohida hisobga ko'chirgan bo'lishi mumkin, qo'lda yozilgan drop-in esa hookni boshqa qoidalarga ega o'ram orqali ishga tushirishi mumkin.
Uchta nomlangan qism, bitta tor trigger
Texnik xizmatdan omon qoladigan tartibda hodisa, trigger va amal bor. Daemon nomlangan sessiya ko'tarilganini xabar qiladi. Trigger bu kichik faktni qabul qiladi va bitta qat'iy amalni so'raydi. Amal o'zi tegadigan fayllarga ega mahalliy hisob ostida ishlaydi. Zanjirda hech narsa o'zboshimchalik bilan buyruq yo'lini qabul qilmaydi.
Amalning o'zi oddiy xizmat birligi, shaxsiyat esa uning ichidagi bitta direktiva:
[Service]
Type=oneshot
User=alice
Group=alice
ExecStart=/usr/local/bin/refresh-vpn-status --slot %i
User=alice butun birlikka tegishli ekanini e'tiborga oling, va systemd bilishga arziydigan bitta istisnoni hujjatlashtiradi: + prefiksli buyruq bundan qat'i nazar to'liq imtiyozlar bilan ishlaydi. Bu prefiks bitta imtiyozli qadam uchun qonuniy vosita va hozir qurgan ajratishni bekor qilishning qulay yo'li, shuning uchun o'sha birlikdagi har qanday + ni ko'rikda asoslanishi kerak bo'lgan narsa deb biling.
Trigger kirishini minimal va maxfiy bo'lmagan holda saqlang. Sessiya identifikatori, xaritalangan hisob va vaqt tamg'asi odatda kerak bo'lgan hamma narsa. Hech qachon chegara orqali shell bo'lagini, bajariladigan fayl yo'lini yoki klient taqdim etgan muhit blokini uzatmang, chunki qabul qiluvchi tomon qonuniy qiymatni kiritilgan qiymatdan ajratish usuliga ega emas.
Haqiqatan ishlagan shaxsiyatni tekshiring
Konfiguratsiya ko'rigi dalil emas. Tasdiqlangan sinov ulanishidan keyin faylga tekkan UIDni va daemon hali ishlatayotgan UIDni tasdiqlang:
stat -c '%U %G %y %n' /home/alice/.local/state/vpn-status.json
ps -o user=,pid=,cmd= -p "$(pgrep -o -f 'openvpn --daemon')"
systemd-run --uid=alice --pipe /usr/local/bin/refresh-vpn-status --dry-run
Birinchi satr Aliceni va sinov oynangiz ichidagi vaqt tamg'asini ko'rsatishi kerak. Ikkinchisi hali ham root yoki paketning xizmat hisobini ko'rsatishi kerak, bu daemon joyidan jilmaganini isbotlaydi. Uchinchisi haqiqiy qayta ulanishni kutmasdan amalning ruxsatlarini sinashning eng arzon usuli.
Agar faylning egasi Alice bo'lsa, lekin uning guruhi yoki rejimi ishga tushirishlar orasida o'zgargan bo'lsa, mantiqiy xato o'rniga UMask= yoki katalog ruxsati farqini qidiring. Agar vaqt tamg'asi umuman qimirlamagan bo'lsa, trigger hech qachon ishga tushmagan, va foydali keyingi qadam yana bir klient qayta ulanishi emas, balki amal birligi uchun journalctl -u.
Ulanish hodisasi hali nimani isbotlamaydi
O'rnatilgan tunnel bitta fakt. Bu ish stoli sessiyasi ochilganini, sessiya shinasi yetib borishini yoki amal istagan xususiy resurs allaqachon mavjudligini anglatmaydi. Alice UIDsi ostidagi oneshot birligi uning shaxsiyatiga ega va sessiyasidan hech narsaga ega emas, shuning uchun grafik shina talab qiladigan hamma narsa qo'llab-quvvatlanadigan foydalanuvchi sessiyasi mexanizmidan o'tishi va u tizimdan chiqqanda nima bo'lishini belgilashi kerak.
Qayta ulanishlar ham takrorlanadi. Poyezdda uxlab qolgan noutbuk bir soatda o'nlab ulanish hodisalarini keltirib chiqarishi mumkin, va har safar satr qo'shadigan hook holat faylini hech kim o'qiy olmaydigan jurnalga aylantiradi. Amalni idempotent qiling yoki sessiya bo'yicha kalitlangan bitta yozuvni almashtirishga ruxsat bering.
Nihoyat, zarar radiusini birlikning o'zida cheklang: holat katalogidan tashqarida faqat o'qish uchun fayl tizimi ko'rinishi, yangi imtiyozlar yo'q va aniq vaqt chegarasi. Daemon va foydalanuvchi amali o'rtasidagi ajratish o'z-o'zidan qimmatli, ammo amal siz tasdiqlagan yagona narsadan boshqa hech narsa qila olmasa, u ancha qimmatliroq.