Edge Data Engine

Data-Driven
Web Output

Use datasets and variables to dynamically control content at the edge — without a CMS, without a backend, without code.

Core Concept

Data Powers Everything

Rules without data are limited. Rules with data become a runtime engine that shapes every HTML response based on who is asking, where they are, and what they need.

DATASET
↓ defines
Data Source
A structured collection of key-value pairs, objects, or records. You define it once. Ninja reads it at runtime — for every request, every user, every page.
VARIABLE
↓ references
Data Reference
A {{variable}} placeholder in your HTML or rule. It points to a value in the dataset and gets resolved at the edge before delivery.
RULE
↓ controls
Logic
A rule binds a variable to an HTML element — a title, a heading, a price, a CTA. It defines when to inject it, where in the page, and under what conditions.
OUTPUT
↓ delivered to
Browser
The user receives a fully rendered HTML page — with real values, correct context, and dynamic content. No extra round trips. No backend calls. Resolved at the edge.
Datasets

Structured Data for Runtime Control

A dataset is a named, structured collection of data that your rules can read and inject into any HTML response — in real time, at the edge.

You define it once. Ninja makes it available to every rule, for every page, for every user — without a database call, without a backend request.

Common dataset examples
Product catalog — titles, prices, descriptions
SEO metadata — per-page titles and descriptions
Geo content — city names, local pricing, languages
Content variations — A/B copy, seasonal offers
Configuration — feature flags, UI settings
dataset: city_content
"london": {
  "city": "London",
  "title": "Best Clinics in London",
  "price": 120,
  "currency": "GBP",
  "cta": "Book in London"
},
"new_york": {
  "city": "New York",
  "title": "Top Clinics in New York",
  "price": 150,
  "currency": "USD",
  "cta": "Book in New York"
}
{{city}} {{title}} {{price}} {{currency}} {{cta}}
Variables

Variables in Action

Variables are references to dataset values — written as {{field_name}} in your HTML templates or rule actions. Ninja resolves them at request time, before the browser receives the page.

{{title}}

Page Title

Inject a dynamic, SEO-relevant title into the <title> tag and the main heading — unique per city, product, or segment.

Example
<title>{{title}}</title>
<h1>{{title}}</h1>
{{price}}

Dynamic Price

Render market-specific pricing without touching the backend. Combine with {{currency}} for full localization.

Example
{{currency}} {{price}} / session
→ GBP 120 / session
{{cta}}

CTA Text

Replace button labels and call-to-action copy per segment — "Book in London" vs "Book in New York" — without any JavaScript.

Example
<button>{{cta}}</button>
→ Book in London
More variables: {{city}} {{country}} {{lang}} {{offer}} {{product_name}} {{meta_description}} {{canonical_url}} {{hero_image}}
Data Binding

Bind Data to HTML

Your HTML template stays the same. Ninja replaces every {{variable}} with the right value from your dataset — at the edge, before delivery, for every request.

HTML Template
<title>{{title}}</title>
<meta name="description"
  content="{{meta_description}}">
<h1>{{city}} Clinics</h1>
<p class="price">
  From {{currency}} {{price}}
</p>
<button>{{cta}}</button>
Delivered Output — London
<title>Best Clinics in London</title>
<meta name="description"
  content="Find top-rated clinics in London">
<h1>London Clinics</h1>
<p class="price">
  From GBP 120
</p>
<button>Book in London</button>
Dynamic Title
Unique <title> and <h1> per page context.
Content Injection
Insert text, HTML, or entire blocks into any element.
UI Elements
Swap button labels, badge text, offers, and CTA copy.
Attributes
Set href, src, content, data-* from dataset values.
Structure

Flexible Data Structures

Datasets adapt to the shape of your content. From simple key-value pairs to nested objects, records, and collections — Ninja handles any structure your use case requires.

Key-Value

The simplest form. One key, one value. Fast to define, fast to resolve.

"city": "London"
"lang": "en-GB"
Structured Object

A named group of related fields — product info, page metadata, local config.

"product": {
 "name": "...",
 "price": 120
}
Records

Keyed datasets — one entry per city, product ID, or route. Look up by key at request time.

"london": { ... }
"paris": { ... }
"berlin": { ... }
Collections

Arrays of items for lists, carousels, pricing tiers, or content modules — rendered to HTML on delivery.

"features": [
 "Edge speed",
 "No backend"
]
Integration

Data + Rules = Power

A rule tells Ninja what to do. A dataset tells it what to use. Together, they create a runtime content engine that responds to every request with precisely the right output.

Example 01 Geo-Based Content
IF
user city = "London"
THEN
inject dataset city_content["london"] into page
BINDS
{{title}} · {{price}} · {{cta}}
→ User sees London-specific title, price, and CTA
Example 02 Product Data Injection
IF
URL matches /product/{id}
THEN
load dataset product_catalog[{id}]
BINDS
{{product_name}} · {{price}} · {{meta_description}}
→ Product page renders unique SEO + content per product
Example 03 SEO Metadata Override
IF
page exists in seo_metadata dataset
THEN
override <title> and <meta description>
BINDS
{{seo_title}} · {{meta_description}}
→ Search engines index optimized metadata per page
Example 04 Seasonal Offer
IF
flag "summer_promo" = active
THEN
inject banner from offers["summer"]
BINDS
{{offer_text}} · {{discount}} · {{expires}}
→ Live promotional banner without a deploy
Live Example

Example Dataset Usage

A user visits /city/london. Ninja reads the dataset, resolves all variables, and delivers a fully rendered page — no backend involved.

Complete example — dataset + rule + output
① Dataset definition
// city_content dataset
{
  "city": "London",
  "title": "Best Clinics in London",
  "price": 120,
  "currency": "GBP",
  "description": "Top-rated clinics near you",
  "cta": "Book in London"
}
② Rule — bind variables
WHEN /city/london
DO inject dataset
  city_content["london"]
INTO <title>{{title}}</title>
     <h1>{{city}} Clinics</h1>
     <span class="price">
       {{currency}} {{price}}
     </span>
③ Delivered HTML — resolved output
// Browser receives:
<title>Best Clinics in London</title>

<h1>London Clinics</h1>

<span class="price">
  GBP 120
</span>

<button>Book in London</button>
Result
Page fully rendered at the edge. Variables resolved. No backend request. No extra latency. The browser receives complete HTML.
Dynamic Pages

Generate Dynamic Pages

One HTML template. Thousands of unique pages. Ninja uses datasets to generate distinct content for every URL — no CMS, no static generation, no backend rendering.

URL Pattern → Dataset Key

/city/london city_content["london"]
/city/new-york city_content["new_york"]
/city/berlin city_content["berlin"]
/product/123 product_catalog[123]
/product/456 product_catalog[456]
/category/wellness categories["wellness"]

What makes this different

No CMS required
Your content lives in a dataset. Pages are assembled at the edge — not published from a content management system.
No static generation
You don't pre-render thousands of pages. Every request triggers Ninja — the right data is injected in milliseconds.
No backend rendering
Data is resolved at the edge, not on an origin server. Latency stays low regardless of how many pages you scale to.
Unlimited scale
Add a row to your dataset. Ninja handles the rest — automatically, for every new URL, with no build step.
How It Works

Data Delivery Pipeline

From request to browser, Ninja resolves every variable in a single, deterministic pass — before the page is delivered.

Step 01
Request Arrives

User requests /city/london — the request hits the Ninja edge layer before origin.

Step 02
Rule Matched

Ninja matches the URL to an active rule and identifies the correct dataset and key.

Step 03
Data Resolved

All {{variables}} are resolved from the matched dataset entry — in a single pass, at the edge.

Step 04
HTML Assembled

The origin HTML is enriched with resolved values. No template placeholders remain.

Step 05
Delivered

The browser receives complete, rendered HTML — unique content for this exact request.

Value

Why Data Matters

Scalable Content

One template powers thousands of unique pages — without a build pipeline.

Dynamic Output

Every response is assembled at request time with the right values for the right user.

Personalization

Deliver geo, segment, and intent-specific content — from one rule set.

Automation

Update the dataset and every page updates instantly — no deploy, no waiting.

Less Manual Work

Stop hand-editing pages. Let data drive the output — for every URL, every time.

Comparison

Static Content
vs Data-Driven Content

DimensionStatic / CMSNinja Data Layer
Content Hardcoded per page Driven by dataset — dynamic per request
Updates Manual edits, redeploy required Update dataset → live instantly, no deploy
Scale Each page managed separately One template, unlimited unique pages
CMS dependency Required for content changes Not needed — dataset replaces CMS for output
Personalization Requires JS or server-side logic Built into the rule — resolved at edge
SEO Same meta for all variations Unique title + description per dataset entry
Backend load Rendering hits origin Zero — all resolved at the edge
Data doesn't rest. It executes — into output,
into HTML, into the page the user sees.
Edge Data Engine
Start Using Data

Define a dataset. Bind variables. Deliver dynamic pages — without touching your backend, without rebuilding your site.

Explore More
Rules Engine
Programmable Rules
Understand how rules control web output — the WHEN, WHERE, DO, WHY model that powers everything in Ninja.
Explore →
Solution
Personalization
Deliver context-aware content — by city, segment, device, and intent — using datasets and rules together.
Explore →
Architecture
How Ninja Works
See how the Ninja edge layer fits between origin and browser — and why it changes everything about web delivery.
Explore →