4

I'm working on a Web Application using node.js in which I'm building a partial copy of the database on the client-side to decrease the load on my server. Right now, I have a function like this (expressed as python-style pseudocode, but implemented in JavaScript):

get(table_name,primary_key):
    if primary_key in cache[table_name]:
        return cache[table_name][primary_key]
    else:
        x = get_data_from_server(table_name,primary_key) # socket.io
        return cache[table_name][primary_key] = x

While this scheme works perfectly well for caching individual rows, I'd like to extend it to support the creation of paginated tables ordered according to the primary_key, and loading additional data using the above function for only the current and possibly the adjacent pages. Now, I don't want to keep the list of primary keys on the server to be retrieved every time I need to change the page (which, for reasons beyond the scope here, will be very frequent), and keeping it on the client side, subject to real-time create/delete events from the server, doesn't seem that good an idea, even after compression (using ranges, instead of individual values).

What is the best way to calculate which items are to be displayed on a random page, minimizing the space requirements & the need for communication with the server?

4
  • the cache has a size restriction based on LRU elimination. Commented Oct 10, 2012 at 16:10
  • Predictive loading or precaching where data will be frequently invalidated doesnt sound like it will reduce the server load at all. The quicker the cache is invalidated, the less benifit there will be from using caching at all. Perhaps it is that the original problem statement isnt clear, for instance while the range of displayed records and associated keys will obviously change from page to page, the keys that are associated with each record do not normally change...the association of key to record is normally fixed....
    – JustinC
    Commented Oct 31, 2012 at 3:43
  • Additionally, the greatest value cache provides is to data that changes, but does so infrequently relative to the rest of the data, so part of the strategy will be to find the things that aren't static, but are nearly static like lookup tables.
    – JustinC
    Commented Oct 31, 2012 at 3:52
  • Assuming each page data is served in JSON format, and has a unique HTTP URI, would a simple HTTP caching server suffice? If the data updates frequently you can use etag or other form of HTTP document versioning. For more frequent changes you can use two way communication with the server (see Atmosphere javascript client for example). Commented Nov 24, 2012 at 14:26

2 Answers 2

1

Keep in mind that node is non blocking when waiting for io, not if you are processing items within your code. If you are using node to loop through or manipulate large datasets, consider offloading that work to the database or other processes.

It also sounds like you are trying to combine database logic (primary keys, rows) with application logic (user views, models) into a single caching function. Consider a dual approach of optimizing at the database layer, and the application layer:

At the database level, Look into your database usage, use EXPLAIN, examine your use of indexes, remove N+1 and other repeated database calls.

At the application level, think of your pages (especially on the initial load) as entire views instead of tables and rows. then cache all of the data needed for the most common views, if the same data is presented to every user, consider caching the entire rendered output. If using ajax calls, consider storing the initial set of cached data as json embedded within the html response. Also look at where your cache is stored, redis and memcached are popular datastores for live site data.

Ref: - NodeJS Event Loop: http://blog.mixu.net/2011/02/01/understanding-the-node-js-event-loop/ - MVVM architecture: http://addyosmani.com/blog/understanding-mvvm-a-guide-for-javascript-developers/ - Nodejs Page Caching: https://stackoverflow.com/questions/9715636/node-js-page-caching

0

If the server does the pagination isn't it already returning a small subset?

You could let the server return only an a list of primary-keys for the requested page. Materialize as many as you can from your cache, then bulk fetch the remaining identities from the server in one call.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.