---
title: 'Güvenlik Gereksinimleri'
source: 'https://academia.sh/tr/kurslar/guvenli-yasam-dongusu/guvenlik-gereksinimleri'
course: 'Güvenli Geliştirme Yaşam Döngüsü'
language: tr
updated: '2026-08-17T18:06:43+00:00'
license: 'CC BY-SA 4.0'
---

# Güvenlik Gereksinimleri

Sınanabilirlik üç parçadan türetilir ve 20 güvenlik gereksinimi üzerinde koşturulur: 13'ü otomatik sınanabilir, 3'ü tek bir eksik parça yüzünden gözle denetlenir, 4'ü nitel yüklemi yüzünden yeniden yazılmadan hiçbir sınıfa geçemez. Beş kötüye kullanım senaryosu listeyi yüzde 40 büyütür ve gelen 8 gereksinimin 7'si engelleyici kiptedir; gözle sınamanın 40 saatlik yükü eksik parçalar yazıldığında tamamen düşer.

Önceki ders önlenen 250 saatin dörtte birinin gereksinim aşamasında doğan kalemlerden geldiğini
saydı, ama o kalemleri yakalayan denetimi tek satırda bıraktı: on sekiz gereksinim incelemesi, beş
uyarı, üç gerçek kalem. Bir incelemenin bir kalemi nasıl yakaladığı açılmadı. Yakalayabilmesinin
tek koşulu vardır: gereksinimin, karşılanıp karşılanmadığı **sınanabilir** biçimde yazılmış olması.
"Sistem güvenli olmalıdır" satırı hiçbir incelemede hiçbir kalem üretmez, çünkü ihlal edildiğini
gösterecek bir gözlem yoktur.

Bu ders sınanabilirliği bir sıfat olmaktan çıkarıp üç parçaya ayırır ve yirmi gereksinimlik bir
liste üzerinde koşturur. İkinci yarıda listenin nereden geldiği sorulur: özellik listesini okuyarak
yazılan gereksinimlerle, sistemin **engellemesi** gereken bir hedefi izleyen bir aktör düşünülerek
yazılan gereksinimler aynı kümeyi vermez.

- **DY12.** Gereksinim listesi kurgusaldır ve `node` ile modellenir. Her gereksinim dört alanla
  yazılır: özne, yüklem türü, eşik, kapsam.
- **DY13.** Sınanabilirlik verilmez, **türetilir**: yüklem gözlenebilirse ve hem eşik hem kapsam
  yazılmışsa gereksinim otomatik sınanabilir. Parçalardan biri eksikse gözle denetlenir; yüklem
  nitelse hiç sınanamaz.
- **DY14.** Yüklem türü ve kip alanları gereksinimin **yazılış biçiminin** kaydıdır, içeriğinin
  değeri değil. Sınanamaz yazılmış bir gereksinim önemsiz değildir; yalnız denetlenemez.
- **DY15.** Kötüye kullanım senaryosu bir aktör ve bir hedefle modellenir; hiçbir adım
  çalıştırılabilir biçimde verilmez. Senaryonun bir kurumun kendi sistemi dışında denenmesi
  **yazılı yetki ve tanımlı kapsam** gerektirir, aksi hem yasadışı hem de meslek dışıdır.
- **DY16.** Koşum sayıları ve gözle denetim dakikası model değerleridir; önceki derslerin değişiklik
  ve dağıtım sayılarıyla uyumludur.

## Sınanabilirliğin Üç Parçası

Bir gereksinimin otomatik sınanabilmesi için üç şey gerekir: ihlalin görüleceği **gözlenebilir bir
yüklem**, karşılandığını söyleyecek bir **eşik** ve nerede geçerli olduğunu söyleyen bir **kapsam**.
Üçünden biri eksikse sınama bir insana devredilir.

```js
// gereksinim.mjs — olcum agi yaziliminin guvenlik gereksinimleri (model)
// satir: ad | ozne | yuklem turu | esik | kapsam | kip
// yuklem: olay = gozlenebilir olay, durum = denetlenebilir durum, nitelik = nitel sifat
// kip: saglar = sistemin yaptigi is, engeller = sistemin reddettigi is
const oku = (s) => s.trim().split('\n').map((r) => {
  const [ad, ozne, yuklem, esik, kapsam, kip] = r.trim().split(/\s+/);
  return { ad, ozne, yuklem, esik, kapsam, kip };
});
export const GEREKSINIM = oku(`
  oturum-suresi-siniri     oturum            durum    30-dk           abone-portali    engeller
  hatali-giris-siniri      giris-ucu         olay     5-deneme        abone-portali    engeller
  aktarim-sifrelemesi      dis-baglanti      durum    zorunlu         tum-uclar        saglar
  olcum-verisi-saklama     olcum-kaydi       durum    24-ay           olcum-deposu     saglar
  yetki-denetimi-kapsami   okuma-ucu         olay     her-istek       faturalama       saglar
  gizli-deger-kaynakta     kaynak-dosya      durum    0-adet          tum-depolar      engeller
  kisisel-veri-gunlukte    gunluk-satiri     durum    0-alan          tum-servisler    engeller
  bagimlilik-yasi          bagimlilik        durum    180-gun         tum-yapilar      saglar
  yonetim-ucu-erisimi      yonetim-ucu       olay     ic-ag           sayac-toplama    engeller
  yedek-sifrelemesi        yedek-dosyasi     durum    zorunlu         fatura-vt        saglar
  istek-hiz-siniri         genel-uc          olay     60-istek-dk     abone-portali    engeller
  oturum-sonlandirma       cikis-eylemi      olay     1-istek         abone-portali    saglar
  dosya-yukleme-boyu       yukleme-ucu       durum    10-mb           saha-uygulamasi  engeller
  hata-mesaji-icerigi      hata-yaniti       durum    -               tum-uclar        engeller
  denetim-kaydi-tutma      yetki-degisikligi olay     her-degisiklik  -                saglar
  parola-saklama-bicimi    abone-kaydi       durum    -               abone-portali    saglar
  kimlik-dogrulama-gucu    abone-girisi      nitelik  -               abone-portali    saglar
  arayuz-guvenligi         saha-uygulamasi   nitelik  -               -                saglar
  veri-butunlugu           olcum-kaydi       nitelik  -               -                saglar
  gorev-ayrimi             fatura-onayi      nitelik  -               faturalama       engeller`);

// Sinanabilirlik turetilir: gozlenebilir yuklem + esik + kapsam varsa otomatik sinanir.
export function sinif(g) {
  if (g.yuklem === 'nitelik') return 'sinanamaz';
  const eksik = ['esik', 'kapsam'].filter((a) => g[a] === '-');
  return eksik.length === 0 ? 'otomatik' : 'gozle';
}
export const eksikParca = (g) => ['esik', 'kapsam'].filter((a) => g[a] === '-');

// Kotuye kullanim senaryosu: bir aktor, sistemin engellemesi gereken bir hedefi izler.
// Model olarak yazilir; hicbir adim calistirilabilir bicimde verilmez.
export const SENARYO = [
  ['abone-hesabini-ele-gecirme', 'dis-aktor',
    ['hatali-giris-siniri', 'oturum-suresi-siniri', 'oturum-sonlandirma', 'giris-bildirimi']],
  ['baskasinin-faturasini-okuma', 'yetkili-abone',
    ['yetki-denetimi-kapsami', 'kayit-kimligi-tahmini']],
  ['olcum-kaydini-degistirme', 'saha-personeli',
    ['denetim-kaydi-tutma', 'olcum-yazma-yetkisi', 'olcum-degisikligi-onayi']],
  ['toplu-abone-verisi-cekme', 'yetkili-abone',
    ['istek-hiz-siniri', 'toplu-indirme-siniri', 'disari-akan-hacim-esigi']],
  ['cihazi-baskasi-adina-kaydetme', 'dis-aktor',
    ['cihaz-kayit-dogrulamasi', 'kayit-hiz-siniri']],
];
// Senaryolardan cikan ve listede olmayan gereksinimler, ayni bicimde yazildiginda:
export const YENI = oku(`
  giris-bildirimi          basarili-giris    olay     her-giris       abone-portali    saglar
  kayit-kimligi-tahmini    fatura-kaydi      durum    tahmin-edilemez  faturalama      engeller
  olcum-yazma-yetkisi      olcum-kaydi       olay     rol-esli        olcum-deposu     engeller
  olcum-degisikligi-onayi  olcum-duzeltmesi  olay     iki-imza        olcum-deposu     engeller
  toplu-indirme-siniri     dis-aktarim       durum    -               abone-portali    engeller
  disari-akan-hacim-esigi  dis-aktarim       durum    50-mb-gun       tum-uclar        engeller
  cihaz-kayit-dogrulamasi  cihaz-kaydi       olay     saha-onayi      saha-uygulamasi  engeller
  kayit-hiz-siniri         cihaz-kaydi       olay     10-kayit-saat   -                engeller`);
```

```js
// kosum1.mjs — gereksinimler sinanabilirlige gore ayrilir; eksik parca sayilir
import { GEREKSINIM, sinif, eksikParca } from './gereksinim.mjs';

const say = (l, s) => l.filter((g) => sinif(g) === s).length;
console.log(`${GEREKSINIM.length} gereksinim; otomatik ${say(GEREKSINIM, 'otomatik')}, ` +
  `gozle ${say(GEREKSINIM, 'gozle')}, sinanamaz ${say(GEREKSINIM, 'sinanamaz')}`);

console.log('\nsinif       gereksinim  esigi olan  kapsami olan  gozlenebilir yuklem');
for (const s of ['otomatik', 'gozle', 'sinanamaz']) {
  const l = GEREKSINIM.filter((g) => sinif(g) === s);
  console.log(s.padEnd(12) + String(l.length).padEnd(12) +
    String(l.filter((g) => g.esik !== '-').length).padEnd(13) +
    String(l.filter((g) => g.kapsam !== '-').length).padEnd(14) +
    l.filter((g) => g.yuklem !== 'nitelik').length);
}

console.log('\notomatige gecmeyen gereksinimler ve eksik parcalari');
for (const g of GEREKSINIM.filter((x) => sinif(x) !== 'otomatik'))
  console.log('  ' + g.ad.padEnd(25) + sinif(g).padEnd(12) +
    (g.yuklem === 'nitelik' ? 'yuklem nitel: yeniden yazilmadan sinif degistiremez'
      : `eksik: ${eksikParca(g).join(', ')}`));

const tekEksik = GEREKSINIM.filter((g) => sinif(g) === 'gozle' && eksikParca(g).length === 1);
console.log(`\ntek parca eklenerek otomatige gecen ${tekEksik.length} gereksinim; ` +
  `yeniden yazim gerektiren ${say(GEREKSINIM, 'sinanamaz')} gereksinim`);
console.log(`onarimdan sonra otomatik ${say(GEREKSINIM, 'otomatik') + tekEksik.length}/` +
  `${GEREKSINIM.length}, kalan ${GEREKSINIM.length - say(GEREKSINIM, 'otomatik') - tekEksik.length}`);
```

```
20 gereksinim; otomatik 13, gozle 3, sinanamaz 4

sinif       gereksinim  esigi olan  kapsami olan  gozlenebilir yuklem
otomatik    13          13           13            13
gozle       3           1            2             3
sinanamaz   4           0            2             0

otomatige gecmeyen gereksinimler ve eksik parcalari
  hata-mesaji-icerigi      gozle       eksik: esik
  denetim-kaydi-tutma      gozle       eksik: kapsam
  parola-saklama-bicimi    gozle       eksik: esik
  kimlik-dogrulama-gucu    sinanamaz   yuklem nitel: yeniden yazilmadan sinif degistiremez
  arayuz-guvenligi         sinanamaz   yuklem nitel: yeniden yazilmadan sinif degistiremez
  veri-butunlugu           sinanamaz   yuklem nitel: yeniden yazilmadan sinif degistiremez
  gorev-ayrimi             sinanamaz   yuklem nitel: yeniden yazilmadan sinif degistiremez

tek parca eklenerek otomatige gecen 3 gereksinim; yeniden yazim gerektiren 4 gereksinim
onarimdan sonra otomatik 16/20, kalan 4
```

Yirmi gereksinimin on üçü otomatik sınanabilir, üçü gözle denetlenir, dördü hiç sınanamaz. Asıl
bilgi ikinci ve üçüncü satırların ayrımındadır. Gözle denetlenen üç gereksinimin **yüklemi
gözlenebilirdir**; eksik olan tek bir alandır. `hata-mesaji-icerigi` hata yanıtının ne
içermeyeceğini söyler ama eşik yazmaz; `denetim-kaydi-tutma` her yetki değişikliğinin kaydını
ister ama hangi servislerde geçerli olduğunu söylemez. İkisi de bir satır eklenerek otomatiğe
geçer.

Sınanamaz dördün durumu farklıdır. `veri-butunlugu` ya da `arayuz-guvenligi` eksik alanı olan
gereksinimler değildir; yüklemleri bir gözleme karşılık gelmez. Bunlara eşik yazmak da işe
yaramaz, çünkü neyin ölçüleceği belli değildir. Sınıf değiştirmeleri için gereken şey tamamlama
değil **yeniden yazımdır**: her biri, ihlalinin görüleceği bir olaya ya da duruma çevrilmelidir ve
bu çeviri genellikle tek bir gereksinimi birkaç gereksinime böler.

Ayrımın karar karşılığı nettir. Üç gereksinim için yapılacak iş bir alan doldurmaktır; dört
gereksinim için yapılacak iş bir tasarım tartışmasıdır. Onarımdan sonra liste 16 otomatik ve 4
sınanamaz gereksinime ayrılır — ve bu dört gereksinim, ne kadar denetim kurulursa kurulsun kod
aşamasında hiçbir uyarı üretmez.

Bir uyarı burada gereklidir: sınanabilirlik **doğruluk değildir**. Oturum süresi sınırının otuz
dakika yazılmış olması onu otomatik sınanabilir yapar, ama otuz dakikanın doğru sayı olduğunu
göstermez; yanlış bir eşik de kusursuz biçimde sınanır. Bu sınıflandırma gereksinimin denetime
uygun olup olmadığını ölçer, isabetli olup olmadığını değil. İkisinin karıştırılması yaygın bir
kusur üretir: eşik, sınanabilir olsun diye yazılır ve sayının nereden geldiği hiç tartışılmaz.

## Kötüye Kullanım Senaryosunun Kattığı

Yukarıdaki yirmi gereksinim özellik listesi okunarak yazılmıştır: sistemin **yapması** gereken
işlerden türetilmiştir. **Kötüye kullanım senaryosu** (misuse case) ters yönden başlar — bir aktör,
sistemin engellemesi gereken bir hedefi izler ve bu hedefin engellenmesi için hangi gereksinimlerin
gerektiği yazılır.

```js
// kosum2.mjs — kotuye kullanim senaryolari listeyi ne kadar buyutuyor, ne bicimde
import { GEREKSINIM, YENI, SENARYO, sinif } from './gereksinim.mjs';

const mevcut = new Set(GEREKSINIM.map((g) => g.ad));
console.log('senaryo                        aktor           gereksinim  listede  yeni');
let ref = 0, varOlan = 0;
for (const [ad, aktor, uretilen] of SENARYO) {
  const v = uretilen.filter((x) => mevcut.has(x)).length;
  ref += uretilen.length; varOlan += v;
  console.log(ad.padEnd(31) + aktor.padEnd(16) + String(uretilen.length).padEnd(12) +
    String(v).padEnd(9) + (uretilen.length - v));
}
console.log(`${SENARYO.length} senaryo, ${ref} gereksinim referansi, ${varOlan} listede, ` +
  `${ref - varOlan} yeni; liste %${(((ref - varOlan) / GEREKSINIM.length) * 100).toFixed(0)} buyuyor`);

const say = (l, s) => l.filter((g) => sinif(g) === s).length;
const kip = (l, k) => l.filter((g) => g.kip === k).length;
console.log('\nkume                 gereksinim  otomatik  gozle  sinanamaz  engeller  engeller %');
for (const [ad, l] of [['ozellik listesinden', GEREKSINIM], ['senaryolardan', YENI]])
  console.log(ad.padEnd(21) + String(l.length).padEnd(12) + String(say(l, 'otomatik')).padEnd(10) +
    String(say(l, 'gozle')).padEnd(7) + String(say(l, 'sinanamaz')).padEnd(11) +
    String(kip(l, 'engeller')).padEnd(10) + ((kip(l, 'engeller') / l.length) * 100).toFixed(0));

// Sinanabilirlik sinifi, gereksinimin hangi asamada sinandigini ve bedelini belirler.
const DAGITIM = 60, DEGISIKLIK = 420, GOZLE_DK = 8;
console.log('\nsinif       sinandigi asama  kosum sayisi  insan dakikasi');
const tum = [...GEREKSINIM, ...YENI];
for (const [s, asama, kosum, dk] of [['otomatik', 'kod', DEGISIKLIK, 0],
  ['gozle', 'dagitim', DAGITIM, GOZLE_DK], ['sinanamaz', 'calisma-zamani', 0, 0]])
  console.log(s.padEnd(12) + asama.padEnd(17) + String(say(tum, s) * kosum).padEnd(14) +
    say(tum, s) * kosum * dk);
const gozleDk = say(tum, 'gozle') * DAGITIM * GOZLE_DK;
console.log(`\n${tum.length} gereksinimin ${say(tum, 'otomatik')}'i kod asamasinda, ` +
  `${say(tum, 'gozle')}'i dagitim asamasinda sinaniyor, ${say(tum, 'sinanamaz')}'u hic sinanmiyor`);
console.log(`gozle sinamanin yillik yaklasigi ${gozleDk} dakika (${(gozleDk / 60).toFixed(1)} saat); ` +
  `eksik parcalar yazilirsa ${(gozleDk / 60).toFixed(1)} saatin tamami dusuyor`);
```

```
senaryo                        aktor           gereksinim  listede  yeni
abone-hesabini-ele-gecirme     dis-aktor       4           3        1
baskasinin-faturasini-okuma    yetkili-abone   2           1        1
olcum-kaydini-degistirme       saha-personeli  3           1        2
toplu-abone-verisi-cekme       yetkili-abone   3           1        2
cihazi-baskasi-adina-kaydetme  dis-aktor       2           0        2
5 senaryo, 14 gereksinim referansi, 6 listede, 8 yeni; liste %40 buyuyor

kume                 gereksinim  otomatik  gozle  sinanamaz  engeller  engeller %
ozellik listesinden  20          13        3      4          9         45
senaryolardan        8           6         2      0          7         88

sinif       sinandigi asama  kosum sayisi  insan dakikasi
otomatik    kod              7980          0
gozle       dagitim          300           2400
sinanamaz   calisma-zamani   0             0

28 gereksinimin 19'i kod asamasinda, 5'i dagitim asamasinda sinaniyor, 4'u hic sinanmiyor
gozle sinamanin yillik yaklasigi 2400 dakika (40.0 saat); eksik parcalar yazilirsa 40.0 saatin tamami dusuyor
```

Beş senaryo on dört gereksinime dokunuyor; altısı listede zaten var, **sekizi yeni**. Liste yüzde
kırk büyüyor ve büyümenin nerede yoğunlaştığı önemlidir: son senaryonun ürettiği iki gereksinimin
**ikisi de** yeni. Cihaz kaydı özellik listesinde bir işlevdir ve o işlevin gereksinimleri
yazılmıştır; kaydın **başkası adına** yapılabilmesi bir işlev değildir, bu yüzden hiçbir özellik
satırından türemez.

Burada bir terim ayrımı gerekir. Bir **senaryo**, sistemin desteklediği bir kullanımı adım adım
yazar ve o kullanımın doğru sonuç vermesini ister. Kötüye kullanım senaryosu aynı biçimi kullanır
ama sahibi sistemin karşı tarafındadır ve istediği sonuç sistemin **vermemesi** gereken sonuçtur.
İkinci tablo farkı sayıya çeviriyor: özellik listesinden gelen yirmi gereksinimin yüzde 45'i
engelleyici kiptedir, senaryolardan gelen sekiz gereksinimin yüzde 88'i. Bir gereksinim listesinde
engelleyici kipin payı düşükse eksik olan güvenlik dikkati değil, **kaynaktır**.

Senaryolardan gelen sekiz gereksinimin altısı doğrudan otomatik sınanabilir yazılmıştır. Bunun
nedeni yazanın daha dikkatli olması değil, sorunun biçimidir: engellenecek bir hedef zaten bir
gözlem, bir eşik ve bir kapsam ister. "Cihaz kaydı saha onayına bağlıdır" cümlesi hem ihlalin
görüleceği olayı hem eşiği taşır; "arayüz güvenli olmalıdır" taşımaz.

Tablonun ölçmediği bir şey var ve bu dersin sınırı orasıdır: **beş senaryonun nereden geldiği.**
Senaryolar birinin aklına geldiği için listededir. Altıncı bir senaryo yazılsaydı listeye kaç
gereksinim daha eklenirdi sorusunun bu tabloda yanıtı yoktur, çünkü senaryo kümesinin kendisi
sistematik bir yöntemle üretilmemiştir. Ölçülen şey senaryo **başına** kazançtır, kapsanan hedef
oranı değildir; ikisi karıştırıldığında beş senaryo yazmış bir ekip işini bitirmiş sayar.

## Sınanabilirliğin Aşama Karşılığı

Son tablo bu kursun ölçü eksenine bağlanıyor. Yirmi sekiz gereksinimin on dokuzu otomatik
sınanabilir olduğu için **kod aşamasında** sınanır ve yılda 7.980 koşum üretir; bu koşumların insan
maliyeti sıfırdır. Beş gereksinim yalnız gözle denetlenebildiği için sınanma noktası **dağıtım
aşamasına** kayar: yılda 300 denetim, 2.400 dakika, yani 40 saat.

İki sayı yan yana okunmalıdır. Otomatik sınanan gereksinim, doğduğu aşamadan sonraki ilk fırsatta
ve her değişiklikte sınanır; ihlali kod aşamasında yakalanır. Gözle sınanan gereksinim ancak bir
dağıtım hazırlanırken bakılır ve ihlali önceki dersin tablosunda üç aşama geç yakalanan kalem
olarak görünür. Sınanabilirlik bir yazım niteliği gibi durur ama sonucu doğrudan **yakalama
aşamasıdır**.

Dört sınanamaz gereksinim üçüncü satırdadır ve hiçbir koşum üretmez. Bunlar sistemde yok sayılmaz;
yalnız ihlalleri bir denetim tarafından değil, bir olay tarafından bildirilir. Önceki dersin
diliyle: bu dört gereksinim, hiçbir denetimin görmediği kalem sınıfının gereksinim aşamasındaki
kaynağıdır. Bir gereksinim listesinin güvenlik değeri, kaç satır içerdiğiyle değil, kaç satırının
bir koşum sayısına karşılık geldiğiyle ölçülür; bu listede oran yirmi sekizde on dokuzdur.

## Özet

- Otomatik sınanabilirlik üç parçadan türer: gözlenebilir yüklem, eşik, kapsam. Üçünden biri
  eksikse gereksinim gözle denetlenir, yüklem nitelse hiç sınanamaz.
- 20 gereksinimin 13'ü otomatik, 3'ü gözle, 4'ü sınanamazdır. Gözle denetlenen 3'ü tek bir alan
  eklenerek otomatiğe geçer; sınanamaz 4'ü yeniden yazılmadan sınıf değiştiremez.
- 5 kötüye kullanım senaryosu 14 gereksinime dokunur, 6'sı listede vardır, 8'i yenidir; liste yüzde
  40 büyür ve tamamen yeni olan senaryo, özellik listesinde bir işlev karşılığı olmayan senaryodur.
- Özellik listesinden gelen gereksinimlerin yüzde 45'i engelleyici kiptedir, senaryolardan gelenin
  yüzde 88'i; engelleyici kipin düşük payı yazarın dikkatini değil listenin kaynağını gösterir.
- 28 gereksinimin 19'u kod aşamasında yılda 7.980 kez sıfır insan maliyetiyle sınanır; 5'i dağıtım
  aşamasında 300 denetimde 40 saat tüketir, 4'ü hiç sınanmaz.
- Eksik parçalar yazıldığında gözle sınamanın 40 saatlik yükünün tamamı düşer; sınanamaz dört
  gereksinim ise hiçbir denetimde uyarı üretmemeye devam eder.

## Sonraki Adım

Bu ders gereksinimin nasıl yazılacağını ölçtü ve iki iş çıkardı: üç gereksinime eksik alan
yazmak, dört gereksinimi yeniden düşünmek. İkisi de birinin yapması gereken işlerdir ve o birinin
kim olduğu hiç sorulmadı. Eksik eşiği yazacak kişi, kötüye kullanım senaryosunu yürütecek kişi ve
tasarım oturumunda gözlenemez bir yüklemi fark edecek kişi aynı kişi değildir; beş ekibin hepsinde
de bulunmaz. Önceki iki ders denetimleri aşamalara dağıttı, bu ders gereksinimleri sınanabilir
biçime çevirdi — ama her ikisi de yapacak **yetkinliğin** her ekipte hazır bulunduğunu varsaydı.
Sonraki ders o varsayımı ölçer: kaç ekip var, kaçında güvenlik gözü olan biri var, bir kişinin
kapasitesi kaç ekibe yetiyor ve kapasite yetmediğinde kaç inceleme güvenlik gözü olmadan geçiyor.
