add support for groups via team slug splitting and some tests

Signed-off-by: Jack Grigg <jrgrigg@gmail.com>
This commit is contained in:
Jack Grigg
2023-02-02 14:53:40 +11:00
parent 4a123fe82a
commit 057f05c1eb
5 changed files with 54 additions and 9 deletions
@@ -21,3 +21,14 @@
* @public
*/
export const ANNOTATION_GITHUB_USER_LOGIN = 'github.com/user-login';
/**
* The value of this annotation is the so-called slug that identifies a team on
[GitHub](https://github.com) (either the public one, or a private GitHub
Enterprise installation) that is related to this entity. It is on the format
`<organization>/<team>`, and is the same as can be seen in the URL location bar
of the browser when viewing that team.
*
* @public
*/
export const ANNOTATION_GITHUB_TEAM_SLUG = 'github.com/team-slug';
@@ -16,7 +16,10 @@
import { GroupEntity, UserEntity } from '@backstage/catalog-model';
import { graphql } from '@octokit/graphql';
import { ANNOTATION_GITHUB_USER_LOGIN } from './annotation';
import {
ANNOTATION_GITHUB_TEAM_SLUG,
ANNOTATION_GITHUB_USER_LOGIN,
} from './annotation';
import { GithubTeam, GithubUser } from './github';
/**
@@ -88,7 +91,7 @@ export const defaultUserTransformer: UserTransformer = async (
export const defaultOrganizationTeamTransformer: TeamTransformer =
async team => {
const annotations: { [annotationName: string]: string } = {
'github.com/team-slug': team.combinedSlug,
[ANNOTATION_GITHUB_TEAM_SLUG]: team.combinedSlug,
};
if (team.editTeamUrl) {
@@ -88,3 +88,14 @@ export function satisfiesForkFilter(
// if forks are allowed, allow all repos through
return true;
}
// Given the github organisation team slug, returns a tuple containing [organisation, team]
export function splitTeamSlug(slug: string): [string, string] {
const parts = slug.split('/');
if (parts.length !== 2) {
throw new Error(
`Github team slug '${slug}' was not in the expected format <organisation>/<team>`,
);
}
return [parts[0], parts[1]];
}
@@ -181,7 +181,10 @@ describe('GithubOrgEntityProvider', () => {
apiVersion: 'backstage.io/v1alpha1',
kind: 'User',
metadata: {
name: 'githubuser',
name: 'user-name',
annotations: {
'github.com/user-login': 'githubuser',
},
},
spec: {
memberOf: [],
@@ -192,12 +195,13 @@ describe('GithubOrgEntityProvider', () => {
apiVersion: 'backstage.io/v1alpha1',
kind: 'User',
metadata: {
name: 'githubuser',
name: 'user-name',
annotations: {
'backstage.io/managed-by-location':
'url:https://github.com/githubuser',
'backstage.io/managed-by-origin-location':
'url:https://github.com/githubuser',
'github.com/user-login': 'githubuser',
},
},
spec: {
@@ -211,7 +215,10 @@ describe('GithubOrgEntityProvider', () => {
apiVersion: 'backstage.io/v1alpha1',
kind: 'Group',
metadata: {
name: 'mygroup',
name: 'group-name',
annotations: {
'github.com/team-slug': 'backstage/mygroup',
},
},
spec: {
type: 'team',
@@ -223,12 +230,13 @@ describe('GithubOrgEntityProvider', () => {
apiVersion: 'backstage.io/v1alpha1',
kind: 'Group',
metadata: {
name: 'mygroup',
name: 'group-name',
annotations: {
'backstage.io/managed-by-location':
'url:https://github.com/orgs/backstage/teams/mygroup',
'backstage.io/managed-by-origin-location':
'url:https://github.com/orgs/backstage/teams/mygroup',
'github.com/team-slug': 'backstage/mygroup',
},
},
spec: {
@@ -65,7 +65,11 @@ import {
getOrganizationTeam,
getOrganizationTeamsFromUsers,
} from '../lib/github';
import { ANNOTATION_GITHUB_USER_LOGIN } from '../lib/annotation';
import {
ANNOTATION_GITHUB_TEAM_SLUG,
ANNOTATION_GITHUB_USER_LOGIN,
} from '../lib/annotation';
import { splitTeamSlug } from '../lib/util';
/**
* Options for {@link GithubOrgEntityProvider}.
@@ -604,11 +608,19 @@ export function withLocations(
entity: Entity,
): Entity {
const login =
entity.metadata.annotations[ANNOTATION_GITHUB_USER_LOGIN] ||
entity.metadata.annotations?.[ANNOTATION_GITHUB_USER_LOGIN] ||
entity.metadata.name;
let team = entity.metadata.name;
const slug = entity.metadata.annotations?.[ANNOTATION_GITHUB_TEAM_SLUG];
if (slug) {
const [_, slugTeam] = splitTeamSlug(slug);
team = slugTeam;
}
const location =
entity.kind === 'Group'
? `url:${baseUrl}/orgs/${org}/teams/${login}`
? `url:${baseUrl}/orgs/${org}/teams/${team}`
: `url:${baseUrl}/${login}`;
return merge(
{