Giter Club home page Giter Club logo

subs-manager's Introduction

SubsManager Build Status

Subscriptions Manager for Meteor

This is a general-purpose subscriptions manager for Meteor. You can use Subscription Manager to cache subscriptions in the client side. This will help you to reduce the CPU usage of your app and improve the client side experience.

Why?

Normally you invoke subscriptions inside the template level or in the router level(in the case of Iron Router). So, when you are switching routes or changing templates/components, subscriptions will run again.

Normally, users go back and forth in your app in a single session. So, in each those route/page changes, app will re-subscribe data from the server. That's a waste and slow down your app in the client side.

Solution

Subscriptions Manager caches your subscriptions in the client side. So, when the user switching between routes, he will no longer have to wait. Also, Meteor won't need to re-send data that's already in the client.

In technical terms, Subscriptions Manager runs it's own Tracker.autorun computation internally. It does not interfere with Router or Templates. It works independently.

Subscriptions Manager does not cache your individual data. It tells Meteor to cache the whole subscription. So, your data will get updated in the background as usual.

Usage

Installation:

meteor add meteorhacks:subs-manager

Then create a new SubsManager instance:

PostSubs = new SubsManager();

Then instead of subscribing to Meteor.subscribe(), use PostSubs.subscribe(). Check this example:

Template.blogPost.onCreated(function() {
    var self = this;
    self.ready = new ReactiveVar();
    self.autorun(function() {
        var postId = FlowRouter.getQueryParam('postId');
        var handle = PostSubs.subscribe('singlePost', postId);
        self.ready.set(handle.ready());
    });
});

Here's how this works:

  • Let's say you visit page /posts?postId=abc.
  • Then Meteor will subscribe to the singlePost publication with abc as the postId.
  • Then let's imagine you visit to /posts?postId=bbc.
  • Just like above, it'll subscribe to the singlePost publication with bbc as the postId.
  • Now, let's say we go back to /posts?postId=abc. Then, subsManager won't fetch data again from the server. Subscription is already exists inside the client.

Check following links for more information:

Resetting

Sometime, we need to re-run our subscriptions due to various reasons.

Eg:- After a user has update the plan.

In those situations, you can try to reset Subscription Manager.

var subs = new SubsManager();

// later in some other place
subs.reset();

Clear Subscriptions

In some cases, we need to clear the all the subscriptions we cache. So, this is how we can do it.

var subs = new SubsManager();

// later in some other place
subs.clear();

Cache Control

Since now you are caching subscriptions, the Meteor server will also cache all your client data. But don't worry - that's not a huge issue.

But, you can control the caching behavior. Here's how to do it.

var subs = new SubsManager({
    // maximum number of cache subscriptions
    cacheLimit: 10,
    // any subscription will be expire after 5 minute, if it's not subscribed again
    expireIn: 5
});

Patterns for using SubsManager

Using a global Subscription Manager

You can create a global subscription manager as shown in the above example. By doing that, all your subscriptions are cached as a whole.

Using separate Subscription Managers

If you need more control over caching, you can create separate Subscription Managers for each set of subscriptions and manage them differently.

If you are using SubsManager inside a ReactComponents, this is the suggested way.

Using global ready checking

You can also check the ready status of all the subscriptions at once like this:

var subs = new SubsManager();
subs.subscribe('postList');
subs.subscribe('singlePost', 'id1');

Tracker.autorun(function() {
  if(subs.ready()) {
    // all the subscriptions are ready to use.
  }
});

Cache subscriptions you only need

With Subscription Manager you don't need to use it everywhere. Simply use it wherever you need without changing other subscriptions.

Limitations

Subscription Manager aims to be a drop-in replacement for Meteor.subscribe (or this.subscribe() in Iron Router). At the moment, the following functionality doesn't work.

  • onError and onReady callbacks (issue)

subs-manager's People

Contributors

arunoda avatar bitomule avatar dandv avatar gadicc avatar pahans avatar pdiniz13 avatar tomwasd avatar yasaricli avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

subs-manager's Issues

Subscriptions that loads different fields of the same collection

I have a itemList route and a item/:name route; the first one shows a list of items, the other one, for every item shows the detailed information about it;

since the itemList route only needs the name of the item, it subscribes a publication that returns only that list (return Items.find({},{fields: {name: 1}}),
otherwise the item/:name route needs all the fields for the current item, so it subscribes a publication that returns: Items.find({name: name},{limit: 1})

loading the itemList route (that is ok) and then clicking on one item's name to navigate the item/:name route, doesn't work, since additional fields are not loaded; it seems that local Items collection is not updated with additional fields sended by the new subscription once they are already loaded by another subscription; in fact, pressing F5 on the item/:name route, let everything work ok

Can Iron Router this.subscribe be replaced?

The README should mention in the Iron Router example whether this.subscribe() can be replaced with a subs.subscribe() call.

This is important because this.subscribe() can be chained with wait().

How can I get all the records the server had sent for a subscription?

As we know, despite this being a very common scenario, Meteor doesn't support querying against a publication, in other words finding on the clients all the records that a particular subscription has returned.

I have a large collection on the server called content, and different filters against it on the server (e.g. content of various types, search fields etc.), with differently named pub/sub for each: content for the most recent items, content-portfolio for content that matches a company in the user's portfolio. Without subs-manager, when the route changes from one view to another, the server resets the publication and I can simply find on the client all the records that the server has published for that view by running

Content.find({})

However, after adding subs-manager, the entire Content collection apparently gets cached on the client, not just the subscription, and Content.find({}) in the contentPortfolio route returns the most recent items as well from the content subscription.

I only use subs-manager for the content subscription, and a regular this.subscribe('content-portfolio') for the portfolio-filtered subscription.

Since subs-manager manages subscriptions at a very low level, it would be great if there were a mechanism to isolate records coming from a specific subscription. That would be a super useful feature and it would solve a very real problem with Meteor core.

Feature Request: Add an existing subscription to be managed

I see a few options here, and would like some outside input before I start coding it.

I would like the ability to either add a subscription that has already been created, or to be able to add a subscription in subs-manager that doesn't start the timeout immediately.

The specific use case I'm looking at is being able to subscribe when the data is needed, and add it to subs-manager when the data isn't required for what is displayed anymore. In that way you would be guaranteed the data needed, but still have the caching behavior of subs-manager.

Proposal - add subs.static property

I have a city picker in my proj with 5000 cities in it (each - a different doc). This picker is present on every page.
Before using subs-manager I subscribed to 'cities' publication only when user clicked on city picker, showing a loader while the data was downloaded to the client.
After installing subs-manager my data is there almost instantly (if user doesn't rush in and clicks city picker instantly after page was rendered). But this means that each of my users will be subscribed to this pub, inducing overhead on the server, related to maintaining all of these reactive subscriptions.
So, I'm in doubts here:

  • with subs-manager I get nice UX, but server overhead
  • w\o it I subscribe only when necessary, but have suboptimal UX

Thus I propose to add to subs-manager the ability to download only the initial data and then sever connection to server if it doesn't need to be reactive. Like adding a subs.static: true property.

Caching persists across refreshes?

If subs-manager caches some subscription data and I close and reopen a browser tab, does the data persist in local storage from one session to the next?

I just ran into a weird situation where data was available on the client even though I wasn't publishing it, and I was wondering if it could be because of subs-manager.

Publish still called on each route change

Using iron-router, if I go from page A to page B to page A, I don't notice any difference in load times. Publish is still called by the server for the same subscriptions and I'm still waiting on the subscriptions.

In some places in my app it does work. I'm not sure when it does or doesn't work though. Sorry I couldn't be more clear. Is there a good way to test this and find out why it's not working?

FlowRouter.subsReady always return true with subs manager

Hello

It seems i am unable to use FlowRouter.subsReady when subs-manager handle the subscription in FlowRouter instead of Meteor.subscribe. In my case, FlowRouter.subsReady always return true, so the messags in my template who is suppose to inform the user that tha data is loading never show.

Regards

Subs manager will send null as a subscription parameter

I'm having trouble narrowing down what's happening, but I have the following line:

  console.log(n);

  if (n)
    subscription = subsManager.subscribe('fixtures', n);

and n is always an int, but the publication will sometimes receive null instead of the number.

What does help me fix this is increasing the subsmanager cachelimit. It seems that when the cache limit is hit, the subscription sends null instead of the number.

This also causes the page to refresh (using iron router). It seems like it's a subsmanager problem since increasing the cachelimit helps things.

SubsManager does not return object with the same API as Meteor.subscribe? (missing stop method)

I can't use the stop() method on subscriptions returned by the SubsManager, whereas I can stop them manually when returned by Meteor.subscribe.

Use case:
I subscribe to a Stats publication for all documents that are clientside available (and don't have an internal cached stats object):

Events.find({stats: {$exists: false}}).observe({
      added: function(doc){
        var sub = subsMngr.subscribe("eventStats", doc._id);
        //var sub = Meteor.subscribe("eventStats", doc._id);
        statsSubscriptions[doc._id] = sub;
      },
      removed: function(doc){
        statsSubscriptions[doc._id].stop();
        delete statsSubscriptions[doc._id];
      }
    });

When an event is not clientside available anymore, the stats shouldn't be published anymore and the stats-subscription must be stopped.

I want to cache these subscription, because events happen to be published and unpublished quite a log in my app, and the stats are quite expensive.

This doesn't seem to be possible, because I can't stop the statsSubscription?!
Does this mean, I can just never stop the subscription and they will stop automatically?

It seemed to me the cache would only become stale, when a subscription was stopped (AND cachetime expired)? No?

Question about limiting collection scope in server or client

I had learned (perhaps mistakenly) somewhere along the way to to limit the scope of my collections via the server side publish functions rather than in the client side data functions (using Iron Router). So for example, I might publish using a complex query and then in my controller simply call collection.find().fetch(). Or in another case where the url contains a single record's _id I would simply call collection.findOne() on the client. There was no need to write any query parameters on the client since only the relevant data was being published. But now with cached subscriptions it seems that I need to duplicate all of these queries on the client side, which will prove to be quite complicated in cases where I am using publish-with-relations.

Am I doing something wrong, or is it necessary that I duplicate all of my query logic on both sides of the wire?

Elaborate on the backwards compatibility of subs.subscribe

Related to the iron-router .wait() issue: How much of a drop-in replacement is subs.subscribe vs. Meteor.subscribe? For example, how does it handle the onError and onReady callbacks?

The code below works fine with this.subscribe(), but never completes with subs.subscribe():

onBeforeAction: function () {
  var user = Meteor.user();
  if (user) {
    Session.set('contentLoaded', false);
    this.subscribe('content-portfolio', user, function onReady() {  // user is a temporary placeholder for a more specific key in the user object
      Session.set('contentLoaded', true);  // PROBLEM: never here if this is replaced with subs
    });
  }
},

Depending on "ready" callback, runs only once

Not sure if I'm doing something that should be done different, but it seems the "onReady" callback is only called once. If you sucscribe to the same pub again, everything is cached and the onReady is skipped. This makes it tricky to hook logic into there. E.g., I use the onReady to set a var, that will make the helper trigger DOM updates only once. Therefore, the second time, it renders nothing.

Or is there another way I should do this in SubMgr? :)

this.Ready() not called correctly with multiple different subscriptions on 1 subscription manager

When I was using spiderable with Iron Router I wasn't having any issues.
Everything loaded as it should with ?_escaped_fragment_=

Something broke,
I tried every way imaginable to get Iron Router to wait for subscriptions using SubsManager, but it didn't want to. So, when I loaded a page up with phantomjs, only 1 of the subscriptions was loaded when the page was supposed to be ready.

Turns out that if you place different subscriptions on the same manager, it will fire ready for all of them, before the latter subscriptions are really ready.

This is probably a minor issue, but it is something people might run into so be warned! (took me forever to figure out what the hell was going on)

Issues with publish-counts package

Hi! It seems the publish-counts package doesn't play well with the cache. After filtering the collection, the count isn't updated unless I refresh the page. Is there something affecting updating changes in client-only collections via this.added and this.removed?

I've just discovered this package and I am confused

From your doc:

When you are subscribing inside a Deps.autorun computation, all the subscriptions started on the previous computation will be stopped.
...
[subscribing in Tracking.autorun] will force the Meteor server to resend data you already had in the client

That is not what I have been taught. To me, when subscribing in Tracker.autorun:

  1. Meteor runs the subscription with the new parameters, sending from the server only the data that has changed (achieving some sort of server-side caching).
  2. Meteor stops the subscription with the old parameters, removing locally the data that has been removed compared to the new subscription.

Also, I don't understand what this means and implies:

Subscriptions Manager caches your subscriptions and runs all the subscriptions that have been cached when a route is changed.

I am really interested in what this package might bring, especially given the limitations of the current Meteor subscription model (see this discussion). But in the end, I'm afraid the doc does not provide enough elements for me to decide if it fits my needs.

reset() in depth example

Several of my publications depend on a users organizationId, which can be set while logged in. If I login, then set the organization it automatically redirects to another page which uses organization specific data.

I subscribe in my router file via

  var subEach = function( subNames ){
    return _.map(subNames, function(sub){ return Meteor.subscribe(sub); });
  };

and

  waitOn: function(){ 
      return subEach(["Meals","UserCurrentVotes","CourseCategories","Courses","Organizations","MealLineItems","Users"]); 
  },

Which works fine, but when I change to

subs = new SubsManager({
  cacheLimit: 500,
  expireIn: 30
});

var subEach = function( subNames ){
  return _.map(subNames, function(sub){ return subs.subscribe(sub); });
};

This is run when the organization is set.

var orgId = $('#orgSelect').val();
Meteor.call('setOrg',orgId,function(){
  subs.reset();
  Router.go('votes');
});

Meteor.methods({
  setOrg: function(orgId){
    var users = Meteor.users;
    var updateOrg = Meteor.wrapAsync(_.bind(users.update, users));
    updateOrg({'_id': Meteor.userId()},{$set: {'profile.organizationId': orgId}});
    return;
  }
});

The route renders with no data and does not refresh. Console logs in the rendered callback show that the user organization has been set correctly, and the collections are empty.

Routing filter "after" called twice when using Subs-manager

Hi,

i've seen a problem in my app this weekend. im' using meteor 0.8.2 and the new blaze hook system. Is allows me to add animation on subscription. In my app i don't want animation on the first set of data so i use routing filters to enable/disable them :

  • Router.after : will enable animation if this.ready is true (should be always true, but not sure)
  • onStop : will disable animation

Without subs-manager : when i change route from /myRoute/Id1 to /myRoute/Id2 then the datas are loaded without animation at the first load.
In the console i can see that "onStop" is called first then "after" is called once. So animation are disabled, then enabled.

With subs-manager, when i change route from /myRoute/Id1 to /myrouteId2, the first time it will work as expected, but next time "after" filter will be called twice, so animation are enabled too early and animations will be played all the time. In that cas, both subscription are managed by subs-manager.

If you want i might create a new project to reproduce the problem.

Any way to interrogate the subs manager to see the current subscriptions

I looked at the code and I don't think you implemented this, so maybe it's more of a feature request, unless I'm overlooking something and there's a better way...

so, I have :
var searchSubsManager = new SubsManager({
// keep the last 3 searches run
cacheLimit: 3,
expireIn: 5
});

and every time the user runs a search query to the database, I do:

searchSubsManager.subscribe("search", query);

which runs the query on the server, then I do a find to retrieve the results.

We're keeping track of the last 3 search queries run, and this is working great, but I would like to be able to show the user on the screen what those last 3 search queries were. Is there a way to ask the searchSubsManager object to give me the cached subscriptions along with the parameter passed to each?.. I can see it in the Subs Manager as _cacheList, but not sure where to go from there. I can also see them in mongol (meteor toys)

SubsManager.subscribe doesnt work if params contains special charaters

I have something like this in my code
subMan.subscribe("subName", param);
subscription doesn't work if param variable contain a string with special chars. (example string: "Method not found [404]")

when I replace subscription with Meteor.subscribe everything works as expected.

Sometimes data lost

Just a heads up, in case it is good to know.

I came across the issue, that some data will be lost in the client when I create a new subscription. E.g., I have a user with an avatar property. When I create a new subscription in an autorun, which is totally unrelated to these avatars (at first sight), the avatar collection is cleared. This doesn't happen if I replace SubMgr with default subscriptions.

Can't update to 1.2.1

I tried to force 1.2.1 but I get this error

meteorhacks:subs-manager: Subscriptions Manager for Meteor
retinaMac:theProject rr$ meteor add meteorhacks:[email protected]
Currently using meteorhacks:subs-manager without any version constraint.
The version constraint will be changed to 1.2.1.
Could not satisfy all the specified constraints:
Error: conflict: constraints on meteorhacks:subs-manager cannot be satisfied.
Constraints come from:
  <top level>

I tried removing and reinstalling. Not sure what causes this issue

my installed packages are:

accounts-facebook                1.0.2  Login service for Facebook accounts
accounts-github                  1.0.2  Login service for Github accounts
accounts-password                1.0.4  Password support for accounts
accounts-twitter                 1.0.2  Login service for Twitter accounts
accounts-ui                      1.1.3  Simple templates to add login widgets to an app
alanning:roles                   1.2.13  Role-based authorization
aldeed:autoform                  4.0.7  Easily create forms with automatic insert and update, and automatic reactive validation.
aldeed:collection2               2.2.0  Automatic validation of insert and update operations on the client and server.
amplify                          1.0.0  API for Persistent Storage, PubSub and Request
arunoda:streams                  0.1.17  DB less realtime communication for meteor
bengott:avatar                   0.6.0  Consolidated user avatar template (twitter, facebook, gravatar, etc.)
bozhao:link-accounts             1.1.1  Meteor external service link system
brentjanderson:buzz              1.1.7  The fantastic Buzz javascript sound library repackaged for Meteor
classcraft:meteor-wkhtmltopdf    0.1.5  Meteor smart package for meteor-wkhtmltopdf.
coffeescript                     1.0.4  Javascript dialect with fewer braces and semicolons
dsyko:jquery-ui-touch-punch      1.2.4  jquery-ui-touch-punch project, Enable iPad/Phone/Pod touch interaction to jQuery UI controls
facebook                         1.1.2  Facebook OAuth flow
gadicohen:phantomjs              0.0.2  phantomjs installation script; wrapper for node phantomjs package + Sun
gadicohen:sitemaps               0.0.20  functions to easily output valid sitemaps
github                           1.1.1  Github OAuth flow
ground:db                        0.0.9  Ground Meteor.Collections offline
http                             1.0.8  Make HTTP calls to remote servers
iron:router                      1.0.3  Routing specifically designed for Meteor
jparker:gravatar                 0.3.0  Simple package to use gravatar images
jquery                           1.0.1  Manipulate the DOM using CSS selectors
launch-screen                    1.0.0  Default and customizable launch screen on mobile.
less                             1.0.11  The dynamic stylesheet language
meteorhacks:fast-render          1.2.1  Render initial page 2-10 times faster by sending data with HTML
meteorhacks:npm                  1.2.1  Use npm modules with your Meteor App
meteorhacks:subs-manager         1.1.0  Subscriptions Manager for Meteor
mizzao:bootboxjs                 4.3.0  Programmatic dialog boxes using Twitter's bootstrap modals
moment-timezone                  0.2.1  Timezone support for moment.js, packaged for Meteor. See http://momentjs.com/timezone.
mquandalle:jade                  0.3.0  Jade template language
mrgalaxy:stripe                  1.5.6  Stripe.js and Node-Stripe brought to Meteor.
mrt:collection-hooks             0.7.2  Extends Meteor.Collection with before/after hooks for insert/update/remove/find/findOne
mrt:jquery-ui-sortable           1.10.3  Reorder elements in a list or grid using the mouse
mrt:mask                         0.0.1  A jQuery Plugin to make masks on form fields and HTML elements.
mrt:moment-timezone              0.2.1  Timezone support for moment.js, packaged for Meteor. See http://momentjs.com/timezone.
mrt:mongodb-aggregation          0.1.71  Straightforward implementation of mongodb aggregation framework
mrt:nprogress                    0.1.0  NProgress for Meteor
mrt:numeral                      1.5.3  Package to wrap Numeral-js, a library for formatting and manipulating numbers
mrt:publish-with-relations       0.1.5  Publish associated collections at once.
mrt:spiderfork                   0.0.1  A more resilient spiderable package with better error reporting
natestrauser:font-awesome        4.2.0  Latest version Font-Awesome loaded via CDN
noorderstorm:hammer              0.1.3  A javascript library for multi-touch gestures
npm-container                    1.0.0  Contains all your npm dependencies
percolatestudio:fastclick        0.6.7  fastclick repackaged for Meteor
percolatestudio:synced-cron      1.0.0  Allows you to define and run scheduled jobs across multiple servers.
raix:handlebar-helpers           0.1.3  Handlebar helpers
service-configuration            1.0.2  Manage the configuration for third-party services
simison:bootstrap3-less          0.3.0  Bootstrap 3, with Less files.
standard-app-packages            1.0.3  Moved to meteor-platform
tsega:bootstrap3-datetimepicker  0.4.0  Bootstrap 3 DateTime picker from @Eonasdan, packaged for Meteor.js
underscore                       1.0.1  Collection of small helpers: _.map, _.each, ...
wizonesolutions:canonical        0.0.5  Require this application to use the ROOT_URL if one is set

Support for template subscriptions?

WIll this work as a like for like replacement for template subscriptions? If i use this.subscribe within my template create(), will Template.subscriptionReady api will work as expected? Thanks

fails on missing underscore dependency

Hi do I need to configure the underscore dependency in some way? I added mrt add underscore but the application still cannot start because of a refference error. _ is not defined.
when I hardcode: api.use('underscore');
in the subs-manager package.js it starts working.

Subscription manager breaks the usage of iron router hooks.

Please see following routes and comments.

var subscriptions = new SubsManager();

Router.route('/user/home', {
  name: 'restrictedHome',
  template: 'restrictedHome',
  onBeforeAction: function (pause) {
    console.log('YES!!!'); // successfully executed
  },
  waitOn: function () {
    return [
      Meteor.subscribe('adminPracticals')
    ];
  }
});

Router.route('/user/home1', {
  name: 'restrictedHome1',
  template: 'restrictedHome1',
  onBeforeAction: function (pause) {
    console.log('NO :((('); // never executed
  },
  waitOn: function () {
    return [
      subscriptions.subscribe('adminPracticals')
    ];
  }
});

subscription manager also break the global Router.onBeforeAction execution.

rendered callback does not fire when using subs manager

This is a huge issue for me and I am surprised it has not come up before.

When using this package and switching between routes, the rendered callback does not get fired anymore.

If the data is cached and you switch between routes the rendered callback for the template rendered on screen is not fired.

So Meteor is removing the template from the DOM, and when it rendered it again the rendered is not called. I have setup listeners function in the rendered function and they get removed when the template is destroyed. Since the rendered callback is not called they do not get setup again.

when, where to use "reset or clear"?

I am a new for this package.
But don't understand when, where to use "reset or clear"?

// In docs
var subs = new SubsManager(); // use in router such as `Flow Router`

// later in some other place
subs.clear()/.reset(); // Where and When??? 

I think that we can't us subs in global, because it declare with var.
Please help me.

Subscription not refreshed as it should

I have these routes:

Router.map ->
  @route "spaces",
    path: "/spaces"
    waitOn: ->
      subs.subscribe "allSpaces"

    data: ->
      spaces: Spaces.find()


  @route "buildingSpaces",
    path: "/buildings/:_id/spaces"
    waitOn: ->
      [Meteor.subscribe("buildingSpaces", @params._id),
       subs.subscribe "allBuildings"]

    data: ->
      building_id: @params._id
      building: Buildings.findOne(@params._id)
      spaces: Spaces.find()
      subTemplate:  "spacesList"

When I click the route "spaces", I get a list with all my spaces (let's say 10)

When I click the route "buildingSpaces", I should see all the spaces for a particular building.

This filter (by building) doesn't work with subscription manager. It shows all the 10 spaces instead. If I replace the subscription for the "spaces" route by Meteor.subscribe("allSpaces"), then it works correctly.

I guess that this is because all your subscriptions are cached using the name of the collection instead of using the name of the publication.

However, I still don't understand why I can't see my spaces filtered by building as this subscription is not using subs. It shouldn't used the cache subscription but it does. Any idea why?

Thank you!

Subs manager & template-level subscriptions

I've been looking at using Subs Manager with template-level subscriptions. If I understand correctly, what this package does is keep subscriptions open, and not just cache the data in Minimongo?

With template-level subscriptions, I might be opening 4-5 different subscriptions on each page. So if you navigate through 2-3 pages times, you can quickly end up with about 10 open subscriptions. I'm just wondering if that will be an issue from a performance point of view? Won't having that many extra subscriptions open add to the server load?

I don't know if it would make sense, but is there any way to cache the data in Minimongo without necessarily keeping all subscriptions open?

Manager interfering with ReactMeteorData

Hi, first thanks for this optimisation item without which I cannot imagine my applications to be. I have found a possible bug in the implementation, when subscription manager is interfering with "ReactMeteorData" mixin. I am attaching a minimal repro application.

The problem is, that if you use a component with subscriptions inside another component with subscriptions, it is invalidating the parent subscriptions, making them run twice or more. Example:

I have following components and only parent has subscriptions:

<Parent>
<Child>
</Parent>

If I put following line inside paren's "render" method console.log("With: " + this.data.posts) where data is fed with following method:

getMeteorData() {
    this.data = { }
    var handle = subs.subscribe("posts");
    if (handle.ready()) {
      this.data = {
        posts: Posts.find().fetch()
      }
    }
    return this.data;
  },

The output is following as expected:

With: undefined
With: undefined
With: [object Object],[object Object],[object Object]

Now I add another subscription inside child component as following:

  getMeteorData() {
    this.data = { }
    var handle = subs.subscribe("user", this.props.post.uid); // Replace with Meteor.subscribe and all is good
    if (handle.ready()) {
      this.data = {
        user: Usrs.findOne({uid: this.props.post.uid})
      }
    }

    return this.data;
  }

Output becomes:

With: undefined
With: undefined
With: [object Object],[object Object],[object Object]
With: undefined
With: [object Object],[object Object],[object Object]

Somewhere there, the subscription invalidated meteor data and it ran again creating havoc in the application. Please note, that when I replace subs.subscribe with Meteor.subscribe all is running as expected and data is not invalidated.

Example minimal app is here 6Kb.

How to clear all template-level subscriptions from 'onLogin' callback

Hi

I have a React component in which I make multiple subscriptions and cache them on the client. Problem is that if I log in to another user, the same subscription is still cached, resulting in the wrong data being shown.

I want to do something like SubsManager.clearAll, because I dont have access to the new SubsManager() reference in the callback.

Is this possible?

infinite loop after 10 subscribe (cacheLimit)

In my repo you will be able to subscribe through iron-router's waitOn using subs-manager.

From 1 to 10 subscribe, everything is fine.
After 10, there is an infinite loop.

https://github.com/darkship/test_SubsManager

cacheLimit is 10 by default. If you increase it you can put more but after the limit you have an infinite loop again. Shouldn't we have a warn message and prevent to add more subscriptions ?

Reset() failing to flush subscriptions

I've got an app that allows users to subscribe to posts by zip code. The app uses subscription manager to save the subscription while looking at individual posts, so that when the user jumps from the newsfeed to a single post and back, the app doesn't have to re-subscribe to the collection.

When the user switches zip codes, the entire subscription should reset, since the app will be receiving a completely different set of posts. However, when I use subs.reset() for this, the app instead shows all the posts from both the original and the changed zip code.

It appears that subs.reset() isn't flushing the existing subscriptions. Am I using it incorrectly, or is this a bug?

Random extremely slow Mongo queries

After using subs-manager for about a week, we've noticed extremely slow queries in the Mongo profiler (> 20 seconds).

db.system.profile.find({ }).limit(5).sort( { millis : -1 } )

These were generated by the Meteor app, and running a particular query again from the shell was fast. It was very hard to debug what was causing the problem, as subs-manager never was a suspect. However, removing subs-manager sped up the app by a lot, and now the slowest query takes only 2 seconds.

Unfortunately I used an expiring pastebin for the slow queries and I no longer have them, but I do remember that some were for empty selectors.

Would it be possible that subs-manager significantly slows down Mongo?

Subscriptions don't expire anymore

Subscriptions don't expire anymore. No unsub messages appear after the expired time (Note: I don't subscribe to them again). I as well tried it manually in the console with expireIn set to 1 minute.

Though it works when I clear the subs manager instance manually.

Iron Router's data function not running with SubsManager.subscribe in waitOn function

Hey Arunoda! Thanks for all your amazing work !

Just test driving your subs manager with my app, and it looks like the data function simply doesn't run when I use subsmanager in my waitOn functions. Not sure how to approach debugging, but going to stay with Meteor.subscribe for now (which is a shame, I'd love to cache!) Have you any suggestions as to where I should look?

Subscription keep all data, not only the ones related to the subscription.

I have app with a following route in iron-router:
/records/:recordId
with subscription setup up to return a record from a collection with a given id

When I navigate to the page /records/1, I have record with Id=1 available
Then, when I navigate to page /records/2 I have TWO records on client, the one with Id=1 and the one with Id=2. Is this a bug in the subscription manager, is it somehow bug in my application or is it a feature of the subscription manager?

When I use standard Meteor subscription, on a given route I have only one record available, while with subscription manager, these records stack up.

expire after stop()

Its hard to come up with a sane expireIn time if a user is looking at a page. Who knows how long they will remain looking at it?

What if expireIn only starts after stop() is called? Thus, expireIn is the amount of time we hold on to that data after it is no longer needed. Else, we run the risk of getting rid of data before we leave the page.

Pattern for updating a subscription limit argument

I have a subscription with a single limit argument. Currently, when I call subs.subscribe 'subname', newLimit, another subscription is added.

image

The old subscriptions are still there. I don't want Meteor to spend time maintaining the old, lower-limit subscriptions. Instead of adding a new subscription, I want to update the argument of the old subscription. What is the best way to do this?

Note that I also don't want to completely tear down eg 'subname', 20 before subscribing to 'subname', 40, because I don't want Meteor to do the extra work of resending the first 20 docs โ€“ I want it to just send docs 21 - 40.

Old documents are not resent?

Hey @arunoda - First of all, I'm a big fan of your packages, I use a handful of them.

So I read this in your "Why?" section:

"When you are subscribing inside a Deps.autorun computation, all the subscriptions started on the previous computation will be stopped...
...Also, this will force the Meteor server to resend data you already had in the client. It will waste your server's CPU and network bandwidth."

I ran some basic tests on the pub/sub by observing the DDP messages on the client. In the Tracker.autorun, No duplicate documents are sent. This is with a bare bones pub/sub in a Test collection. For example, If I sub all docs $near myReactiveCoordinates, the computation will be re-triggered when I move 10 feet, but the documents are mostly the same, no duplicate added messages are seen in the DDP logs.

Can you explain what you mean? I'm running meteor 1.1.0.2 and Meteor seems to be smart enough to not dupe the data.

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.