Skip to content

Commit 949dcce

Browse files
author
Akos Kitta
committed
Refresh menus when opening example/recent fails.
Closes #53 Signed-off-by: Akos Kitta <[email protected]>
1 parent 59ca91d commit 949dcce

13 files changed

+288
-309
lines changed

Diff for: arduino-ide-extension/src/browser/contributions/examples.ts

+69-23
Original file line numberDiff line numberDiff line change
@@ -21,17 +21,17 @@ import {
2121
MenuModelRegistry,
2222
} from './contribution';
2323
import { NotificationCenter } from '../notification-center';
24-
import { Board, SketchRef, SketchContainer } from '../../common/protocol';
24+
import {
25+
Board,
26+
SketchRef,
27+
SketchContainer,
28+
SketchesError,
29+
Sketch,
30+
} from '../../common/protocol';
2531
import { nls } from '@theia/core/lib/common';
2632

2733
@injectable()
2834
export abstract class Examples extends SketchContribution {
29-
@inject(CommandRegistry)
30-
protected readonly commandRegistry: CommandRegistry;
31-
32-
@inject(MenuModelRegistry)
33-
protected readonly menuRegistry: MenuModelRegistry;
34-
3535
@inject(MainMenuManager)
3636
protected readonly menuManager: MainMenuManager;
3737

@@ -41,6 +41,12 @@ export abstract class Examples extends SketchContribution {
4141
@inject(BoardsServiceProvider)
4242
protected readonly boardsServiceClient: BoardsServiceProvider;
4343

44+
@inject(CommandRegistry)
45+
private readonly commandRegistry: CommandRegistry;
46+
47+
@inject(MenuModelRegistry)
48+
private readonly menuRegistry: MenuModelRegistry;
49+
4450
protected readonly toDispose = new DisposableCollection();
4551

4652
protected override init(): void {
@@ -50,10 +56,16 @@ export abstract class Examples extends SketchContribution {
5056
);
5157
}
5258

59+
// eslint-disable-next-line @typescript-eslint/no-unused-vars, unused-imports/no-unused-vars
5360
protected handleBoardChanged(board: Board | undefined): void {
5461
// NOOP
5562
}
5663

64+
protected abstract update(options?: {
65+
board?: Board | undefined;
66+
forceRefresh?: boolean;
67+
}): void;
68+
5769
override registerMenus(registry: MenuModelRegistry): void {
5870
try {
5971
// This is a hack the ensures the desired menu ordering! We cannot use https://github.com/eclipse-theia/theia/pull/8377 due to ATL-222.
@@ -149,23 +161,54 @@ export abstract class Examples extends SketchContribution {
149161
protected createHandler(uri: string): CommandHandler {
150162
return {
151163
execute: async () => {
152-
const sketch = await this.sketchService.cloneExample(uri);
153-
return this.commandService.executeCommand(
154-
OpenSketch.Commands.OPEN_SKETCH.id,
155-
sketch
156-
);
164+
const sketch = await this.clone(uri);
165+
if (sketch) {
166+
try {
167+
return this.commandService.executeCommand(
168+
OpenSketch.Commands.OPEN_SKETCH.id,
169+
sketch
170+
);
171+
} catch (err) {
172+
if (SketchesError.NotFound.is(err)) {
173+
// Do not toast the error message. It's handled by the `Open Sketch` command.
174+
this.update({
175+
board: this.boardsServiceClient.boardsConfig.selectedBoard,
176+
forceRefresh: true,
177+
});
178+
} else {
179+
throw err;
180+
}
181+
}
182+
}
157183
},
158184
};
159185
}
186+
187+
private async clone(uri: string): Promise<Sketch | undefined> {
188+
try {
189+
const sketch = await this.sketchService.cloneExample(uri);
190+
return sketch;
191+
} catch (err) {
192+
if (SketchesError.NotFound.is(err)) {
193+
this.messageService.error(err.message);
194+
this.update({
195+
board: this.boardsServiceClient.boardsConfig.selectedBoard,
196+
forceRefresh: true,
197+
});
198+
} else {
199+
throw err;
200+
}
201+
}
202+
}
160203
}
161204

162205
@injectable()
163206
export class BuiltInExamples extends Examples {
164207
override async onReady(): Promise<void> {
165-
this.register(); // no `await`
208+
this.update(); // no `await`
166209
}
167210

168-
protected async register(): Promise<void> {
211+
protected override async update(): Promise<void> {
169212
let sketchContainers: SketchContainer[] | undefined;
170213
try {
171214
sketchContainers = await this.examplesService.builtIns();
@@ -197,34 +240,37 @@ export class BuiltInExamples extends Examples {
197240
@injectable()
198241
export class LibraryExamples extends Examples {
199242
@inject(NotificationCenter)
200-
protected readonly notificationCenter: NotificationCenter;
243+
private readonly notificationCenter: NotificationCenter;
201244

202-
protected readonly queue = new PQueue({ autoStart: true, concurrency: 1 });
245+
private readonly queue = new PQueue({ autoStart: true, concurrency: 1 });
203246

204247
override onStart(): void {
205-
this.notificationCenter.onLibraryDidInstall(() => this.register());
206-
this.notificationCenter.onLibraryDidUninstall(() => this.register());
248+
this.notificationCenter.onLibraryDidInstall(() => this.update());
249+
this.notificationCenter.onLibraryDidUninstall(() => this.update());
207250
}
208251

209252
override async onReady(): Promise<void> {
210-
this.register(); // no `await`
253+
this.update(); // no `await`
211254
}
212255

213256
protected override handleBoardChanged(board: Board | undefined): void {
214-
this.register(board);
257+
this.update({ board });
215258
}
216259

217-
protected async register(
218-
board: Board | undefined = this.boardsServiceClient.boardsConfig
219-
.selectedBoard
260+
protected override async update(
261+
options: { board?: Board; forceRefresh?: boolean } = {
262+
board: this.boardsServiceClient.boardsConfig.selectedBoard,
263+
}
220264
): Promise<void> {
265+
const { board, forceRefresh } = options;
221266
return this.queue.add(async () => {
222267
this.toDispose.dispose();
223268
const fqbn = board?.fqbn;
224269
const name = board?.name;
225270
// Shows all examples when no board is selected, or the platform of the currently selected board is not installed.
226271
const { user, current, any } = await this.examplesService.installed({
227272
fqbn,
273+
forceRefresh,
228274
});
229275
if (user.length) {
230276
(user as any).unshift(

Diff for: arduino-ide-extension/src/browser/contributions/new-sketch.ts

-9
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,6 @@
11
import { nls } from '@theia/core/lib/common';
22
import { injectable } from '@theia/core/shared/inversify';
33
import { ArduinoMenus } from '../menu/arduino-menus';
4-
import { ArduinoToolbar } from '../toolbar/arduino-toolbar';
54
import {
65
SketchContribution,
76
URI,
@@ -17,11 +16,6 @@ export class NewSketch extends SketchContribution {
1716
registry.registerCommand(NewSketch.Commands.NEW_SKETCH, {
1817
execute: () => this.newSketch(),
1918
});
20-
registry.registerCommand(NewSketch.Commands.NEW_SKETCH__TOOLBAR, {
21-
isVisible: (widget) =>
22-
ArduinoToolbar.is(widget) && widget.side === 'left',
23-
execute: () => registry.executeCommand(NewSketch.Commands.NEW_SKETCH.id),
24-
});
2519
}
2620

2721
override registerMenus(registry: MenuModelRegistry): void {
@@ -54,8 +48,5 @@ export namespace NewSketch {
5448
export const NEW_SKETCH: Command = {
5549
id: 'arduino-new-sketch',
5650
};
57-
export const NEW_SKETCH__TOOLBAR: Command = {
58-
id: 'arduino-new-sketch--toolbar',
59-
};
6051
}
6152
}

Diff for: arduino-ide-extension/src/browser/contributions/open-recent-sketch.ts

+25-15
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,7 @@ import { MainMenuManager } from '../../common/main-menu-manager';
1515
import { OpenSketch } from './open-sketch';
1616
import { NotificationCenter } from '../notification-center';
1717
import { nls } from '@theia/core/lib/common';
18+
import { SketchesError } from '../../common/protocol';
1819

1920
@injectable()
2021
export class OpenRecentSketch extends SketchContribution {
@@ -33,7 +34,7 @@ export class OpenRecentSketch extends SketchContribution {
3334
@inject(NotificationCenter)
3435
protected readonly notificationCenter: NotificationCenter;
3536

36-
protected toDisposeBeforeRegister = new Map<string, DisposableCollection>();
37+
protected toDispose = new DisposableCollection();
3738

3839
override onStart(): void {
3940
this.notificationCenter.onRecentSketchesDidChange(({ sketches }) =>
@@ -42,8 +43,12 @@ export class OpenRecentSketch extends SketchContribution {
4243
}
4344

4445
override async onReady(): Promise<void> {
46+
this.update();
47+
}
48+
49+
private update(forceUpdate?: boolean): void {
4550
this.sketchService
46-
.recentlyOpenedSketches()
51+
.recentlyOpenedSketches(forceUpdate)
4752
.then((sketches) => this.refreshMenu(sketches));
4853
}
4954

@@ -62,19 +67,25 @@ export class OpenRecentSketch extends SketchContribution {
6267

6368
protected register(sketches: Sketch[]): void {
6469
const order = 0;
70+
this.toDispose.dispose();
6571
for (const sketch of sketches) {
6672
const { uri } = sketch;
67-
const toDispose = this.toDisposeBeforeRegister.get(uri);
68-
if (toDispose) {
69-
toDispose.dispose();
70-
}
7173
const command = { id: `arduino-open-recent--${uri}` };
7274
const handler = {
73-
execute: () =>
74-
this.commandRegistry.executeCommand(
75-
OpenSketch.Commands.OPEN_SKETCH.id,
76-
sketch
77-
),
75+
execute: async () => {
76+
try {
77+
await this.commandRegistry.executeCommand(
78+
OpenSketch.Commands.OPEN_SKETCH.id,
79+
sketch
80+
);
81+
} catch (err) {
82+
if (SketchesError.NotFound.is(err)) {
83+
this.update(true);
84+
} else {
85+
throw err;
86+
}
87+
}
88+
},
7889
};
7990
this.commandRegistry.registerCommand(command, handler);
8091
this.menuRegistry.registerMenuAction(
@@ -85,17 +96,16 @@ export class OpenRecentSketch extends SketchContribution {
8596
order: String(order),
8697
}
8798
);
88-
this.toDisposeBeforeRegister.set(
89-
sketch.uri,
99+
this.toDispose.pushAll([
90100
new DisposableCollection(
91101
Disposable.create(() =>
92102
this.commandRegistry.unregisterCommand(command)
93103
),
94104
Disposable.create(() =>
95105
this.menuRegistry.unregisterMenuAction(command)
96106
)
97-
)
98-
);
107+
),
108+
]);
99109
}
100110
}
101111
}

0 commit comments

Comments
 (0)