Files
shields/services/github/github-actions-workflow-status.service.js
chris48s 45bb786147 log 429s to sentry (attempt 2); affects [dynamic endpoint uptimerobot weblate opencollective discord github] (#9546)
* log to sentry if upstream service responds with 429

* allow services to decide which error(s) to log, default to 429

* don't log 429s from endpoint or dynamic badges

* supress 429s from uptime robot badges

* supress 429s from weblate if not calling default server

* cache opencollective badges for longer

* cache discord badges for longer

* cache github workflow badges for longer
2023-12-04 13:37:58 +00:00

105 lines
2.6 KiB
JavaScript

import Joi from 'joi'
import { isBuildStatus, renderBuildStatusBadge } from '../build-status.js'
import { BaseSvgScrapingService } from '../index.js'
import { documentation } from './github-helpers.js'
const schema = Joi.object({
message: Joi.alternatives()
.try(isBuildStatus, Joi.equal('no status'))
.required(),
}).required()
const queryParamSchema = Joi.object({
event: Joi.string(),
branch: Joi.alternatives().try(Joi.string(), Joi.number().cast('string')),
}).required()
const keywords = ['action', 'actions']
export default class GithubActionsWorkflowStatus extends BaseSvgScrapingService {
static category = 'build'
static route = {
base: 'github/actions/workflow/status',
pattern: ':user/:repo/:workflow+',
queryParamSchema,
}
static examples = [
{
title: 'GitHub Workflow Status',
namedParams: {
user: 'actions',
repo: 'toolkit',
workflow: 'unit-tests.yml',
},
staticPreview: renderBuildStatusBadge({
status: 'passing',
}),
documentation,
keywords,
},
{
title: 'GitHub Workflow Status (with branch)',
namedParams: {
user: 'actions',
repo: 'toolkit',
workflow: 'unit-tests.yml',
},
queryParams: {
branch: 'main',
},
staticPreview: renderBuildStatusBadge({
status: 'passing',
}),
documentation,
keywords,
},
{
title: 'GitHub Workflow Status (with event)',
namedParams: {
user: 'actions',
repo: 'toolkit',
workflow: 'unit-tests.yml',
},
queryParams: {
event: 'push',
},
staticPreview: renderBuildStatusBadge({
status: 'passing',
}),
documentation,
keywords,
},
]
static _cacheLength = 60
static defaultBadgeData = {
label: 'build',
}
async fetch({ user, repo, workflow, branch, event }) {
const workflowPath = workflow
.split('/')
.map(el => encodeURIComponent(el))
.join('/')
const { message: status } = await this._requestSvg({
schema,
url: `https://github.com/${user}/${repo}/actions/workflows/${workflowPath}/badge.svg`,
options: { searchParams: { branch, event } },
valueMatcher: />([^<>]+)<\/tspan><\/text><\/g><path/,
httpErrors: {
404: 'repo or workflow not found',
},
})
return { status }
}
async handle({ user, repo, workflow }, { branch, event }) {
const { status } = await this.fetch({ user, repo, workflow, branch, event })
return renderBuildStatusBadge({ status })
}
}