Skip to content

Commit 89d3443

Browse files
committed
fix: rbenv, terraform, aliases, apt, and snap
1 parent a49673c commit 89d3443

11 files changed

Lines changed: 93 additions & 113 deletions

File tree

package-lock.json

Lines changed: 4 additions & 4 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -42,7 +42,7 @@
4242
"license": "ISC",
4343
"type": "module",
4444
"dependencies": {
45-
"@codifycli/plugin-core": "1.1.0-beta5",
45+
"@codifycli/plugin-core": "1.1.0-beta6",
4646
"@codifycli/schemas": "1.0.0",
4747
"ajv": "^8.18.0",
4848
"ajv-formats": "^2.1.1",

src/resources/apt/install-parameter.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -78,7 +78,7 @@ export class AptInstallParameter extends StatefulParameter<AptConfig, string[]>
7878
}
7979

8080
const $ = getPty();
81-
await $.spawn(`apt-get install -y ${packages.join(' ')}`, {
81+
await $.spawn(`apt-get -qq install -o Dpkg::Progress-Fancy=0 -y ${packages.join(' ')}`, {
8282
requiresRoot: true,
8383
env: { DEBIAN_FRONTEND: 'noninteractive', NEEDRESTART_MODE: 'a' }
8484
});
@@ -90,7 +90,7 @@ export class AptInstallParameter extends StatefulParameter<AptConfig, string[]>
9090
}
9191

9292
const $ = getPty();
93-
await $.spawn(`apt-get auto-remove -y ${packages.map(packageName).join(' ')}`, {
93+
await $.spawn(`apt-get -qq auto-remove -o Dpkg::Progress-Fancy=0 -y ${packages.map(packageName).join(' ')}`, {
9494
requiresRoot: true,
9595
env: { DEBIAN_FRONTEND: 'noninteractive', NEEDRESTART_MODE: 'a' }
9696
});
@@ -103,4 +103,4 @@ export class AptInstallParameter extends StatefulParameter<AptConfig, string[]>
103103
}
104104
return desired === current
105105
}
106-
}
106+
}

src/resources/aws-cli/profile/aws-configure.test.ts

Lines changed: 0 additions & 69 deletions
This file was deleted.

src/resources/ruby/rbenv/rbenv.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -72,13 +72,13 @@ async function installOnMacOS(): Promise<void> {
7272
async function installOnLinux(): Promise<void> {
7373
const $ = getPty();
7474

75-
await $.spawn(`git clone https://github.com/rbenv/rbenv.git ${RBENV_ROOT}`, { interactive: true });
75+
await $.spawnSafe(`git clone https://github.com/rbenv/rbenv.git ${RBENV_ROOT}`, { interactive: true });
7676

7777
const rubyBuildPath = path.join(RBENV_ROOT, 'plugins', 'ruby-build');
78-
await $.spawn(`git clone https://github.com/rbenv/ruby-build.git ${rubyBuildPath}`, { interactive: true });
78+
await $.spawnSafe(`git clone https://github.com/rbenv/ruby-build.git ${rubyBuildPath}`, { interactive: true });
7979

8080
await Utils.installViaPkgMgr(
81-
'autoconf patch build-essential rustc libssl-dev libyaml-dev libreadline6-dev zlib1g-dev libgmp-dev libncurses5-dev libffi-dev libgdbm6 libgdbm-dev libdb-dev uuid-dev'
81+
'curl autoconf patch build-essential rustc libssl-dev libyaml-dev libreadline6-dev zlib1g-dev libgmp-dev libncurses5-dev libffi-dev libgdbm6 libgdbm-dev libdb-dev uuid-dev'
8282
);
8383

8484
await FileUtils.addAllToShellRc([RBENV_PATH_EXPORT, RBENV_INIT]);

src/resources/shell/aliases/aliases-resource.ts

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,8 @@ import fs from 'node:fs/promises';
1616

1717
import { FileUtils } from '../../../utils/file-utils.js';
1818
import { Utils } from '../../../utils/index.js';
19+
import os from 'node:os';
20+
import path from 'node:path';
1921

2022
const ALIAS_REGEX = /^'?([^=]+?)'?='?(.*?)'?$/
2123

@@ -118,6 +120,7 @@ export class AliasesResource extends Resource<AliasesConfig> {
118120

119121
let aliases = data.split(/\n/g)
120122
.map((l) => l.trim())
123+
.map((l) => l.replace(/^alias\s+/, ''))
121124
.map((l) => l.match(ALIAS_REGEX))
122125
.filter(Boolean)
123126
.map((m) => (m ? { alias: m[1], value: m[2] } : null))

src/resources/snap/install-parameter.ts

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,9 @@ export class SnapInstallParameter extends StatefulParameter<SnapConfig, Array<Sn
7171
const valuesToAdd = newValue.filter((n) => !previousValue.some((p) => this.isSamePackage(n, p)));
7272
const valuesToRemove = previousValue.filter((p) => !newValue.some((n) => this.isSamePackage(n, p)));
7373

74-
await this.uninstall(valuesToRemove);
74+
if (_plan.isStateful) {
75+
await this.uninstall(valuesToRemove);
76+
}
7577
await this.install(valuesToAdd);
7678
}
7779

@@ -104,7 +106,7 @@ export class SnapInstallParameter extends StatefulParameter<SnapConfig, Array<Sn
104106
}
105107
}
106108

107-
await $.spawn(command, { requiresRoot: true, interactive: true });
109+
await $.spawn(command, { requiresRoot: true, interactive: true, env: { SNAP_QUIET: 1 } });
108110
}
109111
}
110112

@@ -118,7 +120,7 @@ export class SnapInstallParameter extends StatefulParameter<SnapConfig, Array<Sn
118120
// Uninstall packages one by one
119121
for (const p of packages) {
120122
const name = typeof p === 'string' ? p : p.name;
121-
await $.spawn(`snap remove ${name}`, { requiresRoot: true, interactive: true });
123+
await $.spawn(`snap remove ${name}`, { requiresRoot: true, interactive: true, env: { SNAP_QUIET: 1 } });
122124
}
123125
}
124126

src/resources/terraform/terraform.ts

Lines changed: 53 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,21 @@
1-
import { CreatePlan, ExampleConfig, Resource, ResourceSettings, SpawnStatus, getPty } from '@codifycli/plugin-core';
1+
import {
2+
CreatePlan,
3+
ExampleConfig,
4+
Resource,
5+
ResourceSettings,
6+
SpawnStatus,
7+
getPty,
8+
Utils, FileUtils
9+
} from '@codifycli/plugin-core';
210
import { OS, StringIndexedObject } from '@codifycli/schemas';
311
import fs from 'node:fs/promises';
412
import os from 'node:os';
513
import path from 'node:path';
614
import semver from 'semver';
715

8-
import { FileUtils } from '../../utils/file-utils.js';
9-
import { Utils } from '../../utils/index.js';
1016
import Schema from './terraform-schema.json';
1117
import { HashicorpReleaseInfo, HashicorpReleasesAPIResponse, TerraformVersionInfo } from './terraform-types.js';
18+
import { codifySpawn } from '../../utils/codify-spawn.js';
1219

1320
const TERRAFORM_RELEASES_API_URL = 'https://api.releases.hashicorp.com/v1/releases/terraform';
1421
const TERRAFORM_RELEASE_INFO_API_URL = (version: string) => `https://api.releases.hashicorp.com/v1/releases/terraform/${version}`;
@@ -116,18 +123,24 @@ ${JSON.stringify(releaseInfo, null, 2)}
116123
// Create a temporary tmp dir
117124
const temporaryDir = await fs.mkdtemp(path.join(os.tmpdir(), 'terraform-'));
118125

126+
// Ensure unzip is available (not installed by default on some Linux distros)
127+
const unzipCheck = await $.spawnSafe('which unzip');
128+
if (unzipCheck.status === SpawnStatus.ERROR) {
129+
await Utils.installViaPkgMgr('unzip');
130+
}
131+
119132
// Download and unzip the terraform binary
120133
await $.spawn(`curl -fsSL ${downloadUrl} -o terraform.zip`, { cwd: temporaryDir });
121134
await $.spawn('unzip -q terraform.zip', { cwd: temporaryDir });
122135

123136
// Ensure that /usr/local/bin exists. If not then create it
124-
await (directory === '/usr/local/bin' ? Utils.createBinDirectoryIfNotExists() : Utils.createDirectoryIfNotExists(directory));
137+
await (directory === '/usr/local/bin' ? this.createBinDirectoryIfNotExists() : this.createDirectoryIfNotExists(directory));
125138

126139
await $.spawn(`mv ./terraform ${directory}`, { cwd: temporaryDir, requiresRoot: true })
127140
await $.spawn(`rm -rf ${temporaryDir}`)
128141

129142
if (!(await Utils.isDirectoryOnPath(directory))) {
130-
await FileUtils.addToStartupFile(`export PATH=$PATH:${directory}`);
143+
await FileUtils.addToShellRc(`export PATH=$PATH:${directory}`);
131144
}
132145
}
133146

@@ -145,7 +158,7 @@ ${JSON.stringify(releaseInfo, null, 2)}
145158
}
146159

147160
await $.spawn(`rm ${installLocationQuery.data}`, { requiresRoot: true });
148-
await FileUtils.removeLineFromStartupFile(`export PATH=$PATH:${installLocationQuery.data}`);
161+
await FileUtils.removeLineFromShellRc(`export PATH=$PATH:${installLocationQuery.data}`);
149162
}
150163

151164
private async getLatestTerraformInfo(): Promise<HashicorpReleaseInfo> {
@@ -184,4 +197,38 @@ ${JSON.stringify(releaseInfo, null, 2)}
184197

185198
return build.url;
186199
}
200+
201+
private async createBinDirectoryIfNotExists(): Promise<void> {
202+
let lstat = null;
203+
try {
204+
lstat = await fs.lstat('/usr/local/bin')
205+
} catch {}
206+
207+
if (lstat && lstat.isDirectory()) {
208+
return;
209+
}
210+
211+
if (lstat && !lstat.isDirectory()) {
212+
throw new Error('Found file at /usr/local/bin. Cannot create a directory there')
213+
}
214+
215+
await codifySpawn('sudo mkdir -p -m 775 /usr/local/bin')
216+
}
217+
218+
async createDirectoryIfNotExists(path: string): Promise<void> {
219+
let lstat = null;
220+
try {
221+
lstat = await fs.lstat(path)
222+
} catch {}
223+
224+
if (lstat && lstat.isDirectory()) {
225+
return;
226+
}
227+
228+
if (lstat && !lstat.isDirectory()) {
229+
throw new Error(`Found file at ${path}. Cannot create a directory there`)
230+
}
231+
232+
await fs.mkdir(path, { recursive: true })
233+
}
187234
}

test/apt/apt.test.ts

Lines changed: 5 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -14,7 +14,7 @@ describe('Apt resource integration tests', { skip: !Utils.isLinux() }, () => {
1414
type: 'apt',
1515
install: [
1616
'redis',
17-
{ name: 'redis-tools' }
17+
'redis-tools'
1818
]
1919
}], {
2020
skipUninstall: true,
@@ -26,12 +26,10 @@ describe('Apt resource integration tests', { skip: !Utils.isLinux() }, () => {
2626
modifiedConfigs: [{
2727
type: 'apt',
2828
install: [
29-
'vlc',
30-
{ name: 'tilix' }
29+
'tilix'
3130
],
3231
}],
3332
validateModify: async () => {
34-
expect(await testSpawn('which vlc')).toMatchObject({ status: SpawnStatus.SUCCESS });
3533
expect(await testSpawn('which tilix')).toMatchObject({ status: SpawnStatus.SUCCESS });
3634
}
3735
}
@@ -42,9 +40,8 @@ describe('Apt resource integration tests', { skip: !Utils.isLinux() }, () => {
4240
type: 'apt',
4341
install: [
4442
'redis',
45-
{ name: 'redis-tools' },
46-
'vlc',
47-
{ name: 'tilix' }
43+
'redis-tools',
44+
'tilix'
4845
]
4946
}]);
5047
} catch (e) {
@@ -59,7 +56,7 @@ describe('Apt resource integration tests', { skip: !Utils.isLinux() }, () => {
5956
await PluginTester.fullTest(pluginPath, [{
6057
type: 'apt',
6158
install: [
62-
{ name: 'curl', version: availableVersions }
59+
`curl=${availableVersions}`
6360
]
6461
}], {
6562
skipUninstall: true,

test/shell/aliases.test.ts

Lines changed: 14 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,11 @@
1-
21
import { describe, expect, it } from 'vitest';
32
import { PluginTester, testSpawn } from '@codifycli/plugin-test';
43
import * as path from 'node:path';
54
import { TestUtils } from '../test-utils.js';
65
import { SpawnStatus } from '@codifycli/plugin-core';
76
import { ResourceOperation } from '@codifycli/schemas';
87

8+
// Fix for linux
99
describe('Aliases resource integration tests', async () => {
1010
const pluginPath = path.resolve('./src/index.ts');
1111

@@ -47,17 +47,19 @@ describe('Aliases resource integration tests', async () => {
4747

4848
expect(plans[0]).toMatchObject({
4949
operation: ResourceOperation.MODIFY,
50-
parameters: [{
51-
previousValue: [
52-
{ alias: 'my-alias', value: 'ls -l' },
53-
{ alias: 'my-alias2', value: 'pwd' }
54-
],
55-
newValue: [
56-
{ alias: 'my-alias', value: 'cd .' },
57-
{ alias: 'my-alias2', value: 'cd ..' },
58-
{ alias: 'my-alias3', value: 'cd ../..' }
59-
]
60-
}]
50+
parameters: expect.arrayContaining([
51+
expect.objectContaining({
52+
previousValue: [
53+
{ alias: 'my-alias', value: 'ls -l' },
54+
{ alias: 'my-alias2', value: 'pwd' }
55+
],
56+
newValue: [
57+
{ alias: 'my-alias', value: 'cd .' },
58+
{ alias: 'my-alias2', value: 'cd ..' },
59+
{ alias: 'my-alias3', value: 'cd ../..' }
60+
]
61+
})
62+
])
6163
})
6264

6365
const { data: aliasOutput } = await testSpawn('alias')

0 commit comments

Comments
 (0)