Skip to content

Signal sign-out confirmation with the prompt action type - #4480

Merged
ThaminduDilshan merged 1 commit into
thunder-id:mainfrom
madurangasiriwardena:signout-confirm-action-type
Aug 3, 2026
Merged

Signal sign-out confirmation with the prompt action type#4480
ThaminduDilshan merged 1 commit into
thunder-id:mainfrom
madurangasiriwardena:signout-confirm-action-type

Conversation

@madurangasiriwardena

@madurangasiriwardena madurangasiriwardena commented Jul 31, 2026

Copy link
Copy Markdown
Member

Purpose

The session sign-out executor told a confirmed sign-out apart from the initial request by persisting a logoutPromptShown marker in RuntimeData. This addresses @ThaminduDilshan's review comment on #4299: the confirmation prompt already knows which button the End-User pressed, so it can forward that as the prompt action's type and the executor can read it straight off the flow definition. No marker has to be stored.

This also restructures the executor so the confirmation prompt can grow further actions (a sign-out cancel button is planned), and stops the API documentation from enumerating action-type values.

Approach

Read the decision from the action type. common.ActionTypeSignOutConfirm (SIGN_OUT_CONFIRM) marks the confirmation prompt's action edge. The prompt node already forwards a matched action's type on ForwardedData[actionType] (prompt_node.go:154), so on the re-run after the End-User confirms, the executor sees it and terminates. RuntimeKeyLogoutPromptShown is gone.

Dispatch on the type rather than compare against one value. The previous guard was actionType != SIGN_OUT_CONFIRM, which collapsed three distinct cases (no type, the confirm type, some other type) into one boolean and would have sent any future action type down the prompt-again path. decide now returns a named signOutOutcome from a switch keyed on the action type:

switch common.ActionType(actionType) {
case common.ActionTypeSignOutConfirm:
    return signOutTerminate
default:
    // The initial request forwards no action type at all, and a type this executor does not
    // recognize is not consent to end the session. Both ask the End-User to confirm.
    return signOutPrompt
}

Adding the planned cancel action is then one constant, one case, one signOutOutcome, and its handling in Execute. The default branch is deliberately fail closed: an unrecognized type never terminates a session, so adding a type to a flow before the executor handles it cannot sign a user out unintentionally.

Mark the template's confirm button. The Conditional Sign Out Flow template carries the type on the prompt action (which the engine reads) and on the button element (which the flow builder's Action selector reads and re-emits on save). Without the element field, opening that template in the builder and saving it would silently drop the type and regress the flow into an endless confirmation loop.

Stop enumerating action types in the docs. The prompts[].action.type description listed SUBMIT and REJECT in three places, while the same description also said arbitrary strings are accepted. The enumerations were therefore never the contract, and every new action type would need edits in all three. They are replaced with a structural description: the value is opaque, and the executor that consumes it owns the vocabulary.

Related Issues

  • N/A

Related PRs

Checklist

  • Followed the contribution guidelines.
  • Manual test round performed and verified.
  • Documentation provided. (Add links if there are any)
    • Ran Vale and fixed all errors and warnings
  • Tests provided. (Add links if there are any)
    • Unit Tests
    • Integration Tests
  • Breaking changes. (Fill if applicable)
    • Breaking changes section filled.
    • breaking change label added.

Security checks

  • Followed secure coding standards in WSO2 Secure Coding Guidelines
  • Confirmed that this PR doesn't commit any keys, passwords, tokens, usernames, or other secrets.

Summary by CodeRabbit

  • New Features

    • Improved sign-out confirmation handling to reliably distinguish confirmed actions from unrecognized requests.
    • Added support for executor-defined action types in flow configurations.
  • Bug Fixes

    • Unrecognized sign-out actions now prompt for confirmation again instead of ending the session.
  • Documentation

    • Updated flow action documentation to describe action types as executor-defined values rather than fixed options.

Replace the RuntimeKeyLogoutPromptShown runtime-data guard on the session
sign-out executor with the confirmation prompt's action type. When the
End-User confirms, the prompt forwards its SIGN_OUT_CONFIRM action type to
the executor on the re-run, so a confirmed request is told apart from the
initial one without persisting a marker.

Resolve that into an outcome by dispatching on the forwarded action type
rather than comparing against the confirm type alone, so the confirmation
prompt can grow further actions: each action type the prompt raises maps to
one signOutOutcome, and an unrecognized type is treated as no consent and
prompts again rather than falling through to termination.

Mark the confirmation button of the Conditional Sign Out Flow template with
that type, both on the prompt action the engine reads and on the element
itself, so the flow builder's Action selector shows Sign out for it and the
type survives editing the flow.

Describe prompts[].action.type as an opaque string owned by the consuming
executor instead of enumerating its values in the flow management and flow
execution API specs and in the flow configuration guide. The field already
accepted arbitrary strings, so the enumerations were never the contract, and
they would need editing in three places for every action type added.

Refs thunder-id#4299
@coderabbitai

coderabbitai Bot commented Jul 31, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

📝 Walkthrough

Walkthrough

This PR changes sign-out confirmation to use a forwarded action type instead of a persisted runtime marker. It removes RuntimeKeyLogoutPromptShown, adds ActionTypeSignOutConfirm, updates the executor's decision logic and tests, and revises API schemas, docs, and console templates to describe action types as executor-defined.

Changes

Sign-out confirmation action type

Layer / File(s) Summary
Action type constants
backend/internal/flow/common/constants.go
RuntimeKeyLogoutPromptShown is removed. ActionTypeSignOutConfirm is added as a new action type.
Executor decision logic
backend/internal/flow/executor/session_signout_executor.go
confirmationRequired is replaced by signOutOutcome and a decide method. Session termination or confirmation prompting now depends on the forwarded action type instead of a persisted runtime marker.
Executor tests
backend/internal/flow/executor/session_signout_executor_test.go
Tests use ActionTypeSignOutConfirm instead of the runtime marker. A new test checks that an unrecognized action type causes another prompt without terminating the session.
API schema, docs, and template updates
api/flow-execution.yaml, api/flow-management.yaml, docs/content/guides/flows/advanced-configurations.mdx, frontend/apps/console/src/features/flows/data/templates.json
Action.type documentation changes from listing fixed SUBMIT/REJECT values to describing an opaque, executor-defined string. The console flow template adds SIGN_OUT_CONFIRM to the sign-out confirmation action and prompt mapping.

Estimated code review effort: 3 (Moderate) | ~25 minutes

Sequence Diagram(s)

sequenceDiagram
  participant Node as Sign-out Prompt Node
  participant Executor as SessionSignOutExecutor
  participant Session as SessionService

  Node->>Executor: forward action data
  Executor->>Executor: decide(ctx)
  alt actionType == SIGN_OUT_CONFIRM
    Executor->>Session: Terminate()
  else action missing or unrecognized
    Executor->>Node: prompt for confirmation
  end
Loading

Possibly related PRs

  • thunder-id/thunderid#4299: Modifies the same session_signout_executor.go file and introduces the RuntimeKeyLogoutPromptShown state that this PR replaces.
  • thunder-id/thunderid#4456: Introduces the SIGN_OUT_CONFIRM action type that this PR implements in the backend executor and templates.
  • thunder-id/thunderid#3973: Modifies the same executor and test file with earlier confirmation-handling changes.

Suggested reviewers: thamindudilshan, donomalvindula

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly and concisely describes the main change: using the prompt action type to signal sign-out confirmation.
Description check ✅ Passed The description covers the purpose, approach, related PRs, and required template sections; the unchecked checklist does not make it largely incomplete.
Docstring Coverage ✅ Passed No functions found in the changed files to evaluate docstring coverage. Skipping docstring coverage check.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.
✨ Finishing Touches 💡 1
🛠️ Fix failing CI checks 💡
  • Fix failing CI checks
🧪 Generate unit tests (beta)
  • Create PR with unit tests

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

docs/content/guides/flows/advanced-configurations.mdx

ESLint skipped: missing config or dependency (missing-dependency). The ESLint configuration references a package that is not available in the sandbox.


Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 1

🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@backend/internal/flow/executor/session_signout_executor_test.go`:
- Around line 114-115: Update the test comment before the
session_signout_executor_test.go test case to correctly describe the
id_token_hint condition. Change "valid id_token_hint" to "no valid
id_token_hint" to accurately reflect the test setup and the executor behavior
defined in session_signout_executor.go where this path applies when no valid
id_token_hint is present.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yaml

Review profile: CHILL

Plan: Pro Plus

Run ID: 1fd3b697-3d88-4d46-ac10-8f5eb84a9ad7

📥 Commits

Reviewing files that changed from the base of the PR and between 4a8a724 and c2e4a56.

📒 Files selected for processing (7)
  • api/flow-execution.yaml
  • api/flow-management.yaml
  • backend/internal/flow/common/constants.go
  • backend/internal/flow/executor/session_signout_executor.go
  • backend/internal/flow/executor/session_signout_executor_test.go
  • docs/content/guides/flows/advanced-configurations.mdx
  • frontend/apps/console/src/features/flows/data/templates.json

Comment thread backend/internal/flow/executor/session_signout_executor_test.go
@madurangasiriwardena madurangasiriwardena added the trigger-pr-builder Add when the PR is ready for CI; starts the PR Builder for this and all later pushes label Jul 31, 2026
@codecov

codecov Bot commented Jul 31, 2026

Copy link
Copy Markdown

Codecov Report

✅ All modified and coverable lines are covered by tests.

📢 Thoughts on this report? Let us know!

Comment thread backend/internal/flow/common/constants.go
// been shown in this flow run.
func (e *sessionSignOutExecutor) confirmationRequired(ctx *providers.NodeContext) bool {
// signOutOutcome is what the executor does with the current request.
type signOutOutcome int

Copy link
Copy Markdown
Member

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Can there be a case where there are more than 2 signout outcomes? If not we could simply make decide() function to return a boolean instead of defining s dedicated type.
WDYT?

Copy link
Copy Markdown
Member Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

There are 3 outcomes

  • Prompt for confirmation
  • Terminate the session (Sign out button in the prompt)
  • Cancel the termination request (future planned cancel button in the prompt)

Hence keeping the current implementation.

@ThaminduDilshan
ThaminduDilshan added this pull request to the merge queue Aug 3, 2026
Merged via the queue into thunder-id:main with commit 0d5a008 Aug 3, 2026
66 of 67 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

trigger-pr-builder Add when the PR is ready for CI; starts the PR Builder for this and all later pushes Type/Improvement

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants