semantic-release-pypi
Version:
semantic-release plugin to publish a python package to PyPI
84 lines • 3.6 kB
JavaScript
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); }
return new (P || (P = Promise))(function (resolve, reject) {
function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } }
function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } }
function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); }
step((generator = generator.apply(thisArg, _arguments || [])).next());
});
};
import got from 'got';
function getMintTokenUrl(repoUrl) {
const url = new URL(repoUrl);
const host = url.hostname.replace(/^upload\./, '');
if (url.port === '443' || url.port === '80' || url.port === '') {
return `${url.protocol}//${host}/_/oidc/mint-token`;
}
return `${url.protocol}//${host}:${url.port}/_/oidc/mint-token`;
}
function getAudience(repoUrl) {
const url = new URL(repoUrl);
const host = url.hostname.replace(/^upload\./, '');
if (host === 'test.pypi.org')
return 'testpypi';
return 'pypi';
}
function mintApiToken(oidcToken, mintUrl) {
return __awaiter(this, void 0, void 0, function* () {
const response = yield got.post(mintUrl, {
json: { token: oidcToken },
responseType: 'json',
});
const body = response.body;
if (!body.token) {
throw new Error(`Trusted publishing: PyPI did not return an API token`);
}
return body.token;
});
}
function getGithubOidcToken(audience) {
return __awaiter(this, void 0, void 0, function* () {
const requestToken = process.env['ACTIONS_ID_TOKEN_REQUEST_TOKEN'];
const requestUrl = process.env['ACTIONS_ID_TOKEN_REQUEST_URL'];
const url = `${requestUrl}&audience=${audience}`;
const response = yield got.get(url, {
headers: { Authorization: `bearer ${requestToken}` },
responseType: 'json',
});
const body = response.body;
return body.value;
});
}
export function getTrustedPublisher() {
if (!!process.env['ACTIONS_ID_TOKEN_REQUEST_TOKEN'] &&
!!process.env['ACTIONS_ID_TOKEN_REQUEST_URL']) {
return 'github';
}
if (!!process.env['PYPI_ID_TOKEN']) {
return 'gitlab';
}
return null;
}
export function isTrustedPublisher() {
return getTrustedPublisher() !== null;
}
export function getAPIToken(context, repoUrl = 'https://upload.pypi.org/legacy/') {
return __awaiter(this, void 0, void 0, function* () {
const { logger } = context;
const mintUrl = getMintTokenUrl(repoUrl);
const audience = getAudience(repoUrl);
const trustedPublisher = getTrustedPublisher();
if (trustedPublisher === 'github') {
logger.log('Using GitHub Actions Trusted Publishing');
const oidcToken = yield getGithubOidcToken(audience);
return mintApiToken(oidcToken, mintUrl);
}
if (trustedPublisher === 'gitlab') {
logger.log('Using GitLab CI Trusted Publishing');
const oidcToken = process.env['PYPI_ID_TOKEN'];
return mintApiToken(oidcToken, mintUrl);
}
throw new Error('No trusted publisher detected. Set PYPI_TOKEN, configure repoToken, or use a supported Trusted Publisher (GitHub Actions or GitLab CI).');
});
}
//# sourceMappingURL=trusted-publishing.js.map