Skip to main content

Vague vs. Other Tools

Vague isn't competing with fake data libraries. It's solving a different problem: how do you formally describe what valid data looks like?

The Core Difference

Tool CategoryPrimary PurposeVague Equivalent
Faker.js / Chance.jsGenerate realistic-looking valuesBuilt-in via faker.* plugin
JSON SchemaDescribe structure and typesSchema definitions
Property-based testingGenerate from constraintsassume blocks
OpenAPIAPI contract specificationImport/export + validation

Vague combines all four into a single declarative language.

vs. Faker.js

Faker.js generates realistic individual values. Vague describes entire data models with relationships and constraints.

CapabilityFaker.jsVague
Realistic names, emailsfaker.person.fullName()fullName()
Weighted distributionsManual logic0.8: "active" | 0.2: "inactive"
Inter-field constraintsManual logicassume due_date >= issued_date
Cross-record relationshipsManual wiringcustomer: any of customers
Edge case biasManual creationissuer.homoglyph()
Reproducible outputManual seeding--seed 123

When to use Faker alone: Simple scripts that need a few fake values.

When to use Vague: Test suites, API mocking, or anywhere data has relationships.

// Faker: Manual relationship wiring
const customers = Array(50).fill().map(() => ({
id: faker.string.uuid(),
status: Math.random() < 0.8 ? 'active' : 'inactive'
}));

const activeCustomers = customers.filter(c => c.status === 'active');
const invoices = Array(200).fill().map(() => ({
customer_id: activeCustomers[Math.floor(Math.random() * activeCustomers.length)].id,
// due_date must be after issued_date... manual logic
}));
// Vague: Declarative
schema Customer {
id: uuid(),
status: 0.8: "active" | 0.2: "inactive"
}

schema Invoice {
customer: any of customers where .status == "active",
issued_date: date in 2024..2024,
due_date: date in 2024..2024,
assume due_date >= issued_date
}

dataset Test {
customers: 50 of Customer,
invoices: 200 of Invoice
}

vs. JSON Schema

JSON Schema describes what data looks like. Vague describes what data looks like and generates it.

CapabilityJSON SchemaVague
Type definitions"type": "string"name: string
Enums"enum": ["a", "b"]"a" | "b"
Ranges"minimum": 0int in 0..100
GenerationRequires separate toolBuilt-in
Weighted distributionsNot supported0.7: "a" | 0.3: "b"
Cross-field constraintsLimited (if/then)assume a >= b
Cross-record relationshipsNot supportedany of collection

When to use JSON Schema: API documentation, request/response validation.

When to use Vague: When you need to generate data that conforms to constraints JSON Schema can't express.

vs. Property-Based Testing

Property-based testing (QuickCheck, fast-check) generates inputs to find edge cases. Vague generates realistic data that satisfies domain constraints.

CapabilityProperty TestingVague
Random generationYes (uniform)Yes (weighted)
ShrinkingYesNo
Realistic distributionsNo0.8: "active"
Domain modelingCodeDeclarative
Cross-record refsManualany of
Negative testingManualviolating

When to use property-based testing: Finding edge cases in pure functions.

When to use Vague: Generating realistic test fixtures.

Complementary use: Use Vague to generate fixtures, property-based testing to verify invariants.

vs. OpenAPI

OpenAPI specifies API contracts. Vague can import OpenAPI schemas, generate conformant data, and populate specs with examples.

CapabilityOpenAPIVague
Schema definitionYesYes
Format hintsformat: "email"email()
ExamplesManualAuto-generated
GenerationRequires toolsBuilt-in
Cross-schema refs$ref (structure)any of (values)
Business constraintsx- extensionsassume blocks

Workflow integration:

# Import OpenAPI → generate → validate → populate examples
vague data.vague -v api.json --oas-output api-with-examples.json

Feature Matrix

FeatureFakerJSON Schemafast-checkOpenAPIVague
Realistic valuesYesNoNoNoYes
Type constraintsNoYesYesYesYes
Weighted distributionsManualNoManualNoNative
Cross-field constraintsManualLimitedFilterNoNative
Cross-record refsManualNoManual$refNative
Edge case generationManualNoShrinkingNoissuer.*
Negative testingManualNoManualNoviolating
Schema validationNoYesNoYesYes
Reproducible (seeded)ManualNoYesNoYes

When to Choose Vague

Choose Vague when:

  1. Data has relationships — Invoices reference customers
  2. Data has constraints — Due dates must follow issued dates
  3. You need realistic distributions — 80% of orders are fulfilled
  4. You want edge case coverage — Unicode exploits, boundary values
  5. You need reproducibility — Same seed = same data
  6. You validate the same schemas — Generate AND validate

Stick with simpler tools when:

  1. You just need a few random values
  2. Your data has no relationships or constraints
  3. You're testing pure functions

Summary

Vague is not a replacement for Faker — it includes Faker. It's not a replacement for JSON Schema — it can import and validate against OpenAPI. It's not a replacement for property-based testing — they're complementary.

Vague answers: "How do we formally describe what valid data looks like for our APIs?"

The same .vague file that generates your test fixtures can validate your production data. That's a schema contract, not a data faker.