Open mrin9 opened 3 years ago
Hello,
What about typescript definitions?
I tried to use rapidoc in a typescript react project without success.
@francipvb Same problem. I started working on a wrapper for use in react:
/* eslint-disable @typescript-eslint/no-explicit-any */
import React from 'react';
import 'rapidoc';
interface RapiDocProps
extends React.DetailedHTMLProps<
React.HTMLAttributes<HTMLDivElement>,
HTMLDivElement
> {
// General
'spec-url': string;
'update-route'?: boolean;
'route-prefix'?: string;
'sort-tags'?: boolean;
'sort-endpoints-by'?: 'path' | 'method' | 'summary' | 'none';
'heading-text'?: string;
'goto-path'?: string;
'fill-request-fields-with-example'?: boolean;
'persist-auth'?: boolean;
// UI Colors and Fonts
theme?: 'light' | 'dark';
'bg-color'?: string;
'text-color'?: string;
'header-color'?: string;
'primary-color'?: string;
'load-fonts'?: boolean;
'regular-fonts'?: string;
'mono-fonts'?: string;
'font-size'?: 'default' | 'large' | 'largest';
// Navigation
'use-path-in-nav-bar'?: boolean;
'nav-bg-color'?: string;
'nav-text-color'?: string;
'nav-hover-bg-color'?: string;
'nav-hover-text-color'?: string;
'nav-accent-color'?: string;
'nav-item-spacing'?: 'default' | 'compact' | 'relaxed';
// UI Layout & Placement
layout?: 'row' | 'column';
'render-style'?: 'read' | 'view' | 'focused';
'on-nav-tag-click'?: 'expand-collapse' | 'show-description';
'schema-style'?: 'tree' | 'table';
'schema-expand-level'?: number;
'schema-description-expanded'?: boolean;
'schema-hide-read-only'?: 'always' | 'never' | string;
'default-schema-tab'?: 'model' | 'example';
'response-area-height'?: string;
// Hide/Show Sections
'show-info'?: boolean;
'info-description-headings-in-navbar'?: boolean;
'show-components'?: boolean;
'show-header'?: boolean;
'allow-authentication'?: boolean;
'allow-spec-url-load'?: boolean;
'allow-spec-file-load'?: boolean;
'allow-spec-file-download'?: boolean;
'allow-search'?: boolean;
'allow-advanced-search'?: boolean;
'allow-try'?: boolean;
'allow-server-selection'?: boolean;
'allow-schema-description-expand-toggle'?: boolean;
// API Server & calls
'server-url'?: string;
'default-api-server'?: string;
'api-key-name'?: string;
'api-key-location'?: 'header' | 'query';
'api-key-value'?: string;
'fetch-credentials'?: 'omit' | 'same-origin' | 'include';
// Events
beforeRender?: (spec: any) => void;
specLoaded?: (spec: any) => void;
beforeTry?: (request: any) => any;
afterTry?: (data: any) => any;
apiServerChange?: (server: any) => any;
}
declare global {
interface HTMLElementTagNameMap {
'rapi-doc': HTMLDivElement;
}
/* eslint-disable @typescript-eslint/no-namespace */
namespace JSX {
interface IntrinsicElements {
'rapi-doc': RapiDocProps;
}
}
}
export const RapiDocReact = React.forwardRef<HTMLDivElement, RapiDocProps>(
(
{
beforeRender,
specLoaded,
beforeTry,
afterTry,
apiServerChange,
children,
...props
}: RapiDocProps,
ref
) => {
const localRef = React.useRef<HTMLDivElement>(null);
React.useEffect(() => {
const rapiDocRef =
typeof ref === 'object' && ref?.current
? ref?.current
: localRef.current;
const handleBeforeRender = (spec: any) => {
beforeRender && beforeRender(spec);
};
const handleSpecLoaded = (spec: any) => {
specLoaded && specLoaded(spec);
};
const handleBeforeTry = (request: any) => {
beforeTry && beforeTry(request);
};
const handleAfterTry = (data: any) => {
afterTry && afterTry(data);
};
const handleApiServerChange = (server: any) => {
apiServerChange && apiServerChange(server);
};
console.log(`rapiDocRef`, rapiDocRef);
if (rapiDocRef) {
beforeRender &&
rapiDocRef.addEventListener('before-render', handleBeforeRender);
specLoaded &&
rapiDocRef.addEventListener('spec-loaded', handleSpecLoaded);
beforeTry && rapiDocRef.addEventListener('before-try', handleBeforeTry);
afterTry && rapiDocRef.addEventListener('after-try', handleAfterTry);
apiServerChange &&
rapiDocRef.addEventListener(
'api-server-change',
handleApiServerChange
);
}
return () => {
if (rapiDocRef) {
beforeRender &&
rapiDocRef.removeEventListener('before-render', handleBeforeRender);
specLoaded &&
rapiDocRef.removeEventListener('spec-loaded', handleSpecLoaded);
beforeTry &&
rapiDocRef.removeEventListener('before-try', handleBeforeTry);
afterTry &&
rapiDocRef.removeEventListener('after-try', handleAfterTry);
apiServerChange &&
rapiDocRef.removeEventListener(
'api-server-change',
handleApiServerChange
);
}
};
}, [
ref,
localRef,
specLoaded,
beforeRender,
beforeTry,
afterTry,
apiServerChange,
]);
return (
<rapi-doc {...props} ref={ref || localRef}>
{children}
</rapi-doc>
);
}
);
export default RapiDocReact;
Then you can use it like:
export function Example() {
return (
<RapiDocReact
specLoaded={(spec) => {
console.log(spec);
}}
show-header={false}
spec-url="https://petstore.swagger.io/v2/swagger.json"
render-style="read"
theme="dark"
style={{ height: '100vh', width: '100%' }}
/>
);
}
export default Example;
how to change the markdown styles. for ex: If i need to style the table,what is the approach?
@mrin9 Hi Mrinmoy, pls can you update examples for the filtering functionality, specifically to hide certain operations for specific users?
Thanks
It'd be great if you could generate other syntaxes than curl
. This is useful, but generating a fetch
call would also be useful for developers.
Highlighting some of RapiDoc's features as these may be helpful for making a decision if RapiDoc is the right tool
I have included links of some examples below, sources of all of them can be found at https://github.com/rapi-doc/RapiDoc/tree/master/docs/examples and the
OpenAPI
specs used by the examples can be found at https://github.com/rapi-doc/RapiDoc/tree/master/docs/specsRapiDoc Features
Theming and Customization
One of the main advantage of RapiDoc is its powerful customization. RapiDoc do not put any text that indicates the documentation is rendered using RapiDoc, you can completely replace the logos with your own, colors, fonts and theme can be changed to match with your own brand. Below are some of the feature that’s usually used
Three Different Presentation Styles
Hide/Show Sections to restrict or enable functionality
2 Beautiful Schema Presentation style
Search and Filter Functionality
Authentication
client-id
andsecret
exampleBuilt In API console
Not a premium feature, in fact we do not have any premium product.
curl
syntaxesMarkdown
Supports Open Schema Composition
ALL-OF
,ANY-OF
,ONE-OF
combinations and renders them beautifully - Examplerefs
to externalize definitionsHTML, JavaScript and CSS Injection
Sometimes markdown is not enough to achieve, what’s needed. For those situations you can inject your own functionality using JS , HTML and CSS.
It also allows you to present the same spec with different, content to different section of users You can use JS to add functionality, such as provide a button inside the document that can automatically authenticate your user HTML Injection Example
RapiDoc’s Vendor Extensions
Microservices support
Micro-services architecture may end up generating several OpenAPI spec, each with few Operations, However for the purpose of documentation you may want to list all these Specs in a single integrated view and should appear as a single spec. Thats possible with RapiDoc. For an inspiration have a look at this example - https://www.northbricks.io/apis/ , which appears to be a single documentation but is made with multiple instance of RapiDoc , each rendering a separate OpenAPI spec. (VIew source from browser to check implementation)
Framework Agnostic
All the above listed feature is programmable, You may check our API section to see how you can use these feature programatically. This isn’t a React, Angular or Vue component, But a standard natively supported Web Component and therefore can be accessed and integrated with any framework or just using a plain javascript without any other library
Here is a RapiDoc API Playground where we use plain JavaScript to dynamically make changes to the RapiDoc