Created
August 19, 2020 11:19
-
-
Save ShaileshPrajapati-BTC/eab72f70450e74cac1e65569b5a4ab84 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package com.devstepbcn.wifi; | |
import com.facebook.react.uimanager.*; | |
import com.facebook.react.bridge.*; | |
import com.facebook.systrace.Systrace; | |
import com.facebook.systrace.SystraceMessage; | |
import com.facebook.react.ReactInstanceManager; | |
import com.facebook.react.ReactRootView; | |
import com.facebook.react.modules.core.DefaultHardwareBackBtnHandler; | |
import com.facebook.react.modules.core.DeviceEventManagerModule; | |
import com.facebook.react.shell.MainReactPackage; | |
import com.facebook.soloader.SoLoader; | |
import android.provider.Settings; | |
import android.net.wifi.ScanResult; | |
import android.net.wifi.WifiManager; | |
import android.net.wifi.WifiConfiguration; | |
import android.net.ConnectivityManager; | |
import android.net.NetworkInfo; | |
import android.net.NetworkRequest; | |
import android.net.NetworkCapabilities; | |
import android.net.Network; | |
import android.net.Uri; | |
import android.net.wifi.WifiInfo; | |
import android.content.Context; | |
import android.content.Intent; | |
import android.content.IntentFilter; | |
import android.content.BroadcastReceiver; | |
import android.os.Build; | |
import android.os.Bundle; | |
import android.widget.Toast; | |
import java.util.List; | |
import java.lang.Thread; | |
import android.net.DhcpInfo; | |
import org.json.JSONArray; | |
import org.json.JSONException; | |
import org.json.JSONObject; | |
public class AndroidWifiModule extends ReactContextBaseJavaModule { | |
//WifiManager Instance | |
WifiManager wifi; | |
ReactApplicationContext reactContext; | |
//Constructor | |
public AndroidWifiModule(ReactApplicationContext reactContext) { | |
super(reactContext); | |
wifi = (WifiManager)reactContext.getSystemService(Context.WIFI_SERVICE); | |
this.reactContext = reactContext; | |
} | |
//Name for module register to use: | |
@Override | |
public String getName() { | |
return "AndroidWifiModule"; | |
} | |
//Method to load wifi list into string via Callback. Returns a stringified JSONArray | |
@ReactMethod | |
public void loadWifiList(Callback successCallback, Callback errorCallback) { | |
try { | |
List < ScanResult > results = wifi.getScanResults(); | |
JSONArray wifiArray = new JSONArray(); | |
for (ScanResult result: results) { | |
JSONObject wifiObject = new JSONObject(); | |
if(!result.SSID.equals("")){ | |
try { | |
wifiObject.put("SSID", result.SSID); | |
wifiObject.put("BSSID", result.BSSID); | |
wifiObject.put("capabilities", result.capabilities); | |
wifiObject.put("frequency", result.frequency); | |
wifiObject.put("level", result.level); | |
wifiObject.put("timestamp", result.timestamp); | |
//Other fields not added | |
//wifiObject.put("operatorFriendlyName", result.operatorFriendlyName); | |
//wifiObject.put("venueName", result.venueName); | |
//wifiObject.put("centerFreq0", result.centerFreq0); | |
//wifiObject.put("centerFreq1", result.centerFreq1); | |
//wifiObject.put("channelWidth", result.channelWidth); | |
} catch (JSONException e) { | |
errorCallback.invoke(e.getMessage()); | |
} | |
wifiArray.put(wifiObject); | |
} | |
} | |
successCallback.invoke(wifiArray.toString()); | |
} catch (IllegalViewOperationException e) { | |
errorCallback.invoke(e.getMessage()); | |
} | |
} | |
//Method to force wifi usage if the user needs to send requests via wifi | |
//if it does not have internet connection. Useful for IoT applications, when | |
//the app needs to communicate and send requests to a device that have no | |
//internet connection via wifi. | |
//Receives a boolean to enable forceWifiUsage if true, and disable if false. | |
//Is important to enable only when communicating with the device via wifi | |
//and remember to disable it when disconnecting from device. | |
@ReactMethod | |
public void forceWifiUsage(boolean useWifi) { | |
boolean canWriteFlag = false; | |
if (useWifi) { | |
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { | |
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { | |
canWriteFlag = Settings.System.canWrite(reactContext); | |
if (!canWriteFlag) { | |
Intent intent = new Intent(Settings.ACTION_MANAGE_WRITE_SETTINGS); | |
intent.setData(Uri.parse("package:" + reactContext.getPackageName())); | |
intent.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK); | |
reactContext.startActivity(intent); | |
} | |
} | |
if (((Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) && canWriteFlag) || ((Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) && !(Build.VERSION.SDK_INT >= Build.VERSION_CODES.M))) { | |
final ConnectivityManager manager = (ConnectivityManager) reactContext | |
.getSystemService(Context.CONNECTIVITY_SERVICE); | |
NetworkRequest.Builder builder; | |
builder = new NetworkRequest.Builder(); | |
//set the transport type do WIFI | |
builder.addTransportType(NetworkCapabilities.TRANSPORT_WIFI); | |
manager.requestNetwork(builder.build(), new ConnectivityManager.NetworkCallback() { | |
@Override | |
public void onAvailable(Network network) { | |
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { | |
manager.bindProcessToNetwork(network); | |
} else { | |
//This method was deprecated in API level 23 | |
ConnectivityManager.setProcessDefaultNetwork(network); | |
} | |
try { | |
} catch (Exception e) { | |
e.printStackTrace(); | |
} | |
manager.unregisterNetworkCallback(this); | |
} | |
}); | |
} | |
} | |
} else { | |
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.M) { | |
ConnectivityManager manager = (ConnectivityManager) reactContext | |
.getSystemService(Context.CONNECTIVITY_SERVICE); | |
manager.bindProcessToNetwork(null); | |
} else if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.LOLLIPOP) { | |
ConnectivityManager.setProcessDefaultNetwork(null); | |
} | |
} | |
} | |
//Method to check if wifi is enabled | |
@ReactMethod | |
public void isEnabled(Callback isEnabled) { | |
isEnabled.invoke(wifi.isWifiEnabled()); | |
} | |
//Method to connect/disconnect wifi service | |
@ReactMethod | |
public void setEnabled(Boolean enabled) { | |
wifi.setWifiEnabled(enabled); | |
} | |
//Send the ssid and password of a Wifi network into this to connect to the network. | |
//Example: wifi.findAndConnect(ssid, password); | |
//After 10 seconds, a post telling you whether you are connected will pop up. | |
//Callback returns true if ssid is in the range | |
@ReactMethod | |
public void findAndConnect(String ssid, String password, Callback ssidFound) { | |
List < ScanResult > results = wifi.getScanResults(); | |
boolean connected = false; | |
for (ScanResult result: results) { | |
String resultString = "" + result.SSID; | |
if (ssid.equals(resultString)) { | |
connected = connectTo(result, password, ssid); | |
} | |
} | |
ssidFound.invoke(connected); | |
} | |
//Use this method to check if the device is currently connected to Wifi. | |
@ReactMethod | |
public void connectionStatus(Callback connectionStatusResult) { | |
ConnectivityManager connManager = (ConnectivityManager) getReactApplicationContext().getSystemService(Context.CONNECTIVITY_SERVICE); | |
NetworkInfo mWifi = connManager.getNetworkInfo(ConnectivityManager.TYPE_WIFI); | |
if (mWifi.isConnected()) { | |
connectionStatusResult.invoke(true); | |
} else { | |
connectionStatusResult.invoke(false); | |
} | |
} | |
//Method to connect to WIFI Network | |
public Boolean connectTo(ScanResult result, String password, String ssid) { | |
//Make new configuration | |
WifiConfiguration conf = new WifiConfiguration(); | |
//clear alloweds | |
conf.allowedAuthAlgorithms.clear(); | |
conf.allowedGroupCiphers.clear(); | |
conf.allowedKeyManagement.clear(); | |
conf.allowedPairwiseCiphers.clear(); | |
conf.allowedProtocols.clear(); | |
// Quote ssid and password | |
conf.SSID = String.format("\"%s\"", ssid); | |
conf.preSharedKey = String.format("\"%s\"", password); | |
WifiConfiguration tempConfig = this.IsExist(conf.SSID); | |
if (tempConfig != null) { | |
wifi.removeNetwork(tempConfig.networkId); | |
} | |
String capabilities = result.capabilities; | |
// appropriate ciper is need to set according to security type used | |
if (capabilities.contains("WPA") || capabilities.contains("WPA2") || capabilities.contains("WPA/WPA2 PSK")) { | |
// This is needed for WPA/WPA2 | |
// Reference - https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/wifi/java/android/net/wifi/WifiConfiguration.java#149 | |
conf.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN); | |
conf.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.CCMP); | |
conf.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.TKIP); | |
conf.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.WPA_PSK); | |
conf.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.CCMP); | |
conf.allowedPairwiseCiphers.set(WifiConfiguration.PairwiseCipher.TKIP); | |
conf.allowedProtocols.set(WifiConfiguration.Protocol.RSN); | |
conf.allowedProtocols.set(WifiConfiguration.Protocol.WPA); | |
conf.status = WifiConfiguration.Status.ENABLED; | |
} else if (capabilities.contains("WEP")) { | |
// This is needed for WEP | |
// Reference - https://android.googlesource.com/platform/frameworks/base/+/refs/heads/master/wifi/java/android/net/wifi/WifiConfiguration.java#149 | |
conf.wepKeys[0] = "\"" + password + "\""; | |
conf.wepTxKeyIndex = 0; | |
conf.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.OPEN); | |
conf.allowedAuthAlgorithms.set(WifiConfiguration.AuthAlgorithm.SHARED); | |
conf.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE); | |
conf.allowedGroupCiphers.set(WifiConfiguration.GroupCipher.WEP40); | |
} else { | |
conf.allowedKeyManagement.set(WifiConfiguration.KeyMgmt.NONE); | |
} | |
List<WifiConfiguration> mWifiConfigList = wifi.getConfiguredNetworks(); | |
int updateNetwork = -1; | |
// Use the existing network config if exists | |
for (WifiConfiguration wifiConfig : mWifiConfigList) { | |
if (wifiConfig.SSID.equals(conf.SSID)) { | |
conf=wifiConfig; | |
updateNetwork=conf.networkId; | |
} | |
} | |
// If network not already in configured networks add new network | |
if ( updateNetwork == -1 ) { | |
updateNetwork = wifi.addNetwork(conf); | |
wifi.saveConfiguration(); | |
} | |
// if network not added return false | |
if ( updateNetwork == -1 ) { | |
return false; | |
} | |
// disconnect current network | |
boolean disconnect = wifi.disconnect(); | |
if ( !disconnect ) { | |
return false; | |
} | |
// enable new network | |
boolean enableNetwork = wifi.enableNetwork(updateNetwork, true); | |
if ( !enableNetwork ) { | |
return false; | |
} | |
return true; | |
} | |
//Disconnect current Wifi. | |
@ReactMethod | |
public void disconnect() { | |
wifi.disconnect(); | |
} | |
//This method will return current ssid | |
@ReactMethod | |
public void getSSID(final Callback callback) { | |
WifiInfo info = wifi.getConnectionInfo(); | |
// This value should be wrapped in double quotes, so we need to unwrap it. | |
String ssid = info.getSSID(); | |
if (ssid.startsWith("\"") && ssid.endsWith("\"")) { | |
ssid = ssid.substring(1, ssid.length() - 1); | |
} | |
callback.invoke(ssid); | |
} | |
//This method will return the basic service set identifier (BSSID) of the current access point | |
@ReactMethod | |
public void getBSSID(final Callback callback) { | |
WifiInfo info = wifi.getConnectionInfo(); | |
String bssid = info.getBSSID(); | |
callback.invoke(bssid.toUpperCase()); | |
} | |
//This method will return current wifi signal strength | |
@ReactMethod | |
public void getCurrentSignalStrength(final Callback callback) { | |
int linkSpeed = wifi.getConnectionInfo().getRssi(); | |
callback.invoke(linkSpeed); | |
} | |
//This method will return current wifi frequency | |
@ReactMethod | |
public void getFrequency(final Callback callback) { | |
WifiInfo info = wifi.getConnectionInfo(); | |
int frequency = info.getFrequency(); | |
callback.invoke(frequency); | |
} | |
//This method will return current IP | |
@ReactMethod | |
public void getIP(final Callback callback) { | |
WifiInfo info = wifi.getConnectionInfo(); | |
String stringip = longToIP(info.getIpAddress()); | |
callback.invoke(stringip); | |
} | |
//This method will remove the wifi network as per the passed SSID from the device list | |
@ReactMethod | |
public void isRemoveWifiNetwork(String ssid, final Callback callback) { | |
List<WifiConfiguration> mWifiConfigList = wifi.getConfiguredNetworks(); | |
for (WifiConfiguration wifiConfig : mWifiConfigList) { | |
String comparableSSID = ('"' + ssid + '"'); //Add quotes because wifiConfig.SSID has them | |
if(wifiConfig.SSID.equals(comparableSSID)) { | |
wifi.removeNetwork(wifiConfig.networkId); | |
wifi.saveConfiguration(); | |
callback.invoke(true); | |
return; | |
} | |
} | |
callback.invoke(false); | |
} | |
@ReactMethod | |
public void reScanAndLoadWifiList(Callback successCallback, Callback errorCallback) { | |
WifiReceiver receiverWifi = new WifiReceiver(wifi, successCallback, errorCallback); | |
getReactApplicationContext().getCurrentActivity().registerReceiver(receiverWifi, new IntentFilter(WifiManager.SCAN_RESULTS_AVAILABLE_ACTION)); | |
wifi.startScan(); | |
} | |
@ReactMethod | |
public void getDhcpServerAddress(Callback callback) { | |
DhcpInfo dhcpInfo = wifi.getDhcpInfo(); | |
String ip = longToIP(dhcpInfo.serverAddress); | |
callback.invoke(ip); | |
} | |
public static String longToIP(int longIp){ | |
StringBuffer sb = new StringBuffer(""); | |
String[] strip=new String[4]; | |
strip[3]=String.valueOf((longIp >>> 24)); | |
strip[2]=String.valueOf((longIp & 0x00FFFFFF) >>> 16); | |
strip[1]=String.valueOf((longIp & 0x0000FFFF) >>> 8); | |
strip[0]=String.valueOf((longIp & 0x000000FF)); | |
sb.append(strip[0]); | |
sb.append("."); | |
sb.append(strip[1]); | |
sb.append("."); | |
sb.append(strip[2]); | |
sb.append("."); | |
sb.append(strip[3]); | |
return sb.toString(); | |
} | |
private WifiConfiguration IsExist(String SSID) { | |
List<WifiConfiguration> existingConfigs = wifi.getConfiguredNetworks(); | |
for (WifiConfiguration existingConfig : existingConfigs) { | |
if (existingConfig.SSID.equals("\"" + SSID + "\"")) { | |
return existingConfig; | |
} | |
} | |
return null; | |
} | |
class WifiReceiver extends BroadcastReceiver { | |
private Callback successCallback; | |
private Callback errorCallback; | |
private WifiManager wifi; | |
public WifiReceiver(final WifiManager wifi, Callback successCallback, Callback errorCallback) { | |
super(); | |
this.successCallback = successCallback; | |
this.errorCallback = errorCallback; | |
this.wifi = wifi; | |
} | |
// This method call when number of wifi connections changed | |
public void onReceive(Context c, Intent intent) { | |
c.unregisterReceiver(this); | |
try { | |
List < ScanResult > results = this.wifi.getScanResults(); | |
JSONArray wifiArray = new JSONArray(); | |
for (ScanResult result: results) { | |
JSONObject wifiObject = new JSONObject(); | |
if(!result.SSID.equals("")){ | |
try { | |
wifiObject.put("SSID", result.SSID); | |
wifiObject.put("BSSID", result.BSSID); | |
wifiObject.put("capabilities", result.capabilities); | |
wifiObject.put("frequency", result.frequency); | |
wifiObject.put("level", result.level); | |
wifiObject.put("timestamp", result.timestamp); | |
} catch (JSONException e) { | |
this.errorCallback.invoke(e.getMessage()); | |
return; | |
} | |
wifiArray.put(wifiObject); | |
} | |
} | |
this.successCallback.invoke(wifiArray.toString()); | |
return; | |
} catch (IllegalViewOperationException e) { | |
this.errorCallback.invoke(e.getMessage()); | |
return; | |
} | |
} | |
} | |
} | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment