Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

fix: multi-instance problem and styles of live demo feature #2001

Merged
merged 5 commits into from
Jan 8, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
10 changes: 5 additions & 5 deletions src/client/pages/Demo/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,25 +5,25 @@ import './index.less';
const DemoRenderPage: FC = () => {
const { id } = useParams();
const { component } = useDemo(id!) || {};
const { node: liveDemoNode, setSources } = useLiveDemo(id!);
const { node: liveDemoNode, setSource } = useLiveDemo(id!);
const finalNode = liveDemoNode || (component && createElement(component));

useEffect(() => {
const handler = (
ev: MessageEvent<{
type: string;
value: Parameters<typeof setSources>[0];
value: Parameters<typeof setSource>[0];
}>,
) => {
if (ev.data.type === 'dumi.liveDemo.setSources') {
setSources(ev.data.value);
if (ev.data.type === 'dumi.liveDemo.setSource') {
setSource(ev.data.value);
}
};

window.addEventListener('message', handler);

return () => window.removeEventListener('message', handler);
}, [setSources]);
}, [setSource]);

return finalNode;
};
Expand Down
12 changes: 6 additions & 6 deletions src/client/theme-api/useLiveDemo.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,14 +12,14 @@ export const useLiveDemo = (id: string) => {
const { context, asset } = useDemo(id)!;
const [demoNode, setDemoNode] = useState<ReactNode>();
const [error, setError] = useState<Error | null>(null);
const setSources = useCallback(
(sources: Record<string, string>) => {
const setSource = useCallback(
(source: Record<string, string>) => {
const entryFileName = Object.keys(asset.dependencies).find(
(k) => asset.dependencies[k].type === 'FILE',
)!;
const entryFileCode = sources[entryFileName];
const entryFileCode = source[entryFileName];
const require = (v: string) => {
if (v in context) return context[v];
if (v in context!) return context![v];
throw new Error(`Cannot find module: ${v}`);
};
const exports: { default?: ComponentType } = {};
Expand Down Expand Up @@ -50,7 +50,7 @@ export const useLiveDemo = (id: string) => {
renderToStaticMarkup(newDemoNode);
console.error = oError;

// set new demo node with passing sources
// set new demo node with passing source
setDemoNode(newDemoNode);
setError(null);
} catch (err: any) {
Expand All @@ -61,5 +61,5 @@ export const useLiveDemo = (id: string) => {
[context],
);

return { node: demoNode, error, setSources };
return { node: demoNode, error, setSource };
};
20 changes: 16 additions & 4 deletions src/client/theme-default/builtins/Previewer/index.less
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
@import (reference) '../../styles/variables.less';

.@{prefix}-previewer {
@error-bar-height: 30px;

margin: 24px 0 32px;
border: 1px solid @c-border-light;
border-radius: 4px;
Expand Down Expand Up @@ -76,16 +78,26 @@
&[data-compact] {
padding: 0;
}

// error status
&[data-error][data-compact] {
min-height: @error-bar-height;

+ .@{prefix}-previewer-demo-error {
border-top-left-radius: 3px;
border-top-right-radius: 3px;
}
}
}

&-demo-error {
@height: 30px;
@color: darken(desaturate(@c-error, 20%), 1%);

margin-top: -@height;
height: @height;
position: relative;
margin-top: -@error-bar-height;
height: @error-bar-height;
padding: 0 24px;
line-height: @height;
line-height: @error-bar-height;
color: @color;
font-size: 13px;
white-space: nowrap;
Expand Down
11 changes: 6 additions & 5 deletions src/client/theme-default/builtins/Previewer/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ const Previewer: FC<IPreviewerProps> = (props) => {
const {
node: liveDemoNode,
error: liveDemoError,
setSources: setLiveDemoSources,
setSource: setLiveDemoSource,
} = useLiveDemo(props.asset.id);
const [editorError, setEditorError] = useState<Error | null>(null);
const combineError = liveDemoError || editorError;
Expand All @@ -31,6 +31,7 @@ const Previewer: FC<IPreviewerProps> = (props) => {
data-compact={props.compact || undefined}
data-transform={props.transform || undefined}
data-iframe={props.iframe || undefined}
data-error={Boolean(combineError) || undefined}
ref={demoContainer}
>
{props.iframe ? (
Expand Down Expand Up @@ -71,19 +72,19 @@ const Previewer: FC<IPreviewerProps> = (props) => {
)}
<PreviewerActions
{...props}
onSourcesTranspile={({ err, sources }) => {
onSourceTranspile={({ err, source }) => {
if (err) {
setEditorError(err);
} else {
setEditorError(null);
setLiveDemoSources(sources);
setLiveDemoSource(source);

if (props.iframe) {
demoContainer
.current!.querySelector('iframe')!
.contentWindow!.postMessage({
type: 'dumi.liveDemo.setSources',
value: sources,
type: 'dumi.liveDemo.setSource',
value: source,
});
}
}
Expand Down
12 changes: 6 additions & 6 deletions src/client/theme-default/slots/PreviewerActions/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,10 +26,10 @@ export interface IPreviewerActionsProps extends IPreviewerProps {
extra?: ReactNode;
forceShowCode?: boolean;
demoContainer: HTMLDivElement | HTMLIFrameElement;
onSourcesTranspile?: (
onSourceTranspile?: (
args:
| { err: Error; sources?: null }
| { err?: null; sources: Record<string, string> },
| { err: Error; source?: null }
| { err?: null; source: Record<string, string> },
) => void;
}

Expand Down Expand Up @@ -200,10 +200,10 @@ const PreviewerActions: FC<IPreviewerActionsProps> = (props) => {
initialValue={files[i][1].value.trim()}
onTranspile={({ err, code }) => {
if (err) {
props.onSourcesTranspile?.({ err });
props.onSourceTranspile?.({ err });
} else {
props.onSourcesTranspile?.({
sources: { [files[i][0]]: code },
props.onSourceTranspile?.({
source: { [files[i][0]]: code },
});
}
}}
Expand Down
2 changes: 2 additions & 0 deletions src/features/configPlugins/schema.ts
Original file line number Diff line number Diff line change
Expand Up @@ -47,5 +47,7 @@ export function getSchemas(): Record<string, (Joi: JoiRoot) => any> {
extraRehypePlugins: getUnifiedPluginSchema,
themeConfig: (Joi) => Joi.object().optional(),
logo: (Joi) => Joi.string(),
// FIXME: remove before 2.3.0
live: (Joi) => Joi.bool().optional(),
};
}
7 changes: 7 additions & 0 deletions src/features/derivative.ts
Original file line number Diff line number Diff line change
Expand Up @@ -175,6 +175,13 @@ export default (api: IApi) => {
);
}
} catch {}

// FIXME: remove before 2.3.0
if ('live' in api.config) {
logger.warn(
'`live` config is deprecated and live demo is always enabled now, please remove it.',
);
}
});

// skip mfsu for client api, to avoid circular resolve in mfsu mode
Expand Down
19 changes: 10 additions & 9 deletions src/loaders/markdown/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -142,14 +142,15 @@ export const demos = {

// use raw-loader to load all source files
Object.keys(this.resolveMap).forEach((file: string) => {
// handle un-existed source file, e.g. custom tech-stack return custom dependencies
if (!asset.dependencies[file]) return;

// to avoid modify original asset object
asset = lodash.cloneDeep(asset);
asset.dependencies[
file
].value = `{{{require('-!${resolveMap[file]}?dumi-raw').default}}}`;
// skip un-existed source file, e.g. custom tech-stack return custom dependencies
// skip non-file asset because resolveMap will contains all dependencies since 2.3.0
if (asset.dependencies[file]?.type === 'FILE') {
// to avoid modify original asset object
asset = lodash.cloneDeep(asset);
asset.dependencies[
file
].value = `{{{require('-!${resolveMap[file]}?dumi-raw').default}}}`;
}
});

return JSON.stringify(asset, null, 2).replace(/"{{{|}}}"/g, '');
Expand Down Expand Up @@ -304,7 +305,7 @@ export default function mdLoader(this: any, content: string) {
getDemoSourceFiles(ret.meta.demos),
);

// re-generate cache key with latest embeds & sources data
// re-generate cache key with latest embeds & source data
const finalCacheKey = [
baseCacheKey,
getDepsCacheKey(depsMapping[this.resourcePath]),
Expand Down
1 change: 1 addition & 0 deletions src/loaders/markdown/transformer/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -117,6 +117,7 @@ export default async (raw: string, opts: IMdTransformerOptions) => {
'rehype-remove-comments'
);
const resolver = enhancedResolve.create.sync({
mainFields: ['browser', 'module', 'main'],
extensions: ['.js', '.jsx', '.ts', '.tsx'],
alias: opts.alias,
});
Expand Down
4 changes: 2 additions & 2 deletions src/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -101,10 +101,10 @@ export abstract class IDumiTechStack {
| Promise<IDumiDemoProps['previewerProps']>
| IDumiDemoProps['previewerProps'];
/**
* generator for return file path of demo sources
* generator for return file path of demo source
*/
abstract generateSources?(
sources: IParsedBlockAsset['resolveMap'],
source: IParsedBlockAsset['resolveMap'],
opts: Parameters<NonNullable<IDumiTechStack['generateMetadata']>>[1],
): Promise<IParsedBlockAsset['resolveMap']> | IParsedBlockAsset['resolveMap'];
}
Expand Down
Loading