Skip to content

Commit

Permalink
Add GitHub Actions bot view (#37852)
Browse files Browse the repository at this point in the history
* add bots UI, disabled

- in original data table view

* Add bot creation UI

* Remove duplicated types

* add bots UI, disabled

- in original data table view

* Fix types and tests

* Use bot join token api endpoint

* Fix tests

* Linting and small fixes

* Fix tests

* Add missing licenses

* Improve styles, error messages, etc

* Remove clusterId from bot routes

* Undo enabling feature

* Remove unused join role bot

* Rename var

* Reuse makeListBot

* Add missing type

* Revert MachineIDIntegrationSection for now

* Lint

* Apply suggestions from code review - fix typos

Co-authored-by: Noah Stride <[email protected]>

* Remove kubernetes section fromm example yaml

* Remove border color from reftype selector

* Small changes to address code review

* Use setAttempt

* add try/catch block when parsing repo addresses

* Improve tests;remove unecessary fragment

* Use gap in flex. Fix typo

* Lint fix

* Drop "ex" from input placeholders

* Add stories for no perm and bot picker

* Add copy to explain wrkflow name limits

* fix setCurentStep

* Fix invalid host error rendering

* Use PascalCase for error components

* Improve field name validation

* Remove unecessary comments

* Add bot type by label

* Add bot view...

* Show view gh actions yaml only for gh bots

* Use existing pattern for operations

* Add story and missing license

* Fix typos

Co-authored-by: Michelle Bergquist <[email protected]>

---------

Co-authored-by: Michelle Bergquist <[email protected]>
Co-authored-by: Noah Stride <[email protected]>
Co-authored-by: Michelle Bergquist <[email protected]>
  • Loading branch information
4 people committed Feb 12, 2024
1 parent ebaf393 commit ef1463e
Show file tree
Hide file tree
Showing 15 changed files with 293 additions and 15 deletions.
4 changes: 2 additions & 2 deletions web/packages/teleport/src/Bots/Add/AddBots.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -23,7 +23,7 @@ import cfg from 'teleport/config';

import { FeatureBox } from 'teleport/components/Layout';

import { BotType } from '../types';
import { BotFlowType } from '../types';

import GitHubActionsFlow from './GitHubActions';
import { AddBotsPicker } from './AddBotsPicker';
Expand All @@ -33,7 +33,7 @@ export function AddBots() {
<FeatureBox>
<Switch>
<Route
path={cfg.getBotsNewRoute(BotType.GitHubActions)}
path={cfg.getBotsNewRoute(BotFlowType.GitHubActions)}
component={GitHubActionsFlow}
/>
<Route path={cfg.getBotsNewRoute()} component={AddBotsPicker} />
Expand Down
4 changes: 2 additions & 2 deletions web/packages/teleport/src/Bots/Add/AddBotsPicker.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@ import {
import { IntegrationTile } from 'teleport/Integrations';
import { FeatureHeader, FeatureHeaderTitle } from 'teleport/components/Layout';

import { BotType } from '../types';
import { BotFlowType } from '../types';

type BotIntegration = {
title: string;
Expand All @@ -58,7 +58,7 @@ type BotIntegration = {
const integrations: BotIntegration[] = [
{
title: 'GitHub Actions + SSH',
link: cfg.getBotsNewRoute(BotType.GitHubActions),
link: cfg.getBotsNewRoute(BotFlowType.GitHubActions),
icon: <GitHubIcon size={80} />,
kind: IntegrationEnrollKind.MachineIDGitHubActions,
guided: true,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -84,11 +84,12 @@ export function AddBotToWorkflow({ prevStep, nextStep }: FlowStepProps) {
);
}

function getWorkflowExampleYaml(
export function getWorkflowExampleYaml(
botName: string,
version: string,
proxyAddr: string,
tokenName: string
tokenName: string,
includeNameComment: boolean = true
): string {
return `on:
push:
Expand All @@ -101,7 +102,7 @@ demo:
# able to authenticate with the cluster.
id-token: write
contents: read
# if you added a workflow name in the previous step, make sure you use the same value here
${includeNameComment && '# if you added a workflow name in the previous step, make sure you use the same value here'}
name: ${botName}-example
runs-on: ubuntu-latest
steps:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@

import { GitHubIcon } from 'design/SVGIcon';

import { BotType } from 'teleport/Bots/types';
import { BotFlowType } from 'teleport/Bots/types';

import cfg from 'teleport/config';

Expand All @@ -35,7 +35,7 @@ import { GitHubFlowProvider } from './useGitHubFlow';

export const GitHubActionsFlow = {
title: 'GitHub Actions',
link: cfg.getBotsNewRoute(BotType.GitHubActions),
link: cfg.getBotsNewRoute(BotFlowType.GitHubActions),
icon: <GitHubIcon size={80} />,
kind: IntegrationEnrollKind.MachineIDGitHubActions,
guided: true,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,10 @@ import { ResourceLabel } from 'teleport/services/agents';
import {
createBot as serviceCreateBot,
createBotToken,
GITHUB_ACTIONS_LABEL_KEY,
} from 'teleport/services/bot';
import {
BotUiFlow,
CreateBotRequest,
GitHubRepoRule,
RefType,
Expand All @@ -35,8 +37,7 @@ import {
import useTeleport from 'teleport/useTeleport';

export const GITHUB_HOST = 'github.com';
const GITHUB_ACTIONS_LABEL_KEY = 'teleport.internal/ui-flow';
const GITHUB_ACTIONS_LABEL_VAL = 'github-actions-ssh';
const GITHUB_ACTIONS_LABEL_VAL = BotUiFlow.GitHubActionsSsh;

type GitHubFlowContext = {
attempt: Attempt;
Expand Down
8 changes: 7 additions & 1 deletion web/packages/teleport/src/Bots/List/ActionCell.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -21,11 +21,14 @@ import { Cell } from 'design/DataTable';
import { MenuButton, MenuItem } from 'shared/components/MenuAction';

import { BotOptionsCellProps } from 'teleport/Bots/types';
import { BotUiFlow } from 'teleport/services/bot/types';

export function BotOptionsCell({
onClickDelete,
onClickView,
bot,
disabledEdit,
onClickEdit,
onClickDelete,
}: BotOptionsCellProps) {
return (
<Cell align="right">
Expand All @@ -34,6 +37,9 @@ export function BotOptionsCell({
Edit...
</MenuItem>
<MenuItem onClick={onClickDelete}>Delete...</MenuItem>
{bot.type === BotUiFlow.GitHubActionsSsh && (
<MenuItem onClick={onClickView}>View...</MenuItem>
)}
</MenuButton>
</Cell>
);
Expand Down
49 changes: 48 additions & 1 deletion web/packages/teleport/src/Bots/List/BotList.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -16,11 +16,12 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/

import { render, screen } from 'design/utils/testing';
import { fireEvent, render, screen } from 'design/utils/testing';

import { BotList } from 'teleport/Bots/List/BotList';
import { BotListProps } from 'teleport/Bots/types';
import { botsFixture } from 'teleport/Bots/fixtures';
import { BotUiFlow } from 'teleport/services/bot/types';

const makeProps = (): BotListProps => ({
attempt: { status: '' },
Expand Down Expand Up @@ -50,3 +51,49 @@ test('renders table with bots', () => {
});
});
});

test('renders View options if type is github actions ssh', async () => {
const bot = {
namespace: '',
description: '',
labels: null,
revision: '',
traits: [],
status: '',
subKind: '',
version: '',
kind: 'kind',
name: 'github-actions-bot',
roles: [],
type: BotUiFlow.GitHubActionsSsh,
};

const props = makeProps();
props.bots = [bot];
render(<BotList {...props} />);
await fireEvent.click(await screen.findByText('OPTIONS'));
expect(screen.getByText('View...')).toBeInTheDocument();
});

test('doesnt renders View options if bot type is not github actions', async () => {
const bot = {
namespace: '',
description: '',
labels: null,
revision: '',
traits: [],
status: '',
subKind: '',
version: '',
kind: 'kind',
name: 'github-actions-bot',
roles: [],
type: null,
};

const props = makeProps();
props.bots = [bot];
render(<BotList {...props} />);
await fireEvent.click(await screen.findByText('OPTIONS'));
expect(screen.queryByText('View...')).not.toBeInTheDocument();
});
10 changes: 10 additions & 0 deletions web/packages/teleport/src/Bots/List/BotList.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,10 @@ import { BotListProps } from 'teleport/Bots/types';
import { DeleteBot } from 'teleport/Bots/DeleteBot';
import { EditBot } from 'teleport/Bots/EditBot';

import { ViewBot } from '../ViewBot';

enum Interaction {
VIEW,
EDIT,
DELETE,
NONE,
Expand Down Expand Up @@ -70,6 +73,10 @@ export function BotList({
render: bot => (
<BotOptionsCell
bot={bot}
onClickView={() => {
setSelectedBot(bot);
setInteraction(Interaction.VIEW);
}}
disabledEdit={disabledEdit}
onClickEdit={() => {
setSelectedBot(bot);
Expand Down Expand Up @@ -107,6 +114,9 @@ export function BotList({
setSelectedRoles={setSelectedRoles}
/>
)}
{selectedBot && interaction === Interaction.VIEW && (
<ViewBot onClose={onClose} bot={selectedBot} />
)}
</>
);
}
59 changes: 59 additions & 0 deletions web/packages/teleport/src/Bots/ViewBot.story.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,59 @@
/**
* Teleport
* Copyright (C) 2024 Gravitational, Inc.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/

import React from 'react';

import { BotUiFlow } from 'teleport/services/bot/types';

import { ContextProvider } from 'teleport';
import { createTeleportContext } from 'teleport/mocks/contexts';

import { ViewBot } from './ViewBot';
import { ViewBotProps } from './types';

export default {
title: 'Teleport/Bots/Add/ViewBot',
};

export const GitHubActionsSsh = () => {
const ctx = createTeleportContext();

return (
<ContextProvider ctx={ctx}>
<ViewBot {...props} />
</ContextProvider>
);
};

const props: ViewBotProps = {
bot: {
name: 'my-github-bot',
type: BotUiFlow.GitHubActionsSsh,
namespace: '',
description: '',
labels: null,
revision: '',
traits: [],
status: '',
subKind: '',
version: '',
kind: '',
roles: [],
},
onClose: () => {},
};
74 changes: 74 additions & 0 deletions web/packages/teleport/src/Bots/ViewBot.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
/**
* Teleport
* Copyright (C) 2024 Gravitational, Inc.
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU Affero General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU Affero General Public License for more details.
*
* You should have received a copy of the GNU Affero General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/

import React from 'react';
import { ButtonSecondary, Flex, Text } from 'design';
import Dialog, {
DialogContent,
DialogFooter,
DialogHeader,
DialogTitle,
} from 'design/DialogConfirmation';

import TextEditor from 'shared/components/TextEditor';

import { ViewBotProps } from 'teleport/Bots/types';

import useTeleport from 'teleport/useTeleport';

import { getWorkflowExampleYaml } from './Add/GitHubActions/AddBotToWorkflow';

export function ViewBot({ bot, onClose }: ViewBotProps) {
const ctx = useTeleport();
const cluster = ctx.storeUser.state.cluster;

const yaml = getWorkflowExampleYaml(
bot.name,
cluster.authVersion,
cluster.publicURL,
bot.name,
false
);

return (
<Dialog disableEscapeKeyDown={false} onClose={onClose} open={true}>
<DialogHeader>
<DialogTitle>{bot.name}</DialogTitle>
</DialogHeader>
<DialogContent width="640px">
<Text mb="4">
Below is an example GitHub Actions workflow to help you get started.
You can find this again from the bot’s options dropdown.
</Text>
<Flex height="500px" pt="3" pr="3" bg="levels.deep" borderRadius={3}>
<TextEditor
readOnly={true}
bg="levels.deep"
data={[{ content: yaml, type: 'yaml' }]}
copyButton={true}
downloadButton={true}
downloadFileName={`${bot.name}-githubactions.yaml`}
/>
</Flex>
</DialogContent>
<DialogFooter>
<ButtonSecondary onClick={onClose}>Close</ButtonSecondary>
</DialogFooter>
</Dialog>
);
}
8 changes: 7 additions & 1 deletion web/packages/teleport/src/Bots/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ export type BotOptionsCellProps = {
disabledEdit: boolean;
onClickEdit: (bot: FlatBot) => void;
onClickDelete: (bot: FlatBot) => void;
onClickView: (bot: FlatBot) => void;
};

export type BotListProps = {
Expand All @@ -48,7 +49,12 @@ export type DeleteBotProps = {
onDelete: () => void;
};

export enum BotType {
export type ViewBotProps = {
bot: FlatBot;
onClose: () => void;
};

export enum BotFlowType {
GitHubActions = 'github-actions',
}

Expand Down
Loading

0 comments on commit ef1463e

Please sign in to comment.