Skip to content

Commit

Permalink
Basic attempt to implement the README card functionality
Browse files Browse the repository at this point in the history
As per the discussion on loblaw-sre#25
this is the work I did to enable this functionality with a custom
plugin.
  • Loading branch information
Leo Ackerman committed Feb 17, 2022
1 parent de140df commit db3054f
Show file tree
Hide file tree
Showing 7 changed files with 126 additions and 2 deletions.
1 change: 1 addition & 0 deletions src/api/GitlabCIApi.ts
Original file line number Diff line number Diff line change
Expand Up @@ -48,4 +48,5 @@ export type GitlabCIApi = {
pipelineID: string,
): Promise<Object | undefined>;
getProjectDetails(projectSlug: string): Promise<Object | undefined>;
getFileContent(projectId: string, filename: string, ref: string): Promise<string | undefined>;
};
24 changes: 24 additions & 0 deletions src/api/GitlabCIClient.ts
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ import {
ContributorData,
MergeRequest,
PipelineObject,
RepositoryFileObject,
} from '../components/types';

export class GitlabCIClient implements GitlabCIApi {
Expand Down Expand Up @@ -161,4 +162,27 @@ export class GitlabCIClient implements GitlabCIApi {
);
return retryBuild;
}

private static encodeFilename(filename: string) {
return filename.replace(".", "%2E")
}

async getFileContent(
projectId: string,
filename: string,
ref: string
): Promise<string | undefined> {
const encodedFilename = GitlabCIClient.encodeFilename(filename)
let fileObj: any = await this.callApi<RepositoryFileObject>(
`projects/${projectId}/repository/files/${encodedFilename}`,
{ref},
);

if (!fileObj?.content) {
return undefined;
}

const buff = new Buffer(fileObj?.content, 'base64');
return buff.toString('ascii');
}
}
13 changes: 13 additions & 0 deletions src/components/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -34,4 +34,17 @@ export type PipelineObject = {
updated_at: string;
};

export type RepositoryFileObject = {
file_name: string;
file_path: string;
size: number,
encoding: string;
content: string;
content_sha256: string;
ref: string;
blob_id: string;
commit_id: string;
last_commit_id: string;
};

export type MergeRequestState = 'opened' | 'closed' | 'all';
74 changes: 74 additions & 0 deletions src/components/widgets/ReadmeCard/ReadmeCard.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,74 @@
import React from 'react';
import Alert from '@material-ui/lab/Alert';
import { InfoCard, MarkdownContent, Progress } from '@backstage/core-components';
import { makeStyles } from "@material-ui/core";
import { Entity } from "@backstage/catalog-model";
import { useApi } from '@backstage/core-plugin-api';
import { useAsync } from 'react-use';
import { GitlabCIApiRef } from '../../../api';
import { gitlabAppData } from '../../gitlabAppData';

type Props = {
entity?: Entity;
maxHeight?: number;
};

const useStyles = makeStyles((theme) => ({
readMe: {
overflowY: 'auto',
paddingRight: theme.spacing(1),
'&::-webkit-scrollbar-track': {
backgroundColor: '#F5F5F5',
borderRadius: '5px',
},
'&::-webkit-scrollbar': {
width: '5px',
backgroundColor: '#F5F5F5',
borderRadius: '5px',
},
'&::-webkit-scrollbar-thumb': {
border: '1px solid #555555',
backgroundColor: '#555',
borderRadius: '4px',
},
},
}));
export const ReadmeCard = (props: Props) => {
const GitlabCIAPI = useApi(GitlabCIApiRef);
const { project_id } = gitlabAppData();
// This should probably be moved into annotations
const filename = "README.md";
const ref = "master";

const { value, loading, error } = useAsync(async (): Promise<string> => {
const content = await GitlabCIAPI.getFileContent(project_id, filename, ref)
if (!content) {
throw new Error("No content could be found for the specified filename")
}
return content;
});

const classes = useStyles();

if (loading) {
return <Progress/>;
} else if (error) {
return <Alert severity="error">
{error.message}
</Alert>
}

return (
<InfoCard title={filename}>
<div
className={classes.readMe}
style={{
maxHeight: `${props.maxHeight}px`,
}}>
<MarkdownContent
content={value || "_README.md missing or contents are empty_"}
/>
</div>
</InfoCard>
);
};
1 change: 1 addition & 0 deletions src/components/widgets/ReadmeCard/index.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
export { ReadmeCard } from './ReadmeCard';
3 changes: 2 additions & 1 deletion src/components/widgets/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,4 +2,5 @@ export { LanguagesCard } from './LanguagesCard';
export { ContributorsCard } from './ContributorsCard';
export { MergeRequestStats } from './MergeRequestStats';
export { MergeRequestsTable } from './MergeRequestsTable';
export { PipelinesTable } from './PipelinesTable';
export { PipelinesTable } from './PipelinesTable';
export { ReadmeCard } from './ReadmeCard';
12 changes: 11 additions & 1 deletion src/plugin.ts
Original file line number Diff line number Diff line change
Expand Up @@ -86,4 +86,14 @@ export const EntityGitlabPipelinesTable = gitlabPlugin.provide(
import('./components/widgets/index').then((m) => m.PipelinesTable),
},
})
);
);

export const EntityGitlabReadmeCard = gitlabPlugin.provide(
createComponentExtension({
name: 'EntityGitlabReadmeCard',
component: {
lazy: () =>
import('./components/widgets/index').then((m) => m.ReadmeCard),
},
})
);

0 comments on commit db3054f

Please sign in to comment.