UNPKG

bloggify-cli

Version:
214 lines (190 loc) 7.03 kB
"use strict" const ul = require("ul") , path = require("path") , deffy = require("deffy") , abs = require("abs") , iterateObject = require("iterate-object") , { mkdirp } = require("mkdirp") const DOT_BLOGGIFY = ".bloggify" module.exports = class BloggifyPaths { /** * BloggifyPaths * Creates a new instance of `BloggifyPaths`. * * The instance contains the following fields: * * - `publicUrls`: The url endpoints (accesible via HTTP) * - `core`: The core public url. * - `main`: The application public url. * - `root`: The root public url. * * - `public`: The file system paths. * - `core`: The path to the core public directory. * - `main`: The application public directory. * - `root`: The root public directory. * * - `_bundles`: The relative bundle urls. * - `js`: it takes the following value: `/js/index.js` * - `css`: it takes the following value: `/css/index.css` * * - `bundleUrls`: The bundle urls. * - `js`: The absolute url of the js bundle. * - `css`: The absolute url of the css bundle. * * - `bundlePaths`: The bundle paths. * - `js`: The absolute path of the js bundle. * - `css`: The absolute path of the css bundle. * * - `_publicPaths`: An array of pairs of url endpoints and disk paths. * * @param {String} root The path to the application's root. * @param {Object} options The Bloggify options. The `paths` object will be merged with the following defaults: * * - `bloggify` (String): The bloggify directory (by default the root). * - `config` (String): The configuration file path (default: `/bloggify.js`). * - `plugins` (String): The path to the plugins directory (default: `/node_modules`)> * - `public_main` (String): The public main directory endpoint (default: `"/!/bloggify/public/"`). * - `public_assets` (String): The public core directory endpoint (default: `"/!/bloggify/core/"`). * * @param {Bloggify} bloggifyInstance The Bloggify instance. * @return {Object} The BloggifyPaths instance. */ constructor (root, options, bloggifyInstance) { this.root = abs(root) this.dot_bloggify = abs(`${root}/${DOT_BLOGGIFY}`) this._ = bloggifyInstance options = ul.deepMerge(options, { paths: {} }) this.isProduction = process.env.NODE_ENV === "production" this.envLabel = this.isProduction ? "production" : "development" this._paths = options.paths this.prepare() } /** * initPublicPaths * Initializes the path values (documented above). */ initPublicPaths () { this.publicUrls = { core: this._paths.public_assets , main: this._paths.public_main , root:"/" } this.public = { core: `${this.root}/${DOT_BLOGGIFY}/public` , main: `${this.root}/${this._.options.server.public}` , root: `${this.root}/${this._.options.paths.root_public}` } const customStaticPaths = Array.isArray(this._.options.static_dirs) ? this._.options.static_dirs : [] this._publicPaths = [ ...customStaticPaths , [this.publicUrls.main, this.public.main] , [this.publicUrls.core, this.public.core] , [this.publicUrls.root, this.public.root] ] this.bundleCacheDir = `${this.root}/${DOT_BLOGGIFY}/${this.envLabel}-bundle-cache` this.cssUrlMap = `${this.root}/${DOT_BLOGGIFY}/${this.envLabel}-css-urls.json` mkdirp.sync(this.bundleCacheDir) } /** * getBundlePaths * Get the bundle paths for a bundle name. * * @name getBundlePaths * @function * @param {String} name The bundle name (default: `main`). * @returns {Object} An object containing the following fields: * * - `urls`: The URL endpoints. * - `js` (String): The JavaScript bundle url. * - `css` (String): The CSS bundle url. * * - `local`: The local paths. * - `js` (String): The JavaScript bundle local path. * - `css` (String): The CSS bundle local path. */ getBundlePaths (name) { name = name || "main" const bundles = { js: `/${this.envLabel}-bundles/${name}/scripts-${name}.js` , css: `/${this.envLabel}-bundles/${name}/stylesheets-${name}.css` } return { urls: { js: `${this.publicUrls.core}${bundles.js}` , css: `${this.publicUrls.core}${bundles.css}` } , local: { js: `${this.public.core}${bundles.js}` , css: `${this.public.core}${bundles.css}` } , cacheFile: `${this.bundleCacheDir}/${name}.json` } } /** * getPublicPaths * Fetches the public paths of the app. * * @return {Array} The public paths. */ getPublicPaths () { return this._publicPaths } /** * getMainPublic * Returns the path to the app's public directory/uri. * * @param {Boolean} fromDisk Establishes the source of the public directory. * @return {String} The public path. */ getMainPublic (fromDisk) { return fromDisk ? this.public.main : this.publicUrls.main } /** * staticFilePath * Gets the url of a file. * * @param {String} filePath The file path. * @param {Boolean} absolute If `true`, the absolute path will be returned. * @return {String} The file url. */ staticFilePath (filePath, absolute) { if (!filePath || typeof filePath !== "string") { return ""; } // We assume it's a remote url if (filePath.includes(":")) { return filePath } if (absolute) { return this._.options.domain + this.staticFilePath(filePath) } // Main Public if (filePath.charAt(0) === "/") { return path.normalize(`${this.publicUrls.main}/${filePath}`) } throw new Error("Invalid path: " + filePath) } /** * prepare * Initializes the paths values. */ prepare () { this.bloggify = path.join(this.root, this._paths.bloggify) iterateObject(this._paths, (value, pathName) => { if (pathName === "bloggify" || pathName === "root" || typeof this[pathName] === "function") { return; } this[pathName] = value.startsWith("/") ? path.join(this.root, value) : path.join(this.bloggify, value) }) } /** * pluginPath * Fetches the path of the plugin. * * @param {String} name The plugin's name. * @return {type} The plugin's path. */ pluginPath (name) { return path.join(this.plugins, name) } }