Skip to content

Instantly share code, notes, and snippets.

@davinctor
Created February 25, 2016 13:01
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save davinctor/fec6902ce64370eaaab8 to your computer and use it in GitHub Desktop.
Save davinctor/fec6902ce64370eaaab8 to your computer and use it in GitHub Desktop.
**
* Receiver for detecting new sms
*/
public class SmsReceiveUtil {
public static final String TEST_ACTION = "TEST_SMS_RECEIVED";
private static final String EXTRA_BODY = MiscellaneousUtils.getExtra("body");
private final ObservableImpl observable;
private SmsReceiveUtil() {
observable = new SmsObservable();
}
public static void sendTestBroadcast(@NonNull Context context, @NonNull String body) {
Intent intent = new Intent(TEST_ACTION);
intent.putExtra(EXTRA_BODY, body);
context.sendBroadcast(intent);
}
public void addSmsObserver(@NonNull SmsObserver smsObserver) {
AssertionUtils.assertNotNull(smsObserver, "SMS observer");
observable.addObserver(smsObserver);
}
public void removeSmsObserver(@NonNull SmsObserver smsObserver) {
AssertionUtils.assertNotNull(smsObserver, "SMS observer");
observable.deleteObserver(smsObserver);
}
public void cleanup() {
observable.deleteObservers();
}
@SuppressWarnings("deprecation")
public void onReceive(Intent intent) {
if (TEST_ACTION.equals(intent.getAction())) {
checkAndNotify(intent.getStringExtra(EXTRA_BODY));
return;
}
if (!Telephony.Sms.Intents.SMS_RECEIVED_ACTION.equals(intent.getAction())) {
return;
}
Bundle bundle = intent.getExtras();
if (bundle == null) {
return;
}
Object[] pdus = (Object[]) bundle.getSerializable("pdus");
String format = intent.getStringExtra("format");
if (pdus == null)
return;
SmsMessage[] msgs = new SmsMessage[pdus.length];
for (int i = 0; i < msgs.length; i++) {
if (Build.VERSION.SDK_INT < Build.VERSION_CODES.M) {
msgs[i] = SmsMessage.createFromPdu((byte[]) pdus[i]);
} else {
msgs[i] = SmsMessage.createFromPdu((byte[]) pdus[i], format);
}
if (msgs[i] == null)
continue;
String msgBody = msgs[i].getMessageBody();
if (TextUtils.isEmpty(msgBody))
continue;
checkAndNotify(msgBody);
}
}
private void checkAndNotify(String msgBody) {
observable.setChanged();
observable.notifyObservers(msgBody);
}
public static final class Factory {
private Factory() { }
public static SmsReceiveUtil create() {
return new SmsReceiveUtil();
}
}
private static class SmsObservable extends ObservableImpl { }
public static abstract class SmsObserver implements Observer {
@Override
public final void update(Observable observable, Object data) {
if (observable instanceof SmsObservable) {
if (data instanceof String) {
String str = (String) data;
if (!TextUtils.isEmpty(str) && isMatchesFilter(str) ){
String target = retrieveTargetMessage(str);
if (!TextUtils.isEmpty(target)){
onMatch(target);
}
}
}
}
}
/** in this method you should check is this sms message belongs to your app(observer) or is it other message
* @return true if it is target message. True by default */
public boolean isMatchesFilter(String source) {
return true;
}
/** in this method you should retrieve target message from source message. By example with using regex mask.
* By default source message is not changed. Override to provide own
* @return source message, without identifier(key) inside*/
public String retrieveTargetMessage(String source) {
return source;
}
protected abstract void onMatch(@NonNull String string);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment