Design and Implementation of a Virtual Phone Number Service with XB and AXB Modes
This article explains the concept, practical applications, version evolution, and deployment strategy of a virtual phone number service, detailing XB and AXB binding modes, asynchronous retry mechanisms, concurrency handling, and monitoring to ensure reliable integration with third‑party PSTN providers.
1. Introduction
Virtual numbers are an internet‑based telephone service that binds a virtual number to a user's mobile or other communication device, allowing calls to be made and received on different devices while protecting privacy, recording call content, and providing additional features.
Privacy protection: The virtual number acts as an intermediary, hiding the user's real phone number.
Flexibility: Users can choose numbers from different regions or even international numbers.
Multi‑functionality: Supports call forwarding, voicemail, SMS forwarding, and other value‑added services.
Enterprise use: Enables customer service hotlines, call centers, and improves customer satisfaction and operational efficiency.
Overall, virtual numbers provide a flexible, safe, and convenient communication method for both personal and enterprise scenarios.
2. Practice and Application
In store‑business scenarios, staff or users need to dial numbers for sales or inquiries. By using a third‑party virtual‑number service to bind both parties' mobile numbers, calls can be made through the virtual number, protecting user privacy and allowing the store to monitor scripts and analyze data.
Second‑hand transaction virtual‑number binding diagram
2.1 Terminology
A : User's mobile number
X : Virtual number / intermediary
B : Staff's mobile number
Third‑party : Provider of the virtual‑number service
Carrier : Telecom operators such as China Telecom, Unicom, Mobile
2.2 XB Mode
In XB mode, the staff number B is bound to the virtual number X. After binding, any call to X is automatically routed to B.
2.3 AXB Mode
In AXB mode, the user number A and staff number B are both bound to the virtual number X. When A dials X, B sees the call coming from X; similarly, when B dials X, A sees the call coming from X.
2.4 Virtual‑Number Call Flowchart
Call flow diagram
3. Version Evolution of Third‑Party Interaction
As the business evolved, the interaction flow with the third‑party service has been revised multiple times. The following sections describe the initial and latest versions and the problems encountered.
3.1 Initial Version Binding Flow
The early version had a simple bind/unbind flow. However, frequent time‑outs occurred because the interaction with the third‑party was synchronous HTTP‑based; if the third‑party response exceeded the app's timeout, the request was circuit‑broken and failed.
3.2 Latest Version Interaction Flow
To improve reliability, the latest version introduces the following optimizations:
Optimized conceptual model diagram
Timeout handling: Provide an interface to query binding status; the app polls this interface. Pre‑validation code is synchronized, and the bind/unbind calls are made asynchronous.
//开启异步线程,执行重试方法,进行与第三方接口绑定。
ThreadUtil.executor.submit(() -> {
try {
log.info("act=AppOperationHandler type=retryBindXb_retryBindAxb_start");
pstnRetryService.retryBindXb(appOpnParam);
} catch (Exception e) {
log.error("act=AppOperationHandler type=retryBindXb_retryBindAxb_fail", e);
}
});Concurrency handling: Use optimistic locking to avoid concurrent conflicts and add an intermediate "in‑progress" state for bindings.
NOT_BIND(1, "未绑定"),
BIND(2, "已绑定"),
OPERATION(3, "操作中");Exception handling: Capture time‑outs, server errors, etc., and retry via AOP‑based annotation and MQ messages to guarantee consistency.
@Override
@ZZMQRetry(errorHandler = "onErrorMsgPcBindXb", firstSyncCall = true)
public void retryBindXb(PstnBindParam pstnBindParam) {
//调用第三方接口进行绑定
String bindId = bindVirtualNumber(pstnBindParam);
Boolean executeResult = transactionTemplate.execute(status -> {
try {
//创建绑定记录
pstnBindRecordService.insertBindRecord(bindId, pstnBindParam);
//状态流转至已绑定
return this.xbOpnStateToBind(pstnBindParam.getAssignVirtualNum());
} catch (Exception e) {
status.setRollbackOnly();
return Boolean.FALSE;
}
});
if (Objects.isNull(executeResult) || !executeResult) {
throw new BusinessException("修改状态异常进行重试");
}
}Alert handling: When retries exceed a threshold, send an alert message.
public void onErrorMsgPcBindXb(PstnBindParam param) {
int retryCount = RetryContext.getRetryCount();
log.info("act=PcOperationHandler type=onErrorMsgPcBindXb retryCount={} ", retryCount);
if (retryCount >= RETRY_MAX_NUM) {
WxMsgUtil.sendMsg(GROUP, "绑定XB重试" + retryCount + "次,仍未成功请排查,虚拟号:" + param.getVirtualNum());
}
}These measures improve stability and reliability, reducing time‑outs and inconsistent binding states, thereby enhancing the staff's experience.
AXB binding flow diagram
The optimized AXB flow launches a new thread for the binding task; if an error occurs, the thread restarts the operation. Asynchronous processing and status polling solve the high latency of third‑party interaction, while retries guarantee consistency and monitoring alerts provide real‑time fault detection.
In production, more complex scenarios such as simultaneous XB and AXB bindings require additional safeguards to avoid time‑outs and ensure state consistency.
Suggested steps to achieve this include adding separate status fields, using optimistic locks, creating independent threads for each mode, transitioning states to "bound" after completion, and providing a dedicated polling interface for status queries.
4. Deployment Plan
When optimizing versions, keep the entry point unchanged and modify only the underlying implementation. This facilitates gray‑release testing and ensures users experience no new obstacles after an upgrade.
/**
* 是否为灰度虚拟号码
*
* @param grayVirtualNumber
* @return
*/
public boolean isGrayVirtualNumber(String grayVirtualNumber) {
return flag || grayVirtualNumberList.contains(grayVirtualNumber);
}Based on Apollo configuration, certain city virtual numbers are set for gray testing while others continue using the old version. After successful testing, the full rollout can be activated.
5. Retry Component
The functions annotated with @ZZMQRetry are intercepted by AOP; the request does not execute the retry synchronously but instead sends an MQ message, and a consumer group automatically processes the retry function.
6. Summary
Interaction with third‑party services inevitably involves uncontrollable factors. To ensure system stability and reliability, it is essential to implement preventive measures such as exception handling, timeout settings, retry mechanisms, circuit breakers, and monitoring with alerts. These safeguards protect the system from failures caused by external uncertainties.
About the author
Xu Xinhui, Backend Development Engineer, ZheZhe Store Technology Department
References
Tencent Cloud PSTN Number Protection Business – Second‑hand Transaction Virtual Number Binding Image
Zhuanzhuan Tech
A platform for Zhuanzhuan R&D and industry peers to learn and exchange technology, regularly sharing frontline experience and cutting‑edge topics. We welcome practical discussions and sharing; contact waterystone with any questions.
How this landed with the community
Was this worth your time?
0 Comments
Thoughtful readers leave field notes, pushback, and hard-won operational detail here.