From a9a6682b9032be30968e933e3c739323022ef83e Mon Sep 17 00:00:00 2001 From: Jaren Date: Thu, 11 Dec 2025 21:05:07 +0800 Subject: [PATCH 1/3] feat(wifi_iot): add support for WPA3 and explicit WPA2 security types - Updated `NetworkSecurity` enum in Dart to include `WPA2` and `WPA3`. - Updated Android implementation to handle `WPA2` (treated same as WPA) and `WPA3` security types. - Implemented `setWpa3Passphrase` for Android Q/R+ `WifiNetworkSuggestion` and `WifiNetworkSpecifier`. - Added support for `KeyMgmt.SAE` in legacy `WifiConfiguration`. --- .../com/alternadom/wifiiot/WifiIotPlugin.java | 25 +++++++++++++++---- packages/wifi_iot/lib/wifi_iot.dart | 4 ++- 2 files changed, 23 insertions(+), 6 deletions(-) diff --git a/packages/wifi_iot/android/src/main/java/com/alternadom/wifiiot/WifiIotPlugin.java b/packages/wifi_iot/android/src/main/java/com/alternadom/wifiiot/WifiIotPlugin.java index 9f82228e..a8a32d42 100644 --- a/packages/wifi_iot/android/src/main/java/com/alternadom/wifiiot/WifiIotPlugin.java +++ b/packages/wifi_iot/android/src/main/java/com/alternadom/wifiiot/WifiIotPlugin.java @@ -935,8 +935,10 @@ private void registerWifiNetwork(final MethodCall poCall, final Result poResult) suggestedNet.setBssid(macAddress); } - if (security != null && security.toUpperCase().equals("WPA")) { + if (security != null && (security.toUpperCase().equals("WPA") || security.toUpperCase().equals("WPA2"))) { suggestedNet.setWpa2Passphrase(password); + } else if (security != null && security.toUpperCase().equals("WPA3")) { + suggestedNet.setWpa3Passphrase(password); } else if (security != null && security.toUpperCase().equals("WEP")) { // WEP is not supported poResult.error( @@ -1038,7 +1040,9 @@ public void run() { private static String getSecurityType(ScanResult scanResult) { String capabilities = scanResult.capabilities; - if (capabilities.contains("WPA") + if (capabilities.contains("SAE") || capabilities.contains("WPA3")) { + return "WPA3"; + } else if (capabilities.contains("WPA") || capabilities.contains("WPA2") || capabilities.contains("WPA/WPA2 PSK")) { return "WPA"; @@ -1310,8 +1314,10 @@ public void run() { } // set password - if (security != null && security.toUpperCase().equals("WPA")) { + if (security != null && (security.toUpperCase().equals("WPA") || security.toUpperCase().equals("WPA2"))) { builder.setWpa2Passphrase(password); + } else if (security != null && security.toUpperCase().equals("WPA3")) { + builder.setWpa3Passphrase(password); } // remove suggestions if already existing @@ -1360,8 +1366,10 @@ public void run() { } // set security - if (security != null && security.toUpperCase().equals("WPA")) { + if (security != null && (security.toUpperCase().equals("WPA") || security.toUpperCase().equals("WPA2"))) { builder.setWpa2Passphrase(password); + } else if (security != null && security.toUpperCase().equals("WPA3")) { + builder.setWpa3Passphrase(password); } final NetworkRequest networkRequest = @@ -1464,7 +1472,7 @@ private android.net.wifi.WifiConfiguration generateConfiguration( if (security != null) security = security.toUpperCase(); else security = "NONE"; - if (security.toUpperCase().equals("WPA")) { + if (security.equals("WPA") || security.equals("WPA2")) { /// appropriate ciper is need to set according to security type used, /// ifcase of not added it will not be able to connect @@ -1486,6 +1494,13 @@ private android.net.wifi.WifiConfiguration generateConfiguration( conf.allowedProtocols.set(android.net.wifi.WifiConfiguration.Protocol.RSN); conf.allowedProtocols.set(android.net.wifi.WifiConfiguration.Protocol.WPA); + } else if (security.equals("WPA3")) { + if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.Q) { + conf.preSharedKey = "\"" + password + "\""; + conf.allowedKeyManagement.set(android.net.wifi.WifiConfiguration.KeyMgmt.SAE); + conf.allowedProtocols.set(android.net.wifi.WifiConfiguration.Protocol.RSN); + conf.status = android.net.wifi.WifiConfiguration.Status.ENABLED; + } } else if (security.equals("WEP")) { conf.wepKeys[0] = "\"" + password + "\""; conf.wepTxKeyIndex = 0; diff --git a/packages/wifi_iot/lib/wifi_iot.dart b/packages/wifi_iot/lib/wifi_iot.dart index 3cda5388..08531f22 100755 --- a/packages/wifi_iot/lib/wifi_iot.dart +++ b/packages/wifi_iot/lib/wifi_iot.dart @@ -13,12 +13,14 @@ enum WIFI_AP_STATE { WIFI_AP_STATE_FAILED } -enum NetworkSecurity { WPA, WEP, NONE } +enum NetworkSecurity { WPA, WEP, NONE, WPA2, WPA3 } const serializeNetworkSecurityMap = { NetworkSecurity.WPA: "WPA", NetworkSecurity.WEP: "WEP", NetworkSecurity.NONE: "NONE", + NetworkSecurity.WPA2: "WPA2", + NetworkSecurity.WPA3: "WPA3", }; const MethodChannel _channel = const MethodChannel('wifi_iot'); From eddfc9140c25e688b0cc8da82be29e33ae9bacc7 Mon Sep 17 00:00:00 2001 From: Jaren Date: Wed, 31 Dec 2025 11:24:28 +0800 Subject: [PATCH 2/3] fix(wifi_iot): fix WPA3 issue on iOS - Updated security type detection to recognize WPA2/WPA3 type; --- .../ios/Classes/SwiftWifiIotPlugin.swift | 31 ++++++++++++++----- 1 file changed, 24 insertions(+), 7 deletions(-) diff --git a/packages/wifi_iot/ios/Classes/SwiftWifiIotPlugin.swift b/packages/wifi_iot/ios/Classes/SwiftWifiIotPlugin.swift index 5638700a..187c2e0f 100755 --- a/packages/wifi_iot/ios/Classes/SwiftWifiIotPlugin.swift +++ b/packages/wifi_iot/ios/Classes/SwiftWifiIotPlugin.swift @@ -167,13 +167,30 @@ public class SwiftWifiIotPlugin: NSObject, FlutterPlugin { @available(iOS 11.0, *) private func initHotspotConfiguration(ssid: String, passphrase: String?, security: String? = nil) -> NEHotspotConfiguration { - switch security?.uppercased() { - case "WPA": - return NEHotspotConfiguration.init(ssid: ssid, passphrase: passphrase!, isWEP: false) - case "WEP": - return NEHotspotConfiguration.init(ssid: ssid, passphrase: passphrase!, isWEP: true) - default: - return NEHotspotConfiguration.init(ssid: ssid) + let sec = security?.uppercased() ?? "" + + if sec.hasPrefix("WPA") { + // WPA / WPA2 / WPA3 + guard let passphrase = passphrase else { + fatalError("WPA security requires passphrase") + } + return NEHotspotConfiguration( + ssid: ssid, + passphrase: passphrase, + isWEP: false + ) + } else if sec.hasPrefix("WEP") { + guard let passphrase = passphrase else { + fatalError("WEP security requires passphrase") + } + return NEHotspotConfiguration( + ssid: ssid, + passphrase: passphrase, + isWEP: true + ) + } else { + // Open network + return NEHotspotConfiguration(ssid: ssid) } } From a35d21bd4ad4651e60b8fbfb97dfd29e755dae73 Mon Sep 17 00:00:00 2001 From: Jaren Date: Wed, 31 Dec 2025 11:25:26 +0800 Subject: [PATCH 3/3] chore(wifi_iot): bump wifi_iot version to 0.3.20+2 --- packages/wifi_iot/pubspec.yaml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/packages/wifi_iot/pubspec.yaml b/packages/wifi_iot/pubspec.yaml index d20135ec..112fa8f5 100644 --- a/packages/wifi_iot/pubspec.yaml +++ b/packages/wifi_iot/pubspec.yaml @@ -1,6 +1,6 @@ name: wifi_iot description: Flutter plugin which can handle WiFi connections and hotspot (AP, STA) -version: 0.3.19+2 +version: 0.3.20+2 homepage: https://github.com/flutternetwork/WiFiFlutter/tree/master/packages/wifi_iot flutter: