3

I've the following AngularJS App written with TypeScript

The Main App where I initalize the App:

module MainApp {
   export class App {
      public static Module : ng.IModule = angular.module("mainApp", [])
   }
}

And my controller

module MainApp {
   export class Person {
     public firstName: string;
     public lastName: string;
   }

   export  interface IMainAppCtrl {

   }

   export class MainAppCtrl implements IMainAppCtrl {
      public person : Person;
      constructor() {
          this.person = new Person();
          this.person.firstName = "Vorname";
          this.person.lastName = "Nachname";
      }
  }

  MainApp.App.Module.controller("mainAppCtrl", MainAppCtrl);
}

Thats working, but I am not very happy with this solution, because here I have to register the controller for my App in my controller itself

MainApp.App.Module.controller("mainAppCtrl", MainAppCtrl);

It would be nice If ther is a possiblity to register the controller in the "App" class directly like:

public static Module : ng.IModule = angular.module("mainApp", []).controller("mainAppCtrl", MainAppCtrl);

but thats not working here i get the error Message from the browser

"Argument 'mainAppCtrl' is not a function, got undefined"

in my old plain JS angular controllers I had an mainApp where I've registered all my Controllers like

angular.module("app.main", [
    "ui.router",
    "ngSanitize",
    "DirectiveTestsCtrl",
    ....
]);

and in my controller i've only registerd the controller name for angular:

angular.module("DirectiveTestsCtrl", [])
       .controller("DirectiveTestsCtrl", function () { ... });

is this also possible with the above shown snipes with typescript or what is best practise here - I've searched the web and found many examples but not a good one for controlerAs syntax and with "module Name { class xyz }" which was really working.

squadwuschel
  • 3,328
  • 3
  • 34
  • 45
  • What order is the code running in? The initialization of the `MainAppCtrl` class needs to run before the `MainApp.App` initialization runs. – Ryan Cavanaugh Apr 09 '15 at 18:27

1 Answers1

2

TLDR; - Export a static function on your main module that will handle all the bootstrapping/initialization logic. For child/sub modules export a static readonly property which will allow you to build once and retrieve multiple times a defined angular module.


Main Module

I have taken a similar approach, but it at least encapsulates the additional of components (controllers, services) inside the module definition

module appName {
  export class App {
    static createModule(angular: ng.IAngularStatic) {
      angular.module('moduleName', ['ngRoute'])
          .controller('refCtrl', ReferencedControllerClass)
          .service('dataService', DataService);
    }
  }
}

appName.App.createModule(angular);

Child Module(s)

Then in other internal modules I create a static reference to the module to account for it being referenced more than once...

module appName {
  export class SubModuleName {
    private static _module:ng.IModule;

    public static get module():ng.IModule {
      if (this._module) {
        return this._module;
      }

      this._module = angular.module('subModuleName', []);

      this._module.controller('SomeCtrl', SomeController);

      return this._module;
    }
  }
}

With this approach I can inject my SubModule into the main angular module via:

angular.module('moduleName', ['ngRoute', appName.SubModuleName.module.name])

Note: The main module could be defined as the child one's are for consistency, but I am only ever referencing/building it once, so I didn't bother caching it with a local static instance.

Brocco
  • 62,737
  • 12
  • 70
  • 76
  • the first code with the main Module works great, but the second with the Child Module(s) I've tried and here Vs Debugger tells me that "module" is null – squadwuschel Apr 09 '15 at 20:05
  • That seems like the sub-module is not being referenced by the main file? You can take a look at how I've setup a TypeScript AngularJS project here: https://github.com/Brocco/ts-star-wars I am doing my TypeScript building via gulp and not via Visual Studio – Brocco Apr 09 '15 at 20:11
  • Here is mine current SLN: http://squadwuschel.codeplex.com/SourceControl/latest#Testprojekte/MvcTypeScript/MvcTypeScript/TypeScripts/mainApp.ts – squadwuschel Apr 09 '15 at 20:16
  • I've implented it like in your solution and checked it in - but its not working, still the same error. Is it important to have all the reference Tags in every file or is this only optional? – squadwuschel Apr 09 '15 at 20:33
  • Solved the Problem - I've added a _reference.ts with the right Order for the Files - http://stackoverflow.com/questions/23902107/visual-studio-2013-typescript-compiler-isnt-respecting-references-ts-file – squadwuschel Apr 09 '15 at 21:04
  • Glad you were able to solve your problem with resolving references – Brocco Apr 10 '15 at 12:03