@google/dscc-gen
Version:
Create component & connector projects with sane defaults.
125 lines (113 loc) • 4.05 kB
text/typescript
/**
* @license
* Copyright 2018 Google LLC
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
* https://www.apache.org/licenses/LICENSE-2.0
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
import * as path from 'path';
import {Template} from './main';
import * as util from './util';
const ENCODING = 'utf8';
const CURR_DIR = process.cwd();
export const fixTemplates = async (
baseDirectory: string,
templates: Template[]
) => {
const filesToUpdate = await util.readDir(baseDirectory);
return Promise.all(
filesToUpdate.map(async (file) => {
const originalFilePath = path.join(baseDirectory, file);
const stats = await util.statSync(originalFilePath);
if (stats.isFile()) {
const contents = await util.readFile(originalFilePath, ENCODING);
const newContents = templates.reduce(
(acc, {match, replace}) => acc.replace(match, replace),
contents
);
await util.writeFile(originalFilePath, newContents, ENCODING);
} else if (stats.isDirectory()) {
const newBaseDirectory = path.join(baseDirectory, file);
await fixTemplates(newBaseDirectory, templates);
} else {
throw new Error(`${originalFilePath} is not a file or directory.`);
}
})
);
};
export const createDirectoryContents = async (
templatePath: string,
newProjectPath: string
) => {
const filesToCreate: string[] = await util.readDir(templatePath);
return Promise.all(
filesToCreate.map(async (file) => {
const originalFilePath = path.join(templatePath, file);
const stats = await util.statSync(originalFilePath);
if (stats.isFile()) {
const contents = await util.readFile(originalFilePath, ENCODING);
// npm renames .gitignore to .npmignore so rename it back to .gitignore.
if (file === '.npmignore') {
file = '.gitignore';
}
const writePath = path.join(CURR_DIR, newProjectPath, file);
await util.writeFile(writePath, contents, ENCODING);
} else if (stats.isDirectory()) {
await util.makeDir(path.join(CURR_DIR, newProjectPath, file));
const newTemplatePath = path.join(templatePath, file);
const newNewProjectPath = path.join(newProjectPath, file);
await createDirectoryContents(newTemplatePath, newNewProjectPath);
} else {
throw new Error(`${originalFilePath} is not a file or directory.`);
}
})
);
};
export const parseJsonFile = async (filePath: string) => {
try {
const fileContents = await util.readFile(filePath, ENCODING);
return JSON.parse(fileContents);
} catch (e) {
throw new Error(`Could not read: ${filePath}`);
}
};
export interface PackageJson {
version: string;
}
export const getPackageJson = async (packageDir: string) => {
const json = await parseJsonFile(path.join(packageDir, 'package.json'));
const parsed: PackageJson = json;
return parsed;
};
const createAndCopyFilesImpl = async (
projectPath: string,
templatePath: string,
projectName: string
) => {
try {
await util.makeDir(projectPath);
} catch (e) {
throw new Error(`Couldn't create directory: ${projectPath}`);
}
try {
await createDirectoryContents(templatePath, projectName);
} catch (e) {
throw new Error(`Couldn't copy over the template files to: ${projectPath}`);
}
};
export const createAndCopyFiles = async (
projectPath: string,
templatePath: string,
projectName: string
) =>
await util.spinnify(
'Creating directories and copying template files...',
() => createAndCopyFilesImpl(projectPath, templatePath, projectName)
);