mirror of
https://github.com/overleaf/overleaf.git
synced 2024-11-21 20:47:08 -05:00
Merge pull request #13510 from overleaf/em-promisify-clsi-manager
Clean up of ClsiManager and ClsiCookieManager GitOrigin-RevId: e5047b253613e87fd6cb4f12855b821028fcaf8e
This commit is contained in:
parent
8cdfffa6f9
commit
1fc13b8cbf
5 changed files with 1723 additions and 2088 deletions
|
@ -1,32 +1,19 @@
|
|||
/* eslint-disable
|
||||
n/handle-callback-err,
|
||||
max-len,
|
||||
*/
|
||||
// TODO: This file was created by bulk-decaffeinate.
|
||||
// Fix any style issues and re-enable lint.
|
||||
/*
|
||||
* decaffeinate suggestions:
|
||||
* DS102: Remove unnecessary code created because of implicit returns
|
||||
* DS207: Consider shorter variations of null checks
|
||||
* Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md
|
||||
*/
|
||||
let rclientSecondary
|
||||
const { URL, URLSearchParams } = require('url')
|
||||
const OError = require('@overleaf/o-error')
|
||||
const Settings = require('@overleaf/settings')
|
||||
const request = require('request').defaults({ timeout: 30 * 1000 })
|
||||
const RedisWrapper = require('../../infrastructure/RedisWrapper')
|
||||
const rclient = RedisWrapper.client('clsi_cookie')
|
||||
if (Settings.redis.clsi_cookie_secondary != null) {
|
||||
rclientSecondary = RedisWrapper.client('clsi_cookie_secondary')
|
||||
}
|
||||
const Cookie = require('cookie')
|
||||
const logger = require('@overleaf/logger')
|
||||
const Metrics = require('@overleaf/metrics')
|
||||
|
||||
const clsiCookiesEnabled =
|
||||
(Settings.clsiCookie != null ? Settings.clsiCookie.key : undefined) != null &&
|
||||
Settings.clsiCookie.key.length !== 0
|
||||
const clsiCookiesEnabled = (Settings.clsiCookie?.key ?? '') !== ''
|
||||
|
||||
const rclient = RedisWrapper.client('clsi_cookie')
|
||||
let rclientSecondary
|
||||
if (Settings.redis.clsi_cookie_secondary != null) {
|
||||
rclientSecondary = RedisWrapper.client('clsi_cookie_secondary')
|
||||
}
|
||||
|
||||
module.exports = function (backendGroup) {
|
||||
return {
|
||||
|
@ -45,15 +32,12 @@ module.exports = function (backendGroup) {
|
|||
compileBackendClass,
|
||||
callback
|
||||
) {
|
||||
if (callback == null) {
|
||||
callback = function () {}
|
||||
}
|
||||
return rclient.get(this.buildKey(projectId, userId), (err, serverId) => {
|
||||
if (err != null) {
|
||||
rclient.get(this.buildKey(projectId, userId), (err, serverId) => {
|
||||
if (err) {
|
||||
return callback(err)
|
||||
}
|
||||
if (serverId == null || serverId === '') {
|
||||
return this._populateServerIdViaRequest(
|
||||
this._populateServerIdViaRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -61,7 +45,7 @@ module.exports = function (backendGroup) {
|
|||
callback
|
||||
)
|
||||
} else {
|
||||
return callback(null, serverId)
|
||||
callback(null, serverId)
|
||||
}
|
||||
})
|
||||
},
|
||||
|
@ -73,16 +57,13 @@ module.exports = function (backendGroup) {
|
|||
compileBackendClass,
|
||||
callback
|
||||
) {
|
||||
if (callback == null) {
|
||||
callback = function () {}
|
||||
}
|
||||
const u = new URL(`${Settings.apis.clsi.url}/project/${projectId}/status`)
|
||||
u.search = new URLSearchParams({
|
||||
compileGroup,
|
||||
compileBackendClass,
|
||||
}).toString()
|
||||
request.post(u.href, (err, res, body) => {
|
||||
if (err != null) {
|
||||
if (err) {
|
||||
OError.tag(err, 'error getting initial server id for project', {
|
||||
project_id: projectId,
|
||||
})
|
||||
|
@ -96,25 +77,21 @@ module.exports = function (backendGroup) {
|
|||
res,
|
||||
null,
|
||||
function (err, serverId) {
|
||||
if (err != null) {
|
||||
if (err) {
|
||||
logger.warn(
|
||||
{ err, projectId },
|
||||
'error setting server id via populate request'
|
||||
)
|
||||
}
|
||||
return callback(err, serverId)
|
||||
callback(err, serverId)
|
||||
}
|
||||
)
|
||||
})
|
||||
},
|
||||
|
||||
_parseServerIdFromResponse(response) {
|
||||
const cookies = Cookie.parse(
|
||||
(response.headers['set-cookie'] != null
|
||||
? response.headers['set-cookie'][0]
|
||||
: undefined) || ''
|
||||
)
|
||||
return cookies != null ? cookies[Settings.clsiCookie.key] : undefined
|
||||
const cookies = Cookie.parse(response.headers['set-cookie']?.[0] || '')
|
||||
return cookies?.[Settings.clsiCookie.key]
|
||||
},
|
||||
|
||||
checkIsLoadSheddingEvent(clsiserverid, compileGroup, compileBackendClass) {
|
||||
|
@ -155,9 +132,6 @@ module.exports = function (backendGroup) {
|
|||
previous,
|
||||
callback
|
||||
) {
|
||||
if (callback == null) {
|
||||
callback = function () {}
|
||||
}
|
||||
if (!clsiCookiesEnabled) {
|
||||
return callback()
|
||||
}
|
||||
|
@ -195,9 +169,6 @@ module.exports = function (backendGroup) {
|
|||
},
|
||||
|
||||
_setServerIdInRedis(rclient, projectId, userId, serverId, callback) {
|
||||
if (callback == null) {
|
||||
callback = function () {}
|
||||
}
|
||||
rclient.setex(
|
||||
this.buildKey(projectId, userId),
|
||||
this._getTTLInSeconds(serverId),
|
||||
|
@ -207,13 +178,10 @@ module.exports = function (backendGroup) {
|
|||
},
|
||||
|
||||
clearServerId(projectId, userId, callback) {
|
||||
if (callback == null) {
|
||||
callback = function () {}
|
||||
}
|
||||
if (!clsiCookiesEnabled) {
|
||||
return callback()
|
||||
}
|
||||
return rclient.del(this.buildKey(projectId, userId), callback)
|
||||
rclient.del(this.buildKey(projectId, userId), callback)
|
||||
},
|
||||
|
||||
getCookieJar(
|
||||
|
@ -223,13 +191,10 @@ module.exports = function (backendGroup) {
|
|||
compileBackendClass,
|
||||
callback
|
||||
) {
|
||||
if (callback == null) {
|
||||
callback = function () {}
|
||||
}
|
||||
if (!clsiCookiesEnabled) {
|
||||
return callback(null, request.jar(), undefined)
|
||||
}
|
||||
return this._getServerId(
|
||||
this._getServerId(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -246,7 +211,7 @@ module.exports = function (backendGroup) {
|
|||
)
|
||||
const jar = request.jar()
|
||||
jar.setCookie(serverCookie, Settings.apis.clsi.url)
|
||||
return callback(null, jar, serverId)
|
||||
callback(null, jar, serverId)
|
||||
}
|
||||
)
|
||||
},
|
||||
|
|
|
@ -8,12 +8,10 @@ const { URL, URLSearchParams } = require('url')
|
|||
const OError = require('@overleaf/o-error')
|
||||
|
||||
const ClsiCookieManager = require('./ClsiCookieManager')(
|
||||
Settings.apis.clsi != null ? Settings.apis.clsi.backendGroupName : undefined
|
||||
Settings.apis.clsi?.backendGroupName
|
||||
)
|
||||
const NewBackendCloudClsiCookieManager = require('./ClsiCookieManager')(
|
||||
Settings.apis.clsi_new != null
|
||||
? Settings.apis.clsi_new.backendGroupName
|
||||
: undefined
|
||||
Settings.apis.clsi_new?.backendGroupName
|
||||
)
|
||||
const ClsiStateManager = require('./ClsiStateManager')
|
||||
const _ = require('underscore')
|
||||
|
@ -40,29 +38,24 @@ function collectMetricsOnBlgFiles(outputFiles) {
|
|||
Metrics.count('blg_output_file', nested, 1, { path: 'nested' })
|
||||
}
|
||||
|
||||
const ClsiManager = {
|
||||
sendRequest(projectId, userId, options, callback) {
|
||||
function sendRequest(projectId, userId, options, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
ClsiManager.sendRequestOnce(
|
||||
projectId,
|
||||
userId,
|
||||
options,
|
||||
(err, status, ...result) => {
|
||||
sendRequestOnce(projectId, userId, options, (err, status, ...result) => {
|
||||
if (err != null) {
|
||||
return callback(err)
|
||||
}
|
||||
if (status === 'conflict') {
|
||||
// Try again, with a full compile
|
||||
return ClsiManager.sendRequestOnce(
|
||||
return sendRequestOnce(
|
||||
projectId,
|
||||
userId,
|
||||
{ ...options, syncType: 'full' },
|
||||
callback
|
||||
)
|
||||
} else if (status === 'unavailable') {
|
||||
return ClsiManager.sendRequestOnce(
|
||||
return sendRequestOnce(
|
||||
projectId,
|
||||
userId,
|
||||
{ ...options, syncType: 'full', forceNewClsiServer: true },
|
||||
|
@ -70,15 +63,14 @@ const ClsiManager = {
|
|||
)
|
||||
}
|
||||
callback(null, status, ...result)
|
||||
})
|
||||
}
|
||||
)
|
||||
},
|
||||
|
||||
sendRequestOnce(projectId, userId, options, callback) {
|
||||
function sendRequestOnce(projectId, userId, options, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
ClsiManager._buildRequest(projectId, options, (err, req) => {
|
||||
_buildRequest(projectId, options, (err, req) => {
|
||||
if (err != null) {
|
||||
if (err.message === 'no main file specified') {
|
||||
return callback(null, 'validation-problems', null, null, {
|
||||
|
@ -93,7 +85,7 @@ const ClsiManager = {
|
|||
)
|
||||
}
|
||||
}
|
||||
ClsiManager._sendBuiltRequest(
|
||||
_sendBuiltRequest(
|
||||
projectId,
|
||||
userId,
|
||||
req,
|
||||
|
@ -108,14 +100,14 @@ const ClsiManager = {
|
|||
}
|
||||
)
|
||||
})
|
||||
},
|
||||
}
|
||||
|
||||
// for public API requests where there is no project id
|
||||
sendExternalRequest(submissionId, clsiRequest, options, callback) {
|
||||
function sendExternalRequest(submissionId, clsiRequest, options, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
ClsiManager._sendBuiltRequest(
|
||||
_sendBuiltRequest(
|
||||
submissionId,
|
||||
null,
|
||||
clsiRequest,
|
||||
|
@ -132,14 +124,14 @@ const ClsiManager = {
|
|||
callback(null, status, ...result)
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
stopCompile(projectId, userId, options, callback) {
|
||||
function stopCompile(projectId, userId, options, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
const { compileBackendClass, compileGroup } = options
|
||||
const compilerUrl = this._getCompilerUrl(
|
||||
const compilerUrl = _getCompilerUrl(
|
||||
compileBackendClass,
|
||||
compileGroup,
|
||||
projectId,
|
||||
|
@ -150,7 +142,7 @@ const ClsiManager = {
|
|||
url: compilerUrl,
|
||||
method: 'POST',
|
||||
}
|
||||
ClsiManager._makeRequest(
|
||||
_makeRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -158,14 +150,14 @@ const ClsiManager = {
|
|||
opts,
|
||||
callback
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
deleteAuxFiles(projectId, userId, options, clsiserverid, callback) {
|
||||
function deleteAuxFiles(projectId, userId, options, clsiserverid, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
const { compileBackendClass, compileGroup } = options
|
||||
const compilerUrl = this._getCompilerUrl(
|
||||
const compilerUrl = _getCompilerUrl(
|
||||
compileBackendClass,
|
||||
compileGroup,
|
||||
projectId,
|
||||
|
@ -175,7 +167,7 @@ const ClsiManager = {
|
|||
url: compilerUrl,
|
||||
method: 'DELETE',
|
||||
}
|
||||
ClsiManager._makeRequestWithClsiServerId(
|
||||
_makeRequestWithClsiServerId(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -216,9 +208,9 @@ const ClsiManager = {
|
|||
})
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
_sendBuiltRequest(projectId, userId, req, options, callback) {
|
||||
function _sendBuiltRequest(projectId, userId, req, options, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
|
@ -229,13 +221,7 @@ const ClsiManager = {
|
|||
return callback(err)
|
||||
}
|
||||
options.forceNewClsiServer = false // backend has now been reset
|
||||
return ClsiManager._sendBuiltRequest(
|
||||
projectId,
|
||||
userId,
|
||||
req,
|
||||
options,
|
||||
callback
|
||||
)
|
||||
_sendBuiltRequest(projectId, userId, req, options, callback)
|
||||
})
|
||||
}
|
||||
ClsiFormatChecker.checkRecoursesForProblems(
|
||||
|
@ -262,7 +248,7 @@ const ClsiManager = {
|
|||
validationProblems
|
||||
)
|
||||
}
|
||||
ClsiManager._postToClsi(
|
||||
_postToClsi(
|
||||
projectId,
|
||||
userId,
|
||||
req,
|
||||
|
@ -277,7 +263,7 @@ const ClsiManager = {
|
|||
})
|
||||
)
|
||||
}
|
||||
const outputFiles = ClsiManager._parseOutputFiles(
|
||||
const outputFiles = _parseOutputFiles(
|
||||
projectId,
|
||||
response && response.compile && response.compile.outputFiles
|
||||
)
|
||||
|
@ -302,9 +288,9 @@ const ClsiManager = {
|
|||
)
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
_makeRequestWithClsiServerId(
|
||||
function _makeRequestWithClsiServerId(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -328,7 +314,7 @@ const ClsiManager = {
|
|||
callback(null, response, body)
|
||||
})
|
||||
} else {
|
||||
ClsiManager._makeRequest(
|
||||
_makeRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -337,9 +323,9 @@ const ClsiManager = {
|
|||
callback
|
||||
)
|
||||
}
|
||||
},
|
||||
}
|
||||
|
||||
_makeRequest(
|
||||
function _makeRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -414,7 +400,7 @@ const ClsiManager = {
|
|||
},
|
||||
newBackend(cb) {
|
||||
const startTime = new Date()
|
||||
ClsiManager._makeNewBackendRequest(
|
||||
_makeNewBackendRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -425,9 +411,7 @@ const ClsiManager = {
|
|||
logger.warn({ err }, 'Error making request to new CLSI backend')
|
||||
}
|
||||
if (response != null) {
|
||||
Metrics.inc(
|
||||
`compile.newBackend.response.${response.statusCode}`
|
||||
)
|
||||
Metrics.inc(`compile.newBackend.response.${response.statusCode}`)
|
||||
}
|
||||
cb(err, {
|
||||
response,
|
||||
|
@ -463,9 +447,9 @@ const ClsiManager = {
|
|||
}
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
_makeNewBackendRequest(
|
||||
function _makeNewBackendRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -529,9 +513,9 @@ const ClsiManager = {
|
|||
})
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
_getCompilerUrl(
|
||||
function _getCompilerUrl(
|
||||
compileBackendClass,
|
||||
compileGroup,
|
||||
projectId,
|
||||
|
@ -550,9 +534,9 @@ const ClsiManager = {
|
|||
compileGroup,
|
||||
}).toString()
|
||||
return u.href
|
||||
},
|
||||
}
|
||||
|
||||
_postToClsi(
|
||||
function _postToClsi(
|
||||
projectId,
|
||||
userId,
|
||||
req,
|
||||
|
@ -560,7 +544,7 @@ const ClsiManager = {
|
|||
compileGroup,
|
||||
callback
|
||||
) {
|
||||
const compileUrl = this._getCompilerUrl(
|
||||
const compileUrl = _getCompilerUrl(
|
||||
compileBackendClass,
|
||||
compileGroup,
|
||||
projectId,
|
||||
|
@ -572,7 +556,7 @@ const ClsiManager = {
|
|||
json: req,
|
||||
method: 'POST',
|
||||
}
|
||||
ClsiManager._makeRequest(
|
||||
_makeRequest(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -605,24 +589,21 @@ const ClsiManager = {
|
|||
callback(null, { compile: { status: 'unavailable' } })
|
||||
} else {
|
||||
callback(
|
||||
new OError(
|
||||
`CLSI returned non-success code: ${response.statusCode}`,
|
||||
{
|
||||
new OError(`CLSI returned non-success code: ${response.statusCode}`, {
|
||||
projectId,
|
||||
userId,
|
||||
compileOptions: req.compile.options,
|
||||
rootResourcePath: req.compile.rootResourcePath,
|
||||
clsiResponse: body,
|
||||
statusCode: response.statusCode,
|
||||
}
|
||||
)
|
||||
})
|
||||
)
|
||||
}
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
_parseOutputFiles(projectId, rawOutputFiles = []) {
|
||||
function _parseOutputFiles(projectId, rawOutputFiles = []) {
|
||||
const outputFiles = []
|
||||
for (const file of rawOutputFiles) {
|
||||
const f = {
|
||||
|
@ -641,9 +622,9 @@ const ClsiManager = {
|
|||
outputFiles.push(f)
|
||||
}
|
||||
return outputFiles
|
||||
},
|
||||
}
|
||||
|
||||
_buildRequest(projectId, options, callback) {
|
||||
function _buildRequest(projectId, options, callback) {
|
||||
if (options == null) {
|
||||
options = {}
|
||||
}
|
||||
|
@ -652,9 +633,7 @@ const ClsiManager = {
|
|||
{ compiler: 1, rootDoc_id: 1, imageName: 1, rootFolder: 1 },
|
||||
(err, project) => {
|
||||
if (err != null) {
|
||||
return callback(
|
||||
OError.tag(err, 'failed to get project', { projectId })
|
||||
)
|
||||
return callback(OError.tag(err, 'failed to get project', { projectId }))
|
||||
}
|
||||
if (project == null) {
|
||||
return callback(
|
||||
|
@ -668,7 +647,7 @@ const ClsiManager = {
|
|||
if (options.incrementalCompilesEnabled || options.syncType != null) {
|
||||
// new way, either incremental or full
|
||||
const timer = new Metrics.Timer('editor.compile-getdocs-redis')
|
||||
ClsiManager.getContentFromDocUpdaterIfMatch(
|
||||
getContentFromDocUpdaterIfMatch(
|
||||
projectId,
|
||||
project,
|
||||
options,
|
||||
|
@ -687,7 +666,7 @@ const ClsiManager = {
|
|||
err == null
|
||||
) {
|
||||
Metrics.inc('compile-from-redis')
|
||||
ClsiManager._buildRequestFromDocupdater(
|
||||
_buildRequestFromDocupdater(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
|
@ -697,7 +676,7 @@ const ClsiManager = {
|
|||
)
|
||||
} else {
|
||||
Metrics.inc('compile-from-mongo')
|
||||
ClsiManager._buildRequestFromMongo(
|
||||
_buildRequestFromMongo(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
|
@ -710,7 +689,7 @@ const ClsiManager = {
|
|||
} else {
|
||||
// old way, always from mongo
|
||||
const timer = new Metrics.Timer('editor.compile-getdocs-mongo')
|
||||
ClsiManager._getContentFromMongo(projectId, (err, docs, files) => {
|
||||
_getContentFromMongo(projectId, (err, docs, files) => {
|
||||
timer.done()
|
||||
if (err != null) {
|
||||
return callback(
|
||||
|
@ -719,21 +698,19 @@ const ClsiManager = {
|
|||
})
|
||||
)
|
||||
}
|
||||
ClsiManager._finaliseRequest(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
docs,
|
||||
files,
|
||||
callback
|
||||
)
|
||||
_finaliseRequest(projectId, options, project, docs, files, callback)
|
||||
})
|
||||
}
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
getContentFromDocUpdaterIfMatch(projectId, project, options, callback) {
|
||||
function getContentFromDocUpdaterIfMatch(
|
||||
projectId,
|
||||
project,
|
||||
options,
|
||||
callback
|
||||
) {
|
||||
let projectStateHash
|
||||
try {
|
||||
projectStateHash = ClsiStateManager.computeHash(project, options)
|
||||
|
@ -755,9 +732,9 @@ const ClsiManager = {
|
|||
callback(null, projectStateHash, docs)
|
||||
}
|
||||
)
|
||||
},
|
||||
}
|
||||
|
||||
getOutputFileStream(
|
||||
function getOutputFileStream(
|
||||
projectId,
|
||||
userId,
|
||||
options,
|
||||
|
@ -775,9 +752,9 @@ const ClsiManager = {
|
|||
qs: { compileBackendClass, compileGroup, clsiserverid: clsiServerId },
|
||||
})
|
||||
callback(null, readStream)
|
||||
},
|
||||
}
|
||||
|
||||
_buildRequestFromDocupdater(
|
||||
function _buildRequestFromDocupdater(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
|
@ -816,24 +793,17 @@ const ClsiManager = {
|
|||
}
|
||||
}
|
||||
}
|
||||
ClsiManager._finaliseRequest(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
docs,
|
||||
[],
|
||||
callback
|
||||
)
|
||||
},
|
||||
_finaliseRequest(projectId, options, project, docs, [], callback)
|
||||
}
|
||||
|
||||
_buildRequestFromMongo(
|
||||
function _buildRequestFromMongo(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
projectStateHash,
|
||||
callback
|
||||
) {
|
||||
ClsiManager._getContentFromMongo(projectId, (err, docs, files) => {
|
||||
_getContentFromMongo(projectId, (err, docs, files) => {
|
||||
if (err != null) {
|
||||
return callback(
|
||||
OError.tag(err, 'failed to get project contents from Mongo', {
|
||||
|
@ -846,18 +816,11 @@ const ClsiManager = {
|
|||
syncType: 'full',
|
||||
syncState: projectStateHash,
|
||||
}
|
||||
ClsiManager._finaliseRequest(
|
||||
projectId,
|
||||
options,
|
||||
project,
|
||||
docs,
|
||||
files,
|
||||
callback
|
||||
)
|
||||
_finaliseRequest(projectId, options, project, docs, files, callback)
|
||||
})
|
||||
},
|
||||
}
|
||||
|
||||
_getContentFromMongo(projectId, callback) {
|
||||
function _getContentFromMongo(projectId, callback) {
|
||||
DocumentUpdaterHandler.flushProjectToMongo(projectId, err => {
|
||||
if (err != null) {
|
||||
return callback(
|
||||
|
@ -883,9 +846,9 @@ const ClsiManager = {
|
|||
})
|
||||
})
|
||||
})
|
||||
},
|
||||
}
|
||||
|
||||
_finaliseRequest(projectId, options, project, docs, files, callback) {
|
||||
function _finaliseRequest(projectId, options, project, docs, files, callback) {
|
||||
const resources = []
|
||||
let flags
|
||||
let rootResourcePath = null
|
||||
|
@ -944,7 +907,7 @@ const ClsiManager = {
|
|||
resources.push({
|
||||
path,
|
||||
url: `${Settings.apis.filestore.url}/project/${project._id}/file/${file._id}`,
|
||||
modified: file.created != null ? file.created.getTime() : undefined,
|
||||
modified: file.created?.getTime(),
|
||||
})
|
||||
}
|
||||
|
||||
|
@ -974,11 +937,11 @@ const ClsiManager = {
|
|||
resources,
|
||||
},
|
||||
})
|
||||
},
|
||||
}
|
||||
|
||||
wordCount(projectId, userId, file, options, clsiserverid, callback) {
|
||||
function wordCount(projectId, userId, file, options, clsiserverid, callback) {
|
||||
const { compileBackendClass, compileGroup } = options
|
||||
ClsiManager._buildRequest(projectId, options, (err, req) => {
|
||||
_buildRequest(projectId, options, (err, req) => {
|
||||
if (err != null) {
|
||||
return callback(
|
||||
OError.tag(err, 'Failed to build CLSI request', {
|
||||
|
@ -988,7 +951,7 @@ const ClsiManager = {
|
|||
)
|
||||
}
|
||||
const filename = file || req.compile.rootResourcePath
|
||||
const wordCountUrl = ClsiManager._getCompilerUrl(
|
||||
const wordCountUrl = _getCompilerUrl(
|
||||
compileBackendClass,
|
||||
compileGroup,
|
||||
projectId,
|
||||
|
@ -1004,7 +967,7 @@ const ClsiManager = {
|
|||
json: true,
|
||||
method: 'GET',
|
||||
}
|
||||
ClsiManager._makeRequestWithClsiServerId(
|
||||
_makeRequestWithClsiServerId(
|
||||
projectId,
|
||||
userId,
|
||||
compileGroup,
|
||||
|
@ -1013,9 +976,7 @@ const ClsiManager = {
|
|||
clsiserverid,
|
||||
(err, response, body) => {
|
||||
if (err != null) {
|
||||
return callback(
|
||||
OError.tag(err, 'CLSI request failed', { projectId })
|
||||
)
|
||||
return callback(OError.tag(err, 'CLSI request failed', { projectId }))
|
||||
}
|
||||
if (response.statusCode >= 200 && response.statusCode < 300) {
|
||||
callback(null, body)
|
||||
|
@ -1034,7 +995,13 @@ const ClsiManager = {
|
|||
}
|
||||
)
|
||||
})
|
||||
},
|
||||
}
|
||||
|
||||
module.exports = ClsiManager
|
||||
module.exports = {
|
||||
sendRequest,
|
||||
sendExternalRequest,
|
||||
stopCompile,
|
||||
deleteAuxFiles,
|
||||
getOutputFileStream,
|
||||
wordCount,
|
||||
}
|
||||
|
|
|
@ -1272,7 +1272,7 @@ function initialize(webRouter, privateApiRouter, publicApiRouter) {
|
|||
const sendRes = _.once(function (statusCode, message) {
|
||||
res.status(statusCode)
|
||||
plainTextResponse(res, message)
|
||||
ClsiCookieManager.clearServerId(projectId)
|
||||
ClsiCookieManager.clearServerId(projectId, () => {})
|
||||
}) // force every compile to a new server
|
||||
// set a timeout
|
||||
let handler = setTimeout(function () {
|
||||
|
|
|
@ -1,16 +1,3 @@
|
|||
/* eslint-disable
|
||||
n/handle-callback-err,
|
||||
max-len,
|
||||
no-return-assign,
|
||||
no-unused-vars,
|
||||
*/
|
||||
// TODO: This file was created by bulk-decaffeinate.
|
||||
// Fix any style issues and re-enable lint.
|
||||
/*
|
||||
* decaffeinate suggestions:
|
||||
* DS102: Remove unnecessary code created because of implicit returns
|
||||
* Full docs: https://github.com/decaffeinate/decaffeinate/blob/master/docs/suggestions.md
|
||||
*/
|
||||
const sinon = require('sinon')
|
||||
const { assert, expect } = require('chai')
|
||||
const modulePath = '../../../../app/src/Features/Compile/ClsiCookieManager.js'
|
||||
|
@ -19,7 +6,6 @@ const realRequst = require('request')
|
|||
|
||||
describe('ClsiCookieManager', function () {
|
||||
beforeEach(function () {
|
||||
const self = this
|
||||
this.redis = {
|
||||
auth() {},
|
||||
get: sinon.stub(),
|
||||
|
@ -57,25 +43,28 @@ describe('ClsiCookieManager', function () {
|
|||
'@overleaf/settings': this.settings,
|
||||
request: this.request,
|
||||
}
|
||||
return (this.ClsiCookieManager = SandboxedModule.require(modulePath, {
|
||||
this.ClsiCookieManager = SandboxedModule.require(modulePath, {
|
||||
requires: this.requires,
|
||||
})())
|
||||
})()
|
||||
})
|
||||
|
||||
describe('getServerId', function () {
|
||||
it('should call get for the key', function (done) {
|
||||
this.redis.get.callsArgWith(1, null, 'clsi-7')
|
||||
return this.ClsiCookieManager._getServerId(
|
||||
this.ClsiCookieManager._getServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'',
|
||||
'e2',
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.redis.get
|
||||
.calledWith(`clsiserver:${this.project_id}:${this.user_id}`)
|
||||
.should.equal(true)
|
||||
serverId.should.equal('clsi-7')
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -85,15 +74,18 @@ describe('ClsiCookieManager', function () {
|
|||
.stub()
|
||||
.yields(null)
|
||||
this.redis.get.callsArgWith(1, null)
|
||||
return this.ClsiCookieManager._getServerId(
|
||||
this.ClsiCookieManager._getServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'',
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.ClsiCookieManager._populateServerIdViaRequest
|
||||
.calledWith(this.project_id, this.user_id)
|
||||
.should.equal(true)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -103,16 +95,19 @@ describe('ClsiCookieManager', function () {
|
|||
.stub()
|
||||
.yields(null)
|
||||
this.redis.get.callsArgWith(1, null, '')
|
||||
return this.ClsiCookieManager._getServerId(
|
||||
this.ClsiCookieManager._getServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'',
|
||||
'e2',
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.ClsiCookieManager._populateServerIdViaRequest
|
||||
.calledWith(this.project_id, this.user_id)
|
||||
.should.equal(true)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -122,38 +117,42 @@ describe('ClsiCookieManager', function () {
|
|||
beforeEach(function () {
|
||||
this.response = 'some data'
|
||||
this.request.post.callsArgWith(1, null, this.response)
|
||||
return (this.ClsiCookieManager.setServerId = sinon
|
||||
.stub()
|
||||
.yields(null, 'clsi-9'))
|
||||
this.ClsiCookieManager.setServerId = sinon.stub().yields(null, 'clsi-9')
|
||||
})
|
||||
|
||||
it('should make a request to the clsi', function (done) {
|
||||
return this.ClsiCookieManager._populateServerIdViaRequest(
|
||||
this.ClsiCookieManager._populateServerIdViaRequest(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'standard',
|
||||
'e2',
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
const args = this.ClsiCookieManager.setServerId.args[0]
|
||||
args[0].should.equal(this.project_id)
|
||||
args[1].should.equal(this.user_id)
|
||||
args[2].should.equal('standard')
|
||||
args[3].should.equal('e2')
|
||||
args[4].should.deep.equal(this.response)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
||||
it('should return the server id', function (done) {
|
||||
return this.ClsiCookieManager._populateServerIdViaRequest(
|
||||
this.ClsiCookieManager._populateServerIdViaRequest(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'',
|
||||
'e2',
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
serverId.should.equal('clsi-9')
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -168,7 +167,7 @@ describe('ClsiCookieManager', function () {
|
|||
})
|
||||
|
||||
it('should set the server id with a ttl', function (done) {
|
||||
return this.ClsiCookieManager.setServerId(
|
||||
this.ClsiCookieManager.setServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'standard',
|
||||
|
@ -176,6 +175,9 @@ describe('ClsiCookieManager', function () {
|
|||
this.response,
|
||||
null,
|
||||
err => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.redis.setex
|
||||
.calledWith(
|
||||
`clsiserver:${this.project_id}:${this.user_id}`,
|
||||
|
@ -183,7 +185,7 @@ describe('ClsiCookieManager', function () {
|
|||
'clsi-8'
|
||||
)
|
||||
.should.equal(true)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -200,6 +202,9 @@ describe('ClsiCookieManager', function () {
|
|||
this.response,
|
||||
null,
|
||||
err => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
expect(this.redis.setex).to.have.been.calledWith(
|
||||
`clsiserver:${this.project_id}:${this.user_id}`,
|
||||
this.settings.clsiCookie.ttlInSecondsRegular,
|
||||
|
@ -211,7 +216,7 @@ describe('ClsiCookieManager', function () {
|
|||
})
|
||||
|
||||
it('should return the server id', function (done) {
|
||||
return this.ClsiCookieManager.setServerId(
|
||||
this.ClsiCookieManager.setServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'standard',
|
||||
|
@ -219,8 +224,11 @@ describe('ClsiCookieManager', function () {
|
|||
this.response,
|
||||
null,
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
serverId.should.equal('clsi-8')
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -233,7 +241,7 @@ describe('ClsiCookieManager', function () {
|
|||
},
|
||||
requires: this.requires,
|
||||
})()
|
||||
return this.ClsiCookieManager.setServerId(
|
||||
this.ClsiCookieManager.setServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'standard',
|
||||
|
@ -241,8 +249,11 @@ describe('ClsiCookieManager', function () {
|
|||
this.response,
|
||||
null,
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.redis.setex.called.should.equal(false)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -251,7 +262,7 @@ describe('ClsiCookieManager', function () {
|
|||
this.ClsiCookieManager._parseServerIdFromResponse = sinon
|
||||
.stub()
|
||||
.returns(null)
|
||||
return this.ClsiCookieManager.setServerId(
|
||||
this.ClsiCookieManager.setServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'standard',
|
||||
|
@ -259,8 +270,11 @@ describe('ClsiCookieManager', function () {
|
|||
this.response,
|
||||
null,
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.redis.setex.called.should.equal(false)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -282,7 +296,7 @@ describe('ClsiCookieManager', function () {
|
|||
this.ClsiCookieManager._parseServerIdFromResponse = sinon
|
||||
.stub()
|
||||
.returns('clsi-8')
|
||||
return this.ClsiCookieManager.setServerId(
|
||||
this.ClsiCookieManager.setServerId(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'standard',
|
||||
|
@ -290,6 +304,9 @@ describe('ClsiCookieManager', function () {
|
|||
this.response,
|
||||
null,
|
||||
(err, serverId) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
this.redis_secondary.setex
|
||||
.calledWith(
|
||||
`clsiserver:${this.project_id}:${this.user_id}`,
|
||||
|
@ -297,7 +314,7 @@ describe('ClsiCookieManager', function () {
|
|||
'clsi-8'
|
||||
)
|
||||
.should.equal(true)
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -305,25 +322,26 @@ describe('ClsiCookieManager', function () {
|
|||
|
||||
describe('getCookieJar', function () {
|
||||
beforeEach(function () {
|
||||
return (this.ClsiCookieManager._getServerId = sinon
|
||||
.stub()
|
||||
.yields(null, 'clsi-11'))
|
||||
this.ClsiCookieManager._getServerId = sinon.stub().yields(null, 'clsi-11')
|
||||
})
|
||||
|
||||
it('should return a jar with the cookie set populated from redis', function (done) {
|
||||
return this.ClsiCookieManager.getCookieJar(
|
||||
this.ClsiCookieManager.getCookieJar(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'',
|
||||
'e2',
|
||||
(err, jar) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
jar._jar.store.idx['clsi.example.com']['/'][
|
||||
this.settings.clsiCookie.key
|
||||
].key.should.equal
|
||||
jar._jar.store.idx['clsi.example.com']['/'][
|
||||
this.settings.clsiCookie.key
|
||||
].value.should.equal('clsi-11')
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
@ -336,14 +354,17 @@ describe('ClsiCookieManager', function () {
|
|||
},
|
||||
requires: this.requires,
|
||||
})()
|
||||
return this.ClsiCookieManager.getCookieJar(
|
||||
this.ClsiCookieManager.getCookieJar(
|
||||
this.project_id,
|
||||
this.user_id,
|
||||
'',
|
||||
'e2',
|
||||
(err, jar) => {
|
||||
if (err) {
|
||||
return done(err)
|
||||
}
|
||||
assert.deepEqual(jar, realRequst.jar())
|
||||
return done()
|
||||
done()
|
||||
}
|
||||
)
|
||||
})
|
||||
|
|
File diff suppressed because it is too large
Load diff
Loading…
Reference in a new issue