/*
         *     This tool is designed to execute most of the physical releasing:
         *         1. Merge the RC PR into develop.
         *         2. Draft the release using the changelog notes.
         *
         *     Fast-forwarding master up-to-date with develop and publishing the release
         *     are left up to the release sheriff.
         */
        public int Run()
        {
            try
            {
                var gitHubClient = new GitHubClient(options);

                var(repoName, pullRequestId) = ExtractPullRequestInfo(options.PullRequestUrl);

                var spatialOsRemote = string.Format(Common.RemoteUrlTemplate, Common.SpatialOsOrg, repoName);
                var gitHubRepo      = gitHubClient.GetRepositoryFromRemote(spatialOsRemote);

                // Merge into develop
                var mergeResult = gitHubClient.MergePullRequest(gitHubRepo, pullRequestId);

                if (!mergeResult.Merged)
                {
                    throw new InvalidOperationException(
                              $"Was unable to merge pull request at: {options.PullRequestUrl}. Received error: {mergeResult.Message}");
                }

                // Delete remote on the forked repository.
                var forkedRepoRemote = string.Format(Common.RemoteUrlTemplate, Common.GithubBotUser, repoName);
                var branchName       = string.Format(Common.ReleaseBranchNameTemplate, options.Version);
                // gitHubClient.DeleteBranch(gitHubClient.GetRepositoryFromRemote(forkedRepoRemote), branchName);

                var remoteUrl = string.Format(Common.RemoteUrlTemplate, Common.SpatialOsOrg, repoName);

                using (var gitClient = GitClient.FromRemote(remoteUrl))
                {
                    // Create release
                    gitClient.Fetch();
                    gitClient.CheckoutRemoteBranch(Common.DevelopBranch);
                    var release = CreateRelease(gitHubClient, gitHubRepo, gitClient, repoName);

                    Logger.Info("Release Successful!");
                    Logger.Info("Release hash: {0}", gitClient.GetHeadCommit().Sha);
                    Logger.Info("Draft release: {0}", release.HtmlUrl);

                    if (repoName == "gdk-for-unity" && BuildkiteMetadataSink.CanWrite(options))
                    {
                        using (var sink = new BuildkiteMetadataSink(options))
                        {
                            sink.WriteMetadata("gdk-for-unity-hash", gitClient.GetHeadCommit().Sha);
                        }
                    }
                }
            }
            catch (Exception e)
            {
                Logger.Error(e, "ERROR: Unable to release candidate branch. Error: {0}", e);
                return(1);
            }

            return(0);
        }
Esempio n. 2
0
        /*
         *     This tool is designed to be used with a robot Github account which has its own fork of the GDK
         *     repositories. This means that when we prep a release:
         *         1. Checkout our fork of the repo.
         *         2. Add the spatialos org remote to our local copy and fetch this remote.
         *         3. Checkout the spatialos/develop branch (the non-forked develop branch).
         *         4. Make the changes for prepping the release.
         *         5. Push this to an RC branch on the forked repository.
         *         6. Open a PR from the fork into the source repository.
         */
        public int Run()
        {
            var remoteUrl = string.Format(Common.RemoteUrlTemplate, Common.GithubBotUser, options.GitRepoName);

            try
            {
                var gitHubClient = new GitHubClient(options);

                using (var gitClient = GitClient.FromRemote(remoteUrl))
                {
                    // This does step 2 from above.
                    var spatialOsRemote =
                        string.Format(Common.RemoteUrlTemplate, Common.SpatialOsOrg, options.GitRepoName);
                    gitClient.AddRemote(Common.SpatialOsOrg, spatialOsRemote);
                    gitClient.Fetch(Common.SpatialOsOrg);

                    // This does step 3 from above.
                    gitClient.CheckoutRemoteBranch(Common.DevelopBranch, Common.SpatialOsOrg);

                    // This does step 4 from above.
                    using (new WorkingDirectoryScope(gitClient.RepositoryPath))
                    {
                        UpdateManifestJson(gitClient);
                        UpdateAllPackageJsons(gitClient);

                        if (options.ShouldUpdateGdkVersion)
                        {
                            UpdateGdkVersion(gitClient, options.PinnedGdkVersion);
                        }

                        if (!File.Exists(ChangeLogFilename))
                        {
                            throw new InvalidOperationException("Could not update the change log as the file," +
                                                                $" {ChangeLogFilename}, does not exist");
                        }

                        Logger.Info("Updating {0}...", ChangeLogFilename);

                        var changelog = File.ReadAllLines(ChangeLogFilename).ToList();
                        UpdateChangeLog(changelog, options);
                        File.WriteAllLines(ChangeLogFilename, changelog);
                        gitClient.StageFile(ChangeLogFilename);
                    }

                    // This does step 5 from above.
                    var branchName = string.Format(Common.ReleaseBranchNameTemplate, options.Version);
                    gitClient.Commit(string.Format(CommitMessageTemplate, options.Version));
                    gitClient.ForcePush(branchName);

                    // This does step 6 from above.
                    var gitHubRepo = gitHubClient.GetRepositoryFromRemote(spatialOsRemote);

                    var branchFrom = $"{Common.GithubBotUser}:{branchName}";
                    var branchTo   = Common.DevelopBranch;

                    // Only open a PR if one does not exist yet.
                    if (!gitHubClient.TryGetPullRequest(gitHubRepo, branchFrom, branchTo, out var pullRequest))
                    {
                        pullRequest = gitHubClient.CreatePullRequest(gitHubRepo,
                                                                     branchFrom,
                                                                     branchTo,
                                                                     string.Format(PullRequestTemplate, options.Version),
                                                                     GetPullRequestBody(options.GitRepoName));
                    }

                    if (BuildkiteMetadataSink.CanWrite(options))
                    {
                        using (var sink = new BuildkiteMetadataSink(options))
                        {
                            sink.WriteMetadata($"{options.GitRepoName}-release-branch",
                                               $"pull/{pullRequest.Number}/head:{branchName}");
                            sink.WriteMetadata($"{options.GitRepoName}-pr-url", pullRequest.HtmlUrl);
                        }
                    }

                    Logger.Info("Pull request available: {0}", pullRequest.HtmlUrl);
                    Logger.Info("Successfully created release!");
                    Logger.Info("Release hash: {0}", gitClient.GetHeadCommit().Sha);
                }
            }
            catch (Exception e)
            {
                Logger.Error(e, "ERROR: Unable to prep release candidate branch. Error: {0}", e);
                return(1);
            }

            return(0);
        }