Merge branch 'remote-instance-fix' into 'main'

Fix: Cannot Pin/Unpin Instances

Closes #1645

See merge request soapbox-pub/soapbox!2970
This commit is contained in:
marcin mikołajczak 2024-03-30 12:22:51 +00:00
commit 7320299b3c
5 changed files with 26 additions and 19 deletions

View file

@ -5,10 +5,10 @@ import Icon from 'soapbox/components/icon';
import { HStack, Stack, Text } from 'soapbox/components/ui'; import { HStack, Stack, Text } from 'soapbox/components/ui';
import { useInstance } from 'soapbox/hooks'; import { useInstance } from 'soapbox/hooks';
import type { Map as ImmutableMap } from 'immutable'; import type { RemoteInstance } from 'soapbox/selectors';
const hasRestrictions = (remoteInstance: ImmutableMap<string, any>): boolean => { const hasRestrictions = (remoteInstance: RemoteInstance): boolean => {
const { accept, reject_deletes, report_removal, ...federation } = remoteInstance.get('federation'); const { accept, reject_deletes, report_removal, ...federation } = remoteInstance.federation;
return !!Object.values(federation).reduce((acc, value) => Boolean(acc || value), false); return !!Object.values(federation).reduce((acc, value) => Boolean(acc || value), false);
}; };
@ -30,7 +30,7 @@ const Restriction: React.FC<IRestriction> = ({ icon, children }) => {
}; };
interface IInstanceRestrictions { interface IInstanceRestrictions {
remoteInstance: ImmutableMap<string, any>; remoteInstance: RemoteInstance;
} }
const InstanceRestrictions: React.FC<IInstanceRestrictions> = ({ remoteInstance }) => { const InstanceRestrictions: React.FC<IInstanceRestrictions> = ({ remoteInstance }) => {
@ -46,7 +46,7 @@ const InstanceRestrictions: React.FC<IInstanceRestrictions> = ({ remoteInstance
followers_only, followers_only,
media_nsfw, media_nsfw,
media_removal, media_removal,
} = remoteInstance.get('federation').toJS(); } = remoteInstance.federation;
const fullMediaRemoval = media_removal && avatar_removal && banner_removal; const fullMediaRemoval = media_removal && avatar_removal && banner_removal;
const partialMediaRemoval = media_removal || avatar_removal || banner_removal; const partialMediaRemoval = media_removal || avatar_removal || banner_removal;
@ -108,10 +108,10 @@ const InstanceRestrictions: React.FC<IInstanceRestrictions> = ({ remoteInstance
const renderContent = () => { const renderContent = () => {
if (!instance || !remoteInstance) return null; if (!instance || !remoteInstance) return null;
const host = remoteInstance.get('host'); const host = remoteInstance.host;
const siteTitle = instance.title; const siteTitle = instance.title;
if (remoteInstance.getIn(['federation', 'reject']) === true) { if (remoteInstance.federation.reject === true) {
return ( return (
<Restriction icon={require('@tabler/icons/shield-x.svg')}> <Restriction icon={require('@tabler/icons/shield-x.svg')}>
<FormattedMessage <FormattedMessage

View file

@ -27,8 +27,8 @@ const RestrictedInstance: React.FC<IRestrictedInstance> = ({ host }) => {
<div> <div>
<a href='#' className='flex items-center gap-1 py-2.5 no-underline' onClick={toggleExpanded}> <a href='#' className='flex items-center gap-1 py-2.5 no-underline' onClick={toggleExpanded}>
<Icon src={expanded ? require('@tabler/icons/caret-down.svg') : require('@tabler/icons/caret-right.svg')} /> <Icon src={expanded ? require('@tabler/icons/caret-down.svg') : require('@tabler/icons/caret-right.svg')} />
<div className={clsx({ 'line-through': remoteInstance.getIn(['federation', 'reject']) })}> <div className={clsx({ 'line-through': remoteInstance.federation.reject })}>
{remoteInstance.get('host')} {remoteInstance.host}
</div> </div>
</a> </a>
<div <div

View file

@ -39,7 +39,7 @@ const InstanceInfoPanel: React.FC<IInstanceInfoPanel> = ({ host }) => {
return ( return (
<Widget <Widget
title={remoteInstance.get('host')} title={remoteInstance.host}
onActionClick={handlePinHost} onActionClick={handlePinHost}
actionIcon={pinned ? require('@tabler/icons/pinned-off.svg') : require('@tabler/icons/pin.svg')} actionIcon={pinned ? require('@tabler/icons/pinned-off.svg') : require('@tabler/icons/pin.svg')}
actionTitle={intl.formatMessage(pinned ? messages.unpinHost : messages.pinHost, { host })} actionTitle={intl.formatMessage(pinned ? messages.unpinHost : messages.pinHost, { host })}

View file

@ -33,7 +33,7 @@ const EditFederationModal: React.FC<IEditFederationModal> = ({ host, onClose })
const [data, setData] = useState<Record<string, any>>({}); const [data, setData] = useState<Record<string, any>>({});
useEffect(() => { useEffect(() => {
setData(remoteInstance.get('federation') as Record<string, any>); setData(remoteInstance.federation);
}, [remoteInstance]); }, [remoteInstance]);
const handleDataChange = (key: string): React.ChangeEventHandler<HTMLInputElement> => { const handleDataChange = (key: string): React.ChangeEventHandler<HTMLInputElement> => {

View file

@ -2,6 +2,7 @@ import {
Map as ImmutableMap, Map as ImmutableMap,
List as ImmutableList, List as ImmutableList,
OrderedSet as ImmutableOrderedSet, OrderedSet as ImmutableOrderedSet,
Record as ImmutableRecord,
fromJS, fromJS,
} from 'immutable'; } from 'immutable';
import { createSelector } from 'reselect'; import { createSelector } from 'reselect';
@ -305,7 +306,7 @@ const getRemoteInstanceFavicon = (state: RootState, host: string) => {
return account?.pleroma?.favicon; return account?.pleroma?.favicon;
}; };
type HostFederation = { export type HostFederation = {
[key in keyof MRFSimple]: boolean; [key in keyof MRFSimple]: boolean;
}; };
@ -328,19 +329,25 @@ export const makeGetHosts = () => {
}); });
}; };
export const makeGetRemoteInstance = () => { export const RemoteInstanceRecord = ImmutableRecord({
return createSelector([ host: '',
favicon: null as string | null,
federation: null as unknown as HostFederation,
});
export type RemoteInstance = ReturnType<typeof RemoteInstanceRecord>;
export const makeGetRemoteInstance = () =>
createSelector([
(_state: RootState, host: string) => host, (_state: RootState, host: string) => host,
getRemoteInstanceFavicon, getRemoteInstanceFavicon,
getRemoteInstanceFederation, getRemoteInstanceFederation,
], (host, favicon, federation) => { ], (host, favicon, federation) =>
return ImmutableMap({ RemoteInstanceRecord({
host, host,
favicon, favicon,
federation, federation,
}); }));
});
};
type ColumnQuery = { type: string; prefix?: string }; type ColumnQuery = { type: string; prefix?: string };