IdentityIdentity Graph & Join Keys

Identity Graph & Join Keys

The identity graph is how Datafly Signal connects events to people. Custom identity types define what can join; Identity Graph bindings define, per pipeline, which event field carries each type.

Bindings

Configure bindings on Pipelines → your pipeline → Identity → Identity Graph. Each binding maps a source field on the event to a declared identity type:

Source path prefixReads from
properties.Event properties (e.g. a server event’s properties.loyalty_id)
traits.Traits from identify() calls
collected_ids.Values collected in the browser by a custom sync

Because the type is organisation-wide, the same type bound on two different pipelines writes to — and reads from — the same graph key. That is what makes cross-pipeline joins work.

Example: loyalty ID across web and in-store

An organisation declares the type loyalty_id in Settings → Identity, then binds it on two pipelines:

  • Web pipeline — a custom sync reads the loyalty ID from the site’s login cookie, and the binding collected_ids.loyalty_id → loyalty_id writes it into the graph alongside the visitor’s cookie ID, email, and user ID.
  • Server pipeline (POS) — in-store purchase events carry the card number scanned at the till, and the binding properties.loyalty_id → loyalty_id lets each purchase look up the person the web pipeline already knows.
curl -X POST https://collect.example.com/v1/track \
  -H "Content-Type: application/json" \
  -d '{
    "event": "purchase",
    "anonymousId": "pos-7f3a2c91-…",
    "properties": {
      "loyalty_id": "LP-99831",
      "value": 42.50,
      "currency": "GBP"
    }
  }'

The in-store purchase resolves to the same person as their web sessions — attribution, audiences, and downstream destinations all see one customer.

The ID Map: join keys vs attached identifiers

The top of the Identity tab shows the ID Map — a read-only summary of every identifier the pipeline touches, grouped by role:

  • JOIN KEYS — identifiers that resolve events to a person: user ID, hashed email/phone, custom types with a graph binding, device ID, cookie ID. These build and query the graph.
  • ATTACHED IDENTIFIERS — identifiers that are stored on the person and delivered to destinations, but do not join: vendor IDs, click IDs, and collected IDs without a graph binding.

Each row links to the card where that identifier is configured.

⚠️

Collecting an ID does not join it. A custom sync puts a value onto events (collected_ids.loyalty_id) and stores it against the visitor — but it stays an attached identifier until a matching Identity Graph binding exists. If you want the ID to resolve people, configure both: the custom sync (to collect it) and the binding collected_ids.loyalty_id → loyalty_id (to join on it). The ID Map shows at a glance which role each identifier currently has.

If a type has a consent category set, its bindings only act on events whose consent state grants that category — on both the write side (extending the graph) and the lookup side (resolving a person). Events from server sources that carry no consent state at all can be granted a default consent context per pipeline — see Server & In-Store Sources.

Next steps