Skip to content

Commit 753b440

Browse files
committed
Fixed the cloner to not re-clone items.
1 parent b6b9f3b commit 753b440

File tree

2 files changed

+21
-3
lines changed

2 files changed

+21
-3
lines changed

commands/clone.js

+1
Original file line numberDiff line numberDiff line change
@@ -16,6 +16,7 @@ module.exports = function(program, next) {
1616
.option('-d, --dst-project <project_id>', 'The Destination project ID')
1717
.option('-p, --project <project_id>', 'The project ID that you wish to clone from one database to another.')
1818
.option('--forms <forms>', 'A comma-separated value of all the Form ID\'s you wish to clone. If included, then only the provided forms will be cloned.', false)
19+
.option('--exclude <forms>', 'A comma-separated value of all the Form ID\'s you wish to exclude in the clone process.', false)
1920
.option('-u, --update-existing', 'Update existing Projects and Forms instead of cloning (No OSS).', true)
2021
.option('--update-existing-submissions', 'Update existing Submissions when found in the destination (slows down the clone process if set).', false)
2122
.option('--src-ca <source_ca>', 'The TLS certificate authority for the source mongo url')

src/Cloner.js

+20-3
Original file line numberDiff line numberDiff line change
@@ -32,6 +32,7 @@ class Cloner {
3232
* @param {*} options.includeSubmissionRevisions - Include submission revisions when cloning submissions.
3333
* @param {*} options.updateExistingSubmissions - Update existing submissions when found in the destination (performs a complete re-clone).
3434
* @param {*} options.forms - A comma-separated value of all the Form ID's you wish to clone. If included, then only the provided forms will be cloned.
35+
* @param {*} options.exclude - A comma-separated value of all the Form ID's you wish to exclude from cloning.
3536
* @param {*} options.submissionsOnly - Only clone submissions.
3637
* @param {*} options.apiSource - Flag to define if we need to clone from an API.
3738
* @param {*} options.key - API Key to be used to authenticate in source.
@@ -48,6 +49,7 @@ class Cloner {
4849
this.src = null;
4950
this.dest = null;
5051
this.cloneState = {};
52+
this.exclude = this.options.exclude ? this.options.exclude.split(',') : [];
5153

5254
if (this.options.apiSource) {
5355
this.requestHeaders = {
@@ -230,7 +232,7 @@ class Cloner {
230232
* Determine if we should clone the given item.
231233
* @param {*} srcItem - The source item to check.
232234
*/
233-
shouldClone(collection, srcItem) {
235+
shouldClone(collection, srcItem, updatedItem) {
234236
if (this.options.submissionsOnly && collection !== 'submissions') {
235237
return false;
236238
}
@@ -243,6 +245,15 @@ class Cloner {
243245
if (this.options.modifiedAfter && srcModified < parseInt(this.options.modifiedAfter, 10)) {
244246
return false;
245247
}
248+
249+
// Make sure to not re-clone the same item it if has not been modified.
250+
// eslint-disable-next-line max-len
251+
const updatedCreated = (updatedItem.created instanceof Date) ? updatedItem.created.getTime() : parseInt(updatedItem.created, 10);
252+
// eslint-disable-next-line max-len
253+
const updatedModified = (updatedItem.modified instanceof Date) ? updatedItem.modified.getTime() : parseInt(updatedItem.modified, 10);
254+
if (srcCreated === updatedCreated && srcModified === updatedModified) {
255+
return false;
256+
}
246257
return true;
247258
}
248259

@@ -327,6 +338,10 @@ class Cloner {
327338
}
328339
}
329340

341+
if (collection === 'forms' && this.exclude.includes(srcItem._id.toString())) {
342+
return;
343+
}
344+
330345
if (eachItem) {
331346
eachItem(srcItem);
332347
}
@@ -343,7 +358,7 @@ class Cloner {
343358

344359
// Call before handler and then update if it says we should.
345360
if (
346-
this.shouldClone(collection, srcItem) &&
361+
this.shouldClone(collection, srcItem, updatedItem) &&
347362
await this.before(collection, beforeEach, srcItem, updatedItem, destItem) !== false
348363
) {
349364
if (destItem) {
@@ -872,6 +887,8 @@ class Cloner {
872887
const srcId = update.settings.role;
873888
update.settings.role = await this.getDestinationRoleId(srcId, destForm.project);
874889
}
890+
}, null, (current) => {
891+
return {$or: [{_id: current._id}, {machineName: current.machineName}]};
875892
});
876893
}
877894

@@ -886,7 +903,7 @@ class Cloner {
886903
let compsWithEncryptedData = [];
887904
await this.upsertAll('forms', this.formQuery(srcProject), (form) => {
888905
process.stdout.write('\n');
889-
process.stdout.write(`- Form: ${form.title}`);
906+
process.stdout.write(`- Form: ${form.title} (${form._id})`);
890907
}, async(src, update, dest) => {
891908
if (this.options.submissionsOnly) {
892909
return false;

0 commit comments

Comments
 (0)