monaco-react
monaco-react copied to clipboard
refactor useMonaco hook to improve initialization and error handling
Solved by replacing the default useMonaco with a custom hook that safely
initializes Monaco in React Strict Mode environments (like Next.js). It ensures:
- No double-loading of the Monaco instance.
- Proper cleanup and error handling.
- Compatibility with hydration and re-renders.
✅ Custom hook implementation:
// hooks/useCustomMonaco.ts
import { useState, useRef, useEffect } from "react";
import * as monaco from "monaco-editor";
import { loader } from "@monaco-editor/react";
export function useCustomMonaco() {
const [monacoInstance, setMonacoInstance] = useState<typeof monaco | null>(null);
const mountedRef = useRef(true);
const loaderRef = useRef<any>(null);
useEffect(() => {
const instance = loader.__getMonacoInstance();
if (instance) {
setMonacoInstance(instance);
return;
}
if (!loaderRef.current) {
loader.config({
"vs/nls": { availableLanguages: {} },
});
try {
loaderRef.current = loader.init();
loaderRef.current
.then((monacoApi: typeof monaco) => {
if (mountedRef.current) {
setMonacoInstance(monacoApi);
}
})
.catch((error: any) => {
if (mountedRef.current && error.type !== "cancelation") {
console.error("Monaco initialization error:", error);
}
});
} catch (err) {
console.error("Failed to initialize Monaco:", err);
}
}
return () => {
mountedRef.current = false;
};
}, []);
return monacoInstance;
}
export default useCustomMonaco;