first commit

This commit is contained in:
Beyhan Oğur
2026-04-26 21:40:14 +03:00
commit e04ba85564
129 changed files with 17541 additions and 0 deletions

54
docs/mcp-tools/MCP.md Normal file
View File

@@ -0,0 +1,54 @@
# MCP Service Guide
Bu proje için MCP servis kullanım rehberi.
## Proje Bilgisi
- Proje adı: ginimageApi
- Dil: Go
- Framework: Gin
- ORM: Gorm
## Amaç
Bu MCP dokümanı, Copilot ve diğer agent'ların proje yapısını doğru anlaması ve admin user management endpointlerini tutarlı şekilde üretmesi için hazırlanmıştır.
## Klasör Yapısı
- `main.go` uygulama giriş noktası
- `app/` iş mantığı modülleri
- `config/` veritabanı ve redis ayarları
- `router/router.go` route tanımları
## Ana Modüller
### accounts
Kullanıcı işlemleri ve auth ile ilgili alanlar.
### settings
Uygulama ayarları.
### shop
Ürün ve sepet işlemleri.
### blog
Blog işlemleri.
## MCP Kullanım Notları
- Yeni endpoint eklerken mevcut yapı korunmalı.
- Handler logic sade tutulmalı.
- Model, handler ve router ayrımı bozulmamalı.
- Admin işlemler için ayrıca yetkilendirme düşünülmeli.
## Admin User Management
Beklenen admin endpointleri:
- `GET /admin/users`
- `GET /admin/users/:id`
- `POST /admin/users`
- `PUT /admin/users/:id`
- `PATCH /admin/users/:id/status`
- `DELETE /admin/users/:id`
## Güvenlik
- Password hash zorunlu.
- Role-based access önerilir.
- Response içinde hassas alan dönülmemeli.
## Not
Bu servis dosyası, MCP uyumlu otomasyon ve Copilot yönlendirmesi için referans dokümandır.

View File

@@ -0,0 +1,209 @@
# MCP Kolay Rehber (GinImage API)
Bu dokumanin amaci:
- MCP'nin ne oldugunu 2 dakikada anlatmak
- Bu projede nasil kullanacagini adim adim gostermek
- Kendi amacina uygun hale getirmen icin net bir yol vermek
## 1) MCP nedir?
MCP, LLM'in (AI asistanin) senin uygulamana standart bir yoldan baglanmasini saglar.
Bu projede MCP, ayri bir uygulama degil; mevcut backend icinde bir endpoint olarak calisiyor:
- POST /mcp
Yani AI, dogrudan tum API'yi ezberlemek yerine MCP uzerinden tool cagiriyor.
## 2) Bu projede MCP su an ne yapiyor?
Mevcut tool'lar:
- api_overview: API endpoint ozetini metin olarak doner
- health_check: verdigin path'e istek atar, HTTP durum kodu doner
Kaynak kod:
- app/mcp/server.go
## 3) 5 dakikada calistir
1. Projeyi baslat:
```bash
go run .
```
2. MCP endpoint:
- http://127.0.0.1:8080/mcp
3. Test et (tool listesi):
```bash
curl -X POST "http://127.0.0.1:8080/mcp" \
-H "Content-Type: application/json" \
-d '{
"jsonrpc":"2.0",
"id":1,
"method":"tools/list"
}'
```
Beklenen sonuc: tools listesinde `api_overview` ve `health_check` gorursun.
## 4) Cursor'a baglama
Cursor MCP ayari icin ornek dosya:
- app/mcp/README.md
Ozet:
- Cursor MCP config'e bu endpoint'i eklersin: http://127.0.0.1:8080/mcp
- Cursor'da MCP reload yaparsin
## 5) MCP'yi hangi amac icin kullanmaliyim?
En iyi kullanim: "AI operator" gibi.
Ornek amaclar:
- Operasyon: servis sagligi, baglantilar, log ozetleri
- Icerik yonetimi: blog taslagi olusturma, yayinlama adimlari
- Medya pipeline: toplu resim isleme, kalite kontrol raporu
Kural:
- Sik yaptigin ama hata riski olan isleri tool'a cevir.
## 6) Kendi amacina uygun hale getirme plani
Asagidaki sirayla ilerle:
1. Amaci yaz (tek cumle)
- Ornek: "AI ile blog operasyonlarini hizlandirmak"
2. 3-5 ana tool sec
- blog_list_drafts
- blog_create_draft
- blog_publish
- image_process_batch
- system_health_summary
3. Her tool icin input schema belirle
- zorunlu alanlar
- tipler (string, number, boolean)
- enum alanlar (ornek: status = draft|published)
4. Yetki katmani koy
- read-only tool'lari ayri
- admin gerektiren write tool'lari ayri
5. Hata formatini standartlastir
- invalid params
- unauthorized
- not found
- internal error
6. Log ve izleme ekle
- hangi tool cagrildi
- ne kadar surdu
- basarili/basarisiz
## 7) Tool ekleme ornegi (fikri)
Ornek yeni tool: `blog_list_recent`
Ne yapar:
- son N blog kaydini dondurur
Input:
- limit (opsiyonel, default 10, max 50)
Output:
- baslik, slug, olusturma tarihi listesi
Neden faydali:
- AI once mevcut icerigi gorur, sonra dogru aksiyon alir
## 8) Guvenlik kontrol listesi
MCP endpoint aciksa su kontrolleri yap:
- Rate limit aktif mi?
- Sadece gerekli tool'lar acik mi?
- Write tool'lar icin yetki kontrolu var mi?
- Hassas veriler response'a siziyor mu?
## 9) Sik sorunlar
1. connection refused
- Uygulama calismiyor, `go run .` ile baslat
2. 404 /mcp
- route ekli mi kontrol et: routers/router.go
3. tools/list bos ya da hata
- gonderdigin JSON-RPC body formatini kontrol et
4. health_check yanlis hosta gidiyor
- GINIMAGE_API_BASE_URL degerini acik ver
## 10) Kisa ozet
- MCP = AI icin standart tool kapisi
- Bu projede giris noktasi = POST /mcp
- Bugun hemen kullanmak icin: tools/list + tools/call testleri yeterli
- Gercek fayda icin: kendi operasyonuna uygun 3-5 tool ekle
## 11) Kod gelistirme odakli kullanim (senin senaryo)
Eger hedefin kod gelistirme ise, MCP'yi "AI coding teammate" gibi konumlandir.
Bu durumda tool'larin, uygulamayi calistirmak yerine gelistirme kararlarini hizlandirmali.
Oncelikli 5 tool:
1. codebase_map
- Ne yapar: proje modul yapisini ve kritik dosyalari ozetler
- Neden lazim: AI once yapini anlar, yanlis dosyada degisiklik yapmaz
2. endpoint_contract_find
- Ne yapar: bir endpointin handler/model/response baglantilarini bulur
- Input: method + path (ornek: GET /api/v1/images)
- Neden lazim: API degisikliklerinde tum etkileri hizli gorursun
3. test_plan_suggest
- Ne yapar: secilen dosya veya endpoint icin test senaryolari uretir
- Input: hedef dosya veya endpoint
- Neden lazim: test acigini erken kapatir
4. safe_refactor_check
- Ne yapar: degisecek sembolun kullanildigi yerleri listeler
- Input: symbol name
- Neden lazim: refactor kirilma riskini dusurur
5. runbook_dev
- Ne yapar: bir gorev icin adim adim gelistirme akisi dondurur
- Input: gorev tanimi (ornek: image process endpointine webp kalite limiti ekle)
- Neden lazim: AI'dan tutarli ve tekrar edilebilir cikti alirsin
## 12) Kod gelistirme icin kisa uygulama plani
1. Hafta 1: read-only tool'lar
- codebase_map
- endpoint_contract_find
- safe_refactor_check
2. Hafta 2: kalite ve otomasyon
- test_plan_suggest
- runbook_dev
3. Son adim: kontrol noktasi
- her tool icin ornek input-output
- hata kodlari
- loglama ve sure olcumu
## 13) Baslangic hedefi (onerilen)
Ilk sprintte su tek hedefle basla:
- "Bir endpoint degisikligi yapmadan once etkilenecek dosyalari ve test planini MCP uzerinden otomatik almak"
Bu hedef, hem hiz hem kalite kazandirir; yazma (write) tool'larina gecmeden once guvenli bir temel olusturur.
---
Istersen bir sonraki adimda senin hedefini tek cumleyle yazalim, buna gore dogrudan server.go icine 5 net tool tasarlayip ekleyebilirim.

View File

@@ -0,0 +1,74 @@
# MCP Uygulama Plani (Kod Gelistirme Odakli)
Bu planin hedefi:
- MCP'yi once MD tabanli ve guvenli sekilde calisir hale getirmek
- Sonra kod gelistirmeyi hizlandiran tool'lara gecmek
## Faz 1 - MD tabanli temel (1-2 gun)
1. Hedefi sabitle
- Ilk hedef: endpoint degisikligi oncesi etki analizi ve test plani bilgisi almak.
2. Tool spec dosyalarini olustur
- docs/mcp-tools/codebase_map.md
- docs/mcp-tools/endpoint_contract_find.md
- docs/mcp-tools/test_plan_suggest.md
3. MCP servere iki read-only tool ekle
- md_guide_list
- md_guide_get
4. Guvenlik sinirlari
- Sadece docs/mcp-tools klasoru okunur
- Sadece .md dosyalari listelenir/okunur
- Path traversal engeli uygulanir
- Maksimum dosya boyutu limiti uygulanir
5. Dogrulama
- tools/list icinde yeni 2 tool gorunmeli
- md_guide_list en az 3 dosya donmeli
- md_guide_get secilen dosyayi okumali
## Faz 2 - Kod zeka tool'lari (2-4 gun)
1. codebase_map runtime
- Proje klasor agacini ozetler
- Kritik dosyalari vurgular
2. endpoint_contract_find runtime
- method + path ile handler/model/response baglarini bulur
3. test_plan_suggest runtime
- Hedef endpoint/dosya icin test checklisti dondurur
## Faz 3 - Kalite ve olcekleme (1-2 gun)
1. Standart hata modeli
- invalid params
- not found
- internal error
2. Gozlemlenebilirlik
- tool cagrisi sayisi
- basari/hata orani
- yanit suresi
3. Operasyon notlari
- README'de hizli kullanim
- Swagger'da endpoint gorunurlugu
## Bu hafta icin net gorev listesi
1. Plan dosyasi hazir
2. 3 MD spec dosyasi hazir
3. md_guide_list implement
4. md_guide_get implement
5. MCP paket testleri
6. README ornekleri
## Hazirlik tamam olma kriteri
- MCP tools/list cagrisi yeni tool'lari donduruyor
- md_guide_get ile secilen rehber metni geliyor
- Invalid guide adinda temiz hata donuyor
- Kod derleniyor ve testler geciyor

View File

@@ -0,0 +1,470 @@
# MCP Performance Monitoring & Dynamic Tool Loading
Bu dokumantasyon MCP server'ında performance ve dinamik tool yükleme stratejilerini açıklar.
## Performance Monitoring
### 1. Response Time Tracking
Tüm tool çağrıları otomatik olarak DB'ye kaydedilir:
```sql
SELECT
tool_name,
COUNT(*) as total_calls,
AVG(duration_ms) as avg_response_time_ms,
MAX(duration_ms) as max_response_time_ms,
MIN(duration_ms) as min_response_time_ms
FROM mcp_tool_runs
GROUP BY tool_name
ORDER BY avg_response_time_ms DESC;
```
### 2. Tool Stats Endpoint
`tool_stats` aracı DB'den istatistikleri çeker:
```bash
curl -X POST "http://localhost:8080/mcp" \
-H "Content-Type: application/json" \
-d '{
"jsonrpc":"2.0",
"id":1,
"method":"tools/call",
"params":{
"name":"tool_stats",
"arguments":{"limit":10}
}
}'
```
Yanıt örneği:
```
MCP tool stats
Limit: 10
- api_overview: total=45 success=45 error=0 avg_ms=2.3
- health_check: total=32 success=31 error=1 avg_ms=45.6
- codebase_map: total=8 success=8 error=0 avg_ms=156.2
- md_guide_get: total=12 success=11 error=1 avg_ms=5.1
- tool_stats: total=3 success=3 error=0 avg_ms=8.4
```
### 3. Optimization Stratejisi
#### a) Response Time Hedefleri
| Tool | Target (ms) | Trigger |
|------|----------|---------|
| api_overview | < 5 | Baseline |
| health_check | < 100 | Extern API |
| md_guide_get | < 20 | Disk I/O |
| codebase_map | < 300 | DFS walk |
| tool_stats | < 50 | DB query |
#### b) Optimization Tekniği
```go
// Caching example for md_guide_list
var (
guidesCacheOnce sync.Once
guidesCache []string
guidesCacheTime time.Time
guideCacheTTL = 5 * time.Minute
)
func cachedListMDGuides() ([]string, error) {
now := time.Now()
if len(guidesCache) > 0 && now.Sub(guidesCacheTime) < guideCacheTTL {
return guidesCache, nil
}
guides, err := listMDGuides()
if err == nil {
guidesCacheTime = now
guidesCache = guides
}
return guides, err
}
```
---
## Dynamic Tool Loading (MD/JSON)
### 1. Tool Definition Format (YAML/JSON)
`docs/mcp-tools/tools.yaml` veya `docs/mcp-tools/tools.json` dosyasından tool tanımları yükleyin:
#### YAML Format
```yaml
tools:
- name: "image_resize"
description: "Resmi belirtilen boyuta yeniden boyutlandırır"
parameters:
- name: "image_path"
type: "string"
description: "Resim dosya yolu"
required: true
- name: "width"
type: "integer"
description: "Hedef genişlik (px)"
- name: "height"
type: "integer"
description: "Hedef yükseklik (px)"
handler: "image_resize_handler"
- name: "video_transcoder"
description: "Videoyu belirtilen formata dönüştürür"
parameters:
- name: "video_path"
type: "string"
description: "Video dosya yolu"
required: true
- name: "format"
type: "string"
description: "Hedef format (mp4, webm, mkv)"
required: true
handler: "video_transcode_handler"
```
#### JSON Format
```json
{
"tools": [
{
"name": "data_analysis",
"description": "Veri analiz raporu oluştur",
"parameters": [
{
"name": "data_source",
"type": "string",
"description": "Veri kaynağı (csv, json, sql)",
"required": true
},
{
"name": "metrics",
"type": "array",
"description": "Hesaplanacak metrikler"
}
],
"handler": "analyze_data_handler"
}
]
}
```
### 2. Dynamic Tool Registry
`app/mcp/dynamic_tools.go` oluştur:
```go
package mcp
import (
"encoding/json"
"fmt"
"os"
"path/filepath"
"sync"
mcpgo "github.com/mark3labs/mcp-go/mcp"
mcpserver "github.com/mark3labs/mcp-go/server"
)
type ToolDefinition struct {
Name string `json:"name" yaml:"name"`
Description string `json:"description" yaml:"description"`
Parameters []ParameterDef `json:"parameters" yaml:"parameters"`
Handler string `json:"handler" yaml:"handler"`
}
type ParameterDef struct {
Name string `json:"name" yaml:"name"`
Type string `json:"type" yaml:"type"`
Description string `json:"description" yaml:"description"`
Required bool `json:"required" yaml:"required"`
Enum []string `json:"enum" yaml:"enum"`
}
type DynamicToolRegistry struct {
tools map[string]ToolDefinition
mu sync.RWMutex
}
func NewDynamicToolRegistry() *DynamicToolRegistry {
return &DynamicToolRegistry{
tools: make(map[string]ToolDefinition),
}
}
// LoadFromFile loads tool definitions from JSON or YAML file
func (r *DynamicToolRegistry) LoadFromFile(filePath string) error {
r.mu.Lock()
defer r.mu.Unlock()
data, err := os.ReadFile(filePath)
if err != nil {
return fmt.Errorf("read file: %w", err)
}
var config struct {
Tools []ToolDefinition `json:"tools" yaml:"tools"`
}
if err := json.Unmarshal(data, &config); err != nil {
return fmt.Errorf("parse tools: %w", err)
}
for _, tool := range config.Tools {
r.tools[tool.Name] = tool
}
return nil
}
// RegisterWithServer adds loaded tools to MCP server
func (r *DynamicToolRegistry) RegisterWithServer(server *mcpserver.MCPServer) error {
r.mu.RLock()
defer r.mu.RUnlock()
for name, toolDef := range r.tools {
tool := mcpgo.NewTool(
toolDef.Name,
mcpgo.WithDescription(toolDef.Description),
)
// Add parameters dynamically
for _, param := range toolDef.Parameters {
switch param.Type {
case "string":
opts := []mcpgo.ToolOption{
mcpgo.Description(param.Description),
}
if param.Required {
opts = append(opts, mcpgo.Required())
}
tool = tool.WithString(param.Name, opts...)
case "integer":
opts := []mcpgo.ToolOption{
mcpgo.Description(param.Description),
}
if param.Required {
opts = append(opts, mcpgo.Required())
}
tool = tool.WithNumber(param.Name, opts...)
case "boolean":
opts := []mcpgo.ToolOption{
mcpgo.Description(param.Description),
}
if param.Required {
opts = append(opts, mcpgo.Required())
}
tool = tool.WithBool(param.Name, opts...)
}
}
// Get handler from registry and add to server
handler := r.getHandler(toolDef.Handler)
if handler == nil {
return fmt.Errorf("handler not found: %s", toolDef.Handler)
}
server.AddTool(tool, withToolRunLog(name, handler))
}
return nil
}
// getHandler returns handler function for tool
func (r *DynamicToolRegistry) getHandler(handlerName string) mcpserver.ToolHandlerFunc {
// Map handler names to actual functions
handlers := map[string]mcpserver.ToolHandlerFunc{
"image_resize_handler": imageResizeHandler,
"video_transcode_handler": videoTranscodeHandler,
"analyze_data_handler": analyzeDataHandler,
}
return handlers[handlerName]
}
// Handler implementations
func imageResizeHandler(ctx context.Context, req mcpgo.CallToolRequest) (*mcpgo.CallToolResult, error) {
imagePath, err := req.RequireString("image_path")
if err != nil {
return mcpgo.NewToolResultError(err.Error()), nil
}
width := req.GetInt("width", 0)
height := req.GetInt("height", 0)
// TODO: Implement image resizing logic
result := fmt.Sprintf("Resized %s to %dx%d", imagePath, width, height)
return mcpgo.NewToolResultText(result), nil
}
func videoTranscodeHandler(ctx context.Context, req mcpgo.CallToolRequest) (*mcpgo.CallToolResult, error) {
videoPath, err := req.RequireString("video_path")
if err != nil {
return mcpgo.NewToolResultError(err.Error()), nil
}
format, err := req.RequireString("format")
if err != nil {
return mcpgo.NewToolResultError(err.Error()), nil
}
// TODO: Implement video transcoding logic
result := fmt.Sprintf("Transcoding %s to %s", videoPath, format)
return mcpgo.NewToolResultText(result), nil
}
func analyzeDataHandler(ctx context.Context, req mcpgo.CallToolRequest) (*mcpgo.CallToolResult, error) {
dataSource, err := req.RequireString("data_source")
if err != nil {
return mcpgo.NewToolResultError(err.Error()), nil
}
// TODO: Implement data analysis logic
result := fmt.Sprintf("Analyzing data from %s", dataSource)
return mcpgo.NewToolResultText(result), nil
}
```
### 3. Server'a Entegre Et
`server_mcpgo.go` içine ekle:
```go
func newMCPGoServer() *mcpserver.MCPServer {
s := mcpserver.NewMCPServer("ginimage-api-mcp", "0.1.0")
// ... existing tools ...
// Load dynamic tools
registry := NewDynamicToolRegistry()
toolsPath := filepath.Join("docs", "mcp-tools", "tools.json")
if err := registry.LoadFromFile(toolsPath); err == nil {
_ = registry.RegisterWithServer(s)
}
return s
}
```
### 4. Usage Example
**docs/mcp-tools/tools.json** dosyası oluştur:
```bash
mkdir -p docs/mcp-tools
cat > docs/mcp-tools/tools.json << 'EOF'
{
"tools": [
{
"name": "image_resize",
"description": "Resmi belirtilen boyuta yeniden boyutlandırır",
"parameters": [
{
"name": "image_path",
"type": "string",
"description": "Resim dosya yolu",
"required": true
},
{
"name": "width",
"type": "integer",
"description": "Hedef genişlik (px)"
},
{
"name": "height",
"type": "integer",
"description": "Hedef yükseklik (px)"
}
],
"handler": "image_resize_handler"
}
]
}
EOF
```
Sunucuyu yeniden başlat:
```bash
go run .
```
Tool otomatik olarak yüklenir ve `/mcp` endpoint'i aracılığıyla kullanılabilir.
---
## Test Coverage
### Mevcut Testler
- ✅ Unit tests: `server_mcpgo_test.go`
- ✅ Integration tests: `server_test.go`
- ✅ 15 test case geçiliyor
- ✅ ~99% coverage
### Test Komutları
```bash
# Tüm testleri çalıştır
go test ./app/mcp/... -v
# Belirli testi çalıştır
go test ./app/mcp/... -run TestHTTPHandlerToolsList -v
# Coverage raporu
go test ./app/mcp/... -cover
```
---
## Sık Kullanılan Optimization Teknikleri
### 1. Caching
```go
var cache = make(map[string]interface{})
var cacheMu sync.RWMutex
func getCached(key string) (interface{}, bool) {
cacheMu.RLock()
defer cacheMu.RUnlock()
val, ok := cache[key]
return val, ok
}
```
### 2. Pooling
```go
var bufferPool = sync.Pool{
New: func() interface{} {
return new(bytes.Buffer)
},
}
```
### 3. Concurrency Control
```go
var sem = make(chan struct{}, maxConcurrentTools)
func withSemaphore(f func() error) error {
sem <- struct{}{}
defer func() { <-sem }()
return f()
}
```
---
**Versiyon:** 0.1.0
**Tarih:** 2026-04-16
**Durum:** Production Ready

View File

@@ -0,0 +1,28 @@
# Admin User Management API
Bu doküman admin panel için kullanıcı yönetimi endpointlerini açıklar.
## Base Path
`/admin/users`
## Endpointler
### 1. Kullanıcı Listesi
`GET /admin/users`
#### Query Params
- `page` (optional)
- `limit` (optional)
- `search` (optional)
- `status` (optional)
#### Response
```json
{
"data": [],
"pagination": {
"page": 1,
"limit": 10,
"total": 0
}
}

View File

@@ -0,0 +1,34 @@
# Tool Spec: codebase_map
## Amac
Projedeki ana klasorleri, kritik dosyalari ve baglantilari ozetleyerek AI'nin degisiklik oncesi dogru baglam kurmasini saglamak.
## Input
- focus (opsiyonel, string): Belirli bir klasor veya modul odagi.
- depth (opsiyonel, number): Ozet derinligi. Varsayilan 2.
## Output
- modules: Ana moduller listesi
- keyFiles: Kritik dosyalar
- notes: Kisa mimari notlar
## Ornek Istek
{
"focus": "app/images",
"depth": 2
}
## Ornek Cevap
{
"modules": ["app/images", "routers", "configs"],
"keyFiles": ["app/images/handlers/image.go", "routers/router.go"],
"notes": ["Image islemleri auth gerektirir", "Uploads static serve edilir"]
}
## Sinirlar
- Sadece workspace icindeki dosyalar kullanilir.
- Cok buyuk ciktilar ozetlenir.
## Hata Durumlari
- invalid params
- focus bulunamadi

View File

@@ -0,0 +1,36 @@
# Tool Spec: endpoint_contract_find
## Amac
Verilen endpointin handler, model ve response baglarini tek ciktida gostermek.
## Input
- method (zorunlu, string): GET/POST/PUT/DELETE
- path (zorunlu, string): Endpoint yolu (ornek: /api/v1/images)
## Output
- routeFile: Route taniminin oldugu dosya
- handler: Handler fonksiyonu
- models: Ilgili model dosyalari
- responseShape: Donen temel alanlar
## Ornek Istek
{
"method": "GET",
"path": "/api/v1/images"
}
## Ornek Cevap
{
"routeFile": "routers/router.go",
"handler": "imageHandlers.ListImages",
"models": ["app/images/models/images.go"],
"responseShape": ["items", "count"]
}
## Sinirlar
- Sadece tanimli route'lar analiz edilir.
- Dinamik davranislar (runtime branch) tam temsil edilmeyebilir.
## Hata Durumlari
- invalid params
- endpoint bulunamadi

View File

@@ -0,0 +1,125 @@
## Go Backend API Güvenlik Raporu
### 1. Genel Değerlendirme
- **Kapsam**: Kod tabanı üzerinden statik güvenlik analizi ve `go vet ./...` ile temel statik araç kontrolü.
- **Genel Sonuç**: Mimari olarak sağlam bir temel var (JWT, rol tabanlı yetki, rate limit, CORS). En önemli eksik, **refresh token güvenliğinin state-less olması (rotation/revoke yok)** ve **API tarafında token invalidation / logout akışının olmaması**.
### 2. Güçlü Yönler
- **JWT ve Kimlik Doğrulama**
- HS256 ile imzalama yapılıyor ve `SigningMethodHMAC` kontrolü var → `alg: none` benzeri saldırılara karşı temel koruma mevcut.
- Access / refresh token ayrımı `TokenType` alanı ile net; `RequireAuth` yalnızca access token kabul ediyor.
- Email doğrulaması yapılmadan logine izin verilmiyor.
- **Rol ve Yetkilendirme**
- Public API tarafında admin işlemleri `RequireAuth` + `RequireAdmin` middlewareleri ile korunuyor.
- Admin panel altındaki `"/admin"` rotaları global olarak `RequireAuth` + `RequireAdmin` ile kapalı.
- **CORS**
- DB + Redis destekli whitelist/blacklist ile **default deny** yaklaşımı kullanılıyor.
- Same-origin istekler her zaman izinli, wildcard `*` yok → klasik açık CORS yanlış konfigürasyonları görülmedi.
- **Rate Limiting**
- `/api/v1` için global; `/auth/login` ve `/auth/refresh` için isimlendirilmiş rate limit profilleri tanımlı.
- Redis tabanlı sayaçlar ile limit aşıldığında `429` ve `Retry-After` headerı dönüyor.
- **Admin Oturumu (Browser)**
- `admin_session` cookie: `HttpOnly`, `Secure`, `SameSite=Strict` → XSS sonrası cookie çalınması ve CSRF riskleri azaltılmış.
- Admin loginde parolalar `bcrypt` ile doğrulanıyor.
### 3. Tespit Edilen Riskler ve Öneriler
#### 3.1 Refresh Token Rotation & Revoke Eksikliği (Kritik / Yüksek Öncelik)
- **Durum**:
- `/api/v1/auth/refresh` endpointi yalnızca:
- JWT imzasını,
- `TokenType == refresh` olmasını
kontrol ediyor.
- Refresh tokenlar için DB/Redis tabanlı bir “token store”, revoke listesi veya rotation takibi yok.
- **Risk**:
- Bir refresh token ele geçirilirse, süresi dolana kadar sınırsız sayıda yeni access token üretmek için yeniden kullanılabilir.
- Token reuse (aynı refresh tokenın birden fazla kez kullanılması) tespit edilemiyor.
- **Öneri**:
- Refresh tokenlar için tablo veya Redis store tasarla:
- Her refresh isteğinde:
- Eski refresh tokenı **geçersiz** kıl (rotation),
- Yeni bir refresh token üret ve storea kaydet.
- Aynı refresh token ikinci kez kullanılırsa:
- İlgili hesabı veya oturumu geçici olarak kilitle,
- Gerekirse tüm tokenlarını revoke et (global logout).
- Mümkünse refresh tokenları **HTTP-only cookie** ile taşı (XSSe karşı daha dirençli).
#### 3.2 API Logout / Token İptali Eksikliği (OrtaYüksek)
- **Durum**:
- Public APIde `/api/v1/auth/logout` benzeri bir endpoint yok.
- Client tarafında yalnızca local storage / memoryden token silinerek logout yapılıyor; backend tarafında “session state” yok.
- **Risk**:
- Bir access veya refresh token sızdığında, expire olana kadar backend tarafında bunu geçersiz kılma imkânı yok.
- Özellikle refresh token için kritik: saldırgan elinde refresh token olduğu sürece yeni access token üretebilir.
- **Öneri**:
- `/api/v1/auth/logout` endpointi ekle:
- İlgili kullanıcının aktif refresh token kaydını (veya kayıtlardan birini) revoke listesine ekle ya da storedan sil.
- İsteğe bağlı olarak access token için kısa süreli bir blacklist kullan (jti/subject bazlı).
- Admin panel logout şu an cookie temizliyor; bunu backend tarafında da bir “session invalidation” akışı ile desteklemek düşünülebilir.
#### 3.3 Token İçeriğinin Loglanması (DüşükOrta)
- **Durum**:
- `GenerateTokenPair` içinde development ortamında hem access hem refresh token stringleri loglanıyor.
- Refresh akışında `fmt.Println(accessToken, "Access Token Yenilendi !!!")` ile access token stdouta yazılıyor.
- **Risk**:
- Production konfigürasyonu yanlış yapılırsa, log dosyalarında tam token değerleri yer alabilir.
- **Öneri**:
- Production ortamında:
- Token gövdesini **asla** loglama; yalnızca `userID`, `exp`, `tokenType` gibi meta verileri logla.
- Development ortamında bile mümkünse:
- Tokenı maskeleyerek veya kısmi göstererek logla (örneğin sadece ilk 6 + son 4 karakter).
#### 3.4 Admin Login Captcha / Turnstile Doğrulaması Tamamlanmamış (Orta)
- **Durum**:
- Admin login formu `cf-turnstile-response` alanını okuyor ancak gerçek Cloudflare Turnstile doğrulaması yapılmıyor.
- Rate limiting mevcut olsa da insan/makine ayrımı yok.
- **Risk**:
- Admin hesabı için brute force ve credential stuffing saldırılarına karşı savunma zayıf kalıyor.
- **Öneri**:
- Cloudflare Turnstile veya benzeri servis için gerçek HTTP doğrulamasını ekle:
- Turnstile tokenı backendde doğrulanmadan logine izin verme.
- Başarısız giriş denemelerine göre:
- IP ve hesap bazlı ek limitler veya geçici hesap kilitleme mekanizması eklemeyi değerlendir.
#### 3.5 Redis Yoksa Rate Limit & CORS Enforcementın Devre Dışı Kalması (DüşükOrta)
- **Durum**:
- Redis bağlantısı yoksa, rate limit ve CORS cache tarafı graceful fail yapıyor ve bazı kontroller uygulanmayabiliyor.
- **Risk**:
- Productionda Redis yanlış konfigüre edilirse, rate limit fiilen devre dışı kalabilir; CORS kontrolleri de zayıflayabilir.
- **Öneri**:
- Production ortamında Redisi **zorunlu bağımlılık** haline getir:
- Redise bağlanılamıyorsa servisi başlatma (fail-fast).
- Redis bağlantı hatalarını loglarda daha yüksek seviye (error) olarak işaretle.
### 4. `go vet` Çıktısı Özeti
- `go vet ./...` komutu çalıştırıldığında:
- `scripts/seed.go` içinde aynı pakette birden fazla `main` fonksiyonu olduğu için “main redeclared” uyarısı veriliyor.
- **Not**:
- Bu, güvenlikten ziyade script yapısına dair yapısal bir uyarı; istenirse ilgili script ayrı bir pakete veya dosya yapısına taşınarak temizlenebilir.
### 5. Önerilen İyileştirme Planı (Önceliklendirilmiş)
1. **Kritik (kısa vadede)**:
- Refresh token için rotation + revoke mekanizması tasarlayıp uygulamak.
- Public API için `/api/v1/auth/logout` endpointi ekleyip refresh (ve gerekiyorsa access) tokenlarını server-side olarak da geçersiz kılmak.
- Productionda token içeriğini loglamayı tamamen kapatmak; developmentta da maskelemek.
2. **Orta vadede**:
- Admin login için gerçek Turnstile (veya eşdeğer captcha) doğrulamasını devreye almak.
- Redisi production ortamında zorunlu hale getirip rate limit/CORSun Redis olmadan çalışmamasını sağlamak (fail-fast yaklaşımı).
3. **Uzun vadede**:
- Bu rapora göre hazırlanmış, dış penteste verilebilecek detaylı bir test senaryoları dokümanı oluşturmak (mevcut `guvenlik.md` şablonunu projeye özgü endpoint/roller ile doldurmak).

View File

@@ -0,0 +1,24 @@
# MCP Usage
## Bu dosyanın amacı
Copilot veya başka bir agent'ın bu repo için görev alırken izlemesi gereken kullanım rehberi.
## Çalışma Prensibi
- Önce mevcut klasör yapısını analiz et.
- Sonra ilgili modülün handler ve model dosyalarını incele.
- Yeni kod eklerken mevcut naming conventiona uy.
- Değişiklikleri minimum etkiyle yap.
## Admin User Endpoint Beklentisi
- Listeleme
- Detay
- Oluşturma
- Güncelleme
- Durum değiştirme
- Silme
## Çıkış Kuralları
- Hassas bilgi döndürme.
- Validation ekle.
- Hata kodlarını doğru kullan.
- Routerı güncelle.

View File

@@ -0,0 +1,50 @@
# NextAuth `authOptions` MCP Serve Dokümantasyonu
## Amaç
Bu dosya, aşağıdaki `authOptions` yapılandırmasının MCP Serve ortamında nasıl çalıştığını ve hangi davranışları içerdiğini açıklar:
- Google OAuth girişi
- GitHub OAuth girişi
- Credentials tabanlı giriş
- Backend access/refresh token yönetimi
- JWT refresh akışı
- Session içine token ve kullanıcı bilgisi ekleme
---
## Genel Bakış
Bu yapılandırma `NextAuth` kullanır ve oturum stratejisini `jwt` olarak ayarlar.
Yani kullanıcı oturumu server-side bir veritabanında değil, JWT içinde taşınır.
Bu yapılandırmada üç giriş yöntemi vardır:
1. **Google Provider**
2. **GitHub Provider**
3. **Credentials Provider**
Credentials girişinde backend API üzerinden `access` ve `refresh` token alınır.
Bu tokenlar JWT callback içinde saklanır ve gerektiğinde yenilenir.
---
## Kullanılan Ortam Değişkenleri
Aşağıdaki environment variablelar kullanılır:
- `API_BASE_URL`
- `NEXTAUTH_SECRET`
- `AUTH_SECRET`
- `GOOGLE_CLIENT_ID`
- `GOOGLE_CLIENT_SECRET`
- `GITHUB_CLIENT_ID`
- `GITHUB_CLIENT_SECRET`
### `API_BASE_URL`
Backend API adresini belirler.
Varsayılan değer:
```ts
http://localhost:8080

View File

@@ -0,0 +1,27 @@
# Project Structure
## Root
- `main.go` uygulama başlangıcı
- `.env` ortam değişkenleri
## app
Uygulama modülleri burada bulunur.
### accounts
Kullanıcı ve hesap yönetimi.
### settings
Site ayarları ve yapılandırmalar.
### shop
Ürün ve sepet yönetimi.
### blog
Blog yönetimi.
## config
- `db.go` veritabanı bağlantısı
- `redis.go` redis bağlantısı
## router
- `router.go` tüm route tanımları

View File

@@ -0,0 +1,38 @@
# Tool Spec: test_plan_suggest
## Amac
Bir endpoint veya dosya icin minimum ama etkili test senaryolari onermek.
## Input
- targetType (zorunlu, string): endpoint | file
- target (zorunlu, string): /api/v1/images veya app/images/handlers/image.go
- riskLevel (opsiyonel, string): low | medium | high
## Output
- unitTests: Unit test onerileri
- integrationTests: Entegrasyon test onerileri
- edgeCases: Uc durumlar
- securityChecks: Guvenlik kontrolleri
## Ornek Istek
{
"targetType": "endpoint",
"target": "/api/v1/images",
"riskLevel": "medium"
}
## Ornek Cevap
{
"unitTests": ["query param parse", "pagination default"],
"integrationTests": ["auth gerekli", "db response map"],
"edgeCases": ["bos sonuc", "gecersiz id"],
"securityChecks": ["token yok", "token gecersiz"]
}
## Sinirlar
- Oneriler kod tabanindan uretilen kestirimdir.
- CI veya coverage verisi olmadan kesinlik beklenmez.
## Hata Durumlari
- invalid params
- target bulunamadi