2

非常に基本的なプロトタイプ AngularJS プロジェクトを作成したので、それを移行して RequireJS を使用してモジュールをロードしたいと考えました。AngularAMDおよびAngularAMD-sampleプロジェクトに基づいてアプリを変更しました。

ここで、デフォルト ルートにアクセスすると、次のようになります。

Uncaught TypeError: Cannot read property 'directive' of undefined

「アプリ」への依存が満たされていない理由について頭を悩ませてきました。私が明らかに間違っていることを誰かが見つけることができれば、それは大歓迎です。

プロジェクトのソース コードをGitHubに置きましたが、重要な部分は次のとおりです。

main.js

require.config({

    baseUrl: "js/",

  // alias libraries paths
    paths: {
        'angular': '../bower_components/angular/angular',
        'angular-route': '../bower_components/angular-route/angular-route',
        'angular-resource': '../bower_components/angular-resource/angular-resource',
        'angularAMD': '../bower_components/angularAMD/angularAMD',
        'ngload': '../bower_components/angularAMD/ngload',
        'jquery': '../bower_components/jquery/jquery'

    },

    // Add angular modules that does not support AMD out of the box, put it in a shim
    shim: {
        'angularAMD': ['angular'],
        'ngload': [ 'angularAMD' ],
        'angular-route': ['angular'],
        'angular-resource': ['angular']
    },

    // kick start application
    deps: ['app']
});

app.js

define(['angularAMD', 'angular-route', 'controller/login', 'controller/project_detail', 'controller/project_list'], function (angularAMD) {
  'use strict';

  var app = angular.module('cmsApp', ['ngRoute']);

  app.constant('REMOTE_BASE_URL', "/cms/v2/remote");

  app.constant('SERVER_ERROR_TYPES', {
    authentication: 'Authentication',
    application: 'Application',
    transport: 'Transport'
  });

  app.constant('AUTH_ERROR_TYPES', {
    invalidLogin: "INVALID_CREDENTIALS",
    invalidToken: "INVALID_TOKEN",
    noToken: "NO_TOKEN"
  });

  app.constant('AUTH_EVENTS', {
    loginSuccess: 'auth-login-success',
    loginFailed: 'auth-login-failed',
    logoutSuccess: 'auth-logout-success',
    notAuthenticated: 'auth-not-authenticated'
  });

  app.config(['$routeProvider',
    function($routeProvider) {
      $routeProvider.
        when('/login', {
          templateUrl: 'partials/login.html',
          controller: 'LoginCtrl'
        }).
        when('/projects', {
          templateUrl: 'partials/project-list.html',
          controller: 'ProjectListCtrl'
        }).
        when('/projects/:projectId', {
          templateUrl: 'partials/project-detail.html',
          controller: 'ProjectDetailCtrl'
        }).
        otherwise({
          redirectTo: '/projects'
        });
    }]);

  return angularAMD.bootstrap(app);
});

そして、例外が発生しているファイル: login_form.js

define(['app'], function (app) {
   app.directive('loginForm', function (AUTH_EVENTS) {
      return {
        restrict: 'A',
        template: '<div ng-if="visible" ng-include="\'partials/login.html\'">',
        link: function (scope) {
          scope.visible = false;

          scope.$on(AUTH_EVENTS.notAuthenticated, function () {
            scope.visible = true;
          });

          scope.$on(AUTH_EVENTS.loginFailed, function () {
            alert("An error occured while trying to login. Please try again.")
            scope.visible = true;        
          });

          scope.$on(AUTH_EVENTS.logoutSuccess, function () {
            scope.visible = true;
          });
        }
      };
    });
});
4

1 に答える 1

6

アプリ自体が作成される前に「コントローラー/ログイン」をロードしています。

おそらく、次のような別のモジュールを作成する方が良いでしょう

define(['directive/login_form', 'service/authentication'], function () {
   'use strict';
   var loginModule = angular.module('loginModule', []);
   loginModule.controller('LoginCtrl', ...
   loginModule.directive('loginForm', ...

そして、次のようなことをします

   var app = angular.module('cmsApp', ['ngRoute', 'loginModule']);

それは理にかなっていますか?

アップデート:

私はちょうど別の解決策を考えています。アプリの定義から「コントローラー/ログイン」を削除するだけです。angularAMD を使用する場合、指定された URL に移動する前にコントローラーをロードしないでください。削除するだけで、コントローラーがオンデマンドで読み込まれます。そうすれば、アプリが定義されます!(ただし、複数のモジュールを作成することをお勧めします。アプリ モジュールにすべてを含めるのではなく、さまざまな責任のために複数のモジュールを含める方が良いと感じます。また、テストにもはるかに適しています。)

angularAMD.route({
    templateUrl: 'views/home.html',
    controller: 'HomeController',
    controllerUrl: 'scripts/controller'
})

フィールドcontrollerUrlに注意してください。

こちらをご覧ください。

于 2014-11-05T00:18:25.747 に答える