git-watchtower 1.10.10 → 1.10.12
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 +1 -1
- package/src/config/loader.js +1 -210
- package/src/git/commands.js +3 -0
- package/src/index.js +0 -3
- package/src/utils/gitignore.js +4 -11
package/package.json
CHANGED
package/src/config/loader.js
CHANGED
|
@@ -5,7 +5,7 @@
|
|
|
5
5
|
const fs = require('fs');
|
|
6
6
|
const path = require('path');
|
|
7
7
|
const { ConfigError } = require('../utils/errors');
|
|
8
|
-
const {
|
|
8
|
+
const { validateConfig, migrateConfig } = require('./schema');
|
|
9
9
|
|
|
10
10
|
/**
|
|
11
11
|
* Default configuration file name
|
|
@@ -117,212 +117,6 @@ function deleteConfig(projectRoot) {
|
|
|
117
117
|
return true;
|
|
118
118
|
}
|
|
119
119
|
|
|
120
|
-
/**
|
|
121
|
-
* Apply CLI arguments to configuration
|
|
122
|
-
* CLI args take precedence over config file values
|
|
123
|
-
* @param {Object} config - Base configuration
|
|
124
|
-
* @param {Object} cliArgs - CLI arguments
|
|
125
|
-
* @returns {Object} - Merged configuration
|
|
126
|
-
*/
|
|
127
|
-
function applyCliArgs(config, cliArgs) {
|
|
128
|
-
const result = JSON.parse(JSON.stringify(config)); // Deep clone
|
|
129
|
-
|
|
130
|
-
// Server settings
|
|
131
|
-
if (cliArgs.mode !== undefined && cliArgs.mode !== null) {
|
|
132
|
-
result.server.mode = cliArgs.mode;
|
|
133
|
-
}
|
|
134
|
-
if (cliArgs.noServer) {
|
|
135
|
-
result.server.mode = 'none';
|
|
136
|
-
}
|
|
137
|
-
if (cliArgs.port !== undefined && cliArgs.port !== null) {
|
|
138
|
-
result.server.port = cliArgs.port;
|
|
139
|
-
}
|
|
140
|
-
if (cliArgs.staticDir !== undefined && cliArgs.staticDir !== null) {
|
|
141
|
-
result.server.staticDir = cliArgs.staticDir;
|
|
142
|
-
}
|
|
143
|
-
if (cliArgs.command !== undefined && cliArgs.command !== null) {
|
|
144
|
-
result.server.command = cliArgs.command;
|
|
145
|
-
}
|
|
146
|
-
if (cliArgs.restartOnSwitch !== undefined && cliArgs.restartOnSwitch !== null) {
|
|
147
|
-
result.server.restartOnSwitch = cliArgs.restartOnSwitch;
|
|
148
|
-
}
|
|
149
|
-
|
|
150
|
-
// Web dashboard
|
|
151
|
-
if (cliArgs.web) {
|
|
152
|
-
result.web = { ...result.web, enabled: true };
|
|
153
|
-
}
|
|
154
|
-
if (cliArgs.webPort !== undefined && cliArgs.webPort !== null) {
|
|
155
|
-
result.web = { ...result.web, port: cliArgs.webPort };
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
// Git settings
|
|
159
|
-
if (cliArgs.remote !== undefined && cliArgs.remote !== null) {
|
|
160
|
-
result.remoteName = cliArgs.remote;
|
|
161
|
-
}
|
|
162
|
-
if (cliArgs.autoPull !== undefined && cliArgs.autoPull !== null) {
|
|
163
|
-
result.autoPull = cliArgs.autoPull;
|
|
164
|
-
}
|
|
165
|
-
if (cliArgs.pollInterval !== undefined && cliArgs.pollInterval !== null) {
|
|
166
|
-
result.gitPollInterval = cliArgs.pollInterval;
|
|
167
|
-
}
|
|
168
|
-
|
|
169
|
-
// UI settings
|
|
170
|
-
if (cliArgs.sound !== undefined && cliArgs.sound !== null) {
|
|
171
|
-
result.soundEnabled = cliArgs.sound;
|
|
172
|
-
}
|
|
173
|
-
if (cliArgs.visibleBranches !== undefined && cliArgs.visibleBranches !== null) {
|
|
174
|
-
result.visibleBranches = cliArgs.visibleBranches;
|
|
175
|
-
}
|
|
176
|
-
if (cliArgs.casino !== undefined && cliArgs.casino !== null) {
|
|
177
|
-
result.casinoMode = cliArgs.casino;
|
|
178
|
-
}
|
|
179
|
-
|
|
180
|
-
return result;
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
/**
|
|
184
|
-
* Parse CLI arguments
|
|
185
|
-
* @param {string[]} [argv] - Command line arguments (defaults to process.argv.slice(2))
|
|
186
|
-
* @returns {Object} - Parsed arguments
|
|
187
|
-
*/
|
|
188
|
-
function parseCliArgs(argv = process.argv.slice(2)) {
|
|
189
|
-
const result = {
|
|
190
|
-
// Server settings
|
|
191
|
-
mode: null,
|
|
192
|
-
noServer: false,
|
|
193
|
-
port: null,
|
|
194
|
-
staticDir: null,
|
|
195
|
-
command: null,
|
|
196
|
-
restartOnSwitch: null,
|
|
197
|
-
// Git settings
|
|
198
|
-
remote: null,
|
|
199
|
-
autoPull: null,
|
|
200
|
-
pollInterval: null,
|
|
201
|
-
// UI settings
|
|
202
|
-
sound: null,
|
|
203
|
-
visibleBranches: null,
|
|
204
|
-
casino: null,
|
|
205
|
-
// Special flags
|
|
206
|
-
init: false,
|
|
207
|
-
help: false,
|
|
208
|
-
version: false,
|
|
209
|
-
};
|
|
210
|
-
|
|
211
|
-
for (let i = 0; i < argv.length; i++) {
|
|
212
|
-
const arg = argv[i];
|
|
213
|
-
|
|
214
|
-
switch (arg) {
|
|
215
|
-
// Server settings
|
|
216
|
-
case '--mode':
|
|
217
|
-
result.mode = argv[++i];
|
|
218
|
-
break;
|
|
219
|
-
case '--no-server':
|
|
220
|
-
result.noServer = true;
|
|
221
|
-
break;
|
|
222
|
-
case '--port':
|
|
223
|
-
case '-p':
|
|
224
|
-
result.port = parseInt(argv[++i], 10);
|
|
225
|
-
break;
|
|
226
|
-
case '--static-dir':
|
|
227
|
-
result.staticDir = argv[++i];
|
|
228
|
-
break;
|
|
229
|
-
case '--command':
|
|
230
|
-
case '-c':
|
|
231
|
-
result.command = argv[++i];
|
|
232
|
-
break;
|
|
233
|
-
case '--restart-on-switch':
|
|
234
|
-
result.restartOnSwitch = true;
|
|
235
|
-
break;
|
|
236
|
-
case '--no-restart-on-switch':
|
|
237
|
-
result.restartOnSwitch = false;
|
|
238
|
-
break;
|
|
239
|
-
|
|
240
|
-
// Git settings
|
|
241
|
-
case '--remote':
|
|
242
|
-
case '-r':
|
|
243
|
-
result.remote = argv[++i];
|
|
244
|
-
break;
|
|
245
|
-
case '--auto-pull':
|
|
246
|
-
result.autoPull = true;
|
|
247
|
-
break;
|
|
248
|
-
case '--no-auto-pull':
|
|
249
|
-
result.autoPull = false;
|
|
250
|
-
break;
|
|
251
|
-
case '--poll-interval':
|
|
252
|
-
result.pollInterval = parseInt(argv[++i], 10) * 1000; // Convert seconds to ms
|
|
253
|
-
break;
|
|
254
|
-
|
|
255
|
-
// UI settings
|
|
256
|
-
case '--sound':
|
|
257
|
-
result.sound = true;
|
|
258
|
-
break;
|
|
259
|
-
case '--no-sound':
|
|
260
|
-
result.sound = false;
|
|
261
|
-
break;
|
|
262
|
-
case '--visible-branches':
|
|
263
|
-
result.visibleBranches = parseInt(argv[++i], 10);
|
|
264
|
-
break;
|
|
265
|
-
case '--casino':
|
|
266
|
-
result.casino = true;
|
|
267
|
-
break;
|
|
268
|
-
case '--no-casino':
|
|
269
|
-
result.casino = false;
|
|
270
|
-
break;
|
|
271
|
-
|
|
272
|
-
// Special flags
|
|
273
|
-
case '--init':
|
|
274
|
-
result.init = true;
|
|
275
|
-
break;
|
|
276
|
-
case '--help':
|
|
277
|
-
case '-h':
|
|
278
|
-
result.help = true;
|
|
279
|
-
break;
|
|
280
|
-
case '--version':
|
|
281
|
-
case '-v':
|
|
282
|
-
result.version = true;
|
|
283
|
-
break;
|
|
284
|
-
}
|
|
285
|
-
}
|
|
286
|
-
|
|
287
|
-
return result;
|
|
288
|
-
}
|
|
289
|
-
|
|
290
|
-
/**
|
|
291
|
-
* Ensure configuration exists
|
|
292
|
-
* Loads from file, runs wizard if needed, and applies CLI args
|
|
293
|
-
* @param {Object} cliArgs - CLI arguments
|
|
294
|
-
* @param {Object} [options] - Options
|
|
295
|
-
* @param {string} [options.projectRoot] - Project root directory
|
|
296
|
-
* @param {boolean} [options.interactive=true] - Allow interactive prompts
|
|
297
|
-
* @param {Function} [options.runWizard] - Wizard function to run if needed
|
|
298
|
-
* @returns {Promise<Object>} - Final configuration
|
|
299
|
-
*/
|
|
300
|
-
async function ensureConfig(cliArgs, options = {}) {
|
|
301
|
-
const { projectRoot, interactive = true, runWizard } = options;
|
|
302
|
-
|
|
303
|
-
// Check if --init flag was passed (force reconfiguration)
|
|
304
|
-
if (cliArgs.init && runWizard) {
|
|
305
|
-
const config = await runWizard();
|
|
306
|
-
return applyCliArgs(config, cliArgs);
|
|
307
|
-
}
|
|
308
|
-
|
|
309
|
-
// Load existing config
|
|
310
|
-
let config = loadConfig(projectRoot);
|
|
311
|
-
|
|
312
|
-
// If no config exists
|
|
313
|
-
if (!config) {
|
|
314
|
-
if (runWizard && interactive && process.stdin.isTTY) {
|
|
315
|
-
config = await runWizard();
|
|
316
|
-
} else {
|
|
317
|
-
// Use defaults
|
|
318
|
-
config = getDefaultConfig();
|
|
319
|
-
}
|
|
320
|
-
}
|
|
321
|
-
|
|
322
|
-
// Apply CLI args over config
|
|
323
|
-
return applyCliArgs(config, cliArgs);
|
|
324
|
-
}
|
|
325
|
-
|
|
326
120
|
module.exports = {
|
|
327
121
|
CONFIG_FILE_NAME,
|
|
328
122
|
getConfigPath,
|
|
@@ -331,7 +125,4 @@ module.exports = {
|
|
|
331
125
|
loadConfig,
|
|
332
126
|
saveConfig,
|
|
333
127
|
deleteConfig,
|
|
334
|
-
applyCliArgs,
|
|
335
|
-
parseCliArgs,
|
|
336
|
-
ensureConfig,
|
|
337
128
|
};
|
package/src/git/commands.js
CHANGED
|
@@ -160,6 +160,9 @@ async function fetch(remoteName = 'origin', options = {}) {
|
|
|
160
160
|
const args = ['fetch'];
|
|
161
161
|
if (all) args.push('--all');
|
|
162
162
|
if (prune) args.push('--prune');
|
|
163
|
+
// When not fetching all remotes, target the specified remote.
|
|
164
|
+
// (`git fetch --all <remote>` is redundant and can confuse older git versions.)
|
|
165
|
+
if (!all && remoteName) args.push(remoteName);
|
|
163
166
|
|
|
164
167
|
try {
|
|
165
168
|
await execGit(args, { cwd, timeout: FETCH_TIMEOUT });
|
package/src/index.js
CHANGED
|
@@ -151,9 +151,6 @@ module.exports = {
|
|
|
151
151
|
loadConfig: configLoader.loadConfig,
|
|
152
152
|
saveConfig: configLoader.saveConfig,
|
|
153
153
|
deleteConfig: configLoader.deleteConfig,
|
|
154
|
-
applyCliArgs: configLoader.applyCliArgs,
|
|
155
|
-
parseCliArgs: configLoader.parseCliArgs,
|
|
156
|
-
ensureConfig: configLoader.ensureConfig,
|
|
157
154
|
|
|
158
155
|
// Server process management
|
|
159
156
|
ProcessManager: serverProcess.ProcessManager,
|
package/src/utils/gitignore.js
CHANGED
|
@@ -125,19 +125,12 @@ function loadGitignorePatterns(searchPaths) {
|
|
|
125
125
|
* @returns {boolean} - True if the file is in the .git directory
|
|
126
126
|
*/
|
|
127
127
|
function isGitDirectory(filename) {
|
|
128
|
-
if (filename === '.git' || filename.startsWith('.git/') || filename.startsWith('.git\\')) {
|
|
129
|
-
return true;
|
|
130
|
-
}
|
|
131
|
-
|
|
132
128
|
// Normalize path separators for cross-platform support
|
|
133
|
-
const
|
|
129
|
+
const p = filename.replace(/\\/g, '/');
|
|
134
130
|
|
|
135
|
-
//
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
}
|
|
139
|
-
|
|
140
|
-
return false;
|
|
131
|
+
// Match exactly ".git" as a path segment, not ".github", ".gitignore", etc.
|
|
132
|
+
// Valid matches: ".git", ".git/hooks/pre-commit", "src/.git/config"
|
|
133
|
+
return /^\.git(\/|$)/.test(p) || /\/\.git(\/|$)/.test(p);
|
|
141
134
|
}
|
|
142
135
|
|
|
143
136
|
/**
|