"use strict";
/*
 * @adonisjs/core
 *
 * (c) Harminder Virk <virk@adonisjs.com>
 *
 * For the full copyright and license information, please view the LICENSE
 * file that was distributed with this source code.
 */
Object.defineProperty(exports, "__esModule", { value: true });
exports.loadAceCommands = exports.createHttpServer = exports.registerTsHook = void 0;
const path_1 = require("path");
const http_1 = require("http");
const ace_1 = require("@adonisjs/ace");
const helpers_1 = require("@poppinss/utils/build/helpers");
/**
 * Registers the ts hook to compile typescript code within the memory
 */
function registerTsHook(appRoot) {
    try {
        require((0, helpers_1.resolveFrom)(appRoot, '@adonisjs/assembler/build/src/requireHook')).default(appRoot);
    }
    catch (error) {
        if (['MODULE_NOT_FOUND', 'ENOENT'].includes(error.code)) {
            throw new Error('AdonisJS requires "@adonisjs/assembler" in order to run typescript source directly');
        }
        throw error;
    }
}
exports.registerTsHook = registerTsHook;
/**
 * Creates the AdonisJS HTTP server. The method is abstracted to be used by
 * test utils and the HTTP server process both.
 */
function createHttpServer(application, server, callback) {
    /**
     * Optimizing the server by pre-compiling routes and middleware
     */
    application.logger.trace('optimizing http server handler');
    server.optimize();
    /**
     * Bind exception handler to handle exceptions occured during HTTP requests.
     */
    if (application.exceptionHandlerNamespace) {
        application.logger.trace('binding %s exception handler', application.exceptionHandlerNamespace);
        server.errorHandler(application.exceptionHandlerNamespace);
    }
    const handler = server.handle.bind(server);
    server.instance = callback ? callback(handler) : (0, http_1.createServer)(handler);
}
exports.createHttpServer = createHttpServer;
/**
 * Helper function to optionally resolve files from a given path
 */
function resolve(fromPath, resolvePath, onMatch) {
    try {
        onMatch((0, helpers_1.resolveFrom)(fromPath, resolvePath));
    }
    catch {
        return null;
    }
}
/**
 * Loads ace commands from the assembler manifest and the app manifest files
 */
function loadAceCommands(application, ace) {
    const manifestFiles = [];
    resolve(application.appRoot, '@adonisjs/assembler/build/ace-manifest.json', (manifestAbsPath) => {
        const basePath = (0, path_1.join)(manifestAbsPath, '../');
        manifestFiles.push({ manifestAbsPath, basePath });
    });
    resolve(application.appRoot, './ace-manifest.json', (manifestAbsPath) => {
        const basePath = (0, path_1.join)(manifestAbsPath, '../');
        manifestFiles.push({ manifestAbsPath, basePath });
    });
    /**
     * Load commands using manifest loader
     */
    ace.useManifest(new ace_1.ManifestLoader(manifestFiles));
    return ace.preloadManifest();
}
exports.loadAceCommands = loadAceCommands;
