HttpController.coffee 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144
  1. DocManager = require "./DocManager"
  2. logger = require "logger-sharelatex"
  3. DocArchive = require "./DocArchiveManager"
  4. HealthChecker = require "./HealthChecker"
  5. Settings = require "settings-sharelatex"
  6. module.exports = HttpController =
  7. getDoc: (req, res, next = (error) ->) ->
  8. project_id = req.params.project_id
  9. doc_id = req.params.doc_id
  10. include_deleted = req.query?.include_deleted == "true"
  11. logger.log project_id: project_id, doc_id: doc_id, "getting doc"
  12. DocManager.getFullDoc project_id, doc_id, (error, doc) ->
  13. return next(error) if error?
  14. logger.log {doc_id, project_id}, "got doc"
  15. if !doc?
  16. res.send 404
  17. else if doc.deleted && !include_deleted
  18. res.send 404
  19. else
  20. res.json HttpController._buildDocView(doc)
  21. getRawDoc: (req, res, next = (error)->)->
  22. project_id = req.params.project_id
  23. doc_id = req.params.doc_id
  24. logger.log project_id: project_id, doc_id: doc_id, "getting raw doc"
  25. DocManager.getDocLines project_id, doc_id, (error, doc) ->
  26. return next(error) if error?
  27. if !doc?
  28. res.send 404
  29. else
  30. res.setHeader('content-type', 'text/plain')
  31. res.send HttpController._buildRawDocView(doc)
  32. getAllDocs: (req, res, next = (error) ->) ->
  33. project_id = req.params.project_id
  34. logger.log project_id: project_id, "getting all docs"
  35. DocManager.getAllNonDeletedDocs project_id, {lines: true, rev: true}, (error, docs = []) ->
  36. return next(error) if error?
  37. res.json HttpController._buildDocsArrayView(project_id, docs)
  38. getAllRanges: (req, res, next = (error) ->) ->
  39. project_id = req.params.project_id
  40. logger.log {project_id}, "getting all ranges"
  41. DocManager.getAllNonDeletedDocs project_id, {ranges: true}, (error, docs = []) ->
  42. return next(error) if error?
  43. res.json HttpController._buildDocsArrayView(project_id, docs)
  44. updateDoc: (req, res, next = (error) ->) ->
  45. project_id = req.params.project_id
  46. doc_id = req.params.doc_id
  47. lines = req.body?.lines
  48. version = req.body?.version
  49. ranges = req.body?.ranges
  50. if !lines? or lines not instanceof Array
  51. logger.error project_id: project_id, doc_id: doc_id, "no doc lines provided"
  52. res.send 400 # Bad Request
  53. return
  54. if !version? or typeof version is not "number"
  55. logger.error project_id: project_id, doc_id: doc_id, "no doc version provided"
  56. res.send 400 # Bad Request
  57. return
  58. if !ranges?
  59. logger.error project_id: project_id, doc_id: doc_id, "no doc ranges provided"
  60. res.send 400 # Bad Request
  61. return
  62. bodyLength = lines.reduce(
  63. (len, line) => line.length + len
  64. 0
  65. )
  66. if bodyLength > Settings.max_doc_length
  67. logger.error project_id: project_id, doc_id: doc_id, bodyLength: bodyLength, "document body too large"
  68. res.status(413).send("document body too large")
  69. return
  70. logger.log project_id: project_id, doc_id: doc_id, "got http request to update doc"
  71. DocManager.updateDoc project_id, doc_id, lines, version, ranges, (error, modified, rev) ->
  72. return next(error) if error?
  73. res.json {
  74. modified: modified
  75. rev: rev
  76. }
  77. deleteDoc: (req, res, next = (error) ->) ->
  78. project_id = req.params.project_id
  79. doc_id = req.params.doc_id
  80. logger.log project_id: project_id, doc_id: doc_id, "deleting doc"
  81. DocManager.deleteDoc project_id, doc_id, (error) ->
  82. return next(error) if error?
  83. res.send 204
  84. _buildDocView: (doc) ->
  85. doc_view = { _id: doc._id?.toString() }
  86. for attribute in ["lines", "rev", "version", "ranges", "deleted"]
  87. if doc[attribute]?
  88. doc_view[attribute] = doc[attribute]
  89. return doc_view
  90. _buildRawDocView: (doc)->
  91. return (doc?.lines or []).join("\n")
  92. _buildDocsArrayView: (project_id, docs) ->
  93. docViews = []
  94. for doc in docs
  95. if doc? # There can end up being null docs for some reason :( (probably a race condition)
  96. docViews.push HttpController._buildDocView(doc)
  97. else
  98. logger.error err: new Error("null doc"), project_id: project_id, "encountered null doc"
  99. return docViews
  100. archiveAllDocs: (req, res, next = (error) ->) ->
  101. project_id = req.params.project_id
  102. logger.log project_id: project_id, "archiving all docs"
  103. DocArchive.archiveAllDocs project_id, (error) ->
  104. return next(error) if error?
  105. res.send 204
  106. unArchiveAllDocs: (req, res, next = (error) ->) ->
  107. project_id = req.params.project_id
  108. logger.log project_id: project_id, "unarchiving all docs"
  109. DocArchive.unArchiveAllDocs project_id, (error) ->
  110. return next(error) if error?
  111. res.send 200
  112. destroyAllDocs: (req, res, next = (error) ->) ->
  113. project_id = req.params.project_id
  114. logger.log project_id: project_id, "destroying all docs"
  115. DocArchive.destroyAllDocs project_id, (error) ->
  116. return next(error) if error?
  117. res.send 204
  118. healthCheck: (req, res)->
  119. HealthChecker.check (err)->
  120. if err?
  121. logger.err err:err, "error performing health check"
  122. res.send 500
  123. else
  124. res.send 200