Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
30 changes: 15 additions & 15 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion packages/analyze-query/src/bin-analyze.ts
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ import {asQueryInternals} from '../../zql/src/query/query-internals.ts';
import type {PullRow, Query} from '../../zql/src/query/query.ts';
import {Database} from '../../zqlite/src/db.ts';
import {TableSource} from '../../zqlite/src/table-source.ts';
import {explainQueries} from './explain-queries.ts';
import {explainQueries} from '../../zqlite/src/explain-queries.ts';
import {runAst} from './run-ast.ts';

const options = {
Expand Down
21 changes: 0 additions & 21 deletions packages/analyze-query/src/explain-queries.ts

This file was deleted.

4 changes: 2 additions & 2 deletions packages/replicache/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@
"devDependencies": {
"@op-engineering/op-sqlite": ">=15",
"@rocicorp/prettier-config": "^0.4.0",
"@rocicorp/zero-sqlite3": "^1.0.12",
"@rocicorp/zero-sqlite3": "1.0.13",
"@types/command-line-usage": "^5.0.2",
"@vitest/runner": "3.2.4",
"command-line-args": "^6.0.1",
Expand All @@ -54,7 +54,7 @@
},
"peerDependencies": {
"@op-engineering/op-sqlite": ">=15",
"@rocicorp/zero-sqlite3": "^1.0.12",
"@rocicorp/zero-sqlite3": "1.0.13",
"expo-sqlite": ">=15"
},
"peerDependenciesMeta": {
Expand Down
6 changes: 3 additions & 3 deletions packages/zero-cache/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@
"@rocicorp/lock": "^1.0.4",
"@rocicorp/logger": "^5.4.0",
"@rocicorp/resolver": "^1.0.2",
"@rocicorp/zero-sqlite3": "^1.0.12",
"@rocicorp/zero-sqlite3": "1.0.13",
"@types/basic-auth": "^1.1.8",
"basic-auth": "^2.0.1",
"chalk": "^5.3.0",
Expand All @@ -60,9 +60,9 @@
"urlpattern-polyfill": "^10.1.0",
"ws": "^8.18.1",
"zero-protocol": "0.0.0",
"zero-types": "0.0.0",
"zql": "0.0.0",
"zqlite": "0.0.0",
"zero-types": "0.0.0"
"zqlite": "0.0.0"
},
"devDependencies": {
"@rocicorp/prettier-config": "^0.4.0",
Expand Down
10 changes: 5 additions & 5 deletions packages/zero/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -46,7 +46,8 @@
"@rocicorp/lock": "^1.0.4",
"@rocicorp/logger": "^5.4.0",
"@rocicorp/resolver": "^1.0.2",
"@rocicorp/zero-sqlite3": "^1.0.12",
"@rocicorp/zero-sqlite3": "1.0.13",
"@standard-schema/spec": "^1.0.0",
"@types/basic-auth": "^1.1.8",
"basic-auth": "^2.0.1",
"chalk": "^5.3.0",
Expand All @@ -70,7 +71,6 @@
"postgres": "^3.4.4",
"prettier": "^3.5.3",
"semver": "^7.5.4",
"@standard-schema/spec": "^1.0.0",
"tsx": "^4.19.1",
"url-pattern": "^1.0.3",
"urlpattern-polyfill": "^10.1.0",
Expand All @@ -82,13 +82,13 @@
"@vitest/runner": "3.2.4",
"analyze-query": "0.0.0",
"ast-to-zql": "0.0.0",
"vite": "6.2.1",
"expo-sqlite": ">=15",
"replicache": "15.2.1",
"shared": "0.0.0",
"typedoc": "^0.28.2",
"typedoc-plugin-markdown": "^4.6.1",
"typescript": "~5.9.3",
"vite": "6.2.1",
"vitest": "3.2.4",
"zero-cache": "0.0.0",
"zero-client": "0.0.0",
Expand All @@ -99,8 +99,8 @@
"zqlite": "0.0.0"
},
"peerDependencies": {
"expo-sqlite": ">=15",
"@op-engineering/op-sqlite": ">=15"
"@op-engineering/op-sqlite": ">=15",
"expo-sqlite": ">=15"
},
"peerDependenciesMeta": {
"expo-sqlite": {
Expand Down
153 changes: 153 additions & 0 deletions packages/zql-benchmarks/src/planner-hydration.bench.ts
Original file line number Diff line number Diff line change
Expand Up @@ -125,6 +125,159 @@ benchmarkQuery(
),
);

// ============================================
// Sophisticated queries using `related`
// ============================================

// Full invoice report with customer, support rep, and line items with tracks
benchmarkQuery(
'invoice.related(customer, lines.related(track))',
queries.invoice
.related('customer', c => c.related('supportRep'))
.related('lines', line => line.related('track')),
);

// Full invoice report - even deeper nesting
benchmarkQuery(
'invoice deep: customer->supportRep->reportsTo, lines->track->album->artist',
queries.invoice
.related('customer', c =>
c.related('supportRep', rep => rep.related('reportsToEmployee')),
)
.related('lines', line =>
line.related('track', t => t.related('album', a => a.related('artist'))),
),
);

// Playlist with all track data including album and artist
benchmarkQuery(
'playlist.related(tracks.related(album.related(artist), genre))',
queries.playlist.related('tracks', t =>
t.related('album', a => a.related('artist')).related('genre'),
),
);

// Artist catalog - artist with all albums and their tracks
benchmarkQuery(
'artist.related(albums.related(tracks))',
queries.artist.related('albums', a => a.related('tracks')),
);

// Artist catalog with full track details
benchmarkQuery(
'artist.related(albums.related(tracks.related(genre, mediaType)))',
queries.artist.related('albums', a =>
a.related('tracks', t => t.related('genre').related('mediaType')),
),
);

// Track with all related data
benchmarkQuery(
'track.related(album.related(artist), genre, mediaType, playlists)',
queries.track
.related('album', a => a.related('artist'))
.related('genre')
.related('mediaType')
.related('playlists'),
);

// ============================================
// Combined `exists` and `related` queries
// ============================================

// Invoices for customers in USA with line items
benchmarkQuery(
'invoice.whereExists(customer where country=USA).related(lines)',
queries.invoice
.whereExists('customer', c => c.where('country', 'USA'))
.related('lines', line => line.related('track')),
);

// Playlists that contain Rock tracks, with full track data
benchmarkQuery(
'playlist.whereExists(tracks.whereExists(genre=Rock)).related(tracks)',
queries.playlist
.whereExists('tracks', t =>
t.whereExists('genre', g => g.where('name', 'Rock')),
)
.related('tracks', t =>
t.related('album', a => a.related('artist')).related('genre'),
),
);

// Artists who have albums with tracks in specific genre
benchmarkQuery(
'artist.whereExists(albums.whereExists(tracks.whereExists(genre=Rock)))',
queries.artist.whereExists('albums', a =>
a.whereExists('tracks', t =>
t.whereExists('genre', g => g.where('name', 'Rock')),
),
),
);

// Tracks that have been purchased (exist in invoice lines)
benchmarkQuery(
'track.whereExists(invoiceLines).related(album, genre)',
queries.track
.whereExists('invoiceLines')
.related('album', a => a.related('artist'))
.related('genre'),
);

// Complex: Customers who bought rock tracks, with their invoices
benchmarkQuery(
'customer.whereExists(deep invoice->line->track->genre=Rock).related(supportRep)',
queries.customer
.whereExists('supportRep', rep => rep.whereExists('reportsToEmployee'))
.related('supportRep'),
);

// ============================================
// Filtered `related` queries
// ============================================

// Invoice with only high-quantity line items
benchmarkQuery(
'invoice.related(lines where quantity>1, customer)',
queries.invoice
.related('lines', line => line.where('quantity', '>', 1).related('track'))
.related('customer'),
);

// Album with filtered tracks (only long tracks)
benchmarkQuery(
'album.related(tracks where milliseconds>300000, artist)',
queries.album
.related('tracks', t => t.where('milliseconds', '>', 300000))
.related('artist'),
);

// Album with ordered tracks and artist
benchmarkQuery(
'album.related(tracks orderBy name, artist)',
queries.album
.related('tracks', t => t.orderBy('name', 'asc').limit(10))
.related('artist'),
);

// ============================================
// Complex OR conditions with related
// ============================================

// Tracks from specific albums OR genres, with full data
benchmarkQuery(
'track.where(OR album=BigOnes, genre=Rock).related(album, genre)',
queries.track
.where(({or, exists}) =>
or(
exists('album', a => a.where('title', 'Big Ones')),
exists('genre', g => g.where('name', 'Rock')),
),
)
.related('album', a => a.related('artist'))
.related('genre'),
);

// Check if JSON output is requested via environment variable
const format = process.env.BENCH_OUTPUT_FORMAT;

Expand Down
2 changes: 1 addition & 1 deletion packages/zqlite/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,7 @@
"@databases/escape-identifier": "^1.0.3",
"@databases/sql": "^3.3.0",
"@rocicorp/logger": "^5.4.0",
"@rocicorp/zero-sqlite3": "^1.0.12",
"@rocicorp/zero-sqlite3": "1.0.13",
"zql": "0.0.0"
}
}
Loading
Loading