@mono-labs/cli 0.0.14 → 0.0.16
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/commands/dev/dev-editor.js +2 -4
- package/lib/index.js +0 -2
- package/package.json +1 -1
- package/lib/commands/squash/index.js +0 -8
- package/lib/commands/squash/squash.js +0 -150
- package/lib/commands/test/index.js +0 -251
- package/lib/migrations/index.js +0 -2
- package/lib/migrations/v0.js +0 -3
- package/lib/migrations/v1.js +0 -4
|
@@ -1,14 +1,12 @@
|
|
|
1
|
-
|
|
1
|
+
|
|
2
2
|
import { spawn } from 'child_process'
|
|
3
3
|
import 'dotenv/config'
|
|
4
4
|
import inquirer from 'inquirer'
|
|
5
|
-
import { env } from 'process'
|
|
6
|
-
import readline from 'readline'
|
|
7
5
|
import treeKill from 'tree-kill'
|
|
8
6
|
|
|
9
7
|
import { generateEnvValues } from '../../app.js'
|
|
10
8
|
import { STAGING_URL } from '../../config.js'
|
|
11
|
-
import { getNgrokUrl
|
|
9
|
+
import { getNgrokUrl } from './ngrok.js'
|
|
12
10
|
|
|
13
11
|
// EXPO_FORCE_PROD = true;
|
|
14
12
|
// EXPO_UNSTABLE_ATLAS = false;
|
package/lib/index.js
CHANGED
|
@@ -10,10 +10,8 @@ import './commands/init/index.js'
|
|
|
10
10
|
import './commands/prune/index.js'
|
|
11
11
|
import './commands/reset.js'
|
|
12
12
|
import './commands/seed/index.js'
|
|
13
|
-
import './commands/squash/index.js'
|
|
14
13
|
import './commands/submit/index.js'
|
|
15
14
|
import './commands/update/index.js'
|
|
16
|
-
//import './commands/test/index.js'
|
|
17
15
|
import './commands/build-process/index.js'
|
|
18
16
|
|
|
19
17
|
program.parse()
|
package/package.json
CHANGED
|
@@ -1,150 +0,0 @@
|
|
|
1
|
-
#!/usr/bin/env node
|
|
2
|
-
import { execSync, spawnSync } from 'child_process'
|
|
3
|
-
import fs from 'fs'
|
|
4
|
-
import inquirer from 'inquirer'
|
|
5
|
-
import os from 'os'
|
|
6
|
-
import path from 'path'
|
|
7
|
-
|
|
8
|
-
async function maybeEditFile() {
|
|
9
|
-
const { shouldEdit } = await inquirer.prompt([
|
|
10
|
-
{
|
|
11
|
-
type: 'confirm',
|
|
12
|
-
name: 'shouldEdit',
|
|
13
|
-
message: 'Do you want to edit the commit message in your Git editor?',
|
|
14
|
-
default: true,
|
|
15
|
-
},
|
|
16
|
-
])
|
|
17
|
-
|
|
18
|
-
if (shouldEdit) {
|
|
19
|
-
execSync('git commit --amend')
|
|
20
|
-
}
|
|
21
|
-
}
|
|
22
|
-
|
|
23
|
-
async function confirmDangerousSquash() {
|
|
24
|
-
const { shouldEdit } = await inquirer.prompt([
|
|
25
|
-
{
|
|
26
|
-
type: 'confirm',
|
|
27
|
-
name: 'shouldEdit',
|
|
28
|
-
message:
|
|
29
|
-
"You're about to squash on a previously squashed commit. You will need to manually modify the commit message. Do you want to proceed?",
|
|
30
|
-
default: true,
|
|
31
|
-
},
|
|
32
|
-
])
|
|
33
|
-
|
|
34
|
-
return shouldEdit
|
|
35
|
-
}
|
|
36
|
-
|
|
37
|
-
export async function squash() {
|
|
38
|
-
const status = execSync('git status --porcelain').toString()
|
|
39
|
-
if (status.trim() !== '') {
|
|
40
|
-
console.error('You have unstaged changes. Please commit or stash them before proceeding.')
|
|
41
|
-
process.exit(1)
|
|
42
|
-
}
|
|
43
|
-
const log = execSync(`git log --reverse --pretty=format:"%h %s" -n ${20}`).toString()
|
|
44
|
-
console.log('Log:\n', log)
|
|
45
|
-
|
|
46
|
-
const commits = log
|
|
47
|
-
.split('\n')
|
|
48
|
-
.reverse()
|
|
49
|
-
.map((line, idx) => {
|
|
50
|
-
console.log('message', line.slice(8).split('- '))
|
|
51
|
-
return {
|
|
52
|
-
name: `${idx} [${line.slice(0, 7)}] : ${line.slice(8)}`,
|
|
53
|
-
value: idx, // Just the commit message
|
|
54
|
-
message: line.slice(8).split('- ').join('\n- '),
|
|
55
|
-
}
|
|
56
|
-
})
|
|
57
|
-
console.log(commits)
|
|
58
|
-
|
|
59
|
-
const { count } = await inquirer.prompt([
|
|
60
|
-
{
|
|
61
|
-
type: 'list',
|
|
62
|
-
name: 'count',
|
|
63
|
-
message: 'Select commit to squash down into:',
|
|
64
|
-
choices: commits,
|
|
65
|
-
},
|
|
66
|
-
])
|
|
67
|
-
|
|
68
|
-
if (count === 0) {
|
|
69
|
-
console.log('You may not squash only one commit.')
|
|
70
|
-
return
|
|
71
|
-
}
|
|
72
|
-
let totalMerged = 0
|
|
73
|
-
const commitMessageGen = commits
|
|
74
|
-
.slice(0, count + 1)
|
|
75
|
-
.map((msg) => {
|
|
76
|
-
return msg.message
|
|
77
|
-
})
|
|
78
|
-
.map((msg) => `${msg}`)
|
|
79
|
-
.join('\n')
|
|
80
|
-
|
|
81
|
-
let shouldContinue = true
|
|
82
|
-
const match = commitMessageGen.match(/Merging (\d+)\s+into singular commit/)
|
|
83
|
-
if (match) {
|
|
84
|
-
shouldContinue = await confirmDangerousSquash()
|
|
85
|
-
console.log('Unable to merge with merged commits')
|
|
86
|
-
if (!shouldContinue) return
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
console.log('Total merged:', totalMerged)
|
|
90
|
-
console.log(count + 1 + totalMerged)
|
|
91
|
-
const commitMessage = `Merging ${count + 1 + totalMerged} into singular commit\n${commitMessageGen}`
|
|
92
|
-
|
|
93
|
-
console.log(`Commit message:\n${commitMessage}`)
|
|
94
|
-
|
|
95
|
-
// Write message to temp file
|
|
96
|
-
const tempMessagePath = path.join(os.tmpdir(), 'git_squash_message.txt')
|
|
97
|
-
fs.writeFileSync(tempMessagePath, commitMessage)
|
|
98
|
-
|
|
99
|
-
if (shouldContinue) {
|
|
100
|
-
const { confirmSquash } = await inquirer.prompt([
|
|
101
|
-
{
|
|
102
|
-
type: 'confirm',
|
|
103
|
-
name: 'confirmSquash',
|
|
104
|
-
message: 'Do you want to squash these commits?',
|
|
105
|
-
default: true, // or false if you want "No" as the default
|
|
106
|
-
},
|
|
107
|
-
])
|
|
108
|
-
|
|
109
|
-
shouldContinue = confirmSquash
|
|
110
|
-
}
|
|
111
|
-
|
|
112
|
-
if (!shouldContinue) return
|
|
113
|
-
// proceed with
|
|
114
|
-
|
|
115
|
-
// GIT_EDITOR override for rebase message
|
|
116
|
-
const isWin = process.platform === 'win32'
|
|
117
|
-
const editorScript = path.join(os.tmpdir(), isWin ? 'git-editor.bat' : 'git-editor.sh')
|
|
118
|
-
const messagePath = path.join(os.tmpdir(), 'commit-message.txt')
|
|
119
|
-
|
|
120
|
-
fs.writeFileSync(messagePath, commitMessage)
|
|
121
|
-
|
|
122
|
-
if (isWin) {
|
|
123
|
-
fs.writeFileSync(editorScript, `@echo off\r\ncopy /Y "${messagePath}" %1 > nul\r\n`)
|
|
124
|
-
} else {
|
|
125
|
-
fs.writeFileSync(editorScript, `#!/bin/sh\ncat "${messagePath}" > "$1"\n`)
|
|
126
|
-
fs.chmodSync(editorScript, '755')
|
|
127
|
-
}
|
|
128
|
-
|
|
129
|
-
console.log('Starting interactive rebase...')
|
|
130
|
-
|
|
131
|
-
spawnSync('git', ['reset', '--soft', `HEAD~${count + 1}`], { stdio: 'inherit' })
|
|
132
|
-
|
|
133
|
-
spawnSync('git', ['commit', '-m', commitMessage], { stdio: 'inherit' })
|
|
134
|
-
|
|
135
|
-
const rebaseResult = spawnSync('git', ['rebase', `HEAD~${count}`], {
|
|
136
|
-
stdio: 'inherit',
|
|
137
|
-
env: { ...process.env, GIT_EDITOR: editorScript },
|
|
138
|
-
})
|
|
139
|
-
|
|
140
|
-
console.log(`Rebase result: ${rebaseResult.status}`)
|
|
141
|
-
|
|
142
|
-
if (rebaseResult.status !== 0) {
|
|
143
|
-
console.error('Rebase failed. Resolve conflicts and try again.')
|
|
144
|
-
process.exit(rebaseResult.status)
|
|
145
|
-
}
|
|
146
|
-
|
|
147
|
-
await maybeEditFile()
|
|
148
|
-
|
|
149
|
-
console.log('✅ Rebase complete.')
|
|
150
|
-
}
|
|
@@ -1,251 +0,0 @@
|
|
|
1
|
-
import { spawn } from 'child_process'
|
|
2
|
-
import fs from 'fs'
|
|
3
|
-
import { program } from '../../app.js'
|
|
4
|
-
import { generateEnvValues } from '../../app.js'
|
|
5
|
-
import { STAGING_URL } from '../../config.js'
|
|
6
|
-
import {
|
|
7
|
-
getHasteConfig,
|
|
8
|
-
getHasteFiles,
|
|
9
|
-
getRootDirectory,
|
|
10
|
-
getRootHasteJson,
|
|
11
|
-
getRootJson,
|
|
12
|
-
} from '../loadFromRoot.js'
|
|
13
|
-
|
|
14
|
-
console.log('getRootDirectory', getRootDirectory())
|
|
15
|
-
console.log('rootJson', getRootJson())
|
|
16
|
-
const objHaste = getRootHasteJson()
|
|
17
|
-
const files = getHasteConfig()
|
|
18
|
-
|
|
19
|
-
console.log('Haste files', files)
|
|
20
|
-
|
|
21
|
-
const fileKeys = Object.keys(files)
|
|
22
|
-
|
|
23
|
-
fileKeys.forEach((key) => {
|
|
24
|
-
const commandName = key
|
|
25
|
-
|
|
26
|
-
console.log('Haste file key', commandName, files[key])
|
|
27
|
-
program
|
|
28
|
-
.command(commandName)
|
|
29
|
-
.description('Execute eas build command')
|
|
30
|
-
.option('--android', 'Build to target preview profile')
|
|
31
|
-
.option('--ios', 'Build to target production profile')
|
|
32
|
-
.option('--stage', 'Set environment to staging')
|
|
33
|
-
.action(async (options) => {
|
|
34
|
-
const configObject = files[commandName] || {}
|
|
35
|
-
await runHasteCommand(configObject, options)
|
|
36
|
-
|
|
37
|
-
// const devConfig = configObject.environments ? configObject.environments.dev : {}
|
|
38
|
-
// const productionConfig = configObject.environments ? configObject.environments.production : {}
|
|
39
|
-
// let envObj = {}
|
|
40
|
-
// if (options.stage) {
|
|
41
|
-
// envObj = { ...devConfig }
|
|
42
|
-
// } else {
|
|
43
|
-
// envObj = { ...productionConfig }
|
|
44
|
-
// }
|
|
45
|
-
|
|
46
|
-
// // You can decide what happens when each flag is passed.
|
|
47
|
-
// // Example: run `eas build` with different profiles.
|
|
48
|
-
// if (options.android) {
|
|
49
|
-
// console.log('→ Building Android (preview profile)…')
|
|
50
|
-
// //run('eas', ['build', '--platform', 'android', '--profile', 'preview'])
|
|
51
|
-
// } else if (options.ios) {
|
|
52
|
-
// console.log('→ Building iOS (production profile)…')
|
|
53
|
-
// //run('eas', ['build', '--platform', 'ios', '--profile', 'production'])
|
|
54
|
-
// } else {
|
|
55
|
-
// // console.log('No target specified. Use --android or --ios.')
|
|
56
|
-
// // program.help()
|
|
57
|
-
// console.log('objHaste.actions', configObject)
|
|
58
|
-
// const preactions = configObject['preactions'] || []
|
|
59
|
-
// const actions = configObject.actions || []
|
|
60
|
-
// console.log('preactions', preactions)
|
|
61
|
-
// for (const item of preactions) {
|
|
62
|
-
// console.log(`→ Running pre-action: ${item}`)
|
|
63
|
-
// await run(item, [], envObj)
|
|
64
|
-
// }
|
|
65
|
-
// for (const item of actions) {
|
|
66
|
-
// console.log(`→ Running action: ${item}`)
|
|
67
|
-
// run(item, [], envObj)
|
|
68
|
-
// }
|
|
69
|
-
// }
|
|
70
|
-
// })
|
|
71
|
-
})
|
|
72
|
-
})
|
|
73
|
-
|
|
74
|
-
// const commandName = 'test'
|
|
75
|
-
// program
|
|
76
|
-
// .command(commandName)
|
|
77
|
-
// .description('Execute eas build command')
|
|
78
|
-
// .option('--android', 'Build to target preview profile')
|
|
79
|
-
// .option('--ios', 'Build to target production profile')
|
|
80
|
-
// .option('--stage', 'Set environment to staging')
|
|
81
|
-
// .action((options) => {
|
|
82
|
-
// const configObject = objHaste[commandName] || {}
|
|
83
|
-
|
|
84
|
-
// const devConfig = configObject.environments ? configObject.environments.dev : {}
|
|
85
|
-
// const productionConfig = configObject.environments ? configObject.environments.production : {}
|
|
86
|
-
// let envObj = {}
|
|
87
|
-
// if (options.stage) {
|
|
88
|
-
// envObj = { ...devConfig }
|
|
89
|
-
// } else {
|
|
90
|
-
// envObj = { ...productionConfig }
|
|
91
|
-
// }
|
|
92
|
-
|
|
93
|
-
// // You can decide what happens when each flag is passed.
|
|
94
|
-
// // Example: run `eas build` with different profiles.
|
|
95
|
-
// if (options.android) {
|
|
96
|
-
// console.log('→ Building Android (preview profile)…')
|
|
97
|
-
// //run('eas', ['build', '--platform', 'android', '--profile', 'preview'])
|
|
98
|
-
// } else if (options.ios) {
|
|
99
|
-
// console.log('→ Building iOS (production profile)…')
|
|
100
|
-
// //run('eas', ['build', '--platform', 'ios', '--profile', 'production'])
|
|
101
|
-
// } else {
|
|
102
|
-
// // console.log('No target specified. Use --android or --ios.')
|
|
103
|
-
// // program.help()
|
|
104
|
-
// console.log('objHaste.actions', objHaste)
|
|
105
|
-
// for (const item of configObject.actions) {
|
|
106
|
-
// console.log(`→ Running action: ${item}`)
|
|
107
|
-
// run(item, [], envObj)
|
|
108
|
-
// }
|
|
109
|
-
// }
|
|
110
|
-
// })
|
|
111
|
-
|
|
112
|
-
const totalClosedActions = 0
|
|
113
|
-
// Utility to spawn and pipe child output
|
|
114
|
-
async function run(cmd, args, envObj = {}, count = 1) {
|
|
115
|
-
const child = spawn(cmd, args, {
|
|
116
|
-
stdio: 'inherit',
|
|
117
|
-
shell: true,
|
|
118
|
-
env: {
|
|
119
|
-
...process.env,
|
|
120
|
-
...envObj,
|
|
121
|
-
},
|
|
122
|
-
})
|
|
123
|
-
const isLast = count === totalClosedActions + 1
|
|
124
|
-
|
|
125
|
-
const exitAction = () => {
|
|
126
|
-
totalClosedActions++
|
|
127
|
-
process.exit(code)
|
|
128
|
-
}
|
|
129
|
-
if (!isLast) {
|
|
130
|
-
child.on('exit', (code) => {
|
|
131
|
-
exitAction()
|
|
132
|
-
})
|
|
133
|
-
child.on('sigint', () => {
|
|
134
|
-
exitAction()
|
|
135
|
-
})
|
|
136
|
-
}
|
|
137
|
-
if (isLast) {
|
|
138
|
-
child.on('exit', (code) => {
|
|
139
|
-
if (count < totalClosedActions) exitAction()
|
|
140
|
-
})
|
|
141
|
-
child.on('sigint', () => {
|
|
142
|
-
if (count < totalClosedActions) {
|
|
143
|
-
exitAction()
|
|
144
|
-
process.exit(code)
|
|
145
|
-
}
|
|
146
|
-
})
|
|
147
|
-
}
|
|
148
|
-
}
|
|
149
|
-
|
|
150
|
-
// Track background processes so we can kill them on exit
|
|
151
|
-
const bgChildren = new Set()
|
|
152
|
-
|
|
153
|
-
/** Run a command and resolve when it exits (attach stdio so you can see output). */
|
|
154
|
-
function runForeground(cmd, envObj = {}) {
|
|
155
|
-
return new Promise((resolve, reject) => {
|
|
156
|
-
// run the whole string via the shell so quotes/pipes work
|
|
157
|
-
const child = spawn(cmd, {
|
|
158
|
-
shell: true,
|
|
159
|
-
stdio: 'inherit',
|
|
160
|
-
env: { ...process.env, ...envObj },
|
|
161
|
-
})
|
|
162
|
-
child.on('error', reject)
|
|
163
|
-
child.on('exit', (code, signal) => {
|
|
164
|
-
if (signal) return reject(new Error(`${cmd} exited via signal ${signal}`))
|
|
165
|
-
if (code === 0) return resolve()
|
|
166
|
-
reject(new Error(`${cmd} exited with code ${code}`))
|
|
167
|
-
})
|
|
168
|
-
})
|
|
169
|
-
}
|
|
170
|
-
|
|
171
|
-
/** Start a command fully detached (no stdio). */
|
|
172
|
-
function runBackground(cmd, envObj = {}) {
|
|
173
|
-
const isWin = process.platform === 'win32'
|
|
174
|
-
|
|
175
|
-
const child = spawn(cmd, {
|
|
176
|
-
shell: true,
|
|
177
|
-
stdio: 'ignore', // no output in this terminal
|
|
178
|
-
env: { ...process.env, ...envObj },
|
|
179
|
-
// On POSIX, detach so we can signal the whole group; on Windows, DON'T.
|
|
180
|
-
detached: !isWin,
|
|
181
|
-
windowsHide: isWin, // prevent new console window on Windows
|
|
182
|
-
})
|
|
183
|
-
|
|
184
|
-
// Only unref on POSIX when detached; on Windows keep it referenced.
|
|
185
|
-
if (!isWin) child.unref()
|
|
186
|
-
|
|
187
|
-
bgChildren.add(child)
|
|
188
|
-
child.on('exit', () => bgChildren.delete(child))
|
|
189
|
-
child.on('error', () => bgChildren.delete(child))
|
|
190
|
-
}
|
|
191
|
-
|
|
192
|
-
/** Kill all background children (called on SIGINT/SIGTERM or when foreground ends). */
|
|
193
|
-
function killAllBackground() {
|
|
194
|
-
for (const child of Array.from(bgChildren)) {
|
|
195
|
-
try {
|
|
196
|
-
if (process.platform === 'win32') {
|
|
197
|
-
spawn('taskkill', ['/PID', String(child.pid), '/T', '/F'], { shell: true, stdio: 'ignore' })
|
|
198
|
-
} else {
|
|
199
|
-
process.kill(-child.pid, 'SIGTERM') // whole group
|
|
200
|
-
}
|
|
201
|
-
} catch {}
|
|
202
|
-
}
|
|
203
|
-
bgChildren.clear()
|
|
204
|
-
}
|
|
205
|
-
|
|
206
|
-
process.on('SIGINT', () => {
|
|
207
|
-
console.log('\nSIGINT')
|
|
208
|
-
killAllBackground()
|
|
209
|
-
process.exit(130)
|
|
210
|
-
})
|
|
211
|
-
process.on('SIGTERM', () => {
|
|
212
|
-
killAllBackground()
|
|
213
|
-
process.exit(143)
|
|
214
|
-
})
|
|
215
|
-
|
|
216
|
-
/** In your commander .action handler */
|
|
217
|
-
async function runHasteCommand(configObject, options) {
|
|
218
|
-
const devConfig = configObject.environments?.dev ?? {}
|
|
219
|
-
const productionConfig = configObject.environments?.production ?? {}
|
|
220
|
-
const envObj = options.stage ? devConfig : productionConfig
|
|
221
|
-
|
|
222
|
-
const preactions = configObject.preactions ?? []
|
|
223
|
-
const actions = configObject.actions ?? []
|
|
224
|
-
|
|
225
|
-
// 1) Run preactions SEQUENTIALLY (each waits for previous to finish)
|
|
226
|
-
for (const cmd of preactions) {
|
|
227
|
-
console.log(`→ preaction: ${cmd}`)
|
|
228
|
-
await runForeground(cmd, envObj)
|
|
229
|
-
}
|
|
230
|
-
|
|
231
|
-
// 2) Run actions: background all but the last; attach to the last
|
|
232
|
-
if (actions.length === 0) return
|
|
233
|
-
|
|
234
|
-
const bg = actions.slice(0, -1)
|
|
235
|
-
const fg = actions[actions.length - 1]
|
|
236
|
-
|
|
237
|
-
for (const cmd of bg) {
|
|
238
|
-
console.log(`→ background action: ${cmd}`)
|
|
239
|
-
runBackground(cmd, envObj)
|
|
240
|
-
}
|
|
241
|
-
|
|
242
|
-
console.log(`→ foreground action (attached): ${fg}`)
|
|
243
|
-
console.log('envObj', envObj)
|
|
244
|
-
try {
|
|
245
|
-
console.log('envObj', envObj)
|
|
246
|
-
await runForeground(fg, envObj)
|
|
247
|
-
} finally {
|
|
248
|
-
// When the foreground ends, clean up background processes too (optional)
|
|
249
|
-
killAllBackground()
|
|
250
|
-
}
|
|
251
|
-
}
|
package/lib/migrations/index.js
DELETED
package/lib/migrations/v0.js
DELETED
package/lib/migrations/v1.js
DELETED