Reputation: 12437
I have two databases on Cloudant, staging and production, which are being consumed by a Node.JS based web app running on Heroku, also with staging and production instances. The web app includes an admin area where admins can check on database content and tweak values etc.
What's the best approach for moving data between the two environments? Sometimes we'll want to move new values from staging to production, and perhaps other times move production data to staging to aid with testing etc., so it has to be two way.
Whole database replication is not an option since generally we'll only want to copy certain database objects, not the whole thing.
What sort of things should I be looking at to get this done in Node.JS? Any general approaches? Are we thinking about the setup wrong?
Upvotes: 3
Views: 739
Reputation: 4441
There are two ways to do this with the database itself (versus writing client code to move data around, which would not be optimal).
For an up to date reference on replication, see http://wiki.apache.org/couchdb/Replication (Apache's wiki is down at the time of writing this answer).
Named Document Replication
If you know exactly which documents you want to replicate and their _id
's, then you can specify them in an array when invoking the replication. For example, this would replicate the two docs with _id
's doc-a
and doc-b
.
{
"source": "https://USER:[email protected]/dbname-qa",
"target": "https://USER:[email protected]/dbname-production",
"doc_ids": [ "doc-a", "doc-b" ]
}
Filtered Replication
If you can programatically tell which records you want to move, then you can use filtered replication. You write a function that returns true
if you want the doc to be replicated or false
if you don't. For example...
function(doc) {
/*
* This will not replicate doc deletions. Add `&& doc._deleted` to replicate
* those as well.
*/
if(doc.type === "user") {
return true;
}
return false;
}
...would replicate all the records whose type
attribute is equal to "user"
.
You could also remove the whole if
block and just do return (doc.type === "user");
if you are comfortable with it.
This code is stored in your design document. Here is an example ddoc that stores the above function:
{
"_id": "_design/app",
"filters": {
"myfilter": "function(doc) { return (doc.type === \"user\"); }"
}
}
You then invoke the filter during replication like this:
{
"source": "https://USER:[email protected]/dbname-qa",
"target": "https://USER:[email protected]/dbname-production",
"filter": "app/myfilter"
}
Upvotes: 4