Skip to content

Commit 12f2aa3

Browse files
author
Akos Kitta
committed
Added support for 3rd party core settings.
Closes arduino/arduino-pro-ide#10. Signed-off-by: Akos Kitta <kittaakos@typefox.io>
1 parent 5c16f8d commit 12f2aa3

Some content is hidden

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

43 files changed

+1918
-908
lines changed

.vscode/launch.json

+21
Original file line numberDiff line numberDiff line change
@@ -83,6 +83,27 @@
8383
"smartStep": true,
8484
"internalConsoleOptions": "openOnSessionStart",
8585
"outputCapture": "std"
86+
},
87+
{
88+
"type": "node",
89+
"request": "launch",
90+
"protocol": "inspector",
91+
"name": "Run Test [current]",
92+
"program": "${workspaceRoot}/node_modules/mocha/bin/_mocha",
93+
"args": [
94+
"--require",
95+
"reflect-metadata/Reflect",
96+
"--no-timeouts",
97+
"--colors",
98+
"**/${fileBasenameNoExtension}.js"
99+
],
100+
"env": {
101+
"TS_NODE_PROJECT": "${workspaceRoot}/tsconfig.json"
102+
},
103+
"sourceMaps": true,
104+
"smartStep": true,
105+
"internalConsoleOptions": "openOnSessionStart",
106+
"outputCapture": "std"
86107
}
87108
]
88109
}

arduino-debugger-extension/package.json

+2-2
Original file line numberDiff line numberDiff line change
@@ -26,8 +26,8 @@
2626
],
2727
"theiaExtensions": [
2828
{
29-
"backend": "lib/node/backend-module",
30-
"frontend": "lib/browser/frontend-module"
29+
"backend": "lib/node/arduino-debug-backend-module",
30+
"frontend": "lib/browser/arduino-debug-frontend-module"
3131
}
3232
]
3333
}

arduino-debugger-extension/src/browser/frontend-module.ts renamed to arduino-debugger-extension/src/browser/arduino-debug-frontend-module.ts

-1
Original file line numberDiff line numberDiff line change
@@ -10,7 +10,6 @@ import { ArduinoDebugSessionManager } from './arduino-debug-session-manager';
1010

1111
import '../../src/browser/style/index.css';
1212

13-
1413
export default new ContainerModule((bind, unbind, isBound, rebind) => {
1514
bind(ArduinoVariableResolver).toSelf().inSingletonScope();
1615
bind(VariableContribution).toService(ArduinoVariableResolver);

arduino-ide-extension/data/cli/schema/arduino-cli.schema.json

+3
Original file line numberDiff line numberDiff line change
@@ -110,5 +110,8 @@
110110
"additionalProperties": false
111111
}
112112
},
113+
"// TODOs": [
114+
"additionalProperties should be true. See the new telemetry entry"
115+
],
113116
"additionalProperties": false
114117
}

arduino-ide-extension/package.json

+6-8
Original file line numberDiff line numberDiff line change
@@ -15,8 +15,8 @@
1515
"lint": "tslint -c ./tslint.json --project ./tsconfig.json",
1616
"build": "tsc && ncp ./src/node/cli-protocol/ ./lib/node/cli-protocol/ && yarn lint",
1717
"watch": "tsc -w",
18-
"test": "mocha \"./src/test/**/*.test.ts\"",
19-
"test:watch": "mocha --watch --watch-files src \"./src/test/**/*.test.ts\""
18+
"test": "mocha \"./lib/test/**/*.test.js\"",
19+
"test:watch": "mocha --watch --watch-files lib \"./lib/test/**/*.test.js\""
2020
},
2121
"dependencies": {
2222
"@grpc/grpc-js": "^0.6.18",
@@ -79,18 +79,16 @@
7979
"protoc": "1.0.4",
8080
"shelljs": "^0.8.3",
8181
"temp": "^0.9.1",
82-
"ts-node": "^8.6.2",
8382
"uuid": "^3.2.1",
8483
"yargs": "^11.1.0"
8584
},
8685
"mocha": {
8786
"require": [
88-
"ts-node/register",
8987
"reflect-metadata/Reflect"
9088
],
9189
"reporter": "spec",
9290
"colors": true,
93-
"watch-extensions": "ts,tsx",
91+
"watch-extensions": "js",
9492
"timeout": 10000
9593
},
9694
"files": [
@@ -101,12 +99,12 @@
10199
],
102100
"theiaExtensions": [
103101
{
104-
"backend": "lib/node/arduino-backend-module",
105-
"frontend": "lib/browser/arduino-frontend-module"
102+
"backend": "lib/node/arduino-ide-backend-module",
103+
"frontend": "lib/browser/arduino-ide-frontend-module"
106104
},
107105
{
108106
"frontend": "lib/browser/menu/browser-arduino-menu-module",
109-
"frontendElectron": "lib/electron-browser/electron-arduino-menu-module"
107+
"frontendElectron": "lib/electron-browser/menu/electron-arduino-menu-module"
110108
}
111109
]
112110
}

arduino-ide-extension/src/browser/arduino-daemon-client-impl.ts

+1-1
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import { injectable, inject } from 'inversify';
22
import { ILogger } from '@theia/core/lib/common/logger';
33
import { Event, Emitter } from '@theia/core/lib/common/event';
44
import { MessageService } from '@theia/core/lib/common/message-service';
5-
import { ArduinoDaemonClient } from '../common/protocol/arduino-daemon';
5+
import { ArduinoDaemonClient } from '../common/protocol';
66

77
@injectable()
88
export class ArduinoDaemonClientImpl implements ArduinoDaemonClient {

arduino-ide-extension/src/browser/arduino-frontend-contribution.tsx

+31-28
Original file line numberDiff line numberDiff line change
@@ -5,9 +5,8 @@ import { EditorWidget } from '@theia/editor/lib/browser/editor-widget';
55
import { MessageService } from '@theia/core/lib/common/message-service';
66
import { CommandContribution, CommandRegistry, Command, CommandHandler } from '@theia/core/lib/common/command';
77
import { TabBarToolbarContribution, TabBarToolbarRegistry } from '@theia/core/lib/browser/shell/tab-bar-toolbar';
8-
import { BoardsService } from '../common/protocol/boards-service';
8+
import { BoardsService, BoardsServiceClient, CoreService, Sketch, SketchesService, ToolOutputServiceClient } from '../common/protocol';
99
import { ArduinoCommands } from './arduino-commands';
10-
import { CoreService } from '../common/protocol/core-service';
1110
import { BoardsServiceClientImpl } from './boards/boards-service-client-impl';
1211
import { WorkspaceRootUriAwareCommandHandler, WorkspaceCommands } from '@theia/workspace/lib/browser/workspace-commands';
1312
import { SelectionService, MenuContribution, MenuModelRegistry, MAIN_MENU_BAR, MenuPath } from '@theia/core';
@@ -19,8 +18,6 @@ import {
1918
} from '@theia/core/lib/browser';
2019
import { OpenFileDialogProps, FileDialogService } from '@theia/filesystem/lib/browser/file-dialog';
2120
import { FileSystem, FileStat } from '@theia/filesystem/lib/common';
22-
import { Sketch, SketchesService } from '../common/protocol/sketches-service';
23-
import { ToolOutputServiceClient } from '../common/protocol/tool-output-service';
2421
import { CommonCommands, CommonMenus } from '@theia/core/lib/browser/common-frontend-contribution';
2522
import { FileSystemCommands } from '@theia/filesystem/lib/browser/filesystem-frontend-contribution';
2623
import { FileDownloadCommands } from '@theia/filesystem/lib/browser/download/file-download-command-contribution';
@@ -45,6 +42,8 @@ import { ColorContribution } from '@theia/core/lib/browser/color-application-con
4542
import { ColorRegistry } from '@theia/core/lib/browser/color-registry';
4643
import { ArduinoDaemon } from '../common/protocol/arduino-daemon';
4744
import { ConfigService } from '../common/protocol/config-service';
45+
import { BoardsConfigStore } from './boards/boards-config-store';
46+
import { MainMenuManager } from './menu/main-menu-manager';
4847

4948
export namespace ArduinoMenus {
5049
export const SKETCH = [...MAIN_MENU_BAR, '3_sketch'];
@@ -75,7 +74,11 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
7574
protected readonly toolOutputServiceClient: ToolOutputServiceClient;
7675

7776
@inject(BoardsServiceClientImpl)
78-
protected readonly boardsServiceClient: BoardsServiceClientImpl;
77+
protected readonly boardsServiceClientImpl: BoardsServiceClientImpl;
78+
79+
// Unused but do not remove it. It's required by DI, otherwise `init` method is not called.
80+
@inject(BoardsServiceClient)
81+
protected readonly boardsServiceClient: BoardsServiceClient;
7982

8083
@inject(SelectionService)
8184
protected readonly selectionService: SelectionService;
@@ -143,6 +146,12 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
143146
@inject(ConfigService)
144147
protected readonly configService: ConfigService;
145148

149+
@inject(BoardsConfigStore)
150+
protected readonly boardsConfigStore: BoardsConfigStore;
151+
152+
@inject(MainMenuManager)
153+
protected readonly mainMenuManager: MainMenuManager;
154+
146155
protected application: FrontendApplication;
147156
protected wsSketchCount: number = 0; // TODO: this does not belong here, does it?
148157

@@ -154,15 +163,10 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
154163
text: BoardsConfig.Config.toString(config)
155164
});
156165
}
157-
this.boardsServiceClient.onBoardsConfigChanged(updateStatusBar);
158-
updateStatusBar(this.boardsServiceClient.boardsConfig);
166+
this.boardsServiceClientImpl.onBoardsConfigChanged(updateStatusBar);
167+
updateStatusBar(this.boardsServiceClientImpl.boardsConfig);
159168

160169
this.registerSketchesInMenu(this.menuRegistry);
161-
162-
Promise.all([
163-
this.boardsService.getAttachedBoards(),
164-
this.boardsService.getAvailablePorts()
165-
]).then(([{ boards }, { ports }]) => this.boardsServiceClient.tryReconnect(boards, ports));
166170
}
167171

168172
onStart(app: FrontendApplication): void {
@@ -210,8 +214,7 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
210214
render: () => <BoardsToolBarItem
211215
key='boardsToolbarItem'
212216
commands={this.commandRegistry}
213-
boardsServiceClient={this.boardsServiceClient}
214-
boardService={this.boardsService} />,
217+
boardsServiceClient={this.boardsServiceClientImpl} />,
215218
isVisible: widget => ArduinoToolbar.is(widget) && widget.side === 'left',
216219
priority: 2
217220
});
@@ -276,10 +279,7 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
276279
});
277280

278281
registry.registerCommand(ArduinoCommands.TOGGLE_COMPILE_FOR_DEBUG, {
279-
execute: () => {
280-
this.editorMode.toggleCompileForDebug();
281-
this.editorMode.menuContentChanged.fire();
282-
},
282+
execute: () => this.editorMode.toggleCompileForDebug(),
283283
isToggled: () => this.editorMode.compileForDebug
284284
});
285285

@@ -345,7 +345,7 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
345345
execute: async () => {
346346
const boardsConfig = await this.boardsConfigDialog.open();
347347
if (boardsConfig) {
348-
this.boardsServiceClient.boardsConfig = boardsConfig;
348+
this.boardsServiceClientImpl.boardsConfig = boardsConfig;
349349
}
350350
}
351351
});
@@ -377,18 +377,18 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
377377
}
378378

379379
try {
380-
const { boardsConfig } = this.boardsServiceClient;
380+
const { boardsConfig } = this.boardsServiceClientImpl;
381381
if (!boardsConfig || !boardsConfig.selectedBoard) {
382382
throw new Error('No boards selected. Please select a board.');
383383
}
384384
if (!boardsConfig.selectedBoard.fqbn) {
385-
throw new Error(`No core is installed for ${boardsConfig.selectedBoard.name}. Please install the board.`);
385+
throw new Error(`No core is installed for the '${boardsConfig.selectedBoard.name}' board. Please install the core.`);
386386
}
387-
// Reveal the Output view asynchronously (don't await it)
387+
const fqbn = await this.boardsConfigStore.appendConfigToFqbn(boardsConfig.selectedBoard.fqbn);
388388
this.outputContribution.openView({ reveal: true });
389389
await this.coreService.compile({
390-
uri: uri.toString(),
391-
board: boardsConfig.selectedBoard,
390+
sketchUri: uri.toString(),
391+
fqbn,
392392
optimizeForDebug: this.editorMode.compileForDebug
393393
});
394394
} catch (e) {
@@ -413,19 +413,22 @@ export class ArduinoFrontendContribution implements FrontendApplicationContribut
413413
}
414414

415415
try {
416-
const { boardsConfig } = this.boardsServiceClient;
416+
const { boardsConfig } = this.boardsServiceClientImpl;
417417
if (!boardsConfig || !boardsConfig.selectedBoard) {
418418
throw new Error('No boards selected. Please select a board.');
419419
}
420420
const { selectedPort } = boardsConfig;
421421
if (!selectedPort) {
422422
throw new Error('No ports selected. Please select a port.');
423423
}
424-
// Reveal the Output view asynchronously (don't await it)
424+
if (!boardsConfig.selectedBoard.fqbn) {
425+
throw new Error(`No core is installed for the '${boardsConfig.selectedBoard.name}' board. Please install the core.`);
426+
}
425427
this.outputContribution.openView({ reveal: true });
428+
const fqbn = await this.boardsConfigStore.appendConfigToFqbn(boardsConfig.selectedBoard.fqbn);
426429
await this.coreService.upload({
427-
uri: uri.toString(),
428-
board: boardsConfig.selectedBoard,
430+
sketchUri: uri.toString(),
431+
fqbn,
429432
port: selectedPort.address,
430433
optimizeForDebug: this.editorMode.compileForDebug
431434
});

arduino-ide-extension/src/browser/arduino-frontend-module.ts renamed to arduino-ide-extension/src/browser/arduino-ide-frontend-module.ts

+20-1
Original file line numberDiff line numberDiff line change
@@ -75,6 +75,9 @@ import { ArduinoFrontendConnectionStatusService, ArduinoApplicationConnectionSta
7575
import { FrontendConnectionStatusService, ApplicationConnectionStatusContribution } from '@theia/core/lib/browser/connection-status-service';
7676
import { ConfigServiceClientImpl } from './config-service-client-impl';
7777
import { CoreServiceClientImpl } from './core-service-client-impl';
78+
import { BoardsDetailsMenuUpdater } from './boards/boards-details-menu-updater';
79+
import { BoardsConfigStore } from './boards/boards-config-store';
80+
import { ILogger } from '@theia/core';
7881

7982
const ElementQueries = require('css-element-queries/src/ElementQueries');
8083

@@ -144,12 +147,28 @@ export default new ContainerModule((bind: interfaces.Bind, unbind: interfaces.Un
144147
// Boards service client to receive and delegate notifications from the backend.
145148
bind(BoardsServiceClientImpl).toSelf().inSingletonScope();
146149
bind(FrontendApplicationContribution).toService(BoardsServiceClientImpl);
147-
bind(BoardsServiceClient).toDynamicValue(context => {
150+
bind(BoardsServiceClient).toDynamicValue(async context => {
148151
const client = context.container.get(BoardsServiceClientImpl);
152+
const service = context.container.get<BoardsService>(BoardsService);
153+
const [attachedBoards, availablePorts] = await Promise.all([
154+
service.getAttachedBoards(),
155+
service.getAvailablePorts()
156+
]);
157+
client.init({ attachedBoards, availablePorts });
149158
WebSocketConnectionProvider.createProxy(context.container, BoardsServicePath, client);
150159
return client;
151160
}).inSingletonScope();
152161

162+
// To be able to track, and update the menu based on the core settings (aka. board details) of the currently selected board.
163+
bind(FrontendApplicationContribution).to(BoardsDetailsMenuUpdater).inSingletonScope();
164+
bind(BoardsConfigStore).toSelf().inSingletonScope();
165+
bind(FrontendApplicationContribution).toService(BoardsConfigStore);
166+
// Logger for the Arduino daemon
167+
bind(ILogger).toDynamicValue(ctx => {
168+
const parentLogger = ctx.container.get<ILogger>(ILogger);
169+
return parentLogger.child('store');
170+
}).inSingletonScope().whenTargetNamed('store');
171+
153172
// Boards auto-installer
154173
bind(BoardsAutoInstaller).toSelf().inSingletonScope();
155174
bind(FrontendApplicationContribution).toService(BoardsAutoInstaller);

arduino-ide-extension/src/browser/boards/boards-auto-installer.ts

+3-3
Original file line numberDiff line numberDiff line change
@@ -35,9 +35,9 @@ export class BoardsAutoInstaller implements FrontendApplicationContribution {
3535
protected ensureCoreExists(config: BoardsConfig.Config): void {
3636
const { selectedBoard } = config;
3737
if (selectedBoard) {
38-
this.boardsService.search({}).then(({ items }) => {
39-
const candidates = items
40-
.filter(item => item.boards.some(board => Board.sameAs(board, selectedBoard)))
38+
this.boardsService.search({}).then(packages => {
39+
const candidates = packages
40+
.filter(pkg => pkg.boards.some(board => Board.sameAs(board, selectedBoard)))
4141
.filter(({ installable, installedVersion }) => installable && !installedVersion);
4242
for (const candidate of candidates) {
4343
// tslint:disable-next-line:max-line-length
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,43 @@
1+
import { inject, injectable } from 'inversify';
2+
import { QuickOpenItem, QuickOpenModel } from '@theia/core/lib/common/quick-open-model';
3+
import { QuickOpenService, QuickOpenOptions } from '@theia/core/lib/browser/quick-open/quick-open-service';
4+
import { BoardsService, BoardsServiceClient } from '../../common/protocol';
5+
6+
@injectable()
7+
export class BoardsConfigQuickOpenService {
8+
9+
@inject(QuickOpenService)
10+
protected readonly quickOpenService: QuickOpenService;
11+
12+
@inject(BoardsService)
13+
protected readonly boardsService: BoardsService;
14+
15+
@inject(BoardsServiceClient)
16+
protected readonly boardsServiceClient: BoardsServiceClient;
17+
18+
async selectBoard(): Promise<void> {
19+
20+
}
21+
22+
protected open(items: QuickOpenItem | QuickOpenItem[], placeholder: string): void {
23+
this.quickOpenService.open(this.getModel(Array.isArray(items) ? items : [items]), this.getOptions(placeholder));
24+
}
25+
26+
protected getOptions(placeholder: string, fuzzyMatchLabel: boolean = true, onClose: (canceled: boolean) => void = () => { }): QuickOpenOptions {
27+
return QuickOpenOptions.resolve({
28+
placeholder,
29+
fuzzyMatchLabel,
30+
fuzzySort: false,
31+
onClose
32+
});
33+
}
34+
35+
protected getModel(items: QuickOpenItem | QuickOpenItem[]): QuickOpenModel {
36+
return {
37+
onType(_: string, acceptor: (items: QuickOpenItem[]) => void): void {
38+
acceptor(Array.isArray(items) ? items : [items]);
39+
}
40+
};
41+
}
42+
43+
}

0 commit comments

Comments
 (0)