如何使用Indy获取本地IP4地址?

问题描述:

我正在使用TIdStack.LocalAddress获取本地IP地址。在具有IP6和IP4的OS X系统上,这将返回IP6地址,这不是我想要的。如何使用Indy获取本地IP4地址?

寻找本地IP4地址的最佳方式是什么?例如,我可以简单地使用TIdStack.LocalAddresses中的最短条目。

+0

的计算机可以具有许多_ “本地地址” 的_。如果你只是想要_any_,你可以采取最短的时间,并检查它有四点。 – jachguate 2013-02-25 17:49:44

TIdStack.LocalAddress属性只是返回TIdStack.LocalAddresses属性中列出的第一个IP(注意 - 这些属性由于它们不是线程安全的而不推荐使用,您应该使用TIdStack.AddLocalAddressesToList()方法)。 PC /设备可以有多个本地IP,例如连接到多个网络,同时支持IPv4和IPv6等。LocalAddresses列表中IP的顺序由操作系统决定,而不是由Indy决定。从它的声音,你将不得不获得完整的列表,并通过它寻找你感兴趣的IPv4地址。

TIdStackVCLPosix,Indy用于Mac OSX,实际上是唯一的TIdStack实现,目前支持报告LocalAddresses属性中的IPv4和IPv6地址(其他TIdStack实现此时仅支持IPv4)。但是,该列表是普通的TStrings,它不区分给定的IP是IPv4还是IPv6(它不使用TStrings.Objects属性来提供该信息)。如果您需要区分,则必须手动解析IP。在未来的版本中,Indy将用本地提供IP版本信息的不同实现替换TIdStack.LocalAddress(es)属性。

例如:

var 
    IPs: TStringList; 
    IP: String; 
    I: Integer; 
    Err: Boolean; 
begin 
    IPs := TStringList.Create; 
    try 
    GStack.AddLocalAddressesToList(IPs); 
    for I := 0 to IPs.Count-1 do 
    begin 
     IP := IPs[I]; 

     // TIdStack.IsIP() currently only supports IPv4, but 
     // it will be updated to support IPv6 in a future 
     // release... 
     // 
     // if GStack.IsIP(IP) then 
     // if GStack.IsIPv4(IP) then 

     IPv4ToDWord(IP, Err); 
     if not Err then 
     Break; 
     IP := ''; 

     // alternatively: 
     { 
     IPAddr := TIdIPAddress.MakeAddressObject(IPs[I]); 
     IP := IPAddr.IPv4AsString; // returns blank if not IPv4 
     IPAddr.Free; 
     if IP <> '' then 
     Break; 
     } 
    end; 
    finally 
    IPs.Free; 
    end; 
    if IP <> '' then 
    begin 
    // use IP as needed... 
    end; 
end;