Thanks to visit codestin.com
Credit goes to github.com

Skip to content

feat: Add create template from the UI #5427

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

Merged
merged 61 commits into from
Dec 21, 2022
Merged
Show file tree
Hide file tree
Changes from 1 commit
Commits
Show all changes
61 commits
Select commit Hold shift + click to select a range
300a763
feat: add examples to api
f0ssel Dec 6, 2022
da9fc00
add support for example id in route
f0ssel Dec 7, 2022
a9f04f3
move files
f0ssel Dec 7, 2022
90e6a9d
fix existing tests
f0ssel Dec 7, 2022
7084ceb
add tests
f0ssel Dec 7, 2022
50fb405
more tests
f0ssel Dec 7, 2022
b00a3b9
more tests
f0ssel Dec 7, 2022
86350be
Display starter templates
BrunoQuaresma Dec 8, 2022
c3b2e67
Add styles to the template card
BrunoQuaresma Dec 8, 2022
c144866
Mock entity and handler
BrunoQuaresma Dec 8, 2022
c133cc3
Add storybook
BrunoQuaresma Dec 8, 2022
e7aec29
Add loader
BrunoQuaresma Dec 8, 2022
3062814
Add tests
BrunoQuaresma Dec 8, 2022
d7455c1
Add basic page to starter template
BrunoQuaresma Dec 8, 2022
193c930
Add buttons
BrunoQuaresma Dec 8, 2022
9a5b1de
Fix title
BrunoQuaresma Dec 8, 2022
c820f4b
Addd storybook
BrunoQuaresma Dec 8, 2022
9829ad0
Add test
BrunoQuaresma Dec 8, 2022
c9d1c7a
Use translation
BrunoQuaresma Dec 8, 2022
85266d0
add icon and tag parsing
f0ssel Dec 9, 2022
9f3108f
remove extra test work
f0ssel Dec 9, 2022
0dce958
Merge branch 'f0ssel/examples' of github.com:coder/coder into bq/fe-e…
BrunoQuaresma Dec 9, 2022
3091bea
Merge branch 'main' of github.com:coder/coder into bq/fe-examples
BrunoQuaresma Dec 9, 2022
79442ef
Add icons to page header
BrunoQuaresma Dec 9, 2022
3529c74
Add filters
BrunoQuaresma Dec 9, 2022
efa624c
Improve markdown code
BrunoQuaresma Dec 9, 2022
e05a8dc
Merge branch 'main' of github.com:coder/coder into bq/fe-examples
BrunoQuaresma Dec 12, 2022
e05d148
Add filter
BrunoQuaresma Dec 12, 2022
4fc75b7
Add basic create template form structure
BrunoQuaresma Dec 12, 2022
9805c2f
Add translation
BrunoQuaresma Dec 12, 2022
439ec15
Add services and actions into machine
BrunoQuaresma Dec 12, 2022
ce82a85
Pre-fill info from example data
BrunoQuaresma Dec 12, 2022
36282fc
Create Icon fiels and remove extra console.log
BrunoQuaresma Dec 12, 2022
5b01321
Add basic API for template creation
BrunoQuaresma Dec 13, 2022
ca606a4
Merge branch 'main' of github.com:coder/coder into bq/fe-examples
BrunoQuaresma Dec 13, 2022
521803f
Fix create template from example id
BrunoQuaresma Dec 13, 2022
d39cabe
Show parameters
BrunoQuaresma Dec 14, 2022
fe71988
Add upload
BrunoQuaresma Dec 14, 2022
a9f3e18
Fix steps
BrunoQuaresma Dec 14, 2022
9ae5ed1
Update layout
BrunoQuaresma Dec 14, 2022
e19bd13
Merge branch 'main' of github.com:coder/coder into bq/fe-examples
BrunoQuaresma Dec 14, 2022
cc3a2cb
Update verbiage
BrunoQuaresma Dec 14, 2022
273a711
Merge branch 'main' of github.com:coder/coder into bq/fe-examples
BrunoQuaresma Dec 16, 2022
2d8430b
Use data
BrunoQuaresma Dec 16, 2022
a2e07fb
Show logs on error
BrunoQuaresma Dec 16, 2022
80a2989
Merge branch 'main' of github.com:coder/coder into bq/fe-examples
BrunoQuaresma Dec 19, 2022
43c8faa
Add templates link
BrunoQuaresma Dec 20, 2022
e64db78
Fix upload
BrunoQuaresma Dec 20, 2022
cec4b00
Add link to starter templates
BrunoQuaresma Dec 20, 2022
8b0f95b
Add empty state
BrunoQuaresma Dec 20, 2022
6de5c52
Create empty state and experimental tags
BrunoQuaresma Dec 20, 2022
228bc58
Add help tooltip
BrunoQuaresma Dec 20, 2022
155e901
Fix tests
BrunoQuaresma Dec 20, 2022
4edfed8
Lazy load starter template page
BrunoQuaresma Dec 20, 2022
30e017e
Apply suggestions from code review
BrunoQuaresma Dec 21, 2022
98a5f84
No need to trim display name and description
BrunoQuaresma Dec 21, 2022
6aa0bfa
Return undefined it is not n api error
BrunoQuaresma Dec 21, 2022
f8e8d33
Display error
BrunoQuaresma Dec 21, 2022
4b47137
Merge branch 'bq/fe-examples' of github.com:coder/coder into bq/fe-ex…
BrunoQuaresma Dec 21, 2022
be4de6a
Return error
BrunoQuaresma Dec 21, 2022
e75714f
Fix test
BrunoQuaresma Dec 21, 2022
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
Prev Previous commit
Next Next commit
Create empty state and experimental tags
  • Loading branch information
BrunoQuaresma committed Dec 20, 2022
commit 6de5c5210624e915369ce4ca6ca432975f55877d
34 changes: 31 additions & 3 deletions site/src/pages/TemplatesPage/EmptyTemplates.tsx
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
import Button from "@material-ui/core/Button"
import Link from "@material-ui/core/Link"
import { makeStyles } from "@material-ui/core/styles"
import { TemplateExample } from "api/typesGenerated"
import { Entitlements, TemplateExample } from "api/typesGenerated"
import { CodeExample } from "components/CodeExample/CodeExample"
import { Stack } from "components/Stack/Stack"
import { TableEmpty } from "components/TableEmpty/TableEmpty"
Expand All @@ -28,12 +28,13 @@ const findFeaturedExamples = (examples: TemplateExample[]) => {
export const EmptyTemplates: FC<{
permissions: Permissions
examples: TemplateExample[]
}> = ({ permissions, examples }) => {
entitlements: Entitlements
}> = ({ permissions, examples, entitlements }) => {
const styles = useStyles()
const { t } = useTranslation("templatesPage")
const featuredExamples = findFeaturedExamples(examples)

if (permissions.createTemplates) {
if (permissions.createTemplates && entitlements.experimental) {
return (
<TableEmpty
message={t("empty.message")}
Expand Down Expand Up @@ -80,6 +81,33 @@ export const EmptyTemplates: FC<{
)
}

if (permissions.createTemplates) {
return (
<TableEmpty
className={styles.withImage}
message={t("empty.message")}
description={
<>
To create a workspace you need to have a template. You can{" "}
<Link
target="_blank"
href="https://coder.com/docs/coder-oss/latest/templates"
>
create one from scratch
</Link>{" "}
or use a built-in template using the following Coder CLI command:
</>
}
cta={<CodeExample code="coder templates init" />}
image={
<div className={styles.emptyImage}>
<img src="/featured/templates.webp" alt="" />
</div>
}
/>
)
}

return (
<TableEmpty
className={styles.withImage}
Expand Down
4 changes: 3 additions & 1 deletion site/src/pages/TemplatesPage/TemplatesPage.tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import { useMachine } from "@xstate/react"
import { useEntitlements } from "hooks/useEntitlements"
import { useOrganizationId } from "hooks/useOrganizationId"
import { usePermissions } from "hooks/usePermissions"
import React from "react"
Expand All @@ -10,6 +11,7 @@ import { TemplatesPageView } from "./TemplatesPageView"
export const TemplatesPage: React.FC = () => {
const organizationId = useOrganizationId()
const permissions = usePermissions()
const entitlements = useEntitlements()
const [templatesState] = useMachine(templatesMachine, {
context: {
organizationId,
Expand All @@ -24,7 +26,7 @@ export const TemplatesPage: React.FC = () => {
</Helmet>
<TemplatesPageView
context={templatesState.context}
permissions={permissions}
entitlements={entitlements}
/>
</>
)
Expand Down
124 changes: 91 additions & 33 deletions site/src/pages/TemplatesPage/TemplatesPageView.stories.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,13 @@
import { ComponentMeta, Story } from "@storybook/react"
import { makeMockApiError, MockTemplate } from "../../testHelpers/entities"
import {
makeMockApiError,
MockEntitlements,
MockOrganization,
MockPermissions,
MockTemplate,
MockTemplateExample,
MockTemplateExample2,
} from "../../testHelpers/entities"
import { TemplatesPageView, TemplatesPageViewProps } from "./TemplatesPageView"

export default {
Expand All @@ -11,50 +19,100 @@ const Template: Story<TemplatesPageViewProps> = (args) => (
<TemplatesPageView {...args} />
)

export const AllStates = Template.bind({})
AllStates.args = {
canCreateTemplate: true,
templates: [
MockTemplate,
{
...MockTemplate,
active_user_count: -1,
description: "🚀 Some new template that has no activity data",
icon: "/icon/goland.svg",
},
{
...MockTemplate,
active_user_count: 150,
description: "😮 Wow, this one has a bunch of usage!",
icon: "",
},
{
...MockTemplate,
description:
"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. ",
},
],
export const WithTemplates = Template.bind({})
WithTemplates.args = {
entitlements: MockEntitlements,
context: {
organizationId: MockOrganization.id,
permissions: MockPermissions,
error: undefined,
templates: [
MockTemplate,
{
...MockTemplate,
active_user_count: -1,
description: "🚀 Some new template that has no activity data",
icon: "/icon/goland.svg",
},
{
...MockTemplate,
active_user_count: 150,
description: "😮 Wow, this one has a bunch of usage!",
icon: "",
},
{
...MockTemplate,
description:
"Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Ut enim ad minim veniam, quis nostrud exercitation ullamco laboris nisi ut aliquip ex ea commodo consequat. ",
},
],
examples: [],
},
}

export const SmallViewport = Template.bind({})
SmallViewport.args = {
...AllStates.args,
export const WithTemplatesSmallViewPort = Template.bind({})
WithTemplatesSmallViewPort.args = {
...WithTemplates.args,
}
SmallViewport.parameters = {
WithTemplatesSmallViewPort.parameters = {
chromatic: { viewports: [600] },
}

export const EmptyCanCreate = Template.bind({})
EmptyCanCreate.args = {
canCreateTemplate: true,
entitlements: MockEntitlements,
context: {
organizationId: MockOrganization.id,
permissions: MockPermissions,
error: undefined,
templates: [],
examples: [MockTemplateExample, MockTemplateExample2],
},
}

export const EmptyCanCreateExperimental = Template.bind({})
EmptyCanCreateExperimental.args = {
entitlements: {
...MockEntitlements,
experimental: true,
},
context: {
organizationId: MockOrganization.id,
permissions: MockPermissions,
error: undefined,
templates: [],
examples: [MockTemplateExample, MockTemplateExample2],
},
}

export const EmptyCannotCreate = Template.bind({})
EmptyCannotCreate.args = {}
EmptyCannotCreate.args = {
entitlements: MockEntitlements,
context: {
organizationId: MockOrganization.id,
permissions: {
...MockPermissions,
createTemplates: false,
},
error: undefined,
templates: [],
examples: [MockTemplateExample, MockTemplateExample2],
},
}

export const Error = Template.bind({})
Error.args = {
getTemplatesError: makeMockApiError({
message: "Something went wrong fetching templates.",
}),
entitlements: MockEntitlements,
context: {
organizationId: MockOrganization.id,
permissions: {
...MockPermissions,
createTemplates: false,
},
error: makeMockApiError({
message: "Something went wrong fetching templates.",
}),
templates: undefined,
examples: undefined,
},
}
13 changes: 5 additions & 8 deletions site/src/pages/TemplatesPage/TemplatesPageView.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,6 @@ import useTheme from "@material-ui/styles/useTheme"
import { AlertBanner } from "components/AlertBanner/AlertBanner"
import { ChooseOne, Cond } from "components/Conditionals/ChooseOne"
import { Maybe } from "components/Conditionals/Maybe"
import { useEntitlements } from "hooks/useEntitlements"
import { FC } from "react"
import { useNavigate, Link as RouterLink } from "react-router-dom"
import { createDayString } from "util/createDayString"
Expand All @@ -38,10 +37,9 @@ import {
HelpTooltipText,
HelpTooltipTitle,
} from "../../components/Tooltips/HelpTooltip/HelpTooltip"
import { usePermissions } from "hooks/usePermissions"
import { EmptyTemplates } from "./EmptyTemplates"
import { TemplatesContext } from "xServices/templates/templatesXService"
import { Permissions } from "xServices/auth/authXService"
import { Entitlements } from "api/typesGenerated"

export const Language = {
developerCount: (activeCount: number): string => {
Expand Down Expand Up @@ -76,20 +74,18 @@ const TemplateHelpTooltip: React.FC = () => {

export interface TemplatesPageViewProps {
context: TemplatesContext
permissions: Permissions
entitlements: Entitlements
}

export const TemplatesPageView: FC<
React.PropsWithChildren<TemplatesPageViewProps>
> = ({ context }) => {
> = ({ context, entitlements }) => {
const styles = useStyles()
const navigate = useNavigate()
const theme: Theme = useTheme()
const { templates, error, examples } = context
const { templates, error, examples, permissions } = context
const isLoading = !templates
const isEmpty = Boolean(templates && templates.length === 0)
const entitlements = useEntitlements()
const permissions = usePermissions()

return (
<Margins>
Expand Down Expand Up @@ -162,6 +158,7 @@ export const TemplatesPageView: FC<
<EmptyTemplates
permissions={permissions}
examples={examples ?? []}
entitlements={entitlements}
/>
</Cond>

Expand Down
16 changes: 14 additions & 2 deletions site/src/testHelpers/entities.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import { everyOneGroup } from "util/groups"
import * as Types from "../api/types"
import * as TypesGen from "../api/typesGenerated"
import { range } from "lodash"
import { Permissions } from "xServices/auth/authXService"

export const MockTemplateDAUResponse: TypesGen.TemplateDAUsResponse = {
entries: [
Expand Down Expand Up @@ -1065,8 +1066,8 @@ export const MockTemplateACLEmpty: TypesGen.TemplateACL = {
}

export const MockTemplateExample: TypesGen.TemplateExample = {
id: "aws-ecs-container",
url: "https://github.com/coder/coder/tree/main/examples/templates/aws-ecs-container",
id: "aws-windows",
url: "https://github.com/coder/coder/tree/main/examples/templates/aws-windows",
name: "Develop in an ECS-hosted container",
description: "Get started with Linux development on AWS ECS.",
markdown:
Expand All @@ -1085,3 +1086,14 @@ export const MockTemplateExample2: TypesGen.TemplateExample = {
icon: "/icon/aws.png",
tags: ["aws", "cloud"],
}

export const MockPermissions: Permissions = {
createGroup: true,
createTemplates: true,
createUser: true,
deleteTemplates: true,
readAllUsers: true,
updateUsers: true,
viewAuditLog: true,
viewDeploymentConfig: true,
}