diff --git a/.changeset/dull-moles-deny.md b/.changeset/dull-moles-deny.md
new file mode 100644
index 000000000..ed98b7ef4
--- /dev/null
+++ b/.changeset/dull-moles-deny.md
@@ -0,0 +1,5 @@
+---
+'@shopify/theme-check-docs-updater': minor
+---
+
+Add `theme-docs dependencies` command
diff --git a/packages/theme-check-docs-updater/package.json b/packages/theme-check-docs-updater/package.json
index a4f159d5f..27caee101 100644
--- a/packages/theme-check-docs-updater/package.json
+++ b/packages/theme-check-docs-updater/package.json
@@ -19,13 +19,13 @@
"@shopify:registry": "https://registry.npmjs.org"
},
"bin": {
- "theme-docs": "./scripts/cli.js"
+ "theme-docs": "./dist/cli.js"
},
"scripts": {
"build": "yarn build:ts",
"build:ci": "yarn build",
"build:ts": "tsc -b tsconfig.build.json",
- "postbuild": "node scripts/cli.js download data",
+ "postbuild": "chmod u+x dist/cli.js && node dist/cli.js download data",
"test": "vitest",
"type-check": "tsc --noEmit"
},
diff --git a/packages/theme-check-docs-updater/scripts/cli.js b/packages/theme-check-docs-updater/scripts/cli.js
deleted file mode 100755
index fa6597e0e..000000000
--- a/packages/theme-check-docs-updater/scripts/cli.js
+++ /dev/null
@@ -1,48 +0,0 @@
-#!/usr/bin/env node
-
-const path = require('path');
-const fs = require('fs');
-const { downloadThemeLiquidDocs, root } = require(path.resolve(__dirname, '../dist'));
-
-// Get the command line arguments
-const args = process.argv.slice(2);
-
-// Check if a command was provided
-if (args.length === 0) {
- console.log(`
-Please provide a command.
-
-Usage:
- download
\t\tDownloads all docsets and JSON Schemas to the specified directory.
- root \tPrints the default docsets root directory.
- clear-cache \tClears the default docsets root directory.
-`);
- process.exit(1);
-}
-
-// Handle the command
-switch (args[0]) {
- case 'download':
- if (args.length > 2) {
- console.log('Please provide a directory to download docs into.');
- process.exit(1);
- }
- console.log('Downloading docs...');
-
- downloadThemeLiquidDocs(args[1], console.error.bind(console));
-
- break;
-
- case 'root':
- console.log(root);
- break;
-
- case 'clear-cache':
- console.log(`Removing '${root}'`);
- fs.rmSync(root, { recursive: true });
- break;
-
- default:
- console.log(`Unknown command: ${args[0]}`);
- process.exit(1);
-}
diff --git a/packages/theme-check-docs-updater/src/cli.ts b/packages/theme-check-docs-updater/src/cli.ts
new file mode 100755
index 000000000..b79b487f2
--- /dev/null
+++ b/packages/theme-check-docs-updater/src/cli.ts
@@ -0,0 +1,74 @@
+#!/usr/bin/env node
+
+import fs from 'node:fs';
+import { downloadThemeLiquidDocs, root, ThemeLiquidDocsManager } from '.';
+
+// Get the command line arguments
+const args = process.argv.slice(2);
+
+// Check if a command was provided
+if (args.length === 0) {
+ console.log(`
+Please provide a command.
+
+Usage:
+ download \t\tDownloads all docsets and JSON Schemas to the specified directory.
+ dependencies \t\tPrints the up to date theme dependencies.
+ root \tPrints the default docsets root directory.
+ clear-cache \tClears the default docsets root directory.
+`);
+ process.exit(1);
+}
+
+async function main() {
+ // Handle the command
+ switch (args[0]) {
+ case 'download':
+ if (args.length > 2) {
+ console.log('Please provide a directory to download docs into.');
+ process.exit(1);
+ }
+ console.log('Downloading docs...');
+
+ downloadThemeLiquidDocs(args[1], console.error.bind(console));
+
+ break;
+
+ case 'dependencies':
+ // This command is used to print the current state of the docs.
+ // It's a bit like what the webpack build of the fallback does in the browser VS Code extension.
+ const docsManager = new ThemeLiquidDocsManager();
+ const [tags, filters, objects, systemTranslations, schemas] = await Promise.all([
+ docsManager.tags(),
+ docsManager.filters(),
+ docsManager.objects(),
+ docsManager.systemTranslations(),
+ docsManager.schemas('theme'), // assuming we want the theme JSON schema validation
+ ]);
+ console.log(
+ JSON.stringify({
+ tags,
+ filters,
+ objects,
+ systemTranslations,
+ schemas,
+ }),
+ );
+ break;
+
+ case 'root':
+ console.log(root);
+ break;
+
+ case 'clear-cache':
+ console.log(`Removing '${root}'`);
+ fs.rmSync(root, { recursive: true });
+ break;
+
+ default:
+ console.log(`Unknown command: ${args[0]}`);
+ process.exit(1);
+ }
+}
+
+main();
diff --git a/packages/vscode-extension/src/browser/ThemeDocset.ts b/packages/vscode-extension/src/browser/ThemeDocset.ts
new file mode 100644
index 000000000..465252948
--- /dev/null
+++ b/packages/vscode-extension/src/browser/ThemeDocset.ts
@@ -0,0 +1,63 @@
+import { memo } from '@shopify/theme-check-common';
+import { Dependencies } from '@shopify/theme-language-server-browser';
+import { Connection } from 'vscode-languageserver/browser';
+
+/**
+ * These are replaced at build time by the contents of
+ * @shopify/theme-check-docs-updater's DocsManager
+ */
+declare global {
+ export const WEBPACK_TAGS: any[];
+ export const WEBPACK_FILTERS: any[];
+ export const WEBPACK_OBJECTS: any[];
+ export const WEBPACK_SYSTEM_TRANSLATIONS: any;
+ export const WEBPACK_SCHEMAS: any;
+}
+
+const tags = WEBPACK_TAGS;
+const filters = WEBPACK_FILTERS;
+const objects = WEBPACK_OBJECTS;
+const systemTranslations = WEBPACK_SYSTEM_TRANSLATIONS;
+const schemas = WEBPACK_SCHEMAS;
+
+type ThemeDocset = Dependencies['themeDocset'];
+type JsonValidationSet = Dependencies['jsonValidationSet'];
+
+const fetchDeps = memo(async () => {
+ return fetch('https://vs-code-for-web.shop.dev/deps.json').then((response) => {
+ if (!response.ok) {
+ console.error(response);
+ throw new Error(`Failed to fetch dependencies: ${response.statusText}`);
+ }
+ return response.json();
+ });
+});
+
+export class ThemeDocsetManager implements ThemeDocset, JsonValidationSet {
+ constructor(private connection: Connection) {}
+
+ // Liquid documentation
+ filters = memo(async () => this.fetchUpdatedData('filters', filters));
+ tags = memo(async () => this.fetchUpdatedData('tags', tags));
+ objects = memo(async () => this.fetchUpdatedData('objects', objects));
+ liquidDrops = memo(async () => this.fetchUpdatedData('objects', objects));
+
+ // prettier-ignore
+ systemTranslations = memo(async () => this.fetchUpdatedData('systemTranslations', systemTranslations));
+
+ // JSON validation data
+ schemas = memo(async () => this.fetchUpdatedData('schemas', schemas));
+
+ fetchUpdatedData = async (
+ dependency: 'filters' | 'tags' | 'objects' | 'systemTranslations' | 'schemas',
+ fallback: T,
+ ): Promise => {
+ return fetchDeps()
+ .then((deps) => deps[dependency] ?? fallback)
+ .then((data) => {
+ console.error(`data received! ${dependency}`, data);
+ return data as T;
+ })
+ .catch(() => fallback);
+ };
+}
diff --git a/packages/vscode-extension/src/browser/server.ts b/packages/vscode-extension/src/browser/server.ts
index 958d0a225..d6ad6b3c2 100644
--- a/packages/vscode-extension/src/browser/server.ts
+++ b/packages/vscode-extension/src/browser/server.ts
@@ -6,28 +6,12 @@ import {
startServer,
} from '@shopify/theme-language-server-browser';
import { VsCodeFileSystem } from '../common/VsCodeFileSystem';
-
-/**
- * These are replaced at build time by the contents of
- * @shopify/theme-check-docs-updater's DocsManager
- */
-declare global {
- export const WEBPACK_TAGS: any[];
- export const WEBPACK_FILTERS: any[];
- export const WEBPACK_OBJECTS: any[];
- export const WEBPACK_SYSTEM_TRANSLATIONS: any;
- export const WEBPACK_SCHEMAS: any;
-}
-
-const tags = WEBPACK_TAGS;
-const filters = WEBPACK_FILTERS;
-const objects = WEBPACK_OBJECTS;
-const systemTranslations = WEBPACK_SYSTEM_TRANSLATIONS;
-const schemas = WEBPACK_SCHEMAS;
+import { ThemeDocsetManager } from './ThemeDocset';
const worker = self as any as Worker;
const connection = getConnection(worker);
const fileSystem = new VsCodeFileSystem(connection, {});
+const themeDocset = new ThemeDocsetManager(connection);
const dependencies: Dependencies = {
fs: fileSystem,
log: console.info.bind(console),
@@ -45,16 +29,8 @@ const dependencies: Dependencies = {
rootUri,
};
},
- themeDocset: {
- filters: async () => filters,
- objects: async () => objects,
- liquidDrops: async () => objects,
- tags: async () => tags,
- systemTranslations: async () => systemTranslations,
- },
- jsonValidationSet: {
- schemas: async () => schemas,
- },
+ themeDocset: themeDocset,
+ jsonValidationSet: themeDocset,
};
startServer(worker, dependencies, connection);