LTM Diameter iRules and Profile Configurations with Support for Server Initiated Request
While in other APIs client send request and server response, IETF/3GPP Diameter charging protocol allows requests to come from servers.
The example for such use case is 3GPP RAR (Re-Authorization Request) or SNR (Spending status Notification Request).
Whenever a subscriber has changes to his/her data packages subscriptions, telecom billing server (OCS) sends RAR to Diameter clients (e.g. mobile data gateway/controller PCEF, PCRF) to reinitiate billing session of the subscriber so that subscriber's subsequent mobile data usage is charged using updated data pacakages.
Diameter clients will respon using RAA (Re-Authorization Answer).
I found that the new F5 MRF framework cannot handle server initiated requests while older LTM Diameter profile can.
It still needs iRules though because F5 doesn't rewite Destination Host and Realm AVP of Diameter answer message sent by client to proper server's realm and host ID.
iRules is also needed to clear persistence records whenever server respond to charging session termination request.
iRules code:
###capture server's realm and host ID from server's CEA message
####then save it into custom session table
####to be used to rewrite client RAA AVPs
when DIAMETER_INGRESS {
if { [serverside] && [DIAMETER::command] == 257 } {
table set -subtable ServerRealm "[server_addr]_[server_port]" [DIAMETER::realm origin] indefinite
table set -subtable ServerHost "[server_addr]_[server_port]" [DIAMETER::host origin] indefinite
}
}
#########
when DIAMETER_EGRESS {
###replace client'ss RAA Destination Realm and Host AVP with values from custom session table
if { [serverside] && [DIAMETER::command] == 258 } {
DIAMETER::realm dest [ table lookup -subtable ServerRealm "[server_addr]_[server_port]" ]
DIAMETER::host dest [ table lookup -subtable ServerHost "[server_addr]_[server_port]" ]
######alternatively, we can also use values stored in Data Group
###DIAMETER::realm dest [ class lookup "[server_addr]_[server_port]" ServerRealmID ]
###DIAMETER::host dest [ class lookup "[server_addr]_[server_port]" ServerHostID ]
}
#########
###delete persistence key whenever server sends answer for termination request.
if { [clientside] && [DIAMETER::command] == 272 && [DIAMETER::avp data get 416 unsigned32] == 3 } {
persist delete uie [DIAMETER::avp data get 263 string]
}
#########
}
In LTM diameter profile we only need to define:
- Persistence key to use Session-ID AVP
- Fill in the F5 LTM's realm and host ID to rewrite values of Origin Realm and Origin Host for message sent to client
ltm profile diameter diameter {
app-service none
persist-avp Session-Id
}
ltm profile diameter diameter111 {
app-service none
defaults-from diameter
origin-host-to-client f5lb.com
origin-realm-to-client f5lb.com
}
INFO: Additional functionalities that older LTM diameter profile can but MRF cannot:
- Ratio load balancing: we can set ratio load balancing for MRF but it doesn't work.
- Automatic destination host and destination realm AVP rewrite when forwarding client's requests to servers: we have to create server side profile, transport config and peer object for every servers if each of them has different realm or host ID
- Pool member health monitor and status doesnt apply to MRF. Eventhough we force disable a pool member, MRF will still send client message to it.
- Virtual server status is always unknown because it seems MRF doesn't use LTM mechanism.