Skip to content

Instantly share code, notes, and snippets.

@travist
Last active September 16, 2020 16:45
Show Gist options
  • Save travist/1e4a2084892ef94a7ee1fc8edc1996b0 to your computer and use it in GitHub Desktop.
Save travist/1e4a2084892ef94a7ee1fc8edc1996b0 to your computer and use it in GitHub Desktop.
Form.io Clone Project

This command will clone a complete Form.io Project, including forms, submissions, revisions, etc. between environments.

Usage

Download the ZIP of this Gist, then run the following inside of the extracted folder.

npm install

Once you do this, you can now clone a project by running the following command.

node clone.js --NODE_CONFIG='{
  "src": "mongodb://localhost:27017/formio",
  "dest": "mongodb://localhost:27017/formio-new",
  "project": "PROJECT_ID"
}'

You will need to provide the following parameters.

  • src - The MongoDB connection string of the source database.
  • dest - The MongoDB connection string of the destination database.
  • project - The Project ID of the project you wish to clone to the new database.
const config = require('config');
const mongodb = require('mongodb');
const async = require('async');
const _ = require('lodash');
const MongoClient = mongodb.MongoClient;
MongoClient.connect(config.src, (err, _src) => {
if (err) {
return console.log(`Could not connect to source database ${config.src}`);
}
const srcDb = _src.db(_src.s.options.dbName);
const src = {
db: srcDb,
projects: srcDb.collection('projects'),
forms: srcDb.collection('forms'),
submissions: srcDb.collection('submissions'),
roles: srcDb.collection('roles'),
actions: srcDb.collection('actions'),
formrevisions: srcDb.collection('formrevisions'),
tags: srcDb.collection('tags')
};
MongoClient.connect(config.dest, (err, _dest) => {
if (err) {
return console.log(`Could not connect to destination database ${config.src}`);
}
const destDb = _dest.db(_dest.s.options.dbName);
const dest = {
db: destDb,
projects: destDb.collection('projects'),
forms: destDb.collection('forms'),
submissions: destDb.collection('submissions'),
roles: destDb.collection('roles'),
actions: destDb.collection('actions'),
formrevisions: destDb.collection('formrevisions'),
tags: destDb.collection('tags')
};
const upsertAll = function(collection, query, each, done) {
src[collection].find(query).toArray((err, items) => {
if (err) {
console.error(`Cannot load source ${collection}`, err);
return done(err);
}
async.eachSeries(items, (item, nextItem) => {
dest[collection].update({_id: item._id}, item, {upsert: true}, (err) => {
if (err) {
console.error(`Error updating ${collection} ${item._id}`, err);
return nextItem();
}
console.log(`Upserting ${collection} - ${item._id}`);
if (each) {
each(item, nextItem);
}
else {
nextItem();
}
});
}, done);
});
};
upsertAll('projects', {_id: mongodb.ObjectID(config.project)}, (project, nextProject) => {
upsertAll('forms', {project: project._id, deleted: {$eq: null}}, (form, nextForm) => {
upsertAll('submissions', {form: form._id, deleted: {$eq: null}}, null, () => {
upsertAll('actions', {form: form._id, deleted: {$eq: null}}, null, () => nextForm());
});
}, () => {
upsertAll('roles', {project: project._id, deleted: {$eq: null}}, null, () => {
upsertAll('tags', {project: project._id, deleted: {$eq: null}}, null, () => {
upsertAll('formrevisions', {project: project._id, deleted: {$eq: null}}, null, () => nextProject());
});
});
});
}, () => {
console.log('DONE!');
});
});
});
{
"name": "formio-clone",
"version": "0.0.1",
"private": true,
"description": "",
"main": "clone.js",
"scripts": {
"test": "echo \"Error: no test specified\" && exit 1"
},
"author": "",
"license": "ISC",
"dependencies": {
"async": "^2.6.1",
"config": "^2.0.1",
"lodash": "^4.17.11",
"mongodb": "^3.1.10"
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment