diff --git a/services/web/test/unit/src/Project/ProjectEntityUpdateHandlerTests.js b/services/web/test/unit/src/Project/ProjectEntityUpdateHandlerTests.js index 28fdfc3a39..d00ca2a1e4 100644 --- a/services/web/test/unit/src/Project/ProjectEntityUpdateHandlerTests.js +++ b/services/web/test/unit/src/Project/ProjectEntityUpdateHandlerTests.js @@ -69,38 +69,50 @@ describe('ProjectEntityUpdateHandler', function () { this.callback = sinon.stub() this.DocstoreManager = { - getDoc: sinon.stub(), - isDocDeleted: sinon.stub(), - updateDoc: sinon.stub(), - deleteDoc: sinon.stub(), + promises: { + getDoc: sinon.stub(), + isDocDeleted: sinon.stub(), + updateDoc: sinon.stub(), + deleteDoc: sinon.stub(), + }, } this.DocumentUpdaterHandler = { - flushDocToMongo: sinon.stub().yields(), - flushProjectToMongo: sinon.stub().yields(), - updateProjectStructure: sinon.stub().yields(), - setDocument: sinon.stub(), - resyncProjectHistory: sinon.stub().yields(), - deleteDoc: sinon.stub().yields(), + promises: { + flushDocToMongo: sinon.stub().resolves(), + flushProjectToMongo: sinon.stub().resolves(), + updateProjectStructure: sinon.stub().resolves(), + setDocument: sinon.stub(), + resyncProjectHistory: sinon.stub().resolves(), + deleteDoc: sinon.stub().resolves(), + }, } this.fs = { - unlink: sinon.stub().yields(), + promises: { + unlink: sinon.stub().resolves(), + }, } this.LockManager = { - runWithLock: sinon.spy((namespace, id, runner, callback) => - runner(callback) - ), + promises: { + runWithLock: sinon.spy((namespace, id, runner, callback) => + runner(callback) + ), + }, withTimeout: sinon.stub().returns(this.LockManager), } this.ProjectModel = { updateOne: sinon.stub(), } this.ProjectGetter = { - getProject: sinon.stub(), - getProjectWithoutDocLines: sinon.stub(), + promises: { + getProject: sinon.stub(), + getProjectWithoutDocLines: sinon.stub(), + }, } this.ProjectLocator = { - findElement: sinon.stub(), - findElementByPath: sinon.stub(), + promises: { + findElement: sinon.stub(), + findElementByPath: sinon.stub(), + }, } this.ProjectUpdater = { promises: { @@ -108,35 +120,44 @@ describe('ProjectEntityUpdateHandler', function () { }, } this.ProjectEntityHandler = { - getDoc: sinon.stub(), - getDocPathByProjectIdAndDocId: sinon.stub(), getAllEntitiesFromProject: sinon.stub(), + promises: { + getDoc: sinon.stub(), + getDocPathByProjectIdAndDocId: sinon.stub(), + }, } this.ProjectEntityMongoUpdateHandler = { - addDoc: sinon.stub(), - addFile: sinon.stub(), - addFolder: sinon.stub(), - _confirmFolder: sinon.stub(), - _putElement: sinon.stub(), - _insertDeletedFileReference: sinon.stub(), - replaceFileWithNew: sinon.stub(), - mkdirp: sinon.stub(), - moveEntity: sinon.stub(), - renameEntity: sinon.stub().yields(), - deleteEntity: sinon.stub(), - replaceDocWithFile: sinon.stub(), - replaceFileWithDoc: sinon.stub(), + promises: { + addDoc: sinon.stub(), + addFile: sinon.stub(), + addFolder: sinon.stub(), + _confirmFolder: sinon.stub(), + _putElement: sinon.stub(), + _insertDeletedFileReference: sinon.stub(), + replaceFileWithNew: sinon.stub(), + mkdirp: sinon.stub(), + moveEntity: sinon.stub(), + renameEntity: sinon.stub().resolves({}), + deleteEntity: sinon.stub(), + replaceDocWithFile: sinon.stub(), + replaceFileWithDoc: sinon.stub(), + }, } this.TpdsUpdateSender = { - addFile: sinon.stub().yields(), - addDoc: sinon.stub(), - deleteEntity: sinon.stub().yields(), - moveEntity: sinon.stub().yields(), + promises: { + addFile: sinon.stub().resolves(), + addDoc: sinon.stub(), + deleteEntity: sinon.stub().resolves(), + moveEntity: sinon.stub().resolves(), + }, } this.FileStoreHandler = { - copyFile: sinon.stub(), - uploadFileFromDisk: sinon.stub(), - deleteFile: sinon.stub(), + promises: { + copyFile: sinon.stub(), + uploadFileFromDisk: sinon.stub(), + deleteFile: sinon.stub(), + }, + _buildUrl: sinon .stub() .callsFake( @@ -144,13 +165,15 @@ describe('ProjectEntityUpdateHandler', function () { ), } this.FileWriter = { - writeLinesToDisk: sinon.stub(), + promises: { + writeLinesToDisk: sinon.stub(), + }, } this.EditorRealTimeController = { emitToRoom: sinon.stub(), } this.ProjectOptionsHandler = { - setHistoryRangesSupport: sinon.stub().yields(), + setHistoryRangesSupport: sinon.stub().resolves(), } this.ProjectEntityUpdateHandler = SandboxedModule.require(MODULE_PATH, { requires: { @@ -189,22 +212,30 @@ describe('ProjectEntityUpdateHandler', function () { this.lastUpdatedAt = new Date().getTime() this.lastUpdatedBy = 'fake-last-updater-id' this.parentFolder = { _id: new ObjectId() } - this.DocstoreManager.isDocDeleted.yields(null, false) - this.ProjectGetter.getProject.yields(null, this.project) - this.ProjectLocator.findElement.yields( - null, - this.doc, - { + this.DocstoreManager.promises.isDocDeleted.resolves(false) + this.ProjectGetter.promises.getProject.resolves(this.project) + this.ProjectLocator.promises.findElement.resolves({ + element: this.doc, + path: { fileSystem: this.path, }, - this.parentFolder - ) - this.TpdsUpdateSender.addDoc.yields() + folder: this.parentFolder, + }) + this.TpdsUpdateSender.promises.addDoc.resolves() }) describe('when the doc has been modified', function () { - beforeEach(function () { - this.DocstoreManager.updateDoc.yields(null, true, (this.rev = 5)) + beforeEach(function (done) { + this.DocstoreManager.promises.updateDoc.resolves({ + modified: true, + rev: (this.rev = 5), + }) + + const callback = (...args) => { + this.callback(...args) + done() + } + this.ProjectEntityUpdateHandler.updateDocLines( projectId, docId, @@ -213,12 +244,12 @@ describe('ProjectEntityUpdateHandler', function () { this.ranges, this.lastUpdatedAt, this.lastUpdatedBy, - this.callback + callback ) }) it('should get the project with very few fields', function () { - this.ProjectGetter.getProject + this.ProjectGetter.promises.getProject .calledWith(projectId, { name: true, rootFolder: true, @@ -227,7 +258,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should find the doc', function () { - this.ProjectLocator.findElement + this.ProjectLocator.promises.findElement .calledWith({ project: this.project, type: 'docs', @@ -237,7 +268,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should update the doc in the docstore', function () { - this.DocstoreManager.updateDoc + this.DocstoreManager.promises.updateDoc .calledWith( projectId, docId, @@ -258,7 +289,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should send the doc the to the TPDS', function () { - this.TpdsUpdateSender.addDoc.should.have.been.calledWith({ + this.TpdsUpdateSender.promises.addDoc.should.have.been.calledWith({ projectId, projectName: this.project.name, docId, @@ -274,8 +305,17 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('when the doc has not been modified', function () { - beforeEach(function () { - this.DocstoreManager.updateDoc.yields(null, false, (this.rev = 5)) + beforeEach(function (done) { + this.DocstoreManager.promises.updateDoc.resolves({ + modified: false, + rev: (this.rev = 5), + }) + + const callback = () => { + this.callback() + done() + } + this.ProjectEntityUpdateHandler.updateDocLines( projectId, docId, @@ -284,7 +324,7 @@ describe('ProjectEntityUpdateHandler', function () { this.ranges, this.lastUpdatedAt, this.lastUpdatedBy, - this.callback + callback ) }) @@ -293,7 +333,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should not send the doc the to the TPDS', function () { - this.TpdsUpdateSender.addDoc.called.should.equal(false) + this.TpdsUpdateSender.promises.addDoc.called.should.equal(false) }) it('should call the callback', function () { @@ -302,11 +342,14 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('when the doc has been deleted', function () { - beforeEach(function () { - this.ProjectGetter.getProject.yields(null, this.project) - this.ProjectLocator.findElement.yields(new Errors.NotFoundError()) - this.DocstoreManager.isDocDeleted.yields(null, true) - this.DocstoreManager.updateDoc.yields() + beforeEach(function (done) { + this.ProjectGetter.promises.getProject.resolves(this.project) + this.ProjectLocator.promises.findElement.rejects( + new Errors.NotFoundError() + ) + this.DocstoreManager.promises.isDocDeleted.resolves(true) + this.DocstoreManager.promises.updateDoc.resolves() + this.ProjectEntityUpdateHandler.updateDocLines( projectId, docId, @@ -315,12 +358,15 @@ describe('ProjectEntityUpdateHandler', function () { this.ranges, this.lastUpdatedAt, this.lastUpdatedBy, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('should update the doc in the docstore', function () { - this.DocstoreManager.updateDoc + this.DocstoreManager.promises.updateDoc .calledWith( projectId, docId, @@ -336,7 +382,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should not send the doc the to the TPDS', function () { - this.TpdsUpdateSender.addDoc.called.should.equal(false) + this.TpdsUpdateSender.promises.addDoc.called.should.equal(false) }) it('should call the callback', function () { @@ -345,15 +391,22 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('when projects and docs collection are de-synced', function () { - beforeEach(function () { - this.ProjectGetter.getProject.yields(null, this.project) + beforeEach(function (done) { + this.ProjectGetter.promises.getProject.resolves(this.project) // The doc is not in the file-tree, but also not marked as deleted. // This should not happen, but web should handle it. - this.ProjectLocator.findElement.yields(new Errors.NotFoundError()) - this.DocstoreManager.isDocDeleted.yields(null, false) + this.ProjectLocator.promises.findElement.rejects( + new Errors.NotFoundError() + ) + this.DocstoreManager.promises.isDocDeleted.resolves(false) + + this.DocstoreManager.promises.updateDoc.resolves() + const callback = (...args) => { + this.callback(...args) + done() + } - this.DocstoreManager.updateDoc.yields() this.ProjectEntityUpdateHandler.updateDocLines( projectId, docId, @@ -362,12 +415,12 @@ describe('ProjectEntityUpdateHandler', function () { this.ranges, this.lastUpdatedAt, this.lastUpdatedBy, - this.callback + callback ) }) it('should update the doc in the docstore', function () { - this.DocstoreManager.updateDoc + this.DocstoreManager.promises.updateDoc .calledWith( projectId, docId, @@ -383,7 +436,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should not send the doc the to the TPDS', function () { - this.TpdsUpdateSender.addDoc.called.should.equal(false) + this.TpdsUpdateSender.promises.addDoc.called.should.equal(false) }) it('should call the callback', function () { @@ -392,10 +445,19 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('when the doc is not related to the project', function () { - beforeEach(function () { - this.ProjectGetter.getProject.yields(null, this.project) - this.ProjectLocator.findElement.yields(new Errors.NotFoundError()) - this.DocstoreManager.isDocDeleted.yields(new Errors.NotFoundError()) + beforeEach(function (done) { + this.ProjectGetter.promises.getProject.resolves(this.project) + this.ProjectLocator.promises.findElement.rejects( + new Errors.NotFoundError() + ) + this.DocstoreManager.promises.isDocDeleted.rejects( + new Errors.NotFoundError() + ) + const callback = (...args) => { + this.callback(...args) + done() + } + this.ProjectEntityUpdateHandler.updateDocLines( projectId, docId, @@ -404,7 +466,7 @@ describe('ProjectEntityUpdateHandler', function () { this.ranges, this.lastUpdatedAt, this.lastUpdatedBy, - this.callback + callback ) }) @@ -415,17 +477,19 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should not update the doc', function () { - this.DocstoreManager.updateDoc.called.should.equal(false) + this.DocstoreManager.promises.updateDoc.called.should.equal(false) }) it('should not send the doc the to the TPDS', function () { - this.TpdsUpdateSender.addDoc.called.should.equal(false) + this.TpdsUpdateSender.promises.addDoc.called.should.equal(false) }) }) describe('when the project is not found', function () { - beforeEach(function () { - this.ProjectGetter.getProject.yields(new Errors.NotFoundError()) + beforeEach(function (done) { + this.ProjectGetter.promises.getProject.rejects( + new Errors.NotFoundError() + ) this.ProjectEntityUpdateHandler.updateDocLines( projectId, docId, @@ -434,7 +498,10 @@ describe('ProjectEntityUpdateHandler', function () { this.ranges, this.lastUpdatedAt, this.lastUpdatedBy, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -445,11 +512,11 @@ describe('ProjectEntityUpdateHandler', function () { }) it('should not update the doc', function () { - this.DocstoreManager.updateDoc.called.should.equal(false) + this.DocstoreManager.promises.updateDoc.called.should.equal(false) }) it('should not send the doc the to the TPDS', function () { - this.TpdsUpdateSender.addDoc.called.should.equal(false) + this.TpdsUpdateSender.promises.addDoc.called.should.equal(false) }) }) }) @@ -459,66 +526,69 @@ describe('ProjectEntityUpdateHandler', function () { this.rootDocId = 'root-doc-id-123123' }) - it('should call Project.updateOne when the doc exists and has a valid extension', function () { - this.ProjectEntityHandler.getDocPathByProjectIdAndDocId.yields( - null, + it('should call Project.updateOne when the doc exists and has a valid extension', function (done) { + this.ProjectEntityHandler.promises.getDocPathByProjectIdAndDocId.resolves( `/main.tex` ) this.ProjectEntityUpdateHandler.setRootDoc( projectId, this.rootDocId, - () => {} + () => { + this.ProjectModel.updateOne + .calledWith({ _id: projectId }, { rootDoc_id: this.rootDocId }) + .should.equal(true) + done() + } ) - this.ProjectModel.updateOne - .calledWith({ _id: projectId }, { rootDoc_id: this.rootDocId }) - .should.equal(true) }) - it("should not call Project.updateOne when the doc doesn't exist", function () { - this.ProjectEntityHandler.getDocPathByProjectIdAndDocId.yields( + it("should not call Project.updateOne when the doc doesn't exist", function (done) { + this.ProjectEntityHandler.promises.getDocPathByProjectIdAndDocId.rejects( Errors.NotFoundError ) this.ProjectEntityUpdateHandler.setRootDoc( projectId, this.rootDocId, - () => {} + () => { + this.ProjectModel.updateOne + .calledWith({ _id: projectId }, { rootDoc_id: this.rootDocId }) + .should.equal(false) + done() + } ) - this.ProjectModel.updateOne - .calledWith({ _id: projectId }, { rootDoc_id: this.rootDocId }) - .should.equal(false) }) it('should call the callback with an UnsupportedFileTypeError when the doc has an unaccepted file extension', function () { - this.ProjectEntityHandler.getDocPathByProjectIdAndDocId.yields( - null, + this.ProjectEntityHandler.promises.getDocPathByProjectIdAndDocId.resolves( `/foo/bar.baz` ) this.ProjectEntityUpdateHandler.setRootDoc( projectId, this.rootDocId, - this.callback - ) - expect(this.callback.firstCall.args[0]).to.be.an.instanceof( - Errors.UnsupportedFileTypeError + error => { + expect(error).to.be.an.instanceof(Errors.UnsupportedFileTypeError) + } ) }) }) describe('unsetRootDoc', function () { - it('should call Project.updateOne', function () { - this.ProjectEntityUpdateHandler.unsetRootDoc(projectId) - this.ProjectModel.updateOne - .calledWith({ _id: projectId }, { $unset: { rootDoc_id: true } }) - .should.equal(true) + it('should call Project.updateOne', function (done) { + this.ProjectEntityUpdateHandler.unsetRootDoc(projectId, () => { + this.ProjectModel.updateOne + .calledWith({ _id: projectId }, { $unset: { rootDoc_id: true } }) + .should.equal(true) + done() + }) }) }) describe('addDoc', function () { describe('adding a doc', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/path/to/doc' this.rev = 5 @@ -528,13 +598,15 @@ describe('ProjectEntityUpdateHandler', function () { _id: docId, rev: this.rev, }) - this.DocstoreManager.updateDoc.yields(null, false, this.rev) - this.TpdsUpdateSender.addDoc.yields() - this.ProjectEntityMongoUpdateHandler.addDoc.yields( - null, - { path: { fileSystem: this.path } }, - this.project - ) + this.DocstoreManager.promises.updateDoc.resolves({ + lines: false, + rev: this.rev, + }) + this.TpdsUpdateSender.promises.addDoc.resolves() + this.ProjectEntityMongoUpdateHandler.promises.addDoc.resolves({ + result: { path: { fileSystem: this.path } }, + project: this.project, + }) this.ProjectEntityUpdateHandler.addDoc( projectId, docId, @@ -542,12 +614,15 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('creates the doc without history', function () { - this.DocstoreManager.updateDoc + this.DocstoreManager.promises.updateDoc .calledWith(projectId, docId, this.docLines, 0, {}) .should.equal(true) }) @@ -561,7 +636,7 @@ describe('ProjectEntityUpdateHandler', function () { ranges: {}, }, ] - this.DocumentUpdaterHandler.updateProjectStructure.should.have.been.calledWith( + this.DocumentUpdaterHandler.promises.updateProjectStructure.should.have.been.calledWith( projectId, projectHistoryId, userId, @@ -575,7 +650,7 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('adding a doc with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/path/to/doc' this.newDoc = { _id: docId } @@ -586,7 +661,10 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -599,7 +677,7 @@ describe('ProjectEntityUpdateHandler', function () { describe('addFile', function () { describe('adding a file', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/path/to/file' this.newFile = { @@ -608,17 +686,15 @@ describe('ProjectEntityUpdateHandler', function () { name: this.fileName, linkedFileData: this.linkedFileData, } - this.FileStoreHandler.uploadFileFromDisk.yields( - null, - this.fileUrl, - this.newFile - ) - this.TpdsUpdateSender.addFile.yields() - this.ProjectEntityMongoUpdateHandler.addFile.yields( - null, - { path: { fileSystem: this.path } }, - this.project - ) + this.FileStoreHandler.promises.uploadFileFromDisk.resolves({ + url: this.fileUrl, + fileRef: this.newFile, + }) + this.TpdsUpdateSender.promises.addFile.resolves() + this.ProjectEntityMongoUpdateHandler.promises.addFile.resolves({ + result: { path: { fileSystem: this.path } }, + project: this.project, + }) this.ProjectEntityUpdateHandler.addFile( projectId, folderId, @@ -627,12 +703,15 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('updates the file in the filestore', function () { - this.FileStoreHandler.uploadFileFromDisk + this.FileStoreHandler.promises.uploadFileFromDisk .calledWith( projectId, { name: this.fileName, linkedFileData: this.linkedFileData }, @@ -646,13 +725,13 @@ describe('ProjectEntityUpdateHandler', function () { return file.name === this.fileName }) - this.ProjectEntityMongoUpdateHandler.addFile + this.ProjectEntityMongoUpdateHandler.promises.addFile .calledWithMatch(projectId, folderId, fileMatcher) .should.equal(true) }) it('notifies the tpds', function () { - this.TpdsUpdateSender.addFile + this.TpdsUpdateSender.promises.addFile .calledWith({ projectId, projectName: this.project.name, @@ -679,23 +758,21 @@ describe('ProjectEntityUpdateHandler', function () { url: this.fileUrl, }, ] - this.DocumentUpdaterHandler.updateProjectStructure - .calledWith( - projectId, - projectHistoryId, - userId, - { - newFiles, - newProject: this.project, - }, - this.source - ) - .should.equal(true) + this.DocumentUpdaterHandler.promises.updateProjectStructure.should.have.been.calledWith( + projectId, + projectHistoryId, + userId, + { + newFiles, + newProject: this.project, + }, + this.source + ) }) }) describe('adding a file with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/path/to/file' this.newFile = { @@ -704,12 +781,11 @@ describe('ProjectEntityUpdateHandler', function () { name: this.fileName, linkedFileData: this.linkedFileData, } - this.TpdsUpdateSender.addFile.yields() - this.ProjectEntityMongoUpdateHandler.addFile.yields( - null, - { path: { fileSystem: this.path } }, - this.project - ) + this.TpdsUpdateSender.promises.addFile.resolves() + this.ProjectEntityMongoUpdateHandler.promises.addFile.resolves({ + result: { path: { fileSystem: this.path } }, + project: this.project, + }) this.ProjectEntityUpdateHandler.addFile( projectId, folderId, @@ -718,7 +794,10 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -731,8 +810,8 @@ describe('ProjectEntityUpdateHandler', function () { describe('upsertDoc', function () { describe('upserting into an invalid folder', function () { - beforeEach(function () { - this.ProjectLocator.findElement.yields() + beforeEach(function (done) { + this.ProjectLocator.promises.findElement.resolves({ element: null }) this.ProjectEntityUpdateHandler.upsertDoc( projectId, folderId, @@ -740,7 +819,10 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -751,7 +833,7 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('updating an existing doc', function () { - beforeEach(function () { + beforeEach(function (done) { this.existingDoc = { _id: docId, name: this.docName } this.existingFile = { _id: fileId, name: this.fileName } this.folder = { @@ -759,8 +841,10 @@ describe('ProjectEntityUpdateHandler', function () { docs: [this.existingDoc], fileRefs: [this.existingFile], } - this.ProjectLocator.findElement.yields(null, this.folder) - this.DocumentUpdaterHandler.setDocument.yields() + this.ProjectLocator.promises.findElement.resolves({ + element: this.folder, + }) + this.DocumentUpdaterHandler.promises.setDocument.resolves() this.ProjectEntityUpdateHandler.upsertDoc( projectId, @@ -769,12 +853,15 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('tries to find the folder', function () { - this.ProjectLocator.findElement + this.ProjectLocator.promises.findElement .calledWith({ project_id: projectId, element_id: folderId, @@ -784,7 +871,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('updates the doc contents', function () { - this.DocumentUpdaterHandler.setDocument + this.DocumentUpdaterHandler.promises.setDocument .calledWith( projectId, this.existingDoc._id, @@ -801,12 +888,14 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('creating a new doc', function () { - beforeEach(function () { + beforeEach(function (done) { this.folder = { _id: folderId, docs: [], fileRefs: [] } this.newDoc = { _id: docId } - this.ProjectLocator.findElement.yields(null, this.folder) - this.ProjectEntityUpdateHandler.addDocWithRanges = { - withoutLock: sinon.stub().yields(null, this.newDoc), + this.ProjectLocator.promises.findElement.resolves({ + element: this.folder, + }) + this.ProjectEntityUpdateHandler.promises.addDocWithRanges = { + withoutLock: sinon.stub().resolves({ doc: this.newDoc }), } this.ProjectEntityUpdateHandler.upsertDoc( @@ -816,12 +905,15 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('tries to find the folder', function () { - this.ProjectLocator.findElement + this.ProjectLocator.promises.findElement .calledWith({ project_id: projectId, element_id: folderId, @@ -831,17 +923,15 @@ describe('ProjectEntityUpdateHandler', function () { }) it('adds the doc', function () { - this.ProjectEntityUpdateHandler.addDocWithRanges.withoutLock - .calledWith( - projectId, - folderId, - this.docName, - this.docLines, - {}, - userId, - this.source - ) - .should.equal(true) + this.ProjectEntityUpdateHandler.promises.addDocWithRanges.withoutLock.should.have.been.calledWith( + projectId, + folderId, + this.docName, + this.docLines, + {}, + userId, + this.source + ) }) it('returns the doc', function () { @@ -850,12 +940,14 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('upserting a new doc with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.folder = { _id: folderId, docs: [], fileRefs: [] } this.newDoc = { _id: docId } - this.ProjectLocator.findElement.yields(null, this.folder) - this.ProjectEntityUpdateHandler.addDocWithRanges = { - withoutLock: sinon.stub().yields(null, this.newDoc), + this.ProjectLocator.promises.findElement.resolves({ + element: this.folder, + }) + this.ProjectEntityUpdateHandler.promises.addDocWithRanges = { + withoutLock: sinon.stub().resolves({ doc: this.newDoc }), } this.ProjectEntityUpdateHandler.upsertDoc( @@ -865,7 +957,10 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -876,7 +971,7 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('upserting a doc on top of a file', function () { - beforeEach(function () { + beforeEach(function (done) { this.newProject = { name: 'new project', overleaf: { history: { id: projectHistoryId } }, @@ -887,21 +982,23 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines = ['line one', 'line two'] this.folderPath = '/path/to/folder' this.filePath = '/path/to/folder/foo.tex' - this.ProjectLocator.findElement + this.ProjectLocator.promises.findElement .withArgs({ project_id: projectId, element_id: this.folder._id, type: 'folder', }) - .yields(null, this.folder, { - fileSystem: this.folderPath, + .resolves({ + element: this.folder, + path: { + fileSystem: this.folderPath, + }, }) - this.DocstoreManager.updateDoc.yields() - this.ProjectEntityMongoUpdateHandler.replaceFileWithDoc.yields( - null, + this.DocstoreManager.promises.updateDoc.resolves({ rev: null }) + this.ProjectEntityMongoUpdateHandler.promises.replaceFileWithDoc.resolves( this.newProject ) - this.TpdsUpdateSender.addDoc.yields() + this.TpdsUpdateSender.promises.addDoc.resolves() this.ProjectEntityUpdateHandler.upsertDoc( projectId, @@ -910,12 +1007,15 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('notifies docstore of the new doc', function () { - expect(this.DocstoreManager.updateDoc).to.have.been.calledWith( + expect(this.DocstoreManager.promises.updateDoc).to.have.been.calledWith( projectId, this.newDoc._id, this.docLines @@ -924,7 +1024,7 @@ describe('ProjectEntityUpdateHandler', function () { it('adds the new doc and removes the file in one go', function () { expect( - this.ProjectEntityMongoUpdateHandler.replaceFileWithDoc + this.ProjectEntityMongoUpdateHandler.promises.replaceFileWithDoc ).to.have.been.calledWithMatch( projectId, this.existingFile._id, @@ -933,7 +1033,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('sends the doc to TPDS', function () { - expect(this.TpdsUpdateSender.addDoc).to.have.been.calledWith({ + expect(this.TpdsUpdateSender.promises.addDoc).to.have.been.calledWith({ projectId, docId: this.newDoc._id, path: this.filePath, @@ -958,7 +1058,7 @@ describe('ProjectEntityUpdateHandler', function () { }, ] expect( - this.DocumentUpdaterHandler.updateProjectStructure + this.DocumentUpdaterHandler.promises.updateProjectStructure ).to.have.been.calledWith( projectId, projectHistoryId, @@ -987,16 +1087,15 @@ describe('ProjectEntityUpdateHandler', function () { describe('upsertFile', function () { beforeEach(function () { - this.FileStoreHandler.uploadFileFromDisk.yields( - null, - this.fileUrl, - this.file - ) + this.FileStoreHandler.promises.uploadFileFromDisk.resolves({ + url: this.fileUrl, + fileRef: this.file, + }) }) describe('upserting into an invalid folder', function () { - beforeEach(function () { - this.ProjectLocator.findElement.yields() + beforeEach(function (done) { + this.ProjectLocator.promises.findElement.resolves({ element: null }) this.ProjectEntityUpdateHandler.upsertFile( projectId, folderId, @@ -1005,7 +1104,10 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1016,19 +1118,22 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('updating an existing file', function () { - beforeEach(function () { + beforeEach(function (done) { this.existingFile = { _id: fileId, name: this.fileName, rev: 1 } this.newFile = { _id: new ObjectId(), name: this.fileName, rev: 3 } this.folder = { _id: folderId, fileRefs: [this.existingFile], docs: [] } - this.ProjectLocator.findElement.yields(null, this.folder) + this.ProjectLocator.promises.findElement.resolves({ + element: this.folder, + }) this.newProject = 'new-project-stub' - this.ProjectEntityMongoUpdateHandler.replaceFileWithNew.yields( - null, - this.existingFile, - this.project, - { fileSystem: this.fileSystemPath }, - this.newProject, - this.newFile + this.ProjectEntityMongoUpdateHandler.promises.replaceFileWithNew.resolves( + { + oldFileRef: this.existingFile, + project: this.project, + path: { fileSystem: this.fileSystemPath }, + newProject: this.newProject, + newFileRef: this.newFile, + } ) this.ProjectEntityUpdateHandler.upsertFile( projectId, @@ -1038,12 +1143,15 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('uploads a new version of the file', function () { - this.FileStoreHandler.uploadFileFromDisk.should.have.been.calledWith( + this.FileStoreHandler.promises.uploadFileFromDisk.should.have.been.calledWith( projectId, { name: this.fileName, @@ -1054,7 +1162,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('replaces the file in mongo', function () { - this.ProjectEntityMongoUpdateHandler.replaceFileWithNew.should.have.been.calledWith( + this.ProjectEntityMongoUpdateHandler.promises.replaceFileWithNew.should.have.been.calledWith( projectId, this.existingFile._id, this.file @@ -1062,7 +1170,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('notifies the tpds', function () { - this.TpdsUpdateSender.addFile.should.have.been.calledWith({ + this.TpdsUpdateSender.promises.addFile.should.have.been.calledWith({ projectId, projectName: this.project.name, fileId: this.newFile._id, @@ -1093,7 +1201,7 @@ describe('ProjectEntityUpdateHandler', function () { url: this.fileUrl, }, ] - this.DocumentUpdaterHandler.updateProjectStructure.should.have.been.calledWith( + this.DocumentUpdaterHandler.promises.updateProjectStructure.should.have.been.calledWith( projectId, projectHistoryId, userId, @@ -1112,17 +1220,18 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('creating a new file', function () { - beforeEach(function () { + beforeEach(function (done) { this.folder = { _id: folderId, fileRefs: [], docs: [] } this.newFile = { _id: fileId } - this.ProjectLocator.findElement.yields(null, this.folder) - this.FileStoreHandler.uploadFileFromDisk.yields( - null, - this.fileUrl, - this.newFile - ) - this.ProjectEntityUpdateHandler.addFile = { - mainTask: sinon.stub().yields(null, this.newFile), + this.ProjectLocator.promises.findElement.resolves({ + element: this.folder, + }) + this.FileStoreHandler.promises.uploadFileFromDisk.resolves({ + url: this.fileUrl, + fileRef: this.newFile, + }) + this.ProjectEntityUpdateHandler.promises.addFile = { + mainTask: sinon.stub().resolves(this.newFile), } this.ProjectEntityUpdateHandler.upsertFile( @@ -1133,34 +1242,32 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('tries to find the folder', function () { - this.ProjectLocator.findElement - .calledWith({ - project_id: projectId, - element_id: folderId, - type: 'folder', - }) - .should.equal(true) + this.ProjectLocator.promises.findElement.should.have.been.calledWith({ + project_id: projectId, + element_id: folderId, + type: 'folder', + }) }) it('adds the file', function () { expect( - this.ProjectEntityUpdateHandler.addFile.mainTask - ).to.have.been.calledWith( + this.ProjectEntityUpdateHandler.promises.addFile.mainTask + ).to.have.been.calledWith({ projectId, folderId, - this.fileName, - this.fileSystemPath, - this.linkedFileData, userId, - this.newFile, - this.fileUrl, - this.source - ) + fileRef: this.newFile, + fileStoreUrl: this.fileUrl, + source: this.source, + }) }) it('returns the file', function () { @@ -1169,12 +1276,14 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('upserting a new file with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.folder = { _id: folderId, fileRefs: [] } this.newFile = { _id: fileId } - this.ProjectLocator.findElement.yields(null, this.folder) - this.ProjectEntityUpdateHandler.addFile = { - mainTask: sinon.stub().yields(null, this.newFile), + this.ProjectLocator.promises.findElement.resolves({ + element: this.folder, + }) + this.ProjectEntityUpdateHandler.promises.addFile = { + mainTask: sinon.stub().resolves(this.newFile), } this.ProjectEntityUpdateHandler.upsertFile( @@ -1185,7 +1294,10 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1204,25 +1316,24 @@ describe('ProjectEntityUpdateHandler', function () { fileRefs: [], docs: [this.existingDoc], } - this.ProjectLocator.findElement + this.ProjectLocator.promises.findElement .withArgs({ project_id: this.project._id.toString(), element_id: folderId, type: 'folder', }) - .yields(null, this.folder) - this.ProjectLocator.findElement + .resolves({ element: this.folder }) + this.ProjectLocator.promises.findElement .withArgs({ project_id: this.project._id.toString(), element_id: this.existingDoc._id, type: 'doc', }) - .yields( - null, - this.existingDoc, - { fileSystem: this.path }, - this.folder - ) + .resolves({ + element: this.existingDoc, + path: { fileSystem: this.path }, + folder: this.folder, + }) this.newFileUrl = 'new-file-url' this.newFile = { @@ -1235,13 +1346,11 @@ describe('ProjectEntityUpdateHandler', function () { name: 'new project', overleaf: { history: { id: projectHistoryId } }, } - this.FileStoreHandler.uploadFileFromDisk.yields( - null, - this.newFileUrl, - this.newFile - ) - this.ProjectEntityMongoUpdateHandler.replaceDocWithFile.yields( - null, + this.FileStoreHandler.promises.uploadFileFromDisk.resolves({ + url: this.newFileUrl, + fileRef: this.newFile, + }) + this.ProjectEntityMongoUpdateHandler.promises.replaceDocWithFile.resolves( this.newProject ) @@ -1259,7 +1368,7 @@ describe('ProjectEntityUpdateHandler', function () { it('replaces the existing doc with a file', function () { expect( - this.ProjectEntityMongoUpdateHandler.replaceDocWithFile + this.ProjectEntityMongoUpdateHandler.promises.replaceDocWithFile ).to.have.been.calledWith(projectId, this.existingDoc._id, this.newFile) }) @@ -1283,7 +1392,7 @@ describe('ProjectEntityUpdateHandler', function () { newProject: this.newProject, } expect( - this.DocumentUpdaterHandler.updateProjectStructure + this.DocumentUpdaterHandler.promises.updateProjectStructure ).to.have.been.calledWith( projectId, projectHistoryId, @@ -1308,17 +1417,21 @@ describe('ProjectEntityUpdateHandler', function () { describe('upsertDocWithPath', function () { describe('upserting a doc', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/folder/doc.tex' this.newFolders = ['mock-a', 'mock-b'] this.folder = { _id: folderId } this.doc = { _id: docId } this.isNewDoc = true - this.ProjectEntityUpdateHandler.mkdirp = { - withoutLock: sinon.stub().yields(null, this.newFolders, this.folder), + this.ProjectEntityUpdateHandler.promises.mkdirp = { + withoutLock: sinon + .stub() + .resolves({ newFolders: this.newFolders, folder: this.folder }), } - this.ProjectEntityUpdateHandler.upsertDoc = { - withoutLock: sinon.stub().yields(null, this.doc, this.isNewDoc), + this.ProjectEntityUpdateHandler.promises.upsertDoc = { + withoutLock: sinon + .stub() + .resolves({ doc: this.doc, isNew: this.isNewDoc }), } this.ProjectEntityUpdateHandler.upsertDocWithPath( @@ -1327,18 +1440,21 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('creates any necessary folders', function () { - this.ProjectEntityUpdateHandler.mkdirp.withoutLock + this.ProjectEntityUpdateHandler.promises.mkdirp.withoutLock .calledWith(projectId, '/folder') .should.equal(true) }) it('upserts the doc', function () { - this.ProjectEntityUpdateHandler.upsertDoc.withoutLock + this.ProjectEntityUpdateHandler.promises.upsertDoc.withoutLock .calledWith( projectId, this.folder._id, @@ -1364,17 +1480,21 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('upserting a doc with an invalid path', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/*folder/doc.tex' this.newFolders = ['mock-a', 'mock-b'] this.folder = { _id: folderId } this.doc = { _id: docId } this.isNewDoc = true - this.ProjectEntityUpdateHandler.mkdirp = { - withoutLock: sinon.stub().yields(null, this.newFolders, this.folder), + this.ProjectEntityUpdateHandler.promises.mkdirp = { + withoutLock: sinon + .stub() + .resolves({ newFolders: this.newFolders, folder: this.folder }), } - this.ProjectEntityUpdateHandler.upsertDoc = { - withoutLock: sinon.stub().yields(null, this.doc, this.isNewDoc), + this.ProjectEntityUpdateHandler.promises.upsertDoc = { + withoutLock: sinon + .stub() + .resolves({ doc: this.doc, isNew: this.isNewDoc }), } this.ProjectEntityUpdateHandler.upsertDocWithPath( @@ -1383,7 +1503,10 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1394,17 +1517,21 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('upserting a doc with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/folder/*doc.tex' this.newFolders = ['mock-a', 'mock-b'] this.folder = { _id: folderId } this.doc = { _id: docId } this.isNewDoc = true - this.ProjectEntityUpdateHandler.mkdirp = { - withoutLock: sinon.stub().yields(null, this.newFolders, this.folder), + this.ProjectEntityUpdateHandler.promises.mkdirp = { + withoutLock: sinon + .stub() + .resolves({ newFolders: this.newFolders, folder: this.folder }), } - this.ProjectEntityUpdateHandler.upsertDoc = { - withoutLock: sinon.stub().yields(null, this.doc, this.isNewDoc), + this.ProjectEntityUpdateHandler.promises.upsertDoc = { + withoutLock: sinon + .stub() + .resolves({ doc: this.doc, isNew: this.isNewDoc }), } this.ProjectEntityUpdateHandler.upsertDocWithPath( @@ -1413,7 +1540,10 @@ describe('ProjectEntityUpdateHandler', function () { this.docLines, this.source, userId, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1426,22 +1556,25 @@ describe('ProjectEntityUpdateHandler', function () { describe('upsertFileWithPath', function () { describe('upserting a file', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/folder/file.png' this.newFolders = ['mock-a', 'mock-b'] this.folder = { _id: folderId } this.file = { _id: fileId } this.isNewFile = true - this.FileStoreHandler.uploadFileFromDisk.yields( - null, - this.fileUrl, - this.newFile - ) - this.ProjectEntityUpdateHandler.mkdirp = { - withoutLock: sinon.stub().yields(null, this.newFolders, this.folder), + this.FileStoreHandler.promises.uploadFileFromDisk.resolves({ + url: this.fileUrl, + fileRef: this.newFile, + }) + this.ProjectEntityUpdateHandler.promises.mkdirp = { + withoutLock: sinon + .stub() + .resolves({ newFolders: this.newFolders, folder: this.folder }), } - this.ProjectEntityUpdateHandler.upsertFile = { - mainTask: sinon.stub().yields(null, this.file, this.isNewFile), + this.ProjectEntityUpdateHandler.promises.upsertFile = { + mainTask: sinon + .stub() + .resolves({ fileRef: this.file, isNew: this.isNewFile }), } this.ProjectEntityUpdateHandler.upsertFileWithPath( @@ -1451,58 +1584,63 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('creates any necessary folders', function () { - this.ProjectEntityUpdateHandler.mkdirp.withoutLock + this.ProjectEntityUpdateHandler.promises.mkdirp.withoutLock .calledWith(projectId, '/folder') .should.equal(true) }) it('upserts the file', function () { - this.ProjectEntityUpdateHandler.upsertFile.mainTask - .calledWith( + this.ProjectEntityUpdateHandler.promises.upsertFile.mainTask.should.have.been.calledWith( + { projectId, - this.folder._id, - 'file.png', - this.fileSystemPath, - this.linkedFileData, + folderId: this.folder._id, + fileName: 'file.png', + fsPath: this.fileSystemPath, + linkedFileData: this.linkedFileData, userId, - this.newFile, - this.fileUrl, - this.source - ) - .should.equal(true) + fileRef: this.newFile, + fileStoreUrl: this.fileUrl, + source: this.source, + } + ) }) it('calls the callback', function () { - this.callback - .calledWith( - null, - this.file, - this.isNewFile, - undefined, - this.newFolders, - this.folder - ) - .should.equal(true) + this.callback.should.have.been.calledWith( + null, + this.file, + this.isNewFile, + undefined, + this.newFolders, + this.folder + ) }) }) describe('upserting a file with an invalid path', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/*folder/file.png' this.newFolders = ['mock-a', 'mock-b'] this.folder = { _id: folderId } this.file = { _id: fileId } this.isNewFile = true - this.ProjectEntityUpdateHandler.mkdirp = { - withoutLock: sinon.stub().yields(null, this.newFolders, this.folder), + this.ProjectEntityUpdateHandler.promises.mkdirp = { + withoutLock: sinon + .stub() + .resolves({ newFolders: this.newFolders, folder: this.folder }), } - this.ProjectEntityUpdateHandler.upsertFile = { - mainTask: sinon.stub().yields(null, this.file, this.isNewFile), + this.ProjectEntityUpdateHandler.promises.upsertFile = { + mainTask: sinon + .stub() + .resolves({ doc: this.file, isNew: this.isNewFile }), } this.ProjectEntityUpdateHandler.upsertFileWithPath( @@ -1512,7 +1650,10 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1523,17 +1664,21 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('upserting a file with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/folder/*file.png' this.newFolders = ['mock-a', 'mock-b'] this.folder = { _id: folderId } this.file = { _id: fileId } this.isNewFile = true - this.ProjectEntityUpdateHandler.mkdirp = { - withoutLock: sinon.stub().yields(null, this.newFolders, this.folder), + this.ProjectEntityUpdateHandler.promises.mkdirp = { + withoutLock: sinon + .stub() + .resolves({ newFolders: this.newFolders, folder: this.folder }), } - this.ProjectEntityUpdateHandler.upsertFile = { - mainTask: sinon.stub().yields(null, this.file, this.isNewFile), + this.ProjectEntityUpdateHandler.promises.upsertFile = { + mainTask: sinon + .stub() + .resolves({ doc: this.file, isNew: this.isNewFile }), } this.ProjectEntityUpdateHandler.upsertFileWithPath( @@ -1543,7 +1688,10 @@ describe('ProjectEntityUpdateHandler', function () { this.linkedFileData, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1555,21 +1703,20 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('deleteEntity', function () { - beforeEach(function () { + beforeEach(function (done) { this.path = '/path/to/doc.tex' this.doc = { _id: docId } this.projectBeforeDeletion = { _id: projectId, name: 'project' } this.newProject = 'new-project' - this.ProjectEntityMongoUpdateHandler.deleteEntity.yields( - null, - this.doc, - { fileSystem: this.path }, - this.projectBeforeDeletion, - this.newProject - ) + this.ProjectEntityMongoUpdateHandler.promises.deleteEntity.resolves({ + entity: this.doc, + path: { fileSystem: this.path }, + projectBeforeDeletion: this.projectBeforeDeletion, + newProject: this.newProject, + }) this.ProjectEntityUpdateHandler._cleanUpEntity = sinon .stub() - .yields(null, [{ type: 'doc', entity: this.doc, path: this.path }]) + .resolves([{ type: 'doc', entity: this.doc, path: this.path }]) this.ProjectEntityUpdateHandler.deleteEntity( projectId, @@ -1577,12 +1724,15 @@ describe('ProjectEntityUpdateHandler', function () { 'doc', userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('deletes the entity in mongo', function () { - this.ProjectEntityMongoUpdateHandler.deleteEntity + this.ProjectEntityMongoUpdateHandler.promises.deleteEntity .calledWith(projectId, docId, 'doc') .should.equal(true) }) @@ -1602,7 +1752,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('it notifies the tpds', function () { - this.TpdsUpdateSender.deleteEntity.should.have.been.calledWith({ + this.TpdsUpdateSender.promises.deleteEntity.should.have.been.calledWith({ projectId, path: this.path, projectName: this.projectBeforeDeletion.name, @@ -1619,11 +1769,14 @@ describe('ProjectEntityUpdateHandler', function () { describe('deleteEntityWithPath', function () { describe('when the entity exists', function () { - beforeEach(function () { + beforeEach(function (done) { this.doc = { _id: docId } - this.ProjectLocator.findElementByPath.yields(null, this.doc, 'doc') - this.ProjectEntityUpdateHandler.deleteEntity = { - withoutLock: sinon.stub().yields(), + this.ProjectLocator.promises.findElementByPath.resolves({ + element: this.doc, + type: 'doc', + }) + this.ProjectEntityUpdateHandler.promises.deleteEntity = { + withoutLock: sinon.stub().resolves(), } this.path = '/path/to/doc.tex' this.ProjectEntityUpdateHandler.deleteEntityWithPath( @@ -1631,12 +1784,12 @@ describe('ProjectEntityUpdateHandler', function () { this.path, userId, this.source, - this.callback + done ) }) it('finds the entity', function () { - this.ProjectLocator.findElementByPath + this.ProjectLocator.promises.findElementByPath .calledWith({ project_id: projectId, path: this.path, @@ -1646,71 +1799,69 @@ describe('ProjectEntityUpdateHandler', function () { }) it('deletes the entity', function () { - this.ProjectEntityUpdateHandler.deleteEntity.withoutLock - .calledWith( - projectId, - this.doc._id, - 'doc', - userId, - this.source, - this.callback - ) - .should.equal(true) + this.ProjectEntityUpdateHandler.promises.deleteEntity.withoutLock.should.have.been.calledWith( + projectId, + this.doc._id, + 'doc', + userId, + this.source + ) }) }) describe('when the entity does not exist', function () { - beforeEach(function () { - this.ProjectLocator.findElementByPath.yields() + beforeEach(function (done) { + this.ProjectLocator.promises.findElementByPath.resolves({ + element: null, + }) this.path = '/doc.tex' this.ProjectEntityUpdateHandler.deleteEntityWithPath( projectId, this.path, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('returns an error', function () { - this.callback - .calledWith(sinon.match.instanceOf(Errors.NotFoundError)) - .should.equal(true) + this.callback.should.have.been.calledWith( + sinon.match.instanceOf(Errors.NotFoundError) + ) }) }) }) describe('mkdirp', function () { - beforeEach(function () { + beforeEach(function (done) { this.docPath = '/folder/doc.tex' - this.ProjectEntityMongoUpdateHandler.mkdirp.yields() - this.ProjectEntityUpdateHandler.mkdirp( - projectId, - this.docPath, - this.callback - ) + this.ProjectEntityMongoUpdateHandler.promises.mkdirp.resolves({}) + this.ProjectEntityUpdateHandler.mkdirp(projectId, this.docPath, done) }) it('calls ProjectEntityMongoUpdateHandler', function () { - this.ProjectEntityMongoUpdateHandler.mkdirp + this.ProjectEntityMongoUpdateHandler.promises.mkdirp .calledWith(projectId, this.docPath) .should.equal(true) }) }) describe('mkdirpWithExactCase', function () { - beforeEach(function () { + beforeEach(function (done) { this.docPath = '/folder/doc.tex' - this.ProjectEntityMongoUpdateHandler.mkdirp.yields() + this.ProjectEntityMongoUpdateHandler.promises.mkdirp.resolves({}) this.ProjectEntityUpdateHandler.mkdirpWithExactCase( projectId, this.docPath, - this.callback + done ) }) it('calls ProjectEntityMongoUpdateHandler', function () { - this.ProjectEntityMongoUpdateHandler.mkdirp + this.ProjectEntityMongoUpdateHandler.promises.mkdirp .calledWith(projectId, this.docPath, { exactCaseMatch: true }) .should.equal(true) }) @@ -1718,35 +1869,38 @@ describe('ProjectEntityUpdateHandler', function () { describe('addFolder', function () { describe('adding a folder', function () { - beforeEach(function () { + beforeEach(function (done) { this.parentFolderId = '123asdf' this.folderName = 'new-folder' - this.ProjectEntityMongoUpdateHandler.addFolder.yields() + this.ProjectEntityMongoUpdateHandler.promises.addFolder.resolves({}) this.ProjectEntityUpdateHandler.addFolder( projectId, this.parentFolderId, this.folderName, - this.callback + done ) }) it('calls ProjectEntityMongoUpdateHandler', function () { - this.ProjectEntityMongoUpdateHandler.addFolder + this.ProjectEntityMongoUpdateHandler.promises.addFolder .calledWith(projectId, this.parentFolderId, this.folderName) .should.equal(true) }) }) describe('adding a folder with an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.parentFolderId = '123asdf' this.folderName = '*new-folder' - this.ProjectEntityMongoUpdateHandler.addFolder.yields() + this.ProjectEntityMongoUpdateHandler.promises.addFolder.resolves({}) this.ProjectEntityUpdateHandler.addFolder( projectId, this.parentFolderId, this.folderName, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1758,20 +1912,19 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('moveEntity', function () { - beforeEach(function () { + beforeEach(function (done) { this.project_name = 'project name' this.startPath = '/a.tex' this.endPath = '/folder/b.tex' this.rev = 2 this.changes = { newDocs: ['old-doc'], newFiles: ['old-file'] } - this.ProjectEntityMongoUpdateHandler.moveEntity.yields( - null, - this.project, - this.startPath, - this.endPath, - this.rev, - this.changes - ) + this.ProjectEntityMongoUpdateHandler.promises.moveEntity.resolves({ + project: this.project, + startPath: this.startPath, + endPath: this.endPath, + rev: this.rev, + changes: this.changes, + }) this.ProjectEntityUpdateHandler.moveEntity( projectId, @@ -1780,18 +1933,18 @@ describe('ProjectEntityUpdateHandler', function () { 'doc', userId, this.source, - this.callback + done ) }) it('moves the entity in mongo', function () { - this.ProjectEntityMongoUpdateHandler.moveEntity + this.ProjectEntityMongoUpdateHandler.promises.moveEntity .calledWith(projectId, docId, folderId, 'doc') .should.equal(true) }) it('notifies tpds', function () { - this.TpdsUpdateSender.moveEntity + this.TpdsUpdateSender.promises.moveEntity .calledWith({ projectId, projectName: this.project_name, @@ -1806,7 +1959,7 @@ describe('ProjectEntityUpdateHandler', function () { }) it('sends the changes in project structure to the doc updater', function () { - this.DocumentUpdaterHandler.updateProjectStructure + this.DocumentUpdaterHandler.promises.updateProjectStructure .calledWith( projectId, projectHistoryId, @@ -1820,21 +1973,20 @@ describe('ProjectEntityUpdateHandler', function () { describe('renameEntity', function () { describe('renaming an entity', function () { - beforeEach(function () { + beforeEach(function (done) { this.project_name = 'project name' this.startPath = '/folder/a.tex' this.endPath = '/folder/b.tex' this.rev = 2 this.changes = { newDocs: ['old-doc'], newFiles: ['old-file'] } this.newDocName = 'b.tex' - this.ProjectEntityMongoUpdateHandler.renameEntity.yields( - null, - this.project, - this.startPath, - this.endPath, - this.rev, - this.changes - ) + this.ProjectEntityMongoUpdateHandler.promises.renameEntity.resolves({ + project: this.project, + startPath: this.startPath, + endPath: this.endPath, + rev: this.rev, + changes: this.changes, + }) this.ProjectEntityUpdateHandler.renameEntity( projectId, @@ -1843,18 +1995,18 @@ describe('ProjectEntityUpdateHandler', function () { this.newDocName, userId, this.source, - this.callback + done ) }) it('moves the entity in mongo', function () { - this.ProjectEntityMongoUpdateHandler.renameEntity + this.ProjectEntityMongoUpdateHandler.promises.renameEntity .calledWith(projectId, docId, 'doc', this.newDocName) .should.equal(true) }) it('notifies tpds', function () { - this.TpdsUpdateSender.moveEntity + this.TpdsUpdateSender.promises.moveEntity .calledWith({ projectId, projectName: this.project_name, @@ -1869,13 +2021,13 @@ describe('ProjectEntityUpdateHandler', function () { }) it('flushes the project in doc updater', function () { - this.DocumentUpdaterHandler.flushProjectToMongo.should.have.been.calledWith( + this.DocumentUpdaterHandler.promises.flushProjectToMongo.should.have.been.calledWith( projectId ) }) it('sends the changes in project structure to the doc updater', function () { - this.DocumentUpdaterHandler.updateProjectStructure + this.DocumentUpdaterHandler.promises.updateProjectStructure .calledWith( projectId, projectHistoryId, @@ -1888,21 +2040,20 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('renaming an entity to an invalid name', function () { - beforeEach(function () { + beforeEach(function (done) { this.project_name = 'project name' this.startPath = '/folder/a.tex' this.endPath = '/folder/b.tex' this.rev = 2 this.changes = { newDocs: ['old-doc'], newFiles: ['old-file'] } this.newDocName = '*b.tex' - this.ProjectEntityMongoUpdateHandler.renameEntity.yields( - null, - this.project, - this.startPath, - this.endPath, - this.rev, - this.changes - ) + this.ProjectEntityMongoUpdateHandler.promises.renameEntity.resolves({ + project: this.project, + startPath: this.startPath, + endPath: this.endPath, + rev: this.rev, + changes: this.changes, + }) this.ProjectEntityUpdateHandler.renameEntity( projectId, @@ -1911,7 +2062,10 @@ describe('ProjectEntityUpdateHandler', function () { this.newDocName, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1922,21 +2076,20 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('renaming an entity with a non-string value', function () { - beforeEach(function () { + beforeEach(function (done) { this.project_name = 'project name' this.startPath = '/folder/a.tex' this.endPath = '/folder/b.tex' this.rev = 2 this.changes = { newDocs: ['old-doc'], newFiles: ['old-file'] } this.newDocName = ['hello'] - this.ProjectEntityMongoUpdateHandler.renameEntity.yields( - null, - this.project, - this.startPath, - this.endPath, - this.rev, - this.changes - ) + this.ProjectEntityMongoUpdateHandler.promises.renameEntity.resolves({ + project: this.project, + startPath: this.startPath, + endPath: this.endPath, + rev: this.rev, + changes: this.changes, + }) this.ProjectEntityUpdateHandler.renameEntity( projectId, @@ -1945,7 +2098,10 @@ describe('ProjectEntityUpdateHandler', function () { this.newDocName, userId, this.source, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1953,7 +2109,7 @@ describe('ProjectEntityUpdateHandler', function () { const errorMatcher = sinon.match.instanceOf(Error) this.callback.calledWithMatch(errorMatcher).should.equal(true) expect( - this.ProjectEntityMongoUpdateHandler.renameEntity.called + this.ProjectEntityMongoUpdateHandler.promises.renameEntity.called ).to.equal(false) }) }) @@ -1961,13 +2117,16 @@ describe('ProjectEntityUpdateHandler', function () { describe('resyncProjectHistory', function () { describe('a deleted project', function () { - beforeEach(function () { - this.ProjectGetter.getProject.yields() + beforeEach(function (done) { + this.ProjectGetter.promises.getProject.resolves({}) this.ProjectEntityUpdateHandler.resyncProjectHistory( projectId, {}, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -1986,14 +2145,17 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('a project without project-history enabled', function () { - beforeEach(function () { + beforeEach(function (done) { this.project.overleaf = {} - this.ProjectGetter.getProject.yields(null, this.project) + this.ProjectGetter.promises.getProject.resolves(this.project) this.ProjectEntityUpdateHandler.resyncProjectHistory( projectId, {}, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -2019,8 +2181,8 @@ describe('ProjectEntityUpdateHandler', function () { path: 'universe.png', }, ] - beforeEach(function () { - this.ProjectGetter.getProject.yields(null, this.project) + beforeEach(function (done) { + this.ProjectGetter.promises.getProject.resolves(this.project) const folders = [] this.ProjectEntityHandler.getAllEntitiesFromProject.returns({ docs, @@ -2030,26 +2192,31 @@ describe('ProjectEntityUpdateHandler', function () { this.ProjectEntityUpdateHandler.resyncProjectHistory( projectId, {}, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) it('gets the project', function () { - this.ProjectGetter.getProject.calledWith(projectId).should.equal(true) + this.ProjectGetter.promises.getProject.should.have.been.calledWith( + projectId + ) }) it('gets the entities for the project', function () { - this.ProjectEntityHandler.getAllEntitiesFromProject - .calledWith(this.project) - .should.equal(true) + this.ProjectEntityHandler.getAllEntitiesFromProject.should.have.been.calledWith( + this.project + ) }) it('uses an extended timeout', function () { - this.LockManager.withTimeout.calledWith(6 * 60).should.equal(true) + this.LockManager.withTimeout.should.have.been.calledWith(6 * 60) }) it('tells the doc updater to sync the project', function () { - this.DocumentUpdaterHandler.resyncProjectHistory + this.DocumentUpdaterHandler.promises.resyncProjectHistory .calledWith(projectId, projectHistoryId, docs, files) .should.equal(true) }) @@ -2061,7 +2228,7 @@ describe('ProjectEntityUpdateHandler', function () { describe('a project with duplicate filenames', function () { beforeEach(function (done) { - this.ProjectGetter.getProject.yields(null, this.project) + this.ProjectGetter.promises.getProject.resolves(this.project) this.docs = [ { doc: { _id: 'doc1', name: 'main.tex' }, path: 'main.tex' }, { @@ -2112,7 +2279,8 @@ describe('ProjectEntityUpdateHandler', function () { }) it('renames the duplicate files', function () { - const renameEntity = this.ProjectEntityMongoUpdateHandler.renameEntity + const renameEntity = + this.ProjectEntityMongoUpdateHandler.promises.renameEntity expect(renameEntity).to.have.callCount(4) expect(renameEntity).to.have.been.calledWith( projectId, @@ -2160,14 +2328,14 @@ describe('ProjectEntityUpdateHandler', function () { return f }) expect( - this.DocumentUpdaterHandler.resyncProjectHistory + this.DocumentUpdaterHandler.promises.resyncProjectHistory ).to.have.been.calledWith(projectId, projectHistoryId, docs, files) }) }) describe('a project with bad filenames', function () { beforeEach(function (done) { - this.ProjectGetter.getProject.yields(null, this.project) + this.ProjectGetter.promises.getProject.resolves(this.project) this.docs = [ { doc: { _id: 'doc1', name: '/d/e/f/test.tex' }, @@ -2201,7 +2369,8 @@ describe('ProjectEntityUpdateHandler', function () { }) it('renames the files', function () { - const renameEntity = this.ProjectEntityMongoUpdateHandler.renameEntity + const renameEntity = + this.ProjectEntityMongoUpdateHandler.promises.renameEntity expect(renameEntity).to.have.callCount(4) expect(renameEntity).to.have.been.calledWith( projectId, @@ -2249,7 +2418,7 @@ describe('ProjectEntityUpdateHandler', function () { return f }) expect( - this.DocumentUpdaterHandler.resyncProjectHistory + this.DocumentUpdaterHandler.promises.resyncProjectHistory ).to.have.been.calledWith(projectId, projectHistoryId, docs, files) }) }) @@ -2277,7 +2446,7 @@ describe('ProjectEntityUpdateHandler', function () { ] const files = [] beforeEach(function (done) { - this.ProjectGetter.getProject.yields(null, this.project) + this.ProjectGetter.promises.getProject.resolves(this.project) this.ProjectEntityHandler.getAllEntitiesFromProject.returns({ docs, files, @@ -2291,7 +2460,8 @@ describe('ProjectEntityUpdateHandler', function () { }) it('renames the folder', function () { - const renameEntity = this.ProjectEntityMongoUpdateHandler.renameEntity + const renameEntity = + this.ProjectEntityMongoUpdateHandler.promises.renameEntity expect(renameEntity).to.have.callCount(1) expect(renameEntity).to.have.been.calledWith( projectId, @@ -2309,7 +2479,7 @@ describe('ProjectEntityUpdateHandler', function () { return d }) expect( - this.DocumentUpdaterHandler.resyncProjectHistory + this.DocumentUpdaterHandler.promises.resyncProjectHistory ).to.have.been.calledWith(projectId, projectHistoryId, fixedDocs, files) }) }) @@ -2333,7 +2503,7 @@ describe('ProjectEntityUpdateHandler', function () { ] const files = [] beforeEach(function (done) { - this.ProjectGetter.getProject.yields(null, this.project) + this.ProjectGetter.promises.getProject.resolves(this.project) this.ProjectEntityHandler.getAllEntitiesFromProject.returns({ docs, files, @@ -2347,7 +2517,8 @@ describe('ProjectEntityUpdateHandler', function () { }) it('renames the doc', function () { - const renameEntity = this.ProjectEntityMongoUpdateHandler.renameEntity + const renameEntity = + this.ProjectEntityMongoUpdateHandler.promises.renameEntity expect(renameEntity).to.have.callCount(1) expect(renameEntity).to.have.been.calledWith( projectId, @@ -2365,20 +2536,23 @@ describe('ProjectEntityUpdateHandler', function () { return d }) expect( - this.DocumentUpdaterHandler.resyncProjectHistory + this.DocumentUpdaterHandler.promises.resyncProjectHistory ).to.have.been.calledWith(projectId, projectHistoryId, fixedDocs, files) }) }) describe('a project with an invalid file tree', function () { - beforeEach(function () { + beforeEach(function (done) { this.callback = sinon.stub() - this.ProjectGetter.getProject.yields(null, this.project) + this.ProjectGetter.promises.getProject.resolves(this.project) this.ProjectEntityHandler.getAllEntitiesFromProject.throws() this.ProjectEntityUpdateHandler.resyncProjectHistory( projectId, {}, - this.callback + (...args) => { + this.callback(...args) + done() + } ) }) @@ -2393,53 +2567,51 @@ describe('ProjectEntityUpdateHandler', function () { describe('_cleanUpEntity', function () { beforeEach(function () { this.entityId = '4eecaffcbffa66588e000009' - this.FileStoreHandler.deleteFile.yields() - this.ProjectEntityUpdateHandler.unsetRootDoc = sinon.stub().yields() - this.ProjectEntityMongoUpdateHandler._insertDeletedFileReference.yields() + this.FileStoreHandler.promises.deleteFile.resolves() + this.ProjectEntityUpdateHandler.promises.unsetRootDoc = sinon + .stub() + .resolves() + this.ProjectEntityMongoUpdateHandler.promises._insertDeletedFileReference.resolves() }) describe('a file', function () { - beforeEach(function (done) { + beforeEach(async function () { this.path = '/file/system/path.png' this.entity = { _id: this.entityId } this.newProject = 'new-project' - this.ProjectEntityUpdateHandler._cleanUpEntity( - this.project, - this.newProject, - this.entity, - 'file', - this.path, - userId, - this.source, - (err, subtreeListing) => { - if (err) { - return done(err) - } - this.subtreeListing = subtreeListing - done() - } - ) + this.subtreeListing = + await this.ProjectEntityUpdateHandler._cleanUpEntity( + this.project, + this.newProject, + this.entity, + 'file', + this.path, + userId, + this.source + ) }) it('should insert the file into the deletedFiles collection', function () { - this.ProjectEntityMongoUpdateHandler._insertDeletedFileReference + this.ProjectEntityMongoUpdateHandler.promises._insertDeletedFileReference .calledWith(this.project._id, this.entity) .should.equal(true) }) it('should not delete the file from FileStoreHandler', function () { - this.FileStoreHandler.deleteFile + this.FileStoreHandler.promises.deleteFile .calledWith(projectId, this.entityId) .should.equal(false) }) it('should not attempt to delete from the document updater', function () { - this.DocumentUpdaterHandler.deleteDoc.called.should.equal(false) + this.DocumentUpdaterHandler.promises.deleteDoc.called.should.equal( + false + ) }) it('should send the update to the doc updater', function () { const oldFiles = [{ file: this.entity, path: this.path }] - this.DocumentUpdaterHandler.updateProjectStructure.should.have.been.calledWith( + this.DocumentUpdaterHandler.promises.updateProjectStructure.should.have.been.calledWith( projectId, projectHistoryId, userId, @@ -2460,27 +2632,21 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('a doc', function () { - beforeEach(function (done) { + beforeEach(async function () { this.path = '/file/system/path.tex' - this.ProjectEntityUpdateHandler._cleanUpDoc = sinon.stub().yields() + this.ProjectEntityUpdateHandler._cleanUpDoc = sinon.stub().resolves() this.entity = { _id: this.entityId } this.newProject = 'new-project' - this.ProjectEntityUpdateHandler._cleanUpEntity( - this.project, - this.newProject, - this.entity, - 'doc', - this.path, - userId, - this.source, - (err, subtreeListing) => { - if (err) { - return done(err) - } - this.subtreeListing = subtreeListing - done() - } - ) + this.subtreeListing = + await this.ProjectEntityUpdateHandler._cleanUpEntity( + this.project, + this.newProject, + this.entity, + 'doc', + this.path, + userId, + this.source + ) }) it('should clean up the doc', function () { @@ -2491,7 +2657,7 @@ describe('ProjectEntityUpdateHandler', function () { it('should send the update to the doc updater', function () { const oldDocs = [{ doc: this.entity, path: this.path }] - this.DocumentUpdaterHandler.updateProjectStructure.should.have.been.calledWith( + this.DocumentUpdaterHandler.promises.updateProjectStructure.should.have.been.calledWith( projectId, projectHistoryId, userId, @@ -2512,7 +2678,7 @@ describe('ProjectEntityUpdateHandler', function () { }) describe('a folder', function () { - beforeEach(function (done) { + beforeEach(async function () { this.folder = { folders: [ { @@ -2528,40 +2694,31 @@ describe('ProjectEntityUpdateHandler', function () { docs: [(this.doc2 = { _id: 'doc-id-2', name: 'doc-name-2' })], } - this.ProjectEntityUpdateHandler._cleanUpDoc = sinon.stub().yields() - this.ProjectEntityUpdateHandler._cleanUpFile = sinon.stub().yields() + this.ProjectEntityUpdateHandler._cleanUpDoc = sinon.stub().resolves() + this.ProjectEntityUpdateHandler._cleanUpFile = sinon.stub().resolves() const path = '/folder' this.newProject = 'new-project' - this.ProjectEntityUpdateHandler._cleanUpEntity( - this.project, - this.newProject, - this.folder, - 'folder', - path, - userId, - this.source, - (err, subtreeListing) => { - if (err) { - return done(err) - } - this.subtreeListing = subtreeListing - done() - } - ) + this.subtreeListing = + await this.ProjectEntityUpdateHandler._cleanUpEntity( + this.project, + this.newProject, + this.folder, + 'folder', + path, + userId, + this.source + ) }) it('should clean up all sub files', function () { - this.ProjectEntityUpdateHandler._cleanUpFile - .calledWith( - this.project, - this.file1, - '/folder/subfolder/file-name-1', - userId - ) - .should.equal(true) - this.ProjectEntityUpdateHandler._cleanUpFile - .calledWith(this.project, this.file2, '/folder/file-name-2', userId) - .should.equal(true) + this.ProjectEntityUpdateHandler._cleanUpFile.should.have.been.calledWith( + this.project, + this.file1 + ) + this.ProjectEntityUpdateHandler._cleanUpFile.should.have.been.calledWith( + this.project, + this.file2 + ) }) it('should clean up all sub docs', function () { @@ -2587,7 +2744,7 @@ describe('ProjectEntityUpdateHandler', function () { { doc: this.doc2, path: '/folder/doc-name-2' }, { doc: this.doc1, path: '/folder/subfolder/doc-name-1' }, ] - this.DocumentUpdaterHandler.updateProjectStructure + this.DocumentUpdaterHandler.promises.updateProjectStructure .calledWith( projectId, projectHistoryId, @@ -2634,63 +2791,57 @@ describe('ProjectEntityUpdateHandler', function () { name: 'test.tex', } this.path = '/path/to/doc' - this.ProjectEntityUpdateHandler.unsetRootDoc = sinon.stub().yields() - this.DocstoreManager.deleteDoc.yields() + this.ProjectEntityUpdateHandler.promises.unsetRootDoc = sinon + .stub() + .resolves() + this.DocstoreManager.promises.deleteDoc.resolves() }) describe('when the doc is the root doc', function () { - beforeEach(function () { + beforeEach(async function () { this.project.rootDoc_id = this.doc._id - this.ProjectEntityUpdateHandler._cleanUpDoc( + await this.ProjectEntityUpdateHandler._cleanUpDoc( this.project, this.doc, this.path, - userId, - this.callback + userId ) }) it('should unset the root doc', function () { - this.ProjectEntityUpdateHandler.unsetRootDoc - .calledWith(projectId) - .should.equal(true) + this.ProjectEntityUpdateHandler.promises.unsetRootDoc.should.have.been.calledWith( + projectId + ) }) it('should delete the doc in the doc updater', function () { - this.DocumentUpdaterHandler.deleteDoc + this.DocumentUpdaterHandler.promises.deleteDoc .calledWith(projectId, this.doc._id.toString()) .should.equal(true) }) it('should delete the doc in the doc store', function () { - this.DocstoreManager.deleteDoc + this.DocstoreManager.promises.deleteDoc .calledWith(projectId, this.doc._id.toString(), 'test.tex') .should.equal(true) }) - - it('should call the callback', function () { - this.callback.called.should.equal(true) - }) }) describe('when the doc is not the root doc', function () { - beforeEach(function () { + beforeEach(async function () { this.project.rootDoc_id = new ObjectId() - this.ProjectEntityUpdateHandler._cleanUpDoc( + await this.ProjectEntityUpdateHandler._cleanUpDoc( this.project, this.doc, this.path, - userId, - this.callback + userId ) }) it('should not unset the root doc', function () { - this.ProjectEntityUpdateHandler.unsetRootDoc.called.should.equal(false) - }) - - it('should call the callback', function () { - this.callback.called.should.equal(true) + this.ProjectEntityUpdateHandler.promises.unsetRootDoc.called.should.equal( + false + ) }) }) }) @@ -2703,31 +2854,37 @@ describe('ProjectEntityUpdateHandler', function () { this.fileStoreUrl = 'http://filestore/file' this.folder = { _id: new ObjectId() } this.rev = 3 - this.ProjectLocator.findElement + this.ProjectLocator.promises.findElement .withArgs({ project_id: this.project._id, element_id: this.doc._id, type: 'doc', }) - .yields(null, this.doc, { fileSystem: this.path }, this.folder) - this.ProjectLocator.findElement + .resolves({ + element: this.doc, + path: { fileSystem: this.path }, + folder: this.folder, + }) + this.ProjectLocator.promises.findElement .withArgs({ project_id: this.project._id.toString(), element_id: this.file._id, type: 'file', }) - .yields(null, this.file, this.docPath, this.folder) - this.DocstoreManager.getDoc + .resolves({ + element: this.file, + path: this.docPath, + folder: this.folder, + }) + this.DocstoreManager.promises.getDoc .withArgs(this.project._id, this.doc._id) - .yields(null, this.docLines, this.rev) - this.FileWriter.writeLinesToDisk.yields(null, this.tmpFilePath) - this.FileStoreHandler.uploadFileFromDisk.yields( - null, - this.fileStoreUrl, - this.file - ) - this.ProjectEntityMongoUpdateHandler.replaceDocWithFile.yields( - null, + .resolves({ lines: this.docLines, rev: this.rev }) + this.FileWriter.promises.writeLinesToDisk.resolves(this.tmpFilePath) + this.FileStoreHandler.promises.uploadFileFromDisk.resolves({ + url: this.fileStoreUrl, + fileRef: this.file, + }) + this.ProjectEntityMongoUpdateHandler.promises.replaceDocWithFile.resolves( this.project ) }) @@ -2744,15 +2901,14 @@ describe('ProjectEntityUpdateHandler', function () { }) it('deletes the document in doc updater', function () { - expect(this.DocumentUpdaterHandler.deleteDoc).to.have.been.calledWith( - this.project._id, - this.doc._id - ) + expect( + this.DocumentUpdaterHandler.promises.deleteDoc + ).to.have.been.calledWith(this.project._id, this.doc._id) }) it('uploads the file to filestore', function () { expect( - this.FileStoreHandler.uploadFileFromDisk + this.FileStoreHandler.promises.uploadFileFromDisk ).to.have.been.calledWith( this.project._id, { name: this.doc.name, rev: this.rev + 1 }, @@ -2761,18 +2917,20 @@ describe('ProjectEntityUpdateHandler', function () { }) it('cleans up the temporary file', function () { - expect(this.fs.unlink).to.have.been.calledWith(this.tmpFilePath) + expect(this.fs.promises.unlink).to.have.been.calledWith( + this.tmpFilePath + ) }) it('replaces the doc with the file', function () { expect( - this.ProjectEntityMongoUpdateHandler.replaceDocWithFile + this.ProjectEntityMongoUpdateHandler.promises.replaceDocWithFile ).to.have.been.calledWith(this.project._id, this.doc._id, this.file) }) it('notifies document updater of changes', function () { expect( - this.DocumentUpdaterHandler.updateProjectStructure + this.DocumentUpdaterHandler.promises.updateProjectStructure ).to.have.been.calledWith( this.project._id, this.project.overleaf.history.id, @@ -2816,9 +2974,14 @@ describe('ProjectEntityUpdateHandler', function () { describe('when the doc has ranges', function () { it('should throw a DocHasRangesError', function (done) { this.ranges = { comments: [{ id: 123 }] } - this.DocstoreManager.getDoc + this.DocstoreManager.promises.getDoc .withArgs(this.project._id, this.doc._id) - .yields(null, this.docLines, 'rev', 'version', this.ranges) + .resolves({ + lines: this.docLines, + rev: 'rev', + version: 'version', + ranges: this.ranges, + }) this.ProjectEntityUpdateHandler.convertDocToFile( this.project._id, this.doc._id,