I am writing an Android application which will place a SIP call. I want to use the native Android SIP APIs and have found documentation under:
http://developer.android.com/guide/topics/connectivity/sip.html and
http://developer.android.com/reference/android/net/sip/SipManager.html
Although I could regsiter with a SIP provider and start a call, it looks like this is too low-level. I want to just hand off the SIP call to the native Android phone app and give it a SIP address to call and assume that the user has already registered a SIP account in the Android phone app.
I thought that there must be an Intent for this, like http://developer.android.com/reference/android/content/Intent.html#ACTION_DIAL where I could provide a SIP address, like this:
Uri phoneCall = Uri.parse("tel:1234567890");
Intent caller = new Intent(Intent.ACTION_DIAL, phoneCall);
startActivity(caller);
but my experiments were unsuccessful. Do I have to use SipManager or is there an Intent I could use?
Assuming you've already created a global SIP-account:
Uri phoneCall = Uri.parse("sip:[number]#[domain]");
Just replace number and domain with the appropriate values.
Related
I've built a WebRTC softphone client on android (using React Native) but the service uses proper uris for dialing
(not just telephone numbers) so in order to get Connection Service integration we use a PhoneAccount and I set the allowable uri type to include SCHEME_SIP - without it, I can't dial using the tel: uri as it doesn't follow the right format - a UI alert pops up telling me so.
All is good, everything works up until the phone gets rebooted and the PhoneAccount disappears from the list and we can no longer make/receive calls without opening the app up again and enabling the PhoneAccount.
I use a project called react-native-callkeep to handle callkit/connection service and you can see the patch where I added support for SIP uris below.
https://github.com/AGProjects/sylk-mobile/blob/master/patches/react-native-callkeep%2B4.0.1.patch#L123
So yes, all works great until a reboot and adb shows these logs during that reboot.
01-18 17:31:49.827 2435 2435 D SIP : [SipAccountRegistry] verifyAndPurgeInvalidPhoneAccounts, deleting account: ComponentInfo{retracted.app.id/io.wazo.callkeep.VoiceConnectionService}, ***, UserHandle{0}
01-18 17:31:49.829 1520 2898 I Telecom : CallsManager: Sending phone-account ComponentInfo{retracted.app.id/io.wazo.callkeep.VoiceConnectionService}, ***, UserHandle{0} unregistered intent as user: TSI.uPA#AQs
01-18 17:31:49.829 1520 2898 I Telecom : CallsManager: Sending phone-account unregistered intent to default dialer: TSI.uPA#AQs
which after a little googling takes you to...
https://android.googlesource.com/platform/packages/services/Telephony/+/a294ae5342410431a568126183efe86261668b5d/sip/src/com/android/services/telephony/sip/SipAccountRegistry.java#126
So if your Phone Account has a SIP Scheme attached to it and you dont have a corresponding SipProfile attached, your calling account/phoneAccount gets deleted... useful.
So I've made a sip profile with the name being the same as the ID of the phone account.... but it looks like it doesnt get saved in the SipProfileDb (referenced in that code)...and then on a reboot of course it isnt in the DB for the check... and we go round in circles. As far as I can see theres no way for me to access that sipPorofileDb and its purely there for accounts made in the Settings UI of the native phone app.
A) can I bring in SipProfileDb into my code and save to it? If this is meant to be done; then why can't I find any docs around this?
B) if I can't what am I missing? The fact I can create a PhoneAccount with a SIP uri enabled on it, for it only to be deleted by the telecom service is super weird and feels like a bug.
I have an app which creates a SIP profile using SipProfile.Builder and I'm able to place a SIP call using that profile by calling makeAudioCall().
I was wondering if it's possible to get the native dialler to use my SIP profile to place a call using an Intent? I tried invoking the native dialler via an intent:
Intent dial = new Intent(Intent.ACTION_CALL);
Uri call = Uri.parse("sip:123455#sip.domain.com");
dial.setData(call);
dial.addFlags(Intent.FLAG_ACTIVITY_NEW_TASK);
startActivity(dial);
but it does not place the call from the SIP profile my app created.
What I want is to avoid re-inventing the wheel in creating my own custom dialler UI and reuse the native dialler for this.
Is this possible?
Can any body suggest me, any Android Intent to make SIP Call? or even third party framework/lib/app, which has the facility to be invoked using an intent and some parameters will be fine.
Kindly Note: Not regular phone call, needed intent for SIP/Internet Phone call.
Thanks In Advance.
1) Do you mean you want to implement a SIP app?
Then, check this:
http://developer.android.com/guide/topics/connectivity/sip.html
Make you app and listen to ACTION_CALL.
Or
2) Do you want to invoke a calling app?
Then the usual ACTION_CALL will do.
(For example, in my phone ACTION_CALL will prompt me if I want to use Skype or Phone App)
Added:
I am using SipDroid in one of my phone. This is what happens when I try to make call:
Alternatively, if you meant to create an Intent, you could trying looking into declaring a custom scheme within an IntentFilter in your AndroidManifest.xml, such as calling an Intent with a sip:<numberToCall> will open your Activity.
Can I make an emergency call programmatically in Android 2.1?
I've tried to use something like this:
Intent intent = new Intent(Intent.ACTION_CALL, Uri.parse(telUri));
intent.setFlags(Intent.FLAG_ACTIVITY_NEW_TASK|Intent.FLAG_ACTIVITY_NO_USER_ACTION);
appCtx.startActivity(intent);
but the only thing that I can do is call the system dialpad with the specified emergency number.
I have to push the 'dial' button to make call. Is there any way to skip the dialer?
No, you can't. The phone activity (actually part of the Contacts application) is what responds to the ACTION_CALL intent and you can't change how it handles it. This is done specifically to make sure the user confirms the number he/she wishes to dial.
I am working on the security aspects of my android application.
I would like to know about the ways to secure the Intent data and extras while sending it from one application to another so that no other application other than these two can snoop it.
One of the brute-force approaches would be to use android's encryption-decryption to encode intent data, is there a better way to achieve the same ??
Thanks in advance.
As pointed in the other answers, although you can send an intent to a fully qualified activity, nothing prevents someone from creating an application with the same package.
You might want to add an additional security step to this scheme:
First send a 'Challenge' intent to the remote activity (it should, for example, encrypt a random string you provided using a shared passphrase and send it back to you).
If that first security step is ok, you may freely send unencrypted messages to this remote app by using its fully qualified activity.
This is rather lame security, but perhaps it's sufficient for your needs.
Please take a look at CommonsWare's comment below.
A more secure way might be to code your activity as a Bound Service, keeping the Challenge step, but by means of more private communication.
My guess is that if you use an explicit intent, i.e. specifying the class to which the intent is to be sent to, then no other class can intercept that intent and look at its data.
This method however, may fail if the class name in the application that you're trying to send the information to changes.
If an intent specifies the the target, which is part of the sender application's package, then other applications won't have the chance to capture it - it will be delivered to the intended receiver.
On the other hand, if you send an intent to another application, there is no guarantee that the receiver of the intent will have the implementation you expect: if you send your intent to com.mycompany.security.SecureReceiver, but instead of your application, another application is installed with the given class description, than you will send your intent to that application.
Also, Android is an open system. If someone compiles his own application framework, than he can manipulate the Intent delivery system.
Do you want to protect your data from the user, or from malicious applications?