Documentation

Documentation.Tutorials-Diameter-Client-Server History

Hide minor edits - Show changes to output

March 07, 2024, at 05:12 PM by liviu -
Added lines 113-124:
log_stdout = yes
...
loadmodule "aaa_diameter.so"
modparam("aaa_diameter", "fd_log_level", 0)
modparam("aaa_diameter", "realm", "diameter.test")
modparam("aaa_diameter", "peer_identity", "server")
...
@]

\\

[@
Added line 183:
log_stdout = yes
Added lines 185-189:
loadmodule "aaa_diameter.so"
modparam("aaa_diameter", "fd_log_level", 0)
modparam("aaa_diameter", "realm", "diameter.test")
modparam("aaa_diameter", "peer_identity", "server")
March 07, 2024, at 12:50 PM by liviu -
Added lines 32-99:
@]

! Defining a Generic Diameter Request + Answer

While the ''freeDiameter'' library is very robust, this also means it will be very ''nitpicky'' with its "known" set of Diameter Applications and Commands. The set of currently known apps and commands (along with each command's precise AVP structure!) make up the library's '''dictionary''', in freeDiameter terminology.

\\

This means that before we can build and send a generic request, we must make sure to ''define the request in the freeDiameter dictionary''. You can achieve this by attaching an ''';extra-avps-file:<path-to-dictionary.opensips>''' option to the [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#param_aaa_url|aaa_url]] modparam of '''aaa_diameter'''. In order to define Apps and Command AVP structure, we have extended the classic, AAA '''dictionary.opensips''' AVP definitions file to support this. See [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_request|dm_send_request]] for full examples.

\\

For our case, we only need the following in ''dictionary.opensips'':

\\

[@
ATTRIBUTE Exponent 429 integer32
ATTRIBUTE Value-Digits 447 integer64

ATTRIBUTE Cost-Unit 424 grouped
{
Value-Digits | REQUIRED | 1
Exponent | OPTIONAL | 1
}

ATTRIBUTE Currency-Code 425 unsigned32

ATTRIBUTE Unit-Value 445 grouped
{
Value-Digits | REQUIRED | 1
Exponent | OPTIONAL | 1
}

ATTRIBUTE Cost-Information 423 grouped
{
Unit-Value | REQUIRED | 1
Currency-Code | REQUIRED | 1
Cost-Unit | OPTIONAL | 1
}

APPLICATION 42 My Diameter Application

REQUEST 92001 My-Custom-Request
{
Origin-Host | REQUIRED | 1
Origin-Realm | REQUIRED | 1
Destination-Realm | REQUIRED | 1
Transaction-Id | REQUIRED | 1
Sip-From-Tag | REQUIRED | 1
Sip-To-Tag | REQUIRED | 1
Acct-Session-Id | REQUIRED | 1
Sip-Call-Duration | REQUIRED | 1
Sip-Call-Setuptime | REQUIRED | 1
Sip-Call-Created | REQUIRED | 1
Sip-Call-MSDuration | REQUIRED | 1
call_cost | REQUIRED | 1
Cost-Information | OPTIONAL | 1
}

ANSWER 92001 My-Custom-Answer
{
Origin-Host | REQUIRED | 1
Origin-Realm | REQUIRED | 1
Destination-Realm | REQUIRED | 1
Transaction-Id | REQUIRED | 1
Result-Code | REQUIRED | 1
}
March 07, 2024, at 12:41 PM by liviu -
Changed line 124 from:
Next, the request must be processed according to the application specifications. Effectively, the result will be a set of AVPs to be included in the answer. Make sure to pack them as a JSON Array (similar to the input of [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_request|dm_send_request()]]), before finally calling '''dm_send_answer()''':
to:
Next, the request must be processed according to the application specifications. Effectively, the result will be a set of AVPs to be included in the answer. Make sure to pack them as a JSON Array (similar to the input of [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_request|dm_send_request()]]), before finally calling [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_answer|dm_send_answer()]]:
March 07, 2024, at 12:41 PM by liviu -
Changed line 124 from:
Next, the request must be processed according to the application specifications. Effectively, the result will be a set of AVPs to be included in the answer. Make sure to pack them as a JSON Array (similar to the input of [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_request|dm_send_request()]]), before calling '''dm_send_answer()''':
to:
Next, the request must be processed according to the application specifications. Effectively, the result will be a set of AVPs to be included in the answer. Make sure to pack them as a JSON Array (similar to the input of [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_request|dm_send_request()]]), before finally calling '''dm_send_answer()''':
March 07, 2024, at 12:39 PM by liviu -
Changed lines 120-143 from:
* '''avps_json''' (string) - a JSON Array containing the AVPs of the request
to:
* '''avps_json''' (string) - a JSON Array containing the AVPs of the request

\\

Next, the request must be processed according to the application specifications. Effectively, the result will be a set of AVPs to be included in the answer. Make sure to pack them as a JSON Array (similar to the input of [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#func_dm_send_request|dm_send_request()]]), before calling '''dm_send_answer()''':

\\

[@
...
$var(ans_avps) = "[
{ \"Vendor-Specific-Application-Id\": [{
\"Vendor-Id\": 0
}] },

{ \"Result-Code\": 2001 },
{ \"Auth-Session-State\": 0 },
{ \"Origin-Host\": \"opensips.diameter.test\" },
{ \"Origin-Realm\": \"diameter.test\" }
]";

if (!dm_send_answer($var(ans_avps)))
xlog("ERROR - failed to send Diameter answer\n");
@]
March 07, 2024, at 12:35 PM by liviu -
Deleted line 116:
* '''sess_id''' (string) - the value of either the '''Session-Id''' AVP, '''Transaction-Id''' AVP or a '''NULL''' value if neither of these transaction-identifying AVPs is present in the Diameter request
Added line 119:
* '''sess_id''' (string) - the value of either the '''Session-Id''' AVP, '''Transaction-Id''' AVP or a '''NULL''' value if neither of these transaction-identifying AVPs is present in the Diameter request
March 07, 2024, at 12:35 PM by liviu -
Added lines 26-27:
\\
Changed lines 94-120 from:
Starting with OpenSIPS '''3.5''', there is the option of acting as a '''Diameter Server''', and process incoming Diameter requests.
to:
Starting with OpenSIPS '''3.5''', there is the option of acting as a '''Diameter Server''' and process incoming Diameter requests, as well as to provide the appropriate AVPs for the Diameter answer, which may also be an error, of course. Here are the steps to achieve this:

\\

First, make sure the [[https://opensips.org/docs/modules/3.5.x/event_route|event_route]] module is loaded. It is required in order to gain access to the '''event_route''', which will be triggered with a '''E_DM_REQUEST''' event on each incoming Diameter request:

\\

[@
...
loadmodule "event_route.so"
...
event_route [E_DM_REQUEST]
{
xlog("Req: $param(sess_id) / $param(app_id) / $param(cmd_code)\n");
xlog("AVPs: $param(avps_json)\n");
}
@]

\\

Notice there are several pieces of information provided through the event's ''parameters'':

* '''sess_id''' (string) - the value of either the '''Session-Id''' AVP, '''Transaction-Id''' AVP or a '''NULL''' value if neither of these transaction-identifying AVPs is present in the Diameter request
* '''app_id''' (integer) - the Diameter Application Identifier
* '''cmd_code''' (integer) - the Diameter Command Code
* '''avps_json''' (string) - a JSON Array containing the AVPs of the request
March 07, 2024, at 12:28 PM by liviu -
Changed line 67 from:
... and, finally, send the request out (in a blocking fashion, for async support, see [[|here]]):
to:
... and, finally, send the request out (in a blocking fashion, for async support, see [[https://opensips.org/docs/modules/3.5.x/aaa_diameter.html#idp5591744|async dm_send_request()]]):
March 07, 2024, at 12:27 PM by liviu -
Changed line 38 from:
After making sure that '''aaa_diameter''' is loaded, simply build the request's AVP list as a JSON array:
to:
After making sure that '''aaa_diameter''' is loaded, start by building the request's AVP list as a JSON array:
March 07, 2024, at 12:27 PM by liviu -
Added lines 39-40:

\\
March 07, 2024, at 12:26 PM by liviu -
Changed lines 34-35 from:
OpenSIPS '''3.2''' and above releases offer the option of building generic Diameter requests with full control over the AVPs of the request, as well as full access to the content of the response. Below is a short tutorial on how to send a Diameter request.
to:
OpenSIPS '''3.2''' and above releases offer the option of building ''generic'' Diameter requests with full control over the AVPs of the request, as well as full access to the content of the response. Below is a short tutorial on how to send a Diameter request.
Changed lines 61-69 from:
to:
@]

\\

... and, finally, send the request out (in a blocking fashion, for async support, see [[|here]]):

\\

[@
March 07, 2024, at 12:25 PM by liviu -
Changed lines 38-78 from:
First,
to:
After making sure that '''aaa_diameter''' is loaded, simply build the request's AVP list as a JSON array:

[@
# Building an sending an My-Custom-Request (92001) for the
# My Diameter Application (42)
$var(payload) = "[
{ \"Origin-Host\": \"client.diameter.test\" },
{ \"Origin-Realm\": \"diameter.test\" },
{ \"Destination-Realm\": \"diameter.test\" },
{ \"Sip-From-Tag\": \"dc93-4fba-91db\" },
{ \"Sip-To-Tag\": \"ae12-47d6-816a\" },
{ \"Acct-Session-Id\": \"a59c-dff0d9efd167\" },
{ \"Sip-Call-Duration\": 6 },
{ \"Sip-Call-Setuptime\": 1 },
{ \"Sip-Call-Created\": 1652372541 },
{ \"Sip-Call-MSDuration\": 5850 },
{ \"out_gw\": \"GW-774\" },
{ \"cost\": \"10.84\" },
{ \"Cost-Information\": [
{\"Unit-Value\": [{\"Value-Digits\": 1000}]},
{\"Currency-Code\": 35}
]}
]";

dm_send_request(42, 92001, $var(payload), $var(rpl_avps));
@]

\\

In this example, the Diameter Application ID is '''42''', and the Command's Code is '''92001'''. Finally, the response AVPs are available under '''$var(rpl_avps)'''. Just use the OpenSIPS [[https://opensips.org/docs/modules/3.5.x/json|JSON module]] in order to parse & access them:

\\

[@
$json(rpl) := $var(rpl_avps);
xlog("Reply AVPs: $json(rpl)\n");
$var(i) = 0;
while ($json(rpl[$var(i)])) {
xlog(" AVP: $json(rpl[$var(i)])\n");
}
@]
March 07, 2024, at 12:15 PM by liviu -
Changed lines 34-35 from:
OpenSIPS '''3.2''' and above releases offer the option of building generic Diameter requests with full control over the AVPs of the request, as well as full access to the content of the response.
to:
OpenSIPS '''3.2''' and above releases offer the option of building generic Diameter requests with full control over the AVPs of the request, as well as full access to the content of the response. Below is a short tutorial on how to send a Diameter request.

\\

First,
Changed line 42 from:
Starting with OpenSIPS '''3.5''', support
to:
Starting with OpenSIPS '''3.5''', there is the option of acting as a '''Diameter Server''', and process incoming Diameter requests.
March 07, 2024, at 12:14 PM by liviu -
Changed lines 34-38 from:
! opensips.cfg: Processing Generic Diameter Requests
to:
OpenSIPS '''3.2''' and above releases offer the option of building generic Diameter requests with full control over the AVPs of the request, as well as full access to the content of the response.

! opensips.cfg: Processing Generic Diameter Requests

Starting with OpenSIPS '''3.5''', support
March 06, 2024, at 09:54 AM by liviu -
Added lines 1-34:
!!!!! Documentation -> [[Documentation.Tutorials | Tutorials ]] -> Diameter Client/Server
This page has been visited {$PageCount} times.

!How to build and process Diameter requests using OpenSIPS scripting
%block text-align=right% '''by Liviu Chircu'''

(:toc-float Table of Content:)
----

! Setting up the freeDiameter libraries

This tutorial has been written for a Xubuntu 22.04 LTS, which comes with freeDiameter library v1.2.1 packages. Other distros, such as Debian 10, are also known to offer standard package-based support for freeDiameter v1.2.1, so they are expected to be compatible just as well.

[@
sudo apt -y install libfreediameter-dev
@]

! Installing the "aaa_diameter" OpenSIPS module

If you are building from source:

[@
include_modules=aaa_diameter make install
@]

Otherwise, if you are installing from packages, make sure to grab the '''opensips-diameter-module''':

[@
sudo apt -y install opensips-diameter-module
@]

! opensips.cfg: Sending Generic Diameter Requests

! opensips.cfg: Processing Generic Diameter Requests

Page last modified on March 07, 2024, at 05:12 PM