# REST API ve kişisel erişim token'ları

> /api/v1 REST API ile betiklerden ve CI'dan sorgu talebi gönderin, izleyin ve maskelenmiş sonuçları okuyun. Token kapsamları, süre, istek sınırı ve curl akışı.

- Dokümantasyon: Kılavuzlar
- Güncelleme: 2026-11-04
- Kaynak: https://queryproxy.com/tr/docs/rest-api/
- Dil: tr-TR
- Yazar: Muhammet Şafak

---
REST API, betiklere ve CI hatlarına web arayüzündeki iş akışının aynısını verir.
API ile açılan bir talep aynı [SQL guard'larından](/tr/docs/sql-korumalari/) geçer,
aynı insan onayını bekler ve tarayıcıdan açılanla aynı denetim izine düşer. Bir
onaylayan karar verene kadar hiçbir şey çalışmaz.

Uç nokta referansı, depodaki OpenAPI 3.1 açıklamasıdır:
[`docs/openapi.yaml`](https://github.com/QueryProxy/QueryProxy/blob/main/docs/openapi.yaml).
Bu sayfa token'ların nasıl çalıştığını anlatır ve eksiksiz bir akışı adım adım
gösterir.

Yalnızca bir talep açıp onayını beklemek ve sonucu bir terminalden ya da hattan
almak istiyorsanız yoklamayı [`qp` komut satırı istemcisi](/tr/docs/komut-satiri-istemcisi/) sizin
yerinize yapar.

## Kişisel erişim token'ları

Her çağrı, bearer token olarak bir kişisel erişim token'ı taşır:

```text
Authorization: Bearer <id>|qp_<secret>
```

- Token **tek bir kullanıcıya aittir** ve o kullanıcının web arayüzünde
  yapabildiğinden fazlasına izin vermez. Kapsamlar bunu yalnızca daraltabilir.
- Token **her zaman sona erer**. Süreyi oluştururken seçersiniz; üst sınır
  `QUERYPROXY_API_TOKEN_MAX_DAYS` gündür (varsayılan `90`).
- Sahibi askıya alınır ya da silinirse token **çalışmaz olur**. Servis hesabı
  yoktur: otomasyon gerçek bir kullanıcının token'ını kullanır.
- `QUERYPROXY_REQUIRE_2FA` politikasının kapsadığı ve henüz iki adımlı doğrulamaya
  kaydolmamış bir kullanıcı API'ye erişemez: token ikinci faktörün yerini tutmamalı.
  Kullanıcı kaydolunca token yeniden çalışır.

### Token oluşturma ve iptal etme

**Profile** sayfasında **API tokens** bölümünü açın. Token'a ad verin, kapsamlarını
seçin, kaç gün geçerli olacağını yazın ve oluşturun. Değer **bir kez** gösterilir
ve bir Copy düğmesi vardır; QueryProxy yalnızca özetini (hash) saklar, sayfayı
yenilemek değeri kalıcı olarak gizler. Token'ı iptal etmek onu hemen durdurur.
Oluşturma ve iptal `token.created` ve `token.revoked` olarak denetlenir.

Token oluşturmak önce onay ister:

- Yerel parolanız varsa onu girin; iki adımlı doğrulama açıksa yerine
  doğrulayıcı uygulamanızdaki kodu girin. Yanlış denemeler istek sınırına tabidir.
- Yerel parolası olmayan (yalnızca SSO) bir hesap, son 15 dakika içinde SSO ile
  girmiş olmalıdır. Aksi hâlde sayfa sizi yeniden SSO'ya gönderir ve geri getirir.

### Kapsamlar

| Kapsam | İzin verdiği | Kimde olabilir |
| :-- | :-- | :-- |
| `requests:submit` | Talep gönderme, kendi bekleyen talebini iptal etme | Takımda DBA ya da developer |
| `requests:read` | Talep okuma, bağlantıları listeleme | Her rol |
| `results:read` | Tamamlanmış talebin saklanan sonucunu okuma | Auditor'lara sunulmaz |
| `approvals:write` | İnceleyebileceğiniz talepleri onaylama ya da reddetme | Takımda DBA |

Profile sayfası yalnızca rollerinizin kullanabildiği kapsamları sunar.

## API'nin koruduğu kurallar

- **Onay atlanamaz.** Talep, web arayüzündeki gibi bir insan kararını bekler.
- **Override yoktur.** Override olacak bir onay (onaylayan, talebin takımında DBA
  olmayan bir sistem yöneticisi ya da talep sahibinin kendisi) yazılı gerekçe ister.
  API bunu `403` ile ve web formuna giden bir `override_url` ile reddeder. API'nin
  kendi override yolu yoktur.
- **Bir token, sahibinin kendi talebini asla onaylayamaz.**
- **Sonuçlar maskelenir**; bağlantının maskeleme kurallarıyla, her yerdeki gibi.
  Sonucun kolon adları sonuç verisidir: Auditor onları alamaz, sonucu da hiç
  okuyamaz.
- **Auditor'lar redakte edilmiş SQL görür.** SQL'in literal değerlerini görmemesi
  gereken biri için `sql_original` ve `sql_prepared` `null` gelir; `sql_redacted`
  ifadeyi literaller değiştirilmiş hâlde taşır.

Bir onaylayanın sızdırılmış token'ı, `approvals:write` kapsamı içinde başka
kullanıcıların taleplerini yine de onaylayabilir; bu yüzden bu kapsamı az verin ve
süreyi kısa tutun.

## İstek sınırları

Her token dakikada `QUERYPROXY_API_RATE_LIMIT` çağrı yapabilir (varsayılan `60`).
Aşılırsa API, `Retry-After` başlığıyla `429` döner. Başarısız kimlik doğrulamalar
adres başına aynı sayıyla sınırlanır. Yanıtlar `X-RateLimit-Limit` ve
`X-RateLimit-Remaining` başlıklarını taşır.

## curl ile adım adım

Örnekler iki değişken varsayar: `QP` kurulumunuzun adresi, `TOKEN` token değeri.

```bash
export QP=https://queryproxy.example.com
export TOKEN='7|qp_...'
```

**1. Bağlantıyı bulun.** `GET /api/v1/connections`, kullanabildiğiniz bağlantıları
host ve kimlik bilgisi olmadan listeler.

```bash
curl -s -H "Authorization: Bearer $TOKEN" -H 'Accept: application/json' \
  "$QP/api/v1/connections"
```

**2. Talebi gönderin.** `requests:submit` ister. `connection_id` ve `sql`
zorunludur; `title` (en fazla 150 karakter) ve `reason` (en fazla 1000) isteğe
bağlıdır. Yanıt `201`'dir ve talep `pending` durumundadır.

```bash
curl -s -X POST "$QP/api/v1/requests" \
  -H "Authorization: Bearer $TOKEN" -H 'Accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{"connection_id": 3, "sql": "SELECT id, status FROM orders", "title": "Orders check", "reason": "Support ticket"}'
```

SQL guard ifadeyi `422` ve bir `violations` listesiyle reddedebilir. Göremediğiniz
bir bağlantı `404` olarak bildirilir; görebildiğiniz ama gönderemeyeceğiniz bir
bağlantı (Auditor ya da yazma için `read` tanımlaması) `403` ile reddedilir.

**3. Talebi izleyin.** `requests:read` ister. `status` `completed` olana (ya da
`failed`, `rejected`, `cancelled`) kadar sorgulayın. Durumlar: `pending`,
`approved`, `rejected`, `queued`, `running`, `completed`, `failed` ve `cancelled`.

```bash
curl -s -H "Authorization: Bearer $TOKEN" -H 'Accept: application/json' \
  "$QP/api/v1/requests/42"
```

**4. Onay.** Takımın bir DBA'i (talep sahibi değil) web arayüzünde, Slack ya da
Teams'te veya `approvals:write` kapsamlı kendi token'ıyla (aşağıda
`REVIEWER_TOKEN`) API üzerinden onaylar:

```bash
curl -s -X POST -H "Authorization: Bearer $REVIEWER_TOKEN" -H 'Accept: application/json' \
  "$QP/api/v1/requests/42/approve"

curl -s -X POST "$QP/api/v1/requests/42/reject" \
  -H "Authorization: Bearer $REVIEWER_TOKEN" -H 'Accept: application/json' \
  -H 'Content-Type: application/json' \
  -d '{"reason": "Add a WHERE clause"}'
```

Karara bağlanmış bir talep `409` döner. Talep sahibi bekleyen talebini
`POST /api/v1/requests/42/cancel` ile geri çekebilir.

**5. Sonucu okuyun.** `results:read` ister. Varsayılan NDJSON'dur: satır başına bir
JSON dizisi, değerler kolon sırasıyla (kolon adları talebin `result.columns`
alanındadır). Başlık satırlı CSV için `Accept: text/csv` gönderin.

```bash
curl -s -H "Authorization: Bearer $TOKEN" "$QP/api/v1/requests/42/result"

curl -s -H "Authorization: Bearer $TOKEN" -H 'Accept: text/csv' \
  "$QP/api/v1/requests/42/result" -o result.csv
```

`X-QueryProxy-Row-Count` ve `X-QueryProxy-Truncated` yanıt başlıkları kaç satırın
saklandığını ve sonucun satır tavanında kesilip kesilmediğini söyler. Tamamlanmamış,
başarısız olmuş ya da sonucu silinmiş bir talep `409` döner; `404`, saklanan dosyanın
sonuç diskinde bulunmadığı anlamına gelir. Her okuma
`result.downloaded` olarak denetlenir.

## Hatalar

Hatalar `message` içeren JSON'dur. Doğrulama hataları (`422`) alan bazında
anahtarlanmış `errors` ekler.

| Durum | Anlamı |
| :-- | :-- |
| `401` | Token yok, bilinmiyor, süresi dolmuş ya da iptal edilmiş; sahibi askıda ya da silinmiş; ya da sahibinin önce iki adımlı doğrulamaya kaydolması gerekiyor |
| `403` | Token'da kapsam yok ya da sahibi bunu yapamaz. Override için `override_url` eklenir |
| `404` | Böyle bir talep ya da bağlantı yok veya bağlantı size görünmüyor. Görüntüleme yetkiniz olmayan bir talep `403` döner |
| `409` | Talep artık bekleyen değil ya da saklanan bir sonucu yok (tamamlanmamış, başarısız ya da silinmiş) |
| `422` | Gövde geçersiz ya da SQL guard ifadeyi reddetti |
| `429` | Token bu dakikanın payını kullandı; `Retry-After` saniye bekleyin |

## Denetim günlüğünde

API ile yapılan gönderimler, onaylar, retler, iptaller ve sonuç okumaları
`channel = api` taşır. Token oluşturma ve iptal `token.created` ve `token.revoked`
olarak kaydedilir. Bkz. [Denetim zinciri ve SIEM aktarımı](/tr/docs/denetim-kaydi-ve-siem/).

## Ayarlar

| Değişken | Varsayılan | Anlamı |
| :-- | :-- | :-- |
| `QUERYPROXY_API_TOKEN_MAX_DAYS` | `90` | Bir token'a verilebilecek en uzun ömür, gün olarak |
| `QUERYPROXY_API_RATE_LIMIT` | `60` | Her token için dakikadaki çağrı sayısı; ayrıca adres başına başarısız kimlik doğrulama sayısı |

## Sonraki adımlar

- Bu API'nin hazır komut satırı istemcisi için [`qp` istemcisi](/tr/docs/komut-satiri-istemcisi/).
- Kimin neyi onaylayabileceği için [Onay akışı](/tr/docs/onay-akisi/).
- Kullanıcılarınız bir sağlayıcıyla giriyorsa [Tek oturum açma](/tr/docs/tek-oturum-acma/).
- Token hijyeni için [Üretim güvenliği](/tr/docs/uretim-guvenligi/).
