From 6929bd5849b1be82336a13e49d296dd79bd29a6b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?nicole=20miko=C5=82ajczyk?= Date: Wed, 7 Jan 2026 22:08:15 +0100 Subject: [PATCH] pl-fe: error handling improvements, some refactoring i forgot to commit before MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Signed-off-by: nicole mikołajczyk --- packages/pl-fe/src/actions/import-data.ts | 37 ---- .../src/components/site-error-boundary.tsx | 204 ------------------ .../src/features/ui/router/error-column.tsx | 45 ---- .../pl-fe/src/features/ui/router/index.tsx | 5 +- packages/pl-fe/src/init/pl-fe-mount.tsx | 9 +- packages/pl-fe/src/locales/en.json | 4 +- .../pl-fe/src/pages/settings/import-data.tsx | 34 ++- packages/pl-fe/src/styles/new/layout.scss | 16 ++ 8 files changed, 46 insertions(+), 308 deletions(-) delete mode 100644 packages/pl-fe/src/actions/import-data.ts delete mode 100644 packages/pl-fe/src/components/site-error-boundary.tsx delete mode 100644 packages/pl-fe/src/features/ui/router/error-column.tsx diff --git a/packages/pl-fe/src/actions/import-data.ts b/packages/pl-fe/src/actions/import-data.ts deleted file mode 100644 index fd9ddc1c3..000000000 --- a/packages/pl-fe/src/actions/import-data.ts +++ /dev/null @@ -1,37 +0,0 @@ -import { defineMessages } from 'react-intl'; - -import toast from 'pl-fe/toast'; - -import { getClient } from '../api'; - -import type { AppDispatch, RootState } from 'pl-fe/store'; - -const messages = defineMessages({ - blocksSuccess: { id: 'import_data.success.blocks', defaultMessage: 'Blocks imported successfully' }, - followersSuccess: { id: 'import_data.success.followers', defaultMessage: 'Followers imported successfully' }, - mutesSuccess: { id: 'import_data.success.mutes', defaultMessage: 'Mutes imported successfully' }, -}); - -const importFollows = (list: File | string, overwrite?: boolean) => - (dispatch: AppDispatch, getState: () => RootState) => - getClient(getState).settings.importFollows(list, overwrite ? 'overwrite' : 'merge').then(response => { - toast.success(messages.followersSuccess); - }); - -const importBlocks = (list: File | string, overwrite?: boolean) => - (dispatch: AppDispatch, getState: () => RootState) => - getClient(getState).settings.importBlocks(list, overwrite ? 'overwrite' : 'merge').then(response => { - toast.success(messages.blocksSuccess); - }); - -const importMutes = (list: File | string) => - (dispatch: AppDispatch, getState: () => RootState) => - getClient(getState).settings.importMutes(list).then(response => { - toast.success(messages.mutesSuccess); - }); - -export { - importFollows, - importBlocks, - importMutes, -}; diff --git a/packages/pl-fe/src/components/site-error-boundary.tsx b/packages/pl-fe/src/components/site-error-boundary.tsx deleted file mode 100644 index 68363fced..000000000 --- a/packages/pl-fe/src/components/site-error-boundary.tsx +++ /dev/null @@ -1,204 +0,0 @@ -import React, { type ErrorInfo, useRef, useState } from 'react'; -import { ErrorBoundary } from 'react-error-boundary'; -import { FormattedMessage } from 'react-intl'; - -import { NODE_ENV } from 'pl-fe/build-config'; -import HStack from 'pl-fe/components/ui/hstack'; -import Stack from 'pl-fe/components/ui/stack'; -import Text from 'pl-fe/components/ui/text'; -import Textarea from 'pl-fe/components/ui/textarea'; -import { useLogo } from 'pl-fe/hooks/use-logo'; -import { usePlFeConfig } from 'pl-fe/hooks/use-pl-fe-config'; -import { captureSentryException } from 'pl-fe/sentry'; -import KVStore from 'pl-fe/storage/kv-store'; -import sourceCode from 'pl-fe/utils/code'; -import { unregisterSW } from 'pl-fe/utils/sw'; - -import SentryFeedbackForm from './sentry-feedback-form'; -import SiteLogo from './site-logo'; - -interface ISiteErrorBoundary { - children: React.ReactNode; -} - -/** Application-level error boundary. Fills the whole screen. */ -const SiteErrorBoundary: React.FC = ({ children }) => { - const { links, sentryDsn } = usePlFeConfig(); - const { src: logoSrc } = useLogo(); - const textarea = useRef(null); - - const [error, setError] = useState(); - const [componentStack, setComponentStack] = useState(); - const [browser, setBrowser] = useState(); - const [sentryEventId, setSentryEventId] = useState(); - - const sentryEnabled = Boolean(sentryDsn); - const isProduction = NODE_ENV === 'production'; - const errorText = String(error) + componentStack; - - const clearCookies: React.MouseEventHandler = (e) => { - localStorage.clear(); - sessionStorage.clear(); - KVStore.clear(); - - if ('serviceWorker' in navigator) { - e.preventDefault(); - unregisterSW().then(goHome).catch(goHome); - } - }; - - const handleCopy: React.MouseEventHandler = () => { - if (!textarea.current) return; - - textarea.current.select(); - textarea.current.setSelectionRange(0, 99999); - - document.execCommand('copy'); - }; - - const handleError = (error: Error, info: ErrorInfo) => { - setError(error); - setComponentStack(info.componentStack); - - captureSentryException(error, { - tags: { - // Allow page crashes to be easily searched in Sentry. - ErrorBoundary: 'yes', - }, - }) - .then((eventId) => setSentryEventId(eventId)) - .catch(console.error); - - import('bowser') - .then(({ default: Bowser }) => setBrowser(Bowser.getParser(window.navigator.userAgent))) - .catch(() => {}); - }; - - const goHome = () => { - location.href = '/'; - }; - - const fallback = ( -
-
- {logoSrc && ( -
- - - -
- )} - -
-
-

- -

-

- - - - ), - }} - /> -

- - - {sourceCode.displayName}: - - {' '}{sourceCode.version} - - - -
- -
- {(isProduction) ? ( - (sentryEnabled && sentryEventId) && ( - - ) - ) : ( - <> - {errorText && ( -