chrome-ext-ci-cd 1.0.0 → 1.0.2
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/lib/bump.js +150 -3
- package/lib/release.js +6 -6
- package/package.json +12 -7
package/lib/bump.js
CHANGED
|
@@ -33,6 +33,25 @@ function calculateNewVersion(currentVersion, bumpType) {
|
|
|
33
33
|
return bumpType;
|
|
34
34
|
}
|
|
35
35
|
|
|
36
|
+
function detectWxtProject(cwd) {
|
|
37
|
+
return fs.existsSync(path.join(cwd, 'wxt.config.ts'));
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
function readWxtVersion(wxtConfigPath) {
|
|
41
|
+
var contents = fs.readFileSync(wxtConfigPath, 'utf-8');
|
|
42
|
+
var match = contents.match(/version:\s*['"]([\d.]+)['"]/);
|
|
43
|
+
return match ? match[1] : null;
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
function writeWxtVersion(wxtConfigPath, newVersion) {
|
|
47
|
+
var contents = fs.readFileSync(wxtConfigPath, 'utf-8');
|
|
48
|
+
var updated = contents.replace(
|
|
49
|
+
/(version:\s*['"])[\d.]+(['"])/,
|
|
50
|
+
'$1' + newVersion + '$2'
|
|
51
|
+
);
|
|
52
|
+
fs.writeFileSync(wxtConfigPath, updated);
|
|
53
|
+
}
|
|
54
|
+
|
|
36
55
|
function checkDirtyTree() {
|
|
37
56
|
try {
|
|
38
57
|
execFileSync('git', ['diff', '--quiet'], { stdio: 'pipe' });
|
|
@@ -46,6 +65,115 @@ function checkDirtyTree() {
|
|
|
46
65
|
}
|
|
47
66
|
}
|
|
48
67
|
|
|
68
|
+
// --- WXT Bump Path ---
|
|
69
|
+
|
|
70
|
+
function bumpWxt(bumpType, projectRoot, opts) {
|
|
71
|
+
var wxtConfigPath = path.join(projectRoot, 'wxt.config.ts');
|
|
72
|
+
var packageJsonPath = path.join(projectRoot, 'package.json');
|
|
73
|
+
var builtManifestPath = path.join(projectRoot, '.output', 'chrome-mv3', 'manifest.json');
|
|
74
|
+
|
|
75
|
+
var data = {
|
|
76
|
+
wxt: true,
|
|
77
|
+
wxtConfigPath: wxtConfigPath,
|
|
78
|
+
packageJsonPath: packageJsonPath
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
// Read current version from wxt.config.ts
|
|
82
|
+
var currentVersion = readWxtVersion(wxtConfigPath);
|
|
83
|
+
if (!currentVersion) {
|
|
84
|
+
return {
|
|
85
|
+
success: false,
|
|
86
|
+
errors: ['Could not parse version from ' + wxtConfigPath + '. Expected: version: \'X.Y.Z\' or version: "X.Y.Z"'],
|
|
87
|
+
warnings: [],
|
|
88
|
+
data: data
|
|
89
|
+
};
|
|
90
|
+
}
|
|
91
|
+
|
|
92
|
+
var newVersion = calculateNewVersion(currentVersion, bumpType);
|
|
93
|
+
var tag = 'v' + newVersion;
|
|
94
|
+
data.previousVersion = currentVersion;
|
|
95
|
+
data.newVersion = newVersion;
|
|
96
|
+
data.tag = tag;
|
|
97
|
+
|
|
98
|
+
var warnings = [];
|
|
99
|
+
|
|
100
|
+
// Validation: check built manifest if it exists
|
|
101
|
+
if (fs.existsSync(builtManifestPath)) {
|
|
102
|
+
data.builtManifestPath = builtManifestPath;
|
|
103
|
+
} else {
|
|
104
|
+
warnings.push('No built manifest found at ' + builtManifestPath + '. Run `wxt build` to validate the generated manifest before tagging.');
|
|
105
|
+
}
|
|
106
|
+
|
|
107
|
+
// Dry run -- return early without side effects
|
|
108
|
+
if (opts.dryRun) {
|
|
109
|
+
data.dryRun = true;
|
|
110
|
+
return { success: true, errors: [], warnings: warnings, data: data };
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
// Check dirty tree
|
|
114
|
+
var treeStatus = checkDirtyTree();
|
|
115
|
+
if (!treeStatus.clean) {
|
|
116
|
+
return { success: false, errors: [treeStatus.message], warnings: warnings, data: data };
|
|
117
|
+
}
|
|
118
|
+
|
|
119
|
+
// Update wxt.config.ts
|
|
120
|
+
writeWxtVersion(wxtConfigPath, newVersion);
|
|
121
|
+
|
|
122
|
+
// Update package.json (always present in WXT projects, but guard anyway)
|
|
123
|
+
var updatedPackageJson = false;
|
|
124
|
+
if (fs.existsSync(packageJsonPath)) {
|
|
125
|
+
try {
|
|
126
|
+
var pkg = JSON.parse(fs.readFileSync(packageJsonPath, 'utf-8'));
|
|
127
|
+
pkg.version = newVersion;
|
|
128
|
+
fs.writeFileSync(packageJsonPath, JSON.stringify(pkg, null, 2) + '\n');
|
|
129
|
+
updatedPackageJson = true;
|
|
130
|
+
} catch (e) {
|
|
131
|
+
return {
|
|
132
|
+
success: false,
|
|
133
|
+
errors: ['Failed to update package.json: ' + e.message],
|
|
134
|
+
warnings: warnings,
|
|
135
|
+
data: data
|
|
136
|
+
};
|
|
137
|
+
}
|
|
138
|
+
}
|
|
139
|
+
|
|
140
|
+
// Git operations -- stage wxt.config.ts + package.json (NEVER the gitignored manifest)
|
|
141
|
+
try {
|
|
142
|
+
execFileSync('git', ['add', wxtConfigPath], { stdio: 'pipe' });
|
|
143
|
+
if (updatedPackageJson) {
|
|
144
|
+
execFileSync('git', ['add', packageJsonPath], { stdio: 'pipe' });
|
|
145
|
+
}
|
|
146
|
+
execFileSync('git', ['commit', '-m', 'chore: bump version to ' + newVersion], { stdio: 'pipe' });
|
|
147
|
+
execFileSync('git', ['tag', '-a', tag, '-m', 'Release ' + tag], { stdio: 'pipe' });
|
|
148
|
+
} catch (e) {
|
|
149
|
+
var errMsg = e.stderr ? e.stderr.toString() : e.message;
|
|
150
|
+
return {
|
|
151
|
+
success: false,
|
|
152
|
+
errors: ['Git operations failed: ' + errMsg + '. Commit and tag were not created.'],
|
|
153
|
+
warnings: warnings,
|
|
154
|
+
data: data
|
|
155
|
+
};
|
|
156
|
+
}
|
|
157
|
+
|
|
158
|
+
// Push
|
|
159
|
+
try {
|
|
160
|
+
var branch = execFileSync('git', ['rev-parse', '--abbrev-ref', 'HEAD'], {
|
|
161
|
+
encoding: 'utf-8'
|
|
162
|
+
}).trim();
|
|
163
|
+
execFileSync('git', ['push', 'origin', branch, '--follow-tags'], { stdio: 'inherit' });
|
|
164
|
+
data.branch = branch;
|
|
165
|
+
} catch (e) {
|
|
166
|
+
return {
|
|
167
|
+
success: false,
|
|
168
|
+
errors: ['Push failed. You can push manually: git push origin --follow-tags'],
|
|
169
|
+
warnings: warnings,
|
|
170
|
+
data: data
|
|
171
|
+
};
|
|
172
|
+
}
|
|
173
|
+
|
|
174
|
+
return { success: true, errors: [], warnings: warnings, data: data };
|
|
175
|
+
}
|
|
176
|
+
|
|
49
177
|
// --- Pure Bump Function ---
|
|
50
178
|
|
|
51
179
|
function bump(bumpType, options) {
|
|
@@ -61,9 +189,19 @@ function bump(bumpType, options) {
|
|
|
61
189
|
};
|
|
62
190
|
}
|
|
63
191
|
|
|
192
|
+
var projectRoot = opts.cwd || process.cwd();
|
|
193
|
+
|
|
194
|
+
// --- WXT auto-detection ---
|
|
195
|
+
// WXT projects keep the version in wxt.config.ts; manifest.json is generated
|
|
196
|
+
// into .output/ (gitignored) at build time. Bypass the manifest path entirely
|
|
197
|
+
// when wxt.config.ts is present at the project root.
|
|
198
|
+
if (detectWxtProject(projectRoot)) {
|
|
199
|
+
return bumpWxt(bumpType, projectRoot, opts);
|
|
200
|
+
}
|
|
201
|
+
|
|
64
202
|
// Resolve manifest path
|
|
65
203
|
var manifestPath = path.resolve(
|
|
66
|
-
opts.manifestPath || opts.manifest || process.env.MANIFEST_PATH || path.join(
|
|
204
|
+
opts.manifestPath || opts.manifest || process.env.MANIFEST_PATH || path.join(projectRoot, 'manifest.json')
|
|
67
205
|
);
|
|
68
206
|
|
|
69
207
|
var data = { manifestPath: manifestPath };
|
|
@@ -208,7 +346,8 @@ function bump(bumpType, options) {
|
|
|
208
346
|
function printHelp() {
|
|
209
347
|
console.log('Usage: chrome-ext-ci-cd bump <patch|minor|major|x.y.z> [options]');
|
|
210
348
|
console.log('');
|
|
211
|
-
console.log('Bump version in manifest.json
|
|
349
|
+
console.log('Bump version in manifest.json (or wxt.config.ts for WXT projects),');
|
|
350
|
+
console.log('commit, tag, and push.');
|
|
212
351
|
console.log('');
|
|
213
352
|
console.log('Arguments:');
|
|
214
353
|
console.log(' patch Increment patch version (1.0.0 -> 1.0.1)');
|
|
@@ -270,6 +409,9 @@ function run(args) {
|
|
|
270
409
|
});
|
|
271
410
|
|
|
272
411
|
// Format output
|
|
412
|
+
if (result.data.wxt) {
|
|
413
|
+
console.log('Detected WXT project (using wxt.config.ts)');
|
|
414
|
+
}
|
|
273
415
|
if (result.data.previousVersion) {
|
|
274
416
|
console.log('Current version: ' + result.data.previousVersion);
|
|
275
417
|
}
|
|
@@ -277,6 +419,11 @@ function run(args) {
|
|
|
277
419
|
console.log('New version: ' + result.data.newVersion);
|
|
278
420
|
}
|
|
279
421
|
|
|
422
|
+
if (result.warnings && result.warnings.length > 0) {
|
|
423
|
+
console.log('');
|
|
424
|
+
result.warnings.forEach(function(w) { console.warn('WARNING: ' + w); });
|
|
425
|
+
}
|
|
426
|
+
|
|
280
427
|
if (result.data.dryRun) {
|
|
281
428
|
console.log('');
|
|
282
429
|
console.log('[DRY RUN] No changes made.');
|
|
@@ -296,4 +443,4 @@ function run(args) {
|
|
|
296
443
|
return result.success ? 0 : 1;
|
|
297
444
|
}
|
|
298
445
|
|
|
299
|
-
module.exports = { bump, run };
|
|
446
|
+
module.exports = { bump, run, detectWxtProject, readWxtVersion, writeWxtVersion, calculateNewVersion };
|
package/lib/release.js
CHANGED
|
@@ -156,7 +156,7 @@ function run(args) {
|
|
|
156
156
|
|
|
157
157
|
// Run each step individually with per-step output
|
|
158
158
|
var manifestPath = values.manifest
|
|
159
|
-
? path.resolve(
|
|
159
|
+
? path.resolve(values.manifest)
|
|
160
160
|
: path.join(process.cwd(), 'manifest.json');
|
|
161
161
|
|
|
162
162
|
var validateResult = validate.validate(manifestPath);
|
|
@@ -171,7 +171,7 @@ function run(args) {
|
|
|
171
171
|
// Step 2: Bump
|
|
172
172
|
var bumpResult = bump.bump(bumpType, {
|
|
173
173
|
manifest: manifestPath,
|
|
174
|
-
dryRun:
|
|
174
|
+
dryRun: values['dry-run']
|
|
175
175
|
});
|
|
176
176
|
if (!bumpResult.success) {
|
|
177
177
|
console.log('[2/3] Bump version... FAILED');
|
|
@@ -179,14 +179,14 @@ function run(args) {
|
|
|
179
179
|
return 1;
|
|
180
180
|
}
|
|
181
181
|
var versionStr = bumpResult.data.previousVersion + ' -> ' + bumpResult.data.newVersion;
|
|
182
|
-
if (
|
|
182
|
+
if (values['dry-run']) {
|
|
183
183
|
console.log('[2/3] Bump version ' + versionStr + '... OK (dry run)');
|
|
184
184
|
} else {
|
|
185
185
|
console.log('[2/3] Bump version ' + versionStr + '... OK');
|
|
186
186
|
}
|
|
187
187
|
|
|
188
188
|
// Step 3: Package
|
|
189
|
-
if (
|
|
189
|
+
if (values['dry-run']) {
|
|
190
190
|
console.log('[3/3] Package extension... SKIPPED (dry run)');
|
|
191
191
|
console.log('');
|
|
192
192
|
console.log('Dry run complete. Version would be ' + bumpResult.data.newVersion + '.');
|
|
@@ -194,8 +194,8 @@ function run(args) {
|
|
|
194
194
|
}
|
|
195
195
|
|
|
196
196
|
var pkgResult = pkg.packageExtension({
|
|
197
|
-
source:
|
|
198
|
-
output:
|
|
197
|
+
source: values.source ? path.resolve(values.source) : undefined,
|
|
198
|
+
output: values.output ? path.resolve(values.output) : undefined
|
|
199
199
|
});
|
|
200
200
|
if (!pkgResult.success) {
|
|
201
201
|
console.log('[3/3] Package extension... FAILED');
|
package/package.json
CHANGED
|
@@ -1,8 +1,9 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "chrome-ext-ci-cd",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.2",
|
|
4
4
|
"description": "CLI toolkit for Chrome extension CI/CD: validate, version, package, and release",
|
|
5
|
-
"license": "
|
|
5
|
+
"license": "UNLICENSED",
|
|
6
|
+
"private": false,
|
|
6
7
|
"bin": {
|
|
7
8
|
"chrome-ext-ci-cd": "./bin/cli.js"
|
|
8
9
|
},
|
|
@@ -16,15 +17,16 @@
|
|
|
16
17
|
},
|
|
17
18
|
"scripts": {
|
|
18
19
|
"test": "node --test",
|
|
19
|
-
"prepublishOnly": "node --test && node -e \"const fs=require('fs');const p=require('./package.json');const bin=p.bin['chrome-ext-ci-cd'];if(!fs.existsSync(bin)){console.error('FAIL: bin entry not found:',bin);process.exit(1)}console.log('OK: bin exists:',bin)\""
|
|
20
|
+
"prepublishOnly": "node --test && node -e \"const fs=require('fs');const p=require('./package.json');const bin=p.bin['chrome-ext-ci-cd'];if(!fs.existsSync(bin)){console.error('FAIL: bin entry not found:',bin);process.exit(1)}console.log('OK: bin exists:',bin)\"",
|
|
21
|
+
"prepare": "husky"
|
|
20
22
|
},
|
|
21
23
|
"repository": {
|
|
22
24
|
"type": "git",
|
|
23
|
-
"url": "https://github.com/
|
|
25
|
+
"url": "https://github.com/elfstrob/chrome-ext-ci-cd.git"
|
|
24
26
|
},
|
|
25
|
-
"homepage": "https://github.com/
|
|
27
|
+
"homepage": "https://github.com/elfstrob/chrome-ext-ci-cd#readme",
|
|
26
28
|
"bugs": {
|
|
27
|
-
"url": "https://github.com/
|
|
29
|
+
"url": "https://github.com/elfstrob/chrome-ext-ci-cd/issues"
|
|
28
30
|
},
|
|
29
31
|
"author": "Brian Grenier",
|
|
30
32
|
"keywords": [
|
|
@@ -33,5 +35,8 @@
|
|
|
33
35
|
"manifest-v3",
|
|
34
36
|
"version-bump",
|
|
35
37
|
"packaging"
|
|
36
|
-
]
|
|
38
|
+
],
|
|
39
|
+
"devDependencies": {
|
|
40
|
+
"husky": "^9.1.7"
|
|
41
|
+
}
|
|
37
42
|
}
|