You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何通过Android SipManager SIP栈向手机号发起呼叫?

解决Android SipManager无法呼叫手机号的问题

看起来你遇到的核心问题是SIP到公共电话网(PSTN)的呼叫格式不匹配——那些能正常工作的软SIP电话已经帮你自动处理了手机号到合法SIP URI的转换,但你直接把手机号作为SipProfile的用户名来构造呼叫,SIP服务器无法识别该如何路由到PSTN网络。

下面是具体的解决步骤和代码调整建议:

1. 先确认你的SIP服务商的呼叫规则

不同SIP服务商对手机号/固话的呼叫格式要求不一样,常见的规则有这几种:

  • 格式1:手机号(带完整国家码)作为用户名,拼接你的SIP域名,比如 sip:0041766666@your-sip-domain.com
  • 格式2:无需拼接域名,直接用手机号作为用户名(部分服务商支持内部自动路由到PSTN)
  • 格式3:需要添加特殊前缀(比如0或9)触发PSTN呼叫,比如 sip:90041766666@your-sip-domain.com

你可以先打开能正常呼叫的软SIP电话,查看它的呼叫日志(大部分软电话都有信令日志功能),找到INVITE请求里的To头格式,照着这个格式构造SipProfile就不会错。

2. 修改你的SipProfile构造代码

以最通用的格式1为例,调整代码如下:

SipProfile.Builder builder;
SipProfile toCall;
try {
    // 正确构造:带国家码的手机号作为用户名,SIP域名保持和注册账号一致
    builder = new SipProfile.Builder("0041766666", DOMAIN);
    // 如果你的服务商要求特定端口/协议,取消以下注释
    // builder.setProtocol("UDP");
    // builder.setPort(5090);
    toCall = builder.build();

    SipSession.Listener ssl = new SipSession.Listener() {
        @Override
        public void onCallEnded(SipSession session) {
            super.onCallEnded(session);
            try {
                if (call != null) {
                    call.endCall();
                }
            } catch (SipException e) {
                e.printStackTrace();
            }
            session.endCall();
        }
    };
    call.makeCall(toCall, manager.createSipSession(profile, ssl), 30);
} catch (Exception e) {
    // 添加异常捕获,方便排查初始化失败问题
    e.printStackTrace();
}

如果你的服务商支持格式2,直接用手机号作为用户名,域名仍填你的SIP服务商域名即可。

3. 额外检查项

  • 确认你的SIP账号已开通PSTN呼叫权限:部分SIP账号默认仅支持SIP地址互呼,需要额外开通打手机号/固话的权限
  • 检查网络连通性:确保Android设备能访问SIP服务器的出站端口(默认5060,部分服务商是5090),没有被防火墙或运营商拦截
  • 对比信令排查差异:用Wireshark抓包,对比软电话和你的代码发起的INVITE请求,看是否有头字段或参数差异(比如Contact头、From头格式)

内容的提问来源于stack exchange,提问作者Tim

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.14 07:15:14