Skip to content

Commit 0190644

Browse files
authored
Smarter decisions on if user should be prompted for Xcode change (#1640)
* Smarter decisions on if user should be prompted for Xcode change If you use a swiftly path then you are prompted everytime VSCode opens even if the xcode-select -p is the same. Example settings: ``` "swift.path": "${userHome}/.swiftly/bin", "swift.swiftEnvironmentVariables": { "DEVELOPER_DIR": "/Applications/Xcode.app/Contents/Developer" }, ``` So consider the DEVELOPER_DIR as well to know if this changed. Issue: #1472 * Re-fetch DEVELOPER_DIR each time * Fix formatting issues
1 parent 49c4c9a commit 0190644

File tree

2 files changed

+101
-34
lines changed

2 files changed

+101
-34
lines changed

src/toolchain/SelectedXcodeWatcher.ts

Lines changed: 18 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -67,10 +67,14 @@ export class SelectedXcodeWatcher implements vscode.Disposable {
6767
*/
6868
private async setup() {
6969
this.xcodePath = await this.xcodeSymlink();
70+
const developerDir = () => configuration.swiftEnvironmentVariables["DEVELOPER_DIR"];
71+
const matchesPath = (xcodePath: string) =>
72+
configuration.path && configuration.path.startsWith(xcodePath);
73+
const matchesDeveloperDir = (xcodePath: string) => developerDir()?.startsWith(xcodePath);
7074
if (
7175
this.xcodePath &&
72-
configuration.path &&
73-
!configuration.path.startsWith(this.xcodePath)
76+
(configuration.path || developerDir()) &&
77+
!(matchesPath(this.xcodePath) || matchesDeveloperDir(this.xcodePath))
7478
) {
7579
this.xcodePath = undefined; // Notify user when initially launching that xcode changed since last session
7680
}
@@ -89,7 +93,18 @@ export class SelectedXcodeWatcher implements vscode.Disposable {
8993
await showReloadExtensionNotification(
9094
"The Swift Extension has detected a change in the selected Xcode. Please reload the extension to apply the changes."
9195
);
92-
} else {
96+
} else if (developerDir() && !matchesDeveloperDir(this.xcodePath)) {
97+
const selected = await vscode.window.showWarningMessage(
98+
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your DEVELOPER_DIR in the "swift.swiftEnvironmentVariables" setting. Would you like to update your configured "swift.swiftEnvironmentVariables" setting?',
99+
"Remove From Settings",
100+
"Select Toolchain"
101+
);
102+
if (selected === "Remove From Settings") {
103+
await removeToolchainPath();
104+
} else if (selected === "Select Toolchain") {
105+
await selectToolchain();
106+
}
107+
} else if (!matchesPath(this.xcodePath)) {
93108
const selected = await vscode.window.showWarningMessage(
94109
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your "swift.path" setting. Would you like to update your configured "swift.path" setting?',
95110
"Remove From Settings",

test/unit-tests/toolchain/SelectedXcodeWatcher.test.ts

Lines changed: 83 additions & 31 deletions
Original file line numberDiff line numberDiff line change
@@ -31,6 +31,7 @@ suite("Selected Xcode Watcher", () => {
3131
const mockedVSCodeWindow = mockGlobalObject(vscode, "window");
3232
let mockOutputChannel: MockedObject<SwiftOutputChannel>;
3333
const pathConfig = mockGlobalValue(configuration, "path");
34+
const envConfig = mockGlobalValue(configuration, "swiftEnvironmentVariables");
3435
const mockWorkspace = mockGlobalObject(vscode, "workspace");
3536
const mockCommands = mockGlobalObject(vscode, "commands");
3637
let mockSwiftConfig: MockedObject<vscode.WorkspaceConfiguration>;
@@ -94,50 +95,101 @@ suite("Selected Xcode Watcher", () => {
9495
);
9596
});
9697

97-
test("Warns that setting is out of date", async () => {
98-
pathConfig.setValue("/path/to/swift/bin");
98+
suite('"swift.path" is out of date', () => {
99+
setup(() => {
100+
pathConfig.setValue("/path/to/swift/bin");
101+
});
99102

100-
await run(["/path/to/swift/bin", "/foo", "/foo"]);
103+
test("Warns that setting is out of date on startup", async () => {
104+
await run(["/foo", "/foo"]);
101105

102-
expect(mockedVSCodeWindow.showWarningMessage).to.have.been.calledOnceWithExactly(
103-
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your "swift.path" setting. Would you like to update your configured "swift.path" setting?',
104-
"Remove From Settings",
105-
"Select Toolchain"
106-
);
107-
});
106+
expect(mockedVSCodeWindow.showWarningMessage).to.have.been.calledOnceWithExactly(
107+
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your "swift.path" setting. Would you like to update your configured "swift.path" setting?',
108+
"Remove From Settings",
109+
"Select Toolchain"
110+
);
111+
});
108112

109-
test("Warns that setting is out of date on startup", async () => {
110-
pathConfig.setValue("/path/to/swift/bin");
113+
test("Remove setting", async () => {
114+
mockedVSCodeWindow.showWarningMessage.resolves("Remove From Settings" as any);
111115

112-
await run(["/foo", "/foo"]);
116+
await run(["/foo", "/foo"]);
113117

114-
expect(mockedVSCodeWindow.showWarningMessage).to.have.been.calledOnceWithExactly(
115-
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your "swift.path" setting. Would you like to update your configured "swift.path" setting?',
116-
"Remove From Settings",
117-
"Select Toolchain"
118-
);
119-
});
118+
expect(mockSwiftConfig.update.args).to.deep.equal([
119+
["path", undefined, vscode.ConfigurationTarget.Global],
120+
["path", undefined, vscode.ConfigurationTarget.Workspace],
121+
]);
122+
});
120123

121-
test("Remove setting", async () => {
122-
pathConfig.setValue("/path/to/swift/bin");
124+
test("Select toolchain", async () => {
125+
mockedVSCodeWindow.showWarningMessage.resolves("Select Toolchain" as any);
123126

124-
mockedVSCodeWindow.showWarningMessage.resolves("Remove From Settings" as any);
127+
await run(["/foo", "/foo"]);
125128

126-
await run(["/foo", "/foo"]);
129+
expect(mockCommands.executeCommand).to.have.been.calledOnceWith(
130+
Commands.SELECT_TOOLCHAIN
131+
);
132+
});
133+
134+
test("Warns that setting is out of date", async () => {
135+
envConfig.setValue({ DEVELOPER_DIR: "/bar" });
136+
await run([undefined, "/bar", "/bar"]);
127137

128-
expect(mockSwiftConfig.update.args).to.deep.equal([
129-
["path", undefined, vscode.ConfigurationTarget.Global],
130-
["path", undefined, vscode.ConfigurationTarget.Workspace],
131-
]);
138+
expect(mockedVSCodeWindow.showWarningMessage).to.have.been.calledOnceWithExactly(
139+
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your "swift.path" setting. Would you like to update your configured "swift.path" setting?',
140+
"Remove From Settings",
141+
"Select Toolchain"
142+
);
143+
});
132144
});
133145

134-
test("Select toolchain", async () => {
135-
pathConfig.setValue("/path/to/swift/bin");
146+
suite("DEVELOPER_DIR is out of date", () => {
147+
setup(() => {
148+
pathConfig.setValue("/path/to/swift/bin");
149+
envConfig.setValue({ DEVELOPER_DIR: "/bar" });
150+
});
136151

137-
mockedVSCodeWindow.showWarningMessage.resolves("Select Toolchain" as any);
152+
test("Warns that environment is out of date on startup", async () => {
153+
pathConfig.setValue("/path/to/swift/bin");
138154

139-
await run(["/foo", "/foo"]);
155+
await run(["/foo", "/foo"]);
156+
157+
expect(mockedVSCodeWindow.showWarningMessage).to.have.been.calledOnceWithExactly(
158+
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your DEVELOPER_DIR in the "swift.swiftEnvironmentVariables" setting. Would you like to update your configured "swift.swiftEnvironmentVariables" setting?',
159+
"Remove From Settings",
160+
"Select Toolchain"
161+
);
162+
});
163+
164+
test("Remove setting", async () => {
165+
mockedVSCodeWindow.showWarningMessage.resolves("Remove From Settings" as any);
166+
167+
await run(["/foo", "/foo"]);
168+
169+
expect(mockSwiftConfig.update.args).to.deep.equal([
170+
["path", undefined, vscode.ConfigurationTarget.Global],
171+
["path", undefined, vscode.ConfigurationTarget.Workspace],
172+
]);
173+
});
174+
175+
test("Select toolchain", async () => {
176+
mockedVSCodeWindow.showWarningMessage.resolves("Select Toolchain" as any);
140177

141-
expect(mockCommands.executeCommand).to.have.been.calledOnceWith(Commands.SELECT_TOOLCHAIN);
178+
await run(["/foo", "/foo"]);
179+
180+
expect(mockCommands.executeCommand).to.have.been.calledOnceWith(
181+
Commands.SELECT_TOOLCHAIN
182+
);
183+
});
184+
185+
test("Warns that setting is out of date", async () => {
186+
await run(["/bar", "/foo", "/foo"]);
187+
188+
expect(mockedVSCodeWindow.showWarningMessage).to.have.been.calledOnceWithExactly(
189+
'The Swift Extension has detected a change in the selected Xcode which does not match the value of your DEVELOPER_DIR in the "swift.swiftEnvironmentVariables" setting. Would you like to update your configured "swift.swiftEnvironmentVariables" setting?',
190+
"Remove From Settings",
191+
"Select Toolchain"
192+
);
193+
});
142194
});
143195
});

0 commit comments

Comments
 (0)