diff --git a/README.md b/README.md index 4b483706..156e23e1 100644 --- a/README.md +++ b/README.md @@ -118,6 +118,27 @@ sentry_set_commits( ) ``` +#### Create deploy + +Creates a new release deployment for a project on Sentry. + +```ruby +sentry_create_deploy( + api_key: '...', # Do not use if using auth_token + auth_token: '...', # Do not use if using api_key + org_slug: '...', + project_slug: '...', + version: '...', + app_identifier: '...', # pass in the bundle_identifer of your app + env: 'staging', # The environment for this deploy. Required. + name: '...', # Optional human readable name + deploy_url: '...', # Optional URL that points to the deployment + started: 1622630647, # Optional unix timestamp when the deployment started + finished: 1622630700, # Optional unix timestamp when the deployment finished + time: 180 # Optional deployment duration in seconds. This can be specified alternatively to `started` and `finished` +) +``` + ## Issues and Feedback For any other issues and feedback about this plugin, please submit it to this repository. diff --git a/lib/fastlane/plugin/sentry/actions/sentry_create_deploy.rb b/lib/fastlane/plugin/sentry/actions/sentry_create_deploy.rb new file mode 100644 index 00000000..21817be4 --- /dev/null +++ b/lib/fastlane/plugin/sentry/actions/sentry_create_deploy.rb @@ -0,0 +1,95 @@ +module Fastlane + module Actions + class SentryCreateDeployAction < Action + def self.run(params) + require 'shellwords' + + Helper::SentryHelper.check_sentry_cli! + Helper::SentryConfig.parse_api_params(params) + + version = params[:version] + version = "#{params[:app_identifier]}@#{params[:version]}" if params[:app_identifier] + + command = [ + "sentry-cli", + "releases", + "deploys", + version, + "new" + ] + command.push('--env').push(params[:env]) unless params[:env].nil? + command.push('--name').push(params[:name]) unless params[:name].nil? + command.push('--url').push(params[:deploy_url]) unless params[:deploy_url].nil? + command.push('--started').push(params[:started]) unless params[:started].nil? + command.push('--finished').push(params[:finished]) unless params[:finished].nil? + command.push('--time').push(params[:time]) unless params[:time].nil? + + Helper::SentryHelper.call_sentry_cli(command) + UI.success("Successfully created deploy: #{version}") + end + + ##################################################### + # @!group Documentation + ##################################################### + + def self.description + "Creates a new release deployment for a project on Sentry" + end + + def self.details + [ + "This action allows you to associate deploys to releases for a project on Sentry.", + "See https://docs.sentry.io/product/cli/releases/#creating-deploys for more information." + ].join(" ") + end + + def self.available_options + Helper::SentryConfig.common_api_config_items + [ + FastlaneCore::ConfigItem.new(key: :version, + description: "Release version to associate the deploy with on Sentry"), + FastlaneCore::ConfigItem.new(key: :env, + short_option: "-e", + description: "Set the environment for this release. This argument is required. Values that make sense here would be 'production' or 'staging'", + optional: false), + FastlaneCore::ConfigItem.new(key: :name, + short_option: "-n", + description: "Optional human readable name for this deployment", + optional: true), + FastlaneCore::ConfigItem.new(key: :deploy_url, + description: "Optional URL that points to the deployment", + optional: true), + FastlaneCore::ConfigItem.new(key: :started, + description: "Optional unix timestamp when the deployment started", + is_string: false, + optional: true), + FastlaneCore::ConfigItem.new(key: :finished, + description: "Optional unix timestamp when the deployment finished", + is_string: false, + optional: true), + FastlaneCore::ConfigItem.new(key: :time, + short_option: "-t", + description: "Optional deployment duration in seconds. This can be specified alternatively to `started` and `finished`", + is_string: false, + optional: true), + FastlaneCore::ConfigItem.new(key: :app_identifier, + short_option: "-a", + env_name: "SENTRY_APP_IDENTIFIER", + description: "App Bundle Identifier, prepended with the version.\nFor example bundle@version", + optional: true) + ] + end + + def self.return_value + nil + end + + def self.authors + ["denrase"] + end + + def self.is_supported?(platform) + true + end + end + end +end diff --git a/spec/sentry_create_deploy_spec.rb b/spec/sentry_create_deploy_spec.rb new file mode 100644 index 00000000..21d88a8c --- /dev/null +++ b/spec/sentry_create_deploy_spec.rb @@ -0,0 +1,110 @@ +describe Fastlane do + describe Fastlane::FastFile do + describe "create deploy" do + it "accepts app_identifier" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + allow(CredentialsManager::AppfileConfig).to receive(:try_fetch_value).with(:app_identifier).and_return(false) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "app.idf@1.0", "new", "--env", "staging"]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + app_identifier: 'app.idf', + env: 'staging') + end").runner.execute(:test) + end + + it "does not prepend app_identifier if not specified" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging"]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging') + end").runner.execute(:test) + end + + it "includes --name if present" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging", "--name", "fixture-name"]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging', + name: 'fixture-name') + end").runner.execute(:test) + end + + it "includes --url if present" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging", "--url", "http://www.sentry.io"]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging', + deploy_url: 'http://www.sentry.io') + end").runner.execute(:test) + end + + it "includes --started and --finished if present" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging", "--started", 1622630647, "--finished", 1622630700]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging', + started: 1622630647, + finished: 1622630700) + end").runner.execute(:test) + end + + it "includes --started if present" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging", "--started", 1622630647]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging', + started: 1622630647) + end").runner.execute(:test) + end + + it "includes --finished if present" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging", "--finished", 1622630700]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging', + finished: 1622630700) + end").runner.execute(:test) + end + + it "includes --time if present" do + expect(Fastlane::Helper::SentryHelper).to receive(:check_sentry_cli!).and_return(true) + expect(Fastlane::Helper::SentryConfig).to receive(:parse_api_params).and_return(true) + expect(Fastlane::Helper::SentryHelper).to receive(:call_sentry_cli).with(["sentry-cli", "releases", "deploys", "1.0", "new", "--env", "staging", "--time", 180]).and_return(true) + + Fastlane::FastFile.new.parse("lane :test do + sentry_create_deploy( + version: '1.0', + env: 'staging', + time: 180) + end").runner.execute(:test) + end + end + end +end