приложение не может найти файл. js - PullRequest
0 голосов
/ 11 февраля 2020

У меня есть приложение Play. UI приложения находится в Angular. Я создал папку ui, которая является каталогом Angular верхнего уровня.

build.sbt
`ui-dev-build` := {
    implicit val UIroot = baseDirectory.value / "ui"
      if (runDevBuild != Success) throw new Exception("Oops! UI Build crashed.")
}

def runDevBuild(implicit dir: File): Int = ifUiInstalled(runScript("npm run build"))

package.json
"build": "ng build --output-path ../public/ui",

При сборке приложения Angular вывод переносится в папку public платформы Play. Оттуда Play передает контакты папки public в папку target для развертывания. В index.html (домашняя страница html файл) я получаю доступ к angular, включая сценарии, созданные в Angular build.

<script src="@routes.Assets.versioned("ui/runtime.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("ui/vendor.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("ui/styles.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("ui/main.js")" type="text/javascript"></script>
<script src="@routes.Assets.versioned("ui/scripts.js")" type="text/javascript"></script>

Это отлично работает.

Я хочу использовать ng-ace2-editor в моем приложении - https://github.com/fxmontigny/ng2-ace-editor. Я добавил его в package.json - "ng2-ace-editor": "0.3.9" и вижу, что каталог ng2-ace-editor присутствует в node_modules.

Когда я запускаю приложение, я получаю ошибку

GET http://localhost:9000/mode-html.js net::ERR_ABORTED 404 (Not Found)
exports.loadScript  @   index.js:3802
exports.loadModule  @   index.js:4174
setMode @   index.js:10152
push../node_modules/ng2-ace-editor/src/component.js.AceEditorComponent.setMode

Я не могу понять, как заставить мое приложение найти mode-html.js. Файл присутствует в местоположении "./node_modules/ace-builds/src-min/mode-html.js. Я добавил этот путь в "script":[] из package.json, но все равно получаю ошибку.

"scripts":[
              "./node_modules/ace-builds/src-min/ace.js",
              "./node_modules/ace-builds/src-min/theme-eclipse.js",
              "./node_modules/ace-builds/src-min/mode-html.js"
]

Интересно, что все работает, если я включаю ace.js в файл домашней страницы

<script src="@routes.Assets.versioned("ui/runtime.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("ui/vendor.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("ui/styles.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("ui/main.js")" type="text/javascript"></script>
<script src="@routes.Assets.versioned("ui/scripts.js")" type="text/javascript"></script>
    <script src="@routes.Assets.versioned("javascripts/common/vendor/ace/src-min/ace.js")" type="text/javascript"></script> <!-- this makes things work-->

Итак, я знаю, что проблема в том, что мой mode-html.js файл не обслуживается, и, скорее всего, это проблема разрешения пути, но я не могу понять, что это такое.

Дальнейший анализ показывает, что следующее код в ace.js вызывает ошибку.

exports.loadModule = function(moduleName, onLoad) {
    var module, moduleType;
    if (Array.isArray(moduleName)) {
        moduleType = moduleName[0];
        moduleName = moduleName[1];
    }

    try {
        module = require(moduleName);
    } catch (e) {}
    if (module && !exports.$loading[moduleName])
        return onLoad && onLoad(module);

    if (!exports.$loading[moduleName])
        exports.$loading[moduleName] = [];

    exports.$loading[moduleName].push(onLoad);

    if (exports.$loading[moduleName].length > 1)
        return;

    var afterLoad = function() {
        require([moduleName], function(module) {
            exports._emit("load.module", {name: moduleName, module: module});
            var listeners = exports.$loading[moduleName];
            exports.$loading[moduleName] = null;
            listeners.forEach(function(onLoad) {
                onLoad && onLoad(module);
            });
        });
    };

    if (!exports.get("packaged"))
        return afterLoad();

    net.loadScript(exports.moduleUrl(moduleName, moduleType), afterLoad);
    reportErrorIfPathIsNotConfigured();
};

var reportErrorIfPathIsNotConfigured = function() {
    if (
        !options.basePath && !options.workerPath 
        && !options.modePath && !options.themePath
        && !Object.keys(options.$moduleUrls).length
    ) {
        console.error(
            "Unable to infer path to ace from script src,",
            "use ace.config.set('basePath', 'path') to enable dynamic loading of modes and themes",
            "or with webpack use ace/webpack-resolver"
        );
        reportErrorIfPathIsNotConfigured = function() {};
    }
};

Почему явный вызов <script src="@routes.Assets.versioned("javascripts/common/vendor/ace/src-min/ace.js")" type="text/javascript"></script> делает код работающим. Должен ли этот сценарий быть доступен в ui/scripts.js согласно Angular способу упаковки https://upgradetoangular.com/angular-news/the-angular-cli-is-a-great-way-to-build-your-angular-app-but-what-it-does-can-be-a-mystery-what-are-those-files-it-generates/?

1 Ответ

0 голосов
/ 18 февраля 2020

Я наконец смог заставить свой код работать. Моя установка отличается. Я создаю свое приложение Angular и оно подается с моего сервера Play. Сборка angular хранится в папке Play / public / ui. Запросы должны быть в формате / assets / ui / .., который отображается в / public / ui / ... из-за правила в файле маршрутов воспроизведения

GET     /assets/*file               controllers.Assets.versioned(path="/public", file: Asset)

Когда я запускал код, я получил ошибка.

Uncaught DOMException: Failed to execute 'importScripts' on 'WorkerGlobalScope': The script at 'http://localhost:9000/worker-javascript.js' failed to load.
    at blob:http://localhost:9000/3df21e42-fecb-4026-8bd6-f2b0d1d0540a:1:1

Ранее я также получил сообщение об ошибке Unable to infer path to ace from script src, use ace.config.set('basePath', 'path') to enable dynamic loading of modes and themes or with webpack use ace/webpack-resolver

Кажется, ng-ace-editor импортирует .js сценарии (тема, режим, рабочий) на основе theme и mode редактора. Файлы theme и mode js могут быть включены в scripts.js, но некоторые файлы worker-.js не могут быть (я не знаю почему, возможно, потому что рабочие загружаются динамически с использованием importScript.

Раздел сценариев в Angular.json (это все будет упаковано в сценарии. js в окончательном пакете Angular)

"scripts": [
              "./node_modules/ace-builds/src/ace.js",
              "./node_modules/ace-builds/src/theme-eclipse.js",
              "./node_modules/ace-builds/src/theme-monokai.js",
              "./node_modules/ace-builds/src/mode-html.js"
            ]]

Чтобы включить worker-.js файлы, я добавил это правило, потому что кажется, что angular-cli не может загружаться из node_modules. Поэтому мне пришлось скопировать файлы из node modules в root моей ui сборки - Как включить ресурсы из node_modules в angular cli project

"assets": [
              "src/assets",
              "src/favicon.ico",
              {
                "glob": "**/*",
                "input": "./node_modules/ace-builds/src/",
                "output": "/"
              }
            ],

Когда я выполнил код, я обнаружил ошибку, что http://localhost:9000/worker-javascript.js can't be loaded. Я понял, что мои файлы загружаются по пути /assets/ui/, а не по root сервера поэтому я установил basepath на /assets/ui в файле .ts компонента

import * as ace from 'ace-builds/src-noconflict/ace';
    ace.config.set('basePath', '/assets/ui/');
    ace.config.set('modePath', '');
    ace.config.set('themePath', '');

В итоге basePath кажется тем, что используется для динамической загрузки скриптов (например, рабочих скриптов) modePath и themePath равны /, так как сценарии режима и темы связаны в scripts.js и доступны на уровне root необходимо скопировать worker-.js файлов за пределы node_modules, так как angular_cli не может копировать активы из node_modules

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...