560 lines
16 KiB
Markdown
560 lines
16 KiB
Markdown
# API Dokümantasyonu
|
||
|
||
YouTube Transcript RSS Feed API'si, YouTube kanallarının video transcript'lerini RSS/Atom feed formatında sunar.
|
||
|
||
## Base URL
|
||
|
||
```
|
||
http://localhost:5000
|
||
```
|
||
|
||
Production için base URL değişebilir.
|
||
|
||
## Authentication
|
||
|
||
**Tüm endpoint'ler API key gerektirir.**
|
||
|
||
API key'i iki şekilde gönderebilirsiniz:
|
||
|
||
### 1. HTTP Header (Programatik kullanım için önerilen)
|
||
|
||
```http
|
||
X-API-Key: your_api_key_here
|
||
```
|
||
|
||
**Not:** RSS okuyucular HTTP header gönderemediği için bu yöntem sadece programatik kullanım için uygundur.
|
||
|
||
### 2. Query Parameter (RSS okuyucular ve tarayıcılar için zorunlu)
|
||
|
||
```
|
||
?api_key=your_api_key_here
|
||
```
|
||
|
||
**Önemli:** RSS okuyucular, tarayıcılar ve feed aggregator'lar için **mutlaka query parameter** kullanılmalıdır çünkü bu uygulamalar HTTP header gönderemez.
|
||
|
||
**Güvenlik Notu:** API key'i URL'de kullanmak güvenlik açısından ideal değildir çünkü:
|
||
- URL'ler log dosyalarında, tarayıcı geçmişinde ve referrer header'larında görünebilir
|
||
- Ancak RSS okuyucular için bu tek seçenektir
|
||
- Production'da farklı API key'ler kullanarak riski azaltabilirsiniz
|
||
- API key'lerinizi düzenli olarak rotate edin
|
||
|
||
### API Key Alma
|
||
|
||
API key'ler `config/security.yaml` dosyasından yönetilir. Yeni bir API key eklemek için:
|
||
|
||
```yaml
|
||
security:
|
||
api_keys:
|
||
your_api_key_here:
|
||
name: "Your API Key Name"
|
||
rate_limit: 100 # Dakikada maksimum istek
|
||
enabled: true
|
||
```
|
||
|
||
### Hata Yanıtları
|
||
|
||
**401 Unauthorized** - API key eksik veya geçersiz:
|
||
```json
|
||
{
|
||
"error": "Geçersiz veya eksik API key",
|
||
"message": "X-API-Key header veya api_key query parametresi gerekli"
|
||
}
|
||
```
|
||
|
||
**429 Too Many Requests** - Rate limit aşıldı:
|
||
```json
|
||
{
|
||
"error": "Rate limit aşıldı",
|
||
"message": "Dakikada 100 istek limiti",
|
||
"retry_after": 60
|
||
}
|
||
```
|
||
|
||
## Rate Limiting
|
||
|
||
Her API key için dakikada maksimum istek sayısı tanımlanır. Rate limit bilgisi response header'ında döner:
|
||
|
||
```
|
||
X-RateLimit-Remaining: 45
|
||
```
|
||
|
||
Rate limit aşıldığında `429 Too Many Requests` hatası döner.
|
||
|
||
## Endpoints
|
||
|
||
### 1. RSS/Atom Feed Oluştur
|
||
|
||
YouTube kanalı için transcript feed'i oluşturur.
|
||
|
||
**Endpoint:** `GET /`
|
||
|
||
**Query Parameters:**
|
||
|
||
| Parametre | Tip | Zorunlu | Açıklama |
|
||
|-----------|-----|---------|----------|
|
||
| `api_key` | string | ✅ | API key (header ile de gönderilebilir) |
|
||
| `channel_id` | string | ⚠️* | YouTube Channel ID (UC ile başlar, 24 karakter) |
|
||
| `channel` | string | ⚠️* | Channel handle (@username veya username) |
|
||
| `channel_url` | string | ⚠️* | Full YouTube channel URL |
|
||
| `format` | string | ❌ | Feed formatı: `Atom` (varsayılan) veya `Rss` |
|
||
| `max_items` | integer | ❌ | Maksimum transcript sayısı (varsayılan: 10, max: 100, 20'şer batch'ler halinde işlenir) |
|
||
|
||
\* `channel_id`, `channel` veya `channel_url` parametrelerinden biri zorunludur.
|
||
|
||
**Örnek İstekler:**
|
||
|
||
**URL-Based Sorgular (RSS Okuyucular ve Tarayıcılar için):**
|
||
|
||
```bash
|
||
# Channel ID ile (API key URL'de)
|
||
http://localhost:5000/?channel_id=UC9h8BDcXwkhZtnqoQJ7PggA&api_key=demo_key_12345&format=Atom
|
||
|
||
# Channel handle ile (API key URL'de)
|
||
http://localhost:5000/?channel=@tavakfi&api_key=demo_key_12345&format=Atom&max_items=10
|
||
|
||
# Channel URL ile (API key URL'de) - ÖNERİLEN
|
||
http://localhost:5000/?channel_url=https://www.youtube.com/@tavakfi&api_key=demo_key_12345&format=Atom&max_items=50
|
||
|
||
# RSS format ile
|
||
http://localhost:5000/?channel_url=https://www.youtube.com/@politicalfronts&api_key=demo_key_12345&format=Rss&max_items=20
|
||
```
|
||
|
||
**Programatik Kullanım (HTTP Header ile):**
|
||
|
||
```bash
|
||
# Channel ID ile (Header'da API key)
|
||
curl -H "X-API-Key: demo_key_12345" \
|
||
"http://localhost:5000/?channel_id=UC9h8BDcXwkhZtnqoQJ7PggA&format=Atom"
|
||
|
||
# Channel handle ile (Header'da API key)
|
||
curl -H "X-API-Key: demo_key_12345" \
|
||
"http://localhost:5000/?channel=@tavakfi&format=Atom"
|
||
|
||
# Channel URL ile (Header'da API key)
|
||
curl -H "X-API-Key: demo_key_12345" \
|
||
"http://localhost:5000/?channel_url=https://www.youtube.com/@tavakfi&format=Atom&max_items=50"
|
||
```
|
||
|
||
**Production URL Örnekleri:**
|
||
|
||
```
|
||
# Production URL ile Channel URL kullanımı
|
||
https://yt2feed.aligundogar.com.tr/?channel_url=https://www.youtube.com/@politicalfronts&api_key=your_api_key&format=Atom
|
||
|
||
# Production URL ile Channel ID kullanımı
|
||
https://yt2feed.aligundogar.com.tr/?channel_id=UC9h8BDcXwkhZtnqoQJ7PggA&api_key=your_api_key&format=Rss&max_items=50
|
||
```
|
||
|
||
**Başarılı Yanıt:**
|
||
|
||
**Atom Format:**
|
||
```xml
|
||
<?xml version='1.0' encoding='UTF-8'?>
|
||
<feed xmlns="http://www.w3.org/2005/Atom" xml:lang="en">
|
||
<id>UC9h8BDcXwkhZtnqoQJ7PggA</id>
|
||
<title>YouTube Transcript Feed - UC9h8BDcXwkhZtnqoQJ7PggA</title>
|
||
<updated>2025-01-13T00:30:36+00:00</updated>
|
||
<link href="https://www.youtube.com/channel/UC9h8BDcXwkhZtnqoQJ7PggA"/>
|
||
<entry>
|
||
<id>r5KfWUv6wqQ</id>
|
||
<title>Video Title</title>
|
||
<content type="html">
|
||
<p>Transcript content...</p>
|
||
</content>
|
||
<link href="https://www.youtube.com/watch?v=r5KfWUv6wqQ"/>
|
||
<published>2025-01-06T14:13:57+00:00</published>
|
||
</entry>
|
||
</feed>
|
||
```
|
||
|
||
**RSS Format:**
|
||
```xml
|
||
<?xml version='1.0' encoding='UTF-8'?>
|
||
<rss version="2.0" xmlns:content="http://purl.org/rss/1.0/modules/content/">
|
||
<channel>
|
||
<title>YouTube Transcript Feed - UC9h8BDcXwkhZtnqoQJ7PggA</title>
|
||
<link>https://www.youtube.com/channel/UC9h8BDcXwkhZtnqoQJ7PggA</link>
|
||
<item>
|
||
<title>Video Title</title>
|
||
<content:encoded><![CDATA[<p>Transcript content...</p>]]></content:encoded>
|
||
<link>https://www.youtube.com/watch?v=r5KfWUv6wqQ</link>
|
||
<pubDate>Mon, 06 Jan 2025 14:13:57 +0000</pubDate>
|
||
</item>
|
||
</channel>
|
||
</rss>
|
||
```
|
||
|
||
**Hata Yanıtları:**
|
||
|
||
**400 Bad Request** - Geçersiz parametreler:
|
||
```json
|
||
{
|
||
"error": "Channel ID bulunamadı",
|
||
"usage": {
|
||
"channel_id": "UC... (YouTube Channel ID)",
|
||
"channel": "@username veya username",
|
||
"channel_url": "https://www.youtube.com/@username veya https://www.youtube.com/channel/UC...",
|
||
"format": "Atom veya Rss (varsayılan: Atom)",
|
||
"max_items": "Maksimum transcript sayısı (varsayılan: 10, maksimum: 100, 20'şer batch'ler halinde işlenir)"
|
||
}
|
||
}
|
||
```
|
||
|
||
**400 Bad Request** - Geçersiz format:
|
||
```json
|
||
{
|
||
"error": "Geçersiz channel_id formatı",
|
||
"message": "Channel ID UC ile başlayan 24 karakter olmalı"
|
||
}
|
||
```
|
||
|
||
**404 Not Found** - Henüz işlenmiş video yok:
|
||
```json
|
||
{
|
||
"error": "Henüz işlenmiş video yok",
|
||
"channel_id": "UC9h8BDcXwkhZtnqoQJ7PggA",
|
||
"message": "Lütfen birkaç dakika sonra tekrar deneyin"
|
||
}
|
||
```
|
||
|
||
**500 Internal Server Error** - Sunucu hatası:
|
||
```json
|
||
{
|
||
"error": "RSS-Bridge hatası: ...",
|
||
"channel_id": "UC9h8BDcXwkhZtnqoQJ7PggA"
|
||
}
|
||
```
|
||
|
||
---
|
||
|
||
### 2. Health Check
|
||
|
||
Servisin durumunu kontrol eder. **API key gerektirmez.**
|
||
|
||
**Endpoint:** `GET /health`
|
||
|
||
**Örnek İstek:**
|
||
|
||
```bash
|
||
curl "http://localhost:5000/health"
|
||
```
|
||
|
||
**Başarılı Yanıt:**
|
||
|
||
```json
|
||
{
|
||
"status": "ok",
|
||
"service": "YouTube Transcript RSS Feed"
|
||
}
|
||
```
|
||
|
||
**HTTP Status:** `200 OK`
|
||
|
||
---
|
||
|
||
### 3. API Bilgileri
|
||
|
||
API hakkında bilgi döner.
|
||
|
||
**Endpoint:** `GET /info`
|
||
|
||
**Örnek İstek:**
|
||
|
||
```bash
|
||
curl -H "X-API-Key: demo_key_12345" "http://localhost:5000/info"
|
||
```
|
||
|
||
**Başarılı Yanıt:**
|
||
|
||
```json
|
||
{
|
||
"service": "YouTube Transcript RSS Feed Generator",
|
||
"version": "1.0.0",
|
||
"endpoints": {
|
||
"/": "RSS Feed Generator",
|
||
"/health": "Health Check",
|
||
"/info": "API Info"
|
||
},
|
||
"usage": {
|
||
"channel_id": "UC... (YouTube Channel ID)",
|
||
"channel": "@username veya username",
|
||
"channel_url": "Full YouTube channel URL",
|
||
"format": "Atom veya Rss (varsayılan: Atom)",
|
||
"max_items": "Maksimum transcript sayısı (varsayılan: 10, maksimum: 100, 20'şer batch'ler halinde işlenir)"
|
||
},
|
||
"examples": [
|
||
"/?channel_id=UC9h8BDcXwkhZtnqoQJ7PggA&format=Atom",
|
||
"/?channel=@tavakfi&format=Rss",
|
||
"/?channel_url=https://www.youtube.com/@tavakfi&format=Atom&max_items=50"
|
||
]
|
||
}
|
||
```
|
||
|
||
**HTTP Status:** `200 OK`
|
||
|
||
---
|
||
|
||
## Response Headers
|
||
|
||
Tüm başarılı response'larda aşağıdaki header'lar bulunur:
|
||
|
||
| Header | Açıklama |
|
||
|--------|----------|
|
||
| `X-RateLimit-Remaining` | Kalan istek sayısı |
|
||
| `X-Content-Type-Options` | `nosniff` |
|
||
| `X-Frame-Options` | `DENY` |
|
||
| `X-XSS-Protection` | `1; mode=block` |
|
||
| `Content-Type` | `application/atom+xml` veya `application/rss+xml` |
|
||
|
||
## Hata Kodları
|
||
|
||
| HTTP Status | Açıklama |
|
||
|-------------|----------|
|
||
| `200 OK` | İstek başarılı |
|
||
| `400 Bad Request` | Geçersiz parametreler |
|
||
| `401 Unauthorized` | API key eksik veya geçersiz |
|
||
| `404 Not Found` | Kaynak bulunamadı |
|
||
| `429 Too Many Requests` | Rate limit aşıldı |
|
||
| `500 Internal Server Error` | Sunucu hatası |
|
||
|
||
## Input Validation
|
||
|
||
### Channel ID Formatı
|
||
|
||
- `UC` ile başlamalı
|
||
- Toplam 24 karakter
|
||
- Alfanumerik karakterler + `_` ve `-`
|
||
|
||
**Örnek:** `UC9h8BDcXwkhZtnqoQJ7PggA`
|
||
|
||
### Channel Handle Formatı
|
||
|
||
- `@` ile başlayabilir veya başlamayabilir
|
||
- Maksimum 30 karakter
|
||
- Alfanumerik karakterler + `_` ve `-`
|
||
|
||
**Örnekler:** `@tavakfi`, `tavakfi`
|
||
|
||
### Channel URL Formatı
|
||
|
||
Sadece aşağıdaki formatlar kabul edilir:
|
||
|
||
- `https://www.youtube.com/channel/UC...`
|
||
- `https://www.youtube.com/@username`
|
||
- `https://youtube.com/channel/UC...`
|
||
- `https://youtube.com/@username`
|
||
|
||
### max_items
|
||
|
||
- Tip: Integer
|
||
- Minimum: 1
|
||
- Maksimum: 100
|
||
- Varsayılan: 10
|
||
- **Batch İşleme**: 20'şer batch'ler halinde işlenir (YouTube IP blocking önleme için)
|
||
- **Veritabanı Kaydı**: Her batch işlendikten sonra hemen veritabanına kaydedilir, böylece sonraki sorgularda görülebilir
|
||
|
||
## CORS
|
||
|
||
API CORS desteği sağlar. Preflight request'ler için `OPTIONS` metodu kullanılır.
|
||
|
||
**İzin Verilen Methodlar:** `GET`, `OPTIONS`
|
||
|
||
**İzin Verilen Header'lar:** `Content-Type`, `X-API-Key`
|
||
|
||
## Örnek Kullanım Senaryoları
|
||
|
||
### 1. RSS Reader ile Kullanım
|
||
|
||
RSS reader uygulamanızda feed URL'si olarak kullanın:
|
||
|
||
**Önemli:** RSS okuyucular HTTP header gönderemediği için API key'i **mutlaka query parametresi** olarak eklemeniz gerekir.
|
||
|
||
**URL Formatı:**
|
||
```
|
||
BASE_URL/?channel_url=YOUTUBE_CHANNEL_URL&api_key=YOUR_API_KEY&format=Atom&max_items=10
|
||
```
|
||
|
||
**Örnek URL'ler (Production):**
|
||
|
||
```
|
||
# Channel URL ile (ÖNERİLEN - En kolay ve güvenilir)
|
||
https://yt2feed.aligundogar.com.tr/?channel_url=https://www.youtube.com/@politicalfronts&api_key=your_api_key&format=Atom
|
||
|
||
# Channel URL ile RSS format
|
||
https://yt2feed.aligundogar.com.tr/?channel_url=https://www.youtube.com/@politicalfronts&api_key=your_api_key&format=Rss&max_items=50
|
||
|
||
# Channel ID ile
|
||
https://yt2feed.aligundogar.com.tr/?channel_id=UC9h8BDcXwkhZtnqoQJ7PggA&api_key=your_api_key&format=Atom&max_items=20
|
||
|
||
# Channel Handle ile
|
||
https://yt2feed.aligundogar.com.tr/?channel=@tavakfi&api_key=your_api_key&format=Atom&max_items=50
|
||
|
||
# Channel URL ile (Channel ID formatında)
|
||
https://yt2feed.aligundogar.com.tr/?channel_url=https://www.youtube.com/channel/UC9h8BDcXwkhZtnqoQJ7PggA&api_key=your_api_key&format=Rss
|
||
```
|
||
|
||
**Örnek URL'ler (Localhost - Test için):**
|
||
|
||
```
|
||
# Localhost test URL'i
|
||
http://localhost:5000/?channel_url=https://www.youtube.com/@politicalfronts&api_key=demo_key_12345&format=Atom
|
||
|
||
# Localhost ile Channel ID
|
||
http://localhost:5000/?channel_id=UC9h8BDcXwkhZtnqoQJ7PggA&api_key=demo_key_12345&format=Rss&max_items=10
|
||
```
|
||
|
||
**RSS Okuyucu Adımları:**
|
||
|
||
1. RSS okuyucunuzda "Feed Ekle", "Subscribe" veya "Add Feed" seçeneğini açın
|
||
2. Feed URL alanına yukarıdaki formatlardan birini yapıştırın
|
||
3. `your_api_key` kısmını kendi API key'inizle değiştirin
|
||
4. Feed'i ekleyin ve kaydedin
|
||
|
||
**Popüler RSS Okuyucular:**
|
||
- **Feedly**: Feed URL'sini direkt yapıştırın
|
||
- **Inoreader**: "Add New" > "Feed" > URL yapıştırın
|
||
- **NewsBlur**: "Add Site" > URL yapıştırın
|
||
- **The Old Reader**: "Add Subscription" > URL yapıştırın
|
||
- **NetNewsWire**: "File" > "Add Feed" > URL yapıştırın
|
||
|
||
**Not:**
|
||
- İlk istekte transcript'ler henüz işlenmemiş olabilir. Birkaç dakika bekleyip tekrar deneyin.
|
||
- API key'inizi URL'de paylaşmayın, sadece kendi RSS okuyucunuzda kullanın.
|
||
|
||
### 2. Programatik Kullanım (Python)
|
||
|
||
```python
|
||
import requests
|
||
|
||
api_key = "your_api_key_here"
|
||
channel_id = "UC9h8BDcXwkhZtnqoQJ7PggA"
|
||
|
||
headers = {
|
||
"X-API-Key": api_key
|
||
}
|
||
|
||
response = requests.get(
|
||
f"http://localhost:5000/?channel_id={channel_id}&format=Atom",
|
||
headers=headers
|
||
)
|
||
|
||
if response.status_code == 200:
|
||
feed_content = response.text
|
||
print(feed_content)
|
||
else:
|
||
print(f"Error: {response.status_code}")
|
||
print(response.json())
|
||
```
|
||
|
||
### 3. Programatik Kullanım (JavaScript)
|
||
|
||
**URL-Based (Tarayıcı için):**
|
||
|
||
```javascript
|
||
// Tarayıcıdan kullanım - API key URL'de
|
||
const apiKey = "your_api_key_here";
|
||
const channelUrl = "https://www.youtube.com/@politicalfronts";
|
||
const feedUrl = `https://yt2feed.aligundogar.com.tr/?channel_url=${encodeURIComponent(channelUrl)}&api_key=${apiKey}&format=Atom`;
|
||
|
||
fetch(feedUrl)
|
||
.then(response => {
|
||
if (!response.ok) {
|
||
throw new Error(`HTTP error! status: ${response.status}`);
|
||
}
|
||
return response.text();
|
||
})
|
||
.then(feedContent => {
|
||
console.log(feedContent);
|
||
})
|
||
.catch(error => {
|
||
console.error("Error:", error);
|
||
});
|
||
```
|
||
|
||
**Header-Based (Node.js/Backend için):**
|
||
|
||
```javascript
|
||
const apiKey = "your_api_key_here";
|
||
const channelId = "UC9h8BDcXwkhZtnqoQJ7PggA";
|
||
|
||
fetch(`http://localhost:5000/?channel_id=${channelId}&format=Atom`, {
|
||
headers: {
|
||
"X-API-Key": apiKey
|
||
}
|
||
})
|
||
.then(response => {
|
||
if (!response.ok) {
|
||
throw new Error(`HTTP error! status: ${response.status}`);
|
||
}
|
||
return response.text();
|
||
})
|
||
.then(feedContent => {
|
||
console.log(feedContent);
|
||
})
|
||
.catch(error => {
|
||
console.error("Error:", error);
|
||
});
|
||
```
|
||
|
||
### 4. cURL ile Test
|
||
|
||
**URL-Based Sorgular (RSS Okuyucular ve Tarayıcılar için):**
|
||
|
||
```bash
|
||
# API key URL'de - Channel URL ile (ÖNERİLEN)
|
||
API_KEY="demo_key_12345"
|
||
CHANNEL_URL="https://www.youtube.com/@politicalfronts"
|
||
|
||
curl "http://localhost:5000/?channel_url=${CHANNEL_URL}&api_key=${API_KEY}&format=Atom&max_items=50"
|
||
|
||
# API key URL'de - Channel ID ile
|
||
CHANNEL_ID="UC9h8BDcXwkhZtnqoQJ7PggA"
|
||
curl "http://localhost:5000/?channel_id=${CHANNEL_ID}&api_key=${API_KEY}&format=Rss&max_items=20"
|
||
|
||
# Production URL ile
|
||
curl "https://yt2feed.aligundogar.com.tr/?channel_url=https://www.youtube.com/@politicalfronts&api_key=${API_KEY}&format=Atom"
|
||
```
|
||
|
||
**Header-Based Sorgular (Programatik Kullanım için):**
|
||
|
||
```bash
|
||
# API key header'da - Channel ID ile
|
||
API_KEY="demo_key_12345"
|
||
CHANNEL_ID="UC9h8BDcXwkhZtnqoQJ7PggA"
|
||
|
||
curl -H "X-API-Key: $API_KEY" \
|
||
"http://localhost:5000/?channel_id=$CHANNEL_ID&format=Atom&max_items=50"
|
||
|
||
# API key header'da - Channel URL ile
|
||
CHANNEL_URL="https://www.youtube.com/@tavakfi"
|
||
curl -H "X-API-Key: $API_KEY" \
|
||
"http://localhost:5000/?channel_url=${CHANNEL_URL}&format=Atom&max_items=50"
|
||
```
|
||
|
||
## Notlar
|
||
|
||
1. **İlk İstek**: İlk istekte transcript'ler henüz işlenmemiş olabilir. Birkaç dakika bekleyip tekrar deneyin.
|
||
|
||
2. **Rate Limiting**: Her API key için farklı rate limit tanımlanabilir. Limit aşıldığında 60 saniye beklemeniz gerekir.
|
||
|
||
3. **Transcript İşleme**:
|
||
- Transcript'ler 20'şer batch'ler halinde işlenir (YouTube IP blocking önleme için)
|
||
- Her batch işlendikten sonra veritabanına kaydedilir
|
||
- `max_items` parametresi ile her istekte işlenecek transcript sayısını kontrol edebilirsiniz (maksimum 100)
|
||
- Batch'ler arası 2 saniye bekleme süresi vardır
|
||
- Yeni videolar için birkaç dakika gecikme olabilir
|
||
|
||
4. **Format Seçimi**: Atom formatı daha modern ve önerilir. RSS formatı eski RSS reader'lar için uygundur.
|
||
|
||
5. **API Key Güvenliği**: API key'lerinizi güvenli tutun ve asla public repository'lere commit etmeyin.
|
||
|
||
6. **Batch İşleme Örneği**:
|
||
- `max_items=50` isteği: 20+20+10 batch'ler halinde işlenir
|
||
- Her batch tamamlandığında veritabanına kaydedilir
|
||
- Sonraki sorgularda tüm işlenmiş transcript'ler görülebilir
|
||
|
||
## Destek
|
||
|
||
Sorularınız için GitHub Issues kullanabilirsiniz.
|
||
|