web-dev-qa-db-ja.com

Wi-Fi IPアドレスを取得するAndroid

Wi-Fiで接続されている電話のIPアドレスを取得するにはどうすればよいですか?

メソッドを見つけました here しかし、wifiの下にいて、192.168.1.10のようなものを期待していても、24.182.239.255のようなものを返します。

次のようなものが欲しい:

if (you are under wifi)
    String ip4 = getWifiIP()
else
    String ip4 = getIPAddress with the method linked before

どうもありがとう!

39
Luigi Tiburzi

Wi-Fiに接続したときにデバイスのプライベートIPアドレスを取得したい場合は、これを試すことができます。

WifiManager wifiMgr = (WifiManager) getSystemService(WIFI_SERVICE);
WifiInfo wifiInfo = wifiMgr.getConnectionInfo();
int ip = wifiInfo.getIpAddress();
String ipAddress = Formatter.formatIpAddress(ip);

必ず許可を追加してください

<uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />

あなたのマニフェストに。

44
Siddharth N

考慮すべきことは、 Formatter.formatIpAddress(int) が非推奨になっていることです。

このメソッドはAPIレベル12で廃止されました。getHostAddress()を使用してください。これは、IPv4アドレスとIPv6アドレスの両方をサポートします。このメソッドはIPv6アドレスをサポートしません。

したがって、formatIpAddress(int)を使用することは、うまくいく可能性はありますが、長期的な解決策とは言えません。

WiFiインターフェイスのIPアドレスを絶対に取得しようとしている場合の解決策は次のとおりです。

_protected String wifiIpAddress(Context context) {
    WifiManager wifiManager = (WifiManager) context.getSystemService(WIFI_SERVICE);
    int ipAddress = wifiManager.getConnectionInfo().getIpAddress();

    // Convert little-endian to big-endianif needed
    if (ByteOrder.nativeOrder().equals(ByteOrder.LITTLE_ENDIAN)) {
        ipAddress = Integer.reverseBytes(ipAddress);
    }

    byte[] ipByteArray = BigInteger.valueOf(ipAddress).toByteArray();

    String ipAddressString;
    try {
        ipAddressString = InetAddress.getByAddress(ipByteArray).getHostAddress();
    } catch (UnknownHostException ex) {
        Log.e("WIFIIP", "Unable to get Host address.");
        ipAddressString = null;
    }

    return ipAddressString;
}
_

前の応答で述べたように、AndroidManifest.xmlで以下を設定する必要があります。

_<uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />
_

これはソリューションの例にすぎないことに注意してください。 UXがスムーズであることを確認するために、null値のチェックなどに時間をかける必要があります。

皮肉なことに、GoogleはformatIpAddress(int)を非推奨にしていますが、まだ getIpAddress() が整数値を返します。また、IPアドレスがintであるため、IPv6に準拠していることから除外されます。

次に、エンディアンが問題になる場合とそうでない場合があるという事実です。私がテストしたデバイスは3つだけで、それらはすべてリトルエンディアンです。 VMで実行している場合でも、エンディアンがハードウェアによって異なる可能性があるようです。これは依然として問題になる可能性があります。安全のために、コードにエンディアンチェックを追加しました。

getByAddress(byte []) は、整数値をビッグエンディアンにしたいようです。これを調査すると、ネットワークのバイト順序はビッグエンディアンであるように見えます。 192.168.12.22のようなアドレスはビッグエンディアンの数字なので、意味があります。


HammerNet GitHubプロジェクトをご覧ください。多数の健全性チェック、AVDのデフォルトを処理する機能、単体テストなどとともに上記のコードを実装します。私は自分のアプリにこれを実装しなければならず、ライブラリをオープンソース化することにしました。

71
pedrohdz

これにより、WiFi IPv4、IPv6、またはその両方が取得されます。

public static Enumeration<InetAddress> getWifiInetAddresses(final Context context) {
    final WifiManager wifiManager = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
    final WifiInfo wifiInfo = wifiManager.getConnectionInfo();
    final String macAddress = wifiInfo.getMacAddress();
    final String[] macParts = macAddress.split(":");
    final byte[] macBytes = new byte[macParts.length];
    for (int i = 0; i< macParts.length; i++) {
        macBytes[i] = (byte)Integer.parseInt(macParts[i], 16);
    }
    try {
        final Enumeration<NetworkInterface> e =  NetworkInterface.getNetworkInterfaces();
        while (e.hasMoreElements()) {
            final NetworkInterface networkInterface = e.nextElement();
            if (Arrays.equals(networkInterface.getHardwareAddress(), macBytes)) {
                return networkInterface.getInetAddresses();
            }
        }
    } catch (SocketException e) {
        Log.wtf("WIFIIP", "Unable to NetworkInterface.getNetworkInterfaces()");
    }
    return null;
}

@SuppressWarnings("unchecked")
public static<T extends InetAddress> T getWifiInetAddress(final Context context, final Class<T> inetClass) {
    final Enumeration<InetAddress> e = getWifiInetAddresses(context);
    while (e.hasMoreElements()) {
        final InetAddress inetAddress = e.nextElement();
        if (inetAddress.getClass() == inetClass) {
            return (T)inetAddress;
        }
    }
    return null;
}

使用法:

final Inet4Address inet4Address = getWifiInetAddress(context, Inet4Address.class);
final Inet6Address inet6Address = getWifiInetAddress(context, Inet6Address.class);

そして忘れないでください:

<uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />
8
Dustin

クラッシュログに基づいて、すべてのデバイスがWiFi MACアドレスを返すわけではないようです。

最も人気のある返信のクリーンバージョンです。

final WifiManager wifiManager = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
final ByteBuffer byteBuffer = ByteBuffer.allocate(4);
byteBuffer.order(ByteOrder.LITTLE_ENDIAN);
byteBuffer.putInt(wifiInfo.getIpAddress());
try {
final InetAddress inetAddress = InetAddress.getByAddress(null, byteBuffer.array());
} catch (UnknownHostException e) {
    //TODO: Return null?
}
2
Dustin

Adbがターミナルにインストールされている場合は、次を実行します。

Runtime.getRuntime.exec("adb", "Shell", "getprop", "dhcp.wlan0.ipaddress");
1
Thejus Krishna

この素敵な答えを見つけました https://Gist.github.com/stickupkid/12507

WifiManager wifiManager = (WifiManager) getSystemService(WIFI_SERVICE);
WifiInfo wifiInfo = wifiManager.getConnectionInfo();
int ipAddress = wifiInfo.getIpAddress();
String ipString = String.format(“%d.%d.%d.%d”, (ip & 0xff), (ip >> 8 & 0xff), (ip >> 16 & 0xff), (ip >> 24 & 0xff));
1
ElliotM

次の許可を追加します。

 <uses-permission Android:name="Android.permission.ACCESS_WIFI_STATE" />

WifiManagerはonCreateで初期化します。

 WifiManager wifiMgr = (WifiManager) getContext().getSystemService(context.WIFI_SERVICE);

以下の機能を使用してください。

 public void WI-FI_IP() {
    WifiInfo wifiInfo = wifiMgr.getConnectionInfo();
    int ip = wifiInfo.getIpAddress();
    String ipAddress = Formatter.formatIpAddress(ip);
    }
0
Quantum4U

次のコードは、AOSP設定からのものです。 Wi-Fiやモバイルに関係なく、アクティブリンクのIPを取得します。最も一般的な方法です。

http://androidxref.com/8.0.0_r4/xref/packages/apps/Settings/src/com/Android/settings/deviceinfo/Status.Java#251

/**  
 * Returns the default link's IP addresses, if any, taking into account IPv4 and IPv6 style
 * addresses.
 * @param context the application context
 * @return the formatted and newline-separated IP addresses, or null if none.
 */
public static String getDefaultIpAddresses(ConnectivityManager cm) {                                                                      
    LinkProperties prop = cm.getActiveLinkProperties();
    return formatIpAddresses(prop);
}    

private static String formatIpAddresses(LinkProperties prop) {
    if (prop == null) return null;
    Iterator<InetAddress> iter = prop.getAllAddresses().iterator();
    // If there are no entries, return null
    if (!iter.hasNext()) return null;
    // Concatenate all available addresses, comma separated
    String addresses = "";
    while (iter.hasNext()) {
        addresses += iter.next().getHostAddress();
        if (iter.hasNext()) addresses += "\n";
    }
    return addresses;
}
0
Yong