implemented evaluation of ip addresses
This commit is contained in:
parent
b393146e58
commit
cf924f7b2a
13
.idea/.idea.SddpViewer/.idea/.gitignore
generated
vendored
Normal file
13
.idea/.idea.SddpViewer/.idea/.gitignore
generated
vendored
Normal file
@ -0,0 +1,13 @@
|
||||
# Default ignored files
|
||||
/shelf/
|
||||
/workspace.xml
|
||||
# Rider ignored files
|
||||
/modules.xml
|
||||
/projectSettingsUpdater.xml
|
||||
/.idea.SddpViewer.iml
|
||||
/contentModel.xml
|
||||
# Editor-based HTTP Client requests
|
||||
/httpRequests/
|
||||
# Datasource local storage ignored files
|
||||
/dataSources/
|
||||
/dataSources.local.xml
|
10
.idea/.idea.SddpViewer/.idea/avalonia.xml
generated
Normal file
10
.idea/.idea.SddpViewer/.idea/avalonia.xml
generated
Normal file
@ -0,0 +1,10 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="AvaloniaProject">
|
||||
<option name="projectPerEditor">
|
||||
<map>
|
||||
<entry key="MainWindow.axaml" value="SddpViewer.csproj" />
|
||||
</map>
|
||||
</option>
|
||||
</component>
|
||||
</project>
|
4
.idea/.idea.SddpViewer/.idea/encodings.xml
generated
Normal file
4
.idea/.idea.SddpViewer/.idea/encodings.xml
generated
Normal file
@ -0,0 +1,4 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="Encoding" addBOMForNewFiles="with BOM under Windows, with no BOM otherwise" />
|
||||
</project>
|
8
.idea/.idea.SddpViewer/.idea/indexLayout.xml
generated
Normal file
8
.idea/.idea.SddpViewer/.idea/indexLayout.xml
generated
Normal file
@ -0,0 +1,8 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="UserContentModel">
|
||||
<attachedFolders />
|
||||
<explicitIncludes />
|
||||
<explicitExcludes />
|
||||
</component>
|
||||
</project>
|
6
.idea/.idea.SddpViewer/.idea/vcs.xml
generated
Normal file
6
.idea/.idea.SddpViewer/.idea/vcs.xml
generated
Normal file
@ -0,0 +1,6 @@
|
||||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<project version="4">
|
||||
<component name="VcsDirectoryMappings">
|
||||
<mapping directory="$PROJECT_DIR$" vcs="Git" />
|
||||
</component>
|
||||
</project>
|
@ -20,4 +20,4 @@ public partial class App : Application
|
||||
|
||||
base.OnFrameworkInitializationCompleted();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,53 +1,53 @@
|
||||
namespace SddpViewer
|
||||
{
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
using System;
|
||||
using System.Threading.Tasks;
|
||||
|
||||
using CommunityToolkit.Mvvm.ComponentModel;
|
||||
using CommunityToolkit.Mvvm.ComponentModel;
|
||||
|
||||
using Rssdp;
|
||||
using Rssdp;
|
||||
|
||||
public partial class DiscoveredDeviceViewModel : ObservableObject
|
||||
{
|
||||
private readonly DiscoveredSsdpDevice device;
|
||||
|
||||
public DiscoveredDeviceViewModel(DiscoveredSsdpDevice device)
|
||||
public partial class DiscoveredDeviceViewModel : ObservableObject
|
||||
{
|
||||
this.device = device;
|
||||
private readonly DiscoveredSsdpDevice device;
|
||||
|
||||
public DiscoveredDeviceViewModel(DiscoveredSsdpDevice device)
|
||||
{
|
||||
this.device = device;
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the type of notification, being either a uuid, device type, service type or upnp:rootdevice.
|
||||
/// </summary>
|
||||
public string NotificationType => this.device.NotificationType;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the universal service name (USN) of the device.
|
||||
/// </summary>
|
||||
public string Usn => this.device.Usn;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns a URL pointing to the device description document for this device.
|
||||
/// </summary>
|
||||
public Uri DescriptionLocation => this.device.DescriptionLocation;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the length of time this information is valid for (from the <see cref="P:Rssdp.DiscoveredSsdpDevice.AsAt" /> time).
|
||||
/// </summary>
|
||||
public TimeSpan CacheLifetime => this.device.CacheLifetime;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the date and time this information was received.
|
||||
/// </summary>
|
||||
public DateTimeOffset AsAt => this.device.AsAt;
|
||||
|
||||
[ObservableProperty]
|
||||
private string _friendlyName = "";
|
||||
|
||||
public async Task GetFurtherInformationAsync()
|
||||
{
|
||||
var ssdpDevice = await this.device.GetDeviceInfo().ConfigureAwait(false);
|
||||
FriendlyName = ssdpDevice.FriendlyName;
|
||||
}
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the type of notification, being either a uuid, device type, service type or upnp:rootdevice.
|
||||
/// </summary>
|
||||
public string NotificationType => this.device.NotificationType;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the universal service name (USN) of the device.
|
||||
/// </summary>
|
||||
public string Usn => this.device.Usn;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns a URL pointing to the device description document for this device.
|
||||
/// </summary>
|
||||
public Uri DescriptionLocation => this.device.DescriptionLocation;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the length of time this information is valid for (from the <see cref="P:Rssdp.DiscoveredSsdpDevice.AsAt" /> time).
|
||||
/// </summary>
|
||||
public TimeSpan CacheLifetime => this.device.CacheLifetime;
|
||||
|
||||
/// <summary>
|
||||
/// Sets or returns the date and time this information was received.
|
||||
/// </summary>
|
||||
public DateTimeOffset AsAt => this.device.AsAt;
|
||||
|
||||
[ObservableProperty]
|
||||
private string _friendlyName = "";
|
||||
|
||||
public async Task GetFurtherInformationAsync()
|
||||
{
|
||||
var ssdpDevice = await this.device.GetDeviceInfo().ConfigureAwait(false);
|
||||
FriendlyName = ssdpDevice.FriendlyName;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,35 +1,34 @@
|
||||
<Window
|
||||
x:Class="SddpViewer.MainWindow"
|
||||
xmlns="https://github.com/avaloniaui"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
|
||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:sddpViewer="clr-namespace:SddpViewer"
|
||||
Title="SDDP viewer"
|
||||
d:DesignHeight="450"
|
||||
d:DesignWidth="800"
|
||||
mc:Ignorable="d"
|
||||
x:Class="SddpViewer.MainWindow"
|
||||
x:CompileBindings="True"
|
||||
x:DataType="sddpViewer:MainWindowViewModel"
|
||||
mc:Ignorable="d">
|
||||
xmlns="https://github.com/avaloniaui"
|
||||
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:sddpViewer="clr-namespace:SddpViewer"
|
||||
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml">
|
||||
<Window.DataContext>
|
||||
<sddpViewer:MainWindowViewModel />
|
||||
</Window.DataContext>
|
||||
<Grid RowDefinitions="Auto, *">
|
||||
<StackPanel Margin="10" Spacing="5">
|
||||
<TextBlock Text="Settings" />
|
||||
<TextBox
|
||||
Text="{Binding DeviceIpAddress}"
|
||||
UseFloatingWatermark="True"
|
||||
Watermark="Device IP Address" />
|
||||
<TextBox
|
||||
Text="{Binding NotificationFilter}"
|
||||
UseFloatingWatermark="True"
|
||||
Watermark="Notification filter" />
|
||||
<TextBlock Text="Device IP Address" />
|
||||
<ComboBox
|
||||
DisplayMemberBinding="{Binding DisplayName}"
|
||||
HorizontalAlignment="Stretch"
|
||||
ItemsSource="{Binding NetworkAdapters}"
|
||||
SelectedItem="{Binding SelectedNetworkAdapter}" />
|
||||
<TextBlock Text="Notification filter" />
|
||||
<TextBox Text="{Binding NotificationFilter}" />
|
||||
<Button Command="{Binding SearchDevicesNowCommand}" Content="Search now" />
|
||||
</StackPanel>
|
||||
<DataGrid
|
||||
Grid.Row="1"
|
||||
AutoGenerateColumns="True"
|
||||
Grid.Row="1"
|
||||
IsReadOnly="True"
|
||||
ItemsSource="{Binding SddpDevices}" />
|
||||
</Grid>
|
||||
|
@ -8,4 +8,4 @@ public partial class MainWindow : Window
|
||||
{
|
||||
InitializeComponent();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -1,4 +1,10 @@
|
||||
namespace SddpViewer;
|
||||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net.NetworkInformation;
|
||||
using System.Net.Sockets;
|
||||
|
||||
namespace SddpViewer;
|
||||
|
||||
using System.Collections.ObjectModel;
|
||||
using System.Threading.Tasks;
|
||||
@ -10,35 +16,53 @@ using Rssdp;
|
||||
|
||||
public partial class MainWindowViewModel : ObservableObject
|
||||
{
|
||||
[ObservableProperty]
|
||||
private string _deviceIpAddress = "192.168.42.193";
|
||||
|
||||
[ObservableProperty]
|
||||
private string _notificationFilter = "upnp:rootdevice";
|
||||
|
||||
public ObservableCollection<DiscoveredDeviceViewModel> SddpDevices { get; } = new();
|
||||
|
||||
[RelayCommand(AllowConcurrentExecutions = false)]
|
||||
private async Task SearchDevicesNowAsync()
|
||||
{
|
||||
SddpDevices.Clear();
|
||||
var locator = new SsdpDeviceLocator(DeviceIpAddress);
|
||||
if (!string.IsNullOrWhiteSpace(NotificationFilter))
|
||||
public MainWindowViewModel()
|
||||
{
|
||||
locator.NotificationFilter = NotificationFilter;
|
||||
NetworkAdapters = NetworkAdapter.GetAvailableNetworkAdapter().ToArray();
|
||||
SelectedNetworkAdapter = NetworkAdapters.FirstOrDefault();
|
||||
}
|
||||
var availableDevices = await locator.SearchAsync().ConfigureAwait(true);
|
||||
foreach (var ssdpDevice in availableDevices)
|
||||
|
||||
[ObservableProperty]
|
||||
private IReadOnlyList<NetworkAdapter> _networkAdapters;
|
||||
|
||||
[ObservableProperty]
|
||||
private NetworkAdapter? _selectedNetworkAdapter;
|
||||
|
||||
[ObservableProperty]
|
||||
private string _deviceIpAddress = "192.168.42.193";
|
||||
|
||||
[ObservableProperty]
|
||||
private string _notificationFilter = "upnp:rootdevice";
|
||||
|
||||
public ObservableCollection<DiscoveredDeviceViewModel> SddpDevices { get; } = new();
|
||||
|
||||
[RelayCommand(AllowConcurrentExecutions = false)]
|
||||
private async Task SearchDevicesNowAsync()
|
||||
{
|
||||
var discoveredDeviceViewModel = new DiscoveredDeviceViewModel(ssdpDevice);
|
||||
SddpDevices.Add(discoveredDeviceViewModel);
|
||||
SddpDevices.Clear();
|
||||
if (SelectedNetworkAdapter is null)
|
||||
{
|
||||
throw new NotSupportedException();
|
||||
}
|
||||
var locator = new SsdpDeviceLocator(SelectedNetworkAdapter.IpAddress.ToString());
|
||||
if (!string.IsNullOrWhiteSpace(NotificationFilter))
|
||||
{
|
||||
locator.NotificationFilter = NotificationFilter;
|
||||
}
|
||||
var availableDevices = await locator.SearchAsync().ConfigureAwait(true);
|
||||
foreach (var ssdpDevice in availableDevices)
|
||||
{
|
||||
var discoveredDeviceViewModel = new DiscoveredDeviceViewModel(ssdpDevice);
|
||||
SddpDevices.Add(discoveredDeviceViewModel);
|
||||
}
|
||||
await Parallel
|
||||
.ForEachAsync(
|
||||
SddpDevices,
|
||||
async (device, token) =>
|
||||
{
|
||||
await device.GetFurtherInformationAsync().ConfigureAwait(true);
|
||||
}
|
||||
)
|
||||
.ConfigureAwait(true);
|
||||
}
|
||||
await Parallel.ForEachAsync(
|
||||
SddpDevices,
|
||||
async (device, token) =>
|
||||
{
|
||||
await device.GetFurtherInformationAsync().ConfigureAwait(true);
|
||||
}
|
||||
).ConfigureAwait(true);
|
||||
}
|
||||
}
|
||||
|
31
NetworkAdapter.cs
Normal file
31
NetworkAdapter.cs
Normal file
@ -0,0 +1,31 @@
|
||||
using System.Collections.Generic;
|
||||
using System.Linq;
|
||||
using System.Net;
|
||||
using System.Net.NetworkInformation;
|
||||
using System.Net.Sockets;
|
||||
|
||||
namespace SddpViewer;
|
||||
|
||||
public record NetworkAdapter(string Name, IPAddress IpAddress)
|
||||
{
|
||||
public string DisplayName => $"{Name} - {IpAddress}";
|
||||
|
||||
public static IEnumerable<NetworkAdapter> GetAvailableNetworkAdapter()
|
||||
{
|
||||
foreach (var nic in NetworkInterface.GetAllNetworkInterfaces())
|
||||
{
|
||||
if (nic.OperationalStatus != OperationalStatus.Up)
|
||||
continue;
|
||||
if (nic.NetworkInterfaceType == NetworkInterfaceType.Loopback)
|
||||
continue;
|
||||
var physicalAddress = nic.GetIPProperties()
|
||||
.UnicastAddresses.FirstOrDefault(
|
||||
x => x.Address.AddressFamily == AddressFamily.InterNetwork
|
||||
);
|
||||
if (physicalAddress is not null)
|
||||
{
|
||||
yield return new NetworkAdapter(nic.Name, physicalAddress.Address);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
11
Program.cs
11
Program.cs
@ -9,13 +9,10 @@ class Program
|
||||
// SynchronizationContext-reliant code before AppMain is called: things aren't initialized
|
||||
// yet and stuff might break.
|
||||
[STAThread]
|
||||
public static void Main(string[] args) => BuildAvaloniaApp()
|
||||
.StartWithClassicDesktopLifetime(args);
|
||||
public static void Main(string[] args) =>
|
||||
BuildAvaloniaApp().StartWithClassicDesktopLifetime(args);
|
||||
|
||||
// Avalonia configuration, don't remove; also used by visual designer.
|
||||
public static AppBuilder BuildAvaloniaApp()
|
||||
=> AppBuilder.Configure<App>()
|
||||
.UsePlatformDetect()
|
||||
.WithInterFont()
|
||||
.LogToTrace();
|
||||
public static AppBuilder BuildAvaloniaApp() =>
|
||||
AppBuilder.Configure<App>().UsePlatformDetect().WithInterFont().LogToTrace();
|
||||
}
|
||||
|
Loading…
x
Reference in New Issue
Block a user