Computer >> บทช่วยสอนคอมพิวเตอร์ >  >> การเขียนโปรแกรม >> C#

วิธีดึง IP Address ใน C#

การดึง IP Address ใน C# มีหลายระดับ: Local Machine IP, Public IP, IPv4/IPv6

1. Local IP Address (LAN/IPv4)

using System;
using System.Net;
using System.Net.Sockets;
using System.Linq;

public static string GetLocalIPv4()
{
    string hostName = Dns.GetHostName(); // ชื่อเครื่อง
    IPHostEntry host = Dns.GetHostEntry(hostName);
    
    // หา IPv4 Address แรกที่ไม่ใช่ Loopback (127.0.0.1)
    foreach (IPAddress ip in host.AddressList)
    {
        if (ip.AddressFamily == AddressFamily.InterNetwork) // IPv4
        {
            return ip.ToString();
        }
    }
    return "No IPv4 found";
}

// ใช้งาน
Console.WriteLine(GetLocalIPv4()); // เช่น 192.168.1.100

2. ทุก IP Addresses (IPv4 + IPv6)

public static void PrintAllIPs()
{
    string hostName = Dns.GetHostName();
    IPHostEntry host = Dns.GetHostEntry(hostName);
    
    Console.WriteLine($"Host: {hostName}");
    foreach (IPAddress ip in host.AddressList)
    {
        Console.WriteLine($"  {ip.AddressFamily}: {ip}");
    }
}

/* Output:
Host: MY-PC
  InterNetworkV6: ::1
  InterNetworkV6: fe80::...
  InterNetwork: 192.168.1.100
  InterNetwork: 172.16.0.5 (Docker/Hyper-V)
*/

3. Public IP Address (External IP)

ต้องเรียก External Service เนื่องจากเครื่องอยู่หลัง NAT/Router

using System.Net.Http;

public static async Task GetPublicIPAsync()
{
    using var httpClient = new HttpClient();
    httpClient.Timeout = TimeSpan.FromSeconds(5);
    
    try
    {
        // ใช้ Service ฟรี (มี Rate Limits)
        string ip = await httpClient.GetStringAsync("https://api.ipify.org");
        // หรือ https://ifconfig.me/ip, https://icanhazip.com
        return ip.Trim();
    }
    catch (Exception ex)
    {
        return $"Error: {ex.Message}";
    }
}

// ใช้งาน
string publicIp = await GetPublicIPAsync();
Console.WriteLine($"Public IP: {publicIp}"); // เช่น 203.0.113.45

4. IP Address ของ Network Interface (Detail)

using System.Net.NetworkInformation;

public static void PrintNetworkInterfaces()
{
    foreach (NetworkInterface ni in NetworkInterface.GetAllNetworkInterfaces())
    {
        if (ni.OperationalStatus == OperationalStatus.Up && 
            ni.NetworkInterfaceType != NetworkInterfaceType.Loopback)
        {
            Console.WriteLine($"Interface: {ni.Name} ({ni.NetworkInterfaceType})");
            
            IPInterfaceProperties props = ni.GetIPProperties();
            foreach (UnicastIPAddressInformation ip in props.UnicastAddresses)
            {
                if (ip.Address.AddressFamily == AddressFamily.InterNetwork)
                {
                    Console.WriteLine($"  IPv4: {ip.Address} / Prefix: {ip.PrefixLength}");
                    Console.WriteLine($"  Gateway: {props.GatewayAddresses.FirstOrDefault()?.Address}");
                }
            }
        }
    }
}

5. ใน ASP.NET Core (Client IP)

// ใน Controller/Service
public IActionResult GetClientIp(HttpContext context)
{
    // รองรับ Reverse Proxy (Load Balancer, Nginx, Cloudflare)
    string ip = context.Connection.RemoteIpAddress?.ToString();
    
    // ถ้ามี Forwarded Headers
    if (context.Request.Headers.ContainsKey("X-Forwarded-For"))
    {
        ip = context.Request.Headers["X-Forwarded-For"].FirstOrDefault()?.Split(',')[0].Trim();
    }
    
    return Ok(new { ClientIP = ip });
}

// Startup.cs - Configure Forwarded Headers
app.UseForwardedHeaders(new ForwardedHeadersOptions
{
    ForwardedHeaders = ForwardedHeaders.XForwardedFor | ForwardedHeaders.XForwardedProto
});

ข้อควรระวัง

  • Dns.GetHostEntry อาจช้า (DNS Lookup) → Cache หรือ Async
  • หลาย Network Adapters (WiFi, Ethernet, VPN, Docker, WSL) → หลาย IPs
  • IPv6: AddressFamily.InterNetworkV6 รูปแบบต่างไป (fe80::, 2001:...)
  • Public IP Services มี Rate Limit → ควร Cache หรือใช้ Service ของตัวเอง
  • Container/Kubernetes: ใช้ HostNetwork หรือ Downward API สำหรับ Pod IP