@liara/cli
Version:
The command line interface for Liara
137 lines (135 loc) • 4.23 kB
JavaScript
import { relative, join, dirname } from 'node:path';
import fs from 'fs-extra';
import { create } from 'tar';
import ignore from 'ignore';
import CreateArchiveException from '../errors/create-archive.js';
const defaultIgnores = [
'.git',
'.idea',
'.vscode',
'.next',
'.dockerignore',
'*.*~',
'liara.json',
'node_modules',
'bower_components',
'.DS_Store',
];
const pythonPlatformsIgnores = [
'venv',
'/venv',
'.venv',
'.env',
'ENV',
'.python-version',
'.cache',
'__pycache__',
'lib',
'lib64',
'*.py[cod]',
'*$py.class',
'pip-log.txt',
'pip-delete-this-directory.txt',
'celerybeat-schedule',
];
const phpPlatformsIgnores = ['/vendor'];
const platformIgnores = {
django: [
...pythonPlatformsIgnores,
'*.log',
'local_settings.py',
'staticfiles',
],
flask: [...pythonPlatformsIgnores, 'instance', '.webassets-cache'],
laravel: [...phpPlatformsIgnores],
php: [...phpPlatformsIgnores],
dotnet: [
// Source: https://gist.github.com/vmandic/ac2ecc9c24f6899ee0ec46e4ce444a0e
'Debug',
'debug',
'Release',
'release',
'Releases',
'releases',
'x64',
'x86',
'build',
'bld',
'Bin',
'bin',
'Obj',
'obj',
],
};
function trimLines(lines) {
return lines.reduce((prev, line) => {
if (!line.trim() || line.startsWith('#')) {
return prev;
}
return [...prev, line];
}, []);
}
const loadIgnoreFile = (ignoreInstance, ignoreFilePath, projectPath) => {
const patterns = trimLines(fs.readFileSync(ignoreFilePath).toString().split('\n'));
const relativeToProjectPath = patterns.map((pattern) => {
const dir = dirname(ignoreFilePath);
if (pattern.startsWith('!')) {
const absolutePrefix = pattern.slice(1).startsWith('/') ? '/' : '';
return ('!' +
absolutePrefix +
relative(projectPath, join(dir, pattern.slice(1))));
}
const absolutePrefix = pattern.startsWith('/') ? '/' : '';
return absolutePrefix + relative(projectPath, join(dir, pattern));
});
const linuxify = relativeToProjectPath.map((p) => p.replace(/\\/g, '/'));
ignoreInstance.add(linuxify);
};
function addIgnorePatterns(ignoreInstance, projectPath, dir) {
const liaraignorePath = join(projectPath, dir, '.liaraignore');
const dockerignorePath = join(projectPath, dir, '.dockerignore');
const gitignorePath = join(projectPath, dir, '.gitignore');
if (fs.existsSync(liaraignorePath)) {
loadIgnoreFile(ignoreInstance, liaraignorePath, projectPath);
}
else if (fs.existsSync(dockerignorePath)) {
loadIgnoreFile(ignoreInstance, dockerignorePath, projectPath);
}
else if (fs.existsSync(gitignorePath)) {
loadIgnoreFile(ignoreInstance, gitignorePath, projectPath);
}
}
export default async function createArchive(archivePath, projectPath, platform, debug = () => { }) {
const ignoreInstance = ignore.default({ ignorecase: false });
ignoreInstance.add(defaultIgnores);
// @ts-ignore
ignoreInstance.add(platformIgnores[platform] || []);
const ignoreCache = {};
const ignoreFN = (f) => {
const dir = dirname(f);
if (!ignoreCache[dir]) {
addIgnorePatterns(ignoreInstance, projectPath, dir);
}
else {
ignoreCache[dir] = true;
}
if (!ignoreInstance.ignores(f)) {
return true;
}
debug(`ignoring ${f}`);
return false;
};
const fileList = fs.readdirSync(projectPath).filter(ignoreFN);
if (fileList.length === 0) {
throw new CreateArchiveException(`Seems like you have ignored everything so we can't upload any of your files. Please double-check the content of your .gitignore, .dockerignore and .liaraignore files.
> Read more: https://docs.liara.ir/app-features/ignore`);
}
return await create({
gzip: {
level: 9,
},
cwd: projectPath,
filter: ignoreFN,
file: archivePath,
}, fileList);
}