Skip to content

Commit

Permalink
Merge pull request #26 from the-markup/compile-os-agnostic
Browse files Browse the repository at this point in the history
Make compile scripts OS-independent
  • Loading branch information
BatMiles authored Mar 1, 2024
2 parents 6e6ca16 + cf2be12 commit e2f151a
Show file tree
Hide file tree
Showing 8 changed files with 115 additions and 73 deletions.
29 changes: 17 additions & 12 deletions scripts/compile.js
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
const fs = require('fs-extra');
const path = require('path');
const html = require('./compile/html');
const css = require('./compile/css');
const javascript = require('./compile/javascript');
Expand All @@ -22,10 +23,12 @@ if (!fs.existsSync('.build')) {
}

function compileGraphic(graphicName) {
const graphicFolder = path.join('src', graphicName);

if (graphicName.indexOf(' ') >= 0) {
console.log('A space was found in', graphicName, 'please rename without spaces');
return false;
} else if (!fs.statSync(`src/${graphicName}`).isDirectory()) {
} else if (!fs.statSync(graphicFolder).isDirectory()) {
console.log('Folder for', graphicName, 'was not found');
return false;
}
Expand All @@ -41,11 +44,13 @@ function compileGraphic(graphicName) {
graphic.path = pathFinder.get(dest, graphic);
//append config options to check if screenshot must be taken
graphic.config = new Object;
if (fs.existsSync(`src/${graphicName}/config.json`)) {
graphic.config = JSON.parse(fs.readFileSync(`src/${graphicName}/config.json`, 'utf8'));
const configPath = path.join(graphicFolder, 'config.json');
if (fs.existsSync(configPath)) {
graphic.config = JSON.parse(fs.readFileSync(configPath, 'utf8'));
}

fs.mkdirSync(`.build/${graphic.name}`);
const buildDir = path.join('.build', graphic.name);
fs.mkdirSync(buildDir);

if (graphic.config.svelte) {
const result = svelte.render(graphic);
Expand All @@ -65,17 +70,19 @@ function compileGraphic(graphicName) {
}

assets.init(graphic);
fs.writeFileSync(`.build/${graphic.name}/manifest.json`, JSON.stringify(manifest, null, 2));
const manifestPath = path.join('.build', graphic.name, 'manifest.json');
fs.writeFileSync(manifestPath, JSON.stringify(manifest, null, 2));

return graphic;
}

let graphics = fs.readdirSync('src/', { withFileTypes: true })
const srcDir = path.join('src', path.sep);
let graphics = fs.readdirSync(srcDir, { withFileTypes: true })
.filter(dirent => dirent.isDirectory())
.map(dirent => dirent.name);

if (process.env.GITHUB_REPOSITORY) {
graphics = fs.readdirSync('src/')
graphics = fs.readdirSync(srcDir)
}
else if (dest === 'remote' && graphics.length > 1) {
let answering = true;
Expand All @@ -87,7 +94,7 @@ else if (dest === 'remote' && graphics.length > 1) {
choices: graphics
}]).then(answers => {
if (answers.graphics === 'All Graphics') {
graphics = fs.readdirSync('src/');
graphics = fs.readdirSync(srcDir);
} else {
graphics = [answers.graphics]
}
Expand All @@ -104,18 +111,16 @@ graphics.forEach((graphic, i) => {
});

preview.init();

if (dest === 'remote') {

const deployBuildDir = path.join('.', path.sep, '.build');
const server = http.createServer((request, response) => {
return handler(request, response, {
public: './.build'
public: deployBuildDir
});
});
server.listen(5001);

graphics = graphics.filter(Boolean);

graphics.forEach(async graphic => {
//check if a screenshot should be taken
if (graphic.config.auto_screenshot) {
Expand Down
10 changes: 7 additions & 3 deletions scripts/compile/assets.js
Original file line number Diff line number Diff line change
@@ -1,18 +1,22 @@
const fs = require('fs-extra');
const path = require('path');
const logger = require('../utilities/logger');

module.exports = {
init(graphic) {
logger.log('assets', 'transferring');

if (fs.existsSync(`src/${graphic.name}/assets`)) {
const assetsDir = path.join('src', graphic.name, 'assets');
if (fs.existsSync(assetsDir)) {
logger.log('assets', 'copying assets');
fs.copySync(`src/${graphic.name}/assets`, `.build/${graphic.name}/assets`);
const assetsBuildDir = path.join('.build', graphic.name, 'assets');
fs.copySync(assetsDir, assetsBuildDir);
}

if (graphic.config.fonts && fs.existsSync(graphic.config.fonts)) {
logger.log('assets', 'copying fonts');
fs.copySync(graphic.config.fonts, `.build/${graphic.name}/fonts`);
const fontsBuildDir = path.join('.build', graphic.name, 'fonts');
fs.copySync(graphic.config.fonts, fontsBuildDir);
}

logger.log('assets', 'finished')
Expand Down
28 changes: 14 additions & 14 deletions scripts/compile/css.js
Original file line number Diff line number Diff line change
@@ -1,32 +1,32 @@
const path = require('path');
const fs = require('fs-extra');
const sass = require('sass');
const glob = require('glob');
const logger = require('../utilities/logger');

module.exports = {
renderAll(graphic) {
const paths = glob.sync(`src/${graphic.name}/sass/*.scss`);
const scssPathsMatch = path.join('src', graphic.name, 'sass', '*scss');
const paths = glob.sync(scssPathsMatch);
const manifest = new Array();

paths.forEach(path => {
this.render(path, graphic);
manifest.push(path.replace(`src/${graphic.name}/sass/`, '').replace('.scss', '.css'));
paths.forEach(filepath => {
this.render(filepath, graphic);
const sassDir = path.join('src', graphic.name, 'sass', path.sep);
manifest.push(filepath.replace(sassDir, '').replace('.scss', '.css'));
});

return manifest;
},

render(path, graphic) {
logger.log('css', 'compiling ' + path);
render(filepath, graphic) {
logger.log('css', 'compiling ' + filepath);
try {
const css = sass.renderSync({
file: path
}).css.toString('utf8').replace(/{{ path }}/g, graphic.path);

const fileName = path.replace(/^.*[\\\/]/, '').replace('.scss', '');

fs.writeFileSync(`./.build/${graphic.name}/${fileName}.css`, css);
logger.log('css', 'finished ' + path);
const css = sass.compile(filepath).css.toString('utf8').replace(/{{ filepath }}/g, graphic.path);
const fileName = path.basename(filepath, '.scss');
const outputCSSPath = path.join('.', path.sep, '.build', graphic.name, `${fileName}.css`);
fs.writeFileSync(outputCSSPath, css);
logger.log('css', 'finished ' + filepath);
} catch (err) {
console.log(err);
}
Expand Down
47 changes: 30 additions & 17 deletions scripts/compile/html.js
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
const path = require('path');
const handlebars = require('handlebars');
const fs = require('fs-extra');
const glob = require('glob');
Expand All @@ -6,41 +7,49 @@ const decache = require('decache');

module.exports = {
render(graphic) {
logger.log('html', `compiling src/${graphic.name}/index.html`);
const indexPath = path.join('src', graphic.name, 'index.html');
logger.log('html', `compiling ${indexPath}`);

let data;

if (fs.existsSync('./src/' + graphic.name + '/data/data.js')) {
decache('../../src/' + graphic.name + '/data/data.js');
data = require('../../src/' + graphic.name + '/data/data.js').init();
const dataPath = path.join('.', 'src', graphic.name, 'data', 'data.js');
if (fs.existsSync(dataPath)) {
const cacheDataPath = path.join('..', '..', 'src', graphic.name, 'data', 'data.js');
decache(cacheDataPath);
data = require(cacheDataPath).init();
} else {
data = new Object;
}

this.registerHelpers();
this.registerPartials(graphic.name);

const html = fs.readFileSync('src/' + graphic.name + '/templates/index.html', 'utf8');
const templateIndexPath = path.join('src', graphic.name, 'templates', 'index.html');
const html = fs.readFileSync(templateIndexPath, 'utf8');
const template = handlebars.compile(html);
fs.writeFileSync('.build/' + graphic.name + '/index.html', template({ path: graphic.path, data: data }));
const buildIndexPath = path.join('.build', graphic.name, 'index.html');
fs.writeFileSync(buildIndexPath, template({ path: graphic.path, data: data }));

logger.log('html', `finished src/${graphic.name}/index.html`);
logger.log('html', `finished ${indexPath}`);

return 'index.html';
},

iframe(graphic, manifest) {
logger.log('html', `compiling src/${graphic.name}/iframe.html`);
const iframePath = path.join('src', graphic.name, 'iframe.html');
logger.log('html', `compiling ${iframePath}`);

const html = fs.readFileSync(`.build/${graphic.name}/index.html`, 'utf8');
const indexPath = path.join('.build', graphic.name, 'index.html');
const html = fs.readFileSync(indexPath, 'utf8');
var css = '';
var js = '';

for (let file of manifest.css) {
css += fs.readFileSync(`.build/${graphic.name}/${file}`, 'utf8') + "\n";
let cssPath = path.join('.build', graphic.name, file);
css += fs.readFileSync(cssPath, 'utf8') + "\n";
}
for (let file of manifest.js) {
js += fs.readFileSync(`.build/${graphic.name}/${file}`, 'utf8') + "\n";
let jsPath = path.join('.build', graphic.name, file);
js += fs.readFileSync(jsPath, 'utf8') + "\n";
}

const iframe = `<!DOCTYPE html>
Expand All @@ -65,9 +74,10 @@ module.exports = {
</script>
</body>
</html>`;
fs.writeFileSync('.build/' + graphic.name + '/iframe.html', iframe);
const buildIndexPath = path.join('.build', graphic.name, 'iframe.html');
fs.writeFileSync(buildIndexPath, iframe);

logger.log('html', `finished src/${graphic.name}/iframe.html`);
logger.log('html', `finished ${iframePath}`);

return 'iframe.html';
},
Expand All @@ -79,11 +89,14 @@ module.exports = {
},

registerPartials(graphicName) {
let partials = glob.sync('src/' + graphicName + '/templates/**/*.*');
partials = partials.concat(glob.sync('.exports/*.*'));
const templateMatch = path.join('src', graphicName, 'templates', '**', '*.*');
const exportsMatch = path.join('.exports', '*.*');
let partials = glob.sync(templateMatch);
partials = partials.concat(glob.sync(exportsMatch));

partials.forEach(partial => {
const name = partial.replace('src/' + graphicName + '/templates/', '').replace('.exports', 'exports').split('.')[0];
const templatesDir = path.join('src', graphicName, 'templates', path.sep);
const name = partial.replace(templatesDir, '').replace('.exports', 'exports').split('.')[0];
const template = fs.readFileSync(partial, 'utf8');

handlebars.registerPartial(name, template);
Expand Down
27 changes: 17 additions & 10 deletions scripts/compile/javascript.js
Original file line number Diff line number Diff line change
@@ -1,30 +1,37 @@
const path = require('path');
const logger = require('../utilities/logger');
const glob = require('glob');
const webpack = require('webpack');

module.exports = {
renderAll(graphic) {
const paths = glob.sync(`src/${graphic.name}/javascript/*.js`);
const jsMatches = path.join('src', graphic.name, 'javascript', '*.js');
const paths = glob.sync(jsMatches);
const manifest = new Array();

paths.forEach(path => {
this.render(path, graphic);
manifest.push(path.replace(`src/${graphic.name}/javascript/`, ''));
paths.forEach(filepath => {
this.render(filepath, graphic);
const jsDir = path.join('src', graphic.name, 'javascript', path.sep);
manifest.push(filepath.replace(jsDir, ''));
});

return manifest;
},

render(path, graphic) {
logger.log('js', 'compiling ' + path);
render(filepath, graphic) {
logger.log('js', 'compiling ' + filepath);
let done = false;

const compileDir = path.join('scripts', 'compile');
const buildDir = path.join('.build', path.sep);
const jsDir = path.join('src', graphic.name, 'javascript', path.sep);

const compiler = webpack({
mode: graphic.dest == 'remote' ? 'production' : 'development',
entry: __dirname.replace('scripts/compile', '') + path,
entry: __dirname.replace(compileDir, '') + filepath,
output: {
path: __dirname.replace('scripts/compile', '') + '.build/' + graphic.name,
filename: path.replace(`src/${graphic.name}/javascript/`, '')
path: __dirname.replace(compileDir, '') + buildDir + graphic.name,
filename: filepath.replace(jsDir, '')
},
module: {
rules: [
Expand All @@ -45,6 +52,6 @@ module.exports = {

require('deasync').loopWhile(function(){return !done;});

logger.log('js', 'finished ' + path);
logger.log('js', 'finished ' + filepath);
}
}
8 changes: 5 additions & 3 deletions scripts/compile/screenshot.js
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
const path = require('path');
const puppeteer = require('puppeteer');
const fs = require('fs-extra');
const logger = require('../utilities/logger');
const pathFinder = require('../utilities/pathfinder');

module.exports = {
async take(graphic) {

logger.log('fallback', 'Taking screenshot...');

let browser = await puppeteer.launch();
Expand All @@ -16,7 +16,8 @@ module.exports = {
height: 1080
});

let html = fs.readFileSync('./.build/index.html', 'utf8');
const indexPath = path.join('.', path.sep, '.build', 'index.html');
let html = fs.readFileSync(indexPath, 'utf8');
const regEx = new RegExp(graphic.path, 'g');
html = html.replace(regEx, pathFinder.get('local', graphic));
await page.setContent(html, {
Expand All @@ -26,7 +27,8 @@ module.exports = {
let el = await page.$(`.graphics--${graphic.name} .graphics__content`);
let image = await el.screenshot();

fs.writeFileSync('./.build/' + graphic.name + '/fallback.png', image);
const imagePath = path.join('.', '.build', graphic.name, 'fallback.png');
fs.writeFileSync(imagePath, image);

await page.close();
await browser.close();
Expand Down
12 changes: 7 additions & 5 deletions scripts/compile/svelte.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,18 +10,19 @@ module.exports = {
logger.log('svelte', 'compiling');
let done = false;

const rootDir = __dirname.replace('/scripts/compile', '');
const compileDir = path.join(path.sep, 'scripts', 'compile');
const rootDir = __dirname.replace(compileDir, '');
const buildDir = path.join(rootDir, '.build', graphic.name);

webpack({
mode: graphic.dest == 'remote' ? 'production' : 'development',
entry: path.join(rootDir, 'src', graphic.name, 'svelte/app.js'),
entry: path.join(rootDir, 'src', graphic.name, 'svelte', 'app.js'),
output: {
path: buildDir
},
resolve: {
alias: {
svelte: path.resolve('node_modules', 'svelte/src/runtime')
svelte: path.resolve('node_modules', 'svelte', 'src', 'runtime')
},
extensions: ['.mjs', '.js', '.svelte'],
mainFields: ['svelte', 'browser', 'module', 'main'],
Expand Down Expand Up @@ -96,8 +97,9 @@ module.exports = {

require('deasync').loopWhile(function(){return !done;});

if (!fs.existsSync(`.build/${graphic.name}/main.css`)) {
fs.writeFileSync(`.build/${graphic.name}/main.css`, '/* Silence is golden */');
const mainCssPath = path.join('.build', graphic.name, 'main.css');
if (!fs.existsSync(mainCssPath)) {
fs.writeFileSync(mainCssPath, '/* Silence is golden */');
}

fs.writeFileSync(`${buildDir}/index.html`, `<div id="svelte-${graphic.name}"></div>`);
Expand Down
Loading

0 comments on commit e2f151a

Please sign in to comment.