我需要检查android上当前连接的wifi SSID。我分别用诺基亚6和OnePlus 5检查了Oreo 8.1.0和Oreo 8.0。其他具有不同操作系统版本的手机正常使用此代码。我的代码有什么问题吗?
private WifiInfo wifiInfo;
private String ssid = "";
private WifiManager wifiManager;
private boolean getWifiStatus() {
wifiManager= (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
wifiInfo = wifiManager.getConnectionInfo();
ssid = "";
ssid = wifiInfo.getSSID();
ConnectivityManager cm =
(ConnectivityManager)context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo activeNetwork = cm.getActiveNetworkInfo();
boolean isWiFi = false;
if(activeNetwork != null){
isWiFi = activeNetwork.getType() == ConnectivityManager.TYPE_WIFI;
}
Log.d(TAG, "getWifiStatus: " + ssid);
if(ssid.contains("TripleMZim") && wifiManager.isWifiEnabled() && isWiFi ){
return true;
}
else{
return false;
}
}
清单文件中的权限:
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
<uses-permission android:name="android.permission.INTERNET"/>
答案 0 :(得分:9)
有多种方法可以在android中获取WIFI信息(例如SSID)。
上面已经列出了其中的一些服务,例如WifiManager服务。
但是对于OP问题:
我的代码有什么问题吗?
否,问题不在您的代码中。 发生意外行为的主要原因是由于最新的android版本的安全补丁。
在补丁程序(或任何未获得更新的设备)之前,黑客可以窃取通过wifi信息泄露的敏感信息。
例如,黑客可以获得设备的地理位置,该地理位置只能通过Dangerous Permission LOCATION访问,应该在运行时请求并可以随时撤消。但是另一方面,WifiInfo
仅可通过安装时授予的Normal Permission android.permission.ACCESS_WIFI_STATE
进行访问,并且无法撤消。
这样,黑客可以完全绕过权限机制,仅使用普通权限即可从危险权限访问数据。
该问题已由CVE-2018-9489
报告并跟踪,您可以在此处了解更多信息:Sensitive information expose via WIFI
所以您遇到这些问题的原因是因为现在,Android阻止了敏感的wifi信息,除非该应用程序持有ACCESS_COARSE_LOCATION
或ACCESS_FINE_LOCATION
。
因此,如果您明确要求这些权限(并由用户允许),则代码应该可以正常工作。
例如:
清单
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
<uses-permission android:name="android.permission.ACCESS_WIFI_STATE"/>
活动
private static final int LOCATION = 1;
protected void onStart() {
super.onStart();
//Assume you want to read the SSID when the activity is started
tryToReadSSID();
}
@Override
public void onRequestPermissionsResult(int requestCode, String[] permissions, int[] grantResults) {
if(grantResults[0] == PackageManager.PERMISSION_GRANTED && requestCode == LOCATION){
//User allowed the location and you can read it now
tryToReadSSID();
}
}
private void tryToReadSSID() {
//If requested permission isn't Granted yet
if (ActivityCompat.checkSelfPermission(this, Manifest.permission.ACCESS_FINE_LOCATION) != PackageManager.PERMISSION_GRANTED) {
//Request permission from user
ActivityCompat.requestPermissions(this, new String[]{Manifest.permission.ACCESS_FINE_LOCATION}, LOCATION);
}else{//Permission already granted
WifiManager wifiManager = (WifiManager) getApplicationContext().getSystemService(WIFI_SERVICE);
WifiInfo wifiInfo = wifiManager.getConnectionInfo();
if(wifiInfo.getSupplicantState() == SupplicantState.COMPLETED){
String ssid = wifiInfo.getSSID();//Here you can access your SSID
System.out.println(ssid);
}
}
}
答案 1 :(得分:8)
在Android Oreo中,您可以使用ConnectivityManager
来知道您的WiFi SSID。
权限
<uses-permission android:name="android.permission.ACCESS_NETWORK_STATE"/>
获取SSID的代码
ConnectivityManager cm = (ConnectivityManager) context.getSystemService(Context.CONNECTIVITY_SERVICE);
NetworkInfo info = cm.getActiveNetworkInfo();
if (info != null && info.isConnected()) {
String ssid = info.getExtraInfo();
Log.d(TAG, "WiFi SSID: " + ssid);
}
这已在Android Oreo 8.1.0中进行了测试。您将获得带有双引号的SSID。
答案 2 :(得分:6)
答案 3 :(得分:1)
您需要在清单中请求许可:
<uses-permission android:name="android.permission.ACCESS_FINE_LOCATION"/>
并在您的活动中请求它:
private void grantPermm()
{
try
{
if (ContextCompat.checkSelfPermission(MainScreenActivity.this,
Manifest.permission.ACCESS_FINE_LOCATION) == PackageManager.PERMISSION_GRANTED)
{
}
else
{
ActivityCompat.requestPermissions(MainScreenActivity.this,
new String[]{Manifest.permission.ACCESS_FINE_LOCATION},
101);
}
}
catch (Exception xx){}
}
然后使用此功能:
public static String getWifiName(Context context)
{
String result="";
try {
WifiManager manager = (WifiManager) context.getSystemService(Context.WIFI_SERVICE);
if (manager.isWifiEnabled())
{
WifiInfo wifiInfo = manager.getConnectionInfo();
if (wifiInfo != null)
{
NetworkInfo.DetailedState state = WifiInfo.getDetailedStateOf(wifiInfo.getSupplicantState());
if (state == NetworkInfo.DetailedState.CONNECTED || state == NetworkInfo.DetailedState.OBTAINING_IPADDR)
{
result = wifiInfo.getSSID();
if(result.equalsIgnoreCase("<unknown ssid>"))
{
Toast.makeText(context,"You are connected to mobile data", Toast.LENGTH_SHORT).show();
result="";
}
return result;
}
else
{
Toast.makeText(context,"WIFI not connected", Toast.LENGTH_SHORT).show();
return "";
}
}
else
{
Toast.makeText(context,"No WIFI Information", Toast.LENGTH_SHORT).show();
return "";
}
}
else
{
Toast.makeText(context,"WIFI not enabled", Toast.LENGTH_SHORT).show();
return "";
}
}
catch (Exception xx)
{
Toast.makeText(context, xx.getMessage().toString(), Toast.LENGTH_SHORT).show();
return "";
}
}
答案 4 :(得分:0)
如果即使在尝试使用Yaswant Narayan和令人信服的答案后仍然遇到问题,请确保在尝试获取SSID时已在设备中启用了Location / GPS。即使您已经在Android Oreo及更高版本的设备上获得了相关的权限,但是如果用户关闭了位置/ GPS,则可以从这些设备上获取。
答案 5 :(得分:0)
您需要请求读取手机状态的运行时许可。包括它是为了提高安全性。
代码如下:-
TelephonyManager telephonyManager = (TelephonyManager) getContext()
.getSystemService(Context.TELEPHONY_SERVICE);
String IMEI ="";
if (ActivityCompat.checkSelfPermission(getContext(), Manifest.permission.READ_PHONE_STATE) != PackageManager.PERMISSION_GRANTED) {
ActivityCompat.requestPermissions(getActivity(),
new String[]{Manifest.permission.READ_PHONE_STATE},
123);
}
int permission = ContextCompat.checkSelfPermission(getContext(),
Manifest.permission.READ_PHONE_STATE);
if(permission == PackageManager.PERMISSION_GRANTED){
if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.O) {
IMEI = telephonyManager.getImei();
}
else{
IMEI = telephonyManager.getDeviceId();
}
}
答案 6 :(得分:0)
如果您定位的是API 29(Android 10),则请求的位置权限现在必须是ACCESS_FINE_LOCATION,而不仅仅是ACCESS_COARSE_LOCATION。上面的大多数示例代码都可以,但是某些答案可能会在文本中产生误导。
https://developer.android.com/about/versions/10/privacy/changes