overleaf/services/filestore/app.coffee

143 lines
4.2 KiB
CoffeeScript
Raw Normal View History

2014-02-14 11:39:05 -05:00
express = require('express')
2018-05-21 05:11:47 -04:00
bodyParser = require "body-parser"
2014-02-14 11:39:05 -05:00
logger = require('logger-sharelatex')
logger.initialize("filestore")
settings = require("settings-sharelatex")
request = require("request")
fileController = require("./app/js/FileController")
keyBuilder = require("./app/js/KeyBuilder")
healthCheckController = require("./app/js/HealthCheckController")
2014-02-14 11:39:05 -05:00
domain = require("domain")
appIsOk = true
app = express()
2014-05-09 08:30:35 -04:00
Metrics = require "metrics-sharelatex"
Metrics.initialize("filestore")
Metrics.open_sockets.monitor(logger)
2015-06-23 08:41:14 -04:00
Metrics.event_loop?.monitor(logger)
2015-08-18 10:36:07 -04:00
Metrics.memory.monitor(logger)
2014-02-14 11:39:05 -05:00
2018-05-21 04:49:32 -04:00
app.use Metrics.http.monitor(logger)
2014-02-14 11:39:05 -05:00
2014-05-09 08:30:35 -04:00
Metrics.inc "startup"
2014-02-14 11:39:05 -05:00
app.use (req, res, next)->
2014-05-09 08:30:35 -04:00
Metrics.inc "http-request"
2014-02-14 11:39:05 -05:00
next()
app.use (req, res, next) ->
requestDomain = domain.create()
requestDomain.add req
requestDomain.add res
requestDomain.on "error", (err)->
try
# request a shutdown to prevent memory leaks
beginShutdown()
if !res.headerSent
res.send(500, "uncaught exception")
logger = require('logger-sharelatex')
req =
body:req.body
headers:req.headers
url:req.url
key: req.key
statusCode: req.statusCode
err =
message: err.message
stack: err.stack
name: err.name
type: err.type
arguments: err.arguments
logger.err err:err, req:req, res:res, "uncaught exception thrown on request"
catch exception
logger.err err: exception, "exception in request domain handler"
2014-02-14 11:39:05 -05:00
requestDomain.run next
app.use (req, res, next) ->
if not appIsOk
# when shutting down, close any HTTP keep-alive connections
res.set 'Connection', 'close'
next()
app.get "/project/:project_id/file/:file_id", keyBuilder.userFileKey, fileController.getFile
app.post "/project/:project_id/file/:file_id", keyBuilder.userFileKey, fileController.insertFile
2018-05-21 05:11:47 -04:00
app.put "/project/:project_id/file/:file_id", keyBuilder.userFileKey, bodyParser.json(), fileController.copyFile
2014-02-14 11:39:05 -05:00
app.del "/project/:project_id/file/:file_id", keyBuilder.userFileKey, fileController.deleteFile
app.get "/template/:template_id/v/:version/:format", keyBuilder.templateFileKey, fileController.getFile
app.get "/template/:template_id/v/:version/:format/:sub_type", keyBuilder.templateFileKey, fileController.getFile
2014-02-14 11:39:05 -05:00
app.post "/template/:template_id/v/:version/:format", keyBuilder.templateFileKey, fileController.insertFile
2015-05-08 10:15:48 -04:00
app.get "/project/:project_id/public/:public_file_id", keyBuilder.publicFileKey, fileController.getFile
app.post "/project/:project_id/public/:public_file_id", keyBuilder.publicFileKey, fileController.insertFile
2018-05-21 05:11:47 -04:00
app.put "/project/:project_id/public/:public_file_id", keyBuilder.publicFileKey, bodyParser.json(), fileController.copyFile
2015-05-08 10:15:48 -04:00
app.del "/project/:project_id/public/:public_file_id", keyBuilder.publicFileKey, fileController.deleteFile
app.get "/project/:project_id/size", keyBuilder.publicProjectKey, fileController.directorySize
2016-03-11 20:31:46 -05:00
app.get "/heapdump", (req, res)->
require('heapdump').writeSnapshot '/tmp/' + Date.now() + '.filestore.heapsnapshot', (err, filename)->
res.send filename
2014-02-14 11:39:05 -05:00
app.post "/shutdown", (req, res)->
appIsOk = false
res.send()
app.get '/status', (req, res)->
if appIsOk
2018-01-16 12:00:27 -05:00
res.send('filestore sharelatex up - hello james')
2014-02-14 11:39:05 -05:00
else
logger.log "app is not ok - shutting down"
res.send("server is being shut down", 500)
app.get "/health_check", healthCheckController.check
2014-02-14 11:39:05 -05:00
app.get '*', (req, res)->
res.send 404
2014-02-14 11:39:05 -05:00
beginShutdown = () ->
2014-12-23 11:55:34 -05:00
if appIsOk
appIsOk = false
# hard-terminate this process if graceful shutdown fails
killTimer = setTimeout () ->
process.exit 1
, 120*1000
killTimer.unref?() # prevent timer from keeping process alive
app.close () ->
logger.log "closed all connections"
Metrics.close()
process.disconnect?()
2014-12-23 11:55:34 -05:00
logger.log "server will stop accepting connections"
port = settings.internal.filestore.port or 3009
host = "0.0.0.0"
if !module.parent # Called directly
app.listen port, host, (error) ->
logger.info "Filestore starting up, listening on #{host}:#{port}"
module.exports = app
2015-01-07 05:28:47 -05:00
process.on 'SIGTERM', () ->
logger.log("filestore got SIGTERM, shutting down gracefully")
beginShutdown()
if global.gc?
gcTimer = setInterval () ->
global.gc()
logger.log process.memoryUsage(), "global.gc"
, 3 * oneMinute = 60 * 1000
gcTimer.unref()