Skip to content

GetCustomerInput ​

Collect DTMF (keypad) or voice input from customers. This block presents a prompt and waits for the customer to respond.

Signature ​

csharp
// 1) Prompt + optional action configuration (returns branch builder)
IInputBuilder GetCustomerInput(
    string promptText,
    Action<GetCustomerInputAction>? configure = null,
    string? identifier = null);

// 2) Prompt + branches callback (returns parent flow builder)
// Use this overload when you want to configure all branches inline, then continue chaining
// on the parent flow builder (often paired with ThenContinue()).
IFlowBuilder GetCustomerInput(
    string promptText,
    Action<IInputBuilder> branches,
    Action<GetCustomerInputAction>? configure = null,
    string? identifier = null);

// 3) Advanced configuration with InputConfiguration (Sequential / ASR + DTMF)
IFlowBuilder GetCustomerInput(
    Action<InputConfiguration> configure,
    string? identifier = null);

Required branches

GetCustomerInput is a branching action. Always configure all required branches before you continue your flow:

  • OnTimeout(...)
  • OnDefault(...)
  • OnError(...) (or OnInvalidInput(...) which maps to the same error branch)

Parameters ​

ParameterTypeRequiredDescription
promptTextstringYesThe prompt text to play
configureAction<GetCustomerInputAction>NoConfigure input settings
branchesAction<IInputBuilder>Only for overload (2)Configure all branches (digits/intents + required fallbacks)
identifierstring?NoOptional identifier for the action

GetCustomerInputAction Properties ​

PropertyTypeDefaultDescription
TimeoutSecondsint5Time to wait for input
MaxDigitsint1Maximum digits to collect
EncryptInputboolfalseEncrypt collected input
MaxAttemptsint1Number of retry attempts
TerminatingDigitstring?nullDigit that ends input (e.g., "#")

Return Value ​

Overload (1) returns IInputBuilder which provides branch handlers:

MethodDescription
.OnDigit(string digit, Action<IFlowBuilder>)Handle specific digit input
.OnDigits(Action<IFlowBuilder>)Handle any collected digits
.OnTimeout(Action<IFlowBuilder>)Handle input timeout
.OnError(Action<IFlowBuilder>)Handle errors
.OnDefault(Action<IFlowBuilder>)Handle unmatched input
.OnIntent(string, Action<IFlowBuilder>)Handle Lex bot intent (ASR)
.OnNoMatch(Action<IFlowBuilder>)Handle ASR no match
.OnLowConfidence(Action<IFlowBuilder>)Handle low confidence ASR
.WithRetry(Action<IRetryBuilder>)Configure automatic retry
.WithLexBot(Action<LexBotConfiguration>)Configure Lex bot for ASR

Overload (2) returns IFlowBuilder (the parent builder). This is useful when you want to:

  • configure branches inline via branches:
  • then continue chaining on the parent builder (for example, add shared actions after a successful branch calls ThenContinue())

Examples ​

Simple Menu ​

csharp
Flow.Create("Main Menu")
    .PlayPrompt("Welcome to Nick Software.")
    .GetCustomerInput("Press 1 for Sales, 2 for Support, or 3 for Billing.")
        .OnDigit("1", sales => sales
            .PlayPrompt("Transferring to Sales.")
            .TransferToQueue("Sales")
            .Disconnect())
        .OnDigit("2", support => support
            .PlayPrompt("Transferring to Support.")
            .TransferToQueue("Support")
            .Disconnect())
        .OnDigit("3", billing => billing
            .PlayPrompt("Transferring to Billing.")
            .TransferToQueue("Billing")
            .Disconnect())
        .OnTimeout(timeout => timeout
            .PlayPrompt("No input received. Goodbye.")
            .Disconnect())
        .OnError(error => error
            .PlayPrompt("An error occurred. Goodbye.")
            .Disconnect())
        .OnDefault(def => def
            .PlayPrompt("Invalid selection. Goodbye.")
            .Disconnect());

With Configuration ​

csharp
Flow.Create("Account Entry")
    .GetCustomerInput("Please enter your account number followed by the pound key.",
        input =>
        {
            input.TimeoutSeconds = 15;
            input.MaxDigits = 10;
            input.TerminatingDigit = "#";
        })
        .OnDigits(digits => digits
            .SetContactAttributes(attrs =>
            {
                attrs["AccountNumber"] = Attributes.System(SystemAttributes.LastCollectedDigits);
            })
            .InvokeLambda("ValidateAccount"))
        .OnTimeout(timeout => timeout
            .PlayPrompt("We didn't receive your account number.")
            .Disconnect())
        .OnDefault(def => def
            .PlayPrompt("Invalid entry.")
            .Disconnect())
        .OnError(error => error
            .PlayPrompt("An error occurred.")
            .Disconnect());

With Retry Logic ​

csharp
Flow.Create("PIN with Retry")
    .Loop(3, loop => loop
        .WhileLooping(attempt => attempt
            .GetCustomerInput("Please enter your PIN.", input =>
            {
                input.MaxDigits = 4;
                input.TimeoutSeconds = 10;
            })
            .OnDigits(pin => pin
                .InvokeLambda("ValidatePIN")
                    .OnSuccess(success => success
                        .PlayPrompt("PIN accepted.")
                        .TransferToQueue("Authenticated")
                        .Disconnect())
                    .OnError(error => error
                        .PlayPrompt("Invalid PIN. Please try again.")))
            .OnTimeout(timeout => timeout
                .PlayPrompt("No input received. Please try again."))
            .ThenContinue())
        .WhenDone(maxAttempts => maxAttempts
            .PlayPrompt("Maximum attempts reached. Goodbye.")
            .Disconnect()));

With Lex Bot (ASR) ​

csharp
Flow.Create("Voice Menu")
    .GetCustomerInput("How can I help you today?")
        .WithLexBot(lex =>
        {
            lex.BotName = "CustomerServiceBot";
            lex.BotAlias = "$LATEST";
            lex.Locale = "en_US";
        })
        .OnIntent("OrderStatus", orderStatus => orderStatus
            .PlayPrompt("Let me check your order status.")
            .InvokeLambda("GetOrderStatus"))
        .OnIntent("ReturnItem", returnItem => returnItem
            .PlayPrompt("I can help you return an item.")
            .TransferToQueue("Returns"))
        .OnNoMatch(noMatch => noMatch
            .PlayPrompt("I didn't understand. Let me transfer you to an agent.")
            .TransferToQueue("General"))
        .OnError(error => error
            .PlayPrompt("An error occurred.")
            .Disconnect());

Sequential ASR to DTMF Fallback ​

csharp
Flow.Create("Sequential Input")
    .GetCustomerInput("Say or press 1 for Sales, 2 for Support.")
        .WithSequentialInput(
            asrPrompt: "I can help with Sales or Support. Which would you like?",
            dtmfPrompt: "Press 1 for Sales, or 2 for Support.",
            lexBotName: "MenuBot",
            maxDigits: 1,
            fallbackTriggers: FallbackTrigger.AnyError)
        .OnDigit("1", sales => sales.TransferToQueue("Sales").Disconnect())
        .OnDigit("2", support => support.TransferToQueue("Support").Disconnect())
        .OnIntent("Sales", sales => sales.TransferToQueue("Sales").Disconnect())
        .OnIntent("Support", support => support.TransferToQueue("Support").Disconnect())
        .OnTimeout(t => t.Disconnect())
        .OnError(e => e.Disconnect())
        .OnDefault(d => d.Disconnect());

Complex Authenticated Menu ​

csharp
private static void BuildAuthenticatedMenu(IFlowBuilder flow)
{
    flow.PlayPrompt($"Welcome {Attributes.External("CustomerName")}. You are now authenticated.")
        .GetCustomerInput(
            promptText: """
                To check your balance, press 1.
                To check your orders, press 2.
                To speak to an agent, press 3.
                """,
            branches: input => input
                .OnDigit("1", balance => balance
                    .PlayPrompt($"Your balance is {Attributes.External("Balance")} dollars.")
                    .ThenContinue())
                .OnDigit("2", orders => orders
                    .InvokeLambda("GetOrders")
                        .OnSuccess(s => s.PlayPrompt("You have 3 active orders."))
                        .OnError(e => e.PlayPrompt("Could not retrieve orders."))
                    .ThenContinue())
                .OnDigit("3", agent => agent
                    .PlayPrompt("Transferring to an agent.")
                    .TransferToQueue("Support")
                    .Disconnect())
                .OnTimeout(timeout => timeout
                    .PlayPrompt("No selection received. Goodbye.")
                    .Disconnect())
                .OnError(menuError => menuError
                    .PlayPrompt("An error occurred. Goodbye.")
                    .Disconnect())
                .OnDefault(def => def
                    .PlayPrompt("Invalid selection.")
                    .ContinueAt("AuthMenu")),
            configure: action => action.TimeoutSeconds = 10,
            identifier: "AuthMenu")
        .GetCustomerInput(
            promptText: "Press 1 to return to the menu, or 2 to disconnect.",
            branches: input => input
                .OnDigit("1", returnMenu => returnMenu.ContinueAt("AuthMenu"))
                .OnDigit("2", disconnect => disconnect.Disconnect())
                .OnDefault(d => d.Disconnect())
                .OnTimeout(t => t.Disconnect())
                .OnError(e => e.Disconnect()),
            configure: action => action.TimeoutSeconds = 5,
            identifier: "AuthMenuPostAction");
}

Branch Continuation ​

csharp
Flow.Create("Menu with Continuation")
    .GetCustomerInput(
        promptText: "Press 1 or 2",
        branches: input => input
            .OnDigit("1", one => one
                .SetContactAttributes(attrs => attrs["Selection"] = "Option1")
                .ThenContinue())
            .OnDigit("2", two => two
                .SetContactAttributes(attrs => attrs["Selection"] = "Option2")
                .ThenContinue())
            .OnDefault(d => d.Disconnect())
            .OnTimeout(t => t.Disconnect())
            .OnError(e => e.Disconnect()),
        configure: action => action.TimeoutSeconds = 5,
        identifier: "menu")
    .TransferToQueue("General")
    .Disconnect();

AWS Connect Block Type ​

This block generates the GetParticipantInput action type in the exported flow JSON.

Input Types ​

TypeDescriptionUse Case
DTMFKeypad digit inputMenu selection, account numbers
ASRAutomatic Speech RecognitionNatural language input
SequentialASR with DTMF fallbackBest user experience

Best Practices ​

  1. Always handle all branches - Include OnTimeout, OnError, and OnDefault
  2. Keep menus simple - Maximum 4-5 options per menu
  3. Set appropriate timeouts - 5-10 seconds for simple selections
  4. Use retry loops - Allow multiple attempts for complex input
  5. Provide clear prompts - Tell customers exactly what to press
  6. Use ThenContinue() - When branches should converge

See Also ​

Preview release - Licensing terms TBD before 1.0