implemented input node resolver and major refactoring over execution function
Some checks failed
Build / build (push) Has been cancelled
CodeQL / Analyze (csharp) (push) Has been cancelled

This commit is contained in:
Ankitkumar Satapara
2026-04-21 01:08:29 +05:30
parent 16a5c591f3
commit 8c04e6534a
4 changed files with 334 additions and 9 deletions

View File

@@ -346,11 +346,21 @@ namespace Nodify.Calculator.Execution.Handlers
internal sealed class ApiRequestHandler : INodeExecutionHandler
{
// Matches {name} placeholders in URL templates (e.g., /api/Pizza/{id})
private static readonly System.Text.RegularExpressions.Regex PlaceholderRegex =
new System.Text.RegularExpressions.Regex(@"\{([^{}]+)\}",
System.Text.RegularExpressions.RegexOptions.Compiled);
public bool CanHandle(OperationViewModel node, ExecutionContext ctx) => true; // final fallback
public void Execute(OperationViewModel node, ExecutionContext ctx)
{
var url = node.Title ?? "";
var urlTemplate = node.Title ?? "";
var url = ResolveUrlPlaceholders(urlTemplate, node, ctx);
if (!string.Equals(url, urlTemplate, StringComparison.Ordinal))
ctx.Log($"URL resolved: {urlTemplate} → {url}");
ctx.Log($"Starting Execution : {url}");
var httpMethod = (node is APIOperationViewModel apiVm)
@@ -369,5 +379,42 @@ namespace Nodify.Calculator.Execution.Handlers
}
ctx.Log($"Response Result : {res}");
}
/// <summary>
/// Replaces {name} tokens in the URL template with values read from the
/// matching input connector on the node. Connector titles may include a
/// trailing " (type)" suffix (e.g., "id (int)") which is stripped for matching.
/// </summary>
private static string ResolveUrlPlaceholders(string template, OperationViewModel node, ExecutionContext ctx)
{
if (string.IsNullOrEmpty(template) || template.IndexOf('{') < 0)
return template;
// Build lookup: normalized connector name → value
var inputMap = new Dictionary<string, string>(StringComparer.OrdinalIgnoreCase);
foreach (var inp in node.Input)
{
if (inp.Shape == ConnectorShape.Triangle) continue;
var name = inp.Title ?? "";
var parenIdx = name.IndexOf(" (", StringComparison.Ordinal);
if (parenIdx > 0) name = name.Substring(0, parenIdx);
name = name.Trim();
if (string.IsNullOrEmpty(name)) continue;
var value = ctx.ReadInput(inp);
if (value != null)
inputMap[name] = value;
}
return PlaceholderRegex.Replace(template, m =>
{
var key = m.Groups[1].Value.Trim();
if (inputMap.TryGetValue(key, out var val))
return Uri.EscapeDataString(val);
ctx.Log($"URL placeholder '{{{key}}}' has no matching input value; leaving as-is.", logType.Warning);
return m.Value;
});
}
}
}