"use strict";
/*
 * Tencent is pleased to support the open source community by making
 * Hippy available.
 *
 * Copyright (C) 2017-2019 THL A29 Limited, a Tencent company.
 * All rights reserved.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *   http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
Object.defineProperty(exports, "__esModule", { value: true });
exports.stopServer = exports.startDebugServer = void 0;
const tslib_1 = require("tslib");
const fs_1 = tslib_1.__importDefault(require("fs"));
const kill_port_1 = tslib_1.__importDefault(require("kill-port"));
const koa_1 = tslib_1.__importDefault(require("koa"));
const safe_1 = tslib_1.__importDefault(require("colors/safe"));
const client_1 = require("@debug-server-next/client");
const socket_server_1 = require("@debug-server-next/socket-server");
const log_1 = require("@debug-server-next/utils/log");
const db_1 = require("@debug-server-next/db");
const router_1 = require("@debug-server-next/router");
const config_1 = require("@debug-server-next/config");
const enum_1 = require("@debug-server-next/@types/enum");
const url_1 = require("@debug-server-next/utils/url");
const port_1 = require("@debug-server-next/utils/port");
const file_1 = require("@debug-server-next/utils/file");
const report_1 = require("@debug-server-next/utils/report");
const log = new log_1.Logger('debug-server', enum_1.WinstonColor.Yellow);
let server;
let socketServer;
const startDebugServer = async () => {
    log.info('start server argv: %j', global.debugAppArgv);
    await init();
    const { host, port, env } = global.debugAppArgv;
    if (env === "hippy" /* DevtoolsEnv.Hippy */)
        showHippyGuide();
    const app = new koa_1.default();
    (0, router_1.routeApp)(app);
    server = app.listen(port, host, async () => {
        if (!config_1.config.isCluster) {
            const { startTunnel, startChrome } = await Promise.resolve().then(() => tslib_1.__importStar(require('./child-process/index')));
            await startTunnel();
            startChrome();
            const { startAdbProxy } = await Promise.resolve().then(() => tslib_1.__importStar(require('./child-process/adb')));
            startAdbProxy();
        }
        socketServer = new socket_server_1.SocketServer(server);
        socketServer.start();
    });
    server.on('close', () => {
        log.warn('debug server is closed.');
    });
    server.on('error', (e) => {
        log.error('launch debug server failed: %j', e);
    });
    report_1.report.addCommonParams();
    report_1.report.event({
        name: enum_1.ReportEvent.StartDev,
        ext1: env,
    });
};
exports.startDebugServer = startDebugServer;
const stopServer = async (exitProcess = false, ...arg) => {
    const { iWDPPort } = global.debugAppArgv || {};
    if (iWDPPort) {
        try {
            await (0, kill_port_1.default)(iWDPPort, 'tcp');
        }
        catch (e) {
            log.error('kill port %d failed, %s', iWDPPort, e.stack || e);
        }
    }
    try {
        log.info('stopServer %j', arg);
        if (socketServer) {
            await socketServer.close();
            socketServer = null;
        }
        if (server) {
            server.close();
            server = null;
        }
        if (exitProcess)
            process.exit(0);
    }
    catch (e) {
        log.error('stopServer error, %s', e === null || e === void 0 ? void 0 : e.stack);
    }
};
exports.stopServer = stopServer;
/**
 * init DB, directory, Tunnel.node, AppClient
 */
const init = async () => {
    normalizeArgv();
    await (0, port_1.checkPort)();
    const { cachePath, hmrStaticPath } = config_1.config;
    // clean all unused file
    (0, file_1.rmFolder)(cachePath);
    (0, file_1.rmFolder)(hmrStaticPath);
    if (!config_1.config.isCluster) {
        const { importTunnel } = await Promise.resolve().then(() => tslib_1.__importStar(require('@debug-server-next/child-process/import-addon')));
        await importTunnel();
    }
    await fs_1.default.promises.mkdir(cachePath, { recursive: true });
    await fs_1.default.promises.mkdir(hmrStaticPath, { recursive: true });
    (0, db_1.initDbModel)();
    (0, client_1.initAppClient)();
};
const showHippyGuide = () => {
    log.info(safe_1.default.bold[enum_1.WinstonColor.Green](`hippy debug steps:
1. start debug server by run 'npm run hippy:debug'
2. start dev server by run 'npm run hippy:dev'
3. open hippy pages with debugMode on mobile/emulator
4. find connected debug targets on devtools home page: ${safe_1.default.underline[enum_1.WinstonColor.Blue]((0, url_1.getHomeUrl)())}

find full guide on ${safe_1.default.underline[enum_1.WinstonColor.Blue]('https://hippyjs.org/#/guide/debug')}`));
};
/**
 * set default tunnel in different framework
 */
const normalizeArgv = () => {
    const { env, tunnel } = global.debugAppArgv;
    if (tunnel)
        return;
    if (["hippy" /* DevtoolsEnv.Hippy */, "HippyTDF" /* DevtoolsEnv.HippyTDF */].includes(env)) {
        global.debugAppArgv.tunnel = enum_1.DebugTunnel.WS;
    }
    else if (env === "TDFCore" /* DevtoolsEnv.TDFCore */) {
        global.debugAppArgv.tunnel = enum_1.DebugTunnel.TCP;
    }
};
