# Sipariş İşlemleri

Sipariş endpoint'leri araç kiralama rezervasyonları oluşturmanıza ve yönetmenize olanak tanır. Sipariş sistemi, araç
seçimi, yolcu bilgileri, fatura detayları ve ödeme işleme entegrasyonunu içeren eksiksiz rezervasyon iş akışını ele
alır.

## Sipariş Oluştur

Yeni bir araç kiralama siparişi oluşturur. Bu endpoint, araç rezervasyonu, yolcu kaydı ve ödeme hazırlığını içeren
kapsamlı rezervasyon sürecini başlatır.

### Endpoint

```
POST /order
```

### Kimlik Doğrulama

Bu endpoint kimlik doğrulama gerektirir. Authorization başlığında JWT erişim jetonunuzu ekleyin:

```
Authorization: Bearer ERIŞIM_JETONUNUZ
```

### Son Kullanıcı IP Adresi

Entegre acenta sistemleri, son kullanıcının IP adresini `X-Forwarded-For` başlığı ile iletmelidir. Bu bilgi denetim ve güvenlik amaçları için gereklidir.

### İstek Gövdesi

| Alan | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `paymentType` | string | Evet | Ödeme yöntemi: `creditCard` veya `limit` |
| `searchID` | string | Evet | Araç arama sonuçlarından alınan arama kimliği |
| `code` | string | Evet | Arama sonuçlarından seçilen araç ürün kodu |
| `extraProducts` | array | Hayır | Ek ürün ve hizmetler listesi |
| `passenger` | object | Evet | Birincil yolcu bilgileri |
| `billing` | object | Hayır | Özel fatura adresi (isteğe bağlı, varsayılan olarak yolcu bilgileri) |
| `isFullCredit` | boolean | Hayır | Tam kredi ödemesi kullan (acenta yetkilendirilmeli) |
| `isLimitedCredit` | boolean | Hayır | Sınırlı kredi ödemesi kullan (acenta yetkilendirilmeli) |
| `trackingID` | string | Hayır | Acentenin kendi rezervasyon/takip numarası |


#### Ekstra Ürünler

| Alan | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `code` | string | Evet | Ekstra ürün aramasından ürün kodu |
| `quantity` | integer | Evet | Eklenecek miktar (minimum 1) |


#### Yolcu Bilgileri

| Alan | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `firstName` | string | Evet | Yolcu adı |
| `lastName` | string | Evet | Yolcu soyadı |
| `email` | string | Evet | Geçerli e-posta adresi |
| `nationality` | string | Evet | ISO ülke kodu (2 karakter) |
| `phone` | string | Evet | E.164 formatında telefon numarası (ör. +905551234567) |
| `birthDate` | string | Evet | Doğum tarihi (YYYY-MM-DD formatı) |
| `identityNumber` | string | Hayır | 11 haneli kimlik numarası (Türk vatandaşları için) |
| `passportNo` | string | Hayır | Pasaport numarası (uluslararası seyahatçiler için) |


#### Fatura Adresi (İsteğe Bağlı)

| Alan | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `type` | string | Evet | Adres türü: `individual`, `privateCompany` veya `corporateCompany` |
| `label` | string | Hayır | Adres için özel etiket |
| `firstName` | string | Evet | Fatura adı |
| `lastName` | string | Hayır | Fatura soyadı |
| `email` | string | Hayır | Fatura e-posta adresi |
| `phone` | string | Hayır | E.164 formatında fatura telefon numarası |
| `countryName` | string | Evet | Tam ülke adı |
| `countryCode` | string | Evet | ISO ülke kodu (2 karakter) |
| `adm1` | string | Evet | İdari bölüm seviye 1 (il/eyalet) |
| `adm2` | string | Hayır | İdari bölüm seviye 2 (şehir/ilçe) |
| `line` | string | Hayır | Adres satırı (sokak adresi) |
| `zipCode` | string | Hayır | Posta/ZIP kodu |
| `taxDivision` | string | Hayır | Vergi dairesi/bölümü |
| `taxIdentifier` | string | Hayır | Vergi kimlik numarası |


### Örnek İstek

```bash
curl -X POST https://api.pro.yolcu360.com/api/v1/order \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer ERIŞIM_JETONUNUZ" \
  -H "X-Forwarded-For: 203.0.113.195" \
  -d '{
    "paymentType": "creditCard",
    "searchID": "search_123456789",
    "code": "ECAR",
    "isFullCredit": true,
    "isLimitedCredit": false,
    "trackingID": "AGENCY-RES-12345",
    "extraProducts": [
      {
        "code": "GPS",
        "quantity": 1
      },
      {
        "code": "CDW",
        "quantity": 1
      }
    ],
    "passenger": {
      "firstName": "Ahmet",
      "lastName": "Yılmaz",
      "email": "ahmet.yilmaz@example.com",
      "nationality": "TR",
      "phone": "+905551234567",
      "birthDate": "1990-01-15",
      "identityNumber": "12345678901"
    },
    "billing": {
      "type": "individual",
      "label": "Ev Adresi",
      "firstName": "Ahmet",
      "lastName": "Yılmaz",
      "email": "ahmet.yilmaz@example.com",
      "phone": "+905551234567",
      "countryName": "Türkiye",
      "countryCode": "TR",
      "adm1": "İstanbul",
      "adm2": "Beşiktaş",
      "line": "Barbaros Bulvarı No:123",
      "zipCode": "34349"
    }
  }'
```

**Şahıs Şirketi Fatura Örneği:**

```bash
curl -X POST https://api.pro.yolcu360.com/api/v1/order \
  -H "Content-Type: application/json" \
  -H "Authorization: Bearer ERIŞIM_JETONUNUZ" \
  -d '{
    ...
    "billing": {
      "type": "privateCompany",
      "firstName": "Ayşe",
      "lastName": "Demir",
      "email": "ayse@sirket.com",
      "phone": "+905551234567",
      "countryName": "Türkiye",
      "countryCode": "TR",
      "adm1": "İstanbul",
      "adm2": "Kadıköy",
      "line": "İş Caddesi No:456",
      "zipCode": "34000",
      "taxDivision": "Kadıköy VD",
      "taxIdentifier": "1234567890"
    }
  }'
```

### Yanıt

**Başarılı Yanıt (201 Created):**

```json
{
  "id": "order_123456789",
  "paymentType": "creditCard",
  "paymentCurrency": "TRY",
  "language": "tr",
  "createdAt": "2024-12-25T10:00:00Z",
  "updatedAt": "2024-12-25T10:00:00Z",
  "passenger": {
    "firstName": "Ahmet",
    "lastName": "Yılmaz",
    "email": "ahmet.yilmaz@example.com",
    "nationality": "TR",
    "phone": "+905551234567"
  },
  "billing": {
    "type": "individual",
    "firstName": "Ahmet",
    "lastName": "Yılmaz",
    "email": "ahmet.yilmaz@example.com",
    "phone": "+905551234567"
  },
  "orderedCarProduct": {
    "id": 1001,
    "status": "pending",
    "quantity": 1,
    "isFullCredit": true,
    "isLimitedCredit": false,
    "vendorCancelled": false,
    "trackingID": "AGENCY-RES-12345",
    "createdAt": "2024-12-25T10:00:00Z",
    "updatedAt": "2024-12-25T10:00:00Z",
    "car": {
      "code": "ECAR",
      "searchID": "search_123456789",
      "brand": {
        "id": "toyota",
        "name": "Toyota"
      },
      "model": {
        "id": "corolla",
        "name": "Corolla"
      },
      "class": {
        "id": "economy",
        "name": "Ekonomi"
      },
      "imageURL": "https://example.com/car-image.jpg",
      "pricing": {
        "total": {
          "amount": 50000,
          "currency": "TRY"
        },
        "paymentTotal": {
          "amount": 50000,
          "currency": "TRY"
        }
      }
    }
  },
  "orderedExtraProducts": [
    {
      "id": 1002,
      "status": "pending",
      "quantity": 1,
      "vendorCancelled": false,
      "trackingID": "AGENCY-RES-12345",
      "createdAt": "2024-12-25T10:00:00Z",
      "updatedAt": "2024-12-25T10:00:00Z",
      "extraProduct": {
        "code": "GPS",
        "name": "GPS Navigasyon Sistemi",
        "type": "equipment",
        "pricing": {
          "total": {
            "amount": 1500,
            "currency": "TRY"
          }
        }
      }
    },
    {
      "id": 1003,
      "status": "pending",
      "quantity": 1,
      "vendorCancelled": false,
      "trackingID": "AGENCY-RES-12345",
      "createdAt": "2024-12-25T10:00:00Z",
      "updatedAt": "2024-12-25T10:00:00Z",
      "extraProduct": {
        "code": "CDW",
        "name": "Çarpışma Hasarı Muafiyeti",
        "type": "insurance",
        "pricing": {
          "total": {
            "amount": 3000,
            "currency": "TRY"
          }
        }
      }
    }
  ]
}
```

### Sipariş Durumu Değerleri

| Durum | Açıklama |
|  --- | --- |
| `pending` | Öğe siparişe eklendi, onay bekleniyor |
| `reserved` | Öğe tedarikçide başarıyla rezerve edildi |
| `failed` | Öğe rezervasyonu başarısız |
| `cancelled` | Öğe kullanıcı veya tedarikçi tarafından iptal edildi |
| `removed` | Öğe siparişten kaldırıldı |


## Sipariş Detaylarını Al

Mevcut durum, yolcu bilgileri, sipariş edilen ürünler ve ödeme bilgileri dahil olmak üzere belirli bir siparişin
kapsamlı detaylarını alın.

### Endpoint

```
GET /order/{orderID}
```

### Kimlik Doğrulama

Bu endpoint kimlik doğrulama gerektirir. Authorization başlığında JWT erişim jetonunuzu ekleyin.

### Yol Parametreleri

| Parametre | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `orderID` | string | Evet | Benzersiz sipariş tanımlayıcısı |


### Örnek İstek

```bash
curl -X GET https://api.pro.yolcu360.com/api/v1/order/order_123456789 \
  -H "Authorization: Bearer ERIŞIM_JETONUNUZ"
```

### Yanıt

**Başarılı Yanıt (200 OK):**

Sipariş oluşturma yanıtıyla aynı yapıyı döndürür, güncellenmiş durum bilgileri ve oluşturulduktan sonra gerçekleşen
değişikliklerle birlikte.

```json
{
  "id": "order_123456789",
  "paymentType": "creditCard",
  "paymentCurrency": "TRY",
  "language": "tr",
  "createdAt": "2024-12-25T10:00:00Z",
  "updatedAt": "2024-12-25T10:15:00Z",
  "passenger": {
    "firstName": "Ahmet",
    "lastName": "Yılmaz",
    "email": "ahmet.yilmaz@example.com",
    "nationality": "TR",
    "phone": "+905551234567"
  },
  "orderedCarProduct": {
    "id": 1001,
    "status": "reserved",
    "quantity": 1,
    "isFullCredit": true,
    "isLimitedCredit": false,
    "vendorCancelled": false,
    "vendorReservationID": "AVIS_RES_789012",
    "trackingID": "AGENCY-RES-12345",
    "paymentID": 2001,
    "createdAt": "2024-12-25T10:00:00Z",
    "updatedAt": "2024-12-25T10:15:00Z",
    "car": {
      "code": "ECAR",
      "searchID": "search_123456789",
      "brand": {
        "id": "toyota",
        "name": "Toyota"
      },
      "model": {
        "id": "corolla",
        "name": "Corolla"
      }
    }
  },
  "orderedExtraProducts": [
    {
      "id": 1002,
      "status": "reserved",
      "quantity": 1,
      "paymentID": 2001,
      "vendorReservationID": "AVIS_GPS_789013",
      "trackingID": "AGENCY-RES-12345"
    }
  ]
}
```

## İptal Uygunluğunu Kontrol Et

Bir siparişin iptal ve iade için uygun olup olmadığını kontrol eder. Bu endpoint siparişi değiştirmez ancak iptal ve
iade uygunluk durumu hakkında bilgi sağlar.

### Endpoint

```
POST /order/{orderID}/cancel_eligibility
```

### Kimlik Doğrulama

Bu endpoint kimlik doğrulama gerektirir. Authorization başlığında JWT erişim jetonunuzu ekleyin.

### Yol Parametreleri

| Parametre | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `orderID` | string | Evet | Kontrol edilecek siparişin benzersiz tanımlayıcısı |


### Örnek İstek

```bash
curl -X POST https://api.pro.yolcu360.com/api/v1/order/YLP_123456/cancel_eligibility \
  -H "Authorization: Bearer ERIŞIM_JETONUNUZ"
```

### Yanıt

**Başarılı Yanıt (200 OK):**

```json
{
  "cancellable": true,
  "refundable": true
}
```

### Yanıt Alanları

| Alan | Tür | Açıklama |
|  --- | --- | --- |
| `cancellable` | boolean | Siparişin iptal için uygun olup olmadığı |
| `refundable` | boolean | Siparişin iptal edildiğinde iade için uygun olup olmadığı |


## Siparişi İptal Et

Mevcut bir siparişi iptal eder. Bu işlemin başarılı olması için siparişin iptal edilebilir durumda olması gerekir. Bu
endpoint siparişi tedarikçi ile iptal etmeye çalışır ve sipariş durumunu buna göre günceller.

### Endpoint

```
POST /order/{orderID}/cancel
```

### Kimlik Doğrulama

Bu endpoint kimlik doğrulama gerektirir. Authorization başlığında JWT erişim jetonunuzu ekleyin.

### Yol Parametreleri

| Parametre | Tür | Gerekli | Açıklama |
|  --- | --- | --- | --- |
| `orderID` | string | Evet | İptal edilecek siparişin benzersiz tanımlayıcısı |


### Örnek İstek

```bash
curl -X POST https://api.pro.yolcu360.com/api/v1/order/YLP_123456/cancel \
  -H "Authorization: Bearer ERIŞIM_JETONUNUZ"
```

### Yanıt

**Başarılı Yanıt (200 OK):**

```json
{
  "success": true,
  "message": "Sipariş başarıyla iptal edildi",
  "orderId": "YLP_123456",
  "status": "success"
}
```

### İptal Durumu Değerleri

| Durum | Açıklama |
|  --- | --- |
| `pending` | İptal isteği işleniyor |
| `success` | Sipariş başarıyla iptal edildi |
| `failed` | İptal isteği başarısız oldu |


## Sipariş Oluşturma İş Akışı

Sipariş oluşturma süreci, sistem tarafından otomatik olarak yürütülen birden fazla adımı içerir:

### 1. Sipariş Başlatma

- Temel sipariş kaydı oluşturur
- Arama oturumunu ve araç kullanılabilirliğini doğrular
- Başlangıç durumunu "open" olarak ayarlar


### 2. Ürün Ekleme

- Seçilen aracı siparişe ekler
- Seçilen ekstra ürünleri ekler
- Komisyonlar dahil toplam fiyatlandırmayı hesaplar


### 3. Yolcu Kaydı

- Yolcu bilgilerini doğrular
- Yolcu detaylarını güvenli şekilde saklar
- Yolcuyu siparişe bağlar


### 4. Fatura Kurulumu

- Sağlandıysa özel fatura adresini kullanır
- Faturalama için yolcu bilgilerine geri döner
- Fatura bilgilerinin eksiksizliğini doğrular


### 5. Ödeme Hazırlığı

- Nihai ödeme tutarlarını hesaplar
- Ödeme türüne göre ödeme gereksinimlerini belirler
- Siparişi ödeme işleme için hazırlar


### Sipariş Yaşam Döngüsü

```mermaid
graph TD
    A[Sipariş Oluştur] --> B[Araç Ekle]
    B --> C[Ekstra Ürünler Ekle]
    C --> D[Yolcu Bilgilerini Ekle]
    D --> E[Fatura Bilgilerini Ekle]
    E --> F[Toplamları Hesapla]
    F --> G[Sipariş Ödeme İçin Hazır]
    G --> H[Ödemeyi İşle]
    H --> I{Ödeme Başarılı?}
    I -->|Evet| J[Tedarikçide Rezerve Et]
    I -->|Hayır| K[Ödeme Başarısız]
    J --> L[Sipariş Tamamlandı]
    K --> M[Ödemeyi Yeniden Dene]
    M --> H
```

## Sipariş En İyi Uygulamaları

### Yolcu Bilgileri

- **Gerekli Alanlar**: Tüm zorunlu yolcu alanlarının sağlandığından emin olun
- **Belge Doğrulama**: Kimlik numarası (yerli için) veya pasaport (uluslararası için) sağlayın
- **İletişim Bilgileri**: Bildirimler için geçerli e-posta ve telefon numarası kullanın
- **Yaş Doğrulama**: Yolcunun minimum yaş gereksinimlerini karşıladığından emin olun


### Fatura Adresi

- **İsteğe Bağlı Kullanım**: Yalnızca yolcu adresinden farklıysa fatura adresi sağlayın
- **Kurumsal Siparişler**: İş kiralamaları için şirket fatura bilgilerini kullanın
- **Vergi Bilgileri**: Kurumsal fatura adresleri için vergi detaylarını ekleyin
- **Adres Doğrulama**: Adres bilgilerinin eksiksiz ve doğru olduğundan emin olun


### Ekstra Ürünler

- **Miktar Sınırları**: Minimum ve maksimum miktar kısıtlamalarına saygı gösterin
- **Uyumluluk**: Ürün uyumluluğunu seçilen araçla doğrulayın
- **Fiyat Güncellemeleri**: Arama ve sipariş arasında ekstra ürün fiyatları değişebilir


### Hata İşleme

**Yaygın Hata Yanıtları:**

- `400 Bad Request`: Geçersiz sipariş verisi veya eksik gerekli alanlar
- `401 Unauthorized`: Kimlik doğrulama gerekli veya jetonun süresi dolmuş
- `404 Not Found`: Arama oturumunun süresi dolmuş veya araç kullanılamıyor
- `422 Unprocessable Entity`: Yolcu veya fatura verilerinde doğrulama hataları
- `500 Internal Server Error`: Sipariş işleme sırasında sistem hatası


**Örnek Hata Yanıtı:**

```json
{
  "code": 1001,
  "description": "Geçersiz yolcu bilgisi",
  "details": {
    "field": "passenger.email",
    "message": "Geçersiz e-posta formatı"
  }
}
```

### Doğrulama Kuralları

#### Yolcu Doğrulama

- **E-posta**: Geçerli e-posta formatında olmalı
- **Telefon**: E.164 uluslararası formatında olmalı
- **Doğum Tarihi**: Geçerli tarih olmalı ve minimum yaş gereksinimlerini karşılamalı
- **Uyruk**: Geçerli ISO ülke kodu olmalı
- **Kimlik/Pasaport**: Uyruk ve seyahat gereksinimlerine göre gerekli


#### Fatura Doğrulama

- **Tür**: Şunlardan biri olmalı: individual, privateCompany, corporateCompany
- **Ülke**: Ülke kodu ülke adıyla eşleşmeli
- **Kurumsal Alanlar**: Şirket türleri için vergi dairesi ve tanımlayıcı gerekli
- **Adres**: İdari bölümler ülke için geçerli olmalı


## Entegrasyon Örnekleri

### Temel Sipariş Oluşturma

```javascript
async function createOrder(searchResult, passengerInfo) {
    const orderData = {
        paymentType: 'creditCard',
        searchID: searchResult.searchID,
        code: searchResult.code,
        passenger: {
            firstName: passengerInfo.firstName,
            lastName: passengerInfo.lastName,
            email: passengerInfo.email,
            nationality: passengerInfo.nationality,
            phone: passengerInfo.phone,
            birthDate: passengerInfo.birthDate
        }
    };

    const response = await fetch('/api/v1/order', {
        method: 'POST',
        headers: {
            'Content-Type': 'application/json',
            'Authorization': `Bearer ${accessToken}`
        },
        body: JSON.stringify(orderData)
    });

    if (!response.ok) {
        const error = await response.json();
        throw new Error(`Sipariş oluşturma başarısız: ${error.description}`);
    }

    return await response.json();
}
```

### Ekstra Ürünlerle Sipariş

```javascript
async function createOrderWithExtras(searchResult, passengerInfo, selectedExtras) {
    const orderData = {
        paymentType: 'creditCard',
        searchID: searchResult.searchID,
        code: searchResult.code,
        extraProducts: selectedExtras.map(extra => ({
            code: extra.code,
            quantity: extra.quantity
        })),
        passenger: passengerInfo
    };

    return await createOrder(orderData);
}
```

## Hız Sınırlama

Sipariş endpoint'leri hız sınırlamasına tabidir:

- **Sipariş oluştur**: Kullanıcı başına dakikada maksimum 5 istek
- **Sipariş al**: Kullanıcı başına dakikada maksimum 60 istek


Yanıtlarda hız sınırı başlıklarını izleyin ve uygun yeniden deneme mantığını uygulayın.