downloadIpc.ts 2.5 KB
Newer Older
S
Sandeep Somavarapu 已提交
1 2 3 4 5 6
/*---------------------------------------------------------------------------------------------
 *  Copyright (c) Microsoft Corporation. All rights reserved.
 *  Licensed under the MIT License. See License.txt in the project root for license information.
 *--------------------------------------------------------------------------------------------*/

import { URI } from 'vs/base/common/uri';
7
import * as path from 'vs/base/common/paths.node';
S
Sandeep Somavarapu 已提交
8
import * as fs from 'fs';
J
Joao Moreno 已提交
9
import { IChannel, IServerChannel } from 'vs/base/parts/ipc/node/ipc';
J
Joao Moreno 已提交
10
import { Event, Emitter } from 'vs/base/common/event';
S
Sandeep Somavarapu 已提交
11 12 13 14 15 16 17 18 19 20 21
import { IDownloadService } from 'vs/platform/download/common/download';
import { mkdirp } from 'vs/base/node/pfs';
import { IURITransformer } from 'vs/base/common/uriIpc';

export type UploadResponse = Buffer | string | undefined;

export function upload(uri: URI): Event<UploadResponse> {
	const stream = new Emitter<UploadResponse>();
	const readstream = fs.createReadStream(uri.fsPath);
	readstream.on('data', data => stream.fire(data));
	readstream.on('error', error => stream.fire(error.toString()));
22
	readstream.on('close', () => stream.fire(undefined));
S
Sandeep Somavarapu 已提交
23 24 25
	return stream.event;
}

J
Joao Moreno 已提交
26
export class DownloadServiceChannel implements IServerChannel {
S
Sandeep Somavarapu 已提交
27 28 29

	constructor() { }

J
Joao Moreno 已提交
30
	listen(_, event: string, arg?: any): Event<any> {
S
Sandeep Somavarapu 已提交
31
		switch (event) {
J
Joao Moreno 已提交
32
			case 'upload': return Event.buffer(upload(URI.revive(arg)));
S
Sandeep Somavarapu 已提交
33
		}
J
Joao Moreno 已提交
34 35

		throw new Error(`Event not found: ${event}`);
S
Sandeep Somavarapu 已提交
36 37
	}

J
Johannes Rieken 已提交
38
	call(_, command: string): Promise<any> {
J
Joao Moreno 已提交
39
		throw new Error(`Call not found: ${command}`);
S
Sandeep Somavarapu 已提交
40 41 42 43 44 45 46
	}
}

export class DownloadServiceChannelClient implements IDownloadService {

	_serviceBrand: any;

47
	constructor(private channel: IChannel, private getUriTransformer: () => IURITransformer) { }
S
Sandeep Somavarapu 已提交
48 49

	download(from: URI, to: string): Promise<void> {
A
Alex Dima 已提交
50
		from = this.getUriTransformer().transformOutgoingURI(from);
S
Sandeep Somavarapu 已提交
51 52 53 54 55 56
		const dirName = path.dirname(to);
		let out: fs.WriteStream;
		return new Promise((c, e) => {
			return mkdirp(dirName)
				.then(() => {
					out = fs.createWriteStream(to);
M
Matt Bierner 已提交
57
					out.once('close', () => c());
S
Sandeep Somavarapu 已提交
58
					out.once('error', e);
59 60
					const uploadStream = this.channel.listen<UploadResponse>('upload', from);
					const disposable = uploadStream(result => {
R
Rob Lourens 已提交
61
						if (result === undefined) {
S
Sandeep Somavarapu 已提交
62 63 64 65 66 67 68 69 70 71 72 73 74
							disposable.dispose();
							out.end(c);
						} else if (Buffer.isBuffer(result)) {
							out.write(result);
						} else if (typeof result === 'string') {
							disposable.dispose();
							out.end(() => e(result));
						}
					});
				});
		});
	}
}