@takeshape/ssg 11.143.2 → 11.154.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/package.json +5 -5
- package/dist/compress-html.d.ts +0 -3
- package/dist/compress-html.js +0 -20
- package/dist/config.d.ts +0 -76
- package/dist/config.js +0 -106
- package/dist/errors/formatting.d.ts +0 -4
- package/dist/errors/formatting.js +0 -8
- package/dist/errors/graphql-error.d.ts +0 -6
- package/dist/errors/graphql-error.js +0 -22
- package/dist/errors/index.d.ts +0 -5
- package/dist/errors/index.js +0 -5
- package/dist/errors/pagination-error.d.ts +0 -3
- package/dist/errors/pagination-error.js +0 -6
- package/dist/errors/template-render-error.d.ts +0 -4
- package/dist/errors/template-render-error.js +0 -11
- package/dist/files.d.ts +0 -3
- package/dist/files.js +0 -11
- package/dist/filters/array-filters.d.ts +0 -2
- package/dist/filters/array-filters.js +0 -2
- package/dist/filters/code-filter.d.ts +0 -1
- package/dist/filters/code-filter.js +0 -13
- package/dist/filters/create-asset-filter.d.ts +0 -1
- package/dist/filters/create-asset-filter.js +0 -5
- package/dist/filters/create-date-filter.d.ts +0 -2
- package/dist/filters/create-date-filter.js +0 -12
- package/dist/filters/create-image-filter.d.ts +0 -2
- package/dist/filters/create-image-filter.js +0 -7
- package/dist/filters/create-number-filter.d.ts +0 -3
- package/dist/filters/create-number-filter.js +0 -120
- package/dist/filters/create-route-filter.d.ts +0 -3
- package/dist/filters/create-route-filter.js +0 -24
- package/dist/filters/markdown-filter.d.ts +0 -1
- package/dist/filters/markdown-filter.js +0 -6
- package/dist/filters/pluralize-filter.d.ts +0 -1
- package/dist/filters/pluralize-filter.js +0 -4
- package/dist/generate/context.d.ts +0 -8
- package/dist/generate/context.js +0 -49
- package/dist/generate/generate.d.ts +0 -21
- package/dist/generate/generate.js +0 -300
- package/dist/generate/index.d.ts +0 -1
- package/dist/generate/index.js +0 -1
- package/dist/generate/streams.d.ts +0 -7
- package/dist/generate/streams.js +0 -88
- package/dist/generate/types.d.ts +0 -54
- package/dist/generate/types.js +0 -1
- package/dist/graphql/analyze.d.ts +0 -28
- package/dist/graphql/analyze.js +0 -87
- package/dist/graphql/ast.d.ts +0 -19
- package/dist/graphql/ast.js +0 -122
- package/dist/graphql/client-schema.d.ts +0 -3
- package/dist/graphql/client-schema.js +0 -8
- package/dist/graphql/index.d.ts +0 -6
- package/dist/graphql/index.js +0 -6
- package/dist/graphql/migrate.d.ts +0 -19
- package/dist/graphql/migrate.js +0 -111
- package/dist/graphql/pagination.d.ts +0 -36
- package/dist/graphql/pagination.js +0 -268
- package/dist/graphql/query.d.ts +0 -20
- package/dist/graphql/query.js +0 -141
- package/dist/graphql/schema-connector-factory.d.ts +0 -10
- package/dist/graphql/schema-connector-factory.js +0 -90
- package/dist/gzip.d.ts +0 -3
- package/dist/gzip.js +0 -14
- package/dist/index.d.ts +0 -6
- package/dist/index.js +0 -6
- package/dist/nunjucks.d.ts +0 -7
- package/dist/nunjucks.js +0 -88
- package/dist/paths.d.ts +0 -2
- package/dist/paths.js +0 -10
- package/dist/resolve-context.d.ts +0 -34
- package/dist/resolve-context.js +0 -115
- package/dist/stats.d.ts +0 -4
- package/dist/stats.js +0 -39
- package/dist/types.d.ts +0 -53
- package/dist/types.js +0 -1
- package/dist/util.d.ts +0 -2
- package/dist/util.js +0 -17
|
@@ -1,21 +0,0 @@
|
|
|
1
|
-
import { type Config, type FileLoader, type PaginateConfig, type RouteConfig, type SyncFileLoader } from '../config.ts';
|
|
2
|
-
import type { Data, GraphQLConnector, RenderedPage } from '../types.ts';
|
|
3
|
-
import type { GenerateResult, GetPaginatedData, RenderContext } from './types.ts';
|
|
4
|
-
export declare function calculatePages(total: number, pageSize: number): number;
|
|
5
|
-
export declare function hasListPageConfig(paginate: PaginateConfig): boolean;
|
|
6
|
-
export declare function hasItemPageConfig(route: RouteConfig): boolean;
|
|
7
|
-
type RenderPaginatedRoute = (route: RouteConfig, context: Data) => Promise<RenderedPage[]>;
|
|
8
|
-
export declare function renderPaginatedTemplate(generateContext: RenderContext, getPaginatedData: GetPaginatedData): RenderPaginatedRoute;
|
|
9
|
-
export type GenerateParams = {
|
|
10
|
-
fileLoader: FileLoader;
|
|
11
|
-
connector: GraphQLConnector;
|
|
12
|
-
templateFileLoader: SyncFileLoader;
|
|
13
|
-
};
|
|
14
|
-
export type GenerateRouteParams = {
|
|
15
|
-
routeName: string;
|
|
16
|
-
locale?: string;
|
|
17
|
-
contentId?: string;
|
|
18
|
-
} & GenerateParams;
|
|
19
|
-
export declare function generateRoute(config: Config, params: GenerateRouteParams): Promise<GenerateResult>;
|
|
20
|
-
export default function generate(config: Config, params: GenerateParams): Promise<GenerateResult>;
|
|
21
|
-
export {};
|
|
@@ -1,300 +0,0 @@
|
|
|
1
|
-
import { createAsyncWritable, pump } from '@takeshape/streams';
|
|
2
|
-
import asyncIteratorToStream from 'async-iterator-to-stream';
|
|
3
|
-
import BbPromise from 'bluebird';
|
|
4
|
-
import compose from 'lodash/fp/compose.js';
|
|
5
|
-
import flatten from 'lodash/fp/flatten.js';
|
|
6
|
-
import partition from 'lodash/partition.js';
|
|
7
|
-
import uniqBy from 'lodash/uniqBy.js';
|
|
8
|
-
import { obj as Pumpify } from 'pumpify';
|
|
9
|
-
import compressHtml from "../compress-html.js";
|
|
10
|
-
import { localizeConfig } from "../config.js";
|
|
11
|
-
import GraphQLError from "../errors/graphql-error.js";
|
|
12
|
-
import PaginationError from "../errors/pagination-error.js";
|
|
13
|
-
import { getClientSchema, getQueryIterator, withQueryTransforms } from "../graphql/index.js";
|
|
14
|
-
import gzipContents from "../gzip.js";
|
|
15
|
-
import nunjucks from "../nunjucks.js";
|
|
16
|
-
import { joinPath } from "../paths.js";
|
|
17
|
-
import resolveContext, { resolveGraphQLConfig } from "../resolve-context.js";
|
|
18
|
-
import { combineContext, getItemContext, getListPageContext } from "./context.js";
|
|
19
|
-
import { createItemRenderArgs, createListRenderArgs } from "./streams.js";
|
|
20
|
-
const pageSize = Number(process.env.TS_EXPERIMENTAL_PAGE_SIZE) || 100;
|
|
21
|
-
const getPaginatedData = async (generateContext, paginate, context) => {
|
|
22
|
-
const { connector, fileLoader, srcPath, clientSchema, stats } = generateContext;
|
|
23
|
-
if (paginate.data) {
|
|
24
|
-
const config = await resolveGraphQLConfig(paginate.data, {
|
|
25
|
-
fileLoader,
|
|
26
|
-
srcPath
|
|
27
|
-
});
|
|
28
|
-
const res = await getQueryIterator(clientSchema, config.query, connector, {
|
|
29
|
-
pageSize,
|
|
30
|
-
variables: config.variables,
|
|
31
|
-
source: config.source,
|
|
32
|
-
stats
|
|
33
|
-
});
|
|
34
|
-
return {
|
|
35
|
-
iterable: res.iterator(),
|
|
36
|
-
total: res.total
|
|
37
|
-
};
|
|
38
|
-
}
|
|
39
|
-
if (paginate.property) {
|
|
40
|
-
const itemsArray = context[paginate.property];
|
|
41
|
-
if (itemsArray) {
|
|
42
|
-
const filtered = itemsArray.filter(Boolean);
|
|
43
|
-
return {
|
|
44
|
-
iterable: filtered,
|
|
45
|
-
total: filtered.length
|
|
46
|
-
};
|
|
47
|
-
}
|
|
48
|
-
}
|
|
49
|
-
return null;
|
|
50
|
-
};
|
|
51
|
-
export function calculatePages(total, pageSize) {
|
|
52
|
-
return Math.ceil(total / pageSize);
|
|
53
|
-
}
|
|
54
|
-
export function hasListPageConfig(paginate) {
|
|
55
|
-
return Boolean(paginate.pageSize && paginate.template && paginate.path);
|
|
56
|
-
}
|
|
57
|
-
export function hasItemPageConfig(route) {
|
|
58
|
-
return Boolean(route.path && route.template);
|
|
59
|
-
}
|
|
60
|
-
export function renderPaginatedTemplate(generateContext, getPaginatedData) {
|
|
61
|
-
const { renderTemplate, stats, pathPrefix } = generateContext;
|
|
62
|
-
return async (route, context) => {
|
|
63
|
-
const { paginate } = route;
|
|
64
|
-
if (!paginate) {
|
|
65
|
-
throw new Error('Route missing paginate');
|
|
66
|
-
}
|
|
67
|
-
const shouldRenderItemPage = hasItemPageConfig(route);
|
|
68
|
-
const shouldRenderListPage = hasListPageConfig(paginate);
|
|
69
|
-
try {
|
|
70
|
-
const paginatedData = await getPaginatedData(generateContext, paginate, context);
|
|
71
|
-
if (!paginatedData) {
|
|
72
|
-
return [];
|
|
73
|
-
}
|
|
74
|
-
const totalPages = calculatePages(paginatedData.total, paginate.pageSize);
|
|
75
|
-
const routeContext = {
|
|
76
|
-
pathPrefix,
|
|
77
|
-
totalPages,
|
|
78
|
-
renderTemplate,
|
|
79
|
-
route,
|
|
80
|
-
context
|
|
81
|
-
};
|
|
82
|
-
const pages = [];
|
|
83
|
-
const writePages = () => createAsyncWritable(async (args) => {
|
|
84
|
-
pages.push(await renderTemplate.apply(null, args));
|
|
85
|
-
}, 100);
|
|
86
|
-
const writeStreams = [];
|
|
87
|
-
if (shouldRenderItemPage) {
|
|
88
|
-
writeStreams.push(new Pumpify(createItemRenderArgs(routeContext, getItemContext, stats), writePages()));
|
|
89
|
-
}
|
|
90
|
-
if (shouldRenderListPage) {
|
|
91
|
-
writeStreams.push(new Pumpify(createListRenderArgs(routeContext, getListPageContext), writePages()));
|
|
92
|
-
}
|
|
93
|
-
const data = asyncIteratorToStream.obj(paginatedData.iterable);
|
|
94
|
-
await BbPromise.map(writeStreams, async (writeStream) => pump(data, writeStream));
|
|
95
|
-
return pages;
|
|
96
|
-
}
|
|
97
|
-
catch (e) {
|
|
98
|
-
if (e instanceof GraphQLError || e instanceof PaginationError) {
|
|
99
|
-
throw e;
|
|
100
|
-
}
|
|
101
|
-
throw new Error(`Failed to render paginated route ${route.path}\n ${e.name}: ${e.message}`);
|
|
102
|
-
}
|
|
103
|
-
};
|
|
104
|
-
}
|
|
105
|
-
async function resolveRouteContext(generateContext, route) {
|
|
106
|
-
const { srcPath, connector, fileLoader, stats } = generateContext;
|
|
107
|
-
const contextConfig = route.context;
|
|
108
|
-
return contextConfig
|
|
109
|
-
? resolveContext({
|
|
110
|
-
contextConfig,
|
|
111
|
-
srcPath,
|
|
112
|
-
connector,
|
|
113
|
-
fileLoader,
|
|
114
|
-
stats,
|
|
115
|
-
route
|
|
116
|
-
})
|
|
117
|
-
: {};
|
|
118
|
-
}
|
|
119
|
-
function renderTemplates(generateContext) {
|
|
120
|
-
const { renderTemplate, config, globalContext, pathPrefix } = generateContext;
|
|
121
|
-
return async (routes) => BbPromise.map(routes, async (route) => {
|
|
122
|
-
const routeContext = await resolveRouteContext(generateContext, route);
|
|
123
|
-
const context = combineContext(config.env, globalContext, route, routeContext);
|
|
124
|
-
const path = joinPath(pathPrefix, route.path);
|
|
125
|
-
const page = await renderTemplate(path, route.template, context);
|
|
126
|
-
return {
|
|
127
|
-
pages: [page],
|
|
128
|
-
order: route._routeOrder
|
|
129
|
-
};
|
|
130
|
-
});
|
|
131
|
-
}
|
|
132
|
-
function renderPaginatedTemplates(generateContext) {
|
|
133
|
-
const render = renderPaginatedTemplate(generateContext, getPaginatedData);
|
|
134
|
-
return async (routes) => {
|
|
135
|
-
const { config, globalContext } = generateContext;
|
|
136
|
-
return BbPromise.map(routes, async (route) => {
|
|
137
|
-
const routeContext = await resolveRouteContext(generateContext, route);
|
|
138
|
-
const renderedPages = await render(route, combineContext(config.env, globalContext, route, routeContext));
|
|
139
|
-
return {
|
|
140
|
-
pages: renderedPages,
|
|
141
|
-
order: route._routeOrder
|
|
142
|
-
};
|
|
143
|
-
});
|
|
144
|
-
};
|
|
145
|
-
}
|
|
146
|
-
async function generatePages(config, generateContext) {
|
|
147
|
-
const routeEntries = Object.entries(config.routes);
|
|
148
|
-
const routesWithOrder = routeEntries.map(([, route], index) => ({ ...route, _routeOrder: index }));
|
|
149
|
-
const [paginatedRouteConfigs, singleRouteConfigs] = partition(routesWithOrder, 'paginate');
|
|
150
|
-
const renderContext = {
|
|
151
|
-
...generateContext,
|
|
152
|
-
globalContext: {
|
|
153
|
-
...(config.context
|
|
154
|
-
? await resolveContext({
|
|
155
|
-
contextConfig: config.context,
|
|
156
|
-
srcPath: generateContext.srcPath,
|
|
157
|
-
connector: generateContext.connector,
|
|
158
|
-
fileLoader: generateContext.fileLoader,
|
|
159
|
-
stats: generateContext.stats
|
|
160
|
-
})
|
|
161
|
-
: {}),
|
|
162
|
-
locale: config.locale
|
|
163
|
-
}
|
|
164
|
-
};
|
|
165
|
-
const singleRoutes = await renderTemplates(renderContext)(singleRouteConfigs);
|
|
166
|
-
const paginatedRoutes = await renderPaginatedTemplates(renderContext)(paginatedRouteConfigs);
|
|
167
|
-
const allRoutes = singleRoutes.concat(paginatedRoutes);
|
|
168
|
-
const sortedRoutes = allRoutes.sort((a, b) => a.order - b.order);
|
|
169
|
-
const allPages = sortedRoutes.flatMap((route) => route.pages);
|
|
170
|
-
// First route wins
|
|
171
|
-
return uniqBy(allPages, 'path');
|
|
172
|
-
}
|
|
173
|
-
function removeListingPageConfig(routeConfig) {
|
|
174
|
-
if (routeConfig.paginate) {
|
|
175
|
-
const { template, ...rest } = routeConfig.paginate;
|
|
176
|
-
if (template) {
|
|
177
|
-
return {
|
|
178
|
-
...routeConfig,
|
|
179
|
-
paginate: {
|
|
180
|
-
...rest
|
|
181
|
-
}
|
|
182
|
-
};
|
|
183
|
-
}
|
|
184
|
-
}
|
|
185
|
-
return routeConfig;
|
|
186
|
-
}
|
|
187
|
-
export async function generateRoute(config, params) {
|
|
188
|
-
const { connector, fileLoader, templateFileLoader, routeName, locale, contentId } = params;
|
|
189
|
-
const srcPath = config.templatePath;
|
|
190
|
-
const stats = {
|
|
191
|
-
pagesGenerated: 0,
|
|
192
|
-
warnings: []
|
|
193
|
-
};
|
|
194
|
-
if (config.usageStats) {
|
|
195
|
-
stats.contentUsage = {};
|
|
196
|
-
}
|
|
197
|
-
const clientSchema = await getClientSchema(connector);
|
|
198
|
-
const { locales } = config;
|
|
199
|
-
const localizedConfig = locales && locale && locales[locale] ? localizeConfig(config, locale) : config;
|
|
200
|
-
const routeConfig = config.routes[routeName];
|
|
201
|
-
if (!routeConfig) {
|
|
202
|
-
return { pages: [], stats };
|
|
203
|
-
}
|
|
204
|
-
const globalContext = config.context
|
|
205
|
-
? await resolveContext({
|
|
206
|
-
contextConfig: config.context,
|
|
207
|
-
srcPath,
|
|
208
|
-
connector,
|
|
209
|
-
fileLoader,
|
|
210
|
-
stats
|
|
211
|
-
})
|
|
212
|
-
: {};
|
|
213
|
-
const renderContext = {
|
|
214
|
-
renderTemplate: nunjucks(templateFileLoader, localizedConfig, stats),
|
|
215
|
-
pathPrefix: localizedConfig.pathPrefix || '',
|
|
216
|
-
fileLoader,
|
|
217
|
-
connector: withQueryTransforms(connector, clientSchema, {
|
|
218
|
-
locale,
|
|
219
|
-
contentId,
|
|
220
|
-
usage: config.usageStats
|
|
221
|
-
}),
|
|
222
|
-
clientSchema,
|
|
223
|
-
srcPath,
|
|
224
|
-
stats,
|
|
225
|
-
config,
|
|
226
|
-
globalContext
|
|
227
|
-
};
|
|
228
|
-
const routeWithOrder = { ...routeConfig, _routeOrder: 0 };
|
|
229
|
-
const routes = await (routeConfig.paginate
|
|
230
|
-
? renderPaginatedTemplates(renderContext)([{ ...removeListingPageConfig(routeConfig), _routeOrder: 0 }])
|
|
231
|
-
: renderTemplates(renderContext)([routeWithOrder]));
|
|
232
|
-
// Flatten routes to pages since there's only one route
|
|
233
|
-
const pages = routes.flatMap((route) => route.pages);
|
|
234
|
-
return {
|
|
235
|
-
pages,
|
|
236
|
-
stats
|
|
237
|
-
};
|
|
238
|
-
}
|
|
239
|
-
const identity = (obj) => obj;
|
|
240
|
-
function getRenderTemplateDecorator(config) {
|
|
241
|
-
const decorators = [];
|
|
242
|
-
if (config.gzip) {
|
|
243
|
-
decorators.push(gzipContents);
|
|
244
|
-
}
|
|
245
|
-
if (config.htmlCompression?.enabled) {
|
|
246
|
-
decorators.push(compressHtml(config.htmlCompression));
|
|
247
|
-
}
|
|
248
|
-
return decorators.length ? compose(decorators) : identity;
|
|
249
|
-
}
|
|
250
|
-
export default async function generate(config, params) {
|
|
251
|
-
const { connector, fileLoader, templateFileLoader } = params;
|
|
252
|
-
const srcPath = config.templatePath;
|
|
253
|
-
const stats = {
|
|
254
|
-
pagesGenerated: 0,
|
|
255
|
-
warnings: []
|
|
256
|
-
};
|
|
257
|
-
if (config.usageStats) {
|
|
258
|
-
stats.contentUsage = {};
|
|
259
|
-
}
|
|
260
|
-
const clientSchema = await getClientSchema(connector);
|
|
261
|
-
const generateContext = {
|
|
262
|
-
pathPrefix: '',
|
|
263
|
-
clientSchema,
|
|
264
|
-
srcPath,
|
|
265
|
-
stats,
|
|
266
|
-
config,
|
|
267
|
-
fileLoader
|
|
268
|
-
};
|
|
269
|
-
let pages;
|
|
270
|
-
const renderTemplateDecorator = getRenderTemplateDecorator(config);
|
|
271
|
-
const { locales } = config;
|
|
272
|
-
if (locales) {
|
|
273
|
-
const localizedPages = await BbPromise.map(Object.keys(locales), async (locale) => {
|
|
274
|
-
const localizedConfig = localizeConfig(config, locale);
|
|
275
|
-
return generatePages(localizedConfig, {
|
|
276
|
-
...generateContext,
|
|
277
|
-
renderTemplate: renderTemplateDecorator(nunjucks(templateFileLoader, localizedConfig, stats)),
|
|
278
|
-
pathPrefix: localizedConfig.pathPrefix,
|
|
279
|
-
connector: withQueryTransforms(connector, clientSchema, {
|
|
280
|
-
locale,
|
|
281
|
-
usage: config.usageStats
|
|
282
|
-
})
|
|
283
|
-
});
|
|
284
|
-
});
|
|
285
|
-
pages = flatten(localizedPages);
|
|
286
|
-
}
|
|
287
|
-
else {
|
|
288
|
-
pages = await generatePages(config, {
|
|
289
|
-
...generateContext,
|
|
290
|
-
renderTemplate: renderTemplateDecorator(nunjucks(templateFileLoader, config, stats)),
|
|
291
|
-
connector: withQueryTransforms(connector, clientSchema, {
|
|
292
|
-
usage: config.usageStats
|
|
293
|
-
})
|
|
294
|
-
});
|
|
295
|
-
}
|
|
296
|
-
return {
|
|
297
|
-
pages,
|
|
298
|
-
stats
|
|
299
|
-
};
|
|
300
|
-
}
|
package/dist/generate/index.d.ts
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { default, generateRoute } from './generate.ts';
|
package/dist/generate/index.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export { default, generateRoute } from "./generate.js";
|
|
@@ -1,7 +0,0 @@
|
|
|
1
|
-
import { Transform } from 'node:stream';
|
|
2
|
-
import type { Stats } from '../types.ts';
|
|
3
|
-
import type { GetItemContext, GetListPageContext } from './context.ts';
|
|
4
|
-
import type { PathItem, PathItemContext, RouteContext } from './types.ts';
|
|
5
|
-
export declare function readPageBuffer(buffer: PathItem[], last: boolean): PathItemContext;
|
|
6
|
-
export declare function createItemRenderArgs(routeContext: RouteContext, getItemContext: GetItemContext, stats: Stats): Transform;
|
|
7
|
-
export declare function createListRenderArgs(routeContext: RouteContext, getListPageContext: GetListPageContext): Transform;
|
package/dist/generate/streams.js
DELETED
|
@@ -1,88 +0,0 @@
|
|
|
1
|
-
import { Transform } from 'node:stream';
|
|
2
|
-
import { formatPath } from '@takeshape/routing';
|
|
3
|
-
import { joinPath } from "../paths.js";
|
|
4
|
-
import { generateWarning, recordContentUsage } from "../stats.js";
|
|
5
|
-
export function readPageBuffer(buffer, last) {
|
|
6
|
-
const { length } = buffer;
|
|
7
|
-
const offset = length === 1 || (length < 3 && !last) ? -1 : 0;
|
|
8
|
-
return {
|
|
9
|
-
previous: buffer[offset],
|
|
10
|
-
current: buffer[1 + offset],
|
|
11
|
-
next: buffer[2 + offset]
|
|
12
|
-
};
|
|
13
|
-
}
|
|
14
|
-
function handlePathWarnings(stats, warnings, route) {
|
|
15
|
-
for (const variable of warnings) {
|
|
16
|
-
generateWarning(stats, 'renderPaginatedTemplate', `${route.path} variable ${variable} resolves to undefined.`);
|
|
17
|
-
}
|
|
18
|
-
}
|
|
19
|
-
export function createItemRenderArgs(routeContext, getItemContext, stats) {
|
|
20
|
-
const { route, context, pathPrefix } = routeContext;
|
|
21
|
-
const buffer = [];
|
|
22
|
-
const createArgs = (last) => {
|
|
23
|
-
const itemContext = getItemContext(route, context, readPageBuffer(buffer, last));
|
|
24
|
-
return [itemContext.currentPath, route.template, itemContext];
|
|
25
|
-
};
|
|
26
|
-
return new Transform({
|
|
27
|
-
objectMode: true,
|
|
28
|
-
transform(obj, _, next) {
|
|
29
|
-
const { path, warnings } = formatPath(route.path, obj);
|
|
30
|
-
const currentPath = joinPath(pathPrefix, path);
|
|
31
|
-
if (warnings.length) {
|
|
32
|
-
handlePathWarnings(stats, warnings, route);
|
|
33
|
-
}
|
|
34
|
-
else {
|
|
35
|
-
buffer.push({ item: obj, path: currentPath });
|
|
36
|
-
if (buffer.length > 1) {
|
|
37
|
-
this.push(createArgs(false));
|
|
38
|
-
if (buffer.length > 2) {
|
|
39
|
-
buffer.shift();
|
|
40
|
-
}
|
|
41
|
-
}
|
|
42
|
-
recordContentUsage(stats, obj, currentPath);
|
|
43
|
-
}
|
|
44
|
-
next();
|
|
45
|
-
},
|
|
46
|
-
flush(done) {
|
|
47
|
-
if (buffer.length) {
|
|
48
|
-
this.push(createArgs(true));
|
|
49
|
-
}
|
|
50
|
-
done();
|
|
51
|
-
}
|
|
52
|
-
});
|
|
53
|
-
}
|
|
54
|
-
export function createListRenderArgs(routeContext, getListPageContext) {
|
|
55
|
-
const { pathPrefix, route } = routeContext;
|
|
56
|
-
const { paginate } = route;
|
|
57
|
-
if (!paginate) {
|
|
58
|
-
throw new Error('Cannot create list page for non-paginated route');
|
|
59
|
-
}
|
|
60
|
-
const { template, pageSize } = paginate;
|
|
61
|
-
if (!template) {
|
|
62
|
-
throw new Error('Cannot create list page missing paginate.template');
|
|
63
|
-
}
|
|
64
|
-
let buffer = [];
|
|
65
|
-
let page = 1;
|
|
66
|
-
const createArgs = () => {
|
|
67
|
-
const context = getListPageContext(buffer, page, routeContext);
|
|
68
|
-
page++;
|
|
69
|
-
buffer = [];
|
|
70
|
-
return [joinPath(pathPrefix, context.currentPath), template, context];
|
|
71
|
-
};
|
|
72
|
-
return new Transform({
|
|
73
|
-
objectMode: true,
|
|
74
|
-
transform(obj, _, next) {
|
|
75
|
-
buffer.push(obj);
|
|
76
|
-
if (buffer.length === pageSize) {
|
|
77
|
-
this.push(createArgs());
|
|
78
|
-
}
|
|
79
|
-
next();
|
|
80
|
-
},
|
|
81
|
-
flush(done) {
|
|
82
|
-
if (buffer.length) {
|
|
83
|
-
this.push(createArgs());
|
|
84
|
-
}
|
|
85
|
-
done();
|
|
86
|
-
}
|
|
87
|
-
});
|
|
88
|
-
}
|
package/dist/generate/types.d.ts
DELETED
|
@@ -1,54 +0,0 @@
|
|
|
1
|
-
import type { GraphQLSchema } from 'graphql';
|
|
2
|
-
import type { Config, FileLoader, PaginateConfig, RouteConfig, RoutesMap } from '../config.ts';
|
|
3
|
-
import type { Data, GraphQLConnector, RenderedPage, RenderTemplate, Stats } from '../types.ts';
|
|
4
|
-
export type GenerateResult = {
|
|
5
|
-
pages: RenderedPage[];
|
|
6
|
-
stats: Stats;
|
|
7
|
-
};
|
|
8
|
-
export type GenerateContext = {
|
|
9
|
-
config: Config;
|
|
10
|
-
pathPrefix: string;
|
|
11
|
-
clientSchema: GraphQLSchema;
|
|
12
|
-
srcPath: string;
|
|
13
|
-
stats: Stats;
|
|
14
|
-
renderTemplate: RenderTemplate;
|
|
15
|
-
connector: GraphQLConnector;
|
|
16
|
-
fileLoader: FileLoader;
|
|
17
|
-
};
|
|
18
|
-
export type RenderContext = {
|
|
19
|
-
globalContext: Data;
|
|
20
|
-
} & GenerateContext;
|
|
21
|
-
export type RouteContext = {
|
|
22
|
-
pathPrefix: string;
|
|
23
|
-
totalPages: number;
|
|
24
|
-
renderTemplate: RenderTemplate;
|
|
25
|
-
route: RouteConfig;
|
|
26
|
-
context: Data;
|
|
27
|
-
};
|
|
28
|
-
export type PathItem = {
|
|
29
|
-
item: Data;
|
|
30
|
-
path: string;
|
|
31
|
-
};
|
|
32
|
-
export type PathItemContext = {
|
|
33
|
-
previous?: PathItem;
|
|
34
|
-
current: PathItem;
|
|
35
|
-
next?: PathItem;
|
|
36
|
-
};
|
|
37
|
-
export type ItemBuffer = {
|
|
38
|
-
push(item: Data, path: string): void;
|
|
39
|
-
done(): Promise<RenderedPage[]>;
|
|
40
|
-
};
|
|
41
|
-
export type ListPageBuffer = {
|
|
42
|
-
push(item: Data): void;
|
|
43
|
-
done(): Promise<RenderedPage[]>;
|
|
44
|
-
};
|
|
45
|
-
export type ResolveRoutesContextParams = {
|
|
46
|
-
routes: RoutesMap;
|
|
47
|
-
srcPath: string;
|
|
48
|
-
connector: GraphQLConnector;
|
|
49
|
-
stats: Stats;
|
|
50
|
-
};
|
|
51
|
-
export type GetPaginatedData = (generateContext: GenerateContext, paginate: PaginateConfig, context: Data) => Promise<{
|
|
52
|
-
iterable: Iterable<Data>;
|
|
53
|
-
total: number;
|
|
54
|
-
} | null>;
|
package/dist/generate/types.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
import { type DocumentNode, type GraphQLSchema } from 'graphql';
|
|
2
|
-
import { type Config, type FileLoader, type RouteInfo } from '../config.ts';
|
|
3
|
-
type FileInfo = {
|
|
4
|
-
body: string;
|
|
5
|
-
name: string;
|
|
6
|
-
};
|
|
7
|
-
type Usage = {
|
|
8
|
-
file: string;
|
|
9
|
-
location: {
|
|
10
|
-
line: number;
|
|
11
|
-
column: number;
|
|
12
|
-
};
|
|
13
|
-
};
|
|
14
|
-
type UsageInfo = {
|
|
15
|
-
type: string;
|
|
16
|
-
usage: Usage[];
|
|
17
|
-
};
|
|
18
|
-
type UsageInfoMap = Record<string, Record<string, UsageInfo>>;
|
|
19
|
-
export declare function getFieldUsage(queryAst: DocumentNode, schema: GraphQLSchema, fileInfo: FileInfo): UsageInfoMap;
|
|
20
|
-
export declare function detectTypes(queryAst: DocumentNode, schema: GraphQLSchema): Set<string>;
|
|
21
|
-
export type TypeUsage = Record<string, RouteInfo[]>;
|
|
22
|
-
export type GetTypeUsageParams = {
|
|
23
|
-
config: Config;
|
|
24
|
-
schema: GraphQLSchema;
|
|
25
|
-
fileLoader: FileLoader;
|
|
26
|
-
};
|
|
27
|
-
export declare function getTypeUsage({ config, schema, fileLoader }: GetTypeUsageParams): Promise<TypeUsage>;
|
|
28
|
-
export {};
|
package/dist/graphql/analyze.js
DELETED
|
@@ -1,87 +0,0 @@
|
|
|
1
|
-
import path from 'node:path';
|
|
2
|
-
import BbPromise from 'bluebird';
|
|
3
|
-
import { getLocation, isListType, isObjectType, parse, Source, TypeInfo, visit, visitWithTypeInfo } from 'graphql';
|
|
4
|
-
import { getGraphQLQueries } from "../config.js";
|
|
5
|
-
import { getFields, getItemType } from "./query.js";
|
|
6
|
-
const startLocation = { line: 1, column: 1 };
|
|
7
|
-
export function getFieldUsage(queryAst, schema, fileInfo) {
|
|
8
|
-
const typeInfo = new TypeInfo(schema);
|
|
9
|
-
const result = {};
|
|
10
|
-
const visitor = {
|
|
11
|
-
Field: {
|
|
12
|
-
enter(node) {
|
|
13
|
-
const field = typeInfo.getFieldDef();
|
|
14
|
-
if (!field) {
|
|
15
|
-
return;
|
|
16
|
-
}
|
|
17
|
-
const type = getItemType(field.type);
|
|
18
|
-
const fields = getFields(type);
|
|
19
|
-
const fieldInfo = result[type.toString()] || {};
|
|
20
|
-
if (fields && node.selectionSet) {
|
|
21
|
-
for (const selection of node.selectionSet.selections) {
|
|
22
|
-
if (selection.kind === 'Field' || selection.kind === 'FragmentSpread') {
|
|
23
|
-
const name = selection.name.value;
|
|
24
|
-
const usage = fieldInfo[name] ? fieldInfo[name].usage : [];
|
|
25
|
-
const source = new Source(fileInfo.body, fileInfo.name, startLocation);
|
|
26
|
-
fieldInfo[name] = {
|
|
27
|
-
type: fields[name].type.toString(),
|
|
28
|
-
usage: usage.concat({
|
|
29
|
-
file: fileInfo.name,
|
|
30
|
-
location: selection.loc ? getLocation(source, selection.loc.start) : startLocation
|
|
31
|
-
})
|
|
32
|
-
};
|
|
33
|
-
}
|
|
34
|
-
}
|
|
35
|
-
result[type.toString()] = fieldInfo;
|
|
36
|
-
}
|
|
37
|
-
}
|
|
38
|
-
}
|
|
39
|
-
};
|
|
40
|
-
visit(queryAst, visitWithTypeInfo(typeInfo, visitor));
|
|
41
|
-
return result;
|
|
42
|
-
}
|
|
43
|
-
export function detectTypes(queryAst, schema) {
|
|
44
|
-
const typeInfo = new TypeInfo(schema);
|
|
45
|
-
const result = new Set();
|
|
46
|
-
const queryType = schema.getQueryType();
|
|
47
|
-
if (!queryType) {
|
|
48
|
-
throw new Error('Invalid schema has no queries');
|
|
49
|
-
}
|
|
50
|
-
const topLevelQueries = new Set(Object.keys(queryType.getFields()));
|
|
51
|
-
const visitor = {
|
|
52
|
-
Field: {
|
|
53
|
-
enter(node) {
|
|
54
|
-
if (topLevelQueries.has(node.name.value)) {
|
|
55
|
-
const field = typeInfo.getFieldDef();
|
|
56
|
-
if (field) {
|
|
57
|
-
const fieldType = field.type;
|
|
58
|
-
if (isObjectType(fieldType)) {
|
|
59
|
-
const fields = fieldType.getFields();
|
|
60
|
-
if (fields.items && isListType(fields.items.type)) {
|
|
61
|
-
result.add(fields.items.type.ofType.toString());
|
|
62
|
-
}
|
|
63
|
-
else {
|
|
64
|
-
result.add(fieldType.toString());
|
|
65
|
-
}
|
|
66
|
-
}
|
|
67
|
-
}
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
}
|
|
71
|
-
};
|
|
72
|
-
visit(queryAst, visitWithTypeInfo(typeInfo, visitor));
|
|
73
|
-
return result;
|
|
74
|
-
}
|
|
75
|
-
export async function getTypeUsage({ config, schema, fileLoader }) {
|
|
76
|
-
const queries = getGraphQLQueries(config);
|
|
77
|
-
return BbPromise.reduce(queries, async (result, routeQuery) => {
|
|
78
|
-
const { filePath, ...info } = routeQuery;
|
|
79
|
-
const queryString = await fileLoader(path.join(config.templatePath, filePath));
|
|
80
|
-
const types = detectTypes(parse(queryString), schema);
|
|
81
|
-
for (const type of types) {
|
|
82
|
-
result[type] ||= [];
|
|
83
|
-
result[type].push(info);
|
|
84
|
-
}
|
|
85
|
-
return result;
|
|
86
|
-
}, {});
|
|
87
|
-
}
|
package/dist/graphql/ast.d.ts
DELETED
|
@@ -1,19 +0,0 @@
|
|
|
1
|
-
import type { ArgumentNode, DefinitionNode, DocumentNode, FieldNode, OperationDefinitionNode, SelectionNode, SelectionSetNode, VariableDefinitionNode } from 'graphql';
|
|
2
|
-
export type Arg = {
|
|
3
|
-
name: string;
|
|
4
|
-
value: string;
|
|
5
|
-
};
|
|
6
|
-
export type Var = {
|
|
7
|
-
name: string;
|
|
8
|
-
type: string;
|
|
9
|
-
};
|
|
10
|
-
export declare function createArgument({ name, value }: Arg): ArgumentNode;
|
|
11
|
-
export declare function createVariableDefinition({ name, type }: Var): VariableDefinitionNode;
|
|
12
|
-
export declare function createSelectionSet(selections: SelectionNode[]): SelectionSetNode;
|
|
13
|
-
export declare function createField(name: string): FieldNode;
|
|
14
|
-
export declare function isQueryNode(node: DefinitionNode): node is OperationDefinitionNode;
|
|
15
|
-
export declare function findQuery(ast: DocumentNode): OperationDefinitionNode | undefined;
|
|
16
|
-
export declare function updateQuery(ast: DocumentNode, update: (query: OperationDefinitionNode) => OperationDefinitionNode): DocumentNode;
|
|
17
|
-
export declare function addQueryVariables(variables: Var[], ast: DocumentNode): DocumentNode;
|
|
18
|
-
export declare function wrapSelectionSet(selectionSet: SelectionSetNode, name: string, args?: ArgumentNode[]): SelectionSetNode;
|
|
19
|
-
export declare function wrapQuery(name: string, args: Arg[], ast: DocumentNode): DocumentNode;
|