NetObserver.Helper
2.0.0
dotnet add package NetObserver.Helper --version 2.0.0
NuGet\Install-Package NetObserver.Helper -Version 2.0.0
<PackageReference Include="NetObserver.Helper" Version="2.0.0" />
<PackageVersion Include="NetObserver.Helper" Version="2.0.0" />
<PackageReference Include="NetObserver.Helper" />
paket add NetObserver.Helper --version 2.0.0
#r "nuget: NetObserver.Helper, 2.0.0"
#:package NetObserver.Helper@2.0.0
#addin nuget:?package=NetObserver.Helper&version=2.0.0
#tool nuget:?package=NetObserver.Helper&version=2.0.0
Changelog
All notable changes to NetObserver are documented in this file. For the Russian version, see CHANGELOG.ru.md.
[2.0.0] — Bug fixes, retarget to .NET Standard 2.1, and internal cleanup
This release addresses a set of real bugs found in the original 1.1.3 codebase (netstandard2.0), reduces
duplicated code, and moves the target framework forward. The public API surface is backward compatible:
existing consumers calling LocalIp, DnsInfo, IcmpRequestSender(Async), PingClassic(Async),
Traceroute(Async), and the synchronous OpenPort.GetOpenPort(...) overloads should not need to change any
call sites. New async overloads were added additively.
Fixed
LocalIpaccumulated stale results across calls. The class usedprivate static List<...>fields that were never cleared. CallingGetIpv4Localhost()orGetAllIpv4NetInterface()more than once could return addresses left over from a previous call (and was not thread-safe). Rewritten to build a fresh, local list on every call — nothing is cached or shared between calls anymore.OpenPortcould leak a pending connection attempt on timeout. The original code used the legacyBeginConnect/EndConnectpattern and calledSocket.Close()on timeout without ever callingEndConnect, so a connection completing after the timeout could throw in the background after the socket was already disposed. Rewritten aroundTcpClient.ConnectAsync+Task.WhenAny, with the (possibly still pending) connect task's eventual exception explicitly observed, so it never surfaces as an unobserved task exception.- Lost stack traces when translating exceptions. Every ping/DNS/traceroute method re-threw caught
exceptions using
new SomeException(message, ex.InnerException)— passing the inner exception (frequentlynull) instead of the exception that was actually caught (ex). The original stack trace was discarded. Centralized intoCommon/ExceptionHelper, which always chains the true original exception, soException.InnerException/.ToString()now show the real failure point. - Misused
ArgumentNullException/ArgumentOutOfRangeExceptionconstructors in a few call sites (passing a human-readable message where the API expects a parameter name, or vice-versa) — fixed via the same helper. - Hardcoded, machine-local absolute path in
NetObserver.csproj(..\..\..\..\Users\Laise\Downloads\IconsPacket.png) pointed at the original author's localDownloadsfolder. Anyone else cloning the repository would fail to build the NuGet package (or silently lose the package icon). Fixed to referenceResources\IconsPacket.png, which already ships in the repository.
Changed
- Target framework:
netstandard2.0→netstandard2.1. EnableNETAnalyzersturned back on (it was explicitly disabled in the original project, which likely hid some of the issues above from the IDE/build).LocalIpandDnsInfoare nowstatic class(they only ever exposed static members; this prevents meaningless instantiation). Minor breaking change if any consumer didnew LocalIp()/new DnsInfo()— unlikely, since none of their members were instance members.Traceroute/TracerouteAsync: the_bufferfield is nowstatic readonlyinstead of a mutable instance field; the max-TTL default (previously inconsistently31inTraceroutevs.30inTracerouteAsync) is now30in both.- Reduced duplication:
IcmpRequestSender/IcmpRequestSenderAsync: the five nearly-identicalcatchblocks per overload were replaced by a single call intoCommon/ExceptionHelper.Traceroute/TracerouteAsync: the four public overloads now delegate to two private core methods (TraceRouteCore(Async)/DetailTraceRouteCore(Async)) instead of duplicating the hop-walking loop.LocalIp: four nearly-identical private methods collapsed into one, parameterized byPrefixOrigin.
Added
OpenPort.GetOpenPortAsync(...)— async, cancellable single-port and port-range scanning, with amaxConcurrencyparameter (default 200) that bounds how many ports are probed in parallel, instead of the original's fully sequential range scan (which could block for minutes on wide ranges).- XML doc comments clarified/expanded, including an explicit note on
GetDetailTraceRoute(Async)explaining why it sends a second, direct ping per hop (to get a normalPingReply— round-trip time, buffer, and aSuccessstatus — instead of exposing the rawTtlExpiredreply). This was flagged in review as possibly redundant, but removing it would have changed observable behavior (and broken the existingGetDetailTraceRouteTest, which assertsStatus == Successon every hop), so it was kept and documented instead of "fixed".
Compatibility note
netstandard2.1 is not supported by classic .NET Framework (4.x) — only .NET Core 3.0+, .NET 5+, and
recent Mono/Xamarin. If your consumers are still on .NET Framework, this release (and 3.0.0) are not
suitable; stay on 1.1.x or ask for a netstandard2.0 + netstandard2.1/net10.0 multi-target build.
[1.1.3] and earlier
Original releases by the upstream author, targeting netstandard2.0. See the project's GitHub history for
details predating this fork/rewrite.
| Product | Versions Compatible and additional computed target framework versions. |
|---|---|
| .NET | net5.0 was computed. net5.0-windows was computed. net6.0 was computed. net6.0-android was computed. net6.0-ios was computed. net6.0-maccatalyst was computed. net6.0-macos was computed. net6.0-tvos was computed. net6.0-windows was computed. net7.0 was computed. net7.0-android was computed. net7.0-ios was computed. net7.0-maccatalyst was computed. net7.0-macos was computed. net7.0-tvos was computed. net7.0-windows was computed. net8.0 was computed. net8.0-android was computed. net8.0-browser was computed. net8.0-ios was computed. net8.0-maccatalyst was computed. net8.0-macos was computed. net8.0-tvos was computed. net8.0-windows was computed. net9.0 was computed. net9.0-android was computed. net9.0-browser was computed. net9.0-ios was computed. net9.0-maccatalyst was computed. net9.0-macos was computed. net9.0-tvos was computed. net9.0-windows was computed. net10.0 was computed. net10.0-android was computed. net10.0-browser was computed. net10.0-ios was computed. net10.0-maccatalyst was computed. net10.0-macos was computed. net10.0-tvos was computed. net10.0-windows was computed. |
| .NET Core | netcoreapp3.0 was computed. netcoreapp3.1 was computed. |
| .NET Standard | netstandard2.1 is compatible. |
| MonoAndroid | monoandroid was computed. |
| MonoMac | monomac was computed. |
| MonoTouch | monotouch was computed. |
| Tizen | tizen60 was computed. |
| Xamarin.iOS | xamarinios was computed. |
| Xamarin.Mac | xamarinmac was computed. |
| Xamarin.TVOS | xamarintvos was computed. |
| Xamarin.WatchOS | xamarinwatchos was computed. |
-
.NETStandard 2.1
- No dependencies.
NuGet packages
This package is not used by any NuGet packages.
GitHub repositories
This package is not used by any popular GitHub repositories.
* Retarget to .NET Standard 2.1.
* Fix LocalIp accumulating stale results across calls (removed shared static state).
* Fix OpenPort leaking pending connection attempts on timeout; added async, cancellable, concurrency-limited port scanning.
* Preserve original stack traces when translating low-level exceptions.
* Removed a machine-local absolute path from the package icon reference.