diff --git a/README.md b/README.md index 864a939..891313a 100644 --- a/README.md +++ b/README.md @@ -53,6 +53,7 @@ Use the gettable variables to get current status of the device: - `Future areRootPrivilegesDetected()` - `Future areHooksDetected()` - `Future isSimulatorDetected()` +- `Future isDebuggerDetected()` ### Async Stream API diff --git a/example/lib/main.dart b/example/lib/main.dart index c594314..e28507a 100644 --- a/example/lib/main.dart +++ b/example/lib/main.dart @@ -19,6 +19,7 @@ class _MyAppState extends State { bool _jailbroken = false; bool _hooks = false; bool _simulator = false; + bool _debugger = false; @override void initState() { @@ -31,10 +32,11 @@ class _MyAppState extends State { // Platform messages may fail, so we use a try/catch PlatformException. // We also handle the message potentially returning null. try { - final (jailbroken, hooks, simulator) = await ( + final (jailbroken, hooks, simulator, debugger) = await ( ThreatDetectionCenter.areRootPrivilegesDetected(), ThreatDetectionCenter.areHooksDetected(), ThreatDetectionCenter.isSimulatorDetected(), + ThreatDetectionCenter.isDebuggerDetected(), ).wait; if (!mounted) return; @@ -43,6 +45,7 @@ class _MyAppState extends State { _jailbroken = jailbroken ?? _jailbroken; _hooks = hooks ?? _hooks; _simulator = simulator ?? _simulator; + _debugger = debugger ?? _debugger; }); } on PlatformException { // Do nothing @@ -94,6 +97,11 @@ class _MyAppState extends State { description: 'Running the application in an Simulator', status: _simulator, ), + ThreatCard( + title: 'Debugger', + description: 'A tool that allows developers to inspect and modify the execution of a program in real-time, potentially exposing sensitive data or allowing unauthorized control.', + status: _debugger, + ), ], ), ); diff --git a/example/pubspec.lock b/example/pubspec.lock index 7abe5de..7f30bcf 100644 --- a/example/pubspec.lock +++ b/example/pubspec.lock @@ -37,10 +37,10 @@ packages: dependency: transitive description: name: collection - sha256: ee67cb0715911d28db6bf4af1026078bd6f0128b07a5f66fb2ed94ec6783c09a + sha256: a1ace0a119f20aabc852d165077c036cd864315bd99b7eaa10a60100341941bf url: "https://pub.dev" source: hosted - version: "1.18.0" + version: "1.19.0" cupertino_icons: dependency: "direct main" description: @@ -109,18 +109,18 @@ packages: dependency: transitive description: name: leak_tracker - sha256: "7f0df31977cb2c0b88585095d168e689669a2cc9b97c309665e3386f3e9d341a" + sha256: "7bb2830ebd849694d1ec25bf1f44582d6ac531a57a365a803a6034ff751d2d06" url: "https://pub.dev" source: hosted - version: "10.0.4" + version: "10.0.7" leak_tracker_flutter_testing: dependency: transitive description: name: leak_tracker_flutter_testing - sha256: "06e98f569d004c1315b991ded39924b21af84cf14cc94791b8aea337d25b57f8" + sha256: "9491a714cca3667b60b5c420da8217e6de0d1ba7a5ec322fab01758f6998f379" url: "https://pub.dev" source: hosted - version: "3.0.3" + version: "3.0.8" leak_tracker_testing: dependency: transitive description: @@ -149,18 +149,18 @@ packages: dependency: transitive description: name: material_color_utilities - sha256: "0e0a020085b65b6083975e499759762399b4475f766c21668c4ecca34ea74e5a" + sha256: f7142bb1154231d7ea5f96bc7bde4bda2a0945d2806bb11670e30b850d56bdec url: "https://pub.dev" source: hosted - version: "0.8.0" + version: "0.11.1" meta: dependency: transitive description: name: meta - sha256: "7687075e408b093f36e6bbf6c91878cc0d4cd10f409506f7bc996f68220b9136" + sha256: bdb68674043280c3428e9ec998512fb681678676b3c54e773629ffe74419f8c7 url: "https://pub.dev" source: hosted - version: "1.12.0" + version: "1.15.0" path: dependency: transitive description: @@ -173,10 +173,10 @@ packages: dependency: transitive description: name: platform - sha256: "12220bb4b65720483f8fa9450b4332347737cf8213dd2840d8b2c823e47243ec" + sha256: "9b71283fc13df574056616011fb138fd3b793ea47cc509c189a6c3fa5f8a1a65" url: "https://pub.dev" source: hosted - version: "3.1.4" + version: "3.1.5" plugin_platform_interface: dependency: transitive description: @@ -197,7 +197,7 @@ packages: dependency: transitive description: flutter source: sdk - version: "0.0.99" + version: "0.0.0" source_span: dependency: transitive description: @@ -210,10 +210,10 @@ packages: dependency: transitive description: name: stack_trace - sha256: "73713990125a6d93122541237550ee3352a2d84baad52d375a4cad2eb9b7ce0b" + sha256: "9f47fd3630d76be3ab26f0ee06d213679aa425996925ff3feffdec504931c377" url: "https://pub.dev" source: hosted - version: "1.11.1" + version: "1.12.0" stream_channel: dependency: transitive description: @@ -226,10 +226,10 @@ packages: dependency: transitive description: name: string_scanner - sha256: "556692adab6cfa87322a115640c11f13cb77b3f076ddcc5d6ae3c20242bedcde" + sha256: "688af5ed3402a4bde5b3a6c15fd768dbf2621a614950b17f04626c431ab3c4c3" url: "https://pub.dev" source: hosted - version: "1.2.0" + version: "1.3.0" sync_http: dependency: transitive description: @@ -250,10 +250,10 @@ packages: dependency: transitive description: name: test_api - sha256: "9955ae474176f7ac8ee4e989dadfb411a58c30415bcfb648fa04b2b8a03afa7f" + sha256: "664d3a9a64782fcdeb83ce9c6b39e78fd2971d4e37827b9b06c3aa1edc5e760c" url: "https://pub.dev" source: hosted - version: "0.7.0" + version: "0.7.3" vector_math: dependency: transitive description: @@ -266,18 +266,18 @@ packages: dependency: transitive description: name: vm_service - sha256: "3923c89304b715fb1eb6423f017651664a03bf5f4b29983627c4da791f74a4ec" + sha256: f6be3ed8bd01289b34d679c2b62226f63c0e69f9fd2e50a6b3c1c729a961041b url: "https://pub.dev" source: hosted - version: "14.2.1" + version: "14.3.0" webdriver: dependency: transitive description: name: webdriver - sha256: "003d7da9519e1e5f329422b36c4dcdf18d7d2978d1ba099ea4e45ba490ed845e" + sha256: "3d773670966f02a646319410766d3b5e1037efb7f07cc68f844d5e06cd4d61c8" url: "https://pub.dev" source: hosted - version: "3.0.3" + version: "3.0.4" sdks: dart: ">=3.4.3 <4.0.0" flutter: ">=3.18.0-18.0.pre.54" diff --git a/ios/Classes/FlutterSecurityToolkitPlugin.swift b/ios/Classes/FlutterSecurityToolkitPlugin.swift index 4985d8f..04a99f3 100644 --- a/ios/Classes/FlutterSecurityToolkitPlugin.swift +++ b/ios/Classes/FlutterSecurityToolkitPlugin.swift @@ -17,6 +17,8 @@ public class FlutterSecurityToolkitPlugin: NSObject, FlutterPlugin { result(ThreatDetectionCenter.areHooksDetected) case "isSimulatorDetected": result(ThreatDetectionCenter.isSimulatorDetected) + case "isDebuggerDetected": + result(ThreatDetectionCenter.isDebuggerDetected) default: result(FlutterMethodNotImplemented) } diff --git a/lib/src/flutter_security_toolkit_method_channel.dart b/lib/src/flutter_security_toolkit_method_channel.dart index ba97615..7dcfd45 100644 --- a/lib/src/flutter_security_toolkit_method_channel.dart +++ b/lib/src/flutter_security_toolkit_method_channel.dart @@ -29,4 +29,11 @@ class MethodChannelFlutterSecurityToolkit await methodChannel.invokeMethod('isSimulatorDetected'); return version; } + + @override + Future isDebuggerDetected() async { + final version = + await methodChannel.invokeMethod('isDebuggerDetected'); + return version; + } } diff --git a/lib/src/flutter_security_toolkit_platform_interface.dart b/lib/src/flutter_security_toolkit_platform_interface.dart index 39cfa58..6e9ce68 100644 --- a/lib/src/flutter_security_toolkit_platform_interface.dart +++ b/lib/src/flutter_security_toolkit_platform_interface.dart @@ -36,4 +36,9 @@ abstract class FlutterSecurityToolkitPlatform extends PlatformInterface { throw UnimplementedError( 'isRunningInSimulator() has not been implemented.'); } + + Future isDebuggerDetected() { + throw UnimplementedError( + 'isDebuggerDetected() has not been implemented.'); + } } diff --git a/lib/src/threat_detection_center.dart b/lib/src/threat_detection_center.dart index 77cf82f..7078e21 100644 --- a/lib/src/threat_detection_center.dart +++ b/lib/src/threat_detection_center.dart @@ -23,4 +23,15 @@ class ThreatDetectionCenter { static Future isSimulatorDetected() { return FlutterSecurityToolkitPlatform.instance.isSimulatorDetected(); } + + /// Will check if your application is being traced by a debugger. + /// + /// Returns true if a debugger is detected. + /// + /// A debugger is a tool that allows developers to inspect and modify the execution of a program in real-time, potentially exposing sensitive data or allowing unauthorized control. + /// + /// Please note that Apple itself uses a debugger during reviews. If you perform a debugger prevention, you could prevent Apple from carrying out a complete review, which they certainly will not like. + static Future isDebuggerDetected() { + return FlutterSecurityToolkitPlatform.instance.isDebuggerDetected(); + } } diff --git a/test/threat_detection_center_test.dart b/test/threat_detection_center_test.dart index 6368cf2..ba13e6d 100644 --- a/test/threat_detection_center_test.dart +++ b/test/threat_detection_center_test.dart @@ -15,6 +15,9 @@ class MockFlutterSecurityToolkitPlatform @override Future isSimulatorDetected() => Future.value(false); + + @override + Future isDebuggerDetected() => Future.value(false); } void main() { @@ -49,4 +52,12 @@ void main() { expect(await ThreatDetectionCenter.isSimulatorDetected(), false); }); + + test('isDebuggerDetected', () async { + MockFlutterSecurityToolkitPlatform fakePlatform = + MockFlutterSecurityToolkitPlatform(); + FlutterSecurityToolkitPlatform.instance = fakePlatform; + + expect(await ThreatDetectionCenter.isDebuggerDetected(), false); + }); }