RFC 3680

A Session Initiation Protocol (SIP) Event Package for Registrations

πŸ“… published March 2004, from ietf

RFC 3680 πŸŽ€ A Session Initiation Protocol (SIP) Event Package for Registrations

okay bestie, let's get into it πŸ’– this is RFC 3680, a Standards Track doc from March 2004, written by J. Rosenberg at dynamicsoft. It's from the Network Working Group, and it defines a SIP event package for registrations ✨. The header in this excerpt doesn't list anything it obsoletes or updates, so there's nothing to chase there 🧚


Status of This Memo ✨

This document is an Internet standards track protocol for the Internet community, and it's asking for discussion and suggestions for improvements 🌸 For the standardization state and status of this protocol, check the current edition of the "Internet Official Protocol Standards" (STD 1). Distribution of this memo is unlimited 🫢

Copyright (C) The Internet Society (2004). All Rights Reserved.

Abstract πŸ¦‹

This document defines a Session Initiation Protocol (SIP) event package for registrations. Through its REGISTER method, SIP lets a user agent create, modify, and delete registrations. Administrators can also change registrations to enforce policy, so these registrations are a piece of network state that can change dynamically πŸ‘€ Plenty of user agents want to hear about those changes, and this event package is the mechanism that lets them request and get those notifications πŸ”₯

Table of Contents 🌈

1.  Introduction .................................................  2
2.  Terminology ..................................................  3
3.  Usage Scenarios ..............................................  3
    3.1.  Forcing Re-Authentication ..............................  3
    3.2.  Composing Presence .....................................  3
    3.3.  Welcome Notices ........................................  4
4.  Package Definition ...........................................  4
    4.1.  Event Package Name .....................................  4
    4.2.  Event Package Parameters ...............................  5
    4.3.  SUBSCRIBE Bodies .......................................  5
    4.4.  Subscription Duration ..................................  5
    4.5.  NOTIFY Bodies ..........................................  6
    4.6.  Notifier Processing of SUBSCRIBE Requests ..............  6
    4.7.  Notifier Generation of NOTIFY Requests .................  7
          4.7.1.  The Registration State Machine .................  7
          4.7.2.  Applying the state machine .....................  9
    4.8.  Subscriber Processing of NOTIFY Requests ...............  9
    4.9.  Handling of Forked Requests ............................  9
    4.10. Rate of Notifications .................................. 10
    4.11. State Agents ........................................... 10
5.  Registration Information ..................................... 10
    5.1.  Structure of Registration Information .................. 10
    5.2.  Computing Registrations from the Document .............. 14
    5.3.  Example ................................................ 15
    5.4.  XML Schema ............................................. 16
6.  Example Call Flow ............................................ 18
7.  Security Considerations ...................................... 21
8.  IANA Considerations .......................................... 21
    8.1.  SIP Event Package Registration ......................... 21
    8.2.  application/reginfo+xml MIME Registration .............. 22
    8.3.  URN Sub-Namespace Registration for
          urn:ietf:params:xml:ns:reginfo ......................... 23
9.  References ................................................... 23
    9.1.  Normative References ................................... 23
    9.2.  Informative References ................................. 24
10. Contributors ................................................. 25
11. Acknowledgements ............................................. 25
12. Author's Address ............................................. 25
13. Full Copyright Statement ..................................... 26

1. Introduction ✨

SIP [1] gives you everything you need to set up and keep up communications sessions between users, and one of its jobs is the registration operation πŸ’… A registration is a binding between a SIP URI (called an address-of-record) and one or more contact URIs. Those contacts are extra resources you can reach to get hold of the user behind that address-of-record 🫢 When a proxy gets a request inside its own domain, it treats the Request-URI as an address-of-record, then uses the contacts bound to it to forward (or redirect) the request.

The SIP REGISTER method is how a user agent works with registrations. Contacts can be added or removed, and you can ask for the current set of contacts. Administrator policy can also change registrations 😭 If someone is suspected of fraud, their registration can get deleted so they can't receive any requests. And registrations expire after a while if nobody refreshes them.

Registrations are a dynamic bit of state that the network keeps track of, and plenty of user agents want to know when they change πŸ‘‘ The SIP Events Framework [2] is the generic framework for subscribing to and getting notified about SIP events. It defines the SUBSCRIBE and NOTIFY methods and introduces the idea of a package. A package is a concrete use of the event framework for one class of events. Packages already exist for user presence [9], for example. This specification defines the package for registration state 🌸

2. Terminology πŸ’–

In this document, the key words "MUST", "MUST NOT", "REQUIRED", "SHALL", "SHALL NOT", "SHOULD", "SHOULD NOT", "RECOMMENDED", "MAY", and "OPTIONAL" are to be interpreted as described in BCP 14, RFC 2119 [3] and indicate requirement levels for compliant implementations 🧚

3. Usage Scenarios πŸ¦‹

There are loads of ways to use this event package. A few are written up here, just to illustrate 🌈

3.1. Forcing Re-Authentication πŸ”₯

Lots of SIP devices are expected to be wireless and always on, which means they stay registered to the network all the time. Unfortunately, devices like that have been compromised before πŸ’€ So an administrator will want to end or shorten a registration, then ask the device to re-register so it gets re-authenticated. To make that work, the device subscribes to the registration event package for the address-of-record it's registering contacts against. When the administrator shortens the registration (say, because fraud is suspected), the registration server sends a notification to the device. The device can then re-register and re-authenticate itself. If it can't re-authenticate, the registration expires shortly after πŸ™ˆ

3.2. Composing Presence πŸŽ€

This is a big one: the relationship between this event package and the event package for user presence [9] πŸ‘€ Presence is about how willing and able a user is to communicate with other users on the network. It's made up of a set of contact addresses, one for each way of reaching the user. For voice, for example, the contact address is typically an address-of-record. Whether that contact is open or closed can depend on a bunch of things, including the state of any registrations against that address-of-record. So registration state works as an input to figuring out a user's presence state. Basically, registration state is "raw" data, and it gets combined with other info about the user to produce a document describing their presence ✨

This event package also lets a presence server be split off from a SIP registration server while still using registration info to build presence documents πŸ’… When a presence server gets a presence subscription for some user, it subscribes to the registration server for the registration event package. That way it learns the registration state for that user and can use it to generate presence documents 🫢

3.3. Welcome Notices 🌸

Welcome notices are a common service on mobile networks today πŸ’œ When a user turns on their phone in a foreign country, they get a message welcoming them to the country and telling them about transportation services, for example.

To build this in a SIP system, an application server can subscribe to the user's registration state πŸ”₯ When the user turns on their phone, the phone generates a registration. That results in a notification going to the application saying the user has registered. The application can then send a SIP MESSAGE request [10] to the device to welcome the user and share any necessary info 🧚

4. Package Definition πŸ‘‘

This section fills in the details you need to specify an event package, as defined in Section 4.4 of [2] 🌈

4.1. Event Package Name πŸ¦‹

The SIP Events specification says package definitions have to specify the name of their package or template-package ✨

The name of this package is "reg". As [2] specifies, this value shows up in the Event header of SUBSCRIBE and NOTIFY requests πŸ’–

Example:

Event: reg

4.2. Event Package Parameters πŸŽ€

The SIP Events specification says package and template-package definitions have to specify any package-specific parameters of the Event header they use 🫢

No package-specific Event header parameters are defined for this event package πŸ™ˆ

4.3. SUBSCRIBE Bodies πŸ’…

The SIP Events specification says package or template-package definitions have to define how bodies are used in SUBSCRIBE requests, if at all πŸ”₯

A SUBSCRIBE for registration events MAY contain a body. That body would be used to filter the subscription 🌸 How such a body is defined is outside the scope of this specification 🧚

A SUBSCRIBE for the registration package MAY be sent without a body. That means the default registration filtering policy has been requested. The default policy is:

  • Notifications are generated every time there's any change in the state of any of the registered contacts for the resource being subscribed to. Those notifications only contain information on the contacts whose state has changed πŸ‘€
  • Notifications triggered from a SUBSCRIBE contain full state (the list of all contacts bound to the address-of-record) ✨

Of course, the server can apply any policy it likes to the subscription πŸ‘‘

part 1 of 5 is done bestie πŸ’– next up is 4.4 Subscription Duration, so stay tuned πŸ¦‹

4.4. Subscription Duration πŸ¦‹

okay so the SIP Events spec requires package definitions to define a default value for subscription durations, and to discuss reasonable choices for durations when they're explicitly specified πŸ’…

registration state changes as contacts get created through REGISTER requests, and then time out if nobody refreshes them. So how fast it changes is basically tied to the typical registration expiration. The default expiration for registrations is 3600 seconds, so the default duration of subscriptions to registration state is a teeny bit longer: 3761 seconds 🧚. That helps avoid potential problems with subscription and registration refreshes coupling together. obviously, clients MAY include an Expires header in the SUBSCRIBE request if they want a different duration πŸ’–

4.5. NOTIFY Bodies πŸŽ€

the SIP Events spec requires package definitions to describe the allowed set of body types in NOTIFY requests, and to specify the default value used when there's no Accept header in the SUBSCRIBE request πŸ“

the body of a notification about a change in registration state is a registration information document. It describes some or all of the contacts tied to a particular address-of-record. All subscribers and notifiers MUST support the application/reginfo+xml format described in Section 5 🫢. The SUBSCRIBE request MAY contain an Accept header field. If there's no such header field, it defaults to application/reginfo+xml. If the header field is there, it MUST include application/reginfo+xml, and MAY include any other types that can represent registration information.

Of course, the notifications generated by the server MUST be in one of the formats specified in the Accept header field in the SUBSCRIBE request πŸ”₯

4.6. Notifier Processing of SUBSCRIBE Requests πŸ”

the SIP Events framework says packages should define any package-specific processing of SUBSCRIBE requests at a notifier, especially around authentication and authorization πŸ”

registration state can be sensitive info, ngl. So all subscriptions to it SHOULD be authenticated and authorized before approval. Authentication MAY be done using any of the techniques available through SIP, including digest, S/MIME, TLS, or other transport-specific mechanisms [1]. Authorization policy is up to the administrator, as always. That said, a few recommendations can be made πŸ’…

It is RECOMMENDED that a user be allowed to subscribe to their own registration state. These subscriptions are useful when there are lots of devices representing one user, and each device needs to learn the registration state of the others πŸ“±. We also expect applications and automata to be frequent subscribers to registration state. In those cases, authorization policy will typically be provided ahead of time πŸ€–.

4.7. Notifier Generation of NOTIFY Requests 🌸

the SIP Event framework requests that packages specify the conditions under which notifications get sent for that package, and how those notifications get constructed 🧠

to figure out when a notifier should send notifications about changes in registration state, we define a finite state machine (FSM) that represents the state of a contact for a particular address-of-record. Transitions in this state machine MAY result in the generation of notifications. These notifications carry info about the new state and the event that triggered the state change. Important: this FSM is just a model of the registration state machinery a server maintains. An implementation maps its own state machines onto this one in an implementation-specific manner πŸ¦‹

4.7.1. The Registration State Machine 🧚

the underlying state machine for a registration is shown in Figure 1. It's very simple ✨. An instance of this machine is tied to each address-of-record. When there are no contacts registered to the address-of-record, the state machine is in the init state. This state machine exists, and is well-defined, for every address-of-record in the domain, even if no contacts are registered to it. That's what lets a user agent subscribe to an address-of-record and learn that nothing is registered there πŸ™ˆ. When the first contact is registered to that address-of-record, the state machine moves from init to active.

                           +------------+
                           |            |
                           |    Init    |
                           |            |
                           +------------+
                                  |
                                  V
                           +------------+
                           |            |
                           |   Active   |
                           |            |
                           +------------+
                                  |
                                  V
                           +------------+
                           |            |
                           | Terminated |
                           |            |
                           +------------+

                   Figure 1: Registration State Machine

As long as there's at least one contact bound to the address-of-record, the state machine stays in the active state. When the last contact expires or gets removed, the registration transitions to terminated. From there, it immediately transitions back to init. This transition is invisible: it MUST NOT ever be reported to a subscriber in a NOTIFY request πŸ‘€.

This allows for an implementation optimization: the registrar can destroy the objects associated with the registration state machine once it enters terminated and a NOTIFY has been sent. Instead, the registrar can assume that if the objects for that state machine no longer exist, the state machine is in init.

In addition to this state machine, each registration is associated with a set of contacts, and each contact has its own state machine. Unlike the address-of-record FSM, which exists even when no contacts are registered, the per-contact FSM is instantiated when the contact is registered and deleted when it's removed. The diagram for the per-contact state machine is shown in Figure 2. This FSM has the same states as the registration state machine, but has many more transition events πŸ”₯.

When a new contact is added, its FSM is instantiated and moves into the active state. Because of that, the init state here is transient. There are two ways it can become active. One is through an actual SIP REGISTER request (the registered event), and the other is when the contact is created administratively or through some non-SIP means (the created event) πŸ’….

                                 +------+
                                 |      | refreshed
                                 |      | shortened
                                 V      |
    +------------+            +------------+            +------------+
    |            |            |            |            |            |
    |    Init    |----------->|   Active   |----------->| Terminated |
    |            |            |            |            |            |
    +------------+ registered +------------+ expired    +------------+
                   created                   deactivated
                                             probation
                                             unregistered
                                             rejected

                      Figure 2: Contact State Machine

The FSM stays in the active state for as long as the contact is bound to the address-of-record. When a contact is refreshed through a REGISTER request, the FSM stays in the same state, but a refreshed event is generated. Likewise, when an administrator changes the expiration time of a binding (without deleting it) to make the contact re-register and possibly re-authenticate, the FSM stays active, but a shortened event is generated 🌈.

When the contact is no longer bound to the address-of-record, the FSM moves to terminated, and once a NOTIFY is sent, the state machine is destroyed. So terminated is effectively transient 🫠. There are several reasons this can happen. The first is expired, which happens when the contact wasn't refreshed by a REGISTER request. The second is deactivated: the administrator has removed the contact as a valid binding, but still wants the client to try re-registering it. In contrast, rejected happens when an active contact is removed by the administrator, and re-registrations won't help re-establish it. That might happen if a user doesn't pay their bills, for example πŸ’€. The probation event happens when an active contact is removed by the administrator, and the administrator wants the client to re-register, but to do so at a later time ⏰. The unregistered event happens when a REGISTER request sets the expiration time of that contact to zero.

4.7.2. Applying the state machine ⭐

the server MAY generate a notification to subscribers when any event occurs in either the address-of-record or per-contact state machines, except for the transition from terminated to init in the address-of-record state machine. As noted above, a notification MUST NOT be sent in this case. For other transitions, whether the server sends a notification or not is policy dependent. However, several guidelines are defined πŸ“‹.

As a general rule, when a subscriber is authorized to receive notifications about a set of registrations, it is RECOMMENDED that notifications contain information about those contacts which have changed state (and thus triggered a notification), instead of delivering the current state of every contact in all registrations. However, notifications triggered as a result of a fetch operation (a SUBSCRIBE with Expires of 0) SHOULD result in the full state of all contacts for all registrations being present in the NOTIFY πŸ“¦.

4.8. Subscriber Processing of NOTIFY Requests πŸŽ€

the SIP Events framework expects packages to specify how a subscriber processes NOTIFY requests in any package-specific ways, and in particular how it uses NOTIFY requests to build a coherent view of the state of the subscribed resource. Typically, the NOTIFY only contains info for contacts whose state has changed. To build a coherent view of the total state of all registrations, the subscriber will need to combine NOTIFYs received over time. The details of this process depend on the document format used to convey registration state. Section 5 outlines the process for the application/reginfo+xml format πŸ’–.

4.9. Handling of Forked Requests ✨

okay so the SIP Events framework is pretty strict here πŸ’… it says every package has to spell out whether forked SUBSCRIBE requests are allowed to install multiple subscriptions πŸŽ€

registration state usually lives in one repository (whether that's sitting right next to a proxy/registrar or in its own database) πŸ—„οΈ so there's basically one spot where the contact info for any given address-of-record is stored πŸ“ that means one element with access to that repo can handle the subscription, no problem πŸ™Œ so there's zero real reason for a subscription to registration info to fork πŸ™…β€β™€οΈ which is why the rule is that a subscriber MUST NOT create multiple dialogs from a single subscription request 🚫 the steps that make sure only one dialog gets set up are in Section 4.4.9 of the SIP Events framework [2] πŸ“š literally the main character of this section is "one subscription, one dialog" πŸ’–

4.10. Rate of Notifications

the SIP Events framework also says packages need to define a max rate of notifications for themselves ⏱️

and this matters for congestion control 🌊 we don't want notifications going absolutely feral πŸ’€ so it's RECOMMENDED that the server doesn't send notifications to a single subscriber faster than once every 5 seconds ✨ chill pills, but make it make sense 🫢

4.11. State Agents

the SIP Events framework asks packages to think about what role state agents play in their design πŸ€”

and for this package? state agents have no role at all πŸ™ˆ zero involvement, not even a cameo ✨

5. Registration Information

5.1. Structure of Registration Information

okay this part is the big one, bestie πŸŽ€ registration information is an XML document [4] and it MUST be well-formed πŸ’… it SHOULD be valid too πŸ’– registration information documents MUST be based on XML 1.0 🌸 and MUST be encoded using UTF-8 🧚 this spec uses XML namespaces to identify registration information documents and document fragments 🏷️ the namespace URI for elements defined here is a URN [5], using the namespace identifier 'ietf' that's defined by [6] and extended by [7] πŸ¦‹ the full URN is:

urn:ietf:params:xml:ns:reginfo

a registration information document starts with the root element tag "reginfo" πŸ‘‘ inside it you can have any number of "registration" sub-elements, and each one holds the registration state for one particular address-of-record πŸ“¦ all the registration info for a single address-of-record MUST live inside one single "registration" element 🚫 it can't be split across several "registration" elements in the same document 😭 other elements from different namespaces MAY show up for extensibility 🧩 but elements or attributes from unknown namespaces MUST be ignored πŸ™ˆ the "reginfo" element has two attributes, and BOTH of them MUST be present πŸ’…

  • version: this one lets the recipient put registration info documents in the right order πŸ”’ versions start at 0 and go up by one for every new document sent to a subscriber πŸ“ˆ they're scoped within a subscription πŸŽ€ and versions MUST be representable using a 32 bit integer πŸ’œ
  • state: this tells you whether the document has the full registration state, or only the registrations that changed since the last document (partial) πŸ”„

note that the document format explicitly lets you convey info on multiple addresses-of-record 🫢 that's what makes subscribing to groups of registrations possible, where the group is identified by some kind of URI 🌈 for example, a domain could define sip:allusers@example.com as a subscribable resource that sends notifications whenever the state of any address-of-record in that domain changes πŸ”” iconic 😭

the "registration" element has a list of any number of "contact" sub-elements, and each one has info on a single contact πŸ“‡ other elements from different namespaces MAY be present for extensibility 🧩 and elements or attributes from unknown namespaces MUST be ignored πŸ™ˆ the "registration" element has three attributes, and all three MUST be present 🫢

  • aor: this holds a URI, which is the address-of-record this registration is about πŸ“
  • id: this identifies the registration πŸͺͺ it MUST be unique among all the other id attributes in other "registration" elements sent to the subscriber within their subscription πŸ” specifically, if two URIs identifying an address-of-record differ after canonicalization using the procedures in step 5 of Section 10.3 of RFC 3261 [1], then the id attributes in the "registration" elements for those addresses-of-record MUST differ ✌️ also, the id for a "registration" element for a particular address-of-record MUST stay the same across all notifications sent within the subscription πŸ”’
  • state: this shows the state of the registration 🚦 the valid values are "init", "active" and "terminated" πŸ’«

the "contact" element holds a "uri" element, an optional "display-name" element, and an optional "unknown-param" element πŸŽ€ other elements from different namespaces MAY be present for extensibility 🧩 and elements or attributes from unknown namespaces MUST be ignored πŸ™ˆ there are several attributes on "contact" that MUST be present πŸ’–

  • id: this identifies the contact πŸͺͺ it MUST be unique among all other id attributes in other "contact" elements conveyed to the subscriber within their subscription πŸ” specifically, if the URI for two contacts differ (based on the URI comparison rules in RFC 3261 [1]), then their id attributes MUST differ πŸ™…β€β™€οΈ but unlike the id for an address-of-record, if the URI for two contacts is the same, their id attributes SHOULD be the same across notifications 🫢 this one is SHOULD strength, not MUST strength, because it's hard to compute an id as a function of the URI without keeping extra state 🧠 no hash function applied to the URI can actually meet a MUST requirement 😭 that's because equality of the SIP URI isn't transitive πŸŒ€ a hash function that includes unknown URI parameters (meaning any NOT defined in RFC 3261) will always give a different value when two URIs are different, and usually the same value when the URIs are equal ✨
  • state: this shows the state of the contact 🚦 the valid values are "active" and "terminated" πŸ’«
  • event: this says which event pushed the contact state machine into its current state 🎬 valid values are registered, created, refreshed, shortened, expired, deactivated, probation, unregistered and rejected πŸ¦‹

if the event attribute is shortened, then the "expires" attribute MUST be present ⏳ it's an unsigned long integer for the number of seconds left until the binding is due to expire πŸ•°οΈ this attribute MAY be included with any event value where the contact is still active 🌈

if the event attribute is probation, then the "retry-after" attribute MUST be present πŸ” it's an unsigned long integer for how many seconds later the owner of the contact is expected to retry its registration πŸ“

a few optional bits too πŸŽ€ the "duration-registered" attribute tells you how long, in seconds, the contact has been bound to the address-of-record ⏲️ the "q" attribute gives the relative priority of this contact compared to other registered contacts πŸ‘‘ the "callid" attribute holds the current Call-ID carried in the REGISTER that last updated this contact πŸ“ž and the "cseq" attribute holds the last CSeq value in a REGISTER request that updated this contact πŸ”’

the "uri" element contains the URI for that contact πŸ”— the "display-name" element holds the display name for the contact 🏷️ and the "display-name" element MAY contain the xml:lang attribute to say what language the display name is in 🌍

the "unknown-param" element is for conveying contact header field parameters that aren't specified in RFC 3261 🧩 one example is the user agent capability parameters specified in [11] πŸ“± each "unknown-param" element describes one single contact header field parameter πŸ’… the name of the parameter goes in the mandatory name attribute of the "unknown-param" element, and the parameter's value is the content of the "unknown-param" element πŸ’– for contact header field parameters that have no value, the content of the "unknown-param" element is empty 🫧

5.2. Computing Registrations from the Document

okay so, a NOTIFY for registration info usually only tells you about the contacts whose state just changed ✨ which means you have to stitch every NOTIFY together over time if you want the full picture 🧩 The subscriber keeps a table for each registration it gets info about. Every registration is identified by its "id" attribute in the "registration" element πŸŽ€ Each table has a row for each contact in that registration, and each row is keyed by that contact's unique ID, which lives in the "id" attribute of the "contact" element πŸ’– The row holds that contact's state as given in its "contact" element. Each table also has a version number πŸ”’ The version number MUST be set to the "version" attribute of the "reginfo" element from the very first document you receive. Whenever a new document shows up, compare your local version number with the "version" attribute in the new doc πŸ‘€ If the new one is exactly one higher, bump your local number by one and process the doc πŸ™Œ If it's more than one higher, set your local number to the new value, process the doc, and the subscriber SHOULD generate a refresh request to trigger a full state notification 🚨 (you missed something, babe). If the new value is lower than your local version, toss the doc without processing it πŸ—‘οΈ

Processing depends on whether the document has full or partial state πŸ’… Full state is flagged by the "state" attribute of the "reginfo" element being "full" πŸ’― In that case you flush every table tied to this subscription and rebuild them from the doc: a brand new table for each "registration" element, and a brand new row in each table for each "contact" element 🧹 Partial state is flagged by "state" being "partial" 🧩, and then the doc just updates your existing tables. For each "registration" element, check whether a table already exists for it by comparing the "id" attribute of that registration with the ID tied to each table. If none exists, make one πŸ› οΈ Then, for each "contact" element in that registration, check whether a row exists by comparing the ID in the contact's "id" attribute with the ID tied to each row. If the contact isn't in the table, add a row and set its state to whatever that "contact" element says 🌱 If it is already there, update its state to match that "contact" element πŸ”„ And here's the tea 🍡: if a row gets updated or created and its state is now terminated, that entry MAY be removed from the table at any time 🧹

5.3. Example

Here's an example registration information document πŸŽ€

<?xml version="1.0"?>
    <reginfo xmlns="urn:ietf:params:xml:ns:reginfo"
        xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
                 version="0" state="full">
      <registration aor="sip:user@example.com" id="as9"
                    state="active">
        <contact id="76" state="active" event="registered"
                 duration-registered="7322"
                 q="0.8">
                 <uri>sip:user@pc887.example.com</uri>
        </contact>
        <contact id="77" state="terminated" event="expired"
                 duration-registered="3600"
                 q="0.5">
                 <uri>sip:user@university.edu</uri>
        </contact>
      </registration>
    </reginfo>

5.4. XML Schema

Here's the schema definition for the reginfo format, slay πŸ’…

<?xml version="1.0" encoding="UTF-8"?>
<xs:schema targetNamespace="urn:ietf:params:xml:ns:reginfo"
xmlns:tns="urn:ietf:params:xml:ns:reginfo"
xmlns:xs="http://www.w3.org/2001/XMLSchema"
elementFormDefault="qualified" attributeFormDefault="unqualified">
  <!-- This import brings in the XML language attribute xml:lang-->
  <xs:import namespace="http://www.w3.org/XML/1998/namespace"
schemaLocation="http://www.w3.org/2001/03/xml.xsd"/>
  <xs:element name="reginfo">
   <xs:complexType>
    <xs:sequence>
     <xs:element ref="tns:registration" minOccurs="0"
maxOccurs="unbounded"/>
     <xs:any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
    </xs:sequence>
    <xs:attribute name="version" type="xs:nonNegativeInteger"
use="required"/>
    <xs:attribute name="state" use="required">
     <xs:simpleType>
      <xs:restriction base="xs:string">
       <xs:enumeration value="full"/>
       <xs:enumeration value="partial"/>
      </xs:restriction>
     </xs:simpleType>
    </xs:attribute>
   </xs:complexType>
  </xs:element>
  <xs:element name="registration">
   <xs:complexType>
    <xs:sequence>
     <xs:element ref="tns:contact" minOccurs="0" maxOccurs="unbounded"/>
     <xs:any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
    </xs:sequence>
    <xs:attribute name="aor" type="xs:anyURI" use="required"/>
    <xs:attribute name="id" type="xs:string" use="required"/>
    <xs:attribute name="state" use="required">
     <xs:simpleType>
      <xs:restriction base="xs:string">
       <xs:enumeration value="init"/>
       <xs:enumeration value="active"/>
       <xs:enumeration value="terminated"/>
      </xs:restriction>

     </xs:simpleType>
    </xs:attribute>
   </xs:complexType>
  </xs:element>
  <xs:element name="contact">
   <xs:complexType>
    <xs:sequence>
     <xs:element name="uri" type="xs:anyURI"/>
     <xs:element name="display-name" minOccurs="0">
      <xs:complexType>
       <xs:simpleContent>
        <xs:extension base="xs:string">
         <xs:attribute ref="xml:lang" use="optional"/>
        </xs:extension>
       </xs:simpleContent>
      </xs:complexType>
     </xs:element>
     <xs:element name="unknown-param" minOccurs="0"
maxOccurs="unbounded">
      <xs:complexType>
       <xs:simpleContent>
        <xs:extension base="xs:string">
         <xs:attribute name="name" type="xs:string" use="required"/>
        </xs:extension>
       </xs:simpleContent>
      </xs:complexType>
     </xs:element>
     <xs:any namespace="##other" processContents="lax" minOccurs="0"
maxOccurs="unbounded"/>
    </xs:sequence>
    <xs:attribute name="state" use="required">
     <xs:simpleType>
      <xs:restriction base="xs:string">
       <xs:enumeration value="active"/>
       <xs:enumeration value="terminated"/>
      </xs:restriction>
     </xs:simpleType>
    </xs:attribute>
    <xs:attribute name="event" use="required">
     <xs:simpleType>
      <xs:restriction base="xs:string">
       <xs:enumeration value="registered"/>
       <xs:enumeration value="created"/>
       <xs:enumeration value="refreshed"/>
       <xs:enumeration value="shortened"/>
       <xs:enumeration value="expired"/>
       <xs:enumeration value="deactivated"/>
       <xs:enumeration value="probation"/>
       <xs:enumeration value="unregistered"/>
       <xs:enumeration value="rejected"/>
      </xs:restriction>
     </xs:simpleType>
    </xs:attribute>
    <xs:attribute name="duration-registered" type="xs:unsignedLong"/>
    <xs:attribute name="expires" type="xs:unsignedLong"/>
    <xs:attribute name="retry-after" type="xs:unsignedLong"/>
    <xs:attribute name="id" type="xs:string" use="required"/>
    <xs:attribute name="q" type="xs:string"/>
    <xs:attribute name="callid" type="xs:string"/>
    <xs:attribute name="cseq" type="xs:unsignedLong"/>
   </xs:complexType>
  </xs:element>
</xs:schema>

6. Example Call Flow ✨

okay bestie, this is the fun part πŸŽ€ Figure 3 shows a whole call flow, so you can watch the messages fly between the User, the Registrar and the Application πŸ¦‹

        User              Registrar          Application
          |                   |(1) SUBSCRIBE      |
          |                   |Event:reg          |
          |                   |<------------------|
          |                   |(2) 200 OK         |
          |                   |------------------>|
          |                   |(3) NOTIFY         |
          |                   |------------------>|
          |                   |(4) 200 OK         |
          |                   |<------------------|
          |(5) REGISTER       |                   |
          |------------------>|                   |
          |(6) 200 OK         |                   |
          |<------------------|                   |
          |                   |(7) NOTIFY         |
          |                   |------------------>|
          |                   |(8) 200 OK         |
          |                   |<------------------|
          |(9) MESSAGE        |                   |
          |<--------------------------------------|

                Figure 3: Example Call Flow

This section gives an example call flow, which is Figure 3 🌸 It's an implementation of the welcome notice application from Section 3.3, and it's giving "the app says hi to the user the second they show up" πŸ’– First, the application SUBSCRIBEs to the registration event package for the desired user (1):

SUBSCRIBE sip:joe@example.com SIP/2.0
Via: SIP/2.0/UDP app.example.com;branch=z9hG4bKnashds7
From: sip:app.example.com;tag=123aa9
To: sip:joe@example.com
Call-ID: 9987@app.example.com
CSeq: 9887 SUBSCRIBE
Contact: sip:app.example.com
Event: reg
Max-Forwards: 70
Accept: application/reginfo+xml

The registrar is acting as the notifier for the registration event package, so it sends back a 200 OK to the SUBSCRIBE 🧚

SIP/2.0 200 OK
Via: SIP/2.0/UDP app.example.com;branch=z9hG4bKnashds7
  ;received=192.0.2.1
From: sip:app.example.com;tag=123aa9
To: sip:joe@example.com;tag=xyzygg
Call-ID: 9987@app.example.com
CSeq: 9987 SUBSCRIBE
Contact: sip:server19.example.com
Expires: 3600

Next up, the registrar sends a notification (3) with the current state πŸ“¬ There's no active registration yet, so the state of the registration is "init" 😭

NOTIFY sip:app.example.com SIP/2.0
Via: SIP/2.0/UDP server19.example.com;branch=z9hG4bKnasaii
From: sip:joe@example.com;tag=xyzygg
To: sip:app.example.com;tag=123aa9
Call-ID: 9987@app.example.com
CSeq: 1288 NOTIFY
Contact: sip:server19.example.com
Event: reg
Max-Forwards: 70
Content-Type: application/reginfo+xml
Content-Length: ...

<?xml version="1.0"?>
<reginfo xmlns="urn:ietf:params:xml:ns:reginfo"
             version="0" state="full">
  <registration aor="sip:joe@example.com" id="a7" state="init" />
</reginfo>

Later on, Joe registers (5) πŸ’œ

REGISTER sip:example.com SIP/2.0
Via: SIP/2.0/UDP pc34.example.com;branch=z9hG4bKnaaff
From: sip:joe@example.com;tag=99a8s
To: sip:joe@example.com
Call-ID: 88askjda9@pc34.example.com
CSeq: 9976 REGISTER
Contact: sip:joe@pc34.example.com

And that REGISTER triggers a NOTIFY to the application (7) πŸ”₯

NOTIFY sip:app.example.com SIP/2.0
Via: SIP/2.0/UDP server19.example.com;branch=z9hG4bKnasaij
From: sip:joe@example.com;tag=xyzygg
To: sip:app.example.com;tag=123aa9
Call-ID: 9987@app.example.com
CSeq: 1289 NOTIFY
Contact: sip:server19.example.com
Event: reg
Max-Forwards: 70
Content-Type: application/reginfo+xml
Content-Length: ...

<?xml version="1.0"?>
<reginfo xmlns="urn:ietf:params:xml:ns:reginfo"
          version="1" state="partial">
  <registration aor="sip:joe@example.com" id="a7" state="active">
    <contact id="76" state="active" event="registered"
          duration-registered="0">
       <uri>sip:joe@pc34.example.com</uri>
    </contact>
  </registration>
</reginfo>

Now the app is free to send its instant message to the device (9) πŸ’… Welcome, Joe 🌈

MESSAGE sip:joe@pc34.example.com SIP/2.0
Via: SIP/2.0/UDP app.example.com;branch=z9hG4bKnashds8
From: sip:app.example.com;tag=123aa10
To: sip:joe@example.com
Call-ID: 9988@app.example.com
CSeq: 82779 MESSAGE
Max-Forwards: 70
Content-Type: text/plain
Content-Length: ...

Welcome to the example.com service!

7. Security Considerations πŸ’…

Security for SIP event packages is covered in RFC 3265 [2], and all of that applies here too, so go read it πŸ”

Okay, real talk: registration info is sensitive, and it can be really private πŸ™ˆ Subscriptions to this event package SHOULD be authenticated and authorized according to local policy. Section 4.6 has some suggested policy guidelines. Notifications SHOULD also be sent so they keep things confidential, keep the message integrity intact, and let you verify who the subscriber is. For example, you could send subscriptions and notifications over a SIPS URL, or protect the notification bodies with S/MIME. Don't skip this part, it's giving "lock your diary" energy πŸ”’πŸ’€

8. IANA Considerations πŸ¦‹

This document registers a new SIP Event Package, a new MIME type (application/reginfo+xml), and a new XML namespace. Three registrations in one go, iconic πŸ‘‘

8.1. SIP Event Package Registration

Package name: reg

Type: package

Contact: Jonathan Rosenberg, <jdrosen@jdrosen.net>

Published Specification: RFC 3680.

8.2. application/reginfo+xml MIME Registration

MIME media type name: application

MIME subtype name: reginfo+xml

Mandatory parameters: none

Optional parameters: Same as charset parameter application/xml
     as specified in RFC 3023 [8].

Encoding considerations: Same as encoding considerations of
     application/xml as specified in RFC 3023 [8].

Security considerations: See Section 10 of RFC 3023 [8] and
     Section 7 of this specification.

Interoperability considerations: none.

Published specification: This document.

Applications which use this media type: This document type is
     being used in notifications to alert SIP user agents that
     their registrations have expired and must be redone.

Additional Information:

     Magic Number: None

     File Extension: .rif or .xml

     Macintosh file type code: "TEXT"

Personal and email address for further information: Jonathan
     Rosenberg, <jdrosen@jdrosen.net>

Intended usage: COMMON

Author/Change controller: The IETF.

8.3. URN Sub-Namespace Registration for urn:ietf:params:xml:ns:reginfo

This section registers a new XML namespace, following the guidelines in [7] 🧁

URI: The URI for this namespace is
     urn:ietf:params:xml:ns:reginfo.

Registrant Contact: IETF, SIMPLE working group,
     <simple@ietf.org>, Jonathan Rosenberg
     <jdrosen@jdrosen.net>.

XML:

  BEGIN
  <?xml version="1.0"?>
  <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML Basic 1.0//EN"
            "http://www.w3.org/TR/xhtml-basic/xhtml-basic10.dtd">
  <html xmlns="http://www.w3.org/1999/xhtml">
  <head>
    <meta http-equiv="content-type"
       content="text/html;charset=iso-8859-1"/>
    <title>Registration Information Namespace</title>
  </head>
  <body>
     <h1>Namespace for Registration Information</h1>
     <h2>urn:ietf:params:xml:ns:reginfo</h2>
     <p>See <a href="ftp://ftp.rfc-editor.org/in-notes/rfc3680.txt">
            RFC3680</a>.</p>
   </body>
  </html>
  END

9. References πŸ“š

9.1. Normative References

[1] Rosenberg, J., Schulzrinne, H., Camarillo, G., Johnston, A., Peterson, J., Sparks, R., Handley, M. and E. Schooler, "SIP: Session Initiation Protocol", RFC 3261, June 2002.

[2] Roach, A., "Session Initiation Protocol (SIP)-Specific Event Notification", RFC 3265, June 2002.

[3] Bradner, S., "Key words for use in RFCs to indicate requirement levels", BCP 14, RFC 2119, March 1997.

[4] W. W. W. C. (W3C), "Extensible markup language (xml) 1.0." The XML 1.0 spec can be found at http://www.w3.org/TR/1998/REC-xml-19980210.

[5] Moats, R., "URN Syntax", RFC 2141, May 1997.

[6] Moats, R., "A URN Namespace for IETF Documents", RFC 2648, August 1999.

[7] Mealling, M., "The IETF XML Registry", BCP 81, RFC 3688, January 2004.

[8] Murata, M., St. Laurent, S. and D. Kohn, "XML media types", RFC 3023, January 2001.

9.2. Informative References

[9] Rosenberg, J., "Session initiation protocol (SIP) extensions for presence", Work In Progress.

[10] Campbell, B., Rosenberg, J., Schulzrinne, H., Huitema, C. and D. Gurle, "Session Initiation Protocol (SIP) Extension for Instant Messaging", RFC 3428, December 2002.

[11] Schulzrinne, H. and J. Rosenberg, "Session initiation protocol (SIP) caller preferences and callee capabilities", Work In Progress.

[12] Mayer, G. and M. Beckmann, "Registration event package", Work In Progress.

10. Contributors 🫢

This document is based heavily on the registration event package that Beckmann and Mayer originally proposed in [12]. You can reach them at:

Georg Mayer Siemens AG Hoffmannstr. 51 Munich 81359 Germany

EMail: Georg.Mayer@icn.siemens.de

Mark Beckmann Siemens AG P.O. Box 100702 Salzgitter 38207 Germany

EMail: Mark.Beckmann@siemens.com

Rohan Mahy provided editorial work to help move this specification along. His contact address is:

Rohan Mahy Cisco Systems 170 West Tasman Dr, MS: SJC-21/3/3

Phone: +1 408 526 8570 EMail: rohan@cisco.com

11. Acknowledgements 🌸

We would like to thank Dean Willis for his support πŸ’–

12. Author's Address πŸ“

Jonathan Rosenberg dynamicsoft 600 Lanidex Plaza Parsippany, NJ 07054

EMail: jdrosen@dynamicsoft.com

Copyright (C) The Internet Society (2004). This document is subject to the rights, licenses and restrictions contained in BCP 78, and except as set forth therein, the authors retain all their rights.

This document and the information in it are provided on an "AS IS" basis, and THE CONTRIBUTOR, THE ORGANIZATION HE/SHE REPRESENTS OR IS SPONSORED BY (IF ANY), THE INTERNET SOCIETY AND THE INTERNET ENGINEERING TASK FORCE DISCLAIM ALL WARRANTIES, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTY THAT THE USE OF THE INFORMATION HEREIN WILL NOT INFRINGE ANY RIGHTS OR ANY IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A PARTICULAR PURPOSE.

Intellectual Property 🌈

The IETF takes no position on the validity or scope of any Intellectual Property Rights or other rights that might be claimed to pertain to the implementation or use of the technology described in this document, or on the extent to which any license under such rights might or might not be available. It also doesn't claim to have made any independent effort to identify any such rights. Information on the procedures for rights in RFC documents can be found in BCP 78 and BCP 79.

Copies of IPR disclosures made to the IETF Secretariat, any assurances of licenses to be made available, or the result of an attempt to obtain a general license or permission for implementers or users of this specification to use such proprietary rights, can be obtained from the IETF on-line IPR repository at http://www.ietf.org/ipr.

The IETF invites any interested party to bring to its attention any copyrights, patents or patent applications, or other proprietary rights that may cover technology required to implement this standard. Please send that information to the IETF at ietf-ipr@ietf.org.

Acknowledgement πŸ’œ

Funding for the RFC Editor function is currently provided by the Internet Society.

πŸ“¦ where this page comes from