HEX
Server: Apache
System: Linux webd004.cluster130.gra.hosting.ovh.net 5.15.206-ovh-vps-grsec-zfs-classid #1 SMP Fri May 15 02:41:25 UTC 2026 x86_64
User: frenchy (106757)
PHP: 7.4.33
Disabled: _dyuweyrj4,_dyuweyrj4r,dl
Upload Files
File: /home/f/r/e/frenchy/www/french-american.org/current/node_modules/@frctl/fractal/src/web/theme.js
'use strict';

const _ = require('lodash');
const Path = require('path');
const Promise = require('bluebird');
const fs = Promise.promisifyAll(require('fs-extra'));
const pr = require('path-to-regexp');
const mix = require('../core/mixins/mix');
const WebError = require('./error');
const Configurable = require('../core/mixins/configurable');
const Emitter = require('../core/mixins/emitter');

module.exports = class Theme extends mix(Configurable, Emitter) {

    constructor(viewPaths, options) {
        super();

        this.options = this.config.bind(this);
        this.setOption = this.set.bind(this);
        this.getOption = this.get.bind(this);

        this.options(options || {});

        this._staticPaths = new Set();
        this._routes = new Map();
        this._resolvers = {};
        this._builder = null;
        this._views = [];

        this._filters = [];
        this._extensions = [];
        this._globals = {};

        this._errorView = {};
        this._redirectView = {};

        this.addLoadPath(viewPaths);
        this.setErrorView('__system/error.nunj');
        this.setRedirectView('__system/redirect.nunj');
    }

    addLoadPath(path) {
        path = [].concat(path);
        this._views = _.uniq(path.concat(this._views));
        return this;
    }

    loadPaths() {
        return this._views;
    }

    setErrorView(view) {
        this._errorView = view;
        return this;
    }

    errorView() {
        return this._errorView;
    }

    setRedirectView(view) {
        this._redirectView = view;
        return this;
    }

    redirectView() {
        return this._redirectView;
    }

    addStatic(path, mount) {
        for (const s of this._staticPaths) {
            if (path === s.path) {
                return;
            }
        }
        this._staticPaths.add({
            path: path,
            mount: mount,
        });
        return this;
    }

    static() {
        return Array.from(this._staticPaths.values());
    }

    addRoute(path, opts, resolvers) {
        const keys = [];
        opts.path = path;
        opts.handle = opts.handle || path;
        opts.matcher = pr(path, keys);
        this.addResolver(opts.handle, resolvers || null);
        this._routes.set(opts.handle, _.clone(opts));
        return this;
    }

    addResolver(handle, resolver) {
        _.set(this._resolvers, handle, [].concat(resolver));
        return this;
    }

    routes() {
        return Array.from(this._routes.values());
    }

    resolvers() {
        return this._resolvers;
    }

    matchRoute(urlPath) {
        for (const route of this._routes.values()) {
            const match = route.matcher.exec(urlPath);
            if (match) {
                match.shift();
                const params = {};
                for (let i = 0; i < route.matcher.keys.length; i++) {
                    params[route.matcher.keys[i].name] = match[i];
                }
                return {
                    route: route,
                    params: params,
                };
            }
        }
        if (urlPath === '/') {
            return {
                route: {
                    handle: '__system-index',
                    view: '__system/index.nunj',
                },
                params: {},
            };
        }
        return false;
    }

    urlFromRoute(handle, params, noRedirect) {
        const route = this._routes.get(handle);
        if (route) {
            if (!noRedirect && route.redirect) {
                return route.redirect;
            }
            const compiler = pr.compile(route.path);
            return cleanUrlPath(compiler(params));
        }
        return null;
    }

};

function cleanUrlPath(urlPath) {
    return urlPath.replace(/\%2F/g, '/');
}