index.js 4.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137
  1. import { createSelector } from 'reselect';
  2. import { List as ImmutableList, Map as ImmutableMap } from 'immutable';
  3. import { toServerSideType } from 'mastodon/utils/filters';
  4. import { me } from '../initial_state';
  5. const getAccountBase = (state, id) => state.getIn(['accounts', id], null);
  6. const getAccountCounters = (state, id) => state.getIn(['accounts_counters', id], null);
  7. const getAccountRelationship = (state, id) => state.getIn(['relationships', id], null);
  8. const getAccountMoved = (state, id) => state.getIn(['accounts', state.getIn(['accounts', id, 'moved'])]);
  9. export const makeGetAccount = () => {
  10. return createSelector([getAccountBase, getAccountCounters, getAccountRelationship, getAccountMoved], (base, counters, relationship, moved) => {
  11. if (base === null) {
  12. return null;
  13. }
  14. return base.merge(counters).withMutations(map => {
  15. map.set('relationship', relationship);
  16. map.set('moved', moved);
  17. });
  18. });
  19. };
  20. const getFilters = (state, { contextType }) => {
  21. if (!contextType) return null;
  22. const serverSideType = toServerSideType(contextType);
  23. const now = new Date();
  24. return state.get('filters').filter((filter) => filter.get('context').includes(serverSideType) && (filter.get('expires_at') === null || filter.get('expires_at') > now));
  25. };
  26. export const makeGetStatus = () => {
  27. return createSelector(
  28. [
  29. (state, { id }) => state.getIn(['statuses', id]),
  30. (state, { id }) => state.getIn(['statuses', state.getIn(['statuses', id, 'reblog'])]),
  31. (state, { id }) => state.getIn(['accounts', state.getIn(['statuses', id, 'account'])]),
  32. (state, { id }) => state.getIn(['accounts', state.getIn(['statuses', state.getIn(['statuses', id, 'reblog']), 'account'])]),
  33. getFilters,
  34. ],
  35. (statusBase, statusReblog, accountBase, accountReblog, filters) => {
  36. if (!statusBase || statusBase.get('isLoading')) {
  37. return null;
  38. }
  39. if (statusReblog) {
  40. statusReblog = statusReblog.set('account', accountReblog);
  41. } else {
  42. statusReblog = null;
  43. }
  44. let filtered = false;
  45. if ((accountReblog || accountBase).get('id') !== me && filters) {
  46. let filterResults = statusReblog?.get('filtered') || statusBase.get('filtered') || ImmutableList();
  47. if (filterResults.some((result) => filters.getIn([result.get('filter'), 'filter_action']) === 'hide')) {
  48. return null;
  49. }
  50. filterResults = filterResults.filter(result => filters.has(result.get('filter')));
  51. if (!filterResults.isEmpty()) {
  52. filtered = filterResults.map(result => filters.getIn([result.get('filter'), 'title']));
  53. }
  54. }
  55. return statusBase.withMutations(map => {
  56. map.set('reblog', statusReblog);
  57. map.set('account', accountBase);
  58. map.set('matched_filters', filtered);
  59. });
  60. },
  61. );
  62. };
  63. export const makeGetPictureInPicture = () => {
  64. return createSelector([
  65. (state, { id }) => state.get('picture_in_picture').statusId === id,
  66. (state) => state.getIn(['meta', 'layout']) !== 'mobile',
  67. ], (inUse, available) => ImmutableMap({
  68. inUse: inUse && available,
  69. available,
  70. }));
  71. };
  72. const getAlertsBase = state => state.get('alerts');
  73. export const getAlerts = createSelector([getAlertsBase], (base) => {
  74. let arr = [];
  75. base.forEach(item => {
  76. arr.push({
  77. message: item.get('message'),
  78. message_values: item.get('message_values'),
  79. title: item.get('title'),
  80. key: item.get('key'),
  81. dismissAfter: 5000,
  82. barStyle: {
  83. zIndex: 200,
  84. },
  85. });
  86. });
  87. return arr;
  88. });
  89. export const makeGetNotification = () => createSelector([
  90. (_, base) => base,
  91. (state, _, accountId) => state.getIn(['accounts', accountId]),
  92. ], (base, account) => base.set('account', account));
  93. export const makeGetReport = () => createSelector([
  94. (_, base) => base,
  95. (state, _, targetAccountId) => state.getIn(['accounts', targetAccountId]),
  96. ], (base, targetAccount) => base.set('target_account', targetAccount));
  97. export const getAccountGallery = createSelector([
  98. (state, id) => state.getIn(['timelines', `account:${id}:media`, 'items'], ImmutableList()),
  99. state => state.get('statuses'),
  100. (state, id) => state.getIn(['accounts', id]),
  101. ], (statusIds, statuses, account) => {
  102. let medias = ImmutableList();
  103. statusIds.forEach(statusId => {
  104. const status = statuses.get(statusId);
  105. medias = medias.concat(status.get('media_attachments').map(media => media.set('status', status).set('account', account)));
  106. });
  107. return medias;
  108. });
  109. export const getAccountHidden = createSelector([
  110. (state, id) => state.getIn(['accounts', id, 'hidden']),
  111. (state, id) => state.getIn(['relationships', id, 'following']) || state.getIn(['relationships', id, 'requested']),
  112. (state, id) => id === me,
  113. ], (hidden, followingOrRequested, isSelf) => {
  114. return hidden && !(isSelf || followingOrRequested);
  115. });