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

Improve feature/pass-spec-directly #356

Open
wants to merge 2 commits into
base: feature/pass-spec-directly
Choose a base branch
from
Open
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
8 changes: 2 additions & 6 deletions packages/docusaurus-plugin-redoc/src/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -33,10 +33,6 @@ const version = require('../package.json').version;

export { PluginOptions, PluginDirectUsageOptions, loadRedoclyConfig };

function getIsExternalUrl(url = '') {
return ['http://', 'https://'].some((protocol) => url.startsWith(protocol));
}

export default function redocPlugin(
context: LoadContext,
opts: PluginOptions,
Expand All @@ -49,7 +45,7 @@ export default function redocPlugin(
const { debug, spec, url: downloadUrl, config, themeId } = options;

let url = downloadUrl;
const isExternalUrl = getIsExternalUrl(url);
const isExternalUrl = !!url;

const fileName = path.join(
'redocusaurus',
Expand Down Expand Up @@ -129,7 +125,7 @@ export default function redocPlugin(
}

const data: SpecDataResult = {
url,
downloadSpecUrl: url,
themeId,
// eslint-disable-next-line @typescript-eslint/no-explicit-any
spec: content.converted as any,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -11,13 +11,15 @@ const ApiSchema: React.FC<ApiSchemaProps> = ({
showExample,
pointer,
id,
themeId,
spec,
optionsOverrides,
...rest
}: ApiSchemaProps): JSX.Element => {
const { store } = useSpec(
{
id,
themeId,
spec,
},
optionsOverrides,
Expand Down
6 changes: 1 addition & 5 deletions packages/docusaurus-theme-redoc/src/theme/Redoc/Redoc.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -6,10 +6,6 @@ import useSpecOptions from '@theme/useSpecOptions';
import './styles.css';
import ServerRedoc from './ServerRedoc';

function getIsExternalUrl(url = '') {
return ['http://', 'https://'].some((protocol) => url.startsWith(protocol));
}

/*!
* Redocusaurus
* https://redocusaurus.vercel.app/
Expand All @@ -20,7 +16,7 @@ function Redoc(props: RedocProps): JSX.Element {
const { className, optionsOverrides, url, themeId } = props;
const { options } = useSpecOptions(themeId, optionsOverrides);

if (getIsExternalUrl(url)) {
Copy link
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

this is going to completely disable SSR for anyone using url, if that is what you want then we can just add that as an option I think rather than changing behavior for existing users.

We won't need downloadSpecUrl option, just a ssr option, by default true but which can be disabled to always use client side rendering and skip the bundling logic

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Allright I will try to do that change

if (url) {
return (
<div className={clsx(['redocusaurus', className])}>
<RedocStandalone specUrl={url} options={options} />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,11 +13,12 @@ import './styles.css';
* Released under the MIT License
*/
function ServerRedoc(props: RedocProps): JSX.Element {
const { className, optionsOverrides, url, id, themeId } = props;
const { className, optionsOverrides, id, themeId, downloadSpecUrl } = props;
const { store, spec, darkThemeOptions, lightThemeOptions, hasLogo } = useSpec(
{
spec: props.spec,
themeId,
downloadSpecUrl,
id,
},
optionsOverrides,
Expand All @@ -27,7 +28,7 @@ function ServerRedoc(props: RedocProps): JSX.Element {
<>
<ServerStyles
spec={spec}
url={url}
url={downloadSpecUrl}
lightThemeOptions={lightThemeOptions}
darkThemeOptions={darkThemeOptions}
/>
Expand Down
12 changes: 8 additions & 4 deletions packages/docusaurus-theme-redoc/src/theme/useSpec/useSpec.ts
Original file line number Diff line number Diff line change
Expand Up @@ -20,21 +20,25 @@ export function useSpec(
specInfo: SpecProps,
optionsOverrides?: RedocRawOptions,
): SpecResult {
const { spec, url, themeId } = useSpecData(
const { spec, downloadSpecUrl, themeId } = useSpecData(
specInfo.id,
specInfo.spec,
specInfo.themeId,
);
const specOptions = useSpecOptions(themeId, optionsOverrides);
const fullUrl = useBaseUrl(url, { absolute: true });
// build download URL by using downloadSpecUrl, fallback to useSpecData result
const fullDownloadSpecUrl = useBaseUrl(
specInfo.downloadSpecUrl || downloadSpecUrl,
{ absolute: true },
);
const isBrowser = useIsBrowser();
const isDarkTheme = useColorMode().colorMode === 'dark';

const result = useMemo(() => {
if (currentStore !== null && isBrowser) {
currentStore.dispose();
}
currentStore = new AppStore(spec, fullUrl, specOptions.options);
currentStore = new AppStore(spec, fullDownloadSpecUrl, specOptions.options);

return {
...specOptions,
Expand All @@ -43,7 +47,7 @@ export function useSpec(
store: currentStore,
spec,
};
}, [isBrowser, spec, fullUrl, specOptions]);
}, [isBrowser, spec, fullDownloadSpecUrl, specOptions]);

useEffect(() => {
// to ensure that menu is properly loaded when theme gets changed
Expand Down
9 changes: 4 additions & 5 deletions packages/docusaurus-theme-redoc/src/types/common.ts
Original file line number Diff line number Diff line change
Expand Up @@ -15,14 +15,13 @@ export interface SpecProps {
* docusaurus theme to use
*/
themeId?: string;
}

export type SpecDataResult = Omit<SpecProps, 'id'> & {
/**
* Public path to the spec file used, used by Redoc as download url
*/
url?: string;
};
downloadSpecUrl?: string;
}

export type SpecDataResult = Omit<SpecProps, 'id'>;

export interface MdxProps {
/**
Expand Down
11 changes: 5 additions & 6 deletions packages/docusaurus-theme-redoc/src/types/modules.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,10 @@ interface SpecProps {
* docusaurus theme to use
*/
themeId?: string;
/**
* Public path to the spec file used, used by Redoc as download url
*/
downloadSpecUrl?: string;
}
interface SpecResult {
hasLogo: boolean;
Expand Down Expand Up @@ -85,12 +89,7 @@ declare module '@theme/ApiSchema' {
}

declare module '@theme/useSpecData' {
type SpecDataResult = Omit<SpecProps, 'id'> & {
/**
* Public path to the spec file used, used by Redoc as download url
*/
url?: string;
};
type SpecDataResult = Omit<SpecProps, 'id'>;

/**
* Load redocusaurus plugin data by ID
Expand Down
45 changes: 41 additions & 4 deletions website/docs/guides/component-redoc.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -24,13 +24,28 @@ import Redoc from '@theme/Redoc';

## Props

| Name | Type | Description |
|------|--------------|-------------------------------------|
| spec | OpenAPI spec | A JSON content spec to use |
| url | String | External URL to load spec file from |
| Name | Type | Description |
|-----------------|--------------|---------------------------------------------------------------------------------------------|
| id | String | When spec not provided, load the spec from docusaurus config. Use first spec if not defined |
| spec | OpenAPI spec | A JSON content spec to use |
| url | String | External URL to load spec file from |
| themeId | String | redocusaurus theme to use - default to `theme-redoc` |
| downloadSpecUrl | String | Public path to the spec file used, used by Redoc as download url |

## Examples

### Basic example

It displays here the first element of the redocusaurus configuration.

```tsx
import Redoc from '@theme/Redoc';

<Redoc />
```

<Redoc />

### External URL example

```tsx
Expand All @@ -41,6 +56,26 @@ import Redoc from '@theme/Redoc';

<Redoc url="https://redocly.github.io/redoc/openapi.yaml"/>

### Specific id example

```tsx
import Redoc from '@theme/Redoc';

<Redoc id="using-single-yaml" />
```

<Redoc id="using-single-yaml" />

### Download url example

```tsx
import Redoc from '@theme/Redoc';

<Redoc id="using-single-yaml" downloadSpecUrl="https://redocly.github.io/redoc/openapi.yaml" />
```

<Redoc id="using-single-yaml" downloadSpecUrl="https://redocly.github.io/redoc/openapi.yaml" />

### Webpack loader example

You can provide a JSON spec to the component like this. Webpack will load the file directly,
Expand All @@ -57,9 +92,11 @@ import openApi from './api-with-examples.json'

:::info YAML support
You cannot load yaml file like this:

```tsx
import openApi from './api-with-examples.yaml'
```

Without the right webpack configuration to handle such file format.
:::

Loading