From ab6fe1d948450013d067399465f59c82379dabbc Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Thu, 1 Jun 2017 11:27:56 +0100 Subject: [PATCH 01/28] check for null bytes from JSON.stringify --- .../app/coffee/DocumentUpdaterManager.coffee | 4 +++ .../coffee/DocumentUpdaterManagerTests.coffee | 30 ++++++++++++++----- 2 files changed, 26 insertions(+), 8 deletions(-) diff --git a/services/real-time/app/coffee/DocumentUpdaterManager.coffee b/services/real-time/app/coffee/DocumentUpdaterManager.coffee index ab893aa47f..e183d11cec 100644 --- a/services/real-time/app/coffee/DocumentUpdaterManager.coffee +++ b/services/real-time/app/coffee/DocumentUpdaterManager.coffee @@ -54,6 +54,10 @@ module.exports = DocumentUpdaterManager = queueChange: (project_id, doc_id, change, callback = ()->)-> jsonChange = JSON.stringify change + if jsonChange.indexOf("\u0000") != -1 + error = new Error("null bytes found in op") + logger.error err: error, project_id: project_id, doc_id: doc_id, jsonChange: jsonChange, error.message + return callback(error) doc_key = "#{project_id}:#{doc_id}" # Push onto pendingUpdates for doc_id first, because once the doc updater # gets an entry on pending-updates-list, it starts processing. diff --git a/services/real-time/test/unit/coffee/DocumentUpdaterManagerTests.coffee b/services/real-time/test/unit/coffee/DocumentUpdaterManagerTests.coffee index e6f9b2098b..2d3e0ad3af 100644 --- a/services/real-time/test/unit/coffee/DocumentUpdaterManagerTests.coffee +++ b/services/real-time/test/unit/coffee/DocumentUpdaterManagerTests.coffee @@ -17,14 +17,17 @@ describe 'DocumentUpdaterManager', -> pendingUpdates: ({doc_id}) -> "PendingUpdates:#{doc_id}" @rclient = {auth:->} - @DocumentUpdaterManager = SandboxedModule.require modulePath, requires: - 'settings-sharelatex':@settings - 'logger-sharelatex': @logger = {log: sinon.stub(), error: sinon.stub(), warn: sinon.stub()} - 'request': @request = {} - 'redis-sharelatex' : createClient: () => @rclient - 'metrics-sharelatex': @Metrics = - Timer: class Timer - done: () -> + @DocumentUpdaterManager = SandboxedModule.require modulePath, + requires: + 'settings-sharelatex':@settings + 'logger-sharelatex': @logger = {log: sinon.stub(), error: sinon.stub(), warn: sinon.stub()} + 'request': @request = {} + 'redis-sharelatex' : createClient: () => @rclient + 'metrics-sharelatex': @Metrics = + Timer: class Timer + done: () -> + globals: + JSON: @JSON = Object.create(JSON) # avoid modifying JSON object directly describe "getDocument", -> beforeEach -> @@ -147,3 +150,14 @@ describe 'DocumentUpdaterManager', -> it "should return an error", -> @callback.calledWithExactly(sinon.match(Error)).should.equal true + + describe "with null byte corruption", -> + beforeEach -> + @JSON.stringify = () -> return '["bad bytes! \u0000 <- here"]' + @DocumentUpdaterManager.queueChange(@project_id, @doc_id, @change, @callback) + + it "should return an error", -> + @callback.calledWithExactly(sinon.match(Error)).should.equal true + + it "should not push the change onto the pending-updates-list queue", -> + @rclient.rpush.called.should.equal false From 3dae68a4f0214bc6180f36f06781a303186fc7eb Mon Sep 17 00:00:00 2001 From: Joe Green Date: Fri, 11 Aug 2017 14:24:46 +0100 Subject: [PATCH 02/28] Create Jenkinsfile --- services/real-time/Jenkinsfile | 77 ++++++++++++++++++++++++++++++++++ 1 file changed, 77 insertions(+) create mode 100644 services/real-time/Jenkinsfile diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile new file mode 100644 index 0000000000..7a0be11b68 --- /dev/null +++ b/services/real-time/Jenkinsfile @@ -0,0 +1,77 @@ +pipeline { + + agent { + docker { + image 'node:4.2.1' + args "-v /var/lib/jenkins/.npm:/tmp/.npm" + } + } + + environment { + HOME = "/tmp" + } + + triggers { + pollSCM('* * * * *') + cron('@daily') + } + + stages { + stage('Set up') { + steps { + // we need to disable logallrefupdates, else git clones during the npm install will require git to lookup the user id + // which does not exist in the container's /etc/passwd file, causing the clone to fail. + sh 'git config --global core.logallrefupdates false' + } + } + stage('Install') { + steps { + sh 'rm -fr node_modules' + sh 'npm install' + sh 'npm rebuild' + sh 'npm install --quiet grunt-cli' + } + } + stage('Compile') { + steps { + sh 'node_modules/.bin/grunt install' + } + } + stage('Test') { + steps { + sh 'node_modules/.bin/grunt test:unit' + } + } + stage('Package') { + steps { + sh 'touch build.tar.gz' // Avoid tar warning about files changing during read + sh 'tar -czf build.tar.gz --exclude=build.tar.gz --exclude-vcs .' + } + } + stage('Publish') { + steps { + withAWS(credentials:'S3_CI_BUILDS_AWS_KEYS', region:"${S3_REGION_BUILD_ARTEFACTS}") { + s3Upload(file:'build.tar.gz', bucket:"${S3_BUCKET_BUILD_ARTEFACTS}", path:"${JOB_NAME}/${BUILD_NUMBER}.tar.gz") + } + } + } + } + + post { + failure { + mail(from: "${EMAIL_ALERT_FROM}", + to: "${EMAIL_ALERT_TO}", + subject: "Jenkins build failed: ${JOB_NAME}:${BUILD_NUMBER}", + body: "Build: ${BUILD_URL}") + } + } + + // The options directive is for configuration that applies to the whole job. + options { + // we'd like to make sure remove old builds, so we don't fill up our storage! + buildDiscarder(logRotator(numToKeepStr:'50')) + + // And we'd really like to be sure that this build doesn't hang forever, so let's time it out after: + timeout(time: 30, unit: 'MINUTES') + } +} From 72ef354206711546144d2efe2538e19ef420cedf Mon Sep 17 00:00:00 2001 From: Joe Green Date: Mon, 4 Sep 2017 14:54:05 +0100 Subject: [PATCH 03/28] build.txt --- services/real-time/Jenkinsfile | 3 +++ 1 file changed, 3 insertions(+) diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile index 7a0be11b68..81456dee00 100644 --- a/services/real-time/Jenkinsfile +++ b/services/real-time/Jenkinsfile @@ -44,6 +44,7 @@ pipeline { } stage('Package') { steps { + sh 'echo ${BUILD_NUMBER} > build_number.txt' sh 'touch build.tar.gz' // Avoid tar warning about files changing during read sh 'tar -czf build.tar.gz --exclude=build.tar.gz --exclude-vcs .' } @@ -52,6 +53,8 @@ pipeline { steps { withAWS(credentials:'S3_CI_BUILDS_AWS_KEYS', region:"${S3_REGION_BUILD_ARTEFACTS}") { s3Upload(file:'build.tar.gz', bucket:"${S3_BUCKET_BUILD_ARTEFACTS}", path:"${JOB_NAME}/${BUILD_NUMBER}.tar.gz") + // The deployment process uses this file to figure out the latest build + s3Upload(file:'build_number.txt', bucket:"${S3_BUCKET_BUILD_ARTEFACTS}", path:"${JOB_NAME}/latest") } } } From 0b41d32cbbf783bb58bcfeddcd17507c9336c16d Mon Sep 17 00:00:00 2001 From: Joe Green Date: Thu, 21 Sep 2017 10:59:41 +0100 Subject: [PATCH 04/28] Update Jenkinsfile --- services/real-time/Jenkinsfile | 7 +++++++ 1 file changed, 7 insertions(+) diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile index 81456dee00..f5f121ecf3 100644 --- a/services/real-time/Jenkinsfile +++ b/services/real-time/Jenkinsfile @@ -35,6 +35,7 @@ pipeline { stage('Compile') { steps { sh 'node_modules/.bin/grunt install' + sh 'node_modules/.bin/grunt compile:acceptance_tests' } } stage('Test') { @@ -42,6 +43,12 @@ pipeline { sh 'node_modules/.bin/grunt test:unit' } } + stage('Acceptance Tests') { + steps { + sh 'docker pull sharelatex/acceptance-test-runner' + sh 'docker run --rm -v $(pwd):/app sharelatex/acceptance-test-runner' + } + } stage('Package') { steps { sh 'echo ${BUILD_NUMBER} > build_number.txt' From dc8f4ffc2a48ef2309f44af2a788dd2c1468d4c2 Mon Sep 17 00:00:00 2001 From: Joe Green Date: Thu, 21 Sep 2017 11:03:07 +0100 Subject: [PATCH 05/28] Update Jenkinsfile --- services/real-time/Jenkinsfile | 33 +++++++++++++++++---------------- 1 file changed, 17 insertions(+), 16 deletions(-) diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile index f5f121ecf3..b684c49eb0 100644 --- a/services/real-time/Jenkinsfile +++ b/services/real-time/Jenkinsfile @@ -1,11 +1,6 @@ pipeline { - agent { - docker { - image 'node:4.2.1' - args "-v /var/lib/jenkins/.npm:/tmp/.npm" - } - } + agent any environment { HOME = "/tmp" @@ -17,29 +12,35 @@ pipeline { } stages { - stage('Set up') { + stage('Install') { + agent { + docker { + image 'node:4.2.1' + args "-v /var/lib/jenkins/.npm:/tmp/.npm -e HOME=/tmp" + reuseNode true + } + } steps { // we need to disable logallrefupdates, else git clones during the npm install will require git to lookup the user id // which does not exist in the container's /etc/passwd file, causing the clone to fail. sh 'git config --global core.logallrefupdates false' - } - } - stage('Install') { - steps { sh 'rm -fr node_modules' sh 'npm install' sh 'npm rebuild' sh 'npm install --quiet grunt-cli' } } - stage('Compile') { + stage('Compile and Test') { + agent { + docker { + image 'node:4.2.1' + args "-v /var/lib/jenkins/.npm:/tmp/.npm -e HOME=/tmp" + reuseNode true + } + } steps { sh 'node_modules/.bin/grunt install' sh 'node_modules/.bin/grunt compile:acceptance_tests' - } - } - stage('Test') { - steps { sh 'node_modules/.bin/grunt test:unit' } } From 9f503f1e9f857d90a06d53122c2ba20cb6388375 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 13:25:55 +0100 Subject: [PATCH 06/28] First pass at encoding changes & comments in ranges --- .../app/coffee/WebsocketController.coffee | 24 +++++++++++++++++++ 1 file changed, 24 insertions(+) diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index e0242d4208..e4057baf7c 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -101,6 +101,30 @@ module.exports = WebsocketController = logger.err {err, project_id, doc_id, fromVersion, line, client_id: client.id}, "error encoding line uri component" return callback(err) escapedLines.push line + + if ranges.comments + escapedComments = [] + for comment in ranges.comments + try + comment.op.c = unescape(encodeURIComponent(comment.op.c)) + catch err + logger.err {err, project_id, doc_id, fromVersion, comment, client_id: client.id}, "error encoding comment uri component" + return callback(err) + escapedComments.push comment + ranges.comments = escapedComments + + if ranges.changes + escapedChanges = [] + for change in ranges.changes + try + change.op.i = unescape(encodeURIComponent(change.op.i)) if change.op.i + change.op.d = unescape(encodeURIComponent(change.op.d)) if change.op.d + catch err + logger.err {err, project_id, doc_id, fromVersion, change, client_id: client.id}, "error encoding change uri component" + return callback(err) + escapedChanges.push change + ranges.changes = escapedChanges + AuthorizationManager.addAccessToDoc client, doc_id client.join(doc_id) callback null, escapedLines, version, ops, ranges From aa6e0d0d6977c5a25998b3258943eee1ea20540b Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 14:23:16 +0100 Subject: [PATCH 07/28] Only encode ranges if option passed --- services/real-time/app/coffee/Router.coffee | 4 +- .../app/coffee/WebsocketController.coffee | 47 +++++++++---------- 2 files changed, 25 insertions(+), 26 deletions(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index 2cc655eafc..8821748a35 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -80,13 +80,13 @@ module.exports = Router = Router._handleError null, err, client, "leaveProject" - client.on "joinDoc", (doc_id, fromVersion, callback) -> + client.on "joinDoc", (doc_id, options, fromVersion, callback) -> # fromVersion is optional if typeof fromVersion == "function" callback = fromVersion fromVersion = -1 - WebsocketController.joinDoc client, doc_id, fromVersion, (err, args...) -> + WebsocketController.joinDoc client, doc_id, options, fromVersion, (err, args...) -> if err? Router._handleError callback, err, client, "joinDoc", {doc_id, fromVersion} else diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index e4057baf7c..dec4d3d142 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -80,7 +80,7 @@ module.exports = WebsocketController = callback() , WebsocketController.FLUSH_IF_EMPTY_DELAY - joinDoc: (client, doc_id, fromVersion = -1, callback = (error, doclines, version, ops, ranges) ->) -> + joinDoc: (client, doc_id, options, fromVersion = -1, callback = (error, doclines, version, ops, ranges) ->) -> metrics.inc "editor.join-doc" Utils.getClientAttributes client, ["project_id", "user_id"], (error, {project_id, user_id}) -> return callback(error) if error? @@ -101,29 +101,28 @@ module.exports = WebsocketController = logger.err {err, project_id, doc_id, fromVersion, line, client_id: client.id}, "error encoding line uri component" return callback(err) escapedLines.push line - - if ranges.comments - escapedComments = [] - for comment in ranges.comments - try - comment.op.c = unescape(encodeURIComponent(comment.op.c)) - catch err - logger.err {err, project_id, doc_id, fromVersion, comment, client_id: client.id}, "error encoding comment uri component" - return callback(err) - escapedComments.push comment - ranges.comments = escapedComments - - if ranges.changes - escapedChanges = [] - for change in ranges.changes - try - change.op.i = unescape(encodeURIComponent(change.op.i)) if change.op.i - change.op.d = unescape(encodeURIComponent(change.op.d)) if change.op.d - catch err - logger.err {err, project_id, doc_id, fromVersion, change, client_id: client.id}, "error encoding change uri component" - return callback(err) - escapedChanges.push change - ranges.changes = escapedChanges + if options.encodeRanges + if ranges.comments + escapedComments = [] + for comment in ranges.comments + try + comment.op.c = unescape(encodeURIComponent(comment.op.c)) + catch err + logger.err {err, project_id, doc_id, fromVersion, comment, client_id: client.id}, "error encoding comment uri component" + return callback(err) + escapedComments.push comment + ranges.comments = escapedComments + if ranges.changes + escapedChanges = [] + for change in ranges.changes + try + change.op.i = unescape(encodeURIComponent(change.op.i)) if change.op.i + change.op.d = unescape(encodeURIComponent(change.op.d)) if change.op.d + catch err + logger.err {err, project_id, doc_id, fromVersion, change, client_id: client.id}, "error encoding change uri component" + return callback(err) + escapedChanges.push change + ranges.changes = escapedChanges AuthorizationManager.addAccessToDoc client, doc_id client.join(doc_id) From b796879c9f6d4f262349a1c267c9453608d06e26 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 14:58:49 +0100 Subject: [PATCH 08/28] Handle options not being passed --- services/real-time/app/coffee/Router.coffee | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index 8821748a35..e6dda566e0 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -79,8 +79,22 @@ module.exports = Router = if err? Router._handleError null, err, client, "leaveProject" - + # Variadic. The possible options: + # doc_id, callback + # doc_id, fromVersion, callback + # doc_id, options, callback + # doc_id, options, fromVersion, callback client.on "joinDoc", (doc_id, options, fromVersion, callback) -> + # options is optional + if typeof options == "function" + options = {} + callback = options + fromVersion = -1 + else if typeof options == "number" + options = {} + fromVersion = options + callback = fromVersion + # fromVersion is optional if typeof fromVersion == "function" callback = fromVersion From 55c880e1dd12a2bd777e38da1116d4d30c9104d7 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 15:07:15 +0100 Subject: [PATCH 09/28] DRY up a bit --- .../app/coffee/WebsocketController.coffee | 34 +++++++------------ 1 file changed, 12 insertions(+), 22 deletions(-) diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index dec4d3d142..70d325197f 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -91,38 +91,28 @@ module.exports = WebsocketController = return callback(error) if error? DocumentUpdaterManager.getDocument project_id, doc_id, fromVersion, (error, lines, version, ranges, ops) -> return callback(error) if error? + # Encode any binary bits of data so it can go via WebSockets # See http://ecmanaut.blogspot.co.uk/2006/07/encoding-decoding-utf8-in-javascript.html + encodeForWebsockets = (text) -> unescape(encodeURIComponent(text)) escapedLines = [] for line in lines try - line = unescape(encodeURIComponent(line)) + line = encodeForWebsockets(line) catch err logger.err {err, project_id, doc_id, fromVersion, line, client_id: client.id}, "error encoding line uri component" return callback(err) escapedLines.push line if options.encodeRanges - if ranges.comments - escapedComments = [] - for comment in ranges.comments - try - comment.op.c = unescape(encodeURIComponent(comment.op.c)) - catch err - logger.err {err, project_id, doc_id, fromVersion, comment, client_id: client.id}, "error encoding comment uri component" - return callback(err) - escapedComments.push comment - ranges.comments = escapedComments - if ranges.changes - escapedChanges = [] - for change in ranges.changes - try - change.op.i = unescape(encodeURIComponent(change.op.i)) if change.op.i - change.op.d = unescape(encodeURIComponent(change.op.d)) if change.op.d - catch err - logger.err {err, project_id, doc_id, fromVersion, change, client_id: client.id}, "error encoding change uri component" - return callback(err) - escapedChanges.push change - ranges.changes = escapedChanges + try + for comment in ranges?.comments or [] + comment.op.c = encodeForWebsockets(comment.op.c) + for change in ranges?.changes or [] + change.op.i = encodeForWebsockets(comment.op.i) if change.op.i + change.op.d = encodeForWebsockets(comment.op.d) if change.op.d + catch err + logger.err {err, project_id, doc_id, fromVersion, ranges, client_id: client.id}, "error encoding range uri component" + return callback(err) AuthorizationManager.addAccessToDoc client, doc_id client.join(doc_id) From 790b9ea8edb17c92a49ccdd15c7f818885c672a1 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 15:19:19 +0100 Subject: [PATCH 10/28] Switch order of args --- services/real-time/app/coffee/Router.coffee | 25 +++++++++------------ 1 file changed, 11 insertions(+), 14 deletions(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index e6dda566e0..a55147bfb2 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -79,26 +79,23 @@ module.exports = Router = if err? Router._handleError null, err, client, "leaveProject" - # Variadic. The possible options: + # Variadic. The possible arguments: # doc_id, callback # doc_id, fromVersion, callback # doc_id, options, callback - # doc_id, options, fromVersion, callback - client.on "joinDoc", (doc_id, options, fromVersion, callback) -> - # options is optional + # doc_id, fromVersion, options, callback + client.on "joinDoc", (doc_id, fromVersion, options, callback) -> + if typeof fromVersion == "function" + fromVersion = -1 + options = {} + callback = fromVersion + else if typeof fromVersion == "object" + fromVersion = -1 + options = fromVersion + callback = options if typeof options == "function" options = {} callback = options - fromVersion = -1 - else if typeof options == "number" - options = {} - fromVersion = options - callback = fromVersion - - # fromVersion is optional - if typeof fromVersion == "function" - callback = fromVersion - fromVersion = -1 WebsocketController.joinDoc client, doc_id, options, fromVersion, (err, args...) -> if err? From 3966e2f85bcfd3fcbf742d331af55eb3c2a9b939 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 16:55:49 +0100 Subject: [PATCH 11/28] Make variadic options more explicit --- services/real-time/app/coffee/Router.coffee | 19 ++++++++++++------- 1 file changed, 12 insertions(+), 7 deletions(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index a55147bfb2..b3d6ffeb16 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -85,17 +85,22 @@ module.exports = Router = # doc_id, options, callback # doc_id, fromVersion, options, callback client.on "joinDoc", (doc_id, fromVersion, options, callback) -> - if typeof fromVersion == "function" - fromVersion = -1 - options = {} + if typeof fromVersion == "function" and !options callback = fromVersion - else if typeof fromVersion == "object" fromVersion = -1 - options = fromVersion - callback = options - if typeof options == "function" options = {} + else if typeof fromVersion == "number" and typeof options == "function" callback = options + options = {} + else if typeof fromVersion == "object" and typeof options == "function" + callback = options + options = fromVersion + fromVersion = -1 + else if typeof fromVersion == "number" and typeof options == "object" + # Called with 4 args, things are as expected + else + logger.error { arguments: arguments }, "unexpected arguments" + return {} # ???? WebsocketController.joinDoc client, doc_id, options, fromVersion, (err, args...) -> if err? From 90d05dc6ddeb93dbb44405880874de1e3bb6470d Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 16:56:09 +0100 Subject: [PATCH 12/28] Make args order consistent --- services/real-time/app/coffee/Router.coffee | 2 +- services/real-time/app/coffee/WebsocketController.coffee | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index b3d6ffeb16..0fb502bd4f 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -102,7 +102,7 @@ module.exports = Router = logger.error { arguments: arguments }, "unexpected arguments" return {} # ???? - WebsocketController.joinDoc client, doc_id, options, fromVersion, (err, args...) -> + WebsocketController.joinDoc client, doc_id, fromVersion, options, (err, args...) -> if err? Router._handleError callback, err, client, "joinDoc", {doc_id, fromVersion} else diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index 70d325197f..4b51da8d53 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -80,7 +80,7 @@ module.exports = WebsocketController = callback() , WebsocketController.FLUSH_IF_EMPTY_DELAY - joinDoc: (client, doc_id, options, fromVersion = -1, callback = (error, doclines, version, ops, ranges) ->) -> + joinDoc: (client, doc_id, fromVersion = -1, options, callback = (error, doclines, version, ops, ranges) ->) -> metrics.inc "editor.join-doc" Utils.getClientAttributes client, ["project_id", "user_id"], (error, {project_id, user_id}) -> return callback(error) if error? From a299d7335d847cec2a85a32fe07b43dded07a894 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 16:56:18 +0100 Subject: [PATCH 13/28] Fix incorrect var --- services/real-time/app/coffee/WebsocketController.coffee | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index 4b51da8d53..580e8ac20b 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -108,8 +108,8 @@ module.exports = WebsocketController = for comment in ranges?.comments or [] comment.op.c = encodeForWebsockets(comment.op.c) for change in ranges?.changes or [] - change.op.i = encodeForWebsockets(comment.op.i) if change.op.i - change.op.d = encodeForWebsockets(comment.op.d) if change.op.d + change.op.i = encodeForWebsockets(change.op.i) if change.op.i + change.op.d = encodeForWebsockets(change.op.d) if change.op.d catch err logger.err {err, project_id, doc_id, fromVersion, ranges, client_id: client.id}, "error encoding range uri component" return callback(err) From 5d8e201732eeaff7da2ffa6e8fec36804f3d2742 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Thu, 21 Sep 2017 16:58:03 +0100 Subject: [PATCH 14/28] Don't return obj --- services/real-time/app/coffee/Router.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index 0fb502bd4f..21d9e34b7d 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -100,7 +100,7 @@ module.exports = Router = # Called with 4 args, things are as expected else logger.error { arguments: arguments }, "unexpected arguments" - return {} # ???? + return # ???? WebsocketController.joinDoc client, doc_id, fromVersion, options, (err, args...) -> if err? From 937bf82a2fee9fa166f45df5f210cc0866e75f58 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Fri, 22 Sep 2017 09:25:24 +0100 Subject: [PATCH 15/28] Return callback with guard --- services/real-time/app/coffee/Router.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/services/real-time/app/coffee/Router.coffee b/services/real-time/app/coffee/Router.coffee index 21d9e34b7d..17107e443a 100644 --- a/services/real-time/app/coffee/Router.coffee +++ b/services/real-time/app/coffee/Router.coffee @@ -100,7 +100,7 @@ module.exports = Router = # Called with 4 args, things are as expected else logger.error { arguments: arguments }, "unexpected arguments" - return # ???? + return callback?(new Error("unexpected arguments")) WebsocketController.joinDoc client, doc_id, fromVersion, options, (err, args...) -> if err? From c67150ea10334f5ab57445a6f1b31b852d5750cf Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Fri, 22 Sep 2017 09:33:29 +0100 Subject: [PATCH 16/28] Ensure falsy value doesn't fail conditional --- services/real-time/app/coffee/WebsocketController.coffee | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index 580e8ac20b..63c3ff903a 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -108,8 +108,8 @@ module.exports = WebsocketController = for comment in ranges?.comments or [] comment.op.c = encodeForWebsockets(comment.op.c) for change in ranges?.changes or [] - change.op.i = encodeForWebsockets(change.op.i) if change.op.i - change.op.d = encodeForWebsockets(change.op.d) if change.op.d + change.op.i = encodeForWebsockets(change.op.i) if change.op.i? + change.op.d = encodeForWebsockets(change.op.d) if change.op.d? catch err logger.err {err, project_id, doc_id, fromVersion, ranges, client_id: client.id}, "error encoding range uri component" return callback(err) From a0505afb23a63b39bf81ed7b4fa27ccaef3996d1 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Fri, 22 Sep 2017 09:34:10 +0100 Subject: [PATCH 17/28] Be defensive on comment text --- services/real-time/app/coffee/WebsocketController.coffee | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/services/real-time/app/coffee/WebsocketController.coffee b/services/real-time/app/coffee/WebsocketController.coffee index 63c3ff903a..53ccecd51b 100644 --- a/services/real-time/app/coffee/WebsocketController.coffee +++ b/services/real-time/app/coffee/WebsocketController.coffee @@ -106,7 +106,7 @@ module.exports = WebsocketController = if options.encodeRanges try for comment in ranges?.comments or [] - comment.op.c = encodeForWebsockets(comment.op.c) + comment.op.c = encodeForWebsockets(comment.op.c) if comment.op.c? for change in ranges?.changes or [] change.op.i = encodeForWebsockets(change.op.i) if change.op.i? change.op.d = encodeForWebsockets(change.op.d) if change.op.d? From b8d3f34e5463f9c4dda0942ff9221c62c62d3f9f Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Fri, 22 Sep 2017 10:42:51 +0100 Subject: [PATCH 18/28] Fix joinDoc tests not passing options arg and restructure tests --- .../coffee/WebsocketControllerTests.coffee | 38 ++++++++++++------- 1 file changed, 24 insertions(+), 14 deletions(-) diff --git a/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee b/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee index 8db81b716e..f0ae54ae61 100644 --- a/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee +++ b/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee @@ -221,49 +221,59 @@ describe 'WebsocketController', -> @version = 42 @ops = ["mock", "ops"] @ranges = { "mock": "ranges" } + @options = {} @client.params.project_id = @project_id @AuthorizationManager.addAccessToDoc = sinon.stub() @AuthorizationManager.assertClientCanViewProject = sinon.stub().callsArgWith(1, null) @DocumentUpdaterManager.getDocument = sinon.stub().callsArgWith(3, null, @doc_lines, @version, @ranges, @ops) - - describe "with a fromVersion", -> + + describe "works", -> beforeEach -> - @fromVersion = 40 - @WebsocketController.joinDoc @client, @doc_id, @fromVersion, @callback - + @WebsocketController.joinDoc @client, @doc_id, -1, @options, @callback + it "should check that the client is authorized to view the project", -> @AuthorizationManager.assertClientCanViewProject .calledWith(@client) .should.equal true - - it "should get the document from the DocumentUpdaterManager", -> + + it "should get the document from the DocumentUpdaterManager with fromVersion", -> @DocumentUpdaterManager.getDocument - .calledWith(@project_id, @doc_id, @fromVersion) + .calledWith(@project_id, @doc_id, -1) .should.equal true it "should add permissions for the client to access the doc", -> @AuthorizationManager.addAccessToDoc .calledWith(@client, @doc_id) .should.equal true - + it "should join the client to room for the doc_id", -> @client.join .calledWith(@doc_id) .should.equal true - + it "should call the callback with the lines, version, ranges and ops", -> @callback .calledWith(null, @doc_lines, @version, @ops, @ranges) .should.equal true - + it "should increment the join-doc metric", -> @metrics.inc.calledWith("editor.join-doc").should.equal true + + describe "with a fromVersion", -> + beforeEach -> + @fromVersion = 40 + @WebsocketController.joinDoc @client, @doc_id, @fromVersion, @options, @callback + it "should get the document from the DocumentUpdaterManager with fromVersion", -> + @DocumentUpdaterManager.getDocument + .calledWith(@project_id, @doc_id, @fromVersion) + .should.equal true + describe "with doclines that need escaping", -> beforeEach -> @doc_lines.push ["räksmörgås"] - @WebsocketController.joinDoc @client, @doc_id, -1, @callback + @WebsocketController.joinDoc @client, @doc_id, -1, @options, @callback it "should call the callback with the escaped lines", -> escaped_lines = @callback.args[0][1] @@ -271,11 +281,11 @@ describe 'WebsocketController', -> escaped_word.should.equal 'räksmörgÃ¥s' # Check that unescaping works decodeURIComponent(escape(escaped_word)).should.equal "räksmörgås" - + describe "when not authorized", -> beforeEach -> @AuthorizationManager.assertClientCanViewProject = sinon.stub().callsArgWith(1, @err = new Error("not authorized")) - @WebsocketController.joinDoc @client, @doc_id, -1, @callback + @WebsocketController.joinDoc @client, @doc_id, -1, @options, @callback it "should call the callback with an error", -> @callback.calledWith(@err).should.equal true From 785d6e2eeaa2e6642d19ba9acefaa8e00a59987f Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Fri, 22 Sep 2017 10:43:11 +0100 Subject: [PATCH 19/28] Add tests for comment & change encoding --- .../coffee/WebsocketControllerTests.coffee | 30 +++++++++++++++++++ 1 file changed, 30 insertions(+) diff --git a/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee b/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee index f0ae54ae61..a8a3841faf 100644 --- a/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee +++ b/services/real-time/test/unit/coffee/WebsocketControllerTests.coffee @@ -282,6 +282,36 @@ describe 'WebsocketController', -> # Check that unescaping works decodeURIComponent(escape(escaped_word)).should.equal "räksmörgås" + describe "with comments that need encoding", -> + beforeEach -> + @ranges.comments = [{ op: { c: "räksmörgås" } }] + @WebsocketController.joinDoc @client, @doc_id, -1, { encodeRanges: true }, @callback + + it "should call the callback with the encoded comment", -> + encoded_comments = @callback.args[0][4] + encoded_comment = encoded_comments.comments.pop() + encoded_comment_text = encoded_comment.op.c + encoded_comment_text.should.equal 'räksmörgÃ¥s' + + describe "with changes that need encoding", -> + it "should call the callback with the encoded insert change", -> + @ranges.changes = [{ op: { i: "räksmörgås" } }] + @WebsocketController.joinDoc @client, @doc_id, -1, { encodeRanges: true }, @callback + + encoded_changes = @callback.args[0][4] + encoded_change = encoded_changes.changes.pop() + encoded_change_text = encoded_change.op.i + encoded_change_text.should.equal 'räksmörgÃ¥s' + + it "should call the callback with the encoded delete change", -> + @ranges.changes = [{ op: { d: "räksmörgås" } }] + @WebsocketController.joinDoc @client, @doc_id, -1, { encodeRanges: true }, @callback + + encoded_changes = @callback.args[0][4] + encoded_change = encoded_changes.changes.pop() + encoded_change_text = encoded_change.op.d + encoded_change_text.should.equal 'räksmörgÃ¥s' + describe "when not authorized", -> beforeEach -> @AuthorizationManager.assertClientCanViewProject = sinon.stub().callsArgWith(1, @err = new Error("not authorized")) From 6470577c3fdb223e21c6573a8bd9bcbe83023a76 Mon Sep 17 00:00:00 2001 From: Alasdair Smith Date: Fri, 22 Sep 2017 11:01:11 +0100 Subject: [PATCH 20/28] Add acceptance tests for joinDoc variadic --- .../acceptance/coffee/JoinDocTests.coffee | 79 ++++++++++++++++++- 1 file changed, 78 insertions(+), 1 deletion(-) diff --git a/services/real-time/test/acceptance/coffee/JoinDocTests.coffee b/services/real-time/test/acceptance/coffee/JoinDocTests.coffee index a9d5406345..6c204b6079 100644 --- a/services/real-time/test/acceptance/coffee/JoinDocTests.coffee +++ b/services/real-time/test/acceptance/coffee/JoinDocTests.coffee @@ -166,4 +166,81 @@ describe "joinDoc", -> it "should have joined the doc room", (done) -> RealTimeClient.getConnectedClient @client.socket.sessionid, (error, client) => expect(@doc_id in client.rooms).to.equal true - done() \ No newline at end of file + done() + + describe "with options", -> + before (done) -> + @options = { encodeRanges: true } + async.series [ + (cb) => + FixturesManager.setUpProject { + privilegeLevel: "readAndWrite" + }, (e, {@project_id, @user_id}) => + cb(e) + + (cb) => + FixturesManager.setUpDoc @project_id, {@lines, @version, @ops, @ranges}, (e, {@doc_id}) => + cb(e) + + (cb) => + @client = RealTimeClient.connect() + @client.on "connectionAccepted", cb + + (cb) => + @client.emit "joinProject", project_id: @project_id, cb + + (cb) => + @client.emit "joinDoc", @doc_id, @options, (error, @returnedArgs...) => cb(error) + ], done + + it "should get the doc from the doc updater with the default fromVersion", -> + MockDocUpdaterServer.getDocument + .calledWith(@project_id, @doc_id, -1) + .should.equal true + + it "should return the doc lines, version, ranges and ops", -> + @returnedArgs.should.deep.equal [@lines, @version, @ops, @ranges] + + it "should have joined the doc room", (done) -> + RealTimeClient.getConnectedClient @client.socket.sessionid, (error, client) => + expect(@doc_id in client.rooms).to.equal true + done() + + describe "with fromVersion and options", -> + before (done) -> + @fromVersion = 36 + @options = { encodeRanges: true } + async.series [ + (cb) => + FixturesManager.setUpProject { + privilegeLevel: "readAndWrite" + }, (e, {@project_id, @user_id}) => + cb(e) + + (cb) => + FixturesManager.setUpDoc @project_id, {@lines, @version, @ops, @ranges}, (e, {@doc_id}) => + cb(e) + + (cb) => + @client = RealTimeClient.connect() + @client.on "connectionAccepted", cb + + (cb) => + @client.emit "joinProject", project_id: @project_id, cb + + (cb) => + @client.emit "joinDoc", @doc_id, @fromVersion, @options, (error, @returnedArgs...) => cb(error) + ], done + + it "should get the doc from the doc updater with the fromVersion", -> + MockDocUpdaterServer.getDocument + .calledWith(@project_id, @doc_id, @fromVersion) + .should.equal true + + it "should return the doc lines, version, ranges and ops", -> + @returnedArgs.should.deep.equal [@lines, @version, @ops, @ranges] + + it "should have joined the doc room", (done) -> + RealTimeClient.getConnectedClient @client.socket.sessionid, (error, client) => + expect(@doc_id in client.rooms).to.equal true + done() From ce2238c5d8242767ba8ab2537b428fb8100b10d3 Mon Sep 17 00:00:00 2001 From: Joe Green Date: Thu, 12 Oct 2017 16:56:13 +0100 Subject: [PATCH 21/28] only alert on master --- services/real-time/Jenkinsfile | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile index b684c49eb0..96ee723b26 100644 --- a/services/real-time/Jenkinsfile +++ b/services/real-time/Jenkinsfile @@ -70,6 +70,10 @@ pipeline { post { failure { + when { + branch 'master' + } + mail(from: "${EMAIL_ALERT_FROM}", to: "${EMAIL_ALERT_TO}", subject: "Jenkins build failed: ${JOB_NAME}:${BUILD_NUMBER}", From acc0193211dcdb35f67c36fcad793bdd0f8b8c69 Mon Sep 17 00:00:00 2001 From: Joe Green Date: Mon, 16 Oct 2017 14:13:20 +0100 Subject: [PATCH 22/28] Update Jenkinsfile --- services/real-time/Jenkinsfile | 4 ---- 1 file changed, 4 deletions(-) diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile index 96ee723b26..b684c49eb0 100644 --- a/services/real-time/Jenkinsfile +++ b/services/real-time/Jenkinsfile @@ -70,10 +70,6 @@ pipeline { post { failure { - when { - branch 'master' - } - mail(from: "${EMAIL_ALERT_FROM}", to: "${EMAIL_ALERT_TO}", subject: "Jenkins build failed: ${JOB_NAME}:${BUILD_NUMBER}", From 168d64632801a516ae9f253a0043e345d0596af2 Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Fri, 20 Oct 2017 15:19:20 +0100 Subject: [PATCH 23/28] exit if mock servers fail to start --- .../acceptance/coffee/helpers/MockDocUpdaterServer.coffee | 6 +++++- .../test/acceptance/coffee/helpers/MockWebServer.coffee | 6 +++++- 2 files changed, 10 insertions(+), 2 deletions(-) diff --git a/services/real-time/test/acceptance/coffee/helpers/MockDocUpdaterServer.coffee b/services/real-time/test/acceptance/coffee/helpers/MockDocUpdaterServer.coffee index 0f196371b3..ac5bfc7093 100644 --- a/services/real-time/test/acceptance/coffee/helpers/MockDocUpdaterServer.coffee +++ b/services/real-time/test/acceptance/coffee/helpers/MockDocUpdaterServer.coffee @@ -38,5 +38,9 @@ module.exports = MockDocUpdaterServer = app.listen 3003, (error) -> MockDocUpdaterServer.running = true callback(error) + .on "error", (error) -> + console.error "error starting MockDocUpdaterServer:", error.message + process.exit(1) + -sinon.spy MockDocUpdaterServer, "getDocument" \ No newline at end of file +sinon.spy MockDocUpdaterServer, "getDocument" diff --git a/services/real-time/test/acceptance/coffee/helpers/MockWebServer.coffee b/services/real-time/test/acceptance/coffee/helpers/MockWebServer.coffee index 2fff23e252..06f52a6b19 100644 --- a/services/real-time/test/acceptance/coffee/helpers/MockWebServer.coffee +++ b/services/real-time/test/acceptance/coffee/helpers/MockWebServer.coffee @@ -35,5 +35,9 @@ module.exports = MockWebServer = app.listen 3000, (error) -> MockWebServer.running = true callback(error) + .on "error", (error) -> + console.error "error starting MockWebServer:", error.message + process.exit(1) + -sinon.spy MockWebServer, "joinProject" \ No newline at end of file +sinon.spy MockWebServer, "joinProject" From 510ee6bf4f894a33f34df855ff086e3995bf55c9 Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Mon, 30 Oct 2017 13:43:36 +0000 Subject: [PATCH 24/28] use ioredis 3 via redis-sharelatex --- services/real-time/package.json | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/services/real-time/package.json b/services/real-time/package.json index 4b3de3d5f3..15600c14e1 100644 --- a/services/real-time/package.json +++ b/services/real-time/package.json @@ -18,7 +18,7 @@ "ioredis": "^2.4.0", "logger-sharelatex": "git+https://github.com/sharelatex/logger-sharelatex.git#v1.1.0", "metrics-sharelatex": "git+https://github.com/sharelatex/metrics-sharelatex.git#v1.4.0", - "redis-sharelatex": "git+https://github.com/sharelatex/redis-sharelatex.git#v1.0.2", + "redis-sharelatex": "git+https://github.com/sharelatex/redis-sharelatex.git#v1.0.4", "request": "~2.34.0", "session.socket.io": "^0.1.6", "settings-sharelatex": "git+https://github.com/sharelatex/settings-sharelatex.git#v1.0.0", From cc118fa2304d33a159ece66575217d022c68e3ba Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Mon, 30 Oct 2017 13:44:09 +0000 Subject: [PATCH 25/28] remove unnecessary ioredis package --- services/real-time/package.json | 1 - 1 file changed, 1 deletion(-) diff --git a/services/real-time/package.json b/services/real-time/package.json index 15600c14e1..cb097f8b78 100644 --- a/services/real-time/package.json +++ b/services/real-time/package.json @@ -15,7 +15,6 @@ "cookie-parser": "^1.3.3", "express": "^4.10.1", "express-session": "^1.9.1", - "ioredis": "^2.4.0", "logger-sharelatex": "git+https://github.com/sharelatex/logger-sharelatex.git#v1.1.0", "metrics-sharelatex": "git+https://github.com/sharelatex/metrics-sharelatex.git#v1.4.0", "redis-sharelatex": "git+https://github.com/sharelatex/redis-sharelatex.git#v1.0.4", From 0568aada17eef463ba7a70995b9f05880d8a1e0c Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Mon, 30 Oct 2017 13:46:37 +0000 Subject: [PATCH 26/28] upgrade to node 6 --- services/real-time/.nvmrc | 2 +- services/real-time/Jenkinsfile | 4 ++-- 2 files changed, 3 insertions(+), 3 deletions(-) diff --git a/services/real-time/.nvmrc b/services/real-time/.nvmrc index d87edbfc10..26ec038c18 100644 --- a/services/real-time/.nvmrc +++ b/services/real-time/.nvmrc @@ -1 +1 @@ -4.2.1 \ No newline at end of file +6.9.5 \ No newline at end of file diff --git a/services/real-time/Jenkinsfile b/services/real-time/Jenkinsfile index b684c49eb0..d908d42063 100644 --- a/services/real-time/Jenkinsfile +++ b/services/real-time/Jenkinsfile @@ -15,7 +15,7 @@ pipeline { stage('Install') { agent { docker { - image 'node:4.2.1' + image 'node:6.9.5' args "-v /var/lib/jenkins/.npm:/tmp/.npm -e HOME=/tmp" reuseNode true } @@ -33,7 +33,7 @@ pipeline { stage('Compile and Test') { agent { docker { - image 'node:4.2.1' + image 'node:6.9.5' args "-v /var/lib/jenkins/.npm:/tmp/.npm -e HOME=/tmp" reuseNode true } From 009f8a3eae5e34bbea63d15ff2b09c02d568ffbe Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Mon, 30 Oct 2017 16:14:29 +0000 Subject: [PATCH 27/28] add sentry support --- services/real-time/app.coffee | 2 ++ services/real-time/package.json | 2 +- 2 files changed, 3 insertions(+), 1 deletion(-) diff --git a/services/real-time/app.coffee b/services/real-time/app.coffee index 0365f773c6..23ce867841 100644 --- a/services/real-time/app.coffee +++ b/services/real-time/app.coffee @@ -1,5 +1,7 @@ logger = require "logger-sharelatex" logger.initialize("real-time-sharelatex") +if Settings.sentry?.dsn? + logger.initializeErrorReporting(Settings.sentry.dsn) express = require("express") session = require("express-session") diff --git a/services/real-time/package.json b/services/real-time/package.json index cb097f8b78..8cfb35291a 100644 --- a/services/real-time/package.json +++ b/services/real-time/package.json @@ -15,7 +15,7 @@ "cookie-parser": "^1.3.3", "express": "^4.10.1", "express-session": "^1.9.1", - "logger-sharelatex": "git+https://github.com/sharelatex/logger-sharelatex.git#v1.1.0", + "logger-sharelatex": "git+https://github.com/sharelatex/logger-sharelatex.git#v1.5.6", "metrics-sharelatex": "git+https://github.com/sharelatex/metrics-sharelatex.git#v1.4.0", "redis-sharelatex": "git+https://github.com/sharelatex/redis-sharelatex.git#v1.0.4", "request": "~2.34.0", From 5c8291a8da7c9e1b8d3da60ed0b8c15f58ff7e9f Mon Sep 17 00:00:00 2001 From: Brian Gough Date: Tue, 6 Jun 2017 09:49:38 +0100 Subject: [PATCH 28/28] fix sentry initialisation --- services/real-time/app.coffee | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/services/real-time/app.coffee b/services/real-time/app.coffee index 23ce867841..824cdce5db 100644 --- a/services/real-time/app.coffee +++ b/services/real-time/app.coffee @@ -1,12 +1,12 @@ logger = require "logger-sharelatex" logger.initialize("real-time-sharelatex") -if Settings.sentry?.dsn? - logger.initializeErrorReporting(Settings.sentry.dsn) express = require("express") session = require("express-session") redis = require("redis-sharelatex") Settings = require "settings-sharelatex" +if Settings.sentry?.dsn? + logger.initializeErrorReporting(Settings.sentry.dsn) sessionRedisClient = redis.createClient(Settings.redis.websessions)