2016-10-20 9 views
12

Android 6で静的IPとゲートウェイをプログラムで設定する方法を教えてもらえますか?Android 6.x(Marshmallow)で静的IPとゲートウェイをプログラムで設定する

私はherehereを読みました。

Settings.Systemは、APIレベル17では廃止されましたが、代わりにWifiMangerを使用します。WIFI_STATIC_IPは廃止されました。残念ながら私はそれについてWifiMangerWifiConfigurationクラスで何も見つけることができません。

+0

、なぜこれがhttps://stackoverflow.com/questions/10278461/how-to-configue-a-static-ip-address-netmask-gateway-programmatically異なります - アンドロイド? – Fabio

+0

@Fabioあなたがデバイスの所有者を設定しない限り、参照された例の提案は機能しません。 – Knubo

答えて

7

公式のAPIはありませんので、次のサンプルをcode snipetthis answerに変更して解決策を考えなければなりません。このソリューションは、Lollipopのデバイス上で動作します。

@SuppressWarnings("unchecked") 
public static void setStaticIpConfiguration(WifiManager manager, WifiConfiguration config, InetAddress ipAddress, int prefixLength, InetAddress gateway, InetAddress[] dns) throws ClassNotFoundException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException, NoSuchFieldException, InstantiationException { 
     // First set up IpAssignment to STATIC. 
     Object ipAssignment = getEnumValue("android.net.IpConfiguration$IpAssignment", "STATIC"); 
     callMethod(config, "setIpAssignment", new String[]{"android.net.IpConfiguration$IpAssignment"}, new Object[]{ipAssignment}); 

     // Then set properties in StaticIpConfiguration. 
     Object staticIpConfig = newInstance("android.net.StaticIpConfiguration"); 
     Object linkAddress = newInstance("android.net.LinkAddress", new Class<?>[]{InetAddress.class, int.class}, new Object[]{ipAddress, prefixLength}); 

     setField(staticIpConfig, "ipAddress", linkAddress); 
     setField(staticIpConfig, "gateway", gateway); 
     getField(staticIpConfig, "dnsServers", ArrayList.class).clear(); 
     for (int i = 0; i < dns.length; i++) 
      getField(staticIpConfig, "dnsServers", ArrayList.class).add(dns[i]); 

     callMethod(config, "setStaticIpConfiguration", new String[]{"android.net.StaticIpConfiguration"}, new Object[]{staticIpConfig}); 

     int netId = manager.updateNetwork(config); 
     boolean result = netId != -1; 
     if (result) { 
      boolean isDisconnected = manager.disconnect(); 
      boolean configSaved = manager.saveConfiguration(); 
      boolean isEnabled = manager.enableNetwork(config.networkId, true); 
      boolean isReconnected = manager.reconnect(); 
     } 
    } 

ヘルパー機能、

public static WifiConfiguration getCurrentWiFiConfiguration(Context context) { 
      WifiConfiguration wifiConf = null; 
      ConnectivityManager connManager = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE); 
      NetworkInfo networkInfo = connManager.getNetworkInfo(ConnectivityManager.TYPE_WIFI); 
      if (networkInfo.isConnected()) { 
       final WifiManager wifiManager = (WifiManager) context.getSystemService(Context.WIFI_SERVICE); 
       final WifiInfo connectionInfo = wifiManager.getConnectionInfo(); 
       if (connectionInfo != null && !TextUtils.isEmpty(connectionInfo.getSSID())) { 
        List<WifiConfiguration> configuredNetworks = wifiManager.getConfiguredNetworks(); 
        if (configuredNetworks != null) { 
         for (WifiConfiguration conf : configuredNetworks) { 
          if (conf.networkId == connectionInfo.getNetworkId()) { 
           wifiConf = conf; 
           break; 
          } 
         } 
        } 
       } 
      } 
      return wifiConf; 
     } 

private static Object newInstance(String className) throws ClassNotFoundException, InstantiationException, IllegalAccessException, NoSuchMethodException, IllegalArgumentException, InvocationTargetException { 
     return newInstance(className, new Class<?>[0], new Object[0]); 
    } 

    private static Object newInstance(String className, Class<?>[] parameterClasses, Object[] parameterValues) throws NoSuchMethodException, InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, ClassNotFoundException { 
     Class<?> clz = Class.forName(className); 
     Constructor<?> constructor = clz.getConstructor(parameterClasses); 
     return constructor.newInstance(parameterValues); 
    } 

    @SuppressWarnings({"unchecked", "rawtypes"}) 
    private static Object getEnumValue(String enumClassName, String enumValue) throws ClassNotFoundException { 
     Class<Enum> enumClz = (Class<Enum>) Class.forName(enumClassName); 
     return Enum.valueOf(enumClz, enumValue); 
    } 

    private static void setField(Object object, String fieldName, Object value) throws IllegalAccessException, IllegalArgumentException, NoSuchFieldException { 
     Field field = object.getClass().getDeclaredField(fieldName); 
     field.set(object, value); 
    } 

    private static <T> T getField(Object object, String fieldName, Class<T> type) throws IllegalAccessException, IllegalArgumentException, NoSuchFieldException { 
     Field field = object.getClass().getDeclaredField(fieldName); 
     return type.cast(field.get(object)); 
    } 

    private static void callMethod(Object object, String methodName, String[] parameterTypes, Object[] parameterValues) throws ClassNotFoundException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException { 
     Class<?>[] parameterClasses = new Class<?>[parameterTypes.length]; 
     for (int i = 0; i < parameterTypes.length; i++) 
      parameterClasses[i] = Class.forName(parameterTypes[i]); 

     Method method = object.getClass().getDeclaredMethod(methodName, parameterClasses); 
     method.invoke(object, parameterValues); 
    } 

それを使用するには、

WifiManager wifiManager = (WifiManager) getApplicationContext().getSystemService(Context.WIFI_SERVICE); 
WifiConfiguration wifiConf = WifiHelper.getCurrentWiFiConfiguration(getApplicationContext()); 

     try { 
      setStaticIpConfiguration(wifiManager, wifiConf, 
        InetAddress.getByName("192.168.0.100"), 
        24, 
        InetAddress.getByName("10.0.0.2"), 
        new InetAddress[]{InetAddress.getByName("10.0.0.3"), InetAddress.getByName("10.0.0.4")}); 

     } catch (Exception e) { 
      e.printStackTrace(); 
     } 

最後にあなたは私が正常に追加されている

<uses-permission android:name="android.permission.ACCESS_WIFI_STATE" /> 
    <uses-permission android:name="android.permission.ACCESS_NETWORK_STATE" /> 
    <uses-permission android:name="android.permission.CHANGE_WIFI_STATE" /> 
    <uses-permission android:name="android.permission.WRITE_SETTINGS" /> 
+0

私はアンドロイドAPIで作業していないので、誰かがそれをチェックして、それにダニをかけるよう教えてもらえますか? – Mogi

+0

@茂木それはどういう意味ですか?あなたはAPIで作業していませんか?あなたは何を使っていますか?ちょうどこのコードをあなたのアプリに追加してから、アプリを使用しようとしてください。あなたはそれが動作するかどうかを知るでしょう! – Yazan

+0

@ヤザンあなたはそれが間違っていることを理解しています:)私はアンドロイドでもう作業していないし、質問は2016年10月に尋ねられました!私は仕事を変えた。haha – Mogi

2

私はこの問題のいくつかを掘り下げましたが、アプリケーションがデバイス所有者に設定されている場合、Andrdoi 5.xで動作していたコードが動作する可能性があります。

ソリューション:

ソリューションはdeviceOwnerような装置を追加することです。これにより、Mogiが参照する5.xハックを使用して静的IPを設定することができます。これがどのように行われるかの良い例がここで見つけるの例を使用している:

https://github.com/googlesamples/android-DeviceOwner/

adbのシェルを使用してコマンドを実行している:

dpm set-device-owner com.example.android.deviceowner/.DeviceOwnerReceiver 

は、その仕事をするために許可することができる状態になります。

0

、マニフェストでこれらの権限を追加する必要があります開いてPSK neに接続する私のアプリではプログラムで(2つのデバイスが5.1と6.0を試してみました)。しかし、私はエンタープライズネットワークのためにこれをしようとしているときに動作しません。 addNetwork()が成功した(正のネットIDを返す)のがわかりましたが、設定 - > Wi-Fiを見ると、追加した他のSSIDの場合と同じようにSSIDは表示されません。誰がこれがなぜなのか分かりますか?プログラムでWiFiConfigurationリストを検索すると、SSIDが見つかります。ここで私が使用したコードは次のとおりです。

wifiConf = new WifiConfiguration(); 
wifiConf.SSID = "\"dot1x-test\""; 
wifiConf.BSSID = "c4:e9:84:43:48:e8"; 
if (android.os.Build.VERSION.SDK_INT >= Build.VERSION_CODES.JELLY_BEAN_MR2) { 
    wifiConf.enterpriseConfig.setIdentity("name"); 
    wifiConf.enterpriseConfig.setPassword("testpassword"); 
    wifiConf.enterpriseConfig.setEapMethod(WifiEnterpriseConfig.Eap.PEAP); 
    wifiConf.enterpriseConfig.setPhase2Method(WifiEnterpriseConfig.Phase2.MSCHAPV2); 
} 

netId = wifiMgr.addNetwork(wifiConf); 
wifiMgr.disconnect(); 
wifiMgr.enableNetwork(netId, true); 
wifiMgr.saveConfiguration(); 
wifiMgr.reconnect(); 
関連する問題