---
title: 'Geliştirme Ortamı'
source: 'https://academia.sh/tr/kurslar/android-platformu/gelistirme-ortami'
course: 'Android Platformu ve Araçlar'
language: tr
updated: '2026-10-21T05:02:36+00:00'
license: 'CC BY-SA 4.0'
objectives:
    - 'Emülatör ile fiziksel aygıtın aynı kurulum isteğine verdiği karşılamayı ayırır'
    - 'Aygıtın API düzeyinin en düşük API düzeyinin altında kalmasının karşılıksız, hata ayıklama yetkisinin onay beklemesinin bekleyen olduğunu ölçer'
    - 'Günlük aracı, hata ayıklayıcı ve profil aracının geliştirme ortamındaki yerini ayırır'
    - 'Yerel kodun işlemci mimarisi uyuşmazlığını sınırlayıcı ölçümle doğrular'
---

# Geliştirme Ortamı

Geliştirme ortamında uygulamanın aygıta kurulması isteğinin API düzeyi, hata ayıklama yetkisi ve işlemci mimarisi karşısında modeli.

Önceki ders aynı kaynaktan hangi derleme varyantlarının çıktığını ölçtü. Bir varyant derlenince onu çalıştıracak bir yer gerekir. Geliştirme ortamı (development environment) kaynak kodun yazıldığı, derlendiği, aygıta kurulduğu ve izlendiği araç bütünüdür. Bu ders, bir kurulum isteğine aygıtın ne verdiğini ölçer.

Kursun ölçü ekseni değişmez: bu isteği platform nasıl karşılıyor. Karşılama dörttür: tam, ikame, bekleyen ve karşılıksız. Karşılamayı etiket değil kural verir: verilen değer istenene eşitse tam, eşit değilse ikame; bekleyen ve karşılıksız doğrudan sonuçtan çıkar. Aşağıdaki dosya o kuralı taşır ve her derste aynen yinelenir. Açılış dersindeki 3/2/2/1 sayısı burada değiştirilmez.

```kotlin
// Fulfillment.kt — bir istegin platformca nasil karsilandigini siniflandirir
sealed interface Outcome {
    data class Given(val value: String) : Outcome
    data class Waiting(val on: String) : Outcome
    data class Refused(val reason: String) : Outcome
}

class Ask(val label: String, val wanted: String, val outcome: Outcome) {
    val fulfillment: String = when (outcome) {
        is Outcome.Waiting -> "bekleyen"
        is Outcome.Refused -> "karsiliksiz"
        is Outcome.Given -> if (outcome.value == wanted) "tam" else "ikame"
    }

    fun report() {
        val detail = when (outcome) {
            is Outcome.Given -> "verilen=${outcome.value}"
            is Outcome.Waiting -> "bekledigi=${outcome.on}"
            is Outcome.Refused -> "neden=${outcome.reason}"
        }
        println("$label: istenen=$wanted | $detail -> $fulfillment")
    }
}

fun tally(asks: List<Ask>) {
    for (name in listOf("tam", "ikame", "bekleyen", "karsiliksiz")) {
        println("$name: ${asks.count { it.fulfillment == name }}")
    }
}
```

## Aygıtlar ve Araçlar

Uygulama iki yerde çalıştırılır. Emülatör (emulator) bilgisayarda bir aygıtı taklit eden sanal aygıttır. Fiziksel aygıt ise gerçek bir donanımdır ve bilgisayara bağlanır. İkisi de araçlar açısından aynı arayüzü sunar. Araçlar dört işi yapar:

- Aygıt bağlantı aracı aygıtı bulur, uygulamayı kurar ve aygıtla bilgisayar arasında köprü kurar.
- Günlük (log) aracı aygıtın yazdığı günlük satırlarını gösterir.
- Hata ayıklayıcı (debugger) çalışan uygulamayı durdurup değişkenlerini inceler.
- Profil aracı (profiler) işlemci, bellek ve ağ kullanımını zaman içinde ölçer.

Aşağıdaki parça uygulamanın en düşük API düzeyini bildiren derleme ayarını gösterir. Platform araçlarının okuduğu bir betiktir ve çalıştırılmaz.

```kotlin
// modul derleme betigi
android {
    defaultConfig {
        minSdk = 26
    }
}
```

Bu ayar uygulamanın hangi aygıtlara kurulabileceğini sınırlar. Aygıtın API düzeyi (API level) bu değerin altındaysa kurulum yapılmaz. Model, platformun bu kuralını kurar.

## Kurulum İsteği

Model bir aygıtı adı, API düzeyi, işlemci mimarisi ve hata ayıklama yetkisinin onaylanıp onaylanmadığıyla tanımlar. Kurulum isteğinde üç durum ayrılır:

- Aygıtın API düzeyi en düşük API düzeyinin altındaysa kurulum verilmez: karşılıksız, neden `api-duzeyi`.
- API düzeyi yeterli ama aygıt hata ayıklama yetkisini henüz onaylamamışsa kurulum bekler: bekleyen, bekledigi `kullanici-onayi`.
- Her iki koşul sağlanıyorsa istenen uygulama olduğu gibi kurulur: tam.

```kotlin
// Install.kt — kurulum istegi modeli
class Device(val name: String, val apiLevel: Int, val abi: String, val debugApproved: Boolean)

fun resolveInstall(wanted: String, minApi: Int, device: Device): Ask {
    val outcome = when {
        device.apiLevel < minApi -> Outcome.Refused("api-duzeyi")
        !device.debugApproved -> Outcome.Waiting("kullanici-onayi")
        else -> Outcome.Given(wanted)
    }
    return Ask(device.name, wanted, outcome)
}
```

Ölçümde en düşük API düzeyi 26'dır. Dört aygıt vardır: güncel bir emülatör, onayı verilmiş bir fiziksel aygıt, onay ekranını henüz geçmemiş bir fiziksel aygıt ve eski bir aygıt.

```kotlin
// Main.kt — kurulum istegi
fun main() {
    val devices = listOf(
        Device("emulator", 34, "arm64", true),
        Device("telefon-onayli", 30, "arm64", true),
        Device("telefon-onaysiz", 30, "arm64", false),
        Device("eski-telefon", 23, "arm64", true),
    )
    val asks = devices.map { resolveInstall("uygulama", 26, it) }
    for (ask in asks) ask.report()
    tally(asks)
}
```

```text
emulator: istenen=uygulama | verilen=uygulama -> tam
telefon-onayli: istenen=uygulama | verilen=uygulama -> tam
telefon-onaysiz: istenen=uygulama | bekledigi=kullanici-onayi -> bekleyen
eski-telefon: istenen=uygulama | neden=api-duzeyi -> karsiliksiz
tam: 2
ikame: 0
bekleyen: 1
karsiliksiz: 1
```

İki aygıt tam, bir aygıt bekleyen, bir aygıt karşılıksız aldı. Onaysız telefon reddedilmedi, API düzeyi yetmeyen telefon reddedildi.

**AP1.** Model hata ayıklama yetkisini tek bir mantıksal değer olarak kurar. Gerçek aygıtta bu onay kullanıcı etkileşimiyle verilir ve aygıt başına ayrı tutulur; ölçüm bunu taklit etmez.

**AP2.** Kurulum modeli emülatörle fiziksel aygıt arasında fark kurmaz; fark yalnız sensör ölçümünde vardır. Gerçekte performans ve ağ farkları da vardır.

## Onayın Gelmesi

Bekleyen bir istek onay gelince tam olur. Bunu ölçmek için aynı aygıt iki kez sorulur: önce onaysız, sonra onaylı.

```kotlin
// Main.kt — onay once ve sonra
fun main() {
    val before = Device("telefon", 30, "arm64", false)
    val after = Device("telefon", 30, "arm64", true)
    val asks = listOf(
        resolveInstall("uygulama", 26, before),
        resolveInstall("uygulama", 26, after),
    )
    for (ask in asks) ask.report()
    tally(asks)
}
```

```text
telefon: istenen=uygulama | bekledigi=kullanici-onayi -> bekleyen
telefon: istenen=uygulama | verilen=uygulama -> tam
tam: 1
ikame: 0
bekleyen: 1
karsiliksiz: 0
```

Aynı istek bekleyen iken ve onaydan sonra farklı karşılandı. Bekleyen sonuç bir kullanıcı eylemini adlandırır; eylem gelince aynı istek tam olur.

## Hata Ayıklama ve Profil Araçları

Üç araç aynı çalışan uygulamaya bağlanır ama farklı bir iş görür. Günlük aracı uygulamanın ve sistemin yazdığı satırları akıtır; uygulamayı durdurmaz. Hata ayıklayıcı uygulamayı kaynak kodda belirlenen noktada durdurur, değişkenleri okur ve adım adım ilerletir. Profil aracı uygulamayı durdurmadan işlemci, bellek ve ağ kullanımını zaman çizelgesi olarak kaydeder. Hata ayıklayıcı uygulamanın çalışma biçimine müdahale ettiği için derleme türünün buna izin vermesi gerekir. Aşağıdaki betik parçası bir dağıtım derlemesinin hata ayıklamaya kapalı olduğunu bildirir.

```kotlin
// modul derleme betigi
android {
    buildTypes {
        getByName("release") { isDebuggable = false }
        getByName("debug") { isDebuggable = true }
    }
}
```

Model bu ayara göre üç aracı sınar. Günlük aracı her derlemede tam verilir. Hata ayıklayıcı yalnız hata ayıklamaya açık derlemede tam verilir; kapalıysa karşılıksız, neden `hata-ayiklanabilir-degil`. Profil aracı kapalı derlemede kısıtlı bir ölçüm verir; model bunu ikame sayar.

```kotlin
// Tools.kt — arac baglanma modeli
fun attachTool(tool: String, debuggable: Boolean): Ask {
    val outcome = when (tool) {
        "gunluk-araci" -> Outcome.Given(tool)
        "hata-ayiklayici" ->
            if (debuggable) Outcome.Given(tool) else Outcome.Refused("hata-ayiklanabilir-degil")
        "profil-araci" ->
            if (debuggable) Outcome.Given(tool) else Outcome.Given("kisitli-profil-araci")
        else -> Outcome.Refused("arac-yok")
    }
    return Ask("$tool/${if (debuggable) "debug" else "release"}", tool, outcome)
}
```

Ölçümde üç aracın her biri iki derlemede sorulur ve bilinmeyen bir araç adı eklenir.

```kotlin
// Main.kt — arac baglanma
fun main() {
    val asks = listOf(
        attachTool("gunluk-araci", true),
        attachTool("hata-ayiklayici", true),
        attachTool("profil-araci", true),
        attachTool("gunluk-araci", false),
        attachTool("hata-ayiklayici", false),
        attachTool("profil-araci", false),
    )
    for (ask in asks) ask.report()
    tally(asks)
}
```

```text
gunluk-araci/debug: istenen=gunluk-araci | verilen=gunluk-araci -> tam
hata-ayiklayici/debug: istenen=hata-ayiklayici | verilen=hata-ayiklayici -> tam
profil-araci/debug: istenen=profil-araci | verilen=profil-araci -> tam
gunluk-araci/release: istenen=gunluk-araci | verilen=gunluk-araci -> tam
hata-ayiklayici/release: istenen=hata-ayiklayici | neden=hata-ayiklanabilir-degil -> karsiliksiz
profil-araci/release: istenen=profil-araci | verilen=kisitli-profil-araci -> ikame
tam: 4
ikame: 1
bekleyen: 0
karsiliksiz: 1
```

Aynı üç araç iki derlemede farklı karşılandı: fark araçtan değil derleme türünden geldi. Hata ayıklayıcı dağıtım derlemesinde hiç verilmedi, profil aracı ise başka bir şey olarak verildi.

**AP3.** Model profil aracının kapalı derlemedeki davranışını kısıtlı ölçüm olarak kurar. Gerçek platformda hangi ölçümlerin kaldığı araca ve sürüme bağlıdır; ölçüm bunu doğrulamaz.

## Emülatör ile Fiziksel Aygıt

Emülatör sensör verisini taklit eder: konum, ivme ve kamera için sanal değerler verir. Fiziksel aygıtta bu değerler gerçek donanımdan gelir. Aygıt bağlı değilse hiçbir şey verilemez, ama bağlantı kurulunca istek yeniden sorulabilir. Model üç durumu ayırır: bağlı olmayan aygıt bekleyen, bağlı emülatör ikame, bağlı fiziksel aygıt tam.

```kotlin
// Sensor.kt — sensor istegi modeli
class Target(val name: String, val connected: Boolean, val emulated: Boolean)

fun resolveSensor(wanted: String, target: Target): Ask {
    val outcome = when {
        !target.connected -> Outcome.Waiting("aygit-baglantisi")
        target.emulated -> Outcome.Given("sanal-$wanted")
        else -> Outcome.Given(wanted)
    }
    return Ask(target.name, wanted, outcome)
}
```

Ölçümde üç hedef vardır: kablosu takılı bir telefon, çalışan bir emülatör ve kablosu çıkarılmış bir telefon.

```kotlin
// Main.kt — sensor istegi
fun main() {
    val targets = listOf(
        Target("telefon", true, false),
        Target("emulator", true, true),
        Target("telefon-kablosuz", false, false),
    )
    val asks = targets.map { resolveSensor("konum", it) }
    for (ask in asks) ask.report()
    tally(asks)
}
```

```text
telefon: istenen=konum | verilen=konum -> tam
emulator: istenen=konum | verilen=sanal-konum -> ikame
telefon-kablosuz: istenen=konum | bekledigi=aygit-baglantisi -> bekleyen
tam: 1
ikame: 1
bekleyen: 1
karsiliksiz: 0
```

Emülatörün verdiği değer, istenen değerin sanal bir sürümüdür; bu yüzden ikamedir. Bağlantı kesik telefon ise reddedilmedi, bekliyor.

**AP4.** Model sanal değeri adıyla ayırır. Gerçek emülatörde sanal konumun nasıl verildiği ve sensör türlerinin hangisinin taklit edildiği ölçülmedi.

## Sınırlayıcı Ölçüm

Yerel kod (native code) belirli bir işlemci mimarisi için derlenir. API düzeyi yeterli olan bir aygıt da mimari uyuşmazsa uygulamanın yerel kısmını çalıştıramaz. Model hangi alanı karşılaştırdığını adıyla söyler: önce API düzeyi, sonra işlemci mimarisi.

```kotlin
// Abi.kt — mimari karsilastirmasi
fun resolveNative(wanted: String, minApi: Int, builtFor: Set<String>, device: Device): Ask {
    val outcome = when {
        device.apiLevel < minApi -> Outcome.Refused("api-duzeyi")
        device.abi !in builtFor -> Outcome.Refused("islemci-mimarisi")
        else -> Outcome.Given(wanted)
    }
    return Ask(device.name, wanted, outcome)
}
```

Yerel kod yalnız `arm64` için derlenmiştir. Emülatör API düzeyi yeterli olsa da `x86` mimarisindedir; ikinci bir emülatör `arm64` mimarisindedir.

```kotlin
// Main.kt — mimari uyusmazligi
fun main() {
    val builtFor = setOf("arm64")
    val devices = listOf(
        Device("emulator-x86", 34, "x86", true),
        Device("emulator-arm", 34, "arm64", true),
        Device("eski-emulator", 23, "x86", true),
    )
    val asks = devices.map { resolveNative("yerel-kod", 26, builtFor, it) }
    for (ask in asks) ask.report()
    tally(asks)
}
```

```text
emulator-x86: istenen=yerel-kod | neden=islemci-mimarisi -> karsiliksiz
emulator-arm: istenen=yerel-kod | verilen=yerel-kod -> tam
eski-emulator: istenen=yerel-kod | neden=api-duzeyi -> karsiliksiz
tam: 1
ikame: 0
bekleyen: 0
karsiliksiz: 2
```

İlk emülatör aynı API düzeyindeki ikincisiyle yalnız mimaride ayrılır ve sonuç değişir. Üçüncü aygıtta iki koşul da sağlanmaz; model karşılaştırmayı sırayla yapar ve ilk uyuşmayan alanın adını verir, bu yüzden neden `api-duzeyi` olur.

**AP5.** Model yalnız tam eşleşmeyi kabul eder. Gerçek platformda bir mimari başka bir mimariyi çeviri katmanıyla çalıştırabilir; bu ölçülmedi.

## Özet

- Bu dersin ölçütü: **karşılama**; kurulan şeyin istenen olup olmadığı, aygıtın nerede çalıştığı değil. Bu dersin karşılaması: **bekleyen**.
- Geliştirme ortamı yazma, derleme, kurma ve izleme araçlarının bütünüdür; emülatör ve fiziksel aygıt aynı kurulum arayüzünü kullanır.
- Aygıtın API düzeyi en düşük API düzeyinin altındaysa kurulum karşılıksızdır.
- Hata ayıklama yetkisi onaylanmadıysa kurulum bekleyendir; onay gelince tam olur.
- Yerel kodun işlemci mimarisi aygıtınkiyle uyuşmazsa API düzeyi yeterli olsa bile sonuç karşılıksızdır.

## Sonraki Adım

Uygulama bir aygıta kurulunca kullanıcıdan hassas verilere ve donanıma erişim istemesi gerekir. Sonraki ders izin modelini ele alır.
