Skip to content

Commit 5694c98

Browse files
committed
feat: Add a pre-filled sudo password
1 parent 6e7aba1 commit 5694c98

File tree

7 files changed

+61
-31
lines changed

7 files changed

+61
-31
lines changed

codify.json

Lines changed: 20 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -12,9 +12,13 @@
1212
"$PYENV_ROOT/bin",
1313
"$BUN_INSTALL/bin",
1414
"$DENO_INSTALL/bin",
15+
"~/.jenv/bin",
16+
"~/a/random/path",
17+
"$NVM_DIR/.bin/2",
1518
"$NVM_DIR/.bin/3"
1619
],
17-
"declarationsOnly": true
20+
"declarationsOnly": true,
21+
"name": "1"
1822
},
1923
{
2024
"type": "homebrew",
@@ -35,6 +39,11 @@
3539
"cirrus",
3640
"expect",
3741
"git-lfs",
42+
"groff",
43+
"hyperfine",
44+
"jenv",
45+
"jq",
46+
"mas",
3847
"openjdk@11",
3948
"openjdk@17",
4049
"openjdk@21",
@@ -104,20 +113,20 @@
104113
"type": "aws-cli"
105114
},
106115
{
107-
"type": "git-clone",
116+
"type": "git-repository",
108117
"directory": "~/Projects/codify-homebrew-plugin",
109118
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
110119
},
111120
{
112121
"type": "vscode"
113122
},
114123
{
115-
"type": "git-clone",
124+
"type": "git-repository",
116125
"directory": "~/Projects/codify-plugin-lib",
117126
"repository": "git@github.com:kevinwang5658/codify-plugin-lib.git"
118127
},
119128
{
120-
"type": "git-clone",
129+
"type": "git-repository",
121130
"directory": "~/Projects/codify",
122131
"repository": "git@github.com:kevinwang5658/codify.git"
123132
},
@@ -176,37 +185,37 @@
176185
"region": "us-east-1"
177186
},
178187
{
179-
"type": "git-clone",
188+
"type": "git-repository",
180189
"directory": "~/Projects/codify-homebrew-plugin",
181190
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
182191
},
183192
{
184-
"type": "git-clone",
193+
"type": "git-repository",
185194
"directory": "~/Projects/codify-homebrew-plugin",
186195
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
187196
},
188197
{
189-
"type": "git-clone",
198+
"type": "git-repository",
190199
"directory": "~/Projects/codify-homebrew-plugin",
191200
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
192201
},
193202
{
194-
"type": "git-clone",
203+
"type": "git-repository",
195204
"directory": "~/Projects/codify-homebrew-plugin",
196205
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
197206
},
198207
{
199-
"type": "git-clone",
208+
"type": "git-repository",
200209
"directory": "~/Projects/codify-homebrew-plugin",
201210
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
202211
},
203212
{
204-
"type": "git-clone",
213+
"type": "git-repository",
205214
"directory": "~/Projects/codify-homebrew-plugin",
206215
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
207216
},
208217
{
209-
"type": "git-clone",
218+
"type": "git-repository",
210219
"directory": "~/Projects/codify-homebrew-plugin",
211220
"repository": "git@github.com:kevinwang5658/codify-homebrew-plugin.git"
212221
}
Lines changed: 11 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,19 @@
11
import { Flags } from '@oclif/core'
22

3-
import { BaseCommand } from '../../common/base-command.js';
4-
import { ApplyOrchestrator } from '../../orchestrators/apply.js';
3+
import { BaseCommand } from '../common/base-command.js';
4+
import { ApplyOrchestrator } from '../orchestrators/apply.js';
55

66
export default class Apply extends BaseCommand {
77
static description = 'Apply a codify file onto the system. A plan of the changes is first generated and a list of changes will be shown before proceeding'
88

9+
static flags = {
10+
'sudoPassword': Flags.string({
11+
optional: true,
12+
description: 'Pre-fill the sudo password to automatically use for any commands that require elevated permissions.',
13+
char: 'S'
14+
}),
15+
}
16+
917
static examples = [
1018
'<%= config.bin %> <%= command.id %>',
1119
'<%= config.bin %> <%= command.id %> --path ~',
@@ -21,7 +29,7 @@ export default class Apply extends BaseCommand {
2129

2230
await ApplyOrchestrator.run({
2331
path: flags.path,
24-
secure: flags.secure,
32+
// secure: flags.secure,
2533
}, this.reporter);
2634

2735
process.exit(0);

src/commands/destroy.ts

Lines changed: 11 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,5 @@
1+
import { Flags } from '@oclif/core';
2+
13
import { BaseCommand } from '../common/base-command.js';
24
import { DestroyOrchestrator } from '../orchestrators/destroy.js';
35

@@ -7,6 +9,15 @@ export default class Destroy extends BaseCommand {
79
static examples = [
810
'<%= config.bin %> <%= command.id %> homebrew nvm',
911
]
12+
13+
static flags = {
14+
'sudoPassword': Flags.string({
15+
optional: true,
16+
description: 'Pre-fill the sudo password to automatically use for any commands that require elevated permissions.',
17+
char: 'S',
18+
helpValue: '<password>'
19+
}),
20+
}
1021

1122
public async run(): Promise<void> {
1223
const { flags, raw } = await this.parse(Destroy)
@@ -26,7 +37,6 @@ export default class Destroy extends BaseCommand {
2637
await DestroyOrchestrator.run({
2738
ids: args,
2839
path: flags.path,
29-
secureMode: flags.secure,
3040
}, this.reporter)
3141

3242
process.exit(0);
Lines changed: 2 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,5 @@
1-
import { Args, Flags } from '@oclif/core'
2-
import * as path from 'node:path';
3-
4-
import { PlanOrchestrator } from '../../orchestrators/plan.js';
5-
import { BaseCommand } from '../../common/base-command.js';
1+
import { BaseCommand } from '../common/base-command.js';
2+
import { PlanOrchestrator } from '../orchestrators/plan.js';
63

74
export default class Plan extends BaseCommand {
85
static description = 'Generate a plan based on a codify.json file. This plan will list ' +

src/common/base-command.ts

Lines changed: 13 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -6,21 +6,21 @@ import createDebug from 'debug';
66

77
import { Event, ctx } from '../events/context.js';
88
import { Reporter, ReporterFactory, ReporterType } from '../ui/reporters/reporter.js';
9+
import { SudoUtils } from '../utils/sudo.js';
910
import { prettyPrintError } from './errors.js';
1011

1112
export abstract class BaseCommand extends Command {
1213
static baseFlags = {
13-
'debug': Flags.boolean(),
14+
'debug': Flags.boolean({
15+
description: 'Add additional debug logs.'
16+
}),
1417
'output': Flags.option({
1518
char: 'o',
1619
default: 'default',
1720
options: ['plain', 'default', 'json'],
21+
description: 'Control the output format of Codify.',
1822
})(),
19-
'secure': Flags.boolean({
20-
char: 's',
21-
default: false,
22-
}),
23-
path: Flags.string({ char: 'p', description: 'Path to codify.json file' }),
23+
path: Flags.string({ char: 'p', description: 'Path to run Codify from.' }),
2424
}
2525

2626
protected reporter!: Reporter;
@@ -29,6 +29,7 @@ export abstract class BaseCommand extends Command {
2929
await super.init();
3030

3131
const { flags } = await this.parse({
32+
flags: this.ctor.flags,
3233
baseFlags: (super.ctor as typeof BaseCommand).baseFlags,
3334
strict: false,
3435
});
@@ -42,7 +43,12 @@ export abstract class BaseCommand extends Command {
4243

4344
ctx.on(Event.SUDO_REQUEST, async (pluginName: string, data: SudoRequestData) => {
4445
try {
45-
const result = await this.reporter.promptSudo(pluginName, data, flags.secure);
46+
const password = (flags.sudoPassword) ?? (await this.reporter.promptSudo(pluginName, data, flags.secure));
47+
if (!password) {
48+
throw new Error(`Unable to get sudo password to run command: ${data.command}`);
49+
}
50+
51+
const result = await SudoUtils.runCommand(data.command, data.options, flags.secure, pluginName, password)
4652
ctx.sudoRequestGranted(pluginName, result);
4753

4854
// This listener is outside of the base-command callstack. We have to manually catch the error.

src/ui/reporters/default-reporter.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
import { FormProps, FormReturnValue } from '@codifycli/ink-form';
22
import chalk from 'chalk';
3-
import { SudoRequestData, SudoRequestResponseData } from 'codify-schemas';
3+
import { SudoRequestData } from 'codify-schemas';
44
import { render } from 'ink';
55
import { EventEmitter } from 'node:events';
66
import React from 'react';
@@ -138,7 +138,7 @@ export class DefaultReporter implements Reporter {
138138
this.updateRenderState(RenderStatus.DISPLAY_IMPORT_RESULT, { importResult, showConfigs });
139139
}
140140

141-
async promptSudo(pluginName: string, data: SudoRequestData, secureMode: boolean): Promise<SudoRequestResponseData> {
141+
async promptSudo(pluginName: string, data: SudoRequestData, secureMode: boolean): Promise<string | undefined> {
142142
console.log(chalk.blue(`Plugin: "${pluginName}" requires root access to run command: "${data.command}"`));
143143

144144
let password;
@@ -148,7 +148,7 @@ export class DefaultReporter implements Reporter {
148148
password = await this.getUserPassword();
149149
}
150150

151-
return SudoUtils.runCommand(data.command, data.options, secureMode, pluginName, password)
151+
return password;
152152
}
153153

154154
displayPlan(plan: Plan): void {

src/ui/reporters/reporter.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -59,7 +59,7 @@ export interface Reporter {
5959

6060
promptOptions(message: string, options: string[]): Promise<number>;
6161

62-
promptSudo(pluginName: string, data: SudoRequestData, secureMode: boolean): Promise<SudoRequestResponseData>;
62+
promptSudo(pluginName: string, data: SudoRequestData, secureMode: boolean): Promise<string | undefined>;
6363

6464
promptUserForValues(resources: Array<ResourceInfo>, promptType: PromptType): Promise<ResourceConfig[]>;
6565

0 commit comments

Comments
 (0)