> ## Documentation Index
> Fetch the complete documentation index at: https://docs.factagora.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Embed & Detect

> Step-by-step guide to embedding and detecting DeepStamp watermarks

## 1. Embed a watermark

Send your content to `/fingerprint/embed` to extract the TKG and embed the watermark.

<CodeGroup>
  ```bash cURL theme={null}
  curl -X POST "https://api.factagora.com/api/v1/fingerprint/embed" \
    -H "Authorization: Bearer fa_your_api_key" \
    -H "Content-Type: application/json" \
    -d '{
      "content": "The European Central Bank raised interest rates by 25 basis points on Thursday, citing persistent core inflation in the eurozone. Analysts at Goldman Sachs expect one more hike before a pause in Q4.",
      "content_type": "news",
      "metadata": {
        "author_id": "editor_jane",
        "published_at": "2024-06-15T08:00:00Z",
        "source_id": "article_12345"
      }
    }'
  ```

  ```python Python theme={null}
  import requests

  resp = requests.post(
      "https://api.factagora.com/api/v1/fingerprint/embed",
      headers={"Authorization": "Bearer fa_your_api_key"},
      json={
          "content": "The European Central Bank raised interest rates by 25 basis points on Thursday, citing persistent core inflation in the eurozone. Analysts at Goldman Sachs expect one more hike before a pause in Q4.",
          "content_type": "news",
          "metadata": {
              "author_id": "editor_jane",
              "published_at": "2024-06-15T08:00:00Z",
              "source_id": "article_12345",
          },
      },
  )
  data = resp.json()
  ```

  ```typescript TypeScript theme={null}
  const resp = await fetch("https://api.factagora.com/api/v1/fingerprint/embed", {
    method: "POST",
    headers: {
      Authorization: "Bearer fa_your_api_key",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      content:
        "The European Central Bank raised interest rates by 25 basis points on Thursday, citing persistent core inflation in the eurozone. Analysts at Goldman Sachs expect one more hike before a pause in Q4.",
      content_type: "news",
      metadata: {
        author_id: "editor_jane",
        published_at: "2024-06-15T08:00:00Z",
        source_id: "article_12345",
      },
    }),
  });
  const data = await resp.json();
  ```
</CodeGroup>

### Response

```json theme={null}
{
  "watermarked_content": "The European Central Bank raised interest rates by 25 basis points...",
  "fingerprint_id": "fp_l1p8OPCwGhvu",
  "tkg_snapshot": {
    "entities": ["European Central Bank", "Interest rate", "Goldman Sachs"],
    "timeseries": ["2024-06-15"],
    "relations": [
      { "from": "European Central Bank", "rel": "raises", "to": "Interest rate" }
    ],
    "argument_map": [
      {
        "premise": "Persistent core inflation in the eurozone",
        "evidence": "ECB policy meeting decision",
        "conclusion": "Interest rates raised by 25 basis points"
      }
    ]
  },
  "embed_timestamp": "2024-06-15T08:01:23.456Z",
  "meta": { "executionTimeMs": 1234 }
}
```

<Warning>
  **Distribute `watermarked_content`, not the original.** The watermarked version looks identical to the original but contains invisible zero-width characters that enable watermark-based detection.
</Warning>

<Info>
  **Store `fingerprint_id`** alongside your internal article ID. You'll need it for re-scoring and reporting.
</Info>

## 2. Detect content reuse

When you encounter content that looks like it might originate from your article, even if it's been rewritten, send it to `/fingerprint/detect`.

<CodeGroup>
  ```bash cURL theme={null}
  curl -X POST "https://api.factagora.com/api/v1/fingerprint/detect" \
    -H "Authorization: Bearer fa_your_api_key" \
    -H "Content-Type: application/json" \
    -d '{
      "content": "ECB hiked rates 25bp Thursday due to stubborn inflation. Goldman analysts predict one final increase before year-end pause."
    }'
  ```

  ```python Python theme={null}
  resp = requests.post(
      "https://api.factagora.com/api/v1/fingerprint/detect",
      headers={"Authorization": "Bearer fa_your_api_key"},
      json={
          "content": "ECB hiked rates 25bp Thursday due to stubborn inflation. Goldman analysts predict one final increase before year-end pause."
      },
  )
  result = resp.json()
  ```

  ```typescript TypeScript theme={null}
  const resp = await fetch("https://api.factagora.com/api/v1/fingerprint/detect", {
    method: "POST",
    headers: {
      Authorization: "Bearer fa_your_api_key",
      "Content-Type": "application/json",
    },
    body: JSON.stringify({
      content:
        "ECB hiked rates 25bp Thursday due to stubborn inflation. Goldman analysts predict one final increase before year-end pause.",
    }),
  });
  const result = await resp.json();
  ```
</CodeGroup>

### Response

```json theme={null}
{
  "match_found": true,
  "confidence_score": 0.87,
  "query_fingerprint_id": "fp_tmpQueryId01",
  "matches": [
    {
      "fingerprint_id": "fp_l1p8OPCwGhvu",
      "content_type": "news",
      "metadata": { "author_id": "editor_jane", "source_id": "article_12345" },
      "embed_timestamp": "2024-06-15T08:01:23.456Z",
      "score": 0.87,
      "similarity_breakdown": {
        "entity_match": 0.92,
        "timeseries_match": 1.0,
        "causal_pattern_match": 0.78
      },
      "overlap": {
        "entities": ["european central bank", "interest rate", "goldman sachs"],
        "timeseries": ["2024-06-15"],
        "relations": ["european central bank|raises|interest rate"]
      },
      "watermark_match": false,
      "watermark_correlation": null
    }
  ],
  "meta": {
    "scanned": 156,
    "executionTimeMs": 342,
    "weights": { "entity": 0.5, "time": 0.2, "causal": 0.3 },
    "watermark_detected": false
  }
}
```

Notice that the query text is completely rewritten, "ECB hiked rates 25bp" vs "European Central Bank raised interest rates by 25 basis points", yet the API matched it with 87% confidence by comparing the underlying causal structure.

## 3. Detect with watermark (highest confidence)

If the watermarked version of your content was copied with the invisible characters intact, the watermark layer fires for near-certain provenance:

```json theme={null}
{
  "matches": [
    {
      "fingerprint_id": "fp_l1p8OPCwGhvu",
      "score": 0.87,
      "watermark_match": true,
      "watermark_correlation": 0.98,
      ...
    }
  ],
  "meta": {
    "watermark_detected": true
  }
}
```

When `watermark_match: true`, the match is cryptographically verified, the exact watermarked content (or a portion of it) was used.

## 4. Tune detection with custom weights

Different content types benefit from different scoring emphasis. Override the defaults when needed:

<CodeGroup>
  ```json Legal document (emphasize causal structure) theme={null}
  {
    "content": "...",
    "weights": { "entity": 0.3, "time": 0.1, "causal": 0.6 }
  }
  ```

  ```json Time-sensitive report (emphasize timeline) theme={null}
  {
    "content": "...",
    "weights": { "entity": 0.3, "time": 0.5, "causal": 0.2 }
  }
  ```
</CodeGroup>

The weights used are always echoed back in `meta.weights` so you can verify what was applied.

## 5. Re-score an existing fingerprint

To periodically check if new content matches a fingerprint you already embedded, pass the `fingerprint_id` directly:

```bash theme={null}
curl -X POST "https://api.factagora.com/api/v1/fingerprint/detect" \
  -H "Authorization: Bearer fa_your_api_key" \
  -H "Content-Type: application/json" \
  -d '{"fingerprint_id": "fp_l1p8OPCwGhvu"}'
```

This reuses the stored TKG snapshot without re-extracting, making it faster and ideal for scheduled monitoring.

## Summary

| Step     | Endpoint                                           | What it does                                              |
| -------- | -------------------------------------------------- | --------------------------------------------------------- |
| Embed    | `POST /fingerprint/embed`                          | Extracts TKG, embeds watermark, stores fingerprint        |
| Detect   | `POST /fingerprint/detect`                         | Runs watermark + TKG matching against stored fingerprints |
| Re-score | `POST /fingerprint/detect` (with `fingerprint_id`) | Re-scores existing fingerprint against new candidates     |
