mirror of
https://github.com/arduino/arduino-ide.git
synced 2025-11-23 00:56:10 +00:00
feat: Create remote sketch
Closes #1580 Signed-off-by: Akos Kitta <a.kitta@arduino.cc>
This commit is contained in:
@@ -1,20 +1,26 @@
|
||||
import { inject, injectable, postConstruct } from '@theia/core/shared/inversify';
|
||||
import { TreeNode } from '@theia/core/lib/browser/tree';
|
||||
import {
|
||||
inject,
|
||||
injectable,
|
||||
postConstruct,
|
||||
} from '@theia/core/shared/inversify';
|
||||
import { CompositeTreeNode, TreeNode } from '@theia/core/lib/browser/tree';
|
||||
import { posixSegments, splitSketchPath } from '../../create/create-paths';
|
||||
import { CreateApi } from '../../create/create-api';
|
||||
import { CloudSketchbookTree } from './cloud-sketchbook-tree';
|
||||
import { AuthenticationClientService } from '../../auth/authentication-client-service';
|
||||
import { SketchbookTreeModel } from '../sketchbook/sketchbook-tree-model';
|
||||
import { ArduinoPreferences } from '../../arduino-preferences';
|
||||
import { WorkspaceNode } from '@theia/navigator/lib/browser/navigator-tree';
|
||||
import { CreateUri } from '../../create/create-uri';
|
||||
import { FileStat } from '@theia/filesystem/lib/common/files';
|
||||
import { LocalCacheFsProvider } from '../../local-cache/local-cache-fs-provider';
|
||||
import { FileService } from '@theia/filesystem/lib/browser/file-service';
|
||||
import { FileChangesEvent, FileStat } from '@theia/filesystem/lib/common/files';
|
||||
import {
|
||||
LocalCacheFsProvider,
|
||||
LocalCacheUri,
|
||||
} from '../../local-cache/local-cache-fs-provider';
|
||||
import URI from '@theia/core/lib/common/uri';
|
||||
import { SketchCache } from './cloud-sketch-cache';
|
||||
import { Create } from '../../create/typings';
|
||||
import { nls } from '@theia/core/lib/common';
|
||||
import { nls } from '@theia/core/lib/common/nls';
|
||||
import { Deferred } from '@theia/core/lib/common/promise-util';
|
||||
|
||||
export function sketchBaseDir(sketch: Create.Sketch): FileStat {
|
||||
// extract the sketch path
|
||||
@@ -52,26 +58,16 @@ export function sketchesToFileStats(sketches: Create.Sketch[]): FileStat[] {
|
||||
|
||||
@injectable()
|
||||
export class CloudSketchbookTreeModel extends SketchbookTreeModel {
|
||||
@inject(FileService)
|
||||
protected override readonly fileService: FileService;
|
||||
|
||||
@inject(AuthenticationClientService)
|
||||
protected readonly authenticationService: AuthenticationClientService;
|
||||
|
||||
@inject(CreateApi)
|
||||
protected readonly createApi: CreateApi;
|
||||
|
||||
@inject(CloudSketchbookTree)
|
||||
protected readonly cloudSketchbookTree: CloudSketchbookTree;
|
||||
|
||||
@inject(ArduinoPreferences)
|
||||
protected override readonly arduinoPreferences: ArduinoPreferences;
|
||||
|
||||
private readonly createApi: CreateApi;
|
||||
@inject(AuthenticationClientService)
|
||||
private readonly authenticationService: AuthenticationClientService;
|
||||
@inject(LocalCacheFsProvider)
|
||||
protected readonly localCacheFsProvider: LocalCacheFsProvider;
|
||||
|
||||
private readonly localCacheFsProvider: LocalCacheFsProvider;
|
||||
@inject(SketchCache)
|
||||
protected readonly sketchCache: SketchCache;
|
||||
private readonly sketchCache: SketchCache;
|
||||
|
||||
private _localCacheFsProviderReady: Deferred<void> | undefined;
|
||||
|
||||
@postConstruct()
|
||||
protected override init(): void {
|
||||
@@ -81,6 +77,50 @@ export class CloudSketchbookTreeModel extends SketchbookTreeModel {
|
||||
);
|
||||
}
|
||||
|
||||
override *getNodesByUri(uri: URI): IterableIterator<TreeNode> {
|
||||
if (uri.scheme === LocalCacheUri.scheme) {
|
||||
const workspace = this.root;
|
||||
const { session } = this.authenticationService;
|
||||
if (session && WorkspaceNode.is(workspace)) {
|
||||
const currentUri = this.localCacheFsProvider.to(uri);
|
||||
if (currentUri) {
|
||||
const rootPath = this.localCacheFsProvider
|
||||
.toUri(session)
|
||||
.path.toString();
|
||||
const currentPath = currentUri.path.toString();
|
||||
if (rootPath === currentPath) {
|
||||
return workspace;
|
||||
}
|
||||
if (currentPath.startsWith(rootPath)) {
|
||||
const id = currentPath.substring(rootPath.length);
|
||||
const node = this.getNode(id);
|
||||
if (node) {
|
||||
yield node;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
protected override isRootAffected(changes: FileChangesEvent): boolean {
|
||||
return changes.changes
|
||||
.map(({ resource }) => resource)
|
||||
.some(
|
||||
(uri) => uri.parent.toString().startsWith(LocalCacheUri.root.toString()) // all files under the root might affect the tree
|
||||
);
|
||||
}
|
||||
|
||||
override async refresh(
|
||||
parent?: Readonly<CompositeTreeNode>
|
||||
): Promise<CompositeTreeNode | undefined> {
|
||||
if (parent) {
|
||||
return super.refresh(parent);
|
||||
}
|
||||
await this.updateRoot();
|
||||
return super.refresh();
|
||||
}
|
||||
|
||||
override async createRoot(): Promise<TreeNode | undefined> {
|
||||
const { session } = this.authenticationService;
|
||||
if (!session) {
|
||||
@@ -89,7 +129,10 @@ export class CloudSketchbookTreeModel extends SketchbookTreeModel {
|
||||
}
|
||||
this.createApi.init(this.authenticationService, this.arduinoPreferences);
|
||||
this.sketchCache.init();
|
||||
const sketches = await this.createApi.sketches();
|
||||
const [sketches] = await Promise.all([
|
||||
this.createApi.sketches(),
|
||||
this.ensureLocalFsProviderReady(),
|
||||
]);
|
||||
const rootFileStats = sketchesToFileStats(sketches);
|
||||
if (this.workspaceService.opened) {
|
||||
const workspaceNode = WorkspaceNode.createRoot(
|
||||
@@ -108,7 +151,9 @@ export class CloudSketchbookTreeModel extends SketchbookTreeModel {
|
||||
return this.tree as CloudSketchbookTree;
|
||||
}
|
||||
|
||||
protected override recursivelyFindSketchRoot(node: TreeNode): any {
|
||||
protected override recursivelyFindSketchRoot(
|
||||
node: TreeNode
|
||||
): TreeNode | false {
|
||||
if (node && CloudSketchbookTree.CloudSketchDirNode.is(node)) {
|
||||
return node;
|
||||
}
|
||||
@@ -122,13 +167,25 @@ export class CloudSketchbookTreeModel extends SketchbookTreeModel {
|
||||
}
|
||||
|
||||
override async revealFile(uri: URI): Promise<TreeNode | undefined> {
|
||||
await this.localCacheFsProvider.ready.promise;
|
||||
// we use remote uris as keys for the tree
|
||||
// convert local URIs
|
||||
const remoteuri = this.localCacheFsProvider.from(uri);
|
||||
if (remoteuri) {
|
||||
return super.revealFile(remoteuri);
|
||||
const remoteUri = this.localCacheFsProvider.from(uri);
|
||||
if (remoteUri) {
|
||||
return super.revealFile(remoteUri);
|
||||
} else {
|
||||
return super.revealFile(uri);
|
||||
}
|
||||
}
|
||||
|
||||
private async ensureLocalFsProviderReady(): Promise<void> {
|
||||
if (this._localCacheFsProviderReady) {
|
||||
return this._localCacheFsProviderReady.promise;
|
||||
}
|
||||
this._localCacheFsProviderReady = new Deferred();
|
||||
this.fileService
|
||||
.access(LocalCacheUri.root)
|
||||
.then(() => this._localCacheFsProviderReady?.resolve());
|
||||
return this._localCacheFsProviderReady.promise;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user