MongoManagerTests.coffee 9.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329
  1. sinon = require('sinon')
  2. chai = require('chai')
  3. should = chai.should()
  4. expect = chai.expect
  5. modulePath = "../../../../app/js/MongoManager.js"
  6. SandboxedModule = require('sandboxed-module')
  7. {ObjectId} = require("mongojs")
  8. describe "MongoManager", ->
  9. beforeEach ->
  10. @MongoManager = SandboxedModule.require modulePath, requires:
  11. "./mongojs" : { db: @db = {}, ObjectId: ObjectId }
  12. @callback = sinon.stub()
  13. @doc_id = ObjectId().toString()
  14. @project_id = ObjectId().toString()
  15. describe "getLastCompressedUpdate", ->
  16. beforeEach ->
  17. @update = "mock-update"
  18. @db.docHistory = {}
  19. @db.docHistory.find = sinon.stub().returns @db.docHistory
  20. @db.docHistory.sort = sinon.stub().returns @db.docHistory
  21. @db.docHistory.limit = sinon.stub().returns @db.docHistory
  22. @db.docHistory.toArray = sinon.stub().callsArgWith(0, null, [@update])
  23. @MongoManager.getLastCompressedUpdate @doc_id, @callback
  24. it "should find the updates for the doc", ->
  25. @db.docHistory.find
  26. .calledWith(doc_id: ObjectId(@doc_id))
  27. .should.equal true
  28. it "should limit to one result", ->
  29. @db.docHistory.limit
  30. .calledWith(1)
  31. .should.equal true
  32. it "should sort in descending version order", ->
  33. @db.docHistory.sort
  34. .calledWith(v: -1)
  35. .should.equal true
  36. it "should call the call back with the update", ->
  37. @callback.calledWith(null, @update).should.equal true
  38. describe "deleteCompressedUpdate", ->
  39. beforeEach ->
  40. @update_id = ObjectId().toString()
  41. @db.docHistory =
  42. remove: sinon.stub().callsArg(1)
  43. @MongoManager.deleteCompressedUpdate(@update_id, @callback)
  44. it "should remove the update", ->
  45. @db.docHistory.remove
  46. .calledWith(_id: ObjectId(@update_id))
  47. .should.equal true
  48. it "should call the callback", ->
  49. @callback.called.should.equal true
  50. describe "popLastCompressedUpdate", ->
  51. describe "when there is no last update", ->
  52. beforeEach ->
  53. @MongoManager.getLastCompressedUpdate = sinon.stub().callsArgWith(1, null, null)
  54. @MongoManager.deleteCompressedUpdate = sinon.stub()
  55. @MongoManager.popLastCompressedUpdate @doc_id, @callback
  56. it "should get the last update", ->
  57. @MongoManager.getLastCompressedUpdate
  58. .calledWith(@doc_id)
  59. .should.equal true
  60. it "should not try to delete the last update", ->
  61. @MongoManager.deleteCompressedUpdate.called.should.equal false
  62. it "should call the callback with no update", ->
  63. @callback.calledWith(null, null).should.equal true
  64. describe "when there is an update", ->
  65. beforeEach ->
  66. @update = { _id: Object() }
  67. @MongoManager.getLastCompressedUpdate = sinon.stub().callsArgWith(1, null, @update)
  68. @MongoManager.deleteCompressedUpdate = sinon.stub().callsArgWith(1, null)
  69. @MongoManager.popLastCompressedUpdate @doc_id, @callback
  70. it "should get the last update", ->
  71. @MongoManager.getLastCompressedUpdate
  72. .calledWith(@doc_id)
  73. .should.equal true
  74. it "should delete the last update", ->
  75. @MongoManager.deleteCompressedUpdate
  76. .calledWith(@update._id)
  77. .should.equal true
  78. it "should call the callback with the update", ->
  79. @callback.calledWith(null, @update).should.equal true
  80. describe "insertCompressedUpdate", ->
  81. beforeEach ->
  82. @update = { op: "op", meta: "meta", v: "v"}
  83. @db.docHistory =
  84. insert: sinon.stub().callsArg(1)
  85. @MongoManager.insertCompressedUpdate @project_id, @doc_id, @update, @callback
  86. it "should insert the update", ->
  87. @db.docHistory.insert
  88. .calledWith({
  89. project_id: ObjectId(@project_id),
  90. doc_id: ObjectId(@doc_id),
  91. op: @update.op,
  92. meta: @update.meta,
  93. v: @update.v
  94. })
  95. .should.equal true
  96. it "should call the callback", ->
  97. @callback.called.should.equal true
  98. describe "insertCompressedUpdates", ->
  99. beforeEach (done) ->
  100. @updates = [ "mock-update-1", "mock-update-2" ]
  101. @MongoManager.insertCompressedUpdate = sinon.stub().callsArg(3)
  102. @MongoManager.insertCompressedUpdates @project_id, @doc_id, @updates, (args...) =>
  103. @callback(args...)
  104. done()
  105. it "should insert each update", ->
  106. for update in @updates
  107. @MongoManager.insertCompressedUpdate
  108. .calledWith(@project_id, @doc_id, update)
  109. .should.equal true
  110. it "should call the callback", ->
  111. @callback.called.should.equal true
  112. describe "getDocUpdates", ->
  113. beforeEach ->
  114. @updates = ["mock-update"]
  115. @db.docHistory = {}
  116. @db.docHistory.find = sinon.stub().returns @db.docHistory
  117. @db.docHistory.sort = sinon.stub().returns @db.docHistory
  118. @db.docHistory.limit = sinon.stub().returns @db.docHistory
  119. @db.docHistory.toArray = sinon.stub().callsArgWith(0, null, @updates)
  120. @from = 42
  121. @to = 55
  122. describe "with a to version", ->
  123. beforeEach ->
  124. @MongoManager.getDocUpdates @doc_id, from: @from, to: @to, @callback
  125. it "should find the all updates between the to and from versions", ->
  126. @db.docHistory.find
  127. .calledWith({
  128. doc_id: ObjectId(@doc_id)
  129. v: { $gte: @from, $lte: @to }
  130. })
  131. .should.equal true
  132. it "should sort in descending version order", ->
  133. @db.docHistory.sort
  134. .calledWith("v": -1)
  135. .should.equal true
  136. it "should not limit the results", ->
  137. @db.docHistory.limit
  138. .called.should.equal false
  139. it "should call the call back with the updates", ->
  140. @callback.calledWith(null, @updates).should.equal true
  141. describe "without a to version", ->
  142. beforeEach ->
  143. @MongoManager.getDocUpdates @doc_id, from: @from, @callback
  144. it "should find the all updates after the from version", ->
  145. @db.docHistory.find
  146. .calledWith({
  147. doc_id: ObjectId(@doc_id)
  148. v: { $gte: @from }
  149. })
  150. .should.equal true
  151. it "should call the call back with the updates", ->
  152. @callback.calledWith(null, @updates).should.equal true
  153. describe "with a limit", ->
  154. beforeEach ->
  155. @MongoManager.getDocUpdates @doc_id, from: @from, limit: @limit = 10, @callback
  156. it "should limit the results", ->
  157. @db.docHistory.limit
  158. .calledWith(@limit)
  159. .should.equal true
  160. describe "getDocUpdates", ->
  161. beforeEach ->
  162. @updates = ["mock-update"]
  163. @db.docHistory = {}
  164. @db.docHistory.find = sinon.stub().returns @db.docHistory
  165. @db.docHistory.sort = sinon.stub().returns @db.docHistory
  166. @db.docHistory.limit = sinon.stub().returns @db.docHistory
  167. @db.docHistory.toArray = sinon.stub().callsArgWith(0, null, @updates)
  168. @before = Date.now()
  169. describe "with a before timestamp", ->
  170. beforeEach ->
  171. @MongoManager.getProjectUpdates @project_id, before: @before, @callback
  172. it "should find the all updates before the timestamp", ->
  173. @db.docHistory.find
  174. .calledWith({
  175. project_id: ObjectId(@project_id)
  176. "meta.end_ts": { $lt: @before }
  177. })
  178. .should.equal true
  179. it "should sort in descending version order", ->
  180. @db.docHistory.sort
  181. .calledWith("meta.end_ts": -1)
  182. .should.equal true
  183. it "should not limit the results", ->
  184. @db.docHistory.limit
  185. .called.should.equal false
  186. it "should call the call back with the updates", ->
  187. @callback.calledWith(null, @updates).should.equal true
  188. describe "without a before timestamp", ->
  189. beforeEach ->
  190. @MongoManager.getProjectUpdates @project_id, {}, @callback
  191. it "should find the all updates", ->
  192. @db.docHistory.find
  193. .calledWith({
  194. project_id: ObjectId(@project_id)
  195. })
  196. .should.equal true
  197. it "should call the call back with the updates", ->
  198. @callback.calledWith(null, @updates).should.equal true
  199. describe "with a limit", ->
  200. beforeEach ->
  201. @MongoManager.getProjectUpdates @project_id, before: @before, limit: @limit = 10, @callback
  202. it "should limit the results", ->
  203. @db.docHistory.limit
  204. .calledWith(@limit)
  205. .should.equal true
  206. describe "backportProjectId", ->
  207. beforeEach ->
  208. @db.docHistory =
  209. update: sinon.stub().callsArg(3)
  210. @MongoManager.backportProjectId @project_id, @doc_id, @callback
  211. it "should insert the project_id into all entries for the doc_id which don't have it set", ->
  212. @db.docHistory.update
  213. .calledWith({
  214. doc_id: ObjectId(@doc_id)
  215. project_id: { $exists: false }
  216. }, {
  217. $set: { project_id: ObjectId(@project_id) }
  218. }, {
  219. multi: true
  220. })
  221. .should.equal true
  222. it "should call the callback", ->
  223. @callback.called.should.equal true
  224. describe "getProjectMetaData", ->
  225. beforeEach ->
  226. @metadata = { "mock": "metadata" }
  227. @db.projectHistoryMetaData =
  228. find: sinon.stub().callsArgWith(1, null, [@metadata])
  229. @MongoManager.getProjectMetaData @project_id, @callback
  230. it "should look up the meta data in the db", ->
  231. @db.projectHistoryMetaData.find
  232. .calledWith({ project_id: ObjectId(@project_id) })
  233. .should.equal true
  234. it "should return the metadata", ->
  235. @callback.calledWith(null, @metadata).should.equal true
  236. describe "setProjectMetaData", ->
  237. beforeEach ->
  238. @metadata = { "mock": "metadata" }
  239. @db.projectHistoryMetaData =
  240. update: sinon.stub().callsArgWith(3, null, [@metadata])
  241. @MongoManager.setProjectMetaData @project_id, @metadata, @callback
  242. it "should upsert the metadata into the DB", ->
  243. @db.projectHistoryMetaData.update
  244. .calledWith({
  245. project_id: ObjectId(@project_id)
  246. }, {
  247. $set: @metadata
  248. }, {
  249. upsert: true
  250. })
  251. .should.equal true
  252. it "should call the callback", ->
  253. @callback.called.should.equal true
  254. describe "deleteOldProjectUpdates", ->
  255. beforeEach ->
  256. @before = Date.now() - 10000
  257. @db.docHistory =
  258. remove: sinon.stub().callsArg(1)
  259. @MongoManager.deleteOldProjectUpdates @project_id, @before, @callback
  260. it "should delete updates before the 'before' time", ->
  261. @db.docHistory.remove
  262. .calledWith({
  263. project_id: ObjectId(@project_id)
  264. "meta.end_ts": { "$lt": @before }
  265. })
  266. .should.equal true
  267. it "should return the callback", ->
  268. @callback.called.should.equal true