İçeriğe atla
Belgeler

Giden webhook'lar: payload ve imza

AutoPSEO uyarılarını ve raporlarını herhangi bir HTTPS uç noktasında imzalı JSON olarak alın: istek başlıkları, gövde alanları, olay türleri ve imzanın nasıl doğrulanacağı.

Hesap → Slack, Teams ve Webhooks → Giden webhook'larAbonelik veya deneme sürümü gerektirir5 dk okuma

Giden webhook, AutoPSEO'nun uyarılarını, zamanlanmış raporlarını, test mesajlarını ve rapor özetlerini sizin işlettiğiniz bir uç noktaya iletir. Her mesaj, HMAC-SHA256 ile imzalanmış tek bir JSON POST isteği olarak gönderilir. Zapier, Make, n8n, bir olay yönetimi aracı veya kendi kodunuzu beslemek için kullanabilirsiniz; Slack ya da Teams hesabı gerekmez. Sitenize makale ileten webhook'u mu arıyorsunuz? O webhook içerik motoruna aittir: içerik teslimi sayfasına bakın.

Webhook ekleme

  1. Outbound webhooks bölümünde New webhook düğmesine tıklayın.
  2. Bir Name (ad) verin ve uç noktanın URL'sini yapıştırın. URL herkese açık bir HTTPS adresi olmalıdır: düz http, localhost, .local veya .internal ile biten adlar, noktası olmayan ana makine adları ve özel ya da link-local IP adresleri reddedilir.
  3. Kaydettikten sonra gösterilen signing secret değerini kopyalayın. Bu değer yalnızca bir kez gösterilir.
  4. test olayı göndermek için Send test düğmesine tıklayın, ardından zamanlanmış raporları veya uyarıları webhook'a bağlayın.

Webhook isteği neye benzer

Her mesaj, şu başlıklarla bir POST isteği olarak gönderilir:

BaşlıkDeğer
Content-Typeapplication/json
User-AgentAutoPSEO-Webhook/1.0
X-AutoPSEO-EventOlay türü, örneğin traffic_drop
X-AutoPSEO-Signaturesha256= ve ardından 64 küçük harfli onaltılık karakter

Aşağıda, 12 Ekim 2026 tarihli 06:00 UTC çalıştırmasından bir alan adı mülkü için trafik düşüşü uyarısı okunabilir biçimde gösterilmiştir (gerçekte kompakt JSON olarak gönderilir; id ve site_id değerleri uydurmadır):

{
  "id": "9b2e61f04c3a4d7e8f15a0b6c2d39e47",
  "event_type": "traffic_drop",
  "severity": "high",
  "site_id": "4f0c1e9a2b7d4c58",
  "site_url": "sc-domain:example.com",
  "occurred_at": "2026-10-12T06:00:04.183Z",
  "title": "Traffic drop: example.com",
  "text": "Clicks 1,500 vs 2,000 in the previous window (-25.0%).",
  "url": "https://app.autopseo.com/property/sc-domain%3Aexample.com",
  "payload": {
    "fields": [
      { "label": "Metric", "value": "clicks" },
      { "label": "Current", "value": "1,500" },
      { "label": "Baseline", "value": "2,000" },
      { "label": "Window", "value": "7 days (2026-10-05 → 2026-10-11 vs 2026-09-28 → 2026-10-04)" },
      { "label": "Change", "value": "-25.0%" }
    ],
    "table": null,
    "detector": "traffic_drop",
    "window": 7,
    "range": { "start": "2026-10-05", "end": "2026-10-11", "compStart": "2026-09-28", "compEnd": "2026-10-04" },
    "result": {
      "fired": true,
      "metric": "clicks",
      "value": 1500,
      "baseline": 2000,
      "change": -0.25,
      "severity": "high",
      "summary": "Clicks 1,500 vs 2,000 in the previous window (-25.0%)."
    }
  },
  "source": "autopseo"
}

Üst düzey alanlar tüm olaylarda aynıdır:

Alanİçeriği
idRastgele 32 karakterlik onaltılık bir dize; her istekte yenisi üretilir
event_typeNe olduğu (bir sonraki bölüme bakın)
severityUyarılar için critical, high, medium veya low; raporlar, özetler ve testler için info
site_idAutoPSEO'nun mülk için kullandığı kimlik; testlerde ve demo mülkünde null
site_urlsc-domain:example.com veya https://www.example.com/ gibi Search Console mülkü; testlerde null
occurred_atMesajın oluşturulduğu an; UTC cinsinden ISO 8601 zaman damgası
title, textSlack ve Teams'in gösterdiği başlık ve özet cümlesi
urlAutoPSEO'daki rapor; testlerde null
payload.fieldsSlack'in alan, Teams'in fact olarak gösterdiği etiketli değerler
payload.tableRaporlar ve özetler için columns ve rows; diğer durumlarda null
sourceHer zaman autopseo

Oranlar kesir olarak verilir: -0.25 değerindeki bir change yüzde 25'lik düşüş, 0.034 değerindeki bir ctr ise yüzde 3,4 anlamına gelir.

Olay türleri

event_typeNe zaman gönderilirpayload içindeki ek anahtarlar
traffic_drop, traffic_spike, position_drop, ctr_drop, new_lost_rankings, anomaly, index_flip, rank_drop, audit_regressionBir uyarı kuralı tetiklendiğinde; zamanlamaya göre ya da Test rule iledetector, window, range (tarihler; index_flip, rank_drop ve audit_regression için null), result
scheduled_reportZamanlanmış bir rapor gönderildiğinde; zamanlamaya göre ya da Send now ilereportType (summary, queries, pages veya rankings), range (tarihler ve bir label), totals, previous
report_summaryBiri bir rapor sayfasında Send to Slack düğmesini kullandığındaYok: değerler fields ve table içindedir
testBiri webhook üzerinde Send test düğmesine tıkladığındasample, her zaman true

result, dedektörün ölçtüklerini tekrar eder: fired, metric, value, baseline, change (karşılaştırılacak veri yoksa null), severity ve summary; anomaly için ayrıca değiştirilmiş z-skoru olan z da bulunur. totals ve previous, bir raporun iki dönemi için clicks, impressions, ctr ve position değerlerini içerir. Her dedektörün neyi ölçtüğü Uyarılar sayfasında açıklanmıştır.

İmza nasıl doğrulanır

İmza, AutoPSEO'nun gönderdiği baytların tamamı üzerinden, webhook'un signing secret değeriyle anahtarlanarak hesaplanan bir HMAC-SHA256'dır ve sha256= önekiyle küçük harfli onaltılık biçimde yazılır. Doğrulamak için:

  1. İstek gövdesini, JSON olarak ayrıştırmadan önce ham haliyle okuyun. Ayrıştırıp yeniden serileştirmek baytları değiştirebilir.
  2. Bu baytlar üzerinden HMAC-SHA256 hesaplayın; secret değerini metin olarak kullanın: 64 karakterlik dizeyi gösterildiği gibi alın, onaltılıktan çözmeyin.
  3. Sonucun başına sha256= ekleyin ve X-AutoPSEO-Signature başlığıyla sabit zamanlı (constant-time) bir karşılaştırmayla kıyaslayın.
  4. İkisi farklıysa isteği reddedin. Aksi halde hemen 2xx durum koduyla yanıt verin ve yavaş işleri sonra yapın.

Node.js için bağımlılık gerektirmeyen bir alıcı:

import { createServer } from 'node:http';
import { createHmac, timingSafeEqual } from 'node:crypto';

const secret = process.env.AUTOPSEO_WEBHOOK_SECRET;

createServer((req, res) => {
  const chunks = [];
  req.on('data', (chunk) => chunks.push(chunk));
  req.on('end', () => {
    const raw = Buffer.concat(chunks);
    const expected = Buffer.from('sha256=' + createHmac('sha256', secret).update(raw).digest('hex'));
    const received = Buffer.from(String(req.headers['x-autopseo-signature'] || ''));
    if (received.length !== expected.length || !timingSafeEqual(received, expected)) {
      res.writeHead(401).end();
      return;
    }
    res.writeHead(204).end();
    const event = JSON.parse(raw.toString('utf8'));
    console.log(event.event_type, event.severity, event.site_url);
  });
}).listen(8080);

Uzunluk kontrolü başta yapılır, çünkü Node'un timingSafeEqual fonksiyonu iki arabelleğin uzunluğu farklıysa hata fırlatır.

Teslimat kuralları

  • Her mesaj için tek deneme yapılır ve zaman aşımı 10 saniyedir. 2xx dışındaki her yanıt başarısızlık sayılır ve durum koduyla birlikte yanıt gövdenizin ilk kısmı Delivery history içinde saklanır.
  • Yönlendirmeler izlenmez. 3xx yanıtı, nihai URL'yi kullanmanızı belirten bir notla başarısız olur.
  • Hiçbir şey zamanlayıcıyla yeniden denenmez. Başarısız olan bir uyarı gönderildi olarak işaretlenmez; bu nedenle bir sonraki kontrolde yeniden değerlendirilir ve hâlâ tetikleniyorsa gönderilir: çoğu dedektör için ertesi sabah, index flip için ertesi saat. Başarısız olan bir zamanlanmış rapor aynı dönem içinde yeniden gönderilmez; uç noktayı düzelttikten sonra Send now kullanın.
  • id her istek için ayrı üretilir; yani bir olayı değil, bir teslimatı tanımlar. Uyarıları tekrarlardan ayıklamak için event_type, site_url ve occurred_at tarihini birlikte kullanın: bir kural, biri Test rule çalıştırmadıkça, mülk başına UTC gününde en fazla bir kez gönderim yapar.

Signing secret

AutoPSEO, signing secret değerini webhook'u kaydettiğinizde yalnızca bir kez gösterir; liste bunu bir daha göstermez. Değeri hemen alıcınızın yapılandırmasında, koruduğu uç noktanın yanında saklayın.

URL'nin kendisi şifreli olarak saklanır ve liste yalnızca ana makine adını ve son karakterlerini gösterir. Bir webhook'u silmek, ona gönderim yapan tüm kuralları da siler. Teams kanalında JSON yerine okunaklı bir kart istiyorsanız Microsoft Teams sayfasına bakın.

SEO içeriğinizi otopilota alın

Search Console'u ve sitenizi bağlayın. AutoPSEO siteyi tarar ve ilk konuları hemen planlar. Kredi kartı gerekmez.