afterglowtech / angular-detour

Lazy-loaded/runtime-configurable/server-enhanced routing for AngularJS applications
Other
51 stars 5 forks source link

Is this still being actively worked on? #21

Open ChristianWeyer opened 11 years ago

ChristianWeyer commented 11 years ago

Hi there,

according to this SO post http://stackoverflow.com/questions/15780269/dynamic-routing-in-angularjs-can-i-retrieve-data-from-server-before-setting-up/16796728#16796728

you wanted to work towards a stable version - or at least have docs ;)

Any news on that? Thanks!

laurelnaiad commented 11 years ago

The project is alive. I'm hoping to give it a major update in the next month or so as time permits, including docs, tests, angular-ui-router 0.2.0 features and a first class javascript implementation of a generic server library to go along with it to enable advanced CMS-like features. I'd be happy to help in the meantime. If you run the samples it may give you a sense of what docs would otherwise tell you. Knowledge of ui-router is pretty much a prerequisite though.

olofd commented 10 years ago

How is the project coming along? I've just started using your router and i really like it. I'm hoping to be able to give more feedback soon!

laurelnaiad commented 10 years ago

Hi @olofd,

The short answer is that other non-detour-related "real work" has pulled me away from it in the short run, but I am using it myself in one of my active projects, and I fully expect that I will do a rewrite, as an upcoming project may have need of its feature set, and there are definitely improvements that I'd like to make -- what's here now is really a first draft. The scope of the rewrite is unknown at this point, but I will make a point to add some "next steps" information to the README to give an indication of what I'm considering -- both in terms of the feature set and the relationship between detour and ui-router.

I would very much appreciate any detailed feedback! Are you using the server code that is in the lazy routing sample?

olofd commented 10 years ago

@stu-salsbury Yes. I'm using the code from the sample. I've extracted it away into an module (And loading the json from mongo.) and made som minor improvements (Some that I will post here when I get to use the code a bit more). It's especially the dynamic routing-capabilities that I'm intrested in, and I'm using it for a CMS built in angular that I'm working on. Of course I'm aware of the angular teams goals to have these features in the core in the future. I'll come back to you after the holidays (Intend to give myself some time to work on the project during them.)

laurelnaiad commented 10 years ago

Awesome -- CMS is my inspiration as well. Would be great to collaborate. I'm looking forward to feedback/contributions! I'm not under the impression that these features are on the roadmap for Angular core -- can you point me toward any info you have on that?

btesser commented 10 years ago

I'm interested in collaborating as well. My motivation is more of a nested app structure, so that one parent angular application can load multiple child apps, each written by different groups

laurelnaiad commented 10 years ago

Hi guys! I'm all for collaboration. I don't have much time to devote, but I can tell you that I use this.

I'd love it if someone would rewrite it! I'm actually not joking. My vision is to go back to ui-router in its current form and to develop detour on top of it rather than as a ground-up partial rewrite. I don't know if that vision is realistic because I haven't done the research. That ui-router still won't move to a tree data structure and is firmly against consolidating urlRouter and state is a hurdle.

That all said, I totally welcome contributions. What all do you have in mind?

btesser commented 10 years ago

I've looked into what can be done with the current state of ui-router as well. I think we should have a provider which allows for name-> url mapping of dependencies. For example:

detourProvider.setDependencies({
  controllers: {
    test1Ctrl: '/testCtrl.js',
    test2Ctrl: '/test2Ctrl.js',
  },
  services: {
    testSvc: '/testsvc.js'
  },
  nonAngular: {
    jQueryUI: '/jquery.ui.js'
  },
  css: {
    userSection: '/userSection.css'
  },
  filters: {
    testFilter: '/testfilter.js'
  },
  directives: {
    testDirective: '/testdirective.js'
  }
});
$stateProvider.state('test',{
  controller: 'testCtrl',
  nonAngular: ['jQueryUI'],
  css: 'userSection',
});

As I see it they could also be grouped.

detourProvider.createGroup('testgroup', {
  controllers: ['test1Ctrl'],
  filters: ['testFilter'],
  css: ['userSection']
});
$stateProvider.state('test',{
  controller: 'testCtrl',
  dependencies: ['testgroup']
});

We could also automatically parse the controller constructor for dependencies and load them, so it would be unnecessary for them to be manually specified. This could be optional and allow for urls to be provided in the route definition:

$stateProvider.state('test', {
  controllerUrl: '/myCtrl.js',
  css: ['/file.css'],
  filters: { filterOne: 'filterOne'}
})l

Here's what I've come up with so far:

As far as tree structure is concerned, we can definitely make a parser that converts that format to dot syntax. That wouldn't be too difficult

What I disliked about couchPotato was manually having to call a function for each dependency. I feel like each state should be as close to the standard definition as possible and have the loading happen behind the scenes.

Thoughts?

laurelnaiad commented 10 years ago

Thank for the input!

detourProvider.setDependencies({
  controllers: {
    test1Ctrl: '/testCtrl.js',
    //etc

I'm not a fan of this. You've centralized what was intended to be decentralized. detour isn't solely for optimizing loading speed. Another primary goal is that it decentralize the definition of states and dependencies, such that diverse development can happen in semi-isolation. Centralizing information about dependencies is antithetical to that goal. Basically, detour is trying to operate in the vein of other dependency management frameworks like CommonJS and require.js (and actually uses require.js through couchPotato). That is very much on purpose. I'm not wedded to exposing the require.js syntax, but applying the general model of JS dependency management is a feature, not a bug :)

$stateProvider.state('test',{
  controller: 'testCtrl',
  nonAngular: ['jQueryUI'],
  css: 'userSection',
});

We could also automatically parse the controller constructor for dependencies and load them, so it would be unnecessary for them to be manually specified.

I've thought about how Angular's DI could be leveraged, but it would only help with Angular components, if it were even leverage-able. What would do this interpretation? A server? Build-time? Run time in the browser? With detour using couchPotato using require.js, the browser is in charge behind the scenes, using a proven methodology for dependency management. You'd have to hack angular up into pretty bloody state if you wanted to leverage its DI for dependencies that aren't Angular components!

Asynchronous route definitions aren't allowed... Caveat: I was able to find a workaround by assigning $stateProvider to an angular.value in the config stage

Well that's a bummer. Modfying the route definitions on the fly is also a raison d'etre.

What I disliked about couchPotato was manually having to call a function for each dependency. I feel like each state should be as close to the standard definition as possible and have the loading happen behind the scenes.

Yes, I get the sense that you're not a fan of require.js or couchPotato ;)

I do agree that anything that can be done to minimize developer overhead with the require.js syntax of couchPotato would be great.... but to be honest, require.js has been around for a while and is a proven thing -- not a lot out there for lazy loading dependencies beyond require.js. If there were some way to "make it easier" to get the functionality it provides, I'd expect someone would have done it by now, outside the context of detour.

If we take a step back from the design details you provided, which I guess you've surmised don't align with the detour vision, is detour still something that has value for you? Where is the value? Why are you or would you be using detour? And if we take the require.js aspects off of the table, what problems are you trying to solve with detour that motivated you to come up with a different design?

btesser commented 10 years ago

So here is my thinking. As far as this comment:

detourProvider.setDependencies({ controllers: { test1Ctrl: '/testCtrl.js', //etc I'm not a fan of this. You've centralized what was intended to be decentralized. detour isn't solely for optimizing loading speed. Another primary goal is that it decentralize the definition of states and dependencies, such that diverse development can happen in semi-isolation.

In retrospect I agree, this is better left as a service rather than a provider so new dependencies can be declared at any time.

Making a distinction between one's angular and non-angular dependencies seems artificial and I don't understand the value. Primarily the reason is that angular dependencies have to be manually registered whereas external dependencies just need to be loaded. The value is that dependency are associated with the current route/state/page the user is on. In order for it to display properly, the controller may have a dependency on a service that has not yet been loaded, the view may have a dependency on a directive, and a directive may have a dependency on jQuery UI. If the page's controller is used in multiple places, associating the directive dependency with it could lead to unnecessary dependencies being loaded.

I've thought about how Angular's DI could be leveraged, but it would only help with Angular components, if it were even leverage-able. What would do this interpretation? A server? Build-time? > Run time in the browser? With detour using couchPotato using require.js, the browser is in charge behind the scenes, using a proven methodology for dependency management. You'd have to hack angular up into pretty bloody state if you wanted to leverage its DI for dependencies that aren't Angular components!

Let me start by saying I am not planning to use angular's DI to inject dependencies or modify it at all... Just to use the same strategy for figuring out what they are. In terms of loading them, that is answered further down. It actually isn't very difficult to determine the controller dependencies. It doesn't require modifying the angular source at all. (I recently did it as part of a logging component that automatically logs every scope function that is run). The fact that we will be manually registering the controllers as they are defined async makes it even easier. As far as non-angular components, I didn't originally see parsing the controller for those. Only the controller's angular dependencies. In retrospect, however, we could do non-angular dependencies that way as well. They could be passed into the resolve section of the state providing the controller direct access to them (all just by parsing the name from the fn)

I have no issue with couchPotato or requirejs. In fact, before angular, I used requirejs on every project. I actually did a very large project using a angular with requirejs and a similar lazy controller/lazy directive system to detour (angular js requirejs lazy controllers). The reason I haven't used require with an angular project since then is that it made testing extremely difficult. The solution I am proposing doesn't involve modifying any core angular code and $state could simply have a mock to make testing easier. What I like about the solution I am suggesting is that each dependency has nothing special to do, our patch of $state can take care of everything.

In terms of how to actually load the dependencies then... Require is great for development, and the thing that makes it great for production is the optimizer. I do see it as not necessarily the best way to handle loading dependencies in an angular project however. So much has to happen behind the scenes that it would either require modifying each dependency file to reference detour, or to modify require itself. I am not averse to using it behind the scenes (in fact I intended to use it, or it's lighter brother almond), I just don't want the user to have to worry about it. I believe that almond provides all of the features necessary to do the actual loading without the bulk of require.

Let me know what you think

btesser commented 10 years ago

In retrospect I agree, this is better left as a service rather than a provider so new dependencies can be declared at any time.

I meant to say defined at any time