Skip to content

Commit

Permalink
fix: some merge issue
Browse files Browse the repository at this point in the history
  • Loading branch information
harrytothemoon committed Aug 16, 2022
1 parent 1ab9f97 commit 2dc242a
Showing 1 changed file with 94 additions and 29 deletions.
123 changes: 94 additions & 29 deletions packages/error-overlay/src/client.ts
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import iframeScript from 'iframeScript';
import { parse } from 'stacktrace-parser';
import ReactDOM from 'react-dom/client';

import * as errorTypeHandler from './view/errorTypeHandler';
import {
TYPE_UNHANDLED_ERROR,
Expand All @@ -9,15 +10,31 @@ import {
TYPE_REFRESH,
STACK_TRACE_LIMIT
} from './shared/constants';
import { ErrorOverlay } from './view/ErrorOverlay';
import { parseError } from './shared/helper/parseError';

let isRegistered = false;
let stackTraceLimit: number | undefined = undefined;

let isLoadedRoot = false;
let root: null | HTMLElement = null;
let errorBody: null | ReactDOM.Root = null;
let iframe: null | HTMLIFrameElement = null;
let isLoadingIframe: boolean = false;
let isIframeReady: boolean = false;
let errorType: errorTypeHandler.ErrorTypeEvent;

declare global {
interface Window {
__SHUVI_ERROR_OVERLAY_GLOBAL_HOOK__: string | {};
}
}

const iframeStyle = {
position: 'fixed',
top: '0',
left: '0',
width: '100%',
height: '100%',
border: 'none',
'z-index': 2147483647
};

function onUnhandledError(ev: ErrorEvent) {
const error = ev?.error;
Expand All @@ -26,12 +43,12 @@ function onUnhandledError(ev: ErrorEvent) {
return;
}

errorTypeHandler.emit({
errorType = {
type: TYPE_UNHANDLED_ERROR,
reason: error,
frames: parse(parseError(error.stack))
});
render();
};
update();
}

function onUnhandledRejection(ev: PromiseRejectionEvent) {
Expand All @@ -45,12 +62,12 @@ function onUnhandledRejection(ev: PromiseRejectionEvent) {
return;
}

errorTypeHandler.emit({
errorType = {
type: TYPE_UNHANDLED_REJECTION,
reason: reason,
frames: parse(parseError(reason.stack))
});
render();
};
update();
}

function startReportingRuntimeErrors({ onError }: { onError: () => void }) {
Expand Down Expand Up @@ -93,40 +110,88 @@ function stopReportingRuntimeErrors() {
}

function onBuildOk() {
errorTypeHandler.emit({ type: TYPE_BUILD_OK });
errorType = { type: TYPE_BUILD_OK };
update();
}

function onBuildError(message: string) {
errorTypeHandler.emit({ type: TYPE_BUILD_ERROR, message });
render();
errorType = { type: TYPE_BUILD_ERROR, message };
update();
}

function onRefresh() {
errorTypeHandler.emit({ type: TYPE_REFRESH });
errorType = { type: TYPE_REFRESH };
}

function render() {
if (isLoadedRoot) {
return;
function applyStyles(element: HTMLElement, styles: Object) {
element.setAttribute('style', '');
for (const key in styles) {
if (!Object.prototype.hasOwnProperty.call(styles, key)) {
continue;
}
//@ts-ignore
element.style[key] = styles[key];
}
isLoadedRoot = true;
const errorRoot = window.document.createElement('div');
root = errorRoot;
window.document.body.appendChild(errorRoot);
errorBody = ReactDOM.createRoot(errorRoot);
errorBody.render(<ErrorOverlay />);
}

function update() {
if (root) {
window.document.body.removeChild(root);
root = null;
isLoadedRoot = false;
errorBody?.unmount();
// Loading iframe can be either sync or async depending on the browser.
if (isLoadingIframe) {
// Iframe is loading.
// First render will happen soon--don't need to do anything.
return;
}
if (isIframeReady) {
// Iframe is ready.
// Just update it.
updateIframeContent();
return;
}
// We need to schedule the first render.
isLoadingIframe = true;
const loadingIframe = window.document.createElement('iframe');
applyStyles(loadingIframe, iframeStyle);
loadingIframe.onload = function () {
const iframeDocument = loadingIframe.contentDocument;
if (iframeDocument != null && iframeDocument.body != null) {
iframe = loadingIframe;
const script =
loadingIframe.contentWindow!.document.createElement('script');
script.type = 'text/javascript';
script.innerHTML = iframeScript;
iframeDocument.body.appendChild(script);
}
};
const appDocument = window.document;
appDocument.body.appendChild(loadingIframe);
}

function updateIframeContent() {
if (!iframe) {
throw new Error('Iframe has not been created yet.');
}

//@ts-ignore
const isRendered = iframe.contentWindow!.updateContent(errorType);

if (!isRendered) {
window.document.body.removeChild(iframe);
iframe = null;
isIframeReady = false;
}
}

window.__SHUVI_ERROR_OVERLAY_GLOBAL_HOOK__ =
window.__SHUVI_ERROR_OVERLAY_GLOBAL_HOOK__ || {};

//@ts-ignore
window.__SHUVI_ERROR_OVERLAY_GLOBAL_HOOK__.iframeReady =
function iframeReady() {
isIframeReady = true;
isLoadingIframe = false;
updateIframeContent();
};

export { getErrorByType } from './view/helpers/getErrorByType';
export { getServerError } from './view/helpers/nodeStackFrames';
export {
Expand Down

0 comments on commit 2dc242a

Please sign in to comment.