Skip to content
This repository has been archived by the owner on Apr 4, 2023. It is now read-only.

Rsync events #771

Merged
merged 20 commits into from
Jul 10, 2020
Merged
Show file tree
Hide file tree
Changes from 16 commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions che-theia-init-sources.yml
Original file line number Diff line number Diff line change
Expand Up @@ -14,6 +14,7 @@ sources:
- extensions/eclipse-che-theia-git-provisioner
- extensions/eclipse-che-theia-logging
- extensions/eclipse-che-theia-messaging
- extensions/eclipse-che-theia-file-sync-tracker
- extensions/eclipse-che-theia-cli-endpoint
plugins:
- plugins/containers-plugin
Expand Down
1 change: 1 addition & 0 deletions extensions/eclipse-che-theia-file-sync-tracker/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
lib/
10 changes: 10 additions & 0 deletions extensions/eclipse-che-theia-file-sync-tracker/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
# theia-file-sync-tracker extension

This extension tracks events of file synchronization progress during workspace startup.

### How does the extension work?

If workspace configured to use asynchronous storage, extension will open websocket connection to special service and show progress in status bar. In case some error, error message will be shown in status bar, the popup with error details will be disappeared after mouse click. After successfully file synchronization, status bar also will be updated with corresponding message, in this case message will disappear in 5 seconds.
vparfonov marked this conversation as resolved.
Show resolved Hide resolved


vparfonov marked this conversation as resolved.
Show resolved Hide resolved

30 changes: 30 additions & 0 deletions extensions/eclipse-che-theia-file-sync-tracker/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
{
"name": "@eclipse-che/theia-file-sync-tracker",
"keywords": [
"theia-extension"
],
"version": "0.0.1",
"files": [
"lib",
"src"
],
"dependencies": {
"@theia/core": "next",
"@eclipse-che/theia-plugin-ext": "^0.0.1"
},
"scripts": {
"prepare": "yarn clean && yarn build",
"clean": "rimraf lib",
"format": "tsfmt -r --useTsfmt ../../configs/tsfmt.json",
"lint": "eslint --cache=true --no-error-on-unmatched-pattern=true \"{src,test}/**/*.{ts,tsx}\"",
"compile": "tsc",
"build": "concurrently -n \"format,lint,compile\" -c \"red,green,blue\" \"yarn format\" \"yarn lint\" \"yarn compile\"",
"watch": "tsc -w"
},
"license": "EPL-2.0",
"theiaExtensions": [
{
"frontend": "lib/browser/che-theia-file-sync-frontend-module"
}
]
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,24 @@
/********************************************************************************
* Copyright (C) 2020 Red Hat, Inc. and others.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0.
*
* This Source Code may also be made available under the following Secondary
* Licenses when the conditions for such availability set forth in the Eclipse
* Public License v. 2.0 are satisfied: GNU General Public License, version 2
* with the GNU Classpath Exception which is available at
* https://www.gnu.org/software/classpath/license.html.
*
* SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
********************************************************************************/

import { ContainerModule } from 'inversify';
import { FrontendApplicationContribution } from '@theia/core/lib/browser';
import { StatusBarFrontendContribution } from './status-bar-contribution';
vparfonov marked this conversation as resolved.
Show resolved Hide resolved

export default new ContainerModule(bind => {

bind(FrontendApplicationContribution).to(StatusBarFrontendContribution).inSingletonScope();
});
Original file line number Diff line number Diff line change
@@ -0,0 +1,115 @@
/********************************************************************************
* Copyright (C) 2020 Red Hat, Inc. and others.
*
* This program and the accompanying materials are made available under the
* terms of the Eclipse Public License v. 2.0 which is available at
* http://www.eclipse.org/legal/epl-2.0.
*
* This Source Code may also be made available under the following Secondary
* Licenses when the conditions for such availability set forth in the Eclipse
* Public License v. 2.0 are satisfied: GNU General Public License, version 2
* with the GNU Classpath Exception which is available at
* https://www.gnu.org/software/classpath/license.html.
*
* SPDX-License-Identifier: EPL-2.0 OR GPL-2.0 WITH Classpath-exception-2.0
********************************************************************************/

import { injectable, inject } from 'inversify';
import { FrontendApplicationContribution } from '@theia/core/lib/browser';
import { MessageService } from '@theia/core/lib/common';
import { StatusBar, StatusBarAlignment, StatusBarEntry } from '@theia/core/lib/browser/status-bar/status-bar';
import { CheApiService } from '@eclipse-che/theia-plugin-ext/lib/common/che-protocol';
import URI from '@theia/core/lib/common/uri';
import ReconnectingWebSocket from 'reconnecting-websocket';
import { DisposableCollection, Disposable } from '@theia/core';

@injectable()
export class StatusBarFrontendContribution implements FrontendApplicationContribution {
vparfonov marked this conversation as resolved.
Show resolved Hide resolved

@inject(StatusBar)
private statusBar: StatusBar;
@inject(MessageService)
protected readonly messageService: MessageService;
@inject(CheApiService)
protected cheApiService: CheApiService;
private readonly ID = 'file-synchronization-indicator-id';
protected readonly statusBarDisposable = new DisposableCollection();

private readonly tooltip = 'File synchronization progress';
private readonly fail = 'File Sync: Failed';
private readonly done = 'File Sync: Done';

async initialize(): Promise<void> {
this.connect(await this.getSyncServiceURL());
}

async getSyncServiceURL(): Promise<string> {
const server = await this.cheApiService.findUniqueServerByAttribute('type', 'rsync');
if (server) {
return new URI(server.url).resolve('track').toString();
} else {
return Promise.reject('Server rsync not found');
vparfonov marked this conversation as resolved.
Show resolved Hide resolved
}
}

private connect(endpointAddress: string): void {
const websocket = new ReconnectingWebSocket(endpointAddress, undefined, {
maxRetries: Infinity,
});
websocket.onerror = err => {
console.log(err);
this.messageService.info('Can\'t establish connetion to rsync server. Cause:' + err);
};
websocket.onmessage = ev => {
this.updateStatusBar(ev.data, websocket);
};
websocket.onclose = () => console.log('File synchronization tracking connection closed');
websocket.onopen = () => console.log('File synchronization tracking connection opened');
};

private updateStatusBar(data: string, websocket: ReconnectingWebSocket): void {
this.statusBarDisposable.dispose();
const obj = JSON.parse(data);
if (obj.state === 'DONE') {
websocket.close();
this.setStatusBarEntry({
text: this.done,
tooltip: this.tooltip,
alignment: StatusBarAlignment.LEFT,
onclick: (e: MouseEvent) => this.messageService.info(this.done),
priority: 150
});
(async () => {
await this.delay(5000); // hide message in 5 sec
this.statusBarDisposable.dispose();
})();
} else if (obj.state === 'ERROR') {
websocket.close();
this.setStatusBarEntry({
text: this.fail,
tooltip: this.tooltip,
alignment: StatusBarAlignment.LEFT,
onclick: (e: MouseEvent) => this.messageService.error(obj.info),
priority: 150
});
} else {
const msg = `File Sync: ${obj.info}`;
this.setStatusBarEntry({
text: msg,
tooltip: this.tooltip,
alignment: StatusBarAlignment.LEFT,
onclick: (e: MouseEvent) => this.messageService.info(msg),
priority: 150
});
}
}

private setStatusBarEntry(entry: StatusBarEntry): void {
this.statusBar.setElement(this.ID, entry);
this.statusBarDisposable.push(Disposable.create(() => this.statusBar.removeElement(this.ID)));
}

private delay(ms: number): Promise<void> {
return new Promise(resolve => setTimeout(resolve, ms));
}
}
14 changes: 14 additions & 0 deletions extensions/eclipse-che-theia-file-sync-tracker/tsconfig.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
{
"extends": "../../configs/base.tsconfig.json",
"compilerOptions": {
"lib": [
"es6",
"dom"
],
"rootDir": "src",
"outDir": "lib"
},
"include": [
"src"
]
}