"use strict";
var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) {
    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) : new P(function (resolve) { resolve(result.value); }).then(fulfilled, rejected); }
        step((generator = generator.apply(thisArg, _arguments || [])).next());
    });
};
var __generator = (this && this.__generator) || function (thisArg, body) {
    var _ = { label: 0, sent: function() { if (t[0] & 1) throw t[1]; return t[1]; }, trys: [], ops: [] }, f, y, t, g;
    return g = { next: verb(0), "throw": verb(1), "return": verb(2) }, typeof Symbol === "function" && (g[Symbol.iterator] = function() { return this; }), g;
    function verb(n) { return function (v) { return step([n, v]); }; }
    function step(op) {
        if (f) throw new TypeError("Generator is already executing.");
        while (_) try {
            if (f = 1, y && (t = y[op[0] & 2 ? "return" : op[0] ? "throw" : "next"]) && !(t = t.call(y, op[1])).done) return t;
            if (y = 0, t) op = [0, t.value];
            switch (op[0]) {
                case 0: case 1: t = op; break;
                case 4: _.label++; return { value: op[1], done: false };
                case 5: _.label++; y = op[1]; op = [0]; continue;
                case 7: op = _.ops.pop(); _.trys.pop(); continue;
                default:
                    if (!(t = _.trys, t = t.length > 0 && t[t.length - 1]) && (op[0] === 6 || op[0] === 2)) { _ = 0; continue; }
                    if (op[0] === 3 && (!t || (op[1] > t[0] && op[1] < t[3]))) { _.label = op[1]; break; }
                    if (op[0] === 6 && _.label < t[1]) { _.label = t[1]; t = op; break; }
                    if (t && _.label < t[2]) { _.label = t[2]; _.ops.push(op); break; }
                    if (t[2]) _.ops.pop();
                    _.trys.pop(); continue;
            }
            op = body.call(thisArg, _);
        } catch (e) { op = [6, e]; y = 0; } finally { f = t = 0; }
        if (op[0] & 5) throw op[1]; return { value: op[0] ? op[1] : void 0, done: true };
    }
};
Object.defineProperty(exports, "__esModule", { value: true });
var yaml = require("js-yaml");
var path = require("path");
/**
 * Helpers for extracting information from the webhook event, which can be
 * passed to GitHub API calls.
 *
 * @property {github} github - An authenticated GitHub API client
 * @property {payload} payload - The webhook event payload
 * @property {logger} log - A logger
 */
var Context = /** @class */ (function () {
    function Context(event, github, log) {
        Object.assign(this, event);
        this.id = event.id;
        this.github = github;
        this.log = log;
    }
    /**
     * Return the `owner` and `repo` params for making API requests against a
     * repository.
     *
     * @param {object} [object] - Params to be merged with the repo params.
     *
     * @example
     *
     * const params = context.repo({path: '.github/config.yml'})
     * // Returns: {owner: 'username', repo: 'reponame', path: '.github/config.yml'}
     *
     */
    Context.prototype.repo = function (object) {
        var repo = this.payload.repository;
        return Object.assign({
            owner: repo.owner.login || repo.owner.name,
            repo: repo.name
        }, object);
    };
    /**
     * Return the `owner`, `repo`, and `number` params for making API requests
     * against an issue or pull request. The object passed in will be merged with
     * the repo params.
     *
     * @example
     *
     * const params = context.issue({body: 'Hello World!'})
     * // Returns: {owner: 'username', repo: 'reponame', number: 123, body: 'Hello World!'}
     *
     * @param {object} [object] - Params to be merged with the issue params.
     */
    Context.prototype.issue = function (object) {
        var payload = this.payload;
        return Object.assign({
            number: (payload.issue || payload.pull_request || payload).number
        }, this.repo(object));
    };
    Object.defineProperty(Context.prototype, "isBot", {
        /**
         * Returns a boolean if the actor on the event was a bot.
         * @type {boolean}
         */
        get: function () {
            return this.payload.sender.type === 'Bot';
        },
        enumerable: true,
        configurable: true
    });
    /**
     * Reads the app configuration from the given YAML file in the `.github`
     * directory of the repository.
     *
     * @example <caption>Contents of <code>.github/config.yml</code>.</caption>
     *
     * close: true
     * comment: Check the specs on the rotary girder.
     *
     * @example <caption>App that reads from <code>.github/config.yml</code>.</caption>
     *
     * // Load config from .github/config.yml in the repository
     * const config = await context.config('config.yml')
     *
     * if (config.close) {
     *   context.github.issues.comment(context.issue({body: config.comment}))
     *   context.github.issues.edit(context.issue({state: 'closed'}))
     * }
     *
     * @example <caption>Using a <code>defaultConfig</code> object.</caption>
     *
     * // Load config from .github/config.yml in the repository and combine with default config
     * const config = await context.config('config.yml', {comment: 'Make sure to check all the specs.'})
     *
     * if (config.close) {
     *   context.github.issues.comment(context.issue({body: config.comment}));
     *   context.github.issues.edit(context.issue({state: 'closed'}))
     * }
     *
     * @param {string} fileName - Name of the YAML file in the `.github` directory
     * @param {object} [defaultConfig] - An object of default config options
     * @return {Promise<Object>} - Configuration object read from the file
     */
    Context.prototype.config = function (fileName, defaultConfig) {
        return __awaiter(this, void 0, void 0, function () {
            var params, res, config, err_1;
            return __generator(this, function (_a) {
                switch (_a.label) {
                    case 0:
                        params = this.repo({ path: path.posix.join('.github', fileName) });
                        _a.label = 1;
                    case 1:
                        _a.trys.push([1, 3, , 4]);
                        return [4 /*yield*/, this.github.repos.getContent(params)];
                    case 2:
                        res = _a.sent();
                        config = yaml.safeLoad(Buffer.from(res.data.content, 'base64').toString()) || {};
                        return [2 /*return*/, Object.assign({}, defaultConfig, config)];
                    case 3:
                        err_1 = _a.sent();
                        if (err_1.code === 404) {
                            if (defaultConfig) {
                                return [2 /*return*/, defaultConfig];
                            }
                            return [2 /*return*/, null];
                        }
                        else {
                            throw err_1;
                        }
                        return [3 /*break*/, 4];
                    case 4: return [2 /*return*/];
                }
            });
        });
    };
    return Context;
}());
exports.Context = Context;
//# sourceMappingURL=context.js.map