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

Add <ExecutableDocumentEditor /> component #281

Merged
merged 8 commits into from
Feb 7, 2022
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.
Jump to
Jump to file
Failed to load files.
Diff view
Diff view
5 changes: 5 additions & 0 deletions .changeset/tame-comics-buy.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
---
'@theguild/editor': minor
---

feat: :tada: add `<ExecutableDocumentEditor />` component
4 changes: 4 additions & 0 deletions packages/components/package.json
Original file line number Diff line number Diff line change
Expand Up @@ -28,5 +28,9 @@
},
"publishConfig": {
"access": "public"
},
"devDependencies": {
"@types/dedent": "^0.7.0",
"dedent": "0.7.0"
}
}
61 changes: 39 additions & 22 deletions packages/components/src/components/SchemaType.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import React from 'react';
import React, { FC, useState } from 'react';
import { buildSchema } from 'graphql';

import { ISchemaPageProps, IEditorProps } from '../types/components';
import { useThemeContext } from '../helpers/theme';
Expand All @@ -16,61 +17,62 @@ import {
Frameworks,
} from './SchemaTypes.styles';
import { Tag, TagsContainer } from './Tag';
import { SchemaEditor } from '../../../monaco-graphql-editor/src/editor/SchemaEditor';
import { SchemaEditor, ExecutableDocumentEditor } from '../../../monaco-graphql-editor/src';

const FrameworkList = ({ options }: { options: any }): JSX.Element => {
const FrameworkList = ({ options }: { options: any[] }): JSX.Element => {
const list = options.reduce((prev: string, curr: string) => [
prev,
<span key={prev}></span>,
<span key={prev} />,
curr,
]);

return <Frameworks>{list}</Frameworks>;
};

const Editor: React.FC<IEditorProps> = ({
const Editor: FC<Omit<IEditorProps, 'schema' | 'operations'>> = ({
title,
frameworks,
schema,
frameworks = [],
icon,
image,
children,
}) => (
<EditorWrapper className="wrapper">
<EditorHeader>
<div>
{image && <img src={image} alt="logo" />}
<span>
{title && <p>{title}</p>}
{frameworks && frameworks.length > 0 && (
<FrameworkList options={frameworks} />
)}
{frameworks.length > 0 && <FrameworkList options={frameworks} />}
</span>
</div>
<Button type="button" onClick={() => console.log('clicked')}>
<img src={icon} alt=">" />
</Button>
</EditorHeader>
<SchemaEditor schema={schema} />
{children}
</EditorWrapper>
);

export const SchemaPage: React.FC<ISchemaPageProps> = ({
export const SchemaPage: FC<ISchemaPageProps> = ({
schemaName,
tags,
tags = [],
editorData,
}) => {
const { isDarkTheme } = useThemeContext();
const marketplaceAssets = marketplaceThemedAssets(isDarkTheme || false);
const [schemaObj, setSchemaObj] = useState(() =>
buildSchema(editorData[0].schema!)
);

return (
<Wrapper>
<Container>
<Header>
<Title>{schemaName}</Title>
<TagsContainer>
{tags &&
tags.length > 0 &&
tags.map((tagName) => <Tag key={tagName}>{tagName}</Tag>)}
{tags.map((tagName) => (
<Tag key={tagName}>{tagName}</Tag>
))}
</TagsContainer>
</Header>
<ButtonWrapper>
Expand All @@ -83,15 +85,30 @@ export const SchemaPage: React.FC<ISchemaPageProps> = ({
</ButtonWrapper>
</Container>
<EditorGroupWrapper>
{(editorData as Array<IEditorProps>).map((data) => (
<Editor {...editorData[0]} icon={marketplaceAssets.caret}>
<SchemaEditor
schema={editorData[0].schema}
onSchemaChange={(newSchemaObject) => {
setSchemaObj(newSchemaObject);
}}
/>
</Editor>

<Editor {...editorData[1]} icon={marketplaceAssets.caret}>
<ExecutableDocumentEditor
schema={schemaObj}
defaultValue={editorData[1].operations!}
/>
</Editor>

{editorData.slice(2).map((data) => (
<Editor
{...data}
key={data.title || 'output'}
title={data.title}
frameworks={data.frameworks}
schema={data.schema}
image={data.image}
icon={marketplaceAssets.caret}
/>
>
<SchemaEditor schema={data.schema} />
</Editor>
))}
</EditorGroupWrapper>
</Wrapper>
Expand Down
70 changes: 46 additions & 24 deletions packages/components/src/helpers/dummy.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import dedent from 'dedent';
import featureListImage1 from '../static/dummy/envelop/features-pluggable.png';
import featureListImage2 from '../static/dummy/envelop/features-performant.png';
import featureListImage3 from '../static/dummy/envelop/features-modern.png';
Expand All @@ -24,8 +25,8 @@ export const dummyFeatureList = {
title: 'Learn more',
target: '_blank',
rel: 'noopener norefereer',
href: 'https://github.com/the-guild-org'
}
href: 'https://github.com/the-guild-org',
},
},
{
image: {
Expand Down Expand Up @@ -127,7 +128,7 @@ export const dummyHeroGradient = {
href: '#',
},
version: '1.0.7',
colors: ['#FF34AE', '#1CC8EE'],
colors: ['#ff34ae', '#1cc8ee'],
image: {
src: heroGradientImage,
alt: 'Illustration',
Expand Down Expand Up @@ -201,7 +202,7 @@ export const dummyCardsColorful = {
title: 'Learn more',
href: '#',
},
color: '#3547E5',
color: '#3547e5',
},
{
title: 'Clean up your code!',
Expand All @@ -211,7 +212,7 @@ export const dummyCardsColorful = {
title: 'Learn more',
href: '#',
},
color: '#0B0D11',
color: '#0b0d11',
},
],
};
Expand Down Expand Up @@ -563,7 +564,7 @@ export const dummyMarketplaceSearch = {
'relay',
'jsdoc',
'plugin',
'preset'
'preset',
],
placeholder: 'Search...',
primaryList: {
Expand All @@ -586,26 +587,47 @@ export const dummyMarketplaceSearch = {
},
};

const dummySchema = `type Query {
ping: Boolean
me: User!
}
const dummySchema = dedent(/* GraphQL */ `
type Query {
ping: Boolean
me: User!
}

" represents a valid email "
scalar Email

" represents a valid email "
scalar Email
"""
Represents a simple user
"""
type User {
id: ID!
email: Email!
profile: Profile!
}

""" Represents a simple user """
type User {
id: ID!
email: Email!
profile: Profile!
}
type Profile {
name: String
age: Int
}
`);

type Profile {
name: String
age: Int
}
`;
const dummyOperations = dedent(/* GraphQL */ `
query Me {
me {
id
profile {
name
}
}
ping
}

fragment UserFields on User {
profile {
name
}
}
`);

export const dummySchemaPage = {
schemaName: 'Schema Type 1',
Expand All @@ -620,7 +642,7 @@ export const dummySchemaPage = {
{
title: 'operation.graphql',
frameworks: [],
schema: dummySchema,
operations: dummyOperations,
image: marketplaceListImage,
},
{
Expand Down
12 changes: 10 additions & 2 deletions packages/components/src/types/components.ts
Original file line number Diff line number Diff line change
Expand Up @@ -75,6 +75,7 @@ interface IHeaderModalRestProps {
categoryTitleProps?: React.ComponentProps<'h3'>;
modalProps?: IModalRestProps;
}

export interface IHeaderModalProps extends IHeaderModalRestProps {
title: string | React.ReactNode;
modalOpen: boolean;
Expand Down Expand Up @@ -118,6 +119,7 @@ interface IModalRestProps {
headerLinkProps?: React.ComponentProps<'a'>;
headerImageProps?: React.ComponentProps<'img'>;
}

export interface IModalProps extends IModalRestProps {
title: string | React.ReactNode;
description?: string | ILink;
Expand Down Expand Up @@ -155,6 +157,7 @@ export interface IFeatureListProps {
itemDescriptionProps?: React.ComponentProps<'p'>;
itemImageProps?: React.ComponentProps<'img'>;
}

export interface IInfoListProps {
title?: string | React.ReactNode;
items: {
Expand All @@ -170,6 +173,7 @@ export interface IInfoListProps {
itemDescriptionProps?: React.ComponentProps<'p'>;
itemLinkProps?: React.ComponentProps<'a'>;
}

export interface IHeroVideoProps {
title: string | React.ReactNode;
description: string | React.ReactNode;
Expand All @@ -184,6 +188,7 @@ export interface IHeroVideoProps {
linkProps?: React.ComponentProps<'a'>;
videoProps?: ReactPlayerProps;
}

export interface IHeroIllustrationProps {
title: string | React.ReactNode;
description: string | React.ReactNode;
Expand All @@ -198,6 +203,7 @@ export interface IHeroIllustrationProps {
linkProps?: React.ComponentProps<'a'>;
imageProps?: React.ComponentProps<'img'>;
}

export interface IHeroGradientProps {
title: string | React.ReactNode;
description: string | React.ReactNode;
Expand Down Expand Up @@ -269,6 +275,7 @@ interface IMarketplaceItemRestProps {
dateProps?: React.ComponentProps<'span'>;
linkProps?: React.ComponentProps<'a'>;
}

export interface IMarketplaceItemsProps extends IMarketplaceItemRestProps {
icon: string;
items: IMarketplaceItemProps[];
Expand Down Expand Up @@ -311,13 +318,14 @@ export interface INewsletterProps {
export interface ISchemaPageProps {
schemaName: string;
tags?: string[];
editorData: string[] | React.ReactNode[];
editorData: Omit<IEditorProps, 'icon'>[];
}

export interface IEditorProps {
title?: string;
frameworks?: string[];
schema: string;
schema?: string;
icon: string;
image?: string;
operations?: string
}