Composer quote improvements (#35835)

Co-authored-by: Claire <claire.github-309c@sitedethib.com>
Co-authored-by: diondiondion <mail@diondiondion.com>
This commit is contained in:
Echo 2025-08-21 16:07:31 +02:00 committed by GitHub
commit f85f0eee1b
No known key found for this signature in database
GPG key ID: B5690EEEBB952194
15 changed files with 371 additions and 96 deletions

View file

@ -84,6 +84,7 @@ export const COMPOSE_FOCUS = 'COMPOSE_FOCUS';
const messages = defineMessages({
uploadErrorLimit: { id: 'upload_error.limit', defaultMessage: 'File upload limit exceeded.' },
uploadErrorPoll: { id: 'upload_error.poll', defaultMessage: 'File upload not allowed with polls.' },
uploadQuote: { id: 'upload_error.quote', defaultMessage: 'File upload not allowed with quotes.' },
open: { id: 'compose.published.open', defaultMessage: 'Open' },
published: { id: 'compose.published.body', defaultMessage: 'Post published.' },
saved: { id: 'compose.saved.body', defaultMessage: 'Post saved.' },
@ -146,7 +147,7 @@ export function resetCompose() {
};
}
export const focusCompose = (defaultText) => (dispatch, getState) => {
export const focusCompose = (defaultText = '') => (dispatch, getState) => {
dispatch({
type: COMPOSE_FOCUS,
defaultText,
@ -303,6 +304,11 @@ export function submitComposeFail(error) {
export function uploadCompose(files) {
return function (dispatch, getState) {
// Exit if there's a quote.
if (getState().compose.get('quoted_status_id')) {
dispatch(showAlert({ message: messages.uploadQuote }));
return;
}
const uploadLimit = getState().getIn(['server', 'server', 'configuration', 'statuses', 'max_media_attachments']);
const media = getState().getIn(['compose', 'media_attachments']);
const pending = getState().getIn(['compose', 'pending_media_attachments']);

View file

@ -1,3 +1,5 @@
import { defineMessages } from 'react-intl';
import { createAction } from '@reduxjs/toolkit';
import type { List as ImmutableList, Map as ImmutableMap } from 'immutable';
@ -12,7 +14,27 @@ import {
import type { ApiQuotePolicy } from '../api_types/quotes';
import type { Status } from '../models/status';
import { ensureComposeIsVisible } from './compose';
import { showAlert } from './alerts';
import { focusCompose } from './compose';
const messages = defineMessages({
quoteErrorUpload: {
id: 'quote_error.upload',
defaultMessage: 'Quoting is not allowed with media attachments.',
},
quoteErrorPoll: {
id: 'quote_error.poll',
defaultMessage: 'Quoting is not allowed with polls.',
},
quoteErrorQuote: {
id: 'quote_error.quote',
defaultMessage: 'Only one quote at a time is allowed.',
},
quoteErrorUnauthorized: {
id: 'quote_error.unauthorized',
defaultMessage: 'You are not authorized to quote this post.',
},
});
type SimulatedMediaAttachmentJSON = ApiMediaAttachmentJSON & {
unattached?: boolean;
@ -78,14 +100,43 @@ export const changeUploadCompose = createDataLoadingThunk(
},
);
export const quoteComposeByStatus = createAppThunk(
export const quoteCompose = createAppThunk(
'compose/quoteComposeStatus',
(status: Status, { getState }) => {
ensureComposeIsVisible(getState);
(status: Status, { dispatch }) => {
dispatch(focusCompose());
return status;
},
);
export const quoteComposeByStatus = createAppThunk(
(status: Status, { dispatch, getState }) => {
const composeState = getState().compose;
const mediaAttachments = composeState.get('media_attachments');
if (composeState.get('poll')) {
dispatch(showAlert({ message: messages.quoteErrorPoll }));
} else if (
composeState.get('is_uploading') ||
(mediaAttachments &&
typeof mediaAttachments !== 'string' &&
typeof mediaAttachments !== 'number' &&
typeof mediaAttachments !== 'boolean' &&
mediaAttachments.size !== 0)
) {
dispatch(showAlert({ message: messages.quoteErrorUpload }));
} else if (composeState.get('quoted_status_id')) {
dispatch(showAlert({ message: messages.quoteErrorQuote }));
} else if (
status.getIn(['quote_approval', 'current_user']) !== 'automatic' &&
status.getIn(['quote_approval', 'current_user']) !== 'manual'
) {
dispatch(showAlert({ message: messages.quoteErrorUnauthorized }));
} else {
dispatch(quoteCompose(status));
}
},
);
export const quoteComposeById = createAppThunk(
(statusId: string, { dispatch, getState }) => {
const status = getState().statuses.get(statusId);
@ -97,6 +148,6 @@ export const quoteComposeById = createAppThunk(
export const quoteComposeCancel = createAction('compose/quoteComposeCancel');
export const setQuotePolicy = createAction<ApiQuotePolicy>(
export const setComposeQuotePolicy = createAction<ApiQuotePolicy>(
'compose/setQuotePolicy',
);