request-context.ts 3.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109
  1. import { LanguageCode } from '@vendure/common/lib/generated-types';
  2. import { ID } from '@vendure/common/lib/shared-types';
  3. import i18next from 'i18next';
  4. import { DEFAULT_LANGUAGE_CODE } from '../../common/constants';
  5. import { Channel } from '../../entity/channel/channel.entity';
  6. import { AuthenticatedSession } from '../../entity/session/authenticated-session.entity';
  7. import { Session } from '../../entity/session/session.entity';
  8. import { User } from '../../entity/user/user.entity';
  9. /**
  10. * @description
  11. * The RequestContext holds information relevant to the current request, which may be
  12. * required at various points of the stack.
  13. *
  14. * @docsCategory
  15. * @docsWeight 1
  16. */
  17. export class RequestContext {
  18. private readonly _languageCode: LanguageCode;
  19. private readonly _channel: Channel;
  20. private readonly _session?: Session;
  21. private readonly _isAuthorized: boolean;
  22. private readonly _authorizedAsOwnerOnly: boolean;
  23. private readonly _translationFn: i18next.TranslationFunction;
  24. /**
  25. * @internal
  26. */
  27. constructor(options: {
  28. channel: Channel;
  29. session?: Session;
  30. languageCode?: LanguageCode;
  31. isAuthorized: boolean;
  32. authorizedAsOwnerOnly: boolean;
  33. translationFn?: i18next.TranslationFunction;
  34. }) {
  35. const { channel, session, languageCode, translationFn } = options;
  36. this._channel = channel;
  37. this._session = session;
  38. this._languageCode =
  39. languageCode || (channel && channel.defaultLanguageCode) || DEFAULT_LANGUAGE_CODE;
  40. this._isAuthorized = options.isAuthorized;
  41. this._authorizedAsOwnerOnly = options.authorizedAsOwnerOnly;
  42. this._translationFn = translationFn || (((key: string) => key) as any);
  43. }
  44. get channel(): Channel {
  45. return this._channel;
  46. }
  47. get channelId(): ID {
  48. return this._channel.id;
  49. }
  50. get languageCode(): LanguageCode {
  51. return this._languageCode;
  52. }
  53. get session(): Session | undefined {
  54. return this._session;
  55. }
  56. get activeUserId(): ID | undefined {
  57. const user = this.activeUser;
  58. if (user) {
  59. return user.id;
  60. }
  61. }
  62. get activeUser(): User | undefined {
  63. if (this.session) {
  64. if (this.isAuthenticatedSession(this.session)) {
  65. return this.session.user;
  66. }
  67. }
  68. }
  69. /**
  70. * True if the current session is authorized to access the current resolver method.
  71. */
  72. get isAuthorized(): boolean {
  73. return this._isAuthorized;
  74. }
  75. /**
  76. * True if the current anonymous session is only authorized to operate on entities that
  77. * are owned by the current session.
  78. */
  79. get authorizedAsOwnerOnly(): boolean {
  80. return this._authorizedAsOwnerOnly;
  81. }
  82. /**
  83. * @description
  84. * Translate the given i18n key
  85. */
  86. translate(key: string, variables?: { [k: string]: any }): string {
  87. try {
  88. return this._translationFn(key, variables);
  89. } catch (e) {
  90. return `Translation format error: ${e.message}). Original key: ${key}`;
  91. }
  92. }
  93. private isAuthenticatedSession(session: Session): session is AuthenticatedSession {
  94. return session.hasOwnProperty('user');
  95. }
  96. }