
Son zamanlarda nereye baksam MCP. Herkes MCP server yazıyor, herkes MCP entegrasyonu geliştiriyor. LinkedIn'e girince insan, MCP'den önce yapay zekanın dış dünyayla hiç konuşamadığını sanıyor.
Pazarlama tarafı ise ayrı bir dünya. Dün REST API geliştiren arkadaş bugün aynı endpoint'leri MCP üzerinden sunuyor ve adına "AI-native architecture" diyor. Altına iki kişi "Game changer!" yazınca da devrim tamamlanmış oluyor.
Peki MCP gerçekten bu kadar büyük bir olay mı, yoksa yine zaten yaptığımız bir işe yeni bir isim mi bulduk?
Önce şu MCP neymiş, ona bakalım
MCP (Model Context Protocol), yapay zeka uygulamalarının dış sistemlerdeki verilere ve araçlara standart bir yolla erişmesini sağlayan açık bir protokol.
Bir örnekle gidelim. Asistanınıza "Azure DevOps'taki son başarısız pipeline'ları listele" dediniz. Modelin bu bilgiye ulaşması için Azure DevOps'la konuşması lazım. Azure DevOps'un da bunun için zaten REST API'si var.
MCP olmadan akış şöyle:
Kullanıcı → Yapay Zeka → Function Calling → REST API → Azure DevOps
MCP ile şöyle:
Kullanıcı → Yapay Zeka → MCP Client → MCP Server → REST API → Azure DevOps
Araya bir katman daha koyduk. Teknoloji dünyası olarak yine rahat durmadık.
Şaka bir yana, MCP sadece API çağırmaktan ibaret değil. Hangi araçların olduğunu ve hangi parametreleri aldıklarını tanımlıyor, veri kaynakları ve hazır prompt'lar da sunabiliyor. Ama sahada gördüğüm MCP entegrasyonlarının çoğu, mevcut bir API'ye istek atan adaptörlerden oluşuyor.
Bunu görmenin en kolay yolu koda bakmak. Python SDK'sıyla yazılmış küçük bir MCP server:
# server.py
import os
import httpx
from mcp.server.fastmcp import FastMCP
mcp = FastMCP("azure-devops")
ORG = os.environ["AZDO_ORG"]
PAT = os.environ["AZDO_PAT"]
@mcp.tool()
def list_failed_builds(project: str, top: int = 5) -> list[dict]:
"""Projedeki son başarısız build'leri listeler."""
r = httpx.get(
f"https://dev.azure.com/{ORG}/{project}/_apis/build/builds",
params={"resultFilter": "failed", "$top": top, "api-version": "7.1"},
auth=("", PAT),
)
r.raise_for_status()
return [
{"pipeline": b["definition"]["name"], "build": b["buildNumber"]}
for b in r.json()["value"]
]
if __name__ == "__main__":
mcp.run() # varsayılan olarak stdio üzerinden çalışır
Ortada bildiğimiz bir httpx.get var. Fonksiyonun docstring'i aracın açıklaması oluyor, tip ipuçları da parametre şeması. SDK bunları JSON Schema'ya kendisi çeviriyor.
Bu server'ı Claude ya da Cursor gibi bir istemciye bağlayabilirsiniz. İstemci tarafında ne olduğunu görmek isterseniz de kısa bir client yeterli:
# client.py
import asyncio
from mcp import ClientSession, StdioServerParameters
from mcp.client.stdio import stdio_client
async def main():
params = StdioServerParameters(command="python", args=["server.py"])
async with stdio_client(params) as (read, write):
async with ClientSession(read, write) as session:
await session.initialize()
# Server hangi araçları sunuyor?
tools = await session.list_tools()
for t in tools.tools:
print(t.name, "→", t.inputSchema)
# Aracı çağır
result = await session.call_tool(
"list_failed_builds", {"project": "Ecommerce", "top": 3}
)
print(result.content)
asyncio.run(main())
Gerçek bir asistanda list_tools çıktısı modele verilir. Model hangi aracı hangi parametreyle çağıracağına karar verir, istemci de bunu call_tool ile server'a iletir. Sonuç tekrar modele döner.
Yani daha önce yapılamayan bir şey yapmıyoruz. Zaten yapılan bir işi yeni bir standartla yapıyoruz.
E iyi de API zaten bunu yapmıyor muydu?
Yapıyordu. Hem de yıllardır.
Jira'da issue açmak, GitLab'de merge request oluşturmak, Kubernetes'te pod listelemek, Azure DevOps'ta pipeline tetiklemek... Bunların hiçbiri hayatımıza MCP ile girmedi.
Bu işleri yapay zekaya yaptırmak için de MCP şart değil. Function calling ile API'lerinizi modele tanıtmanız yetiyor. Endpoint'lerin ne yaptığını, hangi parametreleri alıp ne döndürdüğünü OpenAPI/Swagger ile zaten yıllardır tarif ediyoruz. Bu tanımlardan otomatik olarak AI aracı üretmek de mümkün.
Buna rağmen REST API eski dünyanın, MCP de yapay zeka çağının teknolojisiymiş gibi anlatılıyor. Oysa model de sonuçta bir yazılımın içinde çalışıyor. Dışarıda bir iş yapması gerektiğinde bir araç çağırıyor, o araç da çoğu zaman gidip bir HTTP isteği atıyor. Yukarıdaki kodda olduğu gibi.
MCP kullanınca model daha akıllı olmuyor. Daha iyi kod yazmıyor, Kubernetes'i birden daha iyi yönetmeye başlamıyor. Araçlara erişmek için standart bir yol kullanıyor, o kadar.
Peki MCP gereksiz mi?
Hayır. Gayet iyi çözdüğü bir problem var: standartlaşma.
Şirketinizde 20 farklı servis olduğunu düşünün. Azure DevOps, Jira, GitLab, SonarQube, Kubernetes, Artifactory ve bir sürü iç mikroservis. Bunları ChatGPT, Claude, Cursor ve kendi asistanınızla kullanmak istiyorsunuz. Her istemci için ayrı entegrasyon yazıp araç tanımlarını ayrı ayrı güncel tutmak bir süre sonra yorucu olur.
MCP burada ortak bir dil sunuyor. Bir server yazıyorsunuz, MCP destekleyen her istemci araçları keşfedip çağırabiliyor:
Azure DevOps MCP Server
├── list_pipelines
├── get_build_status
├── create_work_item
├── trigger_pipeline
└── list_pull_requests
Güzel mi? Güzel. İşe yarıyor mu? Evet. Devrim mi? Orası tartışılır.
MCP'yi USB-C'ye benzetebiliriz. USB-C kullanınca bilgisayarınız hızlanmıyor, ama her cihaz için ayrı kablo taşımıyorsunuz. MCP de buna benziyor.
Araçların otomatik keşfi, standart parametre şemaları ve istemciler arası taşınabilirlik gerçekten değerli. Ama bunlar entegrasyonu kolaylaştıran şeyler. Yapay zekanın daha önce yapamadığı bir işi yapmaya başlaması değil.
MCP her sorunu çözmüyor
MCP kullanınca sisteminiz kendiliğinden daha güvenli, daha hızlı ya da daha akıllı olmuyor. Kötü tasarlanmış bir MCP server ile yeni güvenlik açıkları bile oluşturabilirsiniz.
Yapay zekaya production'da deployment tetikleyebilen bir araç verdiğinizi düşünün. Model bu aracı hangi koşulda kullanabilir? Hangi kullanıcı hangi işleme yetkili? Kritik işlemler onaydan geçecek mi? Bu soruların cevabını MCP vermiyor, yine siz veriyorsunuz.
Performans tarafında da değişen bir şey yok. MCP server arkada REST API çağırıyorsa o API'nin yanıt süresi aynı kalıyor. Eklediğiniz katman yüzünden az da olsa gecikme eklenebiliyor.
Mimarinizdeki problemler MCP'ye geçince kaybolmuyor. Sadece bir sorun çıktığında bakmanız gereken bir katman daha oluyor.
Her uygulamaya MCP server yazmalı mıyız?
Bence hayır.
Tek bir yapay zeka uygulaması geliştiriyor ve birkaç REST API kullanıyorsanız, doğrudan function calling çoğu zaman yeterli. Çalışan ve düzgün dokümante edilmiş API'lerinizin önüne sırf moda diye MCP server koymanın pek anlamı yok.
Ama aynı araçları birden fazla AI istemcisine sunacaksanız, şirket genelinde ortak bir araç kataloğu kuruyorsanız ya da entegrasyonların taşınabilir olması önemliyse MCP mantıklı bir tercih.
Önemli olan hangi teknolojinin daha havalı olduğu değil, hangi problemi çözmeye çalıştığınız. Yazılım dünyasında bu sıra bazen tersine işliyor: önce teknoloji seçiliyor, sonra ona uygun bir problem aranıyor. MCP de şu sıralar biraz bundan nasibini alıyor.
Sonuç
MCP kötü bir teknoloji değil, doğru yerde kullanıldığında faydalı bir standart. Ama bazı yerlerde anlatıldığı gibi yapay zekayı dış dünyaya bağlayan mucizevi bir buluş da değil.
API'ler zaten vardı. Function calling zaten vardı. OpenAPI zaten vardı. Modeller MCP'den önce de dış sistemlerden veri okuyup işlem yapabiliyordu.
MCP'nin getirdiği asıl yenilik, bu entegrasyonları ortak bir protokol altında toplaması ve farklı istemcilerin aynı araçları kolayca kullanabilmesi.
Yarın biri mevcut REST endpoint'lerini bir MCP server'a bağlayıp "Kurumsal sistemlerimizi yapay zeka çağına taşıdık" derse çok heyecanlanmayın. Muhtemelen arkada hala aynı API çalışıyor.
Sadece artık ona istek atarken kendimizi biraz daha fütüristik hissediyoruz.