【问题标题】:Is it possible to build a self-contained Angular plugin to be embedded in other angular sites?是否可以构建一个独立的 Angular 插件以嵌入到其他 Angular 站点中?
【发布时间】:2016-03-07 04:53:05
【问题描述】:

我真的很喜欢 Angular。

话虽如此,我想在 in Angular 中创建一个可以托管在其他网站上的插件 - 无论他们使用什么框架。这些框架可以是 Angular 的,也可以是其他的。

当然,后者更容易。我只是添加了我的 Angular 代码和中提琴。它只是工作。前者是我遇到的麻烦 - 使用 Angular 的网站。

在本地创建的简单设置失败,原因是:

警告:尝试多次加载 angular。

关于如何克服这个问题的任何建议?

【问题讨论】:

标签: angularjs npm webpack angular-directive


【解决方案1】:

听起来你几乎想创建一个可以在 NPM 上注册的 Angular 模块。

就您引用的错误而言,您可能需要调整“加载程序”脚本。我创建了一些使用这种格式的公共 npm 模块,也使用 webpack 来创建脚本。这就是我的“加载器”脚本的样子。它允许加载脚本标签、commonJS 和 AMD 模块。

import mooAccordionDirective from './mooAccordion.js';
import mooRepeatTranscludeModule from 'moo-utility-repeat-transclude';

(function (root, factory) {
    if (typeof module !== 'undefined' && module.exports) {
        // CommonJS
        if (typeof angular === 'undefined') {
            var angular = require('angular');
            factory(angular);
            module.exports = 'mooAngularAccordion';
        } else {
            factory(angular);
            module.exports = 'mooAngularAccordion';
        }
    } else if (typeof define === 'function' && define.amd) {
        // AMD
        define(['angular'], factory);
    } else {
        // Global Variables
        factory(root.angular);
    }
}(this, function (angular) {
  'use strict';
  // create your angular module and do stuff
  var moduleName = 'mooAngular.accordion';
  var mod = angular.module(moduleName, ['mooAngular.utilityRepeatTransclude']);

  mooAccordionDirective(mod);

  return moduleName; // the name of your module
}));

有关我如何使用 Webpack+AngularJS+ES6 构建整个项目的更多参考,您可以查看 my github page for the moo-angular-accordion 项目。

如果你使用这个脚本,它看起来像:

(function (root, factory) {
    if (typeof module !== 'undefined' && module.exports) {
        // CommonJS also this prevents your error you are getting.
        if (typeof angular === 'undefined') {
            var angular = require('angular');
            factory(angular);
            module.exports = 'myModuleExportString';
        } else {
            factory(angular);
            module.exports = 'myModuleExportString';
        }
    } else if (typeof define === 'function' && define.amd) {
        // AMD
        define(['angular'], factory);
    } else {
        // Global Variables
        factory(root.angular);
    }
}(this, function (angular) {
  'use strict';
  // create your angular module and do stuff
  var moduleName = 'myModule';
  var mod = angular.module(moduleName, ['otherDepModulesIfNeeded']);

  mod.directive(/*... defined here ...*/);

  return moduleName; // the name of your module
}));

细分:

  • 您定义了一个 IIEF,它使用 this 调用,并且您的模块函数 (factory) 作为参数提供。
  • 该逻辑检查angular 是否已存在于全局命名空间中(以及是否支持 CommonJS。
  • 如果 angular 存在,请使用它(这样它就不会被定义两次),并将 angular 传递给您的模块定义 (factory)
  • 如果不是 CommonJS,请检查 AMD
  • 如果不是 AMD,则作为全局加载到根目录(可用作脚本标签)

编辑:您也可以使用 Grunt、Gulp 或任何您想要捆绑资产的构建系统而不是 Webpack,但是上面的神奇脚本使您的模块可以以多种格式导出(AMD、Script Tag、CommonJS 等) .

【讨论】:

    【解决方案2】:

    @Sean Larkin 的回答是正确的,但对于那些使用 jspmtypescript 的人来说,这是我在那里所做的。

    1) 编写你的 App 模块:

    /// <reference path="typings/tsd.d.ts" />
    
    import * as angular from "angular";
    import modules from "./Modules"; // a simple exported array
    
    // Create our angular module.
    angular.module("module.name", modules);
    

    2) 运行此命令来构建一个包:

    jspm bundle-sfx App - angular app.min.js --globals "{ 'angular': 'angular' }" --minify
    

    3) 现在 app.min.js 是一个 ES5 模块库,很容易加载到脚本标签甚至另一个 jspm 消费者网站中。

    【讨论】:

      猜你喜欢
      • 2021-03-10
      • 2017-07-11
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2022-10-30
      • 1970-01-01
      • 1970-01-01
      • 2019-07-30
      相关资源
      最近更新 更多