c# - ¿Cómo obtener una lista de las computadoras de la red local?
c++ winapi (5)
Estoy tratando de obtener una lista de las computadoras de la red local. Traté de utilizar NetServerEnum
y WNetOpenEnum
API, pero ambas API devuelven el código de error 6118 (ERROR_NO_BROWSER_SERVERS_FOUND)
. Active Directory en la red local no se usa.
Lo más extraño de Windows Explorer muestra todas las computadoras locales sin ningún problema.
¿Hay otras maneras de obtener una lista de computadoras en la LAN?
Hice una función de eso. SchemaClassName
tiene que ser una computadora
public List<string> NetworkComputers()
{
return (
from Computers
in (new DirectoryEntry("WinNT:")).Children
from Computer
in Computers.Children
where Computer.SchemaClassName == "Computer"
orderby Computer.Name
select Computer.Name).ToList;
}
Encontré una solución usando la interfaz IShellItem con CSIDL_NETWORK. Tengo todas las PC de red.
C ++: use el método IShellFolder :: EnumObjects
C #: puede usar Gong Solutions Shell Library
using System.Collections;
using System.Collections.Generic;
using GongSolutions.Shell;
using GongSolutions.Shell.Interop;
public sealed class ShellNetworkComputers : IEnumerable<string>
{
public IEnumerator<string> GetEnumerator()
{
ShellItem folder = new ShellItem((Environment.SpecialFolder)CSIDL.NETWORK);
IEnumerator<ShellItem> e = folder.GetEnumerator(SHCONTF.FOLDERS);
while (e.MoveNext())
{
Debug.Print(e.Current.ParsingName);
yield return e.Current.ParsingName;
}
}
IEnumerator IEnumerable.GetEnumerator()
{
return GetEnumerator();
}
}
Use el espacio de nombres System.DirectoryService y pruebe lo siguiente
DirectoryEntry root = new DirectoryEntry("WinNT:");
foreach (DirectoryEntry computers in root.Children)
{
foreach (DirectoryEntry computer in computers.Children)
{
if (computer.Name != "Schema")
{
textBox1.Text += computer.Name + "/r/n";
}
}
}
Funcionó para mí
Una extensión menor a la respuesta de toddmo, si realmente no le gusta la sintaxis de estilo de consulta LINQ y desea incluir también grupos de trabajo como una opción:
public IEnumerable<string> VisibleComputers(bool workgroupOnly = false) {
Func<string, IEnumerable<DirectoryEntry>> immediateChildren = key => new DirectoryEntry("WinNT:" + key)
.Children
.Cast<DirectoryEntry>();
Func<IEnumerable<DirectoryEntry>, IEnumerable<string>> qualifyAndSelect = entries => entries.Where(c => c.SchemaClassName == "Computer")
.Select(c => c.Name);
return (
!workgroupOnly ?
qualifyAndSelect(immediateChildren(String.Empty)
.SelectMany(d => d.Children.Cast<DirectoryEntry>()))
:
qualifyAndSelect(immediateChildren("//WORKGROUP"))
).ToArray();
}
Aquí una propiedad que utiliza una consulta LINQ
private List<string> NetworkHosts
{
get
{
var result = new List<string>();
var root = new DirectoryEntry("WinNT:");
foreach (DirectoryEntry computers in root.Children)
{
result.AddRange(from DirectoryEntry computer in computers.Children where computer.Name != "Schema" select computer.Name);
}
return result;
}
}