respond-util-factory.ts 2.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108
  1. import axios from 'axios';
  2. import urljoin from 'url-join';
  3. import type { IRespondUtil } from '../interfaces/respond-util';
  4. import type { RespondBodyForResponseUrl } from '../interfaces/response-url';
  5. import { isValidResponseUrl } from './response-url-validator';
  6. type AxiosOptions = {
  7. headers?: {
  8. [header: string]: string;
  9. };
  10. };
  11. function getResponseUrlForProxy(proxyUri: string, responseUrl: string): string {
  12. return urljoin(proxyUri, `/g2s/respond?response_url=${responseUrl}`);
  13. }
  14. function getUrl(responseUrl: string, proxyUri?: string): string {
  15. const finalUrl =
  16. proxyUri === undefined
  17. ? responseUrl
  18. : getResponseUrlForProxy(proxyUri, responseUrl);
  19. if (!isValidResponseUrl(responseUrl, proxyUri)) {
  20. throw new Error('Invalid final response URL');
  21. }
  22. return finalUrl;
  23. }
  24. type RespondUtilConstructorArgs = {
  25. responseUrl: string;
  26. appSiteUrl: string;
  27. proxyUri?: string;
  28. };
  29. export class RespondUtil implements IRespondUtil {
  30. url!: string;
  31. options!: AxiosOptions;
  32. constructor({
  33. responseUrl,
  34. appSiteUrl,
  35. proxyUri,
  36. }: RespondUtilConstructorArgs) {
  37. this.url = getUrl(responseUrl, proxyUri);
  38. this.options = {
  39. headers: {
  40. 'x-growi-app-site-url': appSiteUrl,
  41. },
  42. };
  43. }
  44. async respond(body: RespondBodyForResponseUrl): Promise<void> {
  45. return axios.post(
  46. this.url,
  47. {
  48. replace_original: false,
  49. text: body.text,
  50. blocks: body.blocks,
  51. },
  52. this.options,
  53. );
  54. }
  55. async respondInChannel(body: RespondBodyForResponseUrl): Promise<void> {
  56. return axios.post(
  57. this.url,
  58. {
  59. response_type: 'in_channel',
  60. replace_original: false,
  61. text: body.text,
  62. blocks: body.blocks,
  63. },
  64. this.options,
  65. );
  66. }
  67. async replaceOriginal(body: RespondBodyForResponseUrl): Promise<void> {
  68. return axios.post(
  69. this.url,
  70. {
  71. replace_original: true,
  72. text: body.text,
  73. blocks: body.blocks,
  74. },
  75. this.options,
  76. );
  77. }
  78. async deleteOriginal(): Promise<void> {
  79. return axios.post(
  80. this.url,
  81. {
  82. delete_original: true,
  83. },
  84. this.options,
  85. );
  86. }
  87. }
  88. export function generateRespondUtil(
  89. args: RespondUtilConstructorArgs,
  90. ): RespondUtil {
  91. return new RespondUtil(args);
  92. }