Skip to content

Commit 5f2a58e

Browse files
committed
frontend/editor: rename EditorLoadError and do not lazily load it (assuming network problem!)
1 parent d1899b6 commit 5f2a58e

File tree

4 files changed

+20
-23
lines changed

4 files changed

+20
-23
lines changed

src/packages/frontend/file-editors-error.tsx

Lines changed: 2 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@ import { ReactElement } from "react";
88

99
import { Icon, Paragraph } from "@cocalc/frontend/components";
1010

11-
interface EditorLoadErrorComponentProps {
11+
interface EditorLoadErrorProps {
1212
path: string;
1313
error: Error;
1414
}
@@ -17,9 +17,7 @@ interface EditorLoadErrorComponentProps {
1717
* Error component shown when editor fails to load.
1818
* Displays error message with a button to refresh the page.
1919
*/
20-
export function EditorLoadErrorComponent(
21-
props: EditorLoadErrorComponentProps,
22-
): ReactElement {
20+
export function EditorLoadError(props: EditorLoadErrorProps): ReactElement {
2321
const { path, error } = props;
2422

2523
const handleRefresh = () => {

src/packages/frontend/file-editors.ts

Lines changed: 5 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ import {
1818
import { React } from "@cocalc/frontend/app-framework";
1919

2020
import { alert_message } from "./alerts";
21-
import { EditorLoadErrorComponent } from "./file-editors-error";
21+
import { EditorLoadError } from "./file-editors-error";
2222

2323
declare let DEBUG: boolean;
2424

@@ -144,7 +144,9 @@ function logFallback(
144144
is_public: boolean,
145145
): void {
146146
console.warn(
147-
`Editor fallback triggered: No editor found for ext '${ext ?? "unknown"}' on path '${path}' (is_public: ${is_public}), using unknown editor catchall`,
147+
`Editor fallback triggered: No editor found for ext '${
148+
ext ?? "unknown"
149+
}' on path '${path}' (is_public: ${is_public}), using unknown editor catchall`,
148150
);
149151
}
150152

@@ -267,8 +269,7 @@ export async function generateAsync(
267269
timeout: 10,
268270
});
269271
// Return error component with refresh button
270-
return () =>
271-
React.createElement(EditorLoadErrorComponent, { path, error });
272+
return () => React.createElement(EditorLoadError, { path, error });
272273
}
273274
}
274275
return () =>

src/packages/frontend/frame-editors/frame-tree/register.ts

Lines changed: 6 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -89,17 +89,21 @@ if (DEBUG) {
8989
* Wraps an async data loader with timeout protection and retry logic.
9090
*
9191
* Strategy:
92-
* - If 10 second timeout occurs → retry immediately
92+
* - If 15 second timeout occurs → retry immediately
9393
* - If asyncLoader() fails immediately due to network error → wait 5 seconds → retry
9494
* - Maximum 3 attempts total
9595
*
9696
* This ensures that temporary network hiccups don't silently cause fallback to wrong editor.
9797
* NOTE: The caller must wrap this with reuseInFlight to prevent duplicate simultaneous loads.
98+
*
99+
* TEST: refresh CoCalc page, but do not open a complex editor like Jupyter.
100+
* Open Chrome debug panel → Network → Network: "Offline"
101+
* Then click on the ipynb file and watch the console for the retries and the error popping up.
98102
*/
99103
function withTimeoutAndRetry<T>(
100104
asyncLoaderFn: () => Promise<T>,
101105
ext: string | string[],
102-
timeoutMs: number = 10000,
106+
timeoutMs: number = 15_000, // wait up to 15 seconds to load all assets
103107
maxRetries: number = 3,
104108
): () => Promise<T> {
105109
const extStr = Array.isArray(ext) ? ext.join(",") : ext;
@@ -116,11 +120,6 @@ function withTimeoutAndRetry<T>(
116120
);
117121
}
118122

119-
// TEST: Uncomment below to simulate network error for ipynb files
120-
// if (extStr === "ipynb") {
121-
// throw new Error("Simulated network error for testing");
122-
// }
123-
124123
const result = await Promise.race([
125124
asyncLoaderFn(),
126125
new Promise<T>((_, reject) =>

src/packages/frontend/project_actions.ts

Lines changed: 7 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,7 @@ import { reuseInFlight } from "@cocalc/util/reuse-in-flight";
110110
import { MARKERS } from "@cocalc/util/sagews";
111111
import { client_db } from "@cocalc/util/schema";
112112
import { get_editor } from "./editors/react-wrapper";
113+
import { EditorLoadError } from "./file-editors-error";
113114

114115
const { defaults, required } = misc;
115116

@@ -783,13 +784,10 @@ export class ProjectActions extends Actions<ProjectStoreState> {
783784
} catch (err) {
784785
// Error already reported to user by alert_message in file-editors.ts
785786
// Show error component in the editor area
786-
const { EditorLoadErrorComponent } = await import(
787-
"./file-editors-error"
788-
);
789787
if (this.open_files == null) return;
790788
const error = err as Error;
791789
info.Editor = () =>
792-
require("react").createElement(EditorLoadErrorComponent, {
790+
require("react").createElement(EditorLoadError, {
793791
path,
794792
error,
795793
});
@@ -1571,8 +1569,9 @@ export class ProjectActions extends Actions<ProjectStoreState> {
15711569
const computeServerAssociations =
15721570
webapp_client.project_client.computeServers(this.project_id);
15731571
const sidePath = chatFile(path);
1574-
const currentId =
1575-
await computeServerAssociations.getServerIdForPath(sidePath);
1572+
const currentId = await computeServerAssociations.getServerIdForPath(
1573+
sidePath,
1574+
);
15761575
if (currentId != null) {
15771576
// already set
15781577
return;
@@ -2356,8 +2355,8 @@ export class ProjectActions extends Actions<ProjectStoreState> {
23562355
dest_compute_server_id: opts.dest_compute_server_id,
23572356
}
23582357
: opts.src_compute_server_id
2359-
? { compute_server_id: opts.src_compute_server_id }
2360-
: undefined),
2358+
? { compute_server_id: opts.src_compute_server_id }
2359+
: undefined),
23612360
});
23622361

23632362
if (opts.only_contents) {

0 commit comments

Comments
 (0)