Skip to content

[Bug] Inline C# action in Logic App Standard fails AES decryption with valid key and ciphertext #1429

@lilan123

Description

@lilan123

Describe the Bug

The Inline C# action in Logic App Standard fails when attempting to decrypt AES-encrypted data in CBC mode with PKCS7 padding.

  • The AES key is retrieved from Azure Key Vault (Base64-encoded, 32 bytes → AES-256).
  • The ciphertext (Base64-encoded) contains the IV prepended (first 16 bytes) followed by the encrypted payload.
  • The same key and ciphertext decrypt successfully in a function app
// Add the required libraries
#r "Newtonsoft.Json"
#r "Microsoft.Azure.Workflows.Scripting"
using Microsoft.AspNetCore.Mvc;
using Microsoft.Extensions.Primitives;
using Microsoft.Azure.Workflows.Scripting;
using Newtonsoft.Json.Linq;
using System;
using System.IO;
using System.Security.Cryptography;
using System.Text;

/// <summary>
/// Executes the inline csharp code.
/// </summary>
/// <param name="context">The workflow context.</param>
/// <remarks> This is the entry-point to your code. The function signature should remain unchanged.</remarks>
public static async Task<Results> Run(WorkflowContext context, ILogger log)
{
    var composeOutput = (await context.GetActionResults("Compose").ConfigureAwait(false)).Outputs;

    string KeyStringStr = composeOutput["KeyString"].ToString();
    string Base64DataStr = composeOutput["Base64Data"].ToString();

    if (string.IsNullOrEmpty(KeyStringStr))
        throw new ArgumentException("AES key is missing.");
    if (string.IsNullOrEmpty(Base64DataStr))
        throw new ArgumentException("Ciphertext is missing.");

                byte[] key = Convert.FromBase64String(KeyStringStr);
                byte[] allBytes = Convert.FromBase64String(Base64DataStr);

                byte[] iv = allBytes.Take(16).ToArray();
                byte[] cipherBytes = allBytes.Skip(16).ToArray();

                string decryptedText;
                using (var aes = Aes.Create())
                {
                    aes.Key = key;
                    aes.IV = iv;
                    aes.Mode = CipherMode.CBC;
                    aes.Padding = PaddingMode.PKCS7;

                    using var ms = new MemoryStream();
                    using (var cryptoStream = new CryptoStream(ms, aes.CreateDecryptor(), CryptoStreamMode.Write))
                    {
                        cryptoStream.Write(cipherBytes, 0, cipherBytes.Length);
                        cryptoStream.FlushFinalBlock();
                    }
                    decryptedText = Encoding.UTF8.GetString(ms.ToArray());
                }
    

    return new { DecryptedText = decryptedText };
}

public class Results
{
    public string DecryptedText { get; set; }
}

Plan Type

Standard

Steps to Reproduce the Bug or Issue

Steps to reproduce

  1. Create a Logic App Standard workflow.
  2. Add a Get secret from Azure Key Vault action that retrieves an AES key
  3. Add a Compose action that outputs:
  • KeyString (AES key retrieved from Key Vault)
    
  • Base64Data (ciphertext in Base64).
    
  1. Add an Inline C# action that takes outputs from a Compose action: - KeyString (AES key in Base64) - Base64Data (ciphertext)
  2. Attempt AES CBC decryption as shown below:

Workflow JSON

{
    "definition": {
        "$schema": "https://schema.management.azure.com/providers/Microsoft.Logic/schemas/2016-06-01/workflowdefinition.json#",
        "contentVersion": "1.0.0.0",
        "actions": {
            "Parse_JSON": {
                "type": "ParseJson",
                "inputs": {
                    "content": "@triggerBody()?['contentData']",
                    "schema": {
                        "type": "object",
                        "properties": {
                            "specversion": {
                                "type": "string"
                            },
                            "type": {
                                "type": "string"
                            },
                            "source": {
                                "type": "string"
                            },
                            "dataversion": {
                                "type": "string"
                            },
                            "id": {
                                "type": "string"
                            },
                            "time": {
                                "type": "string"
                            },
                            "datacontentType": {
                                "type": "string"
                            },
                            "data": {
                                "type": "object",
                                "properties": {
                                    "payload": {
                                        "type": "string"
                                    },
                                    "sequenceId": {
                                        "type": "string"
                                    },
                                    "batchId": {
                                        "type": "string"
                                    },
                                    "receivedTimestampUTC": {
                                        "type": "string"
                                    }
                                }
                            }
                        }
                    }
                },
                "runAfter": {}
            },
            "Try": {
                "type": "Scope",
                "actions": {
                    "Get_secret": {
                        "type": "ServiceProvider",
                        "inputs": {
                            "parameters": {
                                "secretName": "function-aeskey"
                            },
                            "serviceProviderConfiguration": {
                                "connectionName": "keyVault",
                                "operationId": "getSecret",
                                "serviceProviderId": "/serviceProviders/keyVault"
                            }
                        },
                        "runtimeConfiguration": {
                            "secureData": {
                                "properties": [
                                    "inputs",
                                    "outputs"
                                ]
                            }
                        }
                    },
                    "Compose": {
                        "type": "Compose",
                        "inputs": {
                            "KeyString": "@{body('Get_secret')?['value']}",
                            "Base64Data": "@{body('Parse_JSON')?['data']?['payload']}"
                        },
                        "runAfter": {
                            "Get_secret": [
                                "SUCCEEDED"
                            ]
                        }
                    },
                    "Execute_C#_script_code": {
                        "type": "CSharpScriptCode",
                        "inputs": {
                            "CodeFile": "execute_csharp_script_code.csx"
                        },
                        "runAfter": {
                            "Compose": [
                                "SUCCEEDED"
                            ]
                        }
                    }
                },
                "runAfter": {
                    "Parse_JSON": [
                        "SUCCEEDED"
                    ]
                }
            },
            "Catch": {
                "type": "Scope",
                "actions": {},
                "runAfter": {
                    "Try": [
                        "SUCCEEDED"
                    ]
                }
            }
        },
        "outputs": {},
        "triggers": {
            "When_messages_are_available_in_a_topic": {
                "type": "ServiceProvider",
                "inputs": {
                    "parameters": {
                        "topicName": "process",
                        "subscriptionName": "transaction",
                        "isSessionsEnabled": false
                    },
                    "serviceProviderConfiguration": {
                        "connectionName": "conn_logic_sb",
                        "operationId": "receiveTopicMessages",
                        "serviceProviderId": "/serviceProviders/serviceBus"
                    }
                },
                "splitOn": "@triggerOutputs()?['body']"
            }
        }
    },
    "kind": "Stateful"
}

Screenshots or Videos

Image

Additional context

No response

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions