mirror of
https://github.com/yu-i-i/overleaf-cep.git
synced 2026-06-02 13:49:00 +02:00
Geolocate user on login, and pass country-code to editing-sessions
This commit is contained in:
@@ -6,9 +6,10 @@ module.exports = AnalyticsController =
|
||||
updateEditingSession: (req, res, next) ->
|
||||
userId = AuthenticationController.getLoggedInUserId(req)
|
||||
projectId = req.params.projectId
|
||||
countryCode = req.session.countryCode || null
|
||||
|
||||
if userId?
|
||||
AnalyticsManager.updateEditingSession userId, projectId, {}, (error) ->
|
||||
AnalyticsManager.updateEditingSession userId, projectId, countryCode, {}, (error) ->
|
||||
respondWith(error, res, next)
|
||||
else
|
||||
res.send 204
|
||||
|
||||
@@ -43,7 +43,7 @@ module.exports =
|
||||
opts.qs = {fromV2: 1}
|
||||
makeRequest opts, callback
|
||||
|
||||
updateEditingSession: (userId, projectId, segmentation = {}, callback = (error) ->) ->
|
||||
updateEditingSession: (userId, projectId, countryCode, segmentation = {}, callback = (error) ->) ->
|
||||
if userId+"" == settings.smokeTest?.userId+""
|
||||
return callback()
|
||||
opts =
|
||||
@@ -56,6 +56,7 @@ module.exports =
|
||||
qs:
|
||||
userId: userId
|
||||
projectId: projectId
|
||||
countryCode: countryCode || undefined
|
||||
maxAttempts: 20
|
||||
retryDelay: 5000
|
||||
if settings.overleaf?
|
||||
|
||||
@@ -12,6 +12,7 @@ UserHandler = require("../User/UserHandler")
|
||||
UserSessionsManager = require("../User/UserSessionsManager")
|
||||
Analytics = require "../Analytics/AnalyticsManager"
|
||||
passport = require 'passport'
|
||||
GeoIpLookup = require '../../infrastructure/GeoIpLookup'
|
||||
|
||||
module.exports = AuthenticationController =
|
||||
|
||||
@@ -47,12 +48,17 @@ module.exports = AuthenticationController =
|
||||
req.session[key] = value
|
||||
# copy to the old `session.user` location, for backward-comptability
|
||||
req.session.user = req.session.passport.user
|
||||
req.session.save (err) ->
|
||||
# try to geolocate the user to a country-code
|
||||
GeoIpLookup.getDetails req.ip, (err, geoDetails) ->
|
||||
if err?
|
||||
logger.err {user_id: user._id}, "error saving regenerated session after login"
|
||||
return callback(err)
|
||||
UserSessionsManager.trackSession(user, req.sessionID, () ->)
|
||||
callback(null)
|
||||
logger.err {err, ip: req.ip}, "error geolocating session, continuing"
|
||||
req.session.countryCode = geoDetails?.country_code || null
|
||||
req.session.save (err) ->
|
||||
if err?
|
||||
logger.err {user_id: user._id}, "error saving regenerated session after login"
|
||||
return callback(err)
|
||||
UserSessionsManager.trackSession(user, req.sessionID, () ->)
|
||||
callback(err)
|
||||
|
||||
passportLogin: (req, res, next) ->
|
||||
# This function is middleware which wraps the passport.authenticate middleware,
|
||||
|
||||
@@ -31,6 +31,7 @@ module.exports = GeoIpLookup =
|
||||
e = new Error("no ip passed")
|
||||
return callback(e)
|
||||
ip = ip.trim().split(" ")[0]
|
||||
console.log ">> ", URL.resolve(settings.apis.geoIpLookup.url,ip)
|
||||
opts =
|
||||
url: URL.resolve(settings.apis.geoIpLookup.url,ip)
|
||||
timeout: 1000
|
||||
@@ -49,4 +50,4 @@ module.exports = GeoIpLookup =
|
||||
countryCode = ipDetails?.country_code?.toUpperCase()
|
||||
currencyCode = currencyMappings[countryCode] || "USD"
|
||||
logger.log ip:ip, currencyCode:currencyCode, ipDetails:ipDetails, "got currencyCode for ip"
|
||||
callback(err, currencyCode, countryCode)
|
||||
callback(err, currencyCode, countryCode)
|
||||
|
||||
@@ -139,7 +139,7 @@ module.exports = settings =
|
||||
apiKey: ""
|
||||
subdomain: ""
|
||||
geoIpLookup:
|
||||
url: "http://#{process.env['GEOIP_HOST'] or 'localhost'}:8080/json"
|
||||
url: "http://#{process.env['GEOIP_HOST'] or 'localhost'}:8080/json/"
|
||||
realTime:
|
||||
url: "http://#{process.env['REALTIME_HOST'] or 'localhost'}:3026"
|
||||
contacts:
|
||||
|
||||
@@ -14,7 +14,7 @@ describe 'AnalyticsController', ->
|
||||
getLoggedInUserId: sinon.stub()
|
||||
|
||||
@AnalyticsManager =
|
||||
updateEditingSession: sinon.stub().callsArgWith(3)
|
||||
updateEditingSession: sinon.stub().callsArgWith(4)
|
||||
recordEvent: sinon.stub().callsArgWith(3)
|
||||
|
||||
@controller = SandboxedModule.require modulePath, requires:
|
||||
@@ -31,12 +31,18 @@ describe 'AnalyticsController', ->
|
||||
@req =
|
||||
params:
|
||||
projectId: "a project id"
|
||||
session: {countryCode: 'US'}
|
||||
|
||||
it "delegates to the AnalyticsManager", (done) ->
|
||||
@AuthenticationController.getLoggedInUserId.returns("1234")
|
||||
@controller.updateEditingSession @req, @res
|
||||
|
||||
@AnalyticsManager.updateEditingSession.calledWith("1234", "a project id", {}).should.equal true
|
||||
@AnalyticsManager.updateEditingSession.calledWith(
|
||||
"1234",
|
||||
"a project id",
|
||||
'US',
|
||||
{}
|
||||
).should.equal true
|
||||
done()
|
||||
|
||||
describe "recordEvent", ->
|
||||
@@ -46,6 +52,7 @@ describe 'AnalyticsController', ->
|
||||
event:"i_did_something"
|
||||
body:"stuff"
|
||||
sessionID: "sessionIDHere"
|
||||
session: {}
|
||||
|
||||
it "should use the user_id", (done)->
|
||||
@AuthenticationController.getLoggedInUserId.returns("1234")
|
||||
|
||||
@@ -28,6 +28,8 @@ describe "AuthenticationController", ->
|
||||
trackSession: sinon.stub()
|
||||
untrackSession: sinon.stub()
|
||||
revokeAllUserSessions: sinon.stub().callsArgWith(1, null)
|
||||
"../../infrastructure/GeoIpLookup": @GeoIpLookup =
|
||||
getDetails: sinon.stub().callsArgWith(1, null, {})
|
||||
@user =
|
||||
_id: ObjectId()
|
||||
email: @email = "USER@example.com"
|
||||
@@ -172,6 +174,8 @@ describe "AuthenticationController", ->
|
||||
@req.session.save = sinon.stub().callsArgWith(0, null)
|
||||
@req.sessionStore = {generate: sinon.stub()}
|
||||
@UserSessionsManager.trackSession = sinon.stub()
|
||||
@GeoIpLookup.getDetails = sinon.stub()
|
||||
.callsArgWith(1, null, @geoDetails = {country_code: 'US'})
|
||||
@call = (callback) =>
|
||||
@AuthenticationController.afterLoginSessionSetup @req, @user, callback
|
||||
|
||||
@@ -185,16 +189,23 @@ describe "AuthenticationController", ->
|
||||
@req.login.callCount.should.equal 1
|
||||
done()
|
||||
|
||||
it 'should call req.session.save', (done) ->
|
||||
@call (err) =>
|
||||
@req.session.save.callCount.should.equal 1
|
||||
done()
|
||||
|
||||
it 'should call UserSessionsManager.trackSession', (done) ->
|
||||
@call (err) =>
|
||||
@UserSessionsManager.trackSession.callCount.should.equal 1
|
||||
done()
|
||||
|
||||
it 'should call GeoIpLookup.getDetails', (done) ->
|
||||
@call (err) =>
|
||||
@GeoIpLookup.getDetails.callCount.should.equal 1
|
||||
@req.session.countryCode.should.exist
|
||||
@req.session.countryCode.should.equal @geoDetails.country_code
|
||||
done()
|
||||
|
||||
it 'should call req.session.save', (done) ->
|
||||
@call (err) =>
|
||||
@req.session.save.callCount.should.equal 1
|
||||
done()
|
||||
|
||||
describe 'when req.session.save produces an error', ->
|
||||
|
||||
beforeEach ->
|
||||
@@ -211,6 +222,39 @@ describe "AuthenticationController", ->
|
||||
@UserSessionsManager.trackSession.callCount.should.equal 0
|
||||
done()
|
||||
|
||||
describe 'when GeoIpLookup produces an error', ->
|
||||
beforeEach ->
|
||||
@GeoIpLookup.getDetails = sinon.stub()
|
||||
.callsArgWith(1, new Error('woops'))
|
||||
|
||||
it 'should not produce an error', (done) ->
|
||||
@call (err) =>
|
||||
expect(err).to.not.exist
|
||||
done()
|
||||
|
||||
it 'should still call req.session.save', (done) ->
|
||||
@call (err) =>
|
||||
@req.session.save.callCount.should.equal 1
|
||||
expect(@req.session.countryCode).to.equal null
|
||||
done()
|
||||
|
||||
describe 'when GeoIpLookup produces no data', ->
|
||||
beforeEach ->
|
||||
@GeoIpLookup.getDetails = sinon.stub()
|
||||
.callsArgWith(1, null, undefined)
|
||||
|
||||
it 'should not produce an error', (done) ->
|
||||
@call (err) =>
|
||||
expect(err).to.not.exist
|
||||
done()
|
||||
|
||||
it 'should still call req.session.save', (done) ->
|
||||
@call (err) =>
|
||||
@req.session.save.callCount.should.equal 1
|
||||
expect(@req.session.countryCode).to.equal null
|
||||
done()
|
||||
|
||||
|
||||
describe 'getSessionUser', ->
|
||||
|
||||
it 'should get the user object from session', ->
|
||||
|
||||
Reference in New Issue
Block a user