docs: add prettier

PR-URL: https://github.com/hasura/graphql-engine-mono/pull/9923
GitOrigin-RevId: 94038efe5768b63f38dfb447bc315ae5f7185c43
This commit is contained in:
Rikin Kachhia 2023-07-21 18:20:50 +05:30 committed by hasura-bot
parent b7a6bce19e
commit 4c66d648c7
33 changed files with 505 additions and 354 deletions

4
docs/.prettierignore Normal file
View File

@ -0,0 +1,4 @@
# Add files here to ignore them from prettier formatting
/build
/docs

5
docs/.prettierrc Normal file
View File

@ -0,0 +1,5 @@
{
"singleQuote": true,
"trailingComma": "es5",
"arrowParens": "avoid"
}

View File

@ -43,8 +43,11 @@ const config = {
docs: {
routeBasePath: '/',
sidebarPath: require.resolve('./sidebars.js'),
editUrl: ({ docPath }) => `https://github.com/hasura/graphql-engine/edit/master/docs/docs/${docPath}`,
docItemComponent: require.resolve('./src/components/CustomDocItem/index.tsx'),
editUrl: ({ docPath }) =>
`https://github.com/hasura/graphql-engine/edit/master/docs/docs/${docPath}`,
docItemComponent: require.resolve(
'./src/components/CustomDocItem/index.tsx'
),
exclude: ['**/*.wip'],
breadcrumbs: true,
// showLastUpdateAuthor: true,
@ -73,9 +76,12 @@ const config = {
id: 'wiki',
path: 'wiki',
routeBasePath: 'wiki',
editUrl: ({ docPath }) => `https://github.com/hasura/graphql-engine/edit/master/docs/docs/${docPath}`,
editUrl: ({ docPath }) =>
`https://github.com/hasura/graphql-engine/edit/master/docs/docs/${docPath}`,
editCurrentVersion: true,
docItemComponent: require.resolve('./src/components/CustomDocItem/CustomDocItemWiki.tsx'),
docItemComponent: require.resolve(
'./src/components/CustomDocItem/CustomDocItemWiki.tsx'
),
// disableVersioning: true,
breadcrumbs: false,
sidebarPath: require.resolve('./sidebarsWiki.js'),
@ -84,7 +90,10 @@ const config = {
}),
],
[
path.resolve(__dirname, './src/plugins/docusaurus-plugin-segment-analytics'),
path.resolve(
__dirname,
'./src/plugins/docusaurus-plugin-segment-analytics'
),
{
prodKey: 'RQXoHRpNcmBKllUDihjDjupGv4AHn5TB',
devKey: 'FRKElp5cyMax6GAdM8OVyNMIFVppgEgp',
@ -118,11 +127,20 @@ const config = {
disableSwitch: false,
respectPrefersColorScheme: true,
},
image: 'https://graphql-engine-cdn.hasura.io/assets/hge-docs/og-image.png',
image:
'https://graphql-engine-cdn.hasura.io/assets/hge-docs/og-image.png',
prism: {
theme: lightCodeTheme,
darkTheme: darkCodeTheme,
additionalLanguages: ['rest', 'http', 'haskell', 'plsql', 'docker', 'nginx', 'markdown'],
additionalLanguages: [
'rest',
'http',
'haskell',
'plsql',
'docker',
'nginx',
'markdown',
],
},
algolia: {
// If Algolia did not provide you any appId, use 'BH4D9OD16A'

View File

@ -20,7 +20,8 @@
"write-heading-ids": "docusaurus write-heading-ids",
"typecheck": "tsc",
"spellcheck": "./spell_check.sh",
"spelladd": "./spell_add.sh"
"spelladd": "./spell_add.sh",
"format": "prettier --write \"**/*.+(js|jsx|css|json|md|mdx)\""
},
"dependencies": {
"@docusaurus/core": "^2.2.0",
@ -45,7 +46,7 @@
"@docusaurus/module-type-aliases": "^2.1.0",
"@swc/core": "^1.3.23",
"@tsconfig/docusaurus": "^1.0.6",
"prettier": "^2.7.1",
"prettier": "^3.0.0",
"swc-loader": "^0.2.3",
"typescript": "^4.8.4"
},

View File

@ -27,7 +27,6 @@ module.exports = {
{
type: 'autogenerated',
dirName: '.', // generate sidebar from the docs folder (or versioned_docs/<version>)
},
],
};

View File

@ -18,9 +18,7 @@ const sidebars = {
{
type: 'category',
label: 'Docs Wiki',
items: [
{ type: 'autogenerated', dirName: '.' }
],
items: [{ type: 'autogenerated', dirName: '.' }],
},
// { type: 'autogenerated', dirName: 'migration-guide' },
],

View File

@ -17,7 +17,7 @@ const CloudDeployURLGenerationForm = () => {
}, [repoName, branchName, pathToDir]);
// Handle form input change
const handleChange = (e) => {
const handleChange = e => {
const { name, value } = e.target;
switch (name) {
case 'github-repo':
@ -38,18 +38,27 @@ const CloudDeployURLGenerationForm = () => {
const handleSubmit = () => {
// check for empty fields
if (repoName === '') {
alert('The repository name is empty. Please fill it out before proceeding.');
alert(
'The repository name is empty. Please fill it out before proceeding.'
);
return;
}
// check for whitespace or spaces in the fields
if (repoName.includes(' ') || branchName.includes(' ') || pathToDir.includes(' ')) {
alert('One or more fields contain whitespace. Please remove it and try again.');
if (
repoName.includes(' ') ||
branchName.includes(' ') ||
pathToDir.includes(' ')
) {
alert(
'One or more fields contain whitespace. Please remove it and try again.'
);
return;
}
const url = 'https://cloud.hasura.io/deploy'
+ `?github_repo=${repoName}`
+ `&hasura_dir=${pathToDir !== '' ? pathToDir : '/' }`
+ ((branchName !== '') ? `&branch=${branchName}` : '');
const url =
'https://cloud.hasura.io/deploy' +
`?github_repo=${repoName}` +
`&hasura_dir=${pathToDir !== '' ? pathToDir : '/'}` +
(branchName !== '' ? `&branch=${branchName}` : '');
setUrl(url);
navigator.clipboard.writeText(url);
@ -68,49 +77,58 @@ const CloudDeployURLGenerationForm = () => {
// we're calling the styles object here to apply the styles to the elements using their class names
<div className={styles['form-container']}>
<div>
<label for='github-repo'>Repository URL</label>
<label for="github-repo">Repository URL</label>
<small>
Enter the URL of the GitHub repository containing the Hasura assets
</small>
<input
type='text'
id='github-repo'
name='github-repo'
type="text"
id="github-repo"
name="github-repo"
value={repoName}
onChange={(e) => handleChange(e)}
placeholder='e.g. https://github.com/your-github-username/repository-name'
onChange={e => handleChange(e)}
placeholder="e.g. https://github.com/your-github-username/repository-name"
/>
</div>
<div>
<label for='mms-path'>Path to directory containing Hasura assets</label>
<label for="mms-path">Path to directory containing Hasura assets</label>
<small>
Enter the path to the directory containing your Metadata, Migrations and Seeds. If these are present in the root directory of the repository, you can skip this.
Enter the path to the directory containing your Metadata, Migrations
and Seeds. If these are present in the root directory of the
repository, you can skip this.
</small>
<input
type='text'
id='mms-path'
name='mms-path'
type="text"
id="mms-path"
name="mms-path"
value={pathToDir}
onChange={(e) => handleChange(e)}
placeholder='e.g. hasura'
onChange={e => handleChange(e)}
placeholder="e.g. hasura"
/>
</div>
<div>
<label htmlFor='github-branch'>Branch name</label>
<label htmlFor="github-branch">Branch name</label>
<small>
Enter the repository branch the Hasura assets should be picked from. If you'd like to use the default branch of your repository, you can skip this.
Enter the repository branch the Hasura assets should be picked from.
If you'd like to use the default branch of your repository, you can
skip this.
</small>
<input
type='text'
id='github-branch'
name='github-branch'
type="text"
id="github-branch"
name="github-branch"
value={branchName}
onChange={(e) => handleChange(e)}
placeholder='e.g. main'
onChange={e => handleChange(e)}
placeholder="e.g. main"
/>
</div>
<div className={styles['code-block']} style={{ maxHeight: isSubmitted && `800px` }}>
{isSubmitted && <p>Awesome! We've copied this link to your clipboard for you 🎉</p>}
<div
className={styles['code-block']}
style={{ maxHeight: isSubmitted && `800px` }}
>
{isSubmitted && (
<p>Awesome! We've copied this link to your clipboard for you 🎉</p>
)}
<code>{url}</code>
</div>
<div className={styles['button-container']}>
@ -119,7 +137,11 @@ const CloudDeployURLGenerationForm = () => {
onClick={() => handleSubmit()}
disabled={!isSubmittable}
style={{ cursor: isSubmittable ? 'pointer' : 'not-allowed' }}
title={isSubmittable ? 'Click to submit' : 'Please fill out all required fields'}
title={
isSubmittable
? 'Click to submit'
: 'Please fill out all required fields'
}
>
Generate URL
</button>

View File

@ -1,14 +1,14 @@
a.blue-dot {
position: relative;
position: relative;
}
.blue-dot::after {
content: "";
position: absolute;
top: 3px;
right: 3px;
width: 8px;
height: 8px;
border-radius: 50%;
background-color: #0b89d0;
}
content: '';
position: absolute;
top: 3px;
right: 3px;
width: 8px;
height: 8px;
border-radius: 50%;
background-color: #0b89d0;
}

View File

@ -18,8 +18,15 @@ const SampleAppBlock = ({ dependent }) => (
<h5 className="admonition-title">DOCS E-COMMERCE SAMPLE APP</h5>
</div>
<p dangerouslySetInnerHTML={createMarkup(dependent)} />
<a href="https://cloud.hasura.io/deploy?github_repo=https://github.com/hasura/docs-sample-app&hasura_dir=/" target={"_blank"} rel={"noopener"}>
<img src="https://hasura.io/deploy-button.svg" alt="Deploy to Hasura Cloud" />
<a
href="https://cloud.hasura.io/deploy?github_repo=https://github.com/hasura/docs-sample-app&hasura_dir=/"
target={'_blank'}
rel={'noopener'}
>
<img
src="https://hasura.io/deploy-button.svg"
alt="Deploy to Hasura Cloud"
/>
</a>
</div>
);

View File

@ -1,63 +1,57 @@
const path = require('path');
const { Joi } = require('@docusaurus/utils-validation');
const path = require('path');
const { Joi } = require('@docusaurus/utils-validation');
// import type { LoadContext, Plugin } from '@docusaurus/types';
// import type { PluginOptions } from './plugin-google-gtm';
function pluginGoogleGTM(
context,
options,
) {
const { trackingID } = options;
const isProd = process.env.NODE_ENV === 'production';
return {
name: 'docusaurus-plugin-google-gtm',
async contentLoaded({actions}) {
actions.setGlobalData(options);
},
injectHtmlTags() {
if (!isProd) return {};
return {
headTags: [
{
tagName: 'link',
attributes: {
rel: 'preconnect',
href: 'https://www.googletagmanager.com',
},
},
{
tagName: 'script',
innerHTML: `(function(w,d,s,l,i){w[l]=w[l]||[];w[l].push({'gtm.start':
function pluginGoogleGTM(context, options) {
const { trackingID } = options;
const isProd = process.env.NODE_ENV === 'production';
return {
name: 'docusaurus-plugin-google-gtm',
async contentLoaded({ actions }) {
actions.setGlobalData(options);
},
injectHtmlTags() {
if (!isProd) return {};
return {
headTags: [
{
tagName: 'link',
attributes: {
rel: 'preconnect',
href: 'https://www.googletagmanager.com',
},
},
{
tagName: 'script',
innerHTML: `(function(w,d,s,l,i){w[l]=w[l]||[];w[l].push({'gtm.start':
new Date().getTime(),event:'gtm.js'});var f=d.getElementsByTagName(s)[0],
j=d.createElement(s),dl=l!='dataLayer'?'&l='+l:'';j.async=true;j.src=
'https://www.googletagmanager.com/gtm.js?id='+i+dl;f.parentNode.insertBefore(j,f);
})(window,document,'script','dataLayer', '${trackingID}');`,
},
],
preBodyTags: [
},
],
preBodyTags: [
{
tagName: 'noscript',
innerHTML: `<iframe src="https://www.googletagmanager.com/ns.html?id=${trackingID}" height="0" width="0" style="display:none;visibility:hidden"></iframe>`,
},
],
};
},
};
}
],
};
},
};
}
const pluginOptionsSchema = Joi.object({
const pluginOptionsSchema = Joi.object({
trackingID: Joi.string().required(),
});
pluginGoogleGTM.validateOptions = function ({
validate,
options,
}) {
pluginGoogleGTM.validateOptions = function ({ validate, options }) {
return validate(pluginOptionsSchema, options);
}
module.exports = pluginGoogleGTM
};
module.exports = pluginGoogleGTM;

View File

@ -1,65 +1,59 @@
const path = require('path');
const { Joi } = require('@docusaurus/utils-validation');
const path = require('path');
const { Joi } = require('@docusaurus/utils-validation');
// import type { LoadContext, Plugin } from '@docusaurus/types';
// import type { PluginOptions } from './plugin-segment-analytics';
function pluginSegmentAnalitics(
context,
options,
) {
const { prodKey, devKey, trackPage } = options;
const isProd = process.env.NODE_ENV === 'production';
const writeKey = isProd ? prodKey : devKey;
return {
name: 'docusaurus-plugin-segment-analytics',
async contentLoaded({actions}) {
actions.setGlobalData(options);
},
getClientModules() {
return [path.resolve(__dirname, './segmentAnalytics')];
},
injectHtmlTags() {
if (!isProd) return {};
return {
headTags: [
{
tagName: 'link',
attributes: {
rel: 'preconnect',
href: 'https://cdn.segment.com',
},
},
{
tagName: 'script',
innerHTML: `
function pluginSegmentAnalitics(context, options) {
const { prodKey, devKey, trackPage } = options;
const isProd = process.env.NODE_ENV === 'production';
const writeKey = isProd ? prodKey : devKey;
return {
name: 'docusaurus-plugin-segment-analytics',
async contentLoaded({ actions }) {
actions.setGlobalData(options);
},
getClientModules() {
return [path.resolve(__dirname, './segmentAnalytics')];
},
injectHtmlTags() {
if (!isProd) return {};
return {
headTags: [
{
tagName: 'link',
attributes: {
rel: 'preconnect',
href: 'https://cdn.segment.com',
},
},
{
tagName: 'script',
innerHTML: `
!function(){var analytics=window.analytics=window.analytics||[];if(!analytics.initialize)if(analytics.invoked)window.console&&console.error&&console.error("Segment snippet included twice.");else{analytics.invoked=!0;analytics.methods=["trackSubmit","trackClick","trackLink","trackForm","pageview","identify","reset","group","track","ready","alias","debug","page","once","off","on","addSourceMiddleware","addIntegrationMiddleware","setAnonymousId","addDestinationMiddleware"];analytics.factory=function(e){return function(){var t=Array.prototype.slice.call(arguments);t.unshift(e);analytics.push(t);return analytics}};for(var e=0;e<analytics.methods.length;e++){var key=analytics.methods[e];analytics[key]=analytics.factory(key)}analytics.load=function(key,e){var t=document.createElement("script");t.type="text/javascript";t.async=!0;t.src="https://cdn.segment.com/analytics.js/v1/" + key + "/analytics.min.js";var n=document.getElementsByTagName("script")[0];n.parentNode.insertBefore(t,n);analytics._loadOptions=e};analytics._writeKey="${writeKey}";;analytics.SNIPPET_VERSION="4.15.3";
analytics.load("${writeKey}");
${trackPage ? "analytics.page();" : ""}
${trackPage ? 'analytics.page();' : ''}
}}();`,
},
],
};
},
};
}
},
],
};
},
};
}
const pluginOptionsSchema = Joi.object({
const pluginOptionsSchema = Joi.object({
prodKey: Joi.string().required(),
devKey: Joi.string().required(),
trackPage: Joi.boolean().default(false),
trackPageDelay: Joi.number().default(50),
});
pluginSegmentAnalitics.validateOptions = function ({
validate,
options,
}) {
pluginSegmentAnalitics.validateOptions = function ({ validate, options }) {
return validate(pluginOptionsSchema, options);
}
module.exports = pluginSegmentAnalitics
};
module.exports = pluginSegmentAnalitics;

View File

@ -7,17 +7,27 @@ import EditThisPage from '@theme/EditThisPage';
import TagsListInline from '@theme/TagsListInline';
import styles from './styles.module.css';
import { Feedback } from '@site/src/components/Feedback/Feedback';
import {HasuraReleaseNotification} from "@site/src/components/HasuraReleaseNotification/HasuraReleaseNotification";
import { HasuraReleaseNotification } from '@site/src/components/HasuraReleaseNotification/HasuraReleaseNotification';
function TagsRow(props) {
return (
<div className={clsx(ThemeClassNames.docs.docFooterTagsRow, 'row margin-bottom--sm')}>
<div
className={clsx(
ThemeClassNames.docs.docFooterTagsRow,
'row margin-bottom--sm'
)}
>
<div className="col">
<TagsListInline {...props} />
</div>
</div>
);
}
function EditMetaRow({ editUrl, lastUpdatedAt, lastUpdatedBy, formattedLastUpdatedAt }) {
function EditMetaRow({
editUrl,
lastUpdatedAt,
lastUpdatedBy,
formattedLastUpdatedAt,
}) {
return (
<div className={clsx(ThemeClassNames.docs.docFooterEditMetaRow, 'row')}>
<div className="col">{editUrl && <EditThisPage editUrl={editUrl} />}</div>
@ -36,7 +46,13 @@ function EditMetaRow({ editUrl, lastUpdatedAt, lastUpdatedBy, formattedLastUpdat
}
export default function DocItemFooter() {
const { metadata } = useDoc();
const { editUrl, lastUpdatedAt, formattedLastUpdatedAt, lastUpdatedBy, tags } = metadata;
const {
editUrl,
lastUpdatedAt,
formattedLastUpdatedAt,
lastUpdatedBy,
tags,
} = metadata;
const canDisplayTagsRow = tags.length > 0;
const canDisplayEditMetaRow = !!(editUrl || lastUpdatedAt || lastUpdatedBy);
const canDisplayFooter = canDisplayTagsRow || canDisplayEditMetaRow;
@ -45,9 +61,11 @@ export default function DocItemFooter() {
}
return (
<>
<Feedback metadata={metadata}/>
<HasuraReleaseNotification/>
<footer className={clsx(ThemeClassNames.docs.docFooter, 'docusaurus-mt-lg')}>
<Feedback metadata={metadata} />
<HasuraReleaseNotification />
<footer
className={clsx(ThemeClassNames.docs.docFooter, 'docusaurus-mt-lg')}
>
{canDisplayTagsRow && <TagsRow tags={tags} />}
{canDisplayEditMetaRow && (
<EditMetaRow

View File

@ -8,7 +8,7 @@ import algoliasearch from 'algoliasearch';
import styles from './styles.module.scss';
import Light404 from '@site/static/img/light-404.png';
import Dark404 from '@site/static/img/dark-404.png';
import Link from "@docusaurus/Link";
import Link from '@docusaurus/Link';
export default function NotFound() {
// State for handling search results
@ -16,7 +16,10 @@ export default function NotFound() {
const [loading, setLoading] = useState(true);
// Algolia search initialization
const client = algoliasearch('NS6GBGYACO', '8f0f11e3241b59574c5dd32af09acdc8');
const client = algoliasearch(
'NS6GBGYACO',
'8f0f11e3241b59574c5dd32af09acdc8'
);
const index = client.initIndex('hasura-graphql');
// Get the current location
@ -33,7 +36,7 @@ export default function NotFound() {
// Remove the no-no words from the query
const parsedQuery = query
.split('/')
.filter((word) => !removeList.includes(word))
.filter(word => !removeList.includes(word))
.join(' ');
// Search
@ -45,7 +48,7 @@ export default function NotFound() {
setSearchResults(hits);
setLoading(false);
})
.catch((error) => {
.catch(error => {
console.error(error);
});
}, []);
@ -59,35 +62,42 @@ export default function NotFound() {
})}
/>
<Layout>
<main className='container margin-vert--xl'>
<div className='row'>
<main className="container margin-vert--xl">
<div className="row">
<div className={styles['content']}>
<ThemedImage
sources={{
light: Light404,
dark: Dark404,
}}
alt='404'
alt="404"
/>
<div>
<h1>
<Translate id='theme.NotFound.title' description='The title of the 404 page'>
We have a broken link or the URL entered doesn't exist in our docs.
<Translate
id="theme.NotFound.title"
description="The title of the 404 page"
>
We have a broken link or the URL entered doesn't exist in
our docs.
</Translate>
</h1>
<p>
<Translate id='theme.NotFound.p2' description='The 2nd paragraph of the 404 page'>
<Translate
id="theme.NotFound.p2"
description="The 2nd paragraph of the 404 page"
>
{!loading && searchResults.length > 0
? `Our team has been notified and they're on it. Is there a chance one of these links will help?`
: ``}
</Translate>
</p>
<div className={styles['homeLink']}>
<Link to='/latest/index'>Hasura Docs Home</Link>
<Link to="/latest/index">Hasura Docs Home</Link>
</div>
<ul className={styles['results']}>
{searchResults &&
searchResults.map((result) => (
searchResults.map(result => (
<li key={result.objectID}>
<div>
<a href={result.url}>{result.hierarchy.lvl1}</a>

View File

@ -2,7 +2,12 @@ import React from 'react';
import styles from './styles.module.css';
import TOCItems from '@theme/TOCItems';
// In the event of re-swizzling, make sure to add the `filterTOC` and pass it down to TOCITems
export default function TOCInline({toc, minHeadingLevel, maxHeadingLevel, filterTOC}) {
export default function TOCInline({
toc,
minHeadingLevel,
maxHeadingLevel,
filterTOC,
}) {
return (
<div className={styles.tableOfContentsInline}>
<TOCItems

View File

@ -1,4 +1,4 @@
import React from "react";
import React from 'react';
// Recursive component rendering the toc tree
function TOCItemTree({ toc, className, linkClassName, isChild }) {
@ -7,7 +7,7 @@ function TOCItemTree({ toc, className, linkClassName, isChild }) {
}
return (
<ul className={isChild ? undefined : className}>
{toc.map((heading) => (
{toc.map(heading => (
<li key={heading.id}>
{/* eslint-disable-next-line jsx-a11y/control-has-associated-label */}
<a

View File

@ -1,6 +1,9 @@
import React, { useMemo } from 'react';
import { useThemeConfig } from '@docusaurus/theme-common';
import { useTOCHighlight, useFilteredAndTreeifiedTOC } from '@docusaurus/theme-common/internal';
import {
useTOCHighlight,
useFilteredAndTreeifiedTOC,
} from '@docusaurus/theme-common/internal';
import TOCItemTree from '@theme/TOCItems/Tree';
export default function TOCItems({
@ -13,8 +16,10 @@ export default function TOCItems({
...props
}) {
const themeConfig = useThemeConfig();
const minHeadingLevel = minHeadingLevelOption ?? themeConfig.tableOfContents.minHeadingLevel;
const maxHeadingLevel = maxHeadingLevelOption ?? themeConfig.tableOfContents.maxHeadingLevel;
const minHeadingLevel =
minHeadingLevelOption ?? themeConfig.tableOfContents.minHeadingLevel;
const maxHeadingLevel =
maxHeadingLevelOption ?? themeConfig.tableOfContents.maxHeadingLevel;
let tocTree = useFilteredAndTreeifiedTOC({
toc,
minHeadingLevel,
@ -40,7 +45,12 @@ export default function TOCItems({
__html: heading.value,
}}
/>
<TOCItemList isChild toc={heading.children} className={className} linkClassName={linkClassName} />
<TOCItemList
isChild
toc={heading.children}
className={className}
linkClassName={linkClassName}
/>
</li>
))}
</ul>
@ -92,5 +102,12 @@ export default function TOCItems({
return undefined;
}, [linkClassName, linkActiveClassName, minHeadingLevel, maxHeadingLevel]);
useTOCHighlight(tocHighlightConfig);
return <TOCItemTree toc={tocTree} className={className} linkClassName={linkClassName} {...props} />;
return (
<TOCItemTree
toc={tocTree}
className={className}
linkClassName={linkClassName}
{...props}
/>
);
}

View File

@ -243,7 +243,6 @@ Follow the instructions in the PR template and don't forget to add the `c/docs`
Once you open your PR, hasura-bot will assign a docs reviewer, and prompt you with some steps you need to complete for us to review your PR. You'll also get a handy preview link (which will need some time to build) at the end of the comment.
</TabItem>
<TabItem value='community' label='Community Members'>
@ -301,7 +300,11 @@ Assets are stored in `static/img/<feature-folder>`. Just like the file-based rou
file paths are important for images as well. However, instead of any output to the Console, the page will simply crash
and present a message indicating which image's path cannot be resolved.
<Thumbnail src="/img/wiki/broken-image.png" alt="Add check constraint" width="1000px" />
<Thumbnail
src="/img/wiki/broken-image.png"
alt="Add check constraint"
width="1000px"
/>
Use the erroneous image path to identify the error, facepalm, and then fix your typo.
@ -343,14 +346,22 @@ having to install any dependencies on your local machine.
Head to the `hasura/graphql-engine-mono` repo and click the `Code` button. You should see a `Open with Codespaces`
button. Click it and choose `...` and then `+ New with options...` as in the example below:
<Thumbnail src="/img/wiki/codespaces-1.gif" alt="Create Codespace" width="1000px" />
<Thumbnail
src="/img/wiki/codespaces-1.gif"
alt="Create Codespace"
width="1000px"
/>
### Step 2: Configure your Codespace
You'll be presented with a few options. Select the `docs` devcontainer, the region nearest to you, and a machine type
before clicking `Create codespace`:
<Thumbnail src="/img/wiki/codespaces-2.gif" alt="Create Codespace" width="1000px" />
<Thumbnail
src="/img/wiki/codespaces-2.gif"
alt="Create Codespace"
width="1000px"
/>
The Codespace will spin up and you'll be presented with a fully-configured dev environment. We automatically open you to
the `CODESPACES.md` file where you can follow the instructions to get started quickly.

View File

@ -8,7 +8,7 @@ While adding code blocks, ensure you set the correct language type. Sometimes ad
## Docusaurus - MDX
```markdown
````markdown
```graphql {2,5}
query {
// highlight-next-line
@ -24,32 +24,32 @@ While adding code blocks, ensure you set the correct language type. Sometimes ad
}
}
```
```
````
## Result in UI
```graphql {2,5}
query {
authors (where: {articles: {rating: {_gt: 4}}}) {
query {
authors(where: { articles: { rating: { _gt: 4 } } }) {
id
name
articles(where: { rating: { _gt: 4 } }) {
id
name
articles (where: {rating: {_gt: 4}}) {
id
title
rating
}
title
rating
}
}
}
```
:::caution Supported Languages
- Docusaurus uses prisma under the hood for code-block syntax highlighting. Please refer to the supported languages
[here](https://prismjs.com/#supported-languages).
[here](https://prismjs.com/#supported-languages).
- By default prisma includes a few that are listed
[here](https://github.com/FormidableLabs/prism-react-renderer/blob/master/src/vendor/prism/includeLangs.js). If any
supported language is not listed here, please add it to `additionalLanguages` under prisma plugin in
`docusaurus.config.js`.
[here](https://github.com/FormidableLabs/prism-react-renderer/blob/master/src/vendor/prism/includeLangs.js). If any
supported language is not listed here, please add it to `additionalLanguages` under prisma plugin in
`docusaurus.config.js`.
:::
@ -61,7 +61,7 @@ over `\n`, `\t` etc.
```html
<div className="parsed-literal">
<pre>
<pre>
<code>
{`{
"table" : `}<a href="#tablename">TableName</a>{`
@ -77,17 +77,22 @@ over `\n`, `\t` etc.
Using html + string templates is a workaround, if markdown ever supports this or provides an alternative, it would be
easy to find the respective usage and replace it. Nothing more :)
</details>
<div className="parsed-literal">
<pre>
<code>
{`{
"table" : `}<a href="#tablename">TableName</a>{`
"column" : `}<a href="#pgcolumn">PGColumn</a>{`
<pre>
<code>
{`{
"table" : `}
<a href="#tablename">TableName</a>
{`
"column" : `}
<a href="#pgcolumn">PGColumn</a>
{`
}`}
</code>
</pre>
</code>
</pre>
</div>
:::tip

View File

@ -1,6 +1,7 @@
---
sidebar_position: 8
---
import Tabs from '@theme/Tabs';
import TabItem from '@theme/TabItem';
import GraphiQLIDE from '@site/src/components/GraphiQLIDE';
@ -14,7 +15,7 @@ React component.
- Use a tab-width of 2 for nesting the requests and responses for optimal use of the space and maintaining consistency.
- Nest query arguments for logical readability. Unfortunately, GraphiQL prettify does not do a good job of doing this by
default.
default.
- Ensure that the order of fields in the responses is the same as in the requests for better readability.
Use it as follows:
@ -41,7 +42,6 @@ import GraphiQLIDE from '@site/src/components/GraphiQLIDE';
```
```jsx
// highlight-start
import GraphiQLIDE from '@site/src/components/GraphiQLIDE';
@ -82,12 +82,13 @@ import GraphiQLIDE from '@site/src/components/GraphiQLIDE';
]
}
}`}
/>
/>;
```
## Result in UI
Below is how it should look in UI.
<GraphiQLIDE
query={`query get_authors_in_pincode ($jsonFilter: jsonb){
authors(
@ -122,4 +123,4 @@ Below is how it should look in UI.
]
}
}`}
/>
/>

View File

@ -13,9 +13,9 @@ An example:
import Thumbnail from '@site/src/components/Thumbnail';
<Thumbnail
src='/img/graphql/manual/schema/validation-add-check-constraint.png'
alt='Add check constraint'
width='700px'
src="/img/graphql/manual/schema/validation-add-check-constraint.png"
alt="Add check constraint"
width="700px"
/>;
```

View File

@ -96,7 +96,8 @@ Which would render like this
<tr>
<td>Region</td>
<td>
The region of the datacenter where your New Relic account stores its data.{' '}
The region of the datacenter where your New Relic account stores its
data.{' '}
<Link to="https://docs.newrelic.com/docs/using-new-relic/welcome-new-relic/get-started/our-eu-us-region-data-centers">
Read more about regions on New Relic docs.
</Link>
@ -105,11 +106,17 @@ Which would render like this
<tr>
<td>API Key</td>
<td>
API keys are unique to your organization. An API key is required by the New Relic API to submit metrics and
events to New Relic. You can get the API key from{' '}
<Link to="https://one.newrelic.com/launcher/api-keys-ui.api-keys-launcher">here</Link> if you are in New Relic
US region and <Link to="https://one.eu.newrelic.com/launcher/api-keys-ui.api-keys-launcher">here</Link> if
you're in New Relic EU region.
API keys are unique to your organization. An API key is required by the
New Relic API to submit metrics and events to New Relic. You can get the
API key from{' '}
<Link to="https://one.newrelic.com/launcher/api-keys-ui.api-keys-launcher">
here
</Link>{' '}
if you are in New Relic US region and{' '}
<Link to="https://one.eu.newrelic.com/launcher/api-keys-ui.api-keys-launcher">
here
</Link>{' '}
if you're in New Relic EU region.
</td>
</tr>
<tr>
@ -119,9 +126,10 @@ Which would render like this
<tr>
<td>Custom Attributes</td>
<td>
Custom Attributes associated with your logs and metrics. A default source tag <code>hasura-cloud-metrics</code>{' '}
is added to all exported logs and metrics. Attributes <code>project_id</code> and <code>project_name</code> are
added to all exported metrics.
Custom Attributes associated with your logs and metrics. A default
source tag <code>hasura-cloud-metrics</code> is added to all exported
logs and metrics. Attributes <code>project_id</code> and{' '}
<code>project_name</code> are added to all exported metrics.
</td>
</tr>
<tr>

View File

@ -15,13 +15,11 @@ meta outside frontmatter.
:::
```markdown
---
title: Hasura GraphQL Engine Documentation
description: Hasura GraphQL Engine Documentation
keywords:
- hasura
- docs
- manual
- graphql engine
---
```
---
title: Hasura GraphQL Engine Documentation
description: Hasura GraphQL Engine Documentation
keywords: - hasura - docs - manual - graphql engine
---
```

View File

@ -1,10 +1,9 @@
import Tabs from '@theme/Tabs';
import TabItem from '@theme/TabItem';
import LatestRelease from "@site/src/components/LatestRelease";
import LatestRelease from '@site/src/components/LatestRelease';
# LatestRelease Tag
```jsx {1,5,9}
import LatestRelease from "@site/src/components/LatestRelease";
@ -17,15 +16,18 @@ The current latest pre-release version is:
<code>hasura/graphql-engine:<LatestRelease prerelease /></code>
```
## Result UI
The current latest stable version is:
<code>hasura/graphql-engine:<LatestRelease /></code>
<code>
hasura/graphql-engine:
<LatestRelease />
</code>
The current latest pre-release version is:
<code>hasura/graphql-engine:<LatestRelease prerelease /></code>
<code>
hasura/graphql-engine:
<LatestRelease prerelease />
</code>

View File

@ -1,23 +1,30 @@
---
sidebar_position: 5
---
import TOCInline from '@theme/TOCInline';
import Tabs from '@theme/Tabs';
import TabItem from '@theme/TabItem';
import Link from '@docusaurus/Link';
import { CustomTOCList, CustomTOCListSection, CustomTOCListHead, CustomTOCListContent } from "@site/src/components/CustomTOCList";
import {
CustomTOCList,
CustomTOCListSection,
CustomTOCListHead,
CustomTOCListContent,
} from '@site/src/components/CustomTOCList';
# Table of Contents
Two ways to list table of contents.
1. List the contents within the same document.
2. List contents for different documents. Say, an index page.
<br />
Below is auto listed TOC for this document
<TOCInline toc={toc} />
<TOCInline toc={toc} />
## Full table of contents
@ -26,7 +33,7 @@ This is the simplest way and is autogenerated on usage of `TOCInline` component
```jsx
import TOCInline from '@theme/TOCInline';
<TOCInline toc={toc} />
<TOCInline toc={toc} />;
```
Please refer docusaurus [Inline TOC docs](https://docusaurus.io/docs/markdown-features/inline-toc) for more insights into syntax and usage of `TOCInline`.
@ -45,8 +52,8 @@ Will see more about this component in below sections.
:::info
- The `:depth:` param can be controlled by [`toc_min_heading_level` and `toc_max_heading_level`](https://docusaurus.io/docs/api/plugins/@docusaurus/plugin-content-docs#toc_min_heading_level)
meta for individual files and [`minHeadingLevel` and `maxHeadingLevel`](https://docusaurus.io/docs/api/themes/configuration#table-of-contents)
for global theme config in docusaurus as given in docs.
meta for individual files and [`minHeadingLevel` and `maxHeadingLevel`](https://docusaurus.io/docs/api/themes/configuration#table-of-contents)
for global theme config in docusaurus as given in docs.
- The `:backlinks:` seems to be set to `none` for all and also there is no direct replacement in MDX via Docusaurus. So, can be ignored.
- The `:local` can be ignored as well cause the `TOCInline` component works only for local (same) document
@ -85,10 +92,7 @@ For this section, the url is `/docs/wiki/docusaurus-mdx-guide/table-of-contents/
```jsx {4}
// Render only the "Partial (Sub) Table of Contents" sub-items if any.
<TOCInline
toc={toc}
filterTOC={'partial-sub-table-of-contents'}
/>
<TOCInline toc={toc} filterTOC={'partial-sub-table-of-contents'} />
```
will result in:
@ -98,6 +102,7 @@ will result in:
:::note
The `filterTOC` prop can also be a function whose return value should be an array.
```jsx
filterTOC={tocTree => ([ toc[2], ... ])} or filterTOC={tocTree => toc[1].children}
```
@ -121,8 +126,6 @@ Please check the [Breaking changes that forced us to swizzle](https://docusaurus
### Dummy section 2
## Custom table of contents
Custom/Manually generated TOC can be a simple list or a group of lists (like a root index page)
@ -146,19 +149,26 @@ or if this needs to be done nested in a react component that doesn't support MDX
```jsx
import Link from '@docusaurus/Link';
import {
CustomTOCList, CustomTOCListSection, CustomTOCListHead, CustomTOCListContent,
} from "@site/src/components/CustomTOCList";
CustomTOCList,
CustomTOCListSection,
CustomTOCListHead,
CustomTOCListContent,
} from '@site/src/components/CustomTOCList';
<CustomTOCList>
<CustomTOCListSection>
<CustomTOCListContent>
<Link to="/docs/graphql/cloud/security/allow-lists">Allow Lists</Link>
<Link to="/docs/graphql/cloud/security/api-limits">API Limits</Link>
<Link to="/docs/graphql/cloud/security/disable-graphql-introspection">Disable GraphQL Introspection</Link>
<Link to="/docs/graphql/cloud/security/rotating-admin-secrets">Rotating Admin Secrets</Link>
<Link to="/docs/graphql/cloud/security/disable-graphql-introspection">
Disable GraphQL Introspection
</Link>
<Link to="/docs/graphql/cloud/security/rotating-admin-secrets">
Rotating Admin Secrets
</Link>
</CustomTOCListContent>
</CustomTOCListSection>
</CustomTOCList>
</CustomTOCList>;
```
:::caution Watchout the link type
@ -175,47 +185,47 @@ when using both types of syntax.
:::
#### Result UI
will render something like below.
### Group of lists
Its a list of simple lists (UI wise).
Unfortunately, there is no direct alternative for this in either MDX or Docusaurus. So we have to list these links
manually using this `CustomTOCList` component.
```jsx
import Link from '@docusaurus/Link';
import {
CustomTOCList, CustomTOCListSection, CustomTOCListHead, CustomTOCListContent,
} from "@site/src/components/CustomTOCList";
import Link from '@docusaurus/Link';
import {
CustomTOCList,
CustomTOCListSection,
CustomTOCListHead,
CustomTOCListContent,
} from '@site/src/components/CustomTOCList';
<CustomTOCList>
<CustomTOCList>
<CustomTOCListSection>
<CustomTOCListHead>API Security</CustomTOCListHead>
<CustomTOCListSection>
<CustomTOCListContent>
<Link to="/root/relative/path/to/cloud-api-reference">API Limits</Link>
<Link to="/root/relative/path/to/allow-lists">Allow Lists</Link>
</CustomTOCListContent>
</CustomTOCListSection>
<CustomTOCListHead>API Security</CustomTOCListHead>
<CustomTOCListSection>
<CustomTOCListHead>Reference</CustomTOCListHead>
<CustomTOCListContent>
<Link to="/root/relative/path/to/cloud-api-reference">API Limits</Link>
<Link to="/root/relative/path/to/allow-lists">Allow Lists</Link>
</CustomTOCListContent>
</CustomTOCListSection>
<CustomTOCListSection>
<CustomTOCListHead>Reference</CustomTOCListHead>
<CustomTOCListContent>
<Link to="/root/relative/path/to/cloud-api-reference">Cloud API Reference</Link>
<Link to="/root/relative/path/to/glossary">Glossary</Link>
<Link to="/root/relative/path/to/hasurapro-cli">Hasura Pro CLI</Link>
</CustomTOCListContent>
</CustomTOCListSection>
</CustomTOCList>
<CustomTOCListContent>
<Link to="/root/relative/path/to/cloud-api-reference">
Cloud API Reference
</Link>
<Link to="/root/relative/path/to/glossary">Glossary</Link>
<Link to="/root/relative/path/to/hasurapro-cli">Hasura Pro CLI</Link>
</CustomTOCListContent>
</CustomTOCListSection>
</CustomTOCList>;
```
#### Result UI
@ -249,7 +259,9 @@ This will render something like the below. Please note that links will be broken
```jsx
import Link from '@docusaurus/Link';
<Link to="/wiki/docusaurus-mdx-guide/links#root-relative-links">Root Relative Links</Link>
<Link to="/wiki/docusaurus-mdx-guide/links#root-relative-links">
Root Relative Links
</Link>;
```
- Please refer to the [Root Relative Links](/wiki/docusaurus-mdx-guide/links#root-relative-links) section too.

View File

@ -15,7 +15,8 @@ import TabItem from '@theme/TabItem';
<Tabs className="api-tabs">
<TabItem value="console" label="Console">
Click the `Reload` button in the `Remote Schema` section on the Hasura Console.
Click the `Reload` button in the `Remote Schema` section on the Hasura
Console.
</TabItem>
<TabItem value="api" label="API">
Make a request to the [reload_remote_schema](#) API.

View File

@ -11,21 +11,35 @@ import Thumbnail from '@site/src/components/Thumbnail';
```jsx
import Thumbnail from '@site/src/components/Thumbnail';
<Thumbnail src='/img/account-management/billing/add_new_card.png' alt='add a new card' width='437px' />;
<Thumbnail
src="/img/account-management/billing/add_new_card.png"
alt="add a new card"
width="437px"
/>;
```
Just pass in all the valid attributes for image as props.
## Result UI
<Thumbnail src='/img/account-management/billing/add_new_card.png' alt='add a new card' width='437px' />
<Thumbnail
src="/img/account-management/billing/add_new_card.png"
alt="add a new card"
width="437px"
/>
<hr />
A few examples,
<Thumbnail src='/img/account-management/billing/coupon_redemption.png' alt='Coupons and Credits' />
<Thumbnail
src="/img/account-management/billing/coupon_redemption.png"
alt="Coupons and Credits"
/>
<hr />
<Thumbnail src='/img/account-management/billing/invoice_settings.png' alt='invoice settings' />
<Thumbnail
src="/img/account-management/billing/invoice_settings.png"
alt="invoice settings"
/>

View File

@ -13,12 +13,19 @@ On the following pages, you'll find all the information you need to get started.
setting up your local development environment to creating your first PR.
## Get started with documentation
<video controls width="100%">
<source src={'https://graphql-engine-cdn.hasura.io/assets/videos/docs/documentation-presentation.mp4'} type="video/mp4" />
<source
src={
'https://graphql-engine-cdn.hasura.io/assets/videos/docs/documentation-presentation.mp4'
}
type="video/mp4"
/>
Sorry, your browser doesn't support embedded videos.
</video>
## What is good documentation?
Good documentation uses clear, simple, effective communication to explain the usage and workings of our product as
completely as possible.
@ -42,6 +49,7 @@ user-obsessed, complete and compelling way.
## Types of documentation
We strive to create quality, rich content in four logical areas of documentation including:
- Explanation
- Task guides
- Tutorials
@ -85,5 +93,6 @@ The impact of all documentation whether new, changed or existing should be measu
tools over time to determine its quality and impact for our user audience.
## Next steps...
After your local environment is set up, feel free to poke around the style guide, explanation of our page structures,
and info on working with Docusaurus (our docs framework).

View File

@ -11,7 +11,7 @@ slug: bullets
# Bullet Lists
* Don't use bullet points for one point.
* Make sure that content which belongs under a bullet point is actually indented under that bullet point in markdown.
* Use a period at the end of bullet lists which are a sentence, like this.
* Bullet points should not have a blank line between each point.
- Don't use bullet points for one point.
- Make sure that content which belongs under a bullet point is actually indented under that bullet point in markdown.
- Use a period at the end of bullet lists which are a sentence, like this.
- Bullet points should not have a blank line between each point.

View File

@ -10,45 +10,44 @@ slug: code-blocks
# Code Blocks
* All code blocks should be indented 2 spaces by default.
* Order fields for greater understanding.
* Remove parts of code if necessary in order to provide the greatest clarity to the user.
* Use only mandatory fields to keep examples concise.
* Use MDX [code block highlighting](https://docusaurus.io/docs/markdown-features/code-blocks#line-highlighting) to
- All code blocks should be indented 2 spaces by default.
- Order fields for greater understanding.
- Remove parts of code if necessary in order to provide the greatest clarity to the user.
- Use only mandatory fields to keep examples concise.
- Use MDX [code block highlighting](https://docusaurus.io/docs/markdown-features/code-blocks#line-highlighting) to
draw the user's attention to which lines the user should focus on.
* Show incorrect methods and common errors to improve the user's understanding but make sure they are very well
- Show incorrect methods and common errors to improve the user's understanding but make sure they are very well
highlighted as incorrect.
* Use single quotes instead of double quotes except where necessary eg: JSON
* Arrays in code should be split onto multiple lines, unless there is only one member of the array.
* When specifying code for the Hasura API, you can use either `curl` or an `http` block depending on whichever is
- Use single quotes instead of double quotes except where necessary eg: JSON
- Arrays in code should be split onto multiple lines, unless there is only one member of the array.
- When specifying code for the Hasura API, you can use either `curl` or an `http` block depending on whichever is
clearer for the user.
### HTTP
* All HTTP headers must begin with `First-Letter-Capitalized-Like-This`.
* HTTP blocks should run without changes if they are pasted into Postman, for example.
- All HTTP headers must begin with `First-Letter-Capitalized-Like-This`.
- HTTP blocks should run without changes if they are pasted into Postman, for example.
### Javascript
* Use semicolons `;` at the end of statements.
* Use single quotes instead of double quotes.
- Use semicolons `;` at the end of statements.
- Use single quotes instead of double quotes.
### JSON
* Indent 2 spaces.
* Do not include comments in JSON
- Indent 2 spaces.
- Do not include comments in JSON
### Shell
* Specify `bash` as code type for shell commands.
* Try to break separate commands into separate code blocks or else chain commands with `&&` or break into multi-line
- Specify `bash` as code type for shell commands.
- Try to break separate commands into separate code blocks or else chain commands with `&&` or break into multi-line
with `\`.
* Shell commands can include comments _before_ the command prefixed with `#`.
* If you would like to include output of the command, add it in a new block with `text` type.
- Shell commands can include comments _before_ the command prefixed with `#`.
- If you would like to include output of the command, add it in a new block with `text` type.
### YAML
* YAML should always be indented by 2 spaces as per the spec.
* Include only the relevant part of the code if it provides more clarity to the user. Indicate ommitted lines with
`...`
- YAML should always be indented by 2 spaces as per the spec.
- Include only the relevant part of the code if it provides more clarity to the user. Indicate ommitted lines with
`...`

View File

@ -10,30 +10,30 @@ slug: hasura-features
# Hasura Feature Names
* Hasura feature names should all use Title Case.
* Concepts such as "data federation", "authentication, "mutations", "connection pools" are not features and don't
need to be capitalised.
* If the name is written without the "Hasura" prefix it still needs to have a cap.
* An extensive list of feature names is below:
* Hasura API
* Hasura Actions
* Hasura CLI
* Hasura Cloud
* Hasura Console
* Hasura Enterprise
* Hasura Event Triggers
* Hasura GraphQL API Explorer
* Hasura GraphQL Engine
* Hasura Health Check
* Hasura Metadata
* Hasura Migrations
* Hasura Monitoring
* Hasura Community Edition
* Hasura OSS
* Hasura Preview Apps
* Hasura Projects
* Hasura Remote Schemas
* Hasura Scheduled Triggers
* Hasura Seeds
* Hasura Source Health Check
* Always capitalize 3rd party products appropriately, e.g: PostgreSQL, MS SQL Server, BigQuery.
- Hasura feature names should all use Title Case.
- Concepts such as "data federation", "authentication, "mutations", "connection pools" are not features and don't
need to be capitalised.
- If the name is written without the "Hasura" prefix it still needs to have a cap.
- An extensive list of feature names is below:
- Hasura API
- Hasura Actions
- Hasura CLI
- Hasura Cloud
- Hasura Console
- Hasura Enterprise
- Hasura Event Triggers
- Hasura GraphQL API Explorer
- Hasura GraphQL Engine
- Hasura Health Check
- Hasura Metadata
- Hasura Migrations
- Hasura Monitoring
- Hasura Community Edition
- Hasura OSS
- Hasura Preview Apps
- Hasura Projects
- Hasura Remote Schemas
- Hasura Scheduled Triggers
- Hasura Seeds
- Hasura Source Health Check
- Always capitalize 3rd party products appropriately, e.g: PostgreSQL, MS SQL Server, BigQuery.

View File

@ -34,7 +34,6 @@ An example:
`[Google](https://www.google.com/)` [Google](https://www.google.com/)
:::info Note
If you link to an external resource, make sure to link to the most current version of the same, e.g.

View File

@ -10,5 +10,5 @@ slug: semantics
# Semantics
* Write in the second person tense eg: `you`, `your`, and `we`, `our`. Instead of `the user`, `users` or `customers`.
* Use the word "directory" instead of "folder"
- Write in the second person tense eg: `you`, `your`, and `we`, `our`. Instead of `the user`, `users` or `customers`.
- Use the word "directory" instead of "folder"

View File

@ -5513,7 +5513,7 @@ __metadata:
graphiql: ^1.5.1
graphql: ^15.7.2
graphql-ws: ^5.11.2
prettier: ^2.7.1
prettier: ^3.0.0
prism-react-renderer: ^1.3.5
react: ^17.0.2
react-dom: ^17.0.2
@ -9295,12 +9295,12 @@ __metadata:
languageName: node
linkType: hard
"prettier@npm:^2.7.1":
version: 2.8.1
resolution: "prettier@npm:2.8.1"
"prettier@npm:^3.0.0":
version: 3.0.0
resolution: "prettier@npm:3.0.0"
bin:
prettier: bin-prettier.js
checksum: 4f21a0f1269f76fb36f54e9a8a1ea4c11e27478958bf860661fb4b6d7ac69aac1581f8724fa98ea3585e56d42a2ea317a17ff6e3324f40cb11ff9e20b73785cc
prettier: bin/prettier.cjs
checksum: 6a832876a1552dc58330d2467874e5a0b46b9ccbfc5d3531eb69d15684743e7f83dc9fbd202db6270446deba9c82b79d24383d09924c462b457136a759425e33
languageName: node
linkType: hard