Problem: I am trying to intercept the SMS message body and then send the message body to the database using a POST Call REST API every time I encounter an SMS. This whole interception and sending the message body should work in the background as well and that too automatically.
What I have achieved so far: I am using the telephony plugin to intercept the message body and I am able to print the message body every time I receive one at the UI level but unable to call the API and send the SMS body.
Error: Since I did not find a way to how to automatically call the API every time a new message is intercepted so I used a button to call it instead but even that did not work and it throws the error as
[error:flutter/lib/ui/ui_dart_state.cc(209)] unhandled exception: invalid argument(s) (onerror): the error handler of future.catcherror must return a value of the future's type
Also, I did not manage how do I intercept the SMS message body in the background.
To better understand this error I will be attaching a few of my code snippets:
API usage function:
String body = "";
DateTime currentPhoneDate = DateTime.now();
final telephony = Telephony.instance;
interceptMessage() {
final messaging = ApiService();
messaging.interceptedMessage({
"id": 50,
"body": "$body",
"senderName": "IDK",
"timeStamp": "2021-10-02 12:00:55"
})
..then((value) {
if (value.status == "Success") {
print('Message Intercepted');
} else {
print('Somethig went wrong');
}
});
}
API Class:
Future<SmsResponse> interceptedMessage(dynamic param) async {
var client = http.Client();
String? token = await storage.readSecureToken('key');
if (token == null) {
throw Exception("No token stored in storage");
}
try {
var response = await client
.post(
Uri.https("baseURL", "endpoint"),
headers: <String, String>{
'Authorization': 'Token $token',
},
body: param,
)
.timeout(Duration(seconds: TIME_CONST))
.catchError(handleError);
if (response.statusCode == 200) {
print('Response Body: ${response.body}');
final data = await jsonDecode(response.body);
return SmsResponse.fromJson(data);
} else if (response.statusCode == 401) {
print("Unauthorized Request");
return param;
} else {
print("Bad Input");
return param;
}
} catch(e){
print(e);
}
}
Telephony Plugin Usage:
@override
void initState() {
super.initState();
initPlatformState();
}
onMessage(
SmsMessage message,
) async {
setState(() {
body = message.body ?? "Error reading message body.";
print("$body");
});
}
onSendStatus(SendStatus status) {
setState(() {
body = status == SendStatus.SENT ? "sent" : "delivered";
});
}
Future<void> initPlatformState() async {
final bool? result = await telephony.requestPhoneAndSmsPermissions;
if (result != null && result) {
telephony.listenIncomingSms(
onNewMessage: onMessage,
onBackgroundMessage: onBackgroundMessage,
listenInBackground: true,
);
}
if (!mounted) return;
}
Handle Error Function
void handleError(error) {
//hideLoading();
if (error is BadRequestException) {
var message = error.message;
DialogHelper.showErroDialog(description: message);
} else if (error is FetchDataException) {
var message = error.message;
DialogHelper.showErroDialog(description: message);
} else if (error is ApiNotRespondingException) {
DialogHelper.showErroDialog(
description: 'Oops! It took longer to respond.');
} else if (error is SocketException) {
print(
error); //Have to remove this part this is already being handled at the service level
} else {
print("All OK");
}
}
UI Level:
Text("$body");