Thanks to visit codestin.com
Credit goes to github.com

Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
73 changes: 55 additions & 18 deletions temporalcli/commands.gen.go
Original file line number Diff line number Diff line change
Expand Up @@ -314,6 +314,20 @@ func (v *QueryModifiersOptions) buildFlags(cctx *CommandContext, f *pflag.FlagSe
f.Var(&v.RejectCondition, "reject-condition", "Optional flag for rejecting Queries based on Workflow state. Accepted values: not_open, not_completed_cleanly.")
}

type WorkflowUpdateOptionsOptions struct {
VersioningOverrideBehavior StringEnum
VersioningOverrideDeploymentName string
VersioningOverrideBuildId string
}

func (v *WorkflowUpdateOptionsOptions) buildFlags(cctx *CommandContext, f *pflag.FlagSet) {
v.VersioningOverrideBehavior = NewStringEnum([]string{"pinned", "auto_upgrade"}, "")
f.Var(&v.VersioningOverrideBehavior, "versioning-override-behavior", "Override the versioning behavior of a Workflow. Accepted values: pinned, auto_upgrade. Required.")
_ = cobra.MarkFlagRequired(f, "versioning-override-behavior")
f.StringVar(&v.VersioningOverrideDeploymentName, "versioning-override-deployment-name", "", "When overriding to a `pinned` behavior, specifies the Deployment Name of the version to target.")
f.StringVar(&v.VersioningOverrideBuildId, "versioning-override-build-id", "", "When overriding to a `pinned` behavior, specifies the Build ID of the version to target.")
}

type TemporalCommand struct {
Command cobra.Command
Env string
Expand Down Expand Up @@ -762,9 +776,9 @@ func NewTemporalConfigCommand(cctx *CommandContext, parent *TemporalCommand) *Te
s.Command.Use = "config"
s.Command.Short = "Manage config files (EXPERIMENTAL)"
if hasHighlighting {
s.Command.Long = "Config files are TOML files that contain profiles, with each profile\ncontaining configuration for connecting to Temporal. \n\n\x1b[1mtemporal config set \\\n --prop address \\\n --value us-west-2.aws.api.temporal.io:7233\x1b[0m\n\nThe default config file path is \x1b[1m$CONFIG_PATH/temporalio/temporal.toml\x1b[0m where\n\x1b[1m$CONFIG_PATH\x1b[0m is defined as \x1b[1m$HOME/.config\x1b[0m on Unix,\n\x1b[1m$HOME/Library/Application Support\x1b[0m on macOS, and \x1b[1m%AppData%\x1b[0m on Windows.\nThis can be overridden with the \x1b[1mTEMPORAL_CONFIG_FILE\x1b[0m environment\nvariable or \x1b[1m--config-file\x1b[0m.\n\nThe default profile is \x1b[1mdefault\x1b[0m. This can be overridden with the\n\x1b[1mTEMPORAL_PROFILE\x1b[0m environment variable or \x1b[1m--profile\x1b[0m."
s.Command.Long = "Config files are TOML files that contain profiles, with each profile\ncontaining configuration for connecting to Temporal.\n\n\x1b[1mtemporal config set \\\n --prop address \\\n --value us-west-2.aws.api.temporal.io:7233\x1b[0m\n\nThe default config file path is \x1b[1m$CONFIG_PATH/temporalio/temporal.toml\x1b[0m where\n\x1b[1m$CONFIG_PATH\x1b[0m is defined as \x1b[1m$HOME/.config\x1b[0m on Unix,\n\x1b[1m$HOME/Library/Application Support\x1b[0m on macOS, and \x1b[1m%AppData%\x1b[0m on Windows.\nThis can be overridden with the \x1b[1mTEMPORAL_CONFIG_FILE\x1b[0m environment\nvariable or \x1b[1m--config-file\x1b[0m.\n\nThe default profile is \x1b[1mdefault\x1b[0m. This can be overridden with the\n\x1b[1mTEMPORAL_PROFILE\x1b[0m environment variable or \x1b[1m--profile\x1b[0m."
} else {
s.Command.Long = "Config files are TOML files that contain profiles, with each profile\ncontaining configuration for connecting to Temporal. \n\n```\ntemporal config set \\\n --prop address \\\n --value us-west-2.aws.api.temporal.io:7233\n```\n\nThe default config file path is `$CONFIG_PATH/temporalio/temporal.toml` where\n`$CONFIG_PATH` is defined as `$HOME/.config` on Unix,\n`$HOME/Library/Application Support` on macOS, and `%AppData%` on Windows.\nThis can be overridden with the `TEMPORAL_CONFIG_FILE` environment\nvariable or `--config-file`.\n\nThe default profile is `default`. This can be overridden with the\n`TEMPORAL_PROFILE` environment variable or `--profile`."
s.Command.Long = "Config files are TOML files that contain profiles, with each profile\ncontaining configuration for connecting to Temporal.\n\n```\ntemporal config set \\\n --prop address \\\n --value us-west-2.aws.api.temporal.io:7233\n```\n\nThe default config file path is `$CONFIG_PATH/temporalio/temporal.toml` where\n`$CONFIG_PATH` is defined as `$HOME/.config` on Unix,\n`$HOME/Library/Application Support` on macOS, and `%AppData%` on Windows.\nThis can be overridden with the `TEMPORAL_CONFIG_FILE` environment\nvariable or `--config-file`.\n\nThe default profile is `default`. This can be overridden with the\n`TEMPORAL_PROFILE` environment variable or `--profile`."
}
s.Command.Args = cobra.NoArgs
s.Command.AddCommand(&NewTemporalConfigDeleteCommand(cctx, &s).Command)
Expand Down Expand Up @@ -3395,30 +3409,53 @@ type TemporalWorkflowResetCommand struct {
func NewTemporalWorkflowResetCommand(cctx *CommandContext, parent *TemporalWorkflowCommand) *TemporalWorkflowResetCommand {
var s TemporalWorkflowResetCommand
s.Parent = parent
s.Command.DisableFlagsInUseLine = true
s.Command.Use = "reset [flags]"
s.Command.Use = "reset"
s.Command.Short = "Move Workflow Execution history point"
if hasHighlighting {
s.Command.Long = "Reset a Workflow Execution so it can resume from a point in its Event History\nwithout losing its progress up to that point:\n\n\x1b[1mtemporal workflow reset \\\n --workflow-id YourWorkflowId \\\n --event-id YourLastEvent\x1b[0m\n\nStart from where the Workflow Execution last continued as new:\n\n\x1b[1mtemporal workflow reset \\\n --workflow-id YourWorkflowId \\\n --type LastContinuedAsNew\x1b[0m\n\nFor batch resets, limit your resets to FirstWorkflowTask, LastWorkflowTask, or\nBuildId. Do not use Workflow IDs, run IDs, or event IDs with this command.\n\nVisit https://docs.temporal.io/visibility to read more about Search\nAttributes and Query creation."
} else {
s.Command.Long = "Reset a Workflow Execution so it can resume from a point in its Event History\nwithout losing its progress up to that point:\n\n```\ntemporal workflow reset \\\n --workflow-id YourWorkflowId \\\n --event-id YourLastEvent\n```\n\nStart from where the Workflow Execution last continued as new:\n\n```\ntemporal workflow reset \\\n --workflow-id YourWorkflowId \\\n --type LastContinuedAsNew\n```\n\nFor batch resets, limit your resets to FirstWorkflowTask, LastWorkflowTask, or\nBuildId. Do not use Workflow IDs, run IDs, or event IDs with this command.\n\nVisit https://docs.temporal.io/visibility to read more about Search\nAttributes and Query creation."
}
s.Command.Args = cobra.NoArgs
s.Command.Flags().StringVarP(&s.WorkflowId, "workflow-id", "w", "", "Workflow ID. Required for non-batch reset operations.")
s.Command.Flags().StringVarP(&s.RunId, "run-id", "r", "", "Run ID.")
s.Command.Flags().IntVarP(&s.EventId, "event-id", "e", 0, "Event ID to reset to. Event must occur after `WorkflowTaskStarted`. `WorkflowTaskCompleted`, `WorkflowTaskFailed`, etc. are valid.")
s.Command.Flags().StringVar(&s.Reason, "reason", "", "Reason for reset. Required.")
_ = cobra.MarkFlagRequired(s.Command.Flags(), "reason")
s.Command.AddCommand(&NewTemporalWorkflowResetWithWorkflowUpdateOptionsCommand(cctx, &s).Command)
s.Command.PersistentFlags().StringVarP(&s.WorkflowId, "workflow-id", "w", "", "Workflow ID. Required for non-batch reset operations.")
s.Command.PersistentFlags().StringVarP(&s.RunId, "run-id", "r", "", "Run ID.")
s.Command.PersistentFlags().IntVarP(&s.EventId, "event-id", "e", 0, "Event ID to reset to. Event must occur after `WorkflowTaskStarted`. `WorkflowTaskCompleted`, `WorkflowTaskFailed`, etc. are valid.")
s.Command.PersistentFlags().StringVar(&s.Reason, "reason", "", "Reason for reset. Required.")
_ = cobra.MarkFlagRequired(s.Command.PersistentFlags(), "reason")
s.ReapplyType = NewStringEnum([]string{"All", "Signal", "None"}, "All")
s.Command.Flags().Var(&s.ReapplyType, "reapply-type", "Types of events to re-apply after reset point. Accepted values: All, Signal, None.")
_ = s.Command.Flags().MarkDeprecated("reapply-type", "Use --reapply-exclude instead.")
s.Command.PersistentFlags().Var(&s.ReapplyType, "reapply-type", "Types of events to re-apply after reset point. Accepted values: All, Signal, None.")
_ = s.Command.PersistentFlags().MarkDeprecated("reapply-type", "Use --reapply-exclude instead.")
s.ReapplyExclude = NewStringEnumArray([]string{"All", "Signal", "Update"}, []string{})
s.Command.Flags().Var(&s.ReapplyExclude, "reapply-exclude", "Exclude these event types from re-application. Accepted values: All, Signal, Update.")
s.Command.PersistentFlags().Var(&s.ReapplyExclude, "reapply-exclude", "Exclude these event types from re-application. Accepted values: All, Signal, Update.")
s.Type = NewStringEnum([]string{"FirstWorkflowTask", "LastWorkflowTask", "LastContinuedAsNew", "BuildId"}, "")
s.Command.Flags().VarP(&s.Type, "type", "t", "The event type for the reset. Accepted values: FirstWorkflowTask, LastWorkflowTask, LastContinuedAsNew, BuildId.")
s.Command.Flags().StringVar(&s.BuildId, "build-id", "", "A Build ID. Use only with the BuildId `--type`. Resets the first Workflow task processed by this ID. By default, this reset may be in a prior run, earlier than a Continue as New point.")
s.Command.Flags().StringVarP(&s.Query, "query", "q", "", "Content for an SQL-like `QUERY` List Filter.")
s.Command.Flags().BoolVarP(&s.Yes, "yes", "y", false, "Don't prompt to confirm. Only allowed when `--query` is present.")
s.Command.PersistentFlags().VarP(&s.Type, "type", "t", "The event type for the reset. Accepted values: FirstWorkflowTask, LastWorkflowTask, LastContinuedAsNew, BuildId.")
s.Command.PersistentFlags().StringVar(&s.BuildId, "build-id", "", "A Build ID. Use only with the BuildId `--type`. Resets the first Workflow task processed by this ID. By default, this reset may be in a prior run, earlier than a Continue as New point.")
s.Command.PersistentFlags().StringVarP(&s.Query, "query", "q", "", "Content for an SQL-like `QUERY` List Filter.")
s.Command.PersistentFlags().BoolVarP(&s.Yes, "yes", "y", false, "Don't prompt to confirm. Only allowed when `--query` is present.")
s.Command.Run = func(c *cobra.Command, args []string) {
if err := s.run(cctx, args); err != nil {
cctx.Options.Fail(err)
}
}
return &s
}

type TemporalWorkflowResetWithWorkflowUpdateOptionsCommand struct {
Parent *TemporalWorkflowResetCommand
Command cobra.Command
WorkflowUpdateOptionsOptions
}

func NewTemporalWorkflowResetWithWorkflowUpdateOptionsCommand(cctx *CommandContext, parent *TemporalWorkflowResetCommand) *TemporalWorkflowResetWithWorkflowUpdateOptionsCommand {
var s TemporalWorkflowResetWithWorkflowUpdateOptionsCommand
s.Parent = parent
s.Command.DisableFlagsInUseLine = true
s.Command.Use = "with-workflow-update-options [flags]"
s.Command.Short = "Update options on reset workflow"
s.Command.Long = "Run Workflow Update Options atomically after the Workflow is reset.\nWorkflows selected by the reset command are forwarded onto the subcommand."
s.Command.Args = cobra.NoArgs
s.WorkflowUpdateOptionsOptions.buildFlags(cctx, s.Command.Flags())
s.Command.Run = func(c *cobra.Command, args []string) {
if err := s.run(cctx, args); err != nil {
cctx.Options.Fail(err)
Expand Down Expand Up @@ -3654,9 +3691,9 @@ func NewTemporalWorkflowStartUpdateWithStartCommand(cctx *CommandContext, parent
s.Command.Use = "start-update-with-start [flags]"
s.Command.Short = "Send an Update-With-Start and wait for it to be accepted or rejected (Experimental)"
if hasHighlighting {
s.Command.Long = "Send a message to a Workflow Execution to invoke an Update handler, and wait for\nthe update to be accepted or rejected. If the Workflow Execution is not running, \nthen a new workflow execution is started and the update is sent.\n\nExperimental.\n\n\x1b[1mtemporal workflow start-update-with-start \\\n --update-name YourUpdate \\\n --update-input '{\"update-key\": \"update-value\"}' \\\n --update-wait-for-stage accepted \\\n --workflow-id YourWorkflowId \\\n --type YourWorkflowType \\\n --task-queue YourTaskQueue \\\n --id-conflict-policy Fail \\\n --input '{\"wf-key\": \"wf-value\"}'\x1b[0m"
s.Command.Long = "Send a message to a Workflow Execution to invoke an Update handler, and wait for\nthe update to be accepted or rejected. If the Workflow Execution is not running,\nthen a new workflow execution is started and the update is sent.\n\nExperimental.\n\n\x1b[1mtemporal workflow start-update-with-start \\\n --update-name YourUpdate \\\n --update-input '{\"update-key\": \"update-value\"}' \\\n --update-wait-for-stage accepted \\\n --workflow-id YourWorkflowId \\\n --type YourWorkflowType \\\n --task-queue YourTaskQueue \\\n --id-conflict-policy Fail \\\n --input '{\"wf-key\": \"wf-value\"}'\x1b[0m"
} else {
s.Command.Long = "Send a message to a Workflow Execution to invoke an Update handler, and wait for\nthe update to be accepted or rejected. If the Workflow Execution is not running, \nthen a new workflow execution is started and the update is sent.\n\nExperimental.\n\n```\ntemporal workflow start-update-with-start \\\n --update-name YourUpdate \\\n --update-input '{\"update-key\": \"update-value\"}' \\\n --update-wait-for-stage accepted \\\n --workflow-id YourWorkflowId \\\n --type YourWorkflowType \\\n --task-queue YourTaskQueue \\\n --id-conflict-policy Fail \\\n --input '{\"wf-key\": \"wf-value\"}'\n```"
s.Command.Long = "Send a message to a Workflow Execution to invoke an Update handler, and wait for\nthe update to be accepted or rejected. If the Workflow Execution is not running,\nthen a new workflow execution is started and the update is sent.\n\nExperimental.\n\n```\ntemporal workflow start-update-with-start \\\n --update-name YourUpdate \\\n --update-input '{\"update-key\": \"update-value\"}' \\\n --update-wait-for-stage accepted \\\n --workflow-id YourWorkflowId \\\n --type YourWorkflowType \\\n --task-queue YourTaskQueue \\\n --id-conflict-policy Fail \\\n --input '{\"wf-key\": \"wf-value\"}'\n```"
}
s.Command.Args = cobra.NoArgs
s.Command.Flags().StringVar(&s.UpdateName, "update-name", "", "Update name. Required. Aliased as \"--update-type\".")
Expand Down
14 changes: 12 additions & 2 deletions temporalcli/commands.workflow_reset.go
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import (
"go.temporal.io/api/batch/v1"
"go.temporal.io/api/common/v1"
"go.temporal.io/api/enums/v1"
workflow "go.temporal.io/api/workflow/v1"
"go.temporal.io/api/workflowservice/v1"
"go.temporal.io/sdk/client"

Expand Down Expand Up @@ -66,7 +67,10 @@ func (c *TemporalWorkflowResetCommand) validateBatchResetArguments() error {
return nil
}
func (c *TemporalWorkflowResetCommand) doWorkflowReset(cctx *CommandContext, cl client.Client) error {
return c.doWorkflowResetWithPostOps(cctx, cl, nil)
}

func (c *TemporalWorkflowResetCommand) doWorkflowResetWithPostOps(cctx *CommandContext, cl client.Client, postOps []*workflow.PostResetOperation) error {
var err error
resetBaseRunID := c.RunId
eventID := int64(c.EventId)
Expand Down Expand Up @@ -94,6 +98,7 @@ func (c *TemporalWorkflowResetCommand) doWorkflowReset(cctx *CommandContext, cl
WorkflowTaskFinishEventId: eventID,
ResetReapplyType: reapplyType,
ResetReapplyExcludeTypes: reapplyExcludes,
PostResetOperations: postOps,
})
if err != nil {
return fmt.Errorf("failed to reset workflow: %w", err)
Expand All @@ -108,6 +113,10 @@ func (c *TemporalWorkflowResetCommand) doWorkflowReset(cctx *CommandContext, cl
}

func (c *TemporalWorkflowResetCommand) runBatchReset(cctx *CommandContext, cl client.Client) error {
return c.runBatchResetWithPostOps(cctx, cl, nil)
}

func (c *TemporalWorkflowResetCommand) runBatchResetWithPostOps(cctx *CommandContext, cl client.Client, postOps []*workflow.PostResetOperation) error {
request := workflowservice.StartBatchOperationRequest{
Namespace: c.Parent.Namespace,
JobId: uuid.NewString(),
Expand All @@ -121,8 +130,9 @@ func (c *TemporalWorkflowResetCommand) runBatchReset(cctx *CommandContext, cl cl
}
request.Operation = &workflowservice.StartBatchOperationRequest_ResetOperation{
ResetOperation: &batch.BatchOperationReset{
Identity: clientIdentity(),
Options: batchResetOptions,
Identity: clientIdentity(),
Options: batchResetOptions,
PostResetOperations: postOps,
},
}
count, err := cl.CountWorkflow(cctx, &workflowservice.CountWorkflowExecutionsRequest{Query: c.Query})
Expand Down
75 changes: 75 additions & 0 deletions temporalcli/commands.workflow_reset_update_options.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
package temporalcli

import (
"fmt"

deploymentpb "go.temporal.io/api/deployment/v1"
workflowpb "go.temporal.io/api/workflow/v1"
"google.golang.org/protobuf/types/known/fieldmaskpb"
)

func (c *TemporalWorkflowResetWithWorkflowUpdateOptionsCommand) run(cctx *CommandContext, args []string) error {
validate, _ := c.Parent.getResetOperations()
if err := validate(); err != nil {
return err
}

if c.VersioningOverrideBehavior.Value == "pinned" {
if c.VersioningOverrideDeploymentName == "" || c.VersioningOverrideBuildId == "" {
return fmt.Errorf("deployment name and build id are required with 'pinned' behavior")
}
}
if c.VersioningOverrideBehavior.Value != "pinned" {
if c.VersioningOverrideDeploymentName != "" || c.VersioningOverrideBuildId != "" {
return fmt.Errorf("cannot set deployment name or build id with %v behavior", c.VersioningOverrideBehavior.Value)
}
}

cl, err := c.Parent.Parent.ClientOptions.dialClient(cctx)
if err != nil {
return err
}
defer cl.Close()

VersioningOverride := &workflowpb.VersioningOverride{}
switch c.VersioningOverrideBehavior.Value {
case "pinned":
VersioningOverride.Override = &workflowpb.VersioningOverride_Pinned{
Pinned: &workflowpb.VersioningOverride_PinnedOverride{
Behavior: workflowpb.VersioningOverride_PINNED_OVERRIDE_BEHAVIOR_PINNED,
Version: &deploymentpb.WorkerDeploymentVersion{
DeploymentName: c.VersioningOverrideDeploymentName,
BuildId: c.VersioningOverrideBuildId,
},
},
}
case "auto_upgrade":
VersioningOverride.Override = &workflowpb.VersioningOverride_AutoUpgrade{
AutoUpgrade: true,
}
default:
return fmt.Errorf("invalid deployment behavior: %v, valid values are: 'pinned', and 'auto_upgrade'", c.VersioningOverrideBehavior.Value)
}

var workflowExecutionOptions *workflowpb.WorkflowExecutionOptions
protoMask, err := fieldmaskpb.New(workflowExecutionOptions, "versioning_override")
if err != nil {
return fmt.Errorf("invalid field mask: %w", err)
}

postOp := &workflowpb.PostResetOperation{
Variant: &workflowpb.PostResetOperation_UpdateWorkflowOptions_{
UpdateWorkflowOptions: &workflowpb.PostResetOperation_UpdateWorkflowOptions{
WorkflowExecutionOptions: &workflowpb.WorkflowExecutionOptions{
VersioningOverride: VersioningOverride,
},
UpdateMask: protoMask,
},
},
}

if c.Parent.WorkflowId != "" {
return c.Parent.doWorkflowResetWithPostOps(cctx, cl, []*workflowpb.PostResetOperation{postOp})
}
return c.Parent.runBatchResetWithPostOps(cctx, cl, []*workflowpb.PostResetOperation{postOp})
}
Loading