Skip to content

Commit 1fd6a52

Browse files
committed
Merge remote-tracking branch 'origin/main' into connor4312/sampling-2
2 parents b6ed7f0 + 5a4e405 commit 1fd6a52

File tree

135 files changed

+3735
-1178
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

135 files changed

+3735
-1178
lines changed

.github/workflows/no-package-lock-changes.yml

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,26 +8,44 @@ jobs:
88
name: Prevent package-lock.json changes in PRs
99
runs-on: ubuntu-latest
1010
steps:
11+
- name: Get file changes
12+
uses: trilom/file-changes-action@ce38c8ce2459ca3c303415eec8cb0409857b4272
13+
id: file_changes
14+
- name: Check if lockfiles were modified
15+
id: lockfile_check
16+
run: |
17+
if cat $HOME/files.json | jq -e 'any(test("package-lock\\.json$|Cargo\\.lock$"))' > /dev/null; then
18+
echo "lockfiles_modified=true" >> $GITHUB_OUTPUT
19+
echo "Lockfiles were modified in this PR"
20+
else
21+
echo "lockfiles_modified=false" >> $GITHUB_OUTPUT
22+
echo "No lockfiles were modified in this PR"
23+
fi
24+
- name: Prevent Copilot from modifying lockfiles
25+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && github.event.pull_request.user.login == 'Copilot' }}
26+
run: |
27+
echo "Copilot is not allowed to modify package-lock.json or Cargo.lock files."
28+
echo "If you need to update dependencies, please do so manually or through authorized means."
29+
exit 1
1130
- uses: octokit/request-action@dad4362715b7fb2ddedf9772c8670824af564f0d # v2.4.0
1231
id: get_permissions
32+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && github.event.pull_request.user.login != 'Copilot' }}
1333
with:
1434
route: GET /repos/microsoft/vscode/collaborators/{username}/permission
1535
username: ${{ github.event.pull_request.user.login }}
1636
env:
1737
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
1838
- name: Set control output variable
1939
id: control
40+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && github.event.pull_request.user.login != 'Copilot' }}
2041
run: |
2142
echo "user: ${{ github.event.pull_request.user.login }}"
2243
echo "role: ${{ fromJson(steps.get_permissions.outputs.data).permission }}"
2344
echo "is dependabot: ${{ github.event.pull_request.user.login == 'dependabot[bot]' }}"
2445
echo "should_run: ${{ !contains(fromJson('["admin", "maintain", "write"]'), fromJson(steps.get_permissions.outputs.data).permission) }}"
2546
echo "should_run=${{ !contains(fromJson('["admin", "maintain", "write"]'), fromJson(steps.get_permissions.outputs.data).permission) && github.event.pull_request.user.login != 'dependabot[bot]' }}" >> $GITHUB_OUTPUT
26-
- name: Get file changes
27-
uses: trilom/file-changes-action@ce38c8ce2459ca3c303415eec8cb0409857b4272
28-
if: ${{ steps.control.outputs.should_run == 'true' }}
2947
- name: Check for lockfile changes
30-
if: ${{ steps.control.outputs.should_run == 'true' }}
48+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && steps.control.outputs.should_run == 'true' }}
3149
run: |
32-
cat $HOME/files.json | jq -e 'any(test("package-lock\\.json$|Cargo\\.lock$")) | not' \
33-
|| (echo "Changes to package-lock.json/Cargo.lock files aren't allowed in PRs." && exit 1)
50+
echo "Changes to package-lock.json/Cargo.lock files aren't allowed in PRs."
51+
exit 1

.github/workflows/no-yarn-lock-changes.yml

Lines changed: 24 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -8,26 +8,44 @@ jobs:
88
name: Prevent yarn.lock changes in PRs
99
runs-on: ubuntu-latest
1010
steps:
11+
- name: Get file changes
12+
uses: trilom/file-changes-action@a6ca26c14274c33b15e6499323aac178af06ad4b # v1.2.4
13+
id: file_changes
14+
- name: Check if lockfiles were modified
15+
id: lockfile_check
16+
run: |
17+
if cat $HOME/files.json | jq -e 'any(test("yarn\\.lock$|Cargo\\.lock$"))' > /dev/null; then
18+
echo "lockfiles_modified=true" >> $GITHUB_OUTPUT
19+
echo "Lockfiles were modified in this PR"
20+
else
21+
echo "lockfiles_modified=false" >> $GITHUB_OUTPUT
22+
echo "No lockfiles were modified in this PR"
23+
fi
24+
- name: Prevent Copilot from modifying lockfiles
25+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && github.event.pull_request.user.login == 'Copilot' }}
26+
run: |
27+
echo "Copilot is not allowed to modify yarn.lock or Cargo.lock files."
28+
echo "If you need to update dependencies, please do so manually or through authorized means."
29+
exit 1
1130
- uses: octokit/request-action@dad4362715b7fb2ddedf9772c8670824af564f0d # v2.4.0
1231
id: get_permissions
32+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && github.event.pull_request.user.login != 'Copilot' }}
1333
with:
1434
route: GET /repos/microsoft/vscode/collaborators/{username}/permission
1535
username: ${{ github.event.pull_request.user.login }}
1636
env:
1737
GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }}
1838
- name: Set control output variable
1939
id: control
40+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && github.event.pull_request.user.login != 'Copilot' }}
2041
run: |
2142
echo "user: ${{ github.event.pull_request.user.login }}"
2243
echo "role: ${{ fromJson(steps.get_permissions.outputs.data).permission }}"
2344
echo "is dependabot: ${{ github.event.pull_request.user.login == 'dependabot[bot]' }}"
2445
echo "should_run: ${{ !contains(fromJson('["admin", "maintain", "write"]'), fromJson(steps.get_permissions.outputs.data).permission) }}"
2546
echo "should_run=${{ !contains(fromJson('["admin", "maintain", "write"]'), fromJson(steps.get_permissions.outputs.data).permission) && github.event.pull_request.user.login != 'dependabot[bot]' }}" >> $GITHUB_OUTPUT
26-
- name: Get file changes
27-
uses: trilom/file-changes-action@a6ca26c14274c33b15e6499323aac178af06ad4b # v1.2.4
28-
if: ${{ steps.control.outputs.should_run == 'true' }}
2947
- name: Check for lockfile changes
30-
if: ${{ steps.control.outputs.should_run == 'true' }}
48+
if: ${{ steps.lockfile_check.outputs.lockfiles_modified == 'true' && steps.control.outputs.should_run == 'true' }}
3149
run: |
32-
cat $HOME/files.json | jq -e 'any(test("yarn\\.lock$|Cargo\\.lock$")) | not' \
33-
|| (echo "Changes to yarn.lock/Cargo.lock files aren't allowed in PRs." && exit 1)
50+
echo "Changes to yarn.lock/Cargo.lock files aren't allowed in PRs."
51+
exit 1

build/azure-pipelines/product-build.yml

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -296,7 +296,7 @@ extends:
296296
- ${{ if eq(parameters.VSCODE_BUILD_WIN32, true) }}:
297297
- job: CLIWindowsX64
298298
pool:
299-
name: 1es-windows-2019-x64
299+
name: 1es-windows-2022-x64
300300
os: windows
301301
steps:
302302
- template: build/azure-pipelines/win32/cli-build-win32.yml@self
@@ -308,7 +308,7 @@ extends:
308308
- ${{ if and(eq(variables['VSCODE_CIBUILD'], false), eq(parameters.VSCODE_BUILD_WIN32_ARM64, true)) }}:
309309
- job: CLIWindowsARM64
310310
pool:
311-
name: 1es-windows-2019-x64
311+
name: 1es-windows-2022-x64
312312
os: windows
313313
steps:
314314
- template: build/azure-pipelines/win32/cli-build-win32.yml@self
@@ -320,7 +320,7 @@ extends:
320320
- stage: APIScan
321321
dependsOn: []
322322
pool:
323-
name: 1es-windows-2019-x64
323+
name: 1es-windows-2022-x64
324324
os: windows
325325
jobs:
326326
- job: WindowsAPIScan
@@ -669,7 +669,7 @@ extends:
669669
- stage: Publish
670670
dependsOn: []
671671
pool:
672-
name: 1es-windows-2019-x64
672+
name: 1es-windows-2022-x64
673673
os: windows
674674
variables:
675675
- name: BUILDS_API_URL

extensions/git/src/api/api1.ts

Lines changed: 22 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@
77

88
import { Model } from '../model';
99
import { Repository as BaseRepository, Resource } from '../repository';
10-
import { InputBox, Git, API, Repository, Remote, RepositoryState, Branch, ForcePushMode, Ref, Submodule, Commit, Change, RepositoryUIState, Status, LogOptions, APIState, CommitOptions, RefType, CredentialsProvider, BranchQuery, PushErrorHandler, PublishEvent, FetchOptions, RemoteSourceProvider, RemoteSourcePublisher, PostCommitCommandsProvider, RefQuery, BranchProtectionProvider, InitOptions, SourceControlHistoryItemDetailsProvider } from './git';
10+
import { InputBox, Git, API, Repository, Remote, RepositoryState, Branch, ForcePushMode, Ref, Submodule, Commit, Change, RepositoryUIState, Status, LogOptions, APIState, CommitOptions, RefType, CredentialsProvider, BranchQuery, PushErrorHandler, PublishEvent, FetchOptions, RemoteSourceProvider, RemoteSourcePublisher, PostCommitCommandsProvider, RefQuery, BranchProtectionProvider, InitOptions, SourceControlHistoryItemDetailsProvider, GitErrorCodes } from './git';
1111
import { Event, SourceControlInputBox, Uri, SourceControl, Disposable, commands, CancellationToken } from 'vscode';
1212
import { combinedDisposable, filterEvent, mapEvent } from '../util';
1313
import { toGitUri } from '../uri';
@@ -371,6 +371,27 @@ export class ApiImpl implements API {
371371
return result ? new ApiRepository(result) : null;
372372
}
373373

374+
async getRepositoryRoot(uri: Uri): Promise<Uri | null> {
375+
const repository = this.getRepository(uri);
376+
if (repository) {
377+
return repository.rootUri;
378+
}
379+
380+
try {
381+
const root = await this.#model.git.getRepositoryRoot(uri.fsPath);
382+
return Uri.file(root);
383+
} catch (err) {
384+
if (
385+
err.gitErrorCode === GitErrorCodes.NotAGitRepository ||
386+
err.gitErrorCode === GitErrorCodes.NotASafeGitRepository
387+
) {
388+
return null;
389+
}
390+
391+
throw err;
392+
}
393+
}
394+
374395
async init(root: Uri, options?: InitOptions): Promise<Repository | null> {
375396
const path = root.fsPath;
376397
await this.#model.git.init(path, options);

extensions/git/src/api/git.d.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -364,6 +364,7 @@ export interface API {
364364

365365
toGitUri(uri: Uri, ref: string): Uri;
366366
getRepository(uri: Uri): Repository | null;
367+
getRepositoryRoot(uri: Uri): Promise<Uri | null>;
367368
init(root: Uri, options?: InitOptions): Promise<Repository | null>;
368369
openRepository(root: Uri): Promise<Repository | null>
369370

@@ -402,6 +403,7 @@ export const enum GitErrorCodes {
402403
NoUserEmailConfigured = 'NoUserEmailConfigured',
403404
NoRemoteRepositorySpecified = 'NoRemoteRepositorySpecified',
404405
NotAGitRepository = 'NotAGitRepository',
406+
NotASafeGitRepository = 'NotASafeGitRepository',
405407
NotAtRepositoryRoot = 'NotAtRepositoryRoot',
406408
Conflict = 'Conflict',
407409
StashConflict = 'StashConflict',

extensions/git/src/askpass-main.ts

Lines changed: 6 additions & 29 deletions
Original file line numberDiff line numberDiff line change
@@ -29,38 +29,15 @@ function main(argv: string[]): void {
2929
return fatal('Skip silent fetch commands');
3030
}
3131

32-
const output = process.env['VSCODE_GIT_ASKPASS_PIPE'] as string;
32+
const output = process.env['VSCODE_GIT_ASKPASS_PIPE'];
3333
const askpassType = process.env['VSCODE_GIT_ASKPASS_TYPE'] as 'https' | 'ssh';
3434

35-
// HTTPS (username | password), SSH (passphrase | authenticity)
36-
const request = askpassType === 'https' ? argv[2] : argv[3];
37-
38-
let host: string | undefined,
39-
file: string | undefined,
40-
fingerprint: string | undefined;
41-
42-
if (askpassType === 'https') {
43-
host = argv[4].replace(/^["']+|["':]+$/g, '');
44-
}
45-
46-
if (askpassType === 'ssh') {
47-
if (/passphrase/i.test(request)) {
48-
// passphrase
49-
// Commit signing - Enter passphrase:
50-
// Git operation - Enter passphrase for key '/c/Users/<username>/.ssh/id_ed25519':
51-
file = argv[6]?.replace(/^["']+|["':]+$/g, '');
52-
} else {
53-
// authenticity
54-
host = argv[6].replace(/^["']+|["':]+$/g, '');
55-
fingerprint = argv[15];
56-
}
57-
}
58-
5935
const ipcClient = new IPCClient('askpass');
60-
ipcClient.call({ askpassType, request, host, file, fingerprint }).then(res => {
61-
fs.writeFileSync(output, res + '\n');
62-
setTimeout(() => process.exit(0), 0);
63-
}).catch(err => fatal(err));
36+
ipcClient.call({ askpassType, argv })
37+
.then(res => {
38+
fs.writeFileSync(output, res + '\n');
39+
setTimeout(() => process.exit(0), 0);
40+
}).catch(err => fatal(err));
6441
}
6542

6643
main(process.argv);

extensions/git/src/askpass.ts

Lines changed: 35 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
* Licensed under the MIT License. See License.txt in the project root for license information.
44
*--------------------------------------------------------------------------------------------*/
55

6-
import { window, InputBoxOptions, Uri, Disposable, workspace, QuickPickOptions, l10n } from 'vscode';
6+
import { window, InputBoxOptions, Uri, Disposable, workspace, QuickPickOptions, l10n, LogOutputChannel } from 'vscode';
77
import { IDisposable, EmptyDisposable, toDisposable } from './util';
88
import * as path from 'path';
99
import { IIPCHandler, IIPCServer } from './ipc/ipcServer';
@@ -20,7 +20,7 @@ export class Askpass implements IIPCHandler, ITerminalEnvironmentProvider {
2020

2121
readonly featureDescription = 'git auth provider';
2222

23-
constructor(private ipc?: IIPCServer) {
23+
constructor(private ipc: IIPCServer | undefined, private readonly logger: LogOutputChannel) {
2424
if (ipc) {
2525
this.disposable = ipc.registerHandler('askpass', this);
2626
}
@@ -31,37 +31,41 @@ export class Askpass implements IIPCHandler, ITerminalEnvironmentProvider {
3131
// VSCODE_GIT_ASKPASS
3232
VSCODE_GIT_ASKPASS_NODE: process.execPath,
3333
VSCODE_GIT_ASKPASS_EXTRA_ARGS: '',
34-
VSCODE_GIT_ASKPASS_MAIN: path.join(__dirname, 'askpass-main.js'),
34+
VSCODE_GIT_ASKPASS_MAIN: path.join(__dirname, 'askpass-main.js')
3535
};
3636

3737
this.sshEnv = {
3838
// SSH_ASKPASS
3939
SSH_ASKPASS: path.join(__dirname, this.ipc ? 'ssh-askpass.sh' : 'ssh-askpass-empty.sh'),
40-
SSH_ASKPASS_REQUIRE: 'force',
40+
SSH_ASKPASS_REQUIRE: 'force'
4141
};
4242
}
4343

44-
async handle(payload:
45-
{ askpassType: 'https'; request: string; host: string } |
46-
{ askpassType: 'ssh'; request: string; host?: string; file?: string; fingerprint?: string }
47-
): Promise<string> {
44+
async handle(payload: { askpassType: 'https' | 'ssh'; argv: string[] }): Promise<string> {
45+
this.logger.trace(`[Askpass][handle] ${JSON.stringify(payload)}`);
46+
4847
const config = workspace.getConfiguration('git', null);
4948
const enabled = config.get<boolean>('enabled');
5049

5150
if (!enabled) {
51+
this.logger.trace(`[Askpass][handle] Git is disabled`);
5252
return '';
5353
}
5454

55-
// https
56-
if (payload.askpassType === 'https') {
57-
return await this.handleAskpass(payload.request, payload.host);
58-
}
59-
60-
// ssh
61-
return await this.handleSSHAskpass(payload.request, payload.host, payload.file, payload.fingerprint);
55+
return payload.askpassType === 'https'
56+
? await this.handleAskpass(payload.argv)
57+
: await this.handleSSHAskpass(payload.argv);
6258
}
6359

64-
async handleAskpass(request: string, host: string): Promise<string> {
60+
async handleAskpass(argv: string[]): Promise<string> {
61+
// HTTPS (username | password)
62+
// Username for 'https://github.com':
63+
// Password for 'https://github.com':
64+
const request = argv[2];
65+
const host = argv[4].replace(/^["']+|["':]+$/g, '');
66+
67+
this.logger.trace(`[Askpass][handleAskpass] request: ${request}, host: ${host}`);
68+
6569
const uri = Uri.parse(host);
6670
const authority = uri.authority.replace(/^.*@/, '');
6771
const password = /password/i.test(request);
@@ -96,9 +100,18 @@ export class Askpass implements IIPCHandler, ITerminalEnvironmentProvider {
96100
return await window.showInputBox(options) || '';
97101
}
98102

99-
async handleSSHAskpass(request: string, host?: string, file?: string, fingerprint?: string): Promise<string> {
103+
async handleSSHAskpass(argv: string[]): Promise<string> {
104+
// SSH (passphrase | authenticity)
105+
const request = argv[3];
106+
100107
// passphrase
101108
if (/passphrase/i.test(request)) {
109+
// Commit signing - Enter passphrase:
110+
// Git operation - Enter passphrase for key '/c/Users/<username>/.ssh/id_ed25519':
111+
const file = argv[6]?.replace(/^["']+|["':]+$/g, '');
112+
113+
this.logger.trace(`[Askpass][handleSSHAskpass] request: ${request}, file: ${file}`);
114+
102115
const options: InputBoxOptions = {
103116
password: true,
104117
placeHolder: l10n.t('Passphrase'),
@@ -110,6 +123,11 @@ export class Askpass implements IIPCHandler, ITerminalEnvironmentProvider {
110123
}
111124

112125
// authenticity
126+
const host = argv[6].replace(/^["']+|["':]+$/g, '');
127+
const fingerprint = argv[15];
128+
129+
this.logger.trace(`[Askpass][handleSSHAskpass] request: ${request}, host: ${host}, fingerprint: ${fingerprint}`);
130+
113131
const options: QuickPickOptions = {
114132
canPickMany: false,
115133
ignoreFocusOut: true,

extensions/git/src/git.ts

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -342,6 +342,8 @@ function getGitErrorCode(stderr: string): string | undefined {
342342
return GitErrorCodes.InvalidBranchName;
343343
} else if (/Please,? commit your changes or stash them/.test(stderr)) {
344344
return GitErrorCodes.DirtyWorkTree;
345+
} else if (/detected dubious ownership in repository at/.test(stderr)) {
346+
return GitErrorCodes.NotASafeGitRepository;
345347
}
346348

347349
return undefined;

extensions/git/src/main.ts

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -70,7 +70,7 @@ async function createModel(context: ExtensionContext, logger: LogOutputChannel,
7070
logger.error(`[main] Failed to create git IPC: ${err}`);
7171
}
7272

73-
const askpass = new Askpass(ipcServer);
73+
const askpass = new Askpass(ipcServer, logger);
7474
disposables.push(askpass);
7575

7676
const gitEditor = new GitEditor(ipcServer);

extensions/theme-defaults/themes/dark_modern.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,8 @@
1919
"button.secondaryBackground": "#313131",
2020
"button.secondaryForeground": "#CCCCCC",
2121
"button.secondaryHoverBackground": "#3C3C3C",
22-
"chat.slashCommandBackground": "#34414B",
23-
"chat.slashCommandForeground": "#40A6FF",
22+
"chat.slashCommandBackground": "#26477866",
23+
"chat.slashCommandForeground": "#85B6FF",
2424
"chat.editedFileForeground": "#E2C08D",
2525
"checkbox.background": "#313131",
2626
"checkbox.border": "#3C3C3C",

extensions/theme-defaults/themes/light_modern.json

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -19,8 +19,8 @@
1919
"button.secondaryBackground": "#E5E5E5",
2020
"button.secondaryForeground": "#3B3B3B",
2121
"button.secondaryHoverBackground": "#CCCCCC",
22-
"chat.slashCommandBackground": "#D2ECFF",
23-
"chat.slashCommandForeground": "#306CA2",
22+
"chat.slashCommandBackground": "#ADCEFF7A",
23+
"chat.slashCommandForeground": "#26569E",
2424
"chat.editedFileForeground": "#895503",
2525
"checkbox.background": "#F8F8F8",
2626
"checkbox.border": "#CECECE",

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
{
22
"name": "code-oss-dev",
33
"version": "1.101.0",
4-
"distro": "ba782a84e32786e63185b7946c791bf89cb8da7a",
4+
"distro": "a4a51f792a6f0ce2060af18f27dcb4ae0895851d",
55
"author": {
66
"name": "Microsoft Corporation"
77
},

0 commit comments

Comments
 (0)