V1SubscriptionManager.coffee 3.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100
  1. UserGetter = require "../User/UserGetter"
  2. request = require "request"
  3. settings = require "settings-sharelatex"
  4. logger = require "logger-sharelatex"
  5. { V1ConnectionError } = require "../Errors/Errors"
  6. module.exports = V1SubscriptionManager =
  7. # Returned planCode = 'v1_pro' | 'v1_pro_plus' | 'v1_student' | 'v1_free' | null
  8. # For this to work, we need plans in settings with plan-codes:
  9. # - 'v1_pro'
  10. # - 'v1_pro_plus'
  11. # - 'v1_student'
  12. # - 'v1_free'
  13. getPlanCodeFromV1: (userId, callback=(err, planCode, v1Id)->) ->
  14. logger.log {userId}, "[V1SubscriptionManager] fetching v1 plan for user"
  15. V1SubscriptionManager._v1Request userId, {
  16. method: 'GET',
  17. url: (v1Id) -> "/api/v1/sharelatex/users/#{v1Id}/plan_code"
  18. }, (error, body, v1Id) ->
  19. return callback(error) if error?
  20. planName = body?.plan_name
  21. logger.log {userId, planName, body}, "[V1SubscriptionManager] fetched v1 plan for user"
  22. if planName in ['pro', 'pro_plus', 'student', 'free']
  23. planName = "v1_#{planName}"
  24. else
  25. # Throw away 'anonymous', etc as being equivalent to null
  26. planName = null
  27. return callback(null, planName, v1Id)
  28. notifyV1OfFeaturesChange: (userId, callback = (error) ->) ->
  29. V1SubscriptionManager._v1Request userId, {
  30. method: 'POST',
  31. url: (v1Id) -> "/api/v1/sharelatex/users/#{v1Id}/sync"
  32. }, callback
  33. getSubscriptionsFromV1: (userId, callback=(err, subscriptions, v1Id) ->) ->
  34. V1SubscriptionManager._v1Request userId, {
  35. method: 'GET',
  36. url: (v1Id) -> "/api/v1/sharelatex/users/#{v1Id}/subscriptions"
  37. }, callback
  38. getSubscriptionStatusFromV1: (userId, callback=(err, status) ->) ->
  39. V1SubscriptionManager._v1Request userId, {
  40. method: 'GET',
  41. url: (v1Id) -> "/api/v1/sharelatex/users/#{v1Id}/subscription_status"
  42. }, callback
  43. cancelV1Subscription: (userId, callback=(err)->) ->
  44. V1SubscriptionManager._v1Request userId, {
  45. method: 'DELETE',
  46. url: (v1Id) -> "/api/v1/sharelatex/users/#{v1Id}/subscription"
  47. }, callback
  48. v1IdForUser: (userId, callback=(err, v1Id) ->) ->
  49. UserGetter.getUser userId, {'overleaf.id': 1}, (err, user) ->
  50. return callback(err) if err?
  51. v1Id = user?.overleaf?.id
  52. if !v1Id?
  53. logger.log {userId}, "[V1SubscriptionManager] no v1 id found for user"
  54. callback(null, v1Id)
  55. # v1 accounts created before migration to v2 had github and mendeley for free
  56. # but these are now paid-for features for new accounts (v1id > cutoff)
  57. getGrandfatheredFeaturesForV1User: (v1Id) ->
  58. cutoff = settings.v1GrandfatheredFeaturesUidCutoff
  59. return {} if !cutoff?
  60. return {} if !v1Id?
  61. if (v1Id < cutoff)
  62. return settings.v1GrandfatheredFeatures or {}
  63. else
  64. return {}
  65. _v1Request: (userId, options, callback=(err, body, v1Id)->) ->
  66. if !settings?.apis?.v1
  67. return callback null, null
  68. V1SubscriptionManager.v1IdForUser userId, (err, v1Id) ->
  69. return callback(err) if err?
  70. return callback(null, null, null) if !v1Id?
  71. request {
  72. baseUrl: settings.apis.v1.url
  73. url: options.url(v1Id)
  74. method: options.method
  75. auth:
  76. user: settings.apis.v1.user
  77. pass: settings.apis.v1.pass
  78. sendImmediately: true
  79. json: true,
  80. timeout: 15 * 1000
  81. }, (error, response, body) ->
  82. if error?
  83. # Specially handle no connection err, so warning can be shown
  84. error = new V1ConnectionError('No V1 connection') if error.code == 'ECONNREFUSED'
  85. return callback(error)
  86. if 200 <= response.statusCode < 300
  87. return callback null, body, v1Id
  88. else
  89. return callback new Error("non-success code from v1: #{response.statusCode}")