microsoft/vscode-react-native

Public

mirrored from https://github.com/microsoft/vscode-react-nativeAvailable

CodeCommitsIssuesPull requestsActionsInsightsSecurity
d63a3130008e77d37d6cdf8b22bdbed4b3250986

Branches

Tags

  • No tags available.
0Branches0Tags
Go to file
Add file
Code

Clone

HTTPS

Download ZIP

src/common/node/fileSystem.ts

236lines · modeblame

3fb37ad5unknown10 years ago1// Copyright (c) Microsoft Corporation. All rights reserved.
2// Licensed under the MIT license. See LICENSE file in the project root for details.
3
aab2095edigeff10 years ago4import * as nodeFs from "fs";
bc7a32ceJimmy Thomson10 years ago5import * as path from "path";
3fb37ad5unknown10 years ago6import * as Q from "q";
7
8export class FileSystem {
aab2095edigeff10 years ago9private fs: typeof nodeFs;
10
11constructor({ fs = nodeFs } = {}) {
12this.fs = fs;
13}
3fb37ad5unknown10 years ago14
15public ensureDirectory(dir: string): Q.Promise<void> {
aab2095edigeff10 years ago16return Q.nfcall(this.fs.stat, dir).then((stat: nodeFs.Stats): void => {
3fb37ad5unknown10 years ago17if (stat.isDirectory()) {
18return;
19}
b3a793eeNisheet Jain10 years ago20throw new Error(`Expected ${dir} to be a directory`);
d24fea86Joshua Skelton10 years ago21}, (err: Error & { code?: string }): Q.Promise<any> => {
3fb37ad5unknown10 years ago22if (err && err.code === "ENOENT") {
aab2095edigeff10 years ago23return Q.nfcall(this.fs.mkdir, dir);
3fb37ad5unknown10 years ago24}
b3a793eeNisheet Jain10 years ago25throw err;
3fb37ad5unknown10 years ago26});
27}
28
29public ensureFileWithContents(file: string, contents: string): Q.Promise<void> {
aab2095edigeff10 years ago30return Q.nfcall(this.fs.stat, file).then((stat: nodeFs.Stats) => {
3fb37ad5unknown10 years ago31if (!stat.isFile()) {
32throw new Error(`Expected ${file} to be a file`);
33}
1e812de2dlebu10 years ago34
35return this.readFile(file).then(existingContents => {
36if (contents !== existingContents) {
37return this.writeFile(file, contents);
38}
39});
d24fea86Joshua Skelton10 years ago40}, (err: Error & { code?: string }): Q.Promise<any> => {
3fb37ad5unknown10 years ago41if (err && err.code === "ENOENT") {
aab2095edigeff10 years ago42return Q.nfcall(this.fs.writeFile, file, contents);
3fb37ad5unknown10 years ago43}
b3a793eeNisheet Jain10 years ago44throw err;
3fb37ad5unknown10 years ago45});
46}
47
d24fea86Joshua Skelton10 years ago48/**
49* Helper function to check if a file or directory exists
50*/
51public existsSync(filename: string) {
3fb37ad5unknown10 years ago52try {
aab2095edigeff10 years ago53this.fs.statSync(filename);
3fb37ad5unknown10 years ago54return true;
55} catch (error) {
56return false;
57}
58}
59
2b1090f9Joshua Skelton10 years ago60/**
61* Helper (asynchronous) function to check if a file or directory exists
62*/
63public exists(filename: string): Q.Promise<boolean> {
aab2095edigeff10 years ago64return Q.nfcall(this.fs.stat, filename)
b031edc7digeff10 years ago65.then(function() {
2b1090f9Joshua Skelton10 years ago66return Q.resolve(true);
67})
68.catch(function(err) {
69return Q.resolve(false);
51769beaJoshua Skelton10 years ago70});
2b1090f9Joshua Skelton10 years ago71}
72
db80cd4eJimmy Thomson10 years ago73/**
74* Helper async function to read the contents of a directory
75*/
76public readDir(directory: string): Q.Promise<string[]> {
aab2095edigeff10 years ago77return Q.nfcall<string[]>(this.fs.readdir, directory);
db80cd4eJimmy Thomson10 years ago78}
79
d24fea86Joshua Skelton10 years ago80/**
81* Helper (synchronous) function to create a directory recursively
82*/
3d2b4b71Joshua Skelton10 years ago83public makeDirectoryRecursiveSync(dirPath: string): void {
d24fea86Joshua Skelton10 years ago84let parentPath = path.dirname(dirPath);
85if (!this.existsSync(parentPath)) {
3d2b4b71Joshua Skelton10 years ago86this.makeDirectoryRecursiveSync(parentPath);
d24fea86Joshua Skelton10 years ago87}
88
aab2095edigeff10 years ago89this.fs.mkdirSync(dirPath);
d24fea86Joshua Skelton10 years ago90}
91
92/**
93* Helper function to asynchronously copy a file
94*/
2b1090f9Joshua Skelton10 years ago95public copyFile(from: string, to: string, encoding?: string): Q.Promise<void> {
d8231ba2Joshua Skelton10 years ago96let deferred: Q.Deferred<void> = Q.defer<void>();
aab2095edigeff10 years ago97let destFile: nodeFs.WriteStream = this.fs.createWriteStream(to, { encoding: encoding });
98let srcFile: nodeFs.ReadStream = this.fs.createReadStream(from, { encoding: encoding });
d24fea86Joshua Skelton10 years ago99destFile.on("finish", function(): void {
2b1090f9Joshua Skelton10 years ago100deferred.resolve(void 0);
d24fea86Joshua Skelton10 years ago101});
102
103destFile.on("error", function(e: Error): void {
104deferred.reject(e);
105});
106
107srcFile.on("error", function(e: Error): void {
108deferred.reject(e);
109});
110
111srcFile.pipe(destFile);
112return deferred.promise;
113}
114
3fb37ad5unknown10 years ago115public deleteFileIfExistsSync(filename: string) {
d24fea86Joshua Skelton10 years ago116if (this.existsSync(filename)) {
aab2095edigeff10 years ago117this.fs.unlinkSync(filename);
3fb37ad5unknown10 years ago118}
119}
120
5d4d4de0digeff10 years ago121public readFile(filename: string, encoding: string = "utf8"): Q.Promise<string> {
aab2095edigeff10 years ago122return Q.nfcall<string>(this.fs.readFile, filename, encoding);
3fb37ad5unknown10 years ago123}
124
4677921cdigeff10 years ago125public writeFile(filename: string, data: any): Q.Promise<void> {
aab2095edigeff10 years ago126return Q.nfcall<void>(this.fs.writeFile, filename, data);
4677921cdigeff10 years ago127}
bc7a32ceJimmy Thomson10 years ago128
bc96b26bJimmy Thomson10 years ago129public unlink(filename: string): Q.Promise<void> {
aab2095edigeff10 years ago130return Q.nfcall<void>(this.fs.unlink, filename);
bc96b26bJimmy Thomson10 years ago131}
132
afc46a73Jimmy Thomson10 years ago133public findFilesByExtension(folder: string, extension: string): Q.Promise<string[]> {
aab2095edigeff10 years ago134return Q.nfcall(this.fs.readdir, folder).then((files: string[]) => {
bc7a32ceJimmy Thomson10 years ago135const extFiles = files.filter((file: string) => path.extname(file) === `.${extension}`);
136if (extFiles.length === 0) {
137throw new Error(`Unable to find any ${extension} files.`);
3fb37ad5unknown10 years ago138}
afc46a73Jimmy Thomson10 years ago139return extFiles;
3fb37ad5unknown10 years ago140});
141}
8ab8eac0dlebu10 years ago142
4e7a6f0edlebu10 years ago143public mkDir(p: string): Q.Promise<void> {
bc6696cbdigeff10 years ago144return Q.nfcall<void>(this.fs.mkdir, p);
145}
146
ed2f4750digeff10 years ago147public stat(path: string): Q.Promise<nodeFs.Stats> {
148return Q.nfcall<nodeFs.Stats>(this.fs.stat, path);
bc6696cbdigeff10 years ago149}
150
151public directoryExists(directoryPath: string): Q.Promise<boolean> {
152return this.stat(directoryPath).then(stats => {
153return stats.isDirectory();
154}).catch(reason => {
155return reason.code === "ENOENT"
156? false
157: Q.reject<boolean>(reason);
158});
159}
160
50241c19digeff10 years ago161
162/**
163* Delete 'dirPath' if it's an empty folder. If not fail.
164*
165* @param {dirPath} path to the folder
166* @returns {void} Nothing
167*/
bc6696cbdigeff10 years ago168public rmdir(dirPath: string): Q.Promise<void> {
169return Q.nfcall<void>(this.fs.rmdir, dirPath);
4e7a6f0edlebu10 years ago170}
171
e7f5d062Joshua Skelton10 years ago172/**
173* Recursively copy 'source' to 'target' asynchronously
174*
175* @param {string} source Location to copy from
176* @param {string} target Location to copy to
177* @returns {Q.Promise} A promise which is fulfilled when the copy completes, and is rejected on error
178*/
179public copyRecursive(source: string, target: string): Q.Promise<void> {
aab2095edigeff10 years ago180return Q.nfcall<nodeFs.Stats>(this.fs.stat, source).then(stats => {
e7f5d062Joshua Skelton10 years ago181if (stats.isDirectory()) {
182return this.exists(target).then(exists => {
183if (!exists) {
aab2095edigeff10 years ago184return Q.nfcall<void>(this.fs.mkdir, target);
e7f5d062Joshua Skelton10 years ago185}
186})
b031edc7digeff10 years ago187.then(() => {
aab2095edigeff10 years ago188return Q.nfcall<string[]>(this.fs.readdir, source);
b031edc7digeff10 years ago189})
190.then(contents => {
191Q.all(contents.map((childPath: string): Q.Promise<void> => {
192return this.copyRecursive(path.join(source, childPath), path.join(target, childPath));
193}));
194});
e7f5d062Joshua Skelton10 years ago195} else {
196return this.copyFile(source, target);
197}
198});
199}
200
4e7a6f0edlebu10 years ago201public removePathRecursivelyAsync(p: string): Q.Promise<void> {
e7f5d062Joshua Skelton10 years ago202return this.exists(p).then(exists => {
4e7a6f0edlebu10 years ago203if (exists) {
aab2095edigeff10 years ago204return Q.nfcall<nodeFs.Stats>(this.fs.stat, p).then((stats: nodeFs.Stats) => {
4e7a6f0edlebu10 years ago205if (stats.isDirectory()) {
aab2095edigeff10 years ago206return Q.nfcall<string[]>(this.fs.readdir, p).then((childPaths: string[]) => {
4e7a6f0edlebu10 years ago207let result = Q<void>(void 0);
208childPaths.forEach(childPath =>
209result = result.then<void>(() => this.removePathRecursivelyAsync(path.join(p, childPath))));
210return result;
211}).then(() =>
aab2095edigeff10 years ago212Q.nfcall<void>(this.fs.rmdir, p));
4e7a6f0edlebu10 years ago213} else {
214/* file */
aab2095edigeff10 years ago215return Q.nfcall<void>(this.fs.unlink, p);
4e7a6f0edlebu10 years ago216}
217});
218}
219});
220}
221
8ab8eac0dlebu10 years ago222public removePathRecursivelySync(p: string): void {
aab2095edigeff10 years ago223if (this.fs.existsSync(p)) {
224let stats = this.fs.statSync(p);
8ab8eac0dlebu10 years ago225if (stats.isDirectory()) {
aab2095edigeff10 years ago226let contents = this.fs.readdirSync(p);
8ab8eac0dlebu10 years ago227contents.forEach(childPath =>
228this.removePathRecursivelySync(path.join(p, childPath)));
aab2095edigeff10 years ago229this.fs.rmdirSync(p);
8ab8eac0dlebu10 years ago230} else {
231/* file */
aab2095edigeff10 years ago232this.fs.unlinkSync(p);
8ab8eac0dlebu10 years ago233}
234}
235}
3fb37ad5unknown10 years ago236}