-
-
Notifications
You must be signed in to change notification settings - Fork 920
Open
Description
Please check the following before submitting a new issue.
- I have searched the existing issues.
- I have carefully read the documentation and verified I have added the required platform specific configuration.
Please select affected platform(s)
- Android
- iOS
- Windows
Steps to reproduce
Nothing much needed to reproduce I just added the package to the dependencies. My flutter SDK version is 3.35.3. Gradle version 8.13-all. Java Version 21. AGP 8.13.1.
Expected results
No error.
Actual results
> Could not resolve all artifacts for configuration 'classpath'.
> Could not find builder-8.0.2.jar (com.android.tools.build:builder:8.0.2).
Searched in the following locations:
https://dl.google.com/dl/android/maven2/com/android/tools/build/builder/8.0.2/builder-8.0.2.jar
> Failed to notify project evaluation listener.
> java.lang.NullPointerException (no error message)
> java.lang.NullPointerException (no error message)```
### Code sample
<details><summary>Code sample</summary>
```yaml
name: sms_sender_app
description: "A new Flutter project."
publish_to: 'none'
version: 0.1.0
environment:
sdk: ^3.9.2
dependencies:
dio: ^5.9.0
flutter:
sdk: flutter
flutter_background_service: ^5.1.0
permission_handler: ^12.0.1
flutter:
uses-material-design: true
import 'dart:async';
import 'dart:ui';
import 'package:flutter/material.dart';
import 'package:flutter_background_service/flutter_background_service.dart';
import 'sms_gateway_service.dart';
@pragma('vm:entry-point')
void onStart(ServiceInstance service) async {
WidgetsFlutterBinding.ensureInitialized();
DartPluginRegistrant.ensureInitialized();
final gateway = SmsGatewayService();
gateway.startPolling();
service.on('stop').listen((event) {
gateway.stopPolling();
service.stopSelf();
});
}
Future<void> main() async {
WidgetsFlutterBinding.ensureInitialized();
await Permission.sms.request();
await initializeService();
runApp(const MyApp());
}
Future<void> initializeService() async {
final service = FlutterBackgroundService();
await service.configure(
iosConfiguration: IosConfiguration(),
androidConfiguration: AndroidConfiguration(
onStart: onStart,
isForegroundMode: true,
autoStart: true,
notificationChannelId: 'sms_gateway_channel',
initialNotificationTitle: 'SMS Gateway Service',
initialNotificationContent: 'Polling for OTP messages...',
foregroundServiceNotificationId: 888,
),
);
}
class MyApp extends StatelessWidget {
const MyApp({super.key});
@override
Widget build(BuildContext context) {
return MaterialApp(
home: Scaffold(
appBar: AppBar(title: const Text('SMS Gateway')),
body: Center(
child: Column(
mainAxisAlignment: MainAxisAlignment.center,
children: [
const Text('Service is running in the background.'),
const SizedBox(height: 20),
ElevatedButton(
child: const Text('Stop Service'),
onPressed: () {
final service = FlutterBackgroundService();
service.invoke('stop');
},
),
],
),
),
),
);
}
}
import 'dart:async';
import 'dart:developer' show log;
import 'package:dio/dio.dart';
import 'package:flutter/services.dart';
class SmsGatewayService {
// This channel name MUST match the one in MainActivity.kt
static const _platform = MethodChannel('com.example/sms');
final Dio _dio = Dio();
Timer? _timer;
// This is the main polling loop
void startPolling() {
log("SMS Gateway Service: Starting polling...");
// Poll immediately, then every 5 seconds
_timer = Timer.periodic(const Duration(seconds: 5), (timer) async {
await _fetchAndProcessOtps();
});
}
void stopPolling() {
_timer?.cancel();
log("SMS Gateway Service: Polling stopped.");
}
Future<void> _fetchAndProcessOtps() async {
log("Polling for new OTPs...");
try {
// final response = await _dio.get('{my BASE_URL}/get-otps');
await Future.delayed(const Duration(milliseconds: 100));
final List<Map<String, String>> pendingOtps = [
{'phone': '+99361234567', 'otp': '12345'},
{'phone': '+99361234568', 'otp': '64321'},
];
// final List<Map<String, String>> pendingOtps = response.data;
if (pendingOtps.isEmpty) {
log("No pending OTPs.");
return;
}
log("Found ${pendingOtps.length} OTPs. Initiating send batch.");
final List<Future<void>> sendTasks = [];
for (var item in pendingOtps) {
final phone = item['phone'];
final otp = item['otp'];
if (phone != null && otp != null) {
sendTasks.add(_sendSingleSms(phone, otp));
}
}
await Future.wait(sendTasks);
} catch (e) {
log("Error in polling loop: $e");
}
}
Future<void> _sendSingleSms(String phone, String otp) async {
try {
final String message = 'Your OTP is: $otp';
log("Sending to $phone...");
final result = await _platform.invokeMethod('sendSMS', {
'phone': phone,
'msg': message,
});
log("Sent to $phone: $result");
} on PlatformException catch (e) {
log("Failed to send SMS to $phone: '${e.message}'.");
}
}
}
<manifest xmlns:android="http://schemas.android.com/apk/res/android">
<uses-permission android:name="android.permission.SEND_SMS"/>
<uses-permission android:name="android.permission.INTERNET"/>
<uses-permission android:name="android.permission.FOREGROUND_SERVICE"/>
<uses-permission android:name="android.permission.WAKE_LOCK"/>
<uses-permission android:name="android.permission.FOREGROUND_SERVICE_DATA_SYNC"/>
<uses-permission android:name="android.permission.RECEIVE_BOOT_COMPLETED"/>
<application
android:label="example"
android:name="${applicationName}"
android:icon="@mipmap/ic_launcher">
<activity
android:name=".MainActivity"
android:exported="true"
android:launchMode="singleTop"
android:taskAffinity=""
android:theme="@style/LaunchTheme"
android:configChanges="orientation|keyboardHidden|keyboard|screenSize|smallestScreenSize|locale|layoutDirection|fontScale|screenLayout|density|uiMode"
android:hardwareAccelerated="true"
android:windowSoftInputMode="adjustResize">
<!-- Specifies an Android theme to apply to this Activity as soon as
the Android process has started. This theme is visible to the user
while the Flutter UI initializes. After that, this theme continues
to determine the Window background behind the Flutter UI. -->
<meta-data
android:name="io.flutter.embedding.android.NormalTheme"
android:resource="@style/NormalTheme"
/>
<intent-filter>
<action android:name="android.intent.action.MAIN"/>
<category android:name="android.intent.category.LAUNCHER"/>
</intent-filter>
</activity>
<service
android:name="id.flutter.flutter_background_service.BackgroundService"
android:foregroundServiceType="dataSync" />
<receiver
android:name="id.flutter.flutter_background_service.BootReceiver"
android:enabled="true"
android:exported="true"
>
<intent-filter>
<action android:name="android.intent.action.BOOT_COMPLETED"/>
</intent-filter>
</receiver>
<!-- Don't delete the meta-data below.
This is used by the Flutter tool to generate GeneratedPluginRegistrant.java -->
<meta-data
android:name="flutterEmbedding"
android:value="2" />
</application>
<!-- Required to query activities that can process text, see:
https://developer.android.com/training/package-visibility and
https://developer.android.com/reference/android/content/Intent#ACTION_PROCESS_TEXT.
In particular, this is used by the Flutter engine in io.flutter.plugin.text.ProcessTextPlugin. -->
<queries>
<intent>
<action android:name="android.intent.action.PROCESS_TEXT"/>
<data android:mimeType="text/plain"/>
</intent>
</queries>
</manifest>
,
pluginManagement {
val flutterSdkPath =
run {
val properties = java.util.Properties()
file("local.properties").inputStream().use { properties.load(it) }
val flutterSdkPath = properties.getProperty("flutter.sdk")
require(flutterSdkPath != null) { "flutter.sdk not set in local.properties" }
flutterSdkPath
}
includeBuild("$flutterSdkPath/packages/flutter_tools/gradle")
repositories {
google()
mavenCentral()
gradlePluginPortal()
}
}
plugins {
id("dev.flutter.flutter-plugin-loader") version "1.0.0"
id("com.android.application") version "8.13.1" apply false
id("org.jetbrains.kotlin.android") version "2.2.21" apply false
}
include(":app")
Screenshots or video
Screenshots or video demonstration
[Upload media here]
Version
12.0.1
Flutter Doctor output
Doctor output
Doctor summary (to see all details, run flutter doctor -v):
[✓] Flutter (Channel stable, 3.35.3, on Microsoft Windows [Version 10.0.22631.3296], locale en-US)
[✓] Windows Version (11 Pro 64-bit, 23H2, 2009)
[✓] Android toolchain - develop for Android devices (Android SDK version 36.1.0)
[✓] Chrome - develop for the web
[✗] Visual Studio - develop Windows apps
✗ Visual Studio not installed; this is necessary to develop Windows apps.
Download at https://visualstudio.microsoft.com/downloads/.
Please install the "Desktop development with C++" workload, including all of its default components
[✓] Android Studio (version 2025.2.1)
[✓] VS Code (version 1.106.0)
[✓] Connected device (4 available)
[!] Network resources
✗ A network error occurred while checking "https://pub.dev/": The semaphore timeout period has expired.
! Doctor found issues in 2 categories.Metadata
Metadata
Assignees
Labels
No labels