VasilioRuzanni / angular-modelizer

Simple and lightweight yet feature-rich models to use with AngularJS apps.
MIT License
26 stars 4 forks source link

Trying to change the Rest url at runtime for a .$newCollection #9

Open jackp55 opened 8 years ago

jackp55 commented 8 years ago

HI Vasilio!

It's me again!

Having a hard time trying to figure out how to change a .$newCollection of models's url at runtime.

We have scenarios where we have a model, and you can have several different Rest URLs to get a collection of these models.. depending on scenario.

  1. I can't seem to get the baseUrl(#)s from my model definition at runtime with .$newCollection, I can only get a 'baseUrl'.
  2. I CAN seem to get different 'baseUr(#) if I use a .$new, but I need a .$newCollection
  3. The fetch ({url:urlValue}) doesn't seem to work for .$newCollection either

So:

// Lets define some models first, with different Rest urls
// =============================

modelize.defineModel('post', {
  baseUrl: '/blog/postsdefault',
  baseUrl1: '/blog/posts111',
  baseUrl2: '/blog/posts222',
  baseUrl3: '/blog/posts333'',
...
  })
});

// Fetch collection
// ================
// Create empty collection
var posts = Post.$newCollection();

// Then fetch with different paths
// these are just different scenarios of course

var baseUrl = posts.baseUrl  // works
var baseUrl1 = posts.baseUrl1  // undefined
var baseUrl2 = posts.baseUrl2  // undefined
var baseUrl3 = posts.baseUrl3  // undefined

posts.fetch({ url: baseUrl1 }); 
posts.fetch({ url: baseUrl2 }); 
posts.fetch({ url: baseUrl3 }); 
VasilioRuzanni commented 8 years ago

@jackp55 The baseUrl and urlPrefix are special attributes that are set on collection initialization: https://github.com/VasilioRuzanni/angular-modelizer/blob/master/src/angular-modelizer.js#L2516-L2517

So, there is only one baseUrl on the Model that is propagated to the collection instances.

In your example above:

modelize.defineModel('post', {
  baseUrl: '/blog/postsdefault',
  baseUrl1: '/blog/posts111',
  baseUrl2: '/blog/posts222',
  baseUrl3: '/blog/posts333',
  ...
});

You're effectively setting baseUrl (a special Model class/instance/collection property) as well as baseUrl1, baseUrl2 and baseUrl3 model attributes (this is important, those are treated just as simple model attributes and never get to the collection).

Depending on what exactly you want to achieve, the options you have are:

Let me know if any of the above works for you and describe your particular task in more detail so that we can think about appropriate solution.

jackp55 commented 8 years ago

Ok, thx Vasilio for response!

So, basically I want to be able to get a list of 'Post' objects (collection) with different urls depending on business scenario.

Sometimes i'll fetch a list of 'Post' objects with:

(assuming both these endpoints return same JSON...)

VasilioRuzanni commented 8 years ago

@jackp55 Yeah, then it probably makes sense to just use fetch() with different URLs.

This also can be done with extending model class and/or collection, which might be more convenient (getting "special" posts as an example):

modelize.defineModel('post', {
  baseUrl: '/blog/posts',
  ...

  static: {
    getSpecial: function () {
      var _this = this;
      return this.$request.get(this.resourceUrl() + '/special').then(function (data) {
        return _this.$newCollection(data);
      }
    }
  },

  collection: {
    fetchSpecial: function () {
      return this.fetch({ url: this.resourceUrl() + '/special' });
    }
});

// Now you can
var posts = Post.$newCollection();
posts.fetchSpecial();

// Or as a model class static method
Post.getSpecial().then(function (specialPosts) {
  // Do something with specialPosts
});
jackp55 commented 8 years ago

Getting closer, but I need to define my multiple urls somewhere... I was going to define them in the .defineModel('post'... but I can't seem to access them.

ie:

modelize.defineModel('post', {
  baseUrl: '/blog/posts',
  specialUrl: 'company/posts',
  ...
  static: {
    getSpecial: function () {
      var _this = this;
      return this.$request.get(this.specialUrl).then(function (data) {
        return _this.$newCollection(data);
      }
    }
  },
  collection: {
    fetchSpecial: function () {
      return this.fetch({ url: this.specialUrl });
    }
});
// Now you can
var posts = Post.$newCollection();
posts.fetchSpecial();
// Or as a model class static method
Post.getSpecial().then(function (specialPosts) {
  // Do something with specialPosts
});