Android - LocalBroadcastManager for SMS interception not firing - android

I've got an JavascriptInterface method that registers a LocalBroadcastManager listening to received SMS's. When an SMS arrives the onReceive method doesn't get called.
public void UIregisterSMSSource(String number) {
LocalBroadcastManager.getInstance(this)
.registerReceiver(mMessageReceiver, new IntentFilter(ACTION_SMS_RECEIVE));
}
/**
* SMS Receiver
*/
private BroadcastReceiver mMessageReceiver = new BroadcastReceiver() {
#Override
public void onReceive(Context context, Intent intent) {
if (intent.getAction().equals(ACTION_SMS_RECEIVE)) {
StringBuilder buf = new StringBuilder();
Bundle bundle = intent.getExtras();
if (bundle != null) {
Bundle extras = intent.getExtras();
Object[] pdus = (Object[]) extras.get("pdus");
for (int i = 0; i < pdus.length; i++) {
SmsMessage SMessage = SmsMessage.createFromPdu((byte[]) pdus[i]);
String sender = SMessage.getOriginatingAddress();
String body = SMessage.getMessageBody().toString();
Log.d(TAG, "[SMS] onReceive by " + sender + ". Content - " + body);
// Save preferences of the activation code
}
}
}
}
};
This is the ACTION_SMS_RECEIVE variable:
private static final String ACTION_SMS_RECEIVE = "android.provider.Telephony.SMS_RECEIVED";
I've tested this before as BroadcastaReceiver and it worked. I removed the receiver from the manifest too which I don't know if it's right.
Do I need to configure something more? On the examples I've came across there's no further configuration needed.
Thanks in advance.

Receiver mMessageReceiver can only listen the intent which sent via LocalBroadcastManager.sendBroadcast(intent).
Here, intent with android.provider.Telephony.SMS_RECEIVED action, is being raised by system (not using LocalBroadcastManager.sendBroadcast(intent)), so your app does not listen to this intent.
Your previous approach was correct, and you can continue on that logic.
You can read a detailed example of LocalBroadcastManager to make clear your doubts about its working flow.

Related

Can't launch the activity again if it's already open

I'am working on SMS manager like app. Now when an SMS is received a new Dialog Activity like a pop-up which shows the user the Sender's number and message. It's OK but if another SMS comes before the user press Back button (the Pop-Up activity still there on the Top), then the new SMS can't be shown to the user.
Every new SMS should show up on the pop-up activity diminish any older SMS if on foreground.
I tried in and out the onReceive method of the Broadcast Receiver class. By digging deeper I found that if the pop-up with an SMS is on foreground, the Pop-up Activity cannot gets called. It just don't come to the OnCreate method.
BroadcastReceiver class:
public class SmsBroadcastReceiver extends BroadcastReceiver {
public static final String SMS_BUNDLE = "pdus";
public static String latestSMSnumber, latestSMScontent;
SmsMessage[] msgs = null;
String str = "";
public void onReceive(Context context, Intent intent) {
Bundle bundle = intent.getExtras();
if (bundle != null) {
Object[] pdus = (Object[]) bundle.get("pdus");
msgs = new SmsMessage[pdus.length];
for (int i = 0; i < msgs.length; ++i) {
// Convert Object array
msgs[i] = SmsMessage.createFromPdu((byte[]) pdus[i]);
// Fetch the text message
str += msgs[i].getMessageBody().toString();
str += "\n";
latestSMSnumber = msgs[i].getOriginatingAddress();
latestSMScontent = str;
}
// Display the entire SMS Message
Log.e("TAG1 number: ", latestSMSnumber);
Log.e("TAG2 content: ", str);
latestSMScontent = str;
// Toast.makeText(context, smsMessageStr, Toast.LENGTH_SHORT).show();
Intent i=new Intent(context.getApplicationContext(),NewSMS.class);
// i.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
i.putExtra("Number", latestSMSnumber);
i.putExtra("MsgBody", latestSMScontent);
context.startActivity(i);
}
}
}
I like to show any new SMS with number and msg text in the pop-up window.
Write This in you manifest.xml file in activity tag NewSMS Activity
android:launchMode=”singleTop”
For more information Please read the bellow link
https://android.jlelse.eu/android-activity-launch-mode-e0df1aa72242

Unit Testing Android SMS Receiver

i try to write an unit test on an BroadcastReceiver that gets informed when an SMS was received. Its not meant to be the default Application. Instead i just need this for an two factor authentication. For this case i created an PDU with [1].
But when i pass it down to the BroadcastReceiver the phone nr of the Sender never gets read by android it's just null. The body text is returned.
#TargetApi(Build.VERSION_CODES.KITKAT)
#Test
public void testOnReceive() throws Exception {
final byte[] decodedPDU = BaseEncoding.base16().decode(PDU);
final ReceiveSmsBroadcastReceiver receiveSmsBroadcastReceiver = spy(new ReceiveSmsBroadcastReceiver(true));
final Intent intent = new Intent();
intent.putExtra("format",SmsConstants.FORMAT_3GPP);
intent.putExtra("pdus", new Object[]{decodedPDU});
intent.setAction("android.provider.Telephony.SMS_RECEIVED");
intent.putExtra(PhoneConstants.SUBSCRIPTION_KEY, 1);
receiveSmsBroadcastReceiver.onReceive(InstrumentationRegistry.getTargetContext(), intent);
In the receiver i do this to get the SMSMessage Objects:
#TargetApi(Build.VERSION_CODES.KITKAT)
private void getSMSKitKat(final Context context, final Intent intent) {
final SmsMessage[] messagesFromIntent = Telephony.Sms.Intents.getMessagesFromIntent(intent);
I receive an SmsMessage array here, the body message is correct. But i need to test my check sender phone number before i can notify the UI that the SMS is received: But nr is always null here:
private boolean isCorrectSender(#Nullable final SmsMessage message) {
if (message == null) {
return false;
}
final String nr = message.getOriginatingAddress();
Can someone point me whats wrong here ?
PS: SMSConstants and PhoneConstants are all framework classes i took from AOSP to get it running because those APIs are non public
[1] http://twit88.com/home/utility/sms-pdu-encode-decode

can i able to send broadcast to default sms application in android?

This is my code:
public class MMSReciever extends BroadcastReceiver
{
#Override
public void onReceive(Context context, Intent intent)
{
String incomingNumber = null;
if(intent.getAction().equals("android.provider.Telephony.WAP_PUSH_RECEIVED"))
{
Bundle bundle = intent.getExtras();
try
{
if (bundle != null)
{
String type = intent.getType();
if(type.trim().equalsIgnoreCase("application/vnd.wap.mms-message"))
{
byte[] buffer = bundle.getByteArray("data");
incomingNumber = new String(buffer);
int indx = incomingNumber.indexOf("/TYPE");
if(indx>0 && (indx-15)>0)
{
int newIndx = indx - 15;
incomingNumber = incomingNumber.substring(newIndx, indx);
indx = incomingNumber.indexOf("+");
if(indx>0)
{
incomingNumber = incomingNumber.substring(indx);
System.out.println("Mobile Number: " + incomingNumber);
}
}
}
I have bundle data with me when sms arrives to my device .Then can i able to send broadcast with this bundle data to default sms application
If you getting a sms broadcast event, you don't need to send from your side. As the same broadcast will be received by all applications watching for that intent.
Now unless, you want to change something. then you need to cancel the broadcast and make your own broadcast and fire it. and yes you can do that. make sure, your receiver priority is high enough to receive event before other apps do.
Hope this is what you asking.

Android broadcastreceiver creates new instances

Well, I have a class extending broadcastreceiver which is listening for messages. Now whenever it receives a message I creates a new instance of my app. So when I am closing it I have to tap back button 2 times.
public class SMSReceiver extends BroadcastReceiver {
public void onReceive(Context context, Intent intent) {
Bundle myBundle = intent.getExtras();
SmsMessage [] messages = null;
String strMessage = "";
String phoneNumber = "";
if (myBundle != null) {
Object [] pdus = (Object[]) myBundle.get("pdus");
messages = new SmsMessage[pdus.length];
for (int i = 0; i < messages.length; i++) {
messages[i] = SmsMessage.createFromPdu((byte[]) pdus[i]);
strMessage += "SMS From: " + messages[i].getOriginatingAddress();
strMessage += " : ";
strMessage += messages[i].getMessageBody();
strMessage += "\n";
phoneNumber = messages[i].getDisplayOriginatingAddress();
}
if (phoneNumber.equals("T-Mobile")) {
Toast.makeText(context, strMessage, Toast.LENGTH_SHORT).show();
abortBroadcast();
}
}
}
}
First of all, I don't really think it is creating a new instance of your app. What is more likely happening is that an activity is being brought to the front. I think you should look at the manifest or post it so we can see how the broadcasts are being directed. It could be that the target of the broadcast also has the effect of starting the activity. So check the manifest, there is nothing in the broadcast receiver that will cause this. Having said that its really up to the Android OS what gets shown when. But as far as two instances. Thats just not happening.
PS. I don't know the exact reason but I would say probably don't issue Toast from a broadcast reeiver, instead communicate to an activity using startActivity().

Listen to incoming multipart SMS message

I can catch newly incoming SMS messages. But if that is a multipart message, my broadcast receiver receives all parts of the message at several times.
Is there a way to receive the whole message at one time - like default messaging app does?
Holy...!
After reading the Android source (this file), I realize that this is such a stupid question...
Here is my receiver:
#Override
public void onReceive(Context context, Intent intent) {
Log.d(ClassName, "received SMS");
Bundle bundle = intent.getExtras();
if (bundle != null) {
Object[] pdus = (Object[]) bundle.get("pdus");
// here is what I need, just combine them all :-)
final SmsMessage[] messages = new SmsMessage[pdus.length];
Log.d(ClassName, String.format("message count = %s", messages.length));
for (int i = 0; i < pdus.length; i++) {
messages[i] = SmsMessage.createFromPdu((byte[]) pdus[i]);
}
}
}// onReceive()
Oops... I was too lazy to look at my code. I already got all parts of the message at a time.

Categories

Resources