create-jant 0.2.3 → 0.2.4

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/dist/index.js CHANGED
@@ -8,7 +8,7 @@ import path from "path";
8
8
  import { fileURLToPath } from "url";
9
9
  var __filename = fileURLToPath(import.meta.url);
10
10
  var __dirname = path.dirname(__filename);
11
- var CORE_VERSION = "0.3.7";
11
+ var CORE_VERSION = "0.3.8";
12
12
  var TEMPLATE_DIR = fs.existsSync(path.resolve(__dirname, "../template")) ? path.resolve(__dirname, "../template") : path.resolve(__dirname, "../../../templates/jant-site");
13
13
  function isValidProjectName(name) {
14
14
  return /^[a-z0-9]([a-z0-9-]*[a-z0-9])?$/.test(name);
@@ -32,8 +32,11 @@ async function copyTemplate(config) {
32
32
  if (basename === "pnpm-lock.yaml") return false;
33
33
  if (basename === "dist") return false;
34
34
  if (basename === "wrangler.demo.toml") return false;
35
- if (basename === "reset.sql") return false;
36
- if (basename === "seed.sql") return false;
35
+ if (basename === "reset-demo.sql") return false;
36
+ if (basename === "seed-demo.sql") return false;
37
+ if (basename === "reset-local.sql") return false;
38
+ if (basename === "seed-local.sql") return false;
39
+ if (basename === "export-demo.mjs") return false;
37
40
  return true;
38
41
  }
39
42
  });
@@ -72,6 +75,7 @@ async function copyTemplate(config) {
72
75
  return `${prefix}"${value}"`;
73
76
  }
74
77
  );
78
+ content = content.replace(/^.*#\s*@create-jant:\s*@remove\s*\n?/gm, "");
75
79
  await fs.writeFile(wranglerPath, content, "utf-8");
76
80
  }
77
81
  const authSecret = generateAuthSecret();
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "create-jant",
3
- "version": "0.2.3",
3
+ "version": "0.2.4",
4
4
  "description": "Create a new Jant project",
5
5
  "type": "module",
6
6
  "bin": {
@@ -0,0 +1,79 @@
1
+ import { execSync } from "child_process";
2
+ import { writeFileSync } from "fs";
3
+ import { resolve, dirname } from "path";
4
+ import { fileURLToPath } from "url";
5
+
6
+ const __dirname = dirname(fileURLToPath(import.meta.url));
7
+
8
+ function sqlValue(v) {
9
+ if (v === null) return "NULL";
10
+ if (typeof v === "number") return String(v);
11
+ return "'" + String(v).replaceAll("'", "''") + "'";
12
+ }
13
+
14
+ function queryRemote(sql) {
15
+ let stdout;
16
+ try {
17
+ stdout = execSync(
18
+ `pnpm exec wrangler d1 execute DB --remote --config wrangler.demo.toml --command "${sql}" --json`,
19
+ { encoding: "utf-8", cwd: resolve(__dirname, "..") }
20
+ );
21
+ } catch (err) {
22
+ // Wrangler returns JSON errors on stdout even with non-zero exit codes
23
+ const output = err.stdout || err.stderr || "";
24
+ try {
25
+ const errJson = JSON.parse(output.trim());
26
+ if (errJson.error?.text) {
27
+ console.error(`Wrangler error: ${errJson.error.text}`);
28
+ process.exit(1);
29
+ }
30
+ } catch {
31
+ // Not JSON, fall through
32
+ }
33
+ console.error(`Failed to query remote database: ${output || err.message}`);
34
+ process.exit(1);
35
+ }
36
+ const parsed = JSON.parse(stdout);
37
+ if (parsed.error?.text) {
38
+ console.error(`Wrangler error: ${parsed.error.text}`);
39
+ process.exit(1);
40
+ }
41
+ return parsed[0]?.results || [];
42
+ }
43
+
44
+ function dumpTable(name, query) {
45
+ const rows = queryRemote(query || `SELECT * FROM ${name}`);
46
+ return rows
47
+ .map(
48
+ (row) =>
49
+ `INSERT INTO ${name} VALUES(${Object.values(row).map(sqlValue).join(",")});`
50
+ )
51
+ .join("\n");
52
+ }
53
+
54
+ const header = `-- =============================================================================
55
+ -- Demo seed data for Jant (demo.jant.me)
56
+ -- Exported from remote demo D1 database via: mise run demo-backup
57
+ -- Usage: mise run demo-reset
58
+ -- =============================================================================
59
+ `;
60
+
61
+ const tables = [
62
+ ["settings"],
63
+ ["user"],
64
+ ["account"],
65
+ ["posts", "SELECT * FROM posts WHERE deleted_at IS NULL"],
66
+ ["collections"],
67
+ ["post_collections"],
68
+ ["media"],
69
+ ];
70
+
71
+ let sql = header;
72
+ for (const [name, query] of tables) {
73
+ const data = dumpTable(name, query);
74
+ if (data) sql += `\n-- ${name}\n${data}\n`;
75
+ }
76
+
77
+ const out = resolve(__dirname, "seed-demo.sql");
78
+ writeFileSync(out, sql);
79
+ console.log("Exported demo database to templates/jant-site/scripts/seed-demo.sql");
@@ -3,6 +3,13 @@ import { readdirSync, writeFileSync } from "fs";
3
3
  import { resolve, dirname } from "path";
4
4
  import { fileURLToPath } from "url";
5
5
 
6
+ // Parse flags
7
+ const args = process.argv.slice(2);
8
+ const noMedia = args.includes("--no-media");
9
+ const outputIndex = args.indexOf("--output");
10
+ const outputFile =
11
+ outputIndex !== -1 ? args[outputIndex + 1] : "seed-local.sql";
12
+
6
13
  // better-sqlite3 is installed in packages/core
7
14
  const __dirname = dirname(fileURLToPath(import.meta.url));
8
15
  const coreRequire = createRequire(
@@ -39,7 +46,7 @@ function dumpTable(name, query) {
39
46
  }
40
47
 
41
48
  const header = `-- =============================================================================
42
- -- Development seed data for Jant
49
+ -- ${noMedia ? "Seed data (without media)" : "Local development seed data"} for Jant
43
50
  -- Exported from local D1 database
44
51
  -- Usage: mise run db-seed
45
52
  -- =============================================================================
@@ -49,19 +56,28 @@ const tables = [
49
56
  ["settings"],
50
57
  ["user"],
51
58
  ["account"],
52
- ["posts", "SELECT * FROM posts WHERE deleted_at IS NULL"],
59
+ [
60
+ "posts",
61
+ noMedia
62
+ ? "SELECT * FROM posts WHERE deleted_at IS NULL AND type != 'image'"
63
+ : "SELECT * FROM posts WHERE deleted_at IS NULL",
64
+ ],
53
65
  ["collections"],
54
66
  ["post_collections"],
55
- ["media"],
56
67
  ];
57
68
 
69
+ // Include media table only when --no-media is not set
70
+ if (!noMedia) {
71
+ tables.push(["media"]);
72
+ }
73
+
58
74
  let sql = header;
59
75
  for (const [name, query] of tables) {
60
76
  const data = dumpTable(name, query);
61
77
  if (data) sql += `\n-- ${name}\n${data}\n`;
62
78
  }
63
79
 
64
- const out = resolve(__dirname, "seed-dev.sql");
80
+ const out = resolve(__dirname, outputFile);
65
81
  writeFileSync(out, sql);
66
82
  db.close();
67
- console.log("Exported to templates/jant-site/scripts/seed-dev.sql");
83
+ console.log(`Exported to templates/jant-site/scripts/${outputFile}`);
@@ -1,5 +1,6 @@
1
- -- Reset script for Jant demo site
2
- -- Clears all user-created data while preserving schema
1
+ -- Reset script for Jant demo site (demo.jant.me)
2
+ -- Clears all user-created data while preserving users/schema
3
+ -- Usage: mise run demo-reset (runs this then seed-demo.sql)
3
4
 
4
5
  -- Clear FTS index first (to avoid foreign key issues)
5
6
  DELETE FROM posts_fts;
@@ -21,4 +22,4 @@ DELETE FROM verification;
21
22
  DELETE FROM sqlite_sequence WHERE name IN ('posts', 'media', 'collections', 'redirects');
22
23
 
23
24
  -- Note: Settings and users are preserved
24
- -- Seed data will be re-inserted by seed.sql
25
+ -- Seed data will be re-inserted by seed-demo.sql
@@ -1,7 +1,7 @@
1
1
  -- =============================================================================
2
2
  -- Reset script for local development
3
3
  -- Clears ALL data (including users) to prepare for re-seeding
4
- -- Usage: mise run db-seed
4
+ -- Usage: mise run db-seed (runs this then seed-local.sql)
5
5
  -- =============================================================================
6
6
 
7
7
  -- Clear FTS index first
@@ -0,0 +1,70 @@
1
+ -- =============================================================================
2
+ -- Demo seed data for Jant (demo.jant.me)
3
+ -- Exported from remote demo D1 database via: mise run demo-backup
4
+ -- Usage: mise run demo-reset
5
+ -- =============================================================================
6
+
7
+ -- settings
8
+ INSERT INTO settings VALUES('ONBOARDING_STATUS','completed',1770657027);
9
+ INSERT INTO settings VALUES('SITE_LANGUAGE','zh-Hans',1770673922);
10
+ INSERT INTO settings VALUES('siteName','Jant Demo',1770689095);
11
+ INSERT INTO settings VALUES('siteDescription','A demo site for Jant - Modern microblog for Cloudflare Workers',1770689095);
12
+ INSERT INTO settings VALUES('siteUrl','https://demo.jant.me',1770689095);
13
+ INSERT INTO settings VALUES('postsPerPage','10',1770689095);
14
+ INSERT INTO settings VALUES('timezone','UTC',1770689095);
15
+ INSERT INTO settings VALUES('language','en',1770689095);
16
+
17
+ -- user
18
+ INSERT INTO user VALUES('cV9uL2nAhiFTPKgJnoiKVKyesEoWBdkY','Demo User','demo@jant.me',0,NULL,'admin',1770657027,1770657027);
19
+
20
+ -- account
21
+ INSERT INTO account VALUES('ARFNGzzGCjXacVOYu9vVbq4dwL2XuecG','cV9uL2nAhiFTPKgJnoiKVKyesEoWBdkY','credential','cV9uL2nAhiFTPKgJnoiKVKyesEoWBdkY',NULL,NULL,NULL,NULL,NULL,NULL,'2f0586376d6b21415b93d39aa00b31c3:f7adf50ededaaf477b27eb095035dc38f20ed8baa349bd10762eb5a916602342f32ac21bc8e384047361d2c67d82dbd922c906cc8fa1c43da68d8fa76e414562',1770657027,1770657027);
22
+
23
+ -- posts
24
+ INSERT INTO posts VALUES(1,'article','featured','Welcome to Jant',NULL,'# Welcome to Jant Demo
25
+
26
+ Jant is a modern microblog platform built for Cloudflare Workers. This demo site resets daily at 00:00 UTC.
27
+
28
+ ## Features
29
+
30
+ - **Multiple post types**: Notes, articles, links, quotes, images, and pages
31
+ - **Collections**: Organize posts into collections
32
+ - **Full-text search**: Search across all your content
33
+ - **Internationalization**: Built-in i18n support
34
+ - **Fast**: Edge-deployed on Cloudflare Workers
35
+
36
+ ## Getting Started
37
+
38
+ ```bash
39
+ pnpm create jant my-blog
40
+ cd my-blog
41
+ pnpm install
42
+ pnpm dev
43
+ ```
44
+
45
+ Visit the [dashboard](/dash) to create your own posts!','<h1>Welcome to Jant Demo</h1>
46
+ <p>Jant is a modern microblog platform built for Cloudflare Workers. This demo site resets daily at 00:00 UTC.</p>
47
+ <h2>Features</h2>
48
+ <ul>
49
+ <li><strong>Multiple post types</strong>: Notes, articles, links, quotes, images, and pages</li>
50
+ <li><strong>Collections</strong>: Organize posts into collections</li>
51
+ <li><strong>Full-text search</strong>: Search across all your content</li>
52
+ <li><strong>Internationalization</strong>: Built-in i18n support</li>
53
+ <li><strong>Fast</strong>: Edge-deployed on Cloudflare Workers</li>
54
+ </ul>
55
+ <h2>Getting Started</h2>
56
+ <pre><code class="language-bash">pnpm create jant my-blog
57
+ cd my-blog
58
+ pnpm install
59
+ pnpm dev
60
+ </code></pre>
61
+ <p>Visit the <a href="/dash">dashboard</a> to create your own posts!</p>',NULL,NULL,NULL,NULL,NULL,NULL,1770689095,1770689095,1770689095);
62
+ INSERT INTO posts VALUES(2,'note','quiet',NULL,NULL,'This is a demo note. Notes are short posts without titles, perfect for quick thoughts and updates.','<p>This is a demo note. Notes are short posts without titles, perfect for quick thoughts and updates.</p>',NULL,NULL,NULL,NULL,NULL,NULL,1770685495,1770685495,1770685495);
63
+ INSERT INTO posts VALUES(3,'link','quiet','Jant on GitHub',NULL,'Check out the source code and documentation for Jant.','<p>Check out the source code and documentation for Jant.</p>','https://github.com/nicepkg/jant','GitHub','github.com',NULL,NULL,NULL,1770681895,1770681895,1770681895);
64
+ INSERT INTO posts VALUES(4,'quote','quiet',NULL,NULL,'The best way to predict the future is to invent it.','<p>The best way to predict the future is to invent it.</p>',NULL,'Alan Kay',NULL,NULL,NULL,NULL,1770678295,1770678295,1770678295);
65
+
66
+ -- collections
67
+ INSERT INTO collections VALUES(1,'getting-started','Getting Started','Resources for getting started with Jant',1770689095,1770689095);
68
+
69
+ -- post_collections
70
+ INSERT INTO post_collections VALUES(1,1,1770689095);
@@ -1,6 +1,6 @@
1
1
  -- =============================================================================
2
- -- Development seed data for Jant
3
- -- Exported from local D1 database
2
+ -- Local development seed data for Jant
3
+ -- Exported from local D1 database via: mise run db-export
4
4
  -- Usage: mise run db-seed
5
5
  -- =============================================================================
6
6
 
@@ -5,6 +5,7 @@ name = "jant-demo"
5
5
  main = "src/index.ts"
6
6
  compatibility_date = "2026-01-20"
7
7
  compatibility_flags = ["nodejs_compat"]
8
+ account_id = "03e7294bdb3750ed5a0d6afef6d770e4"
8
9
 
9
10
  [vars]
10
11
  SITE_URL = "https://demo.jant.me"
@@ -2,6 +2,7 @@ name = "jant-site" # @create-jant: "${name}"
2
2
  main = "src/index.ts"
3
3
  compatibility_date = "2026-01-20"
4
4
  compatibility_flags = ["nodejs_compat"]
5
+ account_id = "03e7294bdb3750ed5a0d6afef6d770e4" # @create-jant: @remove
5
6
 
6
7
  [dev]
7
8
  port = 9019
@@ -28,6 +29,7 @@ SITE_URL = "http://localhost:9019"
28
29
 
29
30
  # Optional: R2 Storage (for media uploads)
30
31
  # R2_PUBLIC_URL = "https://cdn.example.com"
32
+ R2_PUBLIC_URL = "https://demo-media.jant.me" # @create-jant: @remove
31
33
 
32
34
  # Optional: Cloudflare Image Transformations
33
35
  # For automatic thumbnail generation and image optimization
@@ -45,4 +47,5 @@ migrations_dir = "../../packages/core/src/db/migrations" # @create-jant: "node_m
45
47
 
46
48
  [[r2_buckets]]
47
49
  binding = "R2"
48
- bucket_name = "jant-site-media" # @create-jant: "${name}-media"
50
+ bucket_name = "jant-demo-media" # @create-jant: "${name}-media"
51
+ remote = true # @create-jant: @remove
@@ -1,100 +0,0 @@
1
- -- Seed data for Jant demo site
2
- -- This data will be restored after each daily reset
3
-
4
- -- Settings
5
- INSERT OR REPLACE INTO settings (key, value, updated_at) VALUES
6
- ('siteName', 'Jant Demo', strftime('%s', 'now')),
7
- ('siteDescription', 'A demo site for Jant - Modern microblog for Cloudflare Workers', strftime('%s', 'now')),
8
- ('siteUrl', 'https://demo.jant.me', strftime('%s', 'now')),
9
- ('postsPerPage', '10', strftime('%s', 'now')),
10
- ('timezone', 'UTC', strftime('%s', 'now')),
11
- ('language', 'en', strftime('%s', 'now'));
12
-
13
- -- Demo posts
14
- INSERT INTO posts (type, visibility, title, content, content_html, published_at, created_at, updated_at) VALUES
15
- -- Welcome article
16
- ('article', 'featured', 'Welcome to Jant',
17
- '# Welcome to Jant Demo
18
-
19
- Jant is a modern microblog platform built for Cloudflare Workers. This demo site resets daily at 00:00 UTC.
20
-
21
- ## Features
22
-
23
- - **Multiple post types**: Notes, articles, links, quotes, images, and pages
24
- - **Collections**: Organize posts into collections
25
- - **Full-text search**: Search across all your content
26
- - **Internationalization**: Built-in i18n support
27
- - **Fast**: Edge-deployed on Cloudflare Workers
28
-
29
- ## Getting Started
30
-
31
- ```bash
32
- pnpm create jant my-blog
33
- cd my-blog
34
- pnpm install
35
- pnpm dev
36
- ```
37
-
38
- Visit the [dashboard](/dash) to create your own posts!',
39
- '<h1>Welcome to Jant Demo</h1>
40
- <p>Jant is a modern microblog platform built for Cloudflare Workers. This demo site resets daily at 00:00 UTC.</p>
41
- <h2>Features</h2>
42
- <ul>
43
- <li><strong>Multiple post types</strong>: Notes, articles, links, quotes, images, and pages</li>
44
- <li><strong>Collections</strong>: Organize posts into collections</li>
45
- <li><strong>Full-text search</strong>: Search across all your content</li>
46
- <li><strong>Internationalization</strong>: Built-in i18n support</li>
47
- <li><strong>Fast</strong>: Edge-deployed on Cloudflare Workers</li>
48
- </ul>
49
- <h2>Getting Started</h2>
50
- <pre><code class="language-bash">pnpm create jant my-blog
51
- cd my-blog
52
- pnpm install
53
- pnpm dev
54
- </code></pre>
55
- <p>Visit the <a href="/dash">dashboard</a> to create your own posts!</p>',
56
- strftime('%s', 'now'), strftime('%s', 'now'), strftime('%s', 'now')),
57
-
58
- -- A note
59
- ('note', 'quiet', NULL,
60
- 'This is a demo note. Notes are short posts without titles, perfect for quick thoughts and updates.',
61
- '<p>This is a demo note. Notes are short posts without titles, perfect for quick thoughts and updates.</p>',
62
- strftime('%s', 'now') - 3600, strftime('%s', 'now') - 3600, strftime('%s', 'now') - 3600),
63
-
64
- -- A link post
65
- ('link', 'quiet', 'Jant on GitHub',
66
- 'Check out the source code and documentation for Jant.',
67
- '<p>Check out the source code and documentation for Jant.</p>',
68
- strftime('%s', 'now') - 7200, strftime('%s', 'now') - 7200, strftime('%s', 'now') - 7200),
69
-
70
- -- A quote
71
- ('quote', 'quiet', NULL,
72
- 'The best way to predict the future is to invent it.',
73
- '<p>The best way to predict the future is to invent it.</p>',
74
- strftime('%s', 'now') - 10800, strftime('%s', 'now') - 10800, strftime('%s', 'now') - 10800);
75
-
76
- -- Update the link post with source info
77
- UPDATE posts SET
78
- source_url = 'https://github.com/nicepkg/jant',
79
- source_name = 'GitHub',
80
- source_domain = 'github.com'
81
- WHERE type = 'link' AND title = 'Jant on GitHub';
82
-
83
- -- Update the quote with source info
84
- UPDATE posts SET
85
- source_name = 'Alan Kay'
86
- WHERE type = 'quote' AND content LIKE '%predict the future%';
87
-
88
- -- Demo collection
89
- INSERT INTO collections (path, title, description, created_at, updated_at) VALUES
90
- ('getting-started', 'Getting Started', 'Resources for getting started with Jant', strftime('%s', 'now'), strftime('%s', 'now'));
91
-
92
- -- Add the welcome article to the collection
93
- INSERT INTO post_collections (post_id, collection_id, added_at)
94
- SELECT p.id, c.id, strftime('%s', 'now')
95
- FROM posts p, collections c
96
- WHERE p.title = 'Welcome to Jant' AND c.path = 'getting-started';
97
-
98
- -- Update FTS index
99
- INSERT INTO posts_fts (rowid, title, content)
100
- SELECT id, COALESCE(title, ''), COALESCE(content, '') FROM posts WHERE deleted_at IS NULL;