Skip to content

Vite plugin

Imported from @qlivedev/qlive-ts/vite, not from the package’s main entry.

function

declare function trackUsage(options?: TrackUsagePluginOptions): Plugin;

The Vite plugin that records the calls QLive’s server-side analysis reads – which query a view injects, which paths declared noSchema() – plus any the application adds through trackedFunctions.

vite build writes the analysis to track-usage.json in the output directory, where the backend reads it. The dev server keeps it in memory and pushes each change to backendOrigin, and while it runs it also rewrites the result type of every saved GraphQLQuery to follow its query (see queryTypes).

Parameters

options where to analyze, what to track and where the backend is

Returns the plugin, for plugins in vite.config.ts

interface

interface TrackUsagePluginOptions

Options of trackUsage. All of them are optional; an application usually sets backendOrigin and nothing else.

trackedFunctions?: Record<string, TrackedFunctionSpec>;

Calls to record on top of QLIVE_TRACKED_FUNCTIONS. Their keys have to be the application’s own: one of QLive’s is refused rather than merged over, because the server reads the framework’s calls back out under exactly those names.

sourceRoot?: string;

Absolute path to the directory tracking is scoped to. Default: src/ below Vite’s root, which is where an application’s own code lives.

debug?: boolean;

Logs to the console every call the analysis matches and every value it records or fails to evaluate. For finding out why a call is missing from the analysis. Default: false.

indexes?: boolean;

Records the source offsets ([start, end]) of every tracked call alongside its arguments. Consumers that rewrite the source at the call site (the QLive backend patches the result type into every new GraphQLQuery<...>()) cannot work without them, so leave this on unless you only need the argument values.

Default: true.

outputFileName?: string;

Default: “track-usage.json”.

backendOrigin?: string;

Origin of the QLive backend, e.g. “http://localhost:8080”. Live track-usage data gets POSTed there as it changes. vite build writes track-usage.json to disk for the backend to read, but vite dev never touches disk, so this is dev mode’s only way to get fresh data to a backend that needs it live (e.g. for codegen). Omit to skip pushing entirely.

pushDebounceMs?: number;

How long to collect changed modules before pushing them to backendOrigin, in milliseconds. One save can transform several modules, and the backend regenerates types for every module it is handed, so they are worth sending as one push. Default: 200.

queryTypes?: QueryTypeOptions | false;

How the query result types are generated. While a dev server runs, every saved query gets its GraphQLQuery<T> rewritten, so the type next to a query follows the query.

Left out, the types are generated whenever schema.graphql is next to the Vite config and @qlivedev/qlive-codegen is installed. Given, its schema has to exist – silence would look like a plugin that does not work. false turns the generation off.

interface

interface QueryTypeOptions

Where the query result types come from and what they import, for TrackUsagePluginOptions.queryTypes.

schema?: string;

GraphQL schema the queries are checked against, relative to Vite’s root. Default: “schema.graphql”.

typesModule?: string;

Module the generated domain types live in, relative to sourceRoot and without extension. It is what a generated result type picks its fields out of, and what the query module gets an import of. Default: “types”, i.e. what generate-ts writes to src/types.d.ts.

constant

declare const QLIVE_TRACKED_FUNCTIONS: Record<string, TrackedFunctionSpec>;

The calls QLive’s own analysis is built on. Their keys are the symbolic names the server looks up a call under – ModuleFunctionReferences.USE_INJECTION_CALL_NAME and its neighbours name the same strings on the Java side – so what belongs in here is the framework’s to state and not an application’s to get right. An application adds its own entries through trackedFunctions, and is refused a key that is already one of these.

interface

interface TrackedFunctionSpec

Which calls the analysis records: calls of fn on whatever module exports, or of the module itself when fn is empty. Only statically evaluable arguments are recorded, unless the options below loosen that.

module: string;

Import source, relative to sourceRoot (e.g. “./service/i18n”) or a bare package specifier.

fn: string;

“” if the module itself is called as a function; otherwise the method/export name called on it.

varArgs?: boolean | number;

Enables varargs support where a function can have n static arguments and then a number of variable arguments that have no restriction on being static. If varargs is a number, it defines how many arguments are statically captured (true is the same as 1)

captureContext?: boolean;

Allows recording context expressions against the matched location in the AST. e.g. “parent.id.name”

allowIdentifier?: boolean;

Enables identifier matching where instead of a static expression, we capture the name of an identifier to reference some global namespace (or local in some way).

requireStatic?: boolean;

Marks a call the analysis cannot do without: one whose arguments don’t evaluate is reported as a warning naming the file, the line and the part of the argument that isn’t static, where otherwise it is left out silently. Right for a call whose absence breaks the page, wrong for one that is often dynamic on purpose.

function

declare function analyzeSourceTree(options: AnalyzeSourceTreeOptions): TrackUsageAnalysis;

Runs the track-usage analysis over a whole source tree in one go, outside of Vite.

The plugin gets its analysis handed to it file by file, as Vite transforms them, which is the wrong shape for a tool that is not a dev server – the codegen CLI wants the whole tree before it starts. Both go through the same babel pass, so what a build-time generator sees is what the dev-time one sees: the same recorded calls under the same names, at the same source offsets.

Parameters

options what to analyze and how

Returns the analysis of every tracked file below sourceRoot

interface

interface AnalyzeSourceTreeOptions

Options of analyzeSourceTree: the plugin’s options minus everything that only makes sense inside a running Vite.

sourceRoot: string;

Absolute path to the directory to analyze, i.e. the sourceRoot the plugin would be given.

trackedFunctions?: Record<string, TrackedFunctionSpec>;

Calls to record on top of QLIVE_TRACKED_FUNCTIONS, same rules as the plugin’s.

debug?: boolean;

See TrackUsagePluginOptions.debug. Default: false.

indexes?: boolean;

See TrackUsagePluginOptions.indexes. Default: true.

onSkippedCall?: (call: SkippedCall) => void;

Receives each call marked TrackedFunctionSpec.requireStatic that the analysis leaves out. Default: a warning on the console, see formatSkippedCall.

interface

interface TrackUsageAnalysis

The analysis of one source tree, as babel-plugin-track-usage records it. Keyed by module id relative to sourceRoot (“./app/Q_Foo”), which is how the backend addresses a module as well.

usages: Record<string, unknown>;

interface

interface SkippedCall

A tracked call left out of the data because one of its arguments did not evaluate statically. What the plugin hands its onSkippedCall option.

name: string;

symbolic name of the tracked function, its key in trackedFunctions

filename: string;

file the call is in, as babel was given it

line: number | null;

1-based line of the part that did not evaluate, null where babel has no location

column: number | null;

1-based column of it

argument: number;

0-based index of the argument

path: string;

property path from the argument to the part, like “.config.sortFields[0]”, “” for the argument itself

code: string;

source text of the part

function

declare function formatSkippedCall(call: SkippedCall): string;

The warning about a call the analysis left out, with the file position an editor or terminal can jump to.