Fix ArgumentNullException ("input") during publish for non-.NET runtimes (latent bug exposed by v4.7.0)#4827
Conversation
What change occured in 4.7.0 that led to this? Point me to the commit/PR for this |
…ilure for non-.NET runtimes Co-authored-by: liliankasem <2198905+liliankasem@users.noreply.github.com>
Co-authored-by: liliankasem <2198905+liliankasem@users.noreply.github.com>
The regression was introduced in PR #4760 ("Add EOL warnings for all runtimes during function app publish"), specifically this one-line change: - private static string _requiredNetFrameworkVersion = "8.0";
+ private static string _requiredNetFrameworkVersion = null;In v4.6.0, In v4.7.0 (post-#4760), the default was changed to The intent of the change was correct — auto-detect TFM instead of hardcoding 8.0 — but it needed guards for the non-.NET case. The fix in this PR adds those guards: |
|
The ArgumentNullException during func azure functionapp publish for non-.NET runtimes (PowerShell, Node.js, Python, Java) on Windows is a latent bug introduced in July 2021 by PR #2639, which refactored UpdateFrameworkVersions and accidentally widened the scope of UpdateNetFrameworkVersionWindows from DotnetIsolated-only to all non-DotnetIsolated Windows apps. Before that refactor, UpdateNetFrameworkVersionWindows was only reachable through UpdateDotNetIsolatedFrameworkVersion, which gates on workerRuntime == DotnetIsolated. The refactor added an else if (!functionApp.IsLinux) branch at the top level of UpdateFrameworkVersions that caught every Windows runtime — PowerShell, Node, Python, Java — and routed them into dotnet-specific version update logic they had no business entering. This was silently masked for over three years because _requiredNetFrameworkVersion defaulted to "8.0", so NormalizeDotnetFrameworkVersion(null) would fall back to new Version("8.0") and harmlessly (but incorrectly) set NetFrameworkVersion=v8.0 on the function app — a property Azure ignores for non-.NET runtimes. When PR #4760 (v4.7.0) correctly changed the default to null for dynamic TFM detection, the mask came off: new Version(null) throws ArgumentNullException. This fix removes the erroneous branch entirely, restoring UpdateFrameworkVersions to its intended structure where only DotnetIsolated enters UpdateNetFrameworkVersionWindows (via UpdateDotNetIsolatedFrameworkVersion), and adds defensive null guards in NormalizeDotnetFrameworkVersion, UpdateNetFrameworkVersionWindows, and DotnetIsolatedLinuxValidation as belt-and-suspenders protection. Update the PR description and title to reflect the updated fix |
…ysis Co-authored-by: liliankasem <2198905+liliankasem@users.noreply.github.com>
Updated the PR title, description, and release notes in commit Latent bug (PR #2639, July 2021): Why it was masked (2021–2024): v4.7.0 exposed it (PR #4760): Primary fix: Removed the erroneous Warning Firewall rules blocked me from connecting to one or more addresses (expand for details)I tried to connect to the following addresses, but was blocked by firewall rules:
If you need me to access, download, or install something from one of these locations, you can either:
|
|
/azp run |
|
Azure Pipelines successfully started running 1 pipeline(s). |
func azure functionapp publishthrowsArgumentNullException: Value cannot be null. (Parameter 'input')for all non-.NET runtimes (PowerShell, Node.js, Python, Java) on Windows function apps when--dotnet-versionis not specified.Root Cause
The true root cause is a latent bug introduced in July 2021 by PR #2639, which refactored
UpdateFrameworkVersionsand accidentally widened the scope ofUpdateNetFrameworkVersionWindowsfromDotnetIsolated-only to all non-DotnetIsolatedWindows apps. Before that refactor,UpdateNetFrameworkVersionWindowswas only reachable throughUpdateDotNetIsolatedFrameworkVersion, which gates onworkerRuntime == DotnetIsolated. The refactor added anelse if (!functionApp.IsLinux)branch at the top level ofUpdateFrameworkVersionsthat caught every Windows runtime — PowerShell, Node, Python, Java — and routed them into dotnet-specific version update logic they had no business entering.This was silently masked for over three years because
_requiredNetFrameworkVersiondefaulted to"8.0", soNormalizeDotnetFrameworkVersion(null)would fall back tonew Version("8.0")and harmlessly (but incorrectly) setNetFrameworkVersion=v8.0on the function app — a property Azure ignores for non-.NET runtimes.PR #4760 (v4.7.0) exposed the bug by correctly changing the default to
nullfor dynamic TFM detection. With no fallback,new Version(null)throwsArgumentNullException: Value cannot be null. (Parameter 'input').Fix
UpdateFrameworkVersions— removed the erroneouselse if (!functionApp.IsLinux)branch, restoring the intended structure where onlyDotnetIsolatedentersUpdateNetFrameworkVersionWindows(viaUpdateDotNetIsolatedFrameworkVersion)NormalizeDotnetFrameworkVersion— returnsnullinstead of throwing when both inputs arenull(belt-and-suspenders)UpdateNetFrameworkVersionWindows— returns early ifnormalizedVersion == null(belt-and-suspenders)DotnetIsolatedLinuxValidation— same null guard added for consistency (belt-and-suspenders)Issue describing the changes in this PR
resolves #4822
Pull request checklist
release_notes.mdAdditional information
Unit tests cover all four affected runtimes (PowerShell, Node, Python, Java):
UpdateFrameworkVersions_NonDotnetWindowsApp_NoDotnetVersion_DoesNotCallUpdateWebSettings— verifies no web settings update occurs when no--dotnet-versionis specifiedUpdateFrameworkVersions_NonDotnetWindowsApp_ExplicitDotnetVersion_DoesNotUpdateWebSettings— verifies that even an explicit--dotnet-versionis correctly ignored for non-.NET runtimesUpdateFrameworkVersions_NonDotnetLinuxApp_NoDotnetVersion_DoesNotThrow— verifies the Linux non-.NET path is also safeOriginal prompt
✨ Let Copilot coding agent set things up for you — coding agent works faster and does higher quality work when set up for your repo.