This commit is contained in:
2022-09-30 05:39:11 +00:00
parent 41ee9463ae
commit 4687fa49bc
11418 changed files with 1312504 additions and 0 deletions

View File

@ -0,0 +1,35 @@
/// <reference types="node" />
import { Arch } from "builder-util";
import { GithubOptions } from "builder-util-runtime";
import { ClientRequest } from "http";
import { Lazy } from "lazy-val";
import { HttpPublisher, PublishContext, PublishOptions } from "./publisher";
export interface Release {
id: number;
tag_name: string;
draft: boolean;
prerelease: boolean;
published_at: string;
upload_url: string;
}
export declare class GitHubPublisher extends HttpPublisher {
private readonly info;
private readonly version;
private readonly options;
private readonly tag;
readonly _release: Lazy<any>;
private readonly token;
readonly providerName = "GitHub";
private readonly releaseType;
private releaseLogFields;
constructor(context: PublishContext, info: GithubOptions, version: string, options?: PublishOptions);
private getOrCreateRelease;
private overwriteArtifact;
protected doUpload(fileName: string, arch: Arch, dataLength: number, requestProcessor: (request: ClientRequest, reject: (error: Error) => void) => void): Promise<any>;
private doUploadFile;
private createRelease;
getRelease(): Promise<any>;
deleteRelease(): Promise<any>;
private githubRequest;
toString(): string;
}

View File

@ -0,0 +1,341 @@
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.GitHubPublisher = void 0;
function _builderUtil() {
const data = require("builder-util");
_builderUtil = function () {
return data;
};
return data;
}
function _builderUtilRuntime() {
const data = require("builder-util-runtime");
_builderUtilRuntime = function () {
return data;
};
return data;
}
function _nodeHttpExecutor() {
const data = require("builder-util/out/nodeHttpExecutor");
_nodeHttpExecutor = function () {
return data;
};
return data;
}
function _lazyVal() {
const data = require("lazy-val");
_lazyVal = function () {
return data;
};
return data;
}
function _mime() {
const data = _interopRequireDefault(require("mime"));
_mime = function () {
return data;
};
return data;
}
function _url() {
const data = require("url");
_url = function () {
return data;
};
return data;
}
function _publisher() {
const data = require("./publisher");
_publisher = function () {
return data;
};
return data;
}
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
class GitHubPublisher extends _publisher().HttpPublisher {
constructor(context, info, version, options = {}) {
super(context, true);
this.info = info;
this.version = version;
this.options = options;
this._release = new (_lazyVal().Lazy)(() => this.token === "__test__" ? Promise.resolve(null) : this.getOrCreateRelease());
this.providerName = "GitHub";
this.releaseLogFields = null;
let token = info.token;
if ((0, _builderUtil().isEmptyOrSpaces)(token)) {
token = process.env.GH_TOKEN || process.env.GITHUB_TOKEN;
if ((0, _builderUtil().isEmptyOrSpaces)(token)) {
throw new (_builderUtil().InvalidConfigurationError)(`GitHub Personal Access Token is not set, neither programmatically, nor using env "GH_TOKEN"`);
}
token = token.trim();
if (!(0, _builderUtil().isTokenCharValid)(token)) {
throw new (_builderUtil().InvalidConfigurationError)(`GitHub Personal Access Token (${JSON.stringify(token)}) contains invalid characters, please check env "GH_TOKEN"`);
}
}
this.token = token;
if (version.startsWith("v")) {
throw new (_builderUtil().InvalidConfigurationError)(`Version must not start with "v": ${version}`);
}
this.tag = info.vPrefixedTagName === false ? version : `v${version}`;
if ((0, _builderUtil().isEnvTrue)(process.env.EP_DRAFT)) {
this.releaseType = "draft";
_builderUtil().log.info({
reason: "env EP_DRAFT is set to true"
}, "GitHub provider release type is set to draft");
} else if ((0, _builderUtil().isEnvTrue)(process.env.EP_PRE_RELEASE) || (0, _builderUtil().isEnvTrue)(process.env.EP_PRELEASE)
/* https://github.com/electron-userland/electron-builder/issues/2878 */
) {
this.releaseType = "prerelease";
_builderUtil().log.info({
reason: "env EP_PRE_RELEASE is set to true"
}, "GitHub provider release type is set to prerelease");
} else if (info.releaseType != null) {
this.releaseType = info.releaseType;
} else if (options.prerelease) {
this.releaseType = "prerelease";
} else {
// noinspection PointlessBooleanExpressionJS
this.releaseType = options.draft === false ? "release" : "draft";
}
}
async getOrCreateRelease() {
const logFields = {
tag: this.tag,
version: this.version
}; // we don't use "Get a release by tag name" because "tag name" means existing git tag, but we draft release and don't create git tag
const releases = await this.githubRequest(`/repos/${this.info.owner}/${this.info.repo}/releases`, this.token);
for (const release of releases) {
if (!(release.tag_name === this.tag || release.tag_name === this.version)) {
continue;
}
if (release.draft) {
return release;
} // https://github.com/electron-userland/electron-builder/issues/1197
// https://github.com/electron-userland/electron-builder/issues/2072
if (this.releaseType === "draft") {
this.releaseLogFields = {
reason: "existing type not compatible with publishing type",
...logFields,
existingType: release.prerelease ? "pre-release" : "release",
publishingType: this.releaseType
};
_builderUtil().log.warn(this.releaseLogFields, "GitHub release not created");
return null;
} // https://github.com/electron-userland/electron-builder/issues/1133
// https://github.com/electron-userland/electron-builder/issues/2074
// if release created < 2 hours — allow to upload
const publishedAt = release.published_at == null ? null : Date.parse(release.published_at);
if (!(0, _builderUtil().isEnvTrue)(process.env.EP_GH_IGNORE_TIME) && publishedAt != null && Date.now() - publishedAt > 2 * 3600 * 1000) {
// https://github.com/electron-userland/electron-builder/issues/1183#issuecomment-275867187
this.releaseLogFields = {
reason: "existing release published more than 2 hours ago",
...logFields,
date: new Date(publishedAt).toString()
};
_builderUtil().log.warn(this.releaseLogFields, "GitHub release not created");
return null;
}
return release;
} // https://github.com/electron-userland/electron-builder/issues/1835
if (this.options.publish === "always" || (0, _publisher().getCiTag)() != null) {
_builderUtil().log.info({
reason: "release doesn't exist",
...logFields
}, `creating GitHub release`);
return this.createRelease();
}
this.releaseLogFields = {
reason: "release doesn't exist and not created because \"publish\" is not \"always\" and build is not on tag",
...logFields
};
return null;
}
async overwriteArtifact(fileName, release) {
// delete old artifact and re-upload
_builderUtil().log.warn({
file: fileName,
reason: "already exists on GitHub"
}, "overwrite published file");
const assets = await this.githubRequest(`/repos/${this.info.owner}/${this.info.repo}/releases/${release.id}/assets`, this.token, null);
for (const asset of assets) {
if (asset.name === fileName) {
await this.githubRequest(`/repos/${this.info.owner}/${this.info.repo}/releases/assets/${asset.id}`, this.token, null, "DELETE");
return;
}
}
_builderUtil().log.debug({
file: fileName,
reason: "not found on GitHub"
}, "trying to upload again");
}
async doUpload(fileName, arch, dataLength, requestProcessor) {
const release = await this._release.value;
if (release == null) {
_builderUtil().log.warn({
file: fileName,
...this.releaseLogFields
}, "skipped publishing");
return;
}
const parsedUrl = (0, _url().parse)(release.upload_url.substring(0, release.upload_url.indexOf("{")) + "?name=" + fileName);
return await this.doUploadFile(0, parsedUrl, fileName, dataLength, requestProcessor, release);
}
doUploadFile(attemptNumber, parsedUrl, fileName, dataLength, requestProcessor, release) {
return _nodeHttpExecutor().httpExecutor.doApiRequest((0, _builderUtilRuntime().configureRequestOptions)({
hostname: parsedUrl.hostname,
path: parsedUrl.path,
method: "POST",
headers: {
accept: "application/vnd.github.v3+json",
"Content-Type": _mime().default.getType(fileName) || "application/octet-stream",
"Content-Length": dataLength
}
}, this.token), this.context.cancellationToken, requestProcessor).catch(e => {
if (e.statusCode === 422 && e.description != null && e.description.errors != null && e.description.errors[0].code === "already_exists") {
return this.overwriteArtifact(fileName, release).then(() => this.doUploadFile(attemptNumber, parsedUrl, fileName, dataLength, requestProcessor, release));
}
if (attemptNumber > 3) {
return Promise.reject(e);
} else {
return new Promise((resolve, reject) => {
const newAttemptNumber = attemptNumber + 1;
setTimeout(() => {
this.doUploadFile(newAttemptNumber, parsedUrl, fileName, dataLength, requestProcessor, release).then(resolve).catch(reject);
}, newAttemptNumber * 2000);
});
}
});
}
createRelease() {
return this.githubRequest(`/repos/${this.info.owner}/${this.info.repo}/releases`, this.token, {
tag_name: this.tag,
name: this.version,
draft: this.releaseType === "draft",
prerelease: this.releaseType === "prerelease"
});
} // test only
//noinspection JSUnusedGlobalSymbols
async getRelease() {
return this.githubRequest(`/repos/${this.info.owner}/${this.info.repo}/releases/${(await this._release.value).id}`, this.token);
} //noinspection JSUnusedGlobalSymbols
async deleteRelease() {
if (!this._release.hasValue) {
return;
}
const release = await this._release.value;
for (let i = 0; i < 3; i++) {
try {
return await this.githubRequest(`/repos/${this.info.owner}/${this.info.repo}/releases/${release.id}`, this.token, null, "DELETE");
} catch (e) {
if (e instanceof _builderUtilRuntime().HttpError) {
if (e.statusCode === 404) {
_builderUtil().log.warn({
releaseId: release.id,
reason: "doesn't exist"
}, "cannot delete release");
return;
} else if (e.statusCode === 405 || e.statusCode === 502) {
continue;
}
}
throw e;
}
}
_builderUtil().log.warn({
releaseId: release.id
}, "cannot delete release");
}
githubRequest(path, token, data = null, method) {
// host can contains port, but node http doesn't support host as url does
const baseUrl = (0, _url().parse)(`https://${this.info.host || "api.github.com"}`);
return (0, _builderUtilRuntime().parseJson)(_nodeHttpExecutor().httpExecutor.request((0, _builderUtilRuntime().configureRequestOptions)({
hostname: baseUrl.hostname,
port: baseUrl.port,
path: this.info.host != null && this.info.host !== "github.com" ? `/api/v3${path.startsWith("/") ? path : `/${path}`}` : path,
headers: {
accept: "application/vnd.github.v3+json"
}
}, token, method), this.context.cancellationToken, data));
}
toString() {
return `Github (owner: ${this.info.owner}, project: ${this.info.repo}, version: ${this.version})`;
}
} exports.GitHubPublisher = GitHubPublisher;
// __ts-babel@6.0.4
//# sourceMappingURL=gitHubPublisher.js.map

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,12 @@
import { ProgressBar } from "./progress";
export declare class MultiProgress {
private readonly stream;
private cursor;
private totalLines;
private isLogListenerAdded;
private barCount;
createBar(format: string, options: any): ProgressBar;
private allocateLines;
private moveCursor;
terminate(): void;
}

View File

@ -0,0 +1,115 @@
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.MultiProgress = void 0;
function _log() {
const data = require("builder-util/out/log");
_log = function () {
return data;
};
return data;
}
function _progress() {
const data = require("./progress");
_progress = function () {
return data;
};
return data;
}
class MultiProgress {
constructor() {
this.stream = process.stdout;
this.cursor = 0;
this.totalLines = 0;
this.isLogListenerAdded = false;
this.barCount = 0;
}
createBar(format, options) {
options.stream = this.stream; // eslint-disable-next-line @typescript-eslint/no-this-alias
const manager = this;
class MultiProgressBar extends _progress().ProgressBar {
constructor(format, options) {
super(format, options);
this.index = -1;
}
render() {
if (this.index === -1) {
this.index = manager.totalLines;
manager.allocateLines(1);
} else {
manager.moveCursor(this.index);
}
super.render();
if (!manager.isLogListenerAdded) {
manager.isLogListenerAdded = true;
(0, _log().setPrinter)(message => {
let newLineCount = 0;
let newLineIndex = message.indexOf("\n");
while (newLineIndex > -1) {
newLineCount++;
newLineIndex = message.indexOf("\n", ++newLineIndex);
}
manager.allocateLines(newLineCount + 1);
manager.stream.write(message);
});
}
}
terminate() {
manager.barCount--;
if (manager.barCount === 0 && manager.totalLines > 0) {
manager.allocateLines(1);
manager.totalLines = 0;
manager.cursor = 0;
(0, _log().setPrinter)(null);
manager.isLogListenerAdded = false;
}
}
}
const bar = new MultiProgressBar(format, options);
this.barCount++;
return bar;
}
allocateLines(count) {
this.stream.moveCursor(0, this.totalLines - 1); // if cursor pointed to previous line where \n is already printed, another \n is ignored, so, we can simply print it
this.stream.write("\n");
this.totalLines += count;
this.cursor = this.totalLines - 1;
}
moveCursor(index) {
this.stream.moveCursor(0, index - this.cursor);
this.cursor = index;
}
terminate() {
this.moveCursor(this.totalLines);
this.stream.clearLine();
this.stream.cursorTo(0);
}
} exports.MultiProgress = MultiProgress;
// __ts-babel@6.0.4
//# sourceMappingURL=multiProgress.js.map

View File

@ -0,0 +1 @@
{"version":3,"sources":["../src/multiProgress.ts"],"names":[],"mappings":"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","sourcesContent":["import { setPrinter } from \"builder-util/out/log\"\nimport { ProgressBar } from \"./progress\"\n\nexport class MultiProgress {\n private readonly stream = process.stdout as any\n private cursor = 0\n\n private totalLines = 0\n\n private isLogListenerAdded = false\n\n private barCount = 0\n\n createBar(format: string, options: any): ProgressBar {\n options.stream = this.stream\n\n // eslint-disable-next-line @typescript-eslint/no-this-alias\n const manager = this\n class MultiProgressBar extends ProgressBar {\n private index = -1\n\n constructor(format: string, options: any) {\n super(format, options)\n }\n\n render() {\n if (this.index === -1) {\n this.index = manager.totalLines\n manager.allocateLines(1)\n }\n else {\n manager.moveCursor(this.index)\n }\n\n super.render()\n\n if (!manager.isLogListenerAdded) {\n manager.isLogListenerAdded = true\n setPrinter(message => {\n let newLineCount = 0\n let newLineIndex = message.indexOf(\"\\n\")\n while (newLineIndex > -1) {\n newLineCount++\n newLineIndex = message.indexOf(\"\\n\", ++newLineIndex)\n }\n\n manager.allocateLines(newLineCount + 1)\n manager.stream.write(message)\n })\n }\n }\n\n terminate() {\n manager.barCount--\n if (manager.barCount === 0 && manager.totalLines > 0) {\n manager.allocateLines(1)\n manager.totalLines = 0\n manager.cursor = 0\n setPrinter(null)\n manager.isLogListenerAdded = false\n }\n }\n }\n\n const bar = new MultiProgressBar(format, options)\n this.barCount++\n return bar\n }\n\n private allocateLines(count: number) {\n this.stream.moveCursor(0, this.totalLines - 1)\n // if cursor pointed to previous line where \\n is already printed, another \\n is ignored, so, we can simply print it\n this.stream.write(\"\\n\")\n this.totalLines += count\n this.cursor = this.totalLines - 1\n }\n\n private moveCursor(index: number) {\n this.stream.moveCursor(0, index - this.cursor)\n this.cursor = index\n }\n\n terminate() {\n this.moveCursor(this.totalLines)\n this.stream.clearLine()\n this.stream.cursorTo(0)\n }\n}"],"sourceRoot":""}

View File

@ -0,0 +1,70 @@
/*!
* node-progress
* Copyright(c) 2011 TJ Holowaychuk <tj@vision-media.ca>
* MIT Licensed
*/
export declare abstract class ProgressBar {
private readonly format;
private stream;
private current;
total: number;
private width;
private chars;
private tokens;
private lastDraw;
private start;
private complete;
/**
* Initialize a `ProgressBar` with the given `fmt` string and `options` or`total`.
*
* Options:
* - `curr` current completed index
* - `total` total number of ticks to complete
* - `width` the displayed width of the progress bar defaulting to total
* - `stream` the output stream defaulting to stderr
* - `head` head character defaulting to complete character
* - `complete` completion character defaulting to "="
* - `incomplete` incomplete character defaulting to "-"
* - `renderThrottle` minimum time between updates in milliseconds defaulting to 16
* - `callback` optional function to call when the progress bar completes
* - `clear` will clear the progress bar upon termination
*
* Tokens:
* - `:bar` the progress bar itself
* - `:current` current tick number
* - `:total` total ticks
* - `:elapsed` time elapsed in seconds
* - `:percent` completion percentage
* - `:eta` eta in seconds
* - `:rate` rate of ticks per second
*/
constructor(format: string, options?: any);
/**
* "tick" the progress bar with optional `len` and optional `tokens`.
*/
tick(delta: number): void;
set currentAmount(value: number);
render(): void;
/**
* "update" the progress bar to represent an exact percentage.
* The ratio (between 0 and 1) specified will be multiplied by `total` and
* floored, representing the closest available "tick." For example, if a
* progress bar has a length of 3 and `update(0.5)` is called, the progress
* will be set to 1.
*
* A ratio of 0.5 will attempt to set the progress to halfway.
*/
update(ratio: number): void;
/**
* "interrupt" the progress bar and write a message above it.
*/
interrupt(message: string): void;
abstract terminate(): void;
}
export declare class ProgressCallback {
private readonly progressBar;
private start;
private nextUpdate;
constructor(progressBar: ProgressBar);
update(transferred: number, total: number): void;
}

View File

@ -0,0 +1,186 @@
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.ProgressCallback = exports.ProgressBar = void 0;
/*!
* node-progress
* Copyright(c) 2011 TJ Holowaychuk <tj@vision-media.ca>
* MIT Licensed
*/
class ProgressBar {
/**
* Initialize a `ProgressBar` with the given `fmt` string and `options` or`total`.
*
* Options:
* - `curr` current completed index
* - `total` total number of ticks to complete
* - `width` the displayed width of the progress bar defaulting to total
* - `stream` the output stream defaulting to stderr
* - `head` head character defaulting to complete character
* - `complete` completion character defaulting to "="
* - `incomplete` incomplete character defaulting to "-"
* - `renderThrottle` minimum time between updates in milliseconds defaulting to 16
* - `callback` optional function to call when the progress bar completes
* - `clear` will clear the progress bar upon termination
*
* Tokens:
* - `:bar` the progress bar itself
* - `:current` current tick number
* - `:total` total ticks
* - `:elapsed` time elapsed in seconds
* - `:percent` completion percentage
* - `:eta` eta in seconds
* - `:rate` rate of ticks per second
*/
constructor(format, options = {}) {
this.format = format;
this.current = 0;
this.total = 0;
this.tokens = null;
this.lastDraw = "";
this.start = 0;
this.complete = false;
this.stream = options.stream || process.stderr;
this.total = options.total;
this.width = options.width || this.total;
this.chars = {
complete: options.complete || "=",
incomplete: options.incomplete || "-",
head: options.head || options.complete || "="
};
}
/**
* "tick" the progress bar with optional `len` and optional `tokens`.
*/
tick(delta) {
this.currentAmount = this.current + delta;
}
set currentAmount(value) {
this.current = value;
if (this.complete) {
return;
}
this.render();
if (this.current >= this.total) {
this.complete = true;
this.terminate();
}
}
render() {
// start time for eta
if (this.start === 0) {
this.start = Date.now();
}
const ratio = Math.min(Math.max(this.current / this.total, 0), 1);
const percent = ratio * 100;
const elapsed = Date.now() - this.start;
const eta = percent === 100 ? 0 : elapsed * (this.total / this.current - 1);
const rate = this.current / (elapsed / 1000);
/* populate the bar template with percentages and timestamps */
let str = this.format.replace(":current", this.current.toString()).replace(":total", this.total.toString()).replace(":elapsed", isNaN(elapsed) ? "0.0" : (elapsed / 1000).toFixed(1)).replace(":eta", isNaN(eta) || !isFinite(eta) ? "0.0" : (eta / 1000).toFixed(1)).replace(":percent", percent.toFixed(0) + "%").replace(":rate", Math.round(rate).toString()); // compute the available space (non-zero) for the bar
let availableSpace = Math.max(0, this.stream.columns - str.replace(":bar", "").length);
if (availableSpace && process.platform === "win32") {
availableSpace -= 1;
}
const width = Math.min(this.width, availableSpace);
const completeLength = Math.round(width * ratio);
let complete = Array(Math.max(0, completeLength + 1)).join(this.chars.complete);
const incomplete = Array(Math.max(0, width - completeLength + 1)).join(this.chars.incomplete);
/* add head to the complete string */
if (completeLength > 0) {
complete = complete.slice(0, -1) + this.chars.head;
}
/* fill in the actual progress bar */
str = str.replace(":bar", complete + incomplete);
/* replace the extra tokens */
if (this.tokens != null) {
for (const key of Object.keys(this.tokens)) {
str = str.replace(`:${key}`, this.tokens[key]);
}
}
if (this.lastDraw !== str) {
this.stream.cursorTo(0);
this.stream.write(str);
this.stream.clearLine(1);
this.lastDraw = str;
}
}
/**
* "update" the progress bar to represent an exact percentage.
* The ratio (between 0 and 1) specified will be multiplied by `total` and
* floored, representing the closest available "tick." For example, if a
* progress bar has a length of 3 and `update(0.5)` is called, the progress
* will be set to 1.
*
* A ratio of 0.5 will attempt to set the progress to halfway.
*/
update(ratio) {
const goal = Math.floor(ratio * this.total);
const delta = goal - this.current;
this.tick(delta);
}
/**
* "interrupt" the progress bar and write a message above it.
*/
interrupt(message) {
// clear the current line
const stream = this.stream;
stream.clearLine(); // move the cursor to the start of the line
stream.cursorTo(0); // write the message text
stream.write(message); // terminate the line after writing the message
stream.write("\n"); // re-display the progress bar with its lastDraw
stream.write(this.lastDraw);
}
}
exports.ProgressBar = ProgressBar;
class ProgressCallback {
constructor(progressBar) {
this.progressBar = progressBar;
this.start = Date.now();
this.nextUpdate = this.start + 1000;
}
update(transferred, total) {
const now = Date.now();
if (now >= this.nextUpdate || transferred >= total) {
this.nextUpdate = now + 1000;
this.progressBar.total = total;
this.progressBar.currentAmount = transferred;
}
}
} exports.ProgressCallback = ProgressCallback;
// __ts-babel@6.0.4
//# sourceMappingURL=progress.js.map

File diff suppressed because one or more lines are too long

View File

@ -0,0 +1,39 @@
/// <reference types="node" />
import { Arch } from "builder-util";
import { CancellationToken } from "builder-util-runtime";
import { Stats } from "fs-extra";
import { ClientRequest } from "http";
import { MultiProgress } from "./multiProgress";
import { ProgressBar } from "./progress";
export declare type PublishPolicy = "onTag" | "onTagOrDraft" | "always" | "never";
export { ProgressCallback } from "./progress";
export interface PublishOptions {
publish?: PublishPolicy | null;
}
export interface PublishContext {
readonly cancellationToken: CancellationToken;
readonly progress: MultiProgress | null;
}
export interface UploadTask {
file: string;
fileContent?: Buffer | null;
arch: Arch | null;
safeArtifactName?: string | null;
}
export declare abstract class Publisher {
protected readonly context: PublishContext;
protected constructor(context: PublishContext);
abstract get providerName(): string;
abstract upload(task: UploadTask): Promise<any>;
protected createProgressBar(fileName: string, size: number): ProgressBar | null;
protected createReadStreamAndProgressBar(file: string, fileStat: Stats, progressBar: ProgressBar | null, reject: (error: Error) => void): NodeJS.ReadableStream;
abstract toString(): string;
}
export declare abstract class HttpPublisher extends Publisher {
protected readonly context: PublishContext;
private readonly useSafeArtifactName;
protected constructor(context: PublishContext, useSafeArtifactName?: boolean);
upload(task: UploadTask): Promise<any>;
protected abstract doUpload(fileName: string, arch: Arch, dataLength: number, requestProcessor: (request: ClientRequest, reject: (error: Error) => void) => void, file?: string): Promise<any>;
}
export declare function getCiTag(): string | null;

View File

@ -0,0 +1,158 @@
"use strict";
Object.defineProperty(exports, "__esModule", {
value: true
});
exports.getCiTag = getCiTag;
Object.defineProperty(exports, "ProgressCallback", {
enumerable: true,
get: function () {
return _progress().ProgressCallback;
}
});
exports.HttpPublisher = exports.Publisher = void 0;
function _builderUtil() {
const data = require("builder-util");
_builderUtil = function () {
return data;
};
return data;
}
function _builderUtilRuntime() {
const data = require("builder-util-runtime");
_builderUtilRuntime = function () {
return data;
};
return data;
}
function _log() {
const data = require("builder-util/out/log");
_log = function () {
return data;
};
return data;
}
function _chalk() {
const data = _interopRequireDefault(require("chalk"));
_chalk = function () {
return data;
};
return data;
}
function _fsExtra() {
const data = require("fs-extra");
_fsExtra = function () {
return data;
};
return data;
}
var _path = require("path");
function _progress() {
const data = require("./progress");
_progress = function () {
return data;
};
return data;
}
function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
const progressBarOptions = {
incomplete: " ",
width: 20
};
class Publisher {
constructor(context) {
this.context = context;
}
createProgressBar(fileName, size) {
_builderUtil().log.info({
file: fileName,
provider: this.providerName
}, "uploading");
if (this.context.progress == null || size < 512 * 1024) {
return null;
}
return this.context.progress.createBar(`${" ".repeat(_log().PADDING + 2)}[:bar] :percent :etas | ${_chalk().default.green(fileName)} to ${this.providerName}`, {
total: size,
...progressBarOptions
});
}
createReadStreamAndProgressBar(file, fileStat, progressBar, reject) {
const fileInputStream = (0, _fsExtra().createReadStream)(file);
fileInputStream.on("error", reject);
if (progressBar == null) {
return fileInputStream;
} else {
const progressStream = new (_builderUtilRuntime().ProgressCallbackTransform)(fileStat.size, this.context.cancellationToken, it => progressBar.tick(it.delta));
progressStream.on("error", reject);
return fileInputStream.pipe(progressStream);
}
}
}
exports.Publisher = Publisher;
class HttpPublisher extends Publisher {
constructor(context, useSafeArtifactName = false) {
super(context);
this.context = context;
this.useSafeArtifactName = useSafeArtifactName;
}
async upload(task) {
const fileName = (this.useSafeArtifactName ? task.safeArtifactName : null) || (0, _path.basename)(task.file);
if (task.fileContent != null) {
await this.doUpload(fileName, task.arch || _builderUtil().Arch.x64, task.fileContent.length, it => it.end(task.fileContent));
return;
}
const fileStat = await (0, _fsExtra().stat)(task.file);
const progressBar = this.createProgressBar(fileName, fileStat.size);
await this.doUpload(fileName, task.arch || _builderUtil().Arch.x64, fileStat.size, (request, reject) => {
if (progressBar != null) {
// reset (because can be called several times (several attempts)
progressBar.update(0);
}
return this.createReadStreamAndProgressBar(task.file, fileStat, progressBar, reject).pipe(request);
}, task.file);
}
}
exports.HttpPublisher = HttpPublisher;
function getCiTag() {
const tag = process.env.TRAVIS_TAG || process.env.APPVEYOR_REPO_TAG_NAME || process.env.CIRCLE_TAG || process.env.BITRISE_GIT_TAG || process.env.CI_BUILD_TAG;
return tag != null && tag.length > 0 ? tag : null;
}
// __ts-babel@6.0.4
//# sourceMappingURL=publisher.js.map

File diff suppressed because one or more lines are too long