Skip to content

Commit f17651f

Browse files
authored
Merge pull request #1606 from salesforcecli/d/W-21064297
feat: enforces that only pinned dependencies should be pinned @W-21064297@
2 parents 2fe113a + 075da5d commit f17651f

3 files changed

Lines changed: 46 additions & 15 deletions

File tree

src/commands/cli/release/build.ts

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77

88
import { promisify } from 'node:util';
99
import { exec as execSync, ExecException } from 'node:child_process';
10-
import { arrayWithDeprecation, Flags, SfCommand, Ux } from '@salesforce/sf-plugins-core';
10+
import { Flags, SfCommand, Ux } from '@salesforce/sf-plugins-core';
1111
import { ensureString } from '@salesforce/ts-types';
1212
import { Env } from '@salesforce/kit';
1313
import { Octokit } from '@octokit/core';
@@ -51,8 +51,10 @@ export default class build extends SfCommand<void> {
5151
default: true,
5252
allowNo: true,
5353
}),
54-
only: arrayWithDeprecation({
54+
only: Flags.string({
5555
summary: messages.getMessage('flags.only.summary'),
56+
multiple: true,
57+
delimiter: ',',
5658
}),
5759
'pinned-deps': Flags.boolean({
5860
summary: messages.getMessage('flags.pinned-deps.summary'),

src/package.ts

Lines changed: 14 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -214,8 +214,10 @@ export class Package extends AsyncOptionalCreatable {
214214
// find dependency in package.json (could be an npm alias)
215215
const depInfo = this.getDependencyInfo(name, { ...dependencies, ...resolutions, ...jitPlugins });
216216

217+
const shouldPin: boolean = this.shouldPinDependency(depInfo.packageName);
218+
217219
// if a version is not provided, we'll look up the "latest" version
218-
depInfo.finalVersion = version ?? this.getDistTags(depInfo.packageName).latest;
220+
depInfo.finalVersion = `${shouldPin ? '' : '^'}${version ?? this.getDistTags(depInfo.packageName).latest}`;
219221

220222
// return if version did not change
221223
if (depInfo.currentVersion === depInfo.finalVersion) return;
@@ -341,6 +343,17 @@ export class Package extends AsyncOptionalCreatable {
341343
'dist-tags': {},
342344
};
343345
}
346+
347+
private shouldPinDependency(dependencyName: string): boolean {
348+
const pinnedDependencies: string[] = this.packageJson.pinnedDependencies ?? [];
349+
const jitDependencies: string[] = this.packageJson.oclif?.jitPlugins
350+
? Object.keys(this.packageJson.oclif.jitPlugins)
351+
: [];
352+
353+
const dependenciesThatShouldBePinned = [...pinnedDependencies, ...jitDependencies];
354+
355+
return dependenciesThatShouldBePinned.includes(dependencyName);
356+
}
344357
}
345358

346359
const getNameAndTag = (plugin: string): [name: string, tag: string | undefined] => {

test/package.test.ts

Lines changed: 28 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -130,6 +130,7 @@ describe('Package', () => {
130130
'@salesforce/plugin-config': '1.2.3',
131131
'left-pad': '1.1.1',
132132
},
133+
pinnedDependencies: ['@salesforce/plugin-config'],
133134
resolutions: {
134135
'@salesforce/source-deploy-retrieve': '1.0.0',
135136
},
@@ -149,70 +150,85 @@ describe('Package', () => {
149150
});
150151
it('should look up latest version if not provided', async () => {
151152
const pkg = await Package.create();
152-
const results = pkg.bumpDependencyVersions(['@salesforce/plugin-config', '@salesforce/jit-me']);
153+
const results = pkg.bumpDependencyVersions(['@salesforce/plugin-config', '@salesforce/jit-me', 'left-pad']);
153154

154155
expect(results).to.deep.equal([
155156
{
156157
packageName: '@salesforce/plugin-config',
157158
currentVersion: '1.2.3',
159+
// Dependency should be pinned because it is listed in `pinnedDependencies`
158160
finalVersion: '9.9.9',
159161
},
160162
{
161163
packageName: '@salesforce/jit-me',
162164
currentVersion: '1.0.0',
165+
// Dependency should be pinned, even though it's not in `pinnedDependencies`, because it's in `oclif.jitPlugins`
163166
finalVersion: '9.9.9',
164167
},
168+
{
169+
packageName: 'left-pad',
170+
currentVersion: '1.1.1',
171+
// Dependency should be unpinned because it is not listed in `pinnedDependencies`
172+
finalVersion: '^9.9.9',
173+
},
165174
]);
166175
});
167176

168177
it('should used passed in version', async () => {
169178
const pkg = await Package.create();
170-
const results = pkg.bumpDependencyVersions(['@salesforce/plugin-config@11.0.0']);
179+
const results = pkg.bumpDependencyVersions(['@salesforce/plugin-config@11.0.0', 'left-pad@11.0.0']);
171180

172181
expect(results).to.deep.equal([
173182
{
174183
packageName: '@salesforce/plugin-config',
175184
currentVersion: '1.2.3',
185+
// Dependency should be pinned because it's in `pinnedDependencies`
176186
finalVersion: '11.0.0',
177187
},
188+
{
189+
packageName: 'left-pad',
190+
currentVersion: '1.1.1',
191+
// Dependency should be unpinned because it's not in `pinnedDependencies`
192+
finalVersion: '^11.0.0',
193+
},
178194
]);
179195
});
180196

181-
it('should work with non-namespaced package', async () => {
197+
it('should unpin a not-explicitly-pinned version even if it is already up-to-date', async () => {
182198
const pkg = await Package.create();
183-
const results = pkg.bumpDependencyVersions(['left-pad']);
199+
const results = pkg.bumpDependencyVersions(['left-pad@11.0.0']);
184200

185201
expect(results).to.deep.equal([
186202
{
187203
packageName: 'left-pad',
188204
currentVersion: '1.1.1',
189-
finalVersion: '9.9.9',
205+
finalVersion: '^11.0.0',
190206
},
191207
]);
192208
});
193209

194-
it('should return an empty array if all versions are already up to date', async () => {
210+
it('should return an empty array if all bumped versions are already up to date', async () => {
195211
const pkg = await Package.create();
196212
const results = pkg.bumpDependencyVersions(['@salesforce/plugin-config@1.2.3']);
197213

198214
expect(results).to.deep.equal([]);
199215
});
200216

201-
it('should update dependencies in package.json', async () => {
217+
it('should update unpinned dependencies in package.json to unpinned version', async () => {
202218
const pkg = await Package.create();
203-
pkg.bumpDependencyVersions(['@salesforce/plugin-config@3.3.3']);
219+
pkg.bumpDependencyVersions(['left-pad@3.3.3']);
204220

205-
expect(pkg.packageJson.dependencies['@salesforce/plugin-config']).to.equal('3.3.3');
221+
expect(pkg.packageJson.dependencies['left-pad']).to.equal('^3.3.3');
206222
});
207223

208-
it('should update resolutions in package.json', async () => {
224+
it('should update resolutions in package.json to unpinned version', async () => {
209225
const pkg = await Package.create();
210226
pkg.bumpDependencyVersions(['@salesforce/source-deploy-retrieve@1.0.1']);
211227
assert(pkg.packageJson.resolutions);
212-
expect(pkg.packageJson.resolutions['@salesforce/source-deploy-retrieve']).to.equal('1.0.1');
228+
expect(pkg.packageJson.resolutions['@salesforce/source-deploy-retrieve']).to.equal('^1.0.1');
213229
});
214230

215-
it('should update jit in package.json', async () => {
231+
it('should update jit in package.json to pinned version', async () => {
216232
const pkg = await Package.create();
217233
pkg.bumpDependencyVersions(['@salesforce/jit-me@1.0.1']);
218234
assert(pkg.packageJson.oclif?.jitPlugins);

0 commit comments

Comments
 (0)