Merge branch 'master' into scaffold
This commit is contained in:
@@ -177,9 +177,6 @@ docs on creating private GitHub access tokens is available
|
||||
Note that the need for private GitHub access tokens will be replaced with GitHub
|
||||
Apps integration further down the line.
|
||||
|
||||
> **Right now it is only possible to scaffold repositories inside GitHub
|
||||
> organizations, and not under personal accounts.**
|
||||
|
||||
The GitHub access token is passed along using the `GITHUB_ACCESS_TOKEN`
|
||||
environment variable.
|
||||
|
||||
|
||||
@@ -30,11 +30,6 @@ the documentation template.
|
||||
Create an entity from the documentation template and you will get the needed
|
||||
setup for free.
|
||||
|
||||
!!! warning Currently the Backstage Software Templates are limited to create
|
||||
repositories inside GitHub organizations. You also need to generate an personal
|
||||
access token and use as an environment variable. Read more about this
|
||||
[here](../software-templates/installation.md#runtime-dependencies).
|
||||
|
||||
### Manually add documentation setup to already existing repository
|
||||
|
||||
Prerequisities:
|
||||
|
||||
+11
-15
@@ -15,26 +15,26 @@
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { ProgressCard } from './ProgressCard';
|
||||
import { GaugeCard } from './GaugeCard';
|
||||
import { Grid } from '@material-ui/core';
|
||||
|
||||
const linkInfo = { title: 'Go to XYZ Location', link: '#' };
|
||||
|
||||
export default {
|
||||
title: 'Progress Card',
|
||||
component: ProgressCard,
|
||||
component: GaugeCard,
|
||||
};
|
||||
|
||||
export const Default = () => (
|
||||
<Grid container spacing={2}>
|
||||
<Grid item>
|
||||
<ProgressCard title="Progress" progress={0.3} />
|
||||
<GaugeCard title="Progress" progress={0.3} />
|
||||
</Grid>
|
||||
<Grid item>
|
||||
<ProgressCard title="Progress" progress={0.57} />
|
||||
<GaugeCard title="Progress" progress={0.57} />
|
||||
</Grid>
|
||||
<Grid item>
|
||||
<ProgressCard title="Progress" progress={0.89} />
|
||||
<GaugeCard title="Progress" progress={0.89} />
|
||||
</Grid>
|
||||
</Grid>
|
||||
);
|
||||
@@ -42,21 +42,17 @@ export const Default = () => (
|
||||
export const Subhead = () => (
|
||||
<Grid container spacing={2}>
|
||||
<Grid item>
|
||||
<ProgressCard
|
||||
title="Progress"
|
||||
subheader="With a subheader"
|
||||
progress={0.3}
|
||||
/>
|
||||
<GaugeCard title="Progress" subheader="With a subheader" progress={0.3} />
|
||||
</Grid>
|
||||
<Grid item>
|
||||
<ProgressCard
|
||||
<GaugeCard
|
||||
title="Progress"
|
||||
subheader="With a subheader"
|
||||
progress={0.57}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item>
|
||||
<ProgressCard
|
||||
<GaugeCard
|
||||
title="Progress"
|
||||
subheader="With a subheader"
|
||||
progress={0.89}
|
||||
@@ -68,13 +64,13 @@ export const Subhead = () => (
|
||||
export const LinkInFooter = () => (
|
||||
<Grid container spacing={2}>
|
||||
<Grid item>
|
||||
<ProgressCard title="Progress" deepLink={linkInfo} progress={0.3} />
|
||||
<GaugeCard title="Progress" deepLink={linkInfo} progress={0.3} />
|
||||
</Grid>
|
||||
<Grid item>
|
||||
<ProgressCard title="Progress" deepLink={linkInfo} progress={0.57} />
|
||||
<GaugeCard title="Progress" deepLink={linkInfo} progress={0.57} />
|
||||
</Grid>
|
||||
<Grid item>
|
||||
<ProgressCard title="Progress" deepLink={linkInfo} progress={0.89} />
|
||||
<GaugeCard title="Progress" deepLink={linkInfo} progress={0.89} />
|
||||
</Grid>
|
||||
</Grid>
|
||||
);
|
||||
+6
-8
@@ -18,32 +18,30 @@ import React from 'react';
|
||||
import { render } from '@testing-library/react';
|
||||
import { wrapInTestApp } from '@backstage/test-utils';
|
||||
|
||||
import { ProgressCard } from './ProgressCard';
|
||||
import { GaugeCard } from './GaugeCard';
|
||||
|
||||
const minProps = { title: 'Tingle upgrade', progress: 0.12 };
|
||||
|
||||
describe('<ProgressCard />', () => {
|
||||
describe('<GaugeCard />', () => {
|
||||
it('renders without exploding', () => {
|
||||
const { getByText } = render(wrapInTestApp(<ProgressCard {...minProps} />));
|
||||
const { getByText } = render(wrapInTestApp(<GaugeCard {...minProps} />));
|
||||
expect(getByText(/Tingle.*/)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('renders progress and title', () => {
|
||||
const { getByText } = render(wrapInTestApp(<ProgressCard {...minProps} />));
|
||||
const { getByText } = render(wrapInTestApp(<GaugeCard {...minProps} />));
|
||||
expect(getByText(/Tingle.*/)).toBeInTheDocument();
|
||||
expect(getByText(/12%.*/)).toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('does not render deepLink', () => {
|
||||
const { queryByText } = render(
|
||||
wrapInTestApp(<ProgressCard {...minProps} />),
|
||||
);
|
||||
const { queryByText } = render(wrapInTestApp(<GaugeCard {...minProps} />));
|
||||
expect(queryByText('View more')).not.toBeInTheDocument();
|
||||
});
|
||||
|
||||
it('handles invalid numbers', () => {
|
||||
const badProps = { title: 'Tingle upgrade', progress: 'hejjo' };
|
||||
const { getByText } = render(wrapInTestApp(<ProgressCard {...badProps} />));
|
||||
const { getByText } = render(wrapInTestApp(<GaugeCard {...badProps} />));
|
||||
expect(getByText(/N\/A.*/)).toBeInTheDocument();
|
||||
});
|
||||
});
|
||||
+3
-3
@@ -18,7 +18,7 @@ import React, { FC } from 'react';
|
||||
import { makeStyles } from '@material-ui/core';
|
||||
import { InfoCard } from '../../layout/InfoCard';
|
||||
import { BottomLinkProps } from '../../layout/BottomLink';
|
||||
import { CircleProgress } from './CircleProgress';
|
||||
import { GaugeProgress } from './GaugeProgress';
|
||||
|
||||
type Props = {
|
||||
title: string;
|
||||
@@ -36,7 +36,7 @@ const useStyles = makeStyles({
|
||||
},
|
||||
});
|
||||
|
||||
export const ProgressCard: FC<Props> = props => {
|
||||
export const GaugeCard: FC<Props> = props => {
|
||||
const classes = useStyles(props);
|
||||
const { title, subheader, progress, deepLink, variant } = props;
|
||||
|
||||
@@ -48,7 +48,7 @@ export const ProgressCard: FC<Props> = props => {
|
||||
deepLink={deepLink}
|
||||
variant={variant}
|
||||
>
|
||||
<CircleProgress value={progress} />
|
||||
<GaugeProgress value={progress} />
|
||||
</InfoCard>
|
||||
</div>
|
||||
);
|
||||
+6
-6
@@ -17,32 +17,32 @@
|
||||
import React from 'react';
|
||||
import { render } from '@testing-library/react';
|
||||
import { wrapInTestApp } from '@backstage/test-utils';
|
||||
import { CircleProgress, getProgressColor } from './CircleProgress';
|
||||
import { GaugeProgress, getProgressColor } from './GaugeProgress';
|
||||
|
||||
describe('<CircleProgress />', () => {
|
||||
describe('<GaugeProgress />', () => {
|
||||
it('renders without exploding', () => {
|
||||
const { getByText } = render(
|
||||
wrapInTestApp(<CircleProgress value={10} fractional={false} />),
|
||||
wrapInTestApp(<GaugeProgress value={10} fractional={false} />),
|
||||
);
|
||||
getByText('10%');
|
||||
});
|
||||
it('handles fractional prop', () => {
|
||||
const { getByText } = render(
|
||||
wrapInTestApp(<CircleProgress value={0.1} fractional />),
|
||||
wrapInTestApp(<GaugeProgress value={0.1} fractional />),
|
||||
);
|
||||
getByText('10%');
|
||||
});
|
||||
|
||||
it('handles max prop', () => {
|
||||
const { getByText } = render(
|
||||
wrapInTestApp(<CircleProgress value={1} max={10} fractional={false} />),
|
||||
wrapInTestApp(<GaugeProgress value={1} max={10} fractional={false} />),
|
||||
);
|
||||
getByText('1%');
|
||||
});
|
||||
|
||||
it('handles unit prop', () => {
|
||||
const { getByText } = render(
|
||||
wrapInTestApp(<CircleProgress value={10} fractional={false} unit="m" />),
|
||||
wrapInTestApp(<GaugeProgress value={10} fractional={false} unit="m" />),
|
||||
);
|
||||
getByText('10m');
|
||||
});
|
||||
+1
-1
@@ -77,7 +77,7 @@ export function getProgressColor(
|
||||
return palette.status.ok;
|
||||
}
|
||||
|
||||
export const CircleProgress: FC<Props> = props => {
|
||||
export const GaugeProgress: FC<Props> = props => {
|
||||
const classes = useStyles(props);
|
||||
const theme = useTheme<BackstageTheme>();
|
||||
const { value, fractional, inverse, unit, max } = {
|
||||
+6
-6
@@ -15,29 +15,29 @@
|
||||
*/
|
||||
|
||||
import React from 'react';
|
||||
import { HorizontalProgress } from './HorizontalProgress';
|
||||
import { LinearGauge } from './LinearGauge';
|
||||
|
||||
const containerStyle = { width: 300 };
|
||||
|
||||
export default {
|
||||
title: 'HorizontalProgress',
|
||||
component: HorizontalProgress,
|
||||
title: 'LinearGauge',
|
||||
component: LinearGauge,
|
||||
};
|
||||
|
||||
export const Default = () => (
|
||||
<div style={containerStyle}>
|
||||
<HorizontalProgress value={0.8} />
|
||||
<LinearGauge value={0.8} />
|
||||
</div>
|
||||
);
|
||||
|
||||
export const MediumProgress = () => (
|
||||
<div style={containerStyle}>
|
||||
<HorizontalProgress value={0.5} />
|
||||
<LinearGauge value={0.5} />
|
||||
</div>
|
||||
);
|
||||
|
||||
export const LowProgress = () => (
|
||||
<div style={containerStyle}>
|
||||
<HorizontalProgress value={0.2} />
|
||||
<LinearGauge value={0.2} />
|
||||
</div>
|
||||
);
|
||||
+2
-2
@@ -19,7 +19,7 @@ import { Tooltip, useTheme } from '@material-ui/core';
|
||||
// @ts-ignore
|
||||
import { Line } from 'rc-progress';
|
||||
import { BackstageTheme } from '@backstage/theme';
|
||||
import { getProgressColor } from './CircleProgress';
|
||||
import { getProgressColor } from './GaugeProgress';
|
||||
|
||||
type Props = {
|
||||
/**
|
||||
@@ -28,7 +28,7 @@ type Props = {
|
||||
value: number;
|
||||
};
|
||||
|
||||
export const HorizontalProgress: FC<Props> = ({ value }) => {
|
||||
export const LinearGauge: FC<Props> = ({ value }) => {
|
||||
const theme = useTheme<BackstageTheme>();
|
||||
if (isNaN(value)) {
|
||||
return null;
|
||||
@@ -14,6 +14,6 @@
|
||||
* limitations under the License.
|
||||
*/
|
||||
|
||||
export { ProgressCard } from './ProgressCard';
|
||||
export { CircleProgress } from './CircleProgress';
|
||||
export { HorizontalProgress } from './HorizontalProgress';
|
||||
export { GaugeCard } from './GaugeCard';
|
||||
export { GaugeProgress } from './GaugeProgress';
|
||||
export { LinearGauge } from './LinearGauge';
|
||||
|
||||
@@ -30,7 +30,7 @@ import {
|
||||
Table,
|
||||
StatusOK,
|
||||
TableColumn,
|
||||
ProgressCard,
|
||||
GaugeCard,
|
||||
TrendLine,
|
||||
} from '../../components';
|
||||
import { Box, Typography, Link, Chip, Grid } from '@material-ui/core';
|
||||
@@ -120,14 +120,14 @@ const DataGrid = () => (
|
||||
direction="row"
|
||||
>
|
||||
<Grid item xs={6}>
|
||||
<ProgressCard
|
||||
<GaugeCard
|
||||
title="GKE Usage Score"
|
||||
subheader="This should be above 75%"
|
||||
progress={0.87}
|
||||
/>
|
||||
</Grid>
|
||||
<Grid item xs={6}>
|
||||
<ProgressCard
|
||||
<GaugeCard
|
||||
title="Deployment Score"
|
||||
subheader="This should be above 40%"
|
||||
progress={0.58}
|
||||
|
||||
@@ -18,7 +18,7 @@ FROM python:3.8-alpine
|
||||
RUN apk update && apk --no-cache add gcc musl-dev openjdk11-jdk curl graphviz ttf-dejavu fontconfig
|
||||
|
||||
RUN curl -L http://sourceforge.net/projects/plantuml/files/plantuml.1.2020.16.jar/download > /opt/plantuml.jar
|
||||
RUN pip install --upgrade pip && pip install mkdocs-techdocs-core==0.0.4
|
||||
RUN pip install --upgrade pip && pip install mkdocs-techdocs-core==0.0.6
|
||||
|
||||
# Create script to call plantuml.jar from a location in path
|
||||
|
||||
|
||||
@@ -50,6 +50,10 @@ python -m black src/
|
||||
|
||||
## Changelog
|
||||
|
||||
### 0.0.5
|
||||
|
||||
- Downgrade some versions of markdown extensions to versions that are more stable
|
||||
|
||||
### 0.0.4
|
||||
|
||||
- Added support for more mkdocs extensions
|
||||
|
||||
@@ -4,10 +4,10 @@
|
||||
mkdocs==1.1.2
|
||||
mkdocs-material==5.3.2
|
||||
mkdocs-monorepo-plugin==0.4.5
|
||||
plantuml-markdown==3.4.0
|
||||
plantuml-markdown==3.1.2
|
||||
markdown_inline_graphviz_extension==1.1
|
||||
pygments==2.6.1
|
||||
pymdown-extensions==7.1
|
||||
pymdown-extensions==8.0.0
|
||||
|
||||
# The linter using for Python
|
||||
# Note: This requires Python 3.6+ to run, but can format Python 2 code too.
|
||||
|
||||
@@ -18,7 +18,7 @@ from setuptools import setup, find_packages
|
||||
|
||||
setup(
|
||||
name='mkdocs-techdocs-core',
|
||||
version='0.0.4',
|
||||
version='0.0.6',
|
||||
description='A Mkdocs package that contains TechDocs defaults',
|
||||
long_description='',
|
||||
keywords='mkdocs',
|
||||
@@ -31,10 +31,10 @@ setup(
|
||||
'mkdocs>=1.1.2',
|
||||
'mkdocs-material==5.3.2',
|
||||
'mkdocs-monorepo-plugin==0.4.5',
|
||||
'plantuml-markdown==3.4.0',
|
||||
'plantuml-markdown==3.1.2',
|
||||
'markdown_inline_graphviz_extension==1.1',
|
||||
'pygments==2.6.1',
|
||||
'pymdown-extensions==7.1'
|
||||
'pymdown-extensions==8.0.0'
|
||||
],
|
||||
classifiers=[
|
||||
'Development Status :: 1 - Planning',
|
||||
|
||||
@@ -19,6 +19,9 @@ export const mockGithubClient = {
|
||||
createInOrg: jest.fn(),
|
||||
createForAuthenticatedUser: jest.fn(),
|
||||
},
|
||||
users: {
|
||||
getByUsername: jest.fn(),
|
||||
},
|
||||
};
|
||||
|
||||
export class Octokit {
|
||||
|
||||
@@ -19,11 +19,18 @@ jest.mock('nodegit');
|
||||
|
||||
import { Octokit } from '@octokit/rest';
|
||||
import * as NodeGit from 'nodegit';
|
||||
import { OctokitResponse, ReposCreateInOrgResponseData } from '@octokit/types';
|
||||
import {
|
||||
OctokitResponse,
|
||||
ReposCreateInOrgResponseData,
|
||||
UsersGetByUsernameResponseData,
|
||||
} from '@octokit/types';
|
||||
import { GithubPublisher } from './github';
|
||||
|
||||
const { mockGithubClient } = require('@octokit/rest') as {
|
||||
mockGithubClient: { repos: jest.Mocked<Octokit['repos']> };
|
||||
mockGithubClient: {
|
||||
repos: jest.Mocked<Octokit['repos']>;
|
||||
users: jest.Mocked<Octokit['users']>;
|
||||
};
|
||||
};
|
||||
|
||||
const {
|
||||
@@ -59,10 +66,14 @@ describe('GitHub Publisher', () => {
|
||||
clone_url: 'mockclone',
|
||||
},
|
||||
} as OctokitResponse<ReposCreateInOrgResponseData>);
|
||||
mockGithubClient.users.getByUsername.mockResolvedValue({
|
||||
data: {
|
||||
type: 'Organization',
|
||||
},
|
||||
} as OctokitResponse<UsersGetByUsernameResponseData>);
|
||||
|
||||
await publisher.publish({
|
||||
values: {
|
||||
isOrg: true,
|
||||
storePath: 'blam/test',
|
||||
owner: 'bob',
|
||||
},
|
||||
@@ -81,6 +92,11 @@ describe('GitHub Publisher', () => {
|
||||
clone_url: 'mockclone',
|
||||
},
|
||||
} as OctokitResponse<ReposCreateInOrgResponseData>);
|
||||
mockGithubClient.users.getByUsername.mockResolvedValue({
|
||||
data: {
|
||||
type: 'User',
|
||||
},
|
||||
} as OctokitResponse<UsersGetByUsernameResponseData>);
|
||||
|
||||
await publisher.publish({
|
||||
values: {
|
||||
@@ -112,6 +128,12 @@ describe('GitHub Publisher', () => {
|
||||
clone_url: 'mockclone',
|
||||
},
|
||||
} as OctokitResponse<ReposCreateInOrgResponseData>);
|
||||
mockGithubClient.users.getByUsername.mockResolvedValue({
|
||||
data: {
|
||||
type: 'Organization',
|
||||
},
|
||||
} as OctokitResponse<UsersGetByUsernameResponseData>);
|
||||
|
||||
it('should call init on the repo with the directory', async () => {
|
||||
await publisher.publish({
|
||||
values,
|
||||
|
||||
@@ -45,9 +45,12 @@ export class GithubPublisher implements PublisherBase {
|
||||
) {
|
||||
const [owner, name] = values.storePath.split('/');
|
||||
|
||||
const repoCreationPromise = values.isOrg
|
||||
? this.client.repos.createInOrg({ name, org: owner })
|
||||
: this.client.repos.createForAuthenticatedUser({ name });
|
||||
const user = await this.client.users.getByUsername({ username: owner });
|
||||
|
||||
const repoCreationPromise =
|
||||
user.data.type === 'Organization'
|
||||
? this.client.repos.createInOrg({ name, org: owner })
|
||||
: this.client.repos.createForAuthenticatedUser({ name });
|
||||
|
||||
const { data } = await repoCreationPromise;
|
||||
|
||||
|
||||
@@ -46,8 +46,7 @@ export class ScaffolderApi {
|
||||
headers: {
|
||||
'Content-Type': 'application/json',
|
||||
},
|
||||
// TODO(shmidt-i): when repo picker is implemented, take isOrg from it
|
||||
body: JSON.stringify({ template, values: { ...values, isOrg: true } }),
|
||||
body: JSON.stringify({ template, values: { ...values } }),
|
||||
});
|
||||
|
||||
if (response.status !== 201) {
|
||||
|
||||
@@ -72,7 +72,7 @@ export const JobStatusModal = ({
|
||||
{entity && (
|
||||
<DialogActions>
|
||||
<Button
|
||||
to={generatePath(entityRoute.path, {
|
||||
to={generatePath(`/catalog/${entityRoute.path}`, {
|
||||
kind: entity.kind,
|
||||
optionalNamespaceAndName: [
|
||||
entity.metadata.namespace,
|
||||
|
||||
Reference in New Issue
Block a user