Skip to content

mid_registrar/usrloc: fix De-REGISTER failures on cluster peers (#3845)#3883

Open
denyspozniak wants to merge 1 commit intoOpenSIPS:masterfrom
denyspozniak:fix/3845-mid-registrar-kv-replication
Open

mid_registrar/usrloc: fix De-REGISTER failures on cluster peers (#3845)#3883
denyspozniak wants to merge 1 commit intoOpenSIPS:masterfrom
denyspozniak:fix/3845-mid-registrar-kv-replication

Conversation

@denyspozniak
Copy link
Copy Markdown

Description

Closes #3845

Problem

In full-sharing-cluster mode, every replicated AoR insert logs the
following on peer nodes, and the AoR can never be De-REGISTER'd
upstream when it expires:

ERROR:usrloc:store_deserialize: bad JSON input or oom
ERROR:mid_registrar:unregister_record: 'from' key not found, skipping De-REGISTER
ERROR:mid_registrar:mid_reg_aor_event: failed to unregister contact

Cause

Since 343f452c1, replicate_urecord_insert() ships
r->kv_storage. But in mid_registrar (save_restore_req_contacts)
store_urecord_data() runs after ul.insert_urecord(), so the
INSERT packet is broadcast with an empty map. Peers cJSON_Parse("")
→ NULL, and the missing keys (from, to, callid, main_reg_uri,
ct_uri, last_cseq) break De-REGISTER on expiry.

Fix

Mirror the existing ucontact pattern (pre_replicate_cb): add an
optional pre-replication callback to insert_urecord() so the caller
can fill kv_storage between mem_insert_urecord() and
replicate_urecord_insert(). mid_registrar plugs
mid_reg_store_aor_data into that hook in the throttle-AoR path.
All other call sites pass NULL, NULL — no behaviour change.

Verified

2-node 127.0.0.1 cluster, mid_registrar mode 2 + usrloc
full-sharing-cluster. After the fix, node2's bin_pop_str for
REPL_URECORD_INSERT already contains the full kv map, no
store_deserialize or unregister_record errors, and De-REGISTER
reaches the main registrar on expiry.

Fixes the race in `full-sharing-cluster` mode where peers received
REPL_URECORD_INSERT packets with an empty kv_storage. The serialization
that 343f452 added shipped whatever was in r->kv_storage at replicate
time, but mid_registrar's store_urecord_data() ran *after*
ul.insert_urecord() — so peers saw an empty store and later failed to
issue De-REGISTERs:

  ERROR:usrloc:store_deserialize: bad JSON input or oom
  ERROR:mid_registrar:unregister_record: 'from' key not found, skipping De-REGISTER
  ERROR:mid_registrar:mid_reg_aor_event: failed to unregister contact

Mirror the existing ucontact pattern (ucontact_info_t.pre_replicate_cb):
extend insert_urecord() with an optional pre-replication callback that
the caller can use to attach record-level data between mem_insert and
replicate_urecord_insert. mid_registrar wires mid_reg_store_aor_data
into the throttle-AoR save path so the kv_storage is populated before
the INSERT packet is built.

Closes OpenSIPS#3845

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

[BUG] ERROR:mid_registrar:unregister_record: 'from' key not found, skipping De-REGISTER

2 participants