Skip to content

Routing

This section describes authentication and routing principles.

General routing algorithm is represented on the picture below:

::: graphviz routing.dot :::

On the first step of general routing algorithm authentication <customer_auth> will be made. As a result of this step Customer Auth <customer_auth> record will be selected for incoming call or call will be dropped with Disconnect Code 110 (Can't find Customer or Customer locked).

On the second step of algorithm Yeti will check Customer's balance if Check account balance <customer_check_account_balance>{.interpreted-text role="ref"} flag of selected Customer Auth <customer_auth> record is enabled. If current balance is less than Min balance <account_min_balance> call will dropped with Disconnect code 8000 (No enough customer balance).

On the third step of general routing algorithm Yeti makes pre-Routing numbers translations. Yeti rewrites (if necessary) Name field in the Source-number, Source-number and Destination-number for incoming call (by using POSIX Regular Expressions <posix_regular_expressions2>{.interpreted-text role="ref"}) with using Number translation settings <customers_auth_number_translation>{.interpreted-text role="ref"} of Customer Auth <customer_auth>{.interpreted-text role="ref"} record that was selected. On this step Yeti also rewrites (if necessary) Source and Destination numbers which will be send to Radius-server if it's required (by using POSIX Regular Expressions <posix_regular_expressions2>{.interpreted-text role="ref"}) with using Radius options <radius_options> of Customer Auth <customer_auth> record that was selected.

On the fourth step of general routing algorithm Yeti makes processing of destination Numberlist <numberlists> if this Numberlist <numberlists> was set in the Customer Auth <customer_auth> record. Depending on chosen mode <numberlists_mode>{.interpreted-text role="ref"} Yeti is going via all related Numberlist items <numberlist_items> and makes some actions <numberlists_action>. As a result of this step Yeti could drop the call with Disconnect code 8001 (Destination blacklisted) or just rewrite (if necessary) Source and Destination numbers (by using POSIX Regular Expressions <posix_regular_expressions2>{.interpreted-text role="ref"}) with using rewrite rules <numberlist_items_rewrite_rules>{.interpreted-text role="ref"} of Numberlist items <numberlist_items>{.interpreted-text role="ref"} record or rewrite rules <numberlists_rewrite_rules>{.interpreted-text role="ref"} relevant Numberlist <numberlists>{.interpreted-text role="ref"} record.

On the fifth step of general routing algorithm Yeti makes processing of source Numberlist <numberlists> if this Numberlist <numberlists> was set in the Customer Auth <customer_auth> record. Depending on chosen mode <numberlists_mode>{.interpreted-text role="ref"} Yeti is going via all related Numberlist items <numberlist_items> and makes some actions <numberlists_action>. As a result of this step Yeti could drop the call with Disconnect code 8002 (Source blacklisted) or just rewrite (if necessary) Source and Destination numbers (by using POSIX Regular Expressions <posix_regular_expressions2>{.interpreted-text role="ref"}) with using rewrite rules <numberlist_items_rewrite_rules>{.interpreted-text role="ref"} of Numberlist items <numberlist_items>{.interpreted-text role="ref"} record or rewrite rules <numberlists_rewrite_rules>{.interpreted-text role="ref"} relevant Numberlist <numberlists>{.interpreted-text role="ref"} record.

On the sixth step of general routing algorithm Yeti will be looking for Areas <areas> (by using Area prefixes <area_prefixes>) that are related to the Source number (From name) and Destination number (URI name) after them processing and translation on the previous steps. Area <areas> records that were found (if any), are used for detecting Routing Tags <routing_tag> for the call on the basis Routing Tag detection Rules <routing_tag_detection_rules>{.interpreted-text role="ref"}.

On the seventh step of general routing algorithm Yeti will be selecting Routing Plan <routing_plan> that was chosen for Customer Auth <customer_auth> record.

On the eighth step of general routing algorithm Yeti (if Use Lnp <routing_plan_use_lnp> flag of Routing Plan <routing_plan> that was chosen for Customer Auth <customer_auth> record is enabled) selects most preferred Routing Plan LNP rule <routing_plan_lnp_rules>{.interpreted-text role="ref"} (by longest match prefix of destination number (number B)) and uses this Routing Plan LNP rule <routing_plan_lnp_rules>{.interpreted-text role="ref"} for processing ported numbers of call. If required record wasn't found in the LNP Cache <lnp_caches>{.interpreted-text role="ref"} - LNP Database <lnp_databases>{.interpreted-text role="ref"} will be requested. In case of failing query Yeti will drop the call with Disconnect code 8003 (No response from LNP DB).

On the ninth step of general routing algorithm Yeti will be searching Destination <destinations> for the call that is matching ALL following conditions:

  • Prefix <destination_prefix> of Destination <destinations> record is in the prefix range of Destination number (URI name);

    ::: note ::: title Note :::

    Examples:

    • Prefix of Destination <destinations>{.interpreted-text role="ref"} record = ** ; URI name = 0662296132 => TRUE
    • Prefix of Destination <destinations>{.interpreted-text role="ref"} record = 066 ; URI name = 0662296132 => TRUE
    • Prefix of Destination <destinations>{.interpreted-text role="ref"} record = 066[1-3] ; URI name = 0662296132 => TRUE
    • Prefix of Destination <destinations>{.interpreted-text role="ref"} record = 066[1-3] ; URI name = 0665296132 => FALSE
    • Prefix of Destination <destinations>{.interpreted-text role="ref"} record = 066[1-3], 0665 ; URI name = 0665296132 => TRUE
    • Prefix of Destination <destinations>{.interpreted-text role="ref"} record = 066[1-3], 0665 ; URI name = 0666296132 => FALSE :::
  • Length of Destination number (URI name) is between Dst number min and max length values of Destination <destinations> record;

    ::: note ::: title Note :::

    Examples:

    • Dst number min length of Destination <destinations> record = 3 ; Dst number max length of Destination <destinations> record = 15 ; URI name = 380662296132 => TRUE
    • Dst number min length of Destination <destinations> record = 7 ; Dst number max length of Destination <destinations> record = 7 ; URI name = 7050460 => TRUE
    • Dst number min length of Destination <destinations> record = 0 ; Dst number max length of Destination <destinations> record = 7 ; URI name = 0487050460 => FALSE :::
  • Rateplan <rateplans> that is chosen for Destination <destinations> record is same with Rateplan <rateplans>{.interpreted-text role="ref"} that is chosen for Customer Auth <customer_auth> record;

  • Destination <destinations> record is enabled;

  • current date&time is more than Valid From <destination_valid_from> value of Destination <destinations> record;

  • current date&time is less than Valid To <destination_valid_to> value of Destination <destinations> record;

  • at least one Routing Tag <routing_tag>{.interpreted-text role="ref"} (from the list of Routing Tags <routing_tag> that were chosen for the call during the sixth step of general routing algorithm) is included in the set of Routing Tags <destination_routing_tag>{.interpreted-text role="ref"} that are chosen forDestination <destinations> record.

If more than one record was found during searching of Destination <destinations> Yeti sorts records with following rules: records with the longest Prefix <destination_prefix> of Destination <destinations> on the top; records with biggest amount of Routing Tags <destination_routing_tag> that were chosen for the call (during the sixth step of general routing algorithm) and are included in the set of Routing Tags <destination_routing_tag> that are chosen forDestination <destinations>{.interpreted-text role="ref"} record on the top. Only first record from sorted list will be chosen.

If no records were found during searching of Destination <destinations> Yeti will drop the call with Disconnect Code 111 (Can't find destination prefix).

If Reject Calls <destination_reject_calls>{.interpreted-text role="ref"} flag is enabled for the Destination <destinations> record that was chosen Yeti will drop the call with Disconnect Code 112 (Rejected by destination).

On the tenth step of general routing algorithm Yeti will search routes (Dialpeers <dialpeers>) for a call on the basis routing (sorting) algorithm <routing_plan_sorting>{.interpreted-text role="ref"} that was chosen for Routing Plan <routing_plan> record. If no records were found during searching of Dialpeers <dialpeers> Yeti will drop the call with Disconnect Code 113 (No routes).

On the eleventh step of general routing algorithm Yeti will pass through list of selected Dialpeers <dialpeers>) that is sorted by chosen routing (sorting) algorithm <routing_plan_sorting>{.interpreted-text role="ref"}. For each Dialpeer <dialpeers>{.interpreted-text role="ref"} following actions will be applied:

  • Search termination Gateways <gateways>{.interpreted-text role="ref"} for selected Dialpeer <dialpeers>{.interpreted-text role="ref"} (Step 11.1). If Gateway <gateways>{.interpreted-text role="ref"} was chosen for Dialpeer <dialpeers> record (and this Gateway <gateways> is Enabled <gateway_enabled>) Yeti will check Vendor <dialpeer_vendor>{.interpreted-text role="ref"} property of Dialpeer <dialpeers>{.interpreted-text role="ref"} and compares it with Contractor <gateway_contractor> property of Gateway <gateways>. In case if Is shared <gateways> flag of Gateway <gateways> record wasn't chosen and Vendor <dialpeer_vendor>{.interpreted-text role="ref"} property of Dialpeer <dialpeers>{.interpreted-text role="ref"} record and Contractor <gateway_contractor> property of Gateway <gateways> record aren't same - Yeti will stop process this Dialpeer <dialpeers> and will go to next record in the sorted list of Dialpeers <dialpeers>. Otherwise Gateway <gateways> that was chosen for Dialpeer <dialpeers> record will be used for attempt of the call termination. If Gateway <gateways> wasn't chosen for Dialpeer <dialpeers> record Yeti will select all enabled <gateway_enabled>{.interpreted-text role="ref"} Gateways <gateways> from Gateway group <gateway_groups>{.interpreted-text role="ref"} that was chosen for Dialpeer <dialpeers> where Point of Presence <gateway_pop> of the termination and origination Gateways <gateways> are same AND Vendor <dialpeer_vendor> property of Dialpeer <dialpeers> record and Contractor <gateway_contractor> property of Gateway <gateways> record are same. If Gateways <gateways>{.interpreted-text role="ref"} from the same Point of Presence <gateway_pop> weren't found - Yeti will select all enabled <gateway_enabled>Gateways <gateways> from Gateway group <gateway_groups> that was chosen for Dialpeer <dialpeers>{.interpreted-text role="ref"} regardless Point of Presence <gateway_pop>, but where Vendor <dialpeer_vendor> property of Dialpeer <dialpeers> record and Contractor <gateway_contractor>{.interpreted-text role="ref"} property of Gateway <gateways>{.interpreted-text role="ref"} record are same. All selected by this way Gateways <gateways> will be used for attempts of the call termination. The quantity of attempts of the call termination for each Dialpeer <dialpeers> record from the sorted list of Dialpeers <dialpeers>{.interpreted-text role="ref"} is determined by quantity of selected Gateways <gateways> that are sorted by following rules: Gateways <gateways>{.interpreted-text role="ref"} from the same (related to origination) Point of Presence <gateway_pop> are first, Gateways <gateways> with higher Priority <gateway_priority>{.interpreted-text role="ref"} are first, random Gateway <gateways> will be chosen first in case of equal Priorities <gateway_priority> for two or more Gateways <gateways> in the list;
  • Yeti will pass through list of selected Gateways <gateways> that is sorted by priority (Step 11.2). For each Gateway <gateways> from the list following actions will be applied:
    • Checking if Customer's min balance will be reached during the call (Step 11.3). On this stage Yeti will check if Connect Fee <destination_connect_fee>{.interpreted-text role="ref"} of Destination <destinations>{.interpreted-text role="ref"} record that was selected for this call is bigger than the result of subtracting Balance <account_balance> of the Customer's Account <accounts>{.interpreted-text role="ref"} and Min balance <account_min_balance>{.interpreted-text role="ref"} of the Customer's Account <accounts>. If no enough money on Customer's Account <accounts> for make connection and for calling during Initial Interval <destination_initial_interval>{.interpreted-text role="ref"} of Destination <destinations>{.interpreted-text role="ref"} record that was selected for this call - call will dropped with Disconnect code 8000 (No enough customer balance);
    • Calculating of allowed time for the call (Step 11.4). Yeti could limit maximum time of the calls to avoid exceeding limits of money (minimum or maximum) that are available on accounts of Customer and Vendor. For this purpose Yeti has two values of allowed time: limited by Customer's Account and limited by Vendor's account:
      • Allowed time that is limited by Customer's Account. If Next Rate <destination_next_rate>{.interpreted-text role="ref"} AND Next Interval <destination_next_interval>{.interpreted-text role="ref"} of the Destination <destinations> record that was selected for this call are not zero: allowed time for the call will be calculated as sum of Initial Interval <destination_initial_interval>{.interpreted-text role="ref"} of this Destination <destinations> record and length of call that can be made within amount of money available on Customer's Account <accounts>{.interpreted-text role="ref"}. Otherwise value Max Call Duration <system_global_configuration_max_call_duration>{.interpreted-text role="ref"} from Global configuration <global_configuration>{.interpreted-text role="ref"} will be used for setting allowed time for the call;
      • Allowed time that is limited by Vendor's Account. If Next Rate <dialpeer_next_rate>{.interpreted-text role="ref"} AND Next Interval <dialpeer_next_interval>{.interpreted-text role="ref"} of the Dialpeer <dialpeers> record that was selected for this call are not zero: allowed time for the call will be calculated as sum of Initial Interval <dialpeer_initial_interval>{.interpreted-text role="ref"} of this Dialpeer <dialpeers> record and length of call that can be made before reaching Max balance <account_max_balance>{.interpreted-text role="ref"} the Vendor's Account <accounts>{.interpreted-text role="ref"}. Otherwise value Max Call Duration <system_global_configuration_max_call_duration>{.interpreted-text role="ref"} from Global configuration <global_configuration>{.interpreted-text role="ref"} will be used for setting allowed time for the call;
    • Checking if Vendor's max balance will be reached during the call (Step 11.5); On this stage Yeti will check if Connect Fee <dialpeer_connect_fee>{.interpreted-text role="ref"} of Dialpeer <dialpeers>{.interpreted-text role="ref"} record that was selected for this call is bigger than the result of subtracting Max balance <account_max_balance>{.interpreted-text role="ref"} and Balance <account_balance>{.interpreted-text role="ref"} of the Vendor's Account <accounts>. If Vendor's max balance will be reached during Initial Interval <dialpeer_initial_interval>{.interpreted-text role="ref"} of Dialpeer <dialpeers>{.interpreted-text role="ref"} record that was selected for this call - this Gateway <gateways> will be ignored and next Gateway <gateways>{.interpreted-text role="ref"} will be chosen from the list on Step 11.2;
    • Post-routing numbers translations (Step 11.6). On this step of general routing algorithm Yeti makes post-Routing numbers translations. Yeti rewrites (if necessary) Name field in the Source-number, Source-number and Destination-number for incoming call (by using POSIX Regular Expressions <posix_regular_expressions2>{.interpreted-text role="ref"}) with using Number translation settings <dialpeer_number_translation_settings>{.interpreted-text role="ref"} of Dialpeer <dialpeers>{.interpreted-text role="ref"} record that was selected for this call;
    • Adding Call Profile to the Array (Step 11.7). On this step Yeti will add Call Profile to the list (array) of Call Profiles. Call Profile will be used by Yeti/SEMS node for making call on Step 12 of general routing algorithm.

On the twelfth step of general routing algorithm Yeti/SEMS node will pass through list of Call Profiles that was received on previous step (Step 12). For each Call Profile following actions will be applied:

  • Checking Disconnect Code (Step 12.1). On this step Yeti will check if Disconnect Code for Call Profile was initialized (not NULL). If yes - Yeti will initiate disconnecting (Step 12.6) from Originator (with using received Disconnect Code) after writing CDR & statistic for route/gateway (Step 12.3a);
  • Trying to connect a call (Step 12.2). On this step Yeti will try to make a connection with LegB via Gateway <gateways> that was selected for current Call Profile. Regardless from call result (successful or not, length of call etc.) Yeti will write CDR & statistic for route/gateway (Step 12.3b) and will change customer's and vendor's balance at billing subsystem (in case of successful call with non-zero length) on Step 12.4. After the checking of call result (Step 12.5) Yeti will disconnect from Originator (Step 12.6) in case of successful call or will go the next Call Profile in the list (Step 12). Yeti will exit from the loop only when call had been made successfully or when all Call Profiles had been used;
  • Writing CDR + writing statistic for route/gateway (Step 12.3 (a & b)). Information about call will be stored to the CDR Table <cdr_partitions> and current statistical parameters (count of answered telephone calls, general length of telephone calls) will be updated for Dialpeer <dialpeers> record that was selected for this call and for Gateway <gateways> that was used for this call;
  • Change Customer's and Vendor's balance at billing subsystem (if necessary) (Step 12.4). On this step Yeti will change Customer's and Vendor's balance <account_balance>{.interpreted-text role="ref"} in case of successful call with non-zero length. For calculating prices of the call for Customer and Vendor following rules are used:

:::

  • Customer's price calculation rules. For calculate Customer's price for the call Yeti will summarize Connect Fee <destination_connect_fee>{.interpreted-text role="ref"} (in currency units) of Destination <destinations> record that was selected for this call, price of initial interval of call that is calculated as multiplication of Initial Interval <destination_initial_interval>{.interpreted-text role="ref"} (in seconds) of Destination <destinations> record to the Initial Rate <destination_initial_rate>{.interpreted-text role="ref"} (in currency units per minute) that was divided on length of a minute in seconds (60 seconds), and (in case of calls that are longer than Initial Interval <destination_initial_interval>{.interpreted-text role="ref"}) price of next interval of call that is calculated as multiplication amount of Next Intervals <destination_next_interval>{.interpreted-text role="ref"} of Destination <destinations>{.interpreted-text role="ref"} record that was selected for this call that were placed in the duration of the call after Initial Interval <destination_initial_interval>{.interpreted-text role="ref"} to the Next Rate <destination_next_rate>{.interpreted-text role="ref"} (in currency units per minute) that was divided on length of a minute in seconds (60 seconds). At the last step Customer's price that was calculated will be increased on the value of value-added tax (VAT) that was specified for the Customer's Account <accounts>. :::

:::

  • Vendor's price calculation rules. For calculate Vendor's price for the call Yeti will summarize Connect Fee <dialpeer_connect_fee>{.interpreted-text role="ref"} (in currency units) of Dialpeer <dialpeers> record that was selected for this call, price of initial interval of call that is calculated as multiplication of Initial Interval <dialpeer_initial_interval>{.interpreted-text role="ref"} (in seconds) of Dialpeer <dialpeers> record to the Initial Rate <dialpeer_initial_rate>{.interpreted-text role="ref"} (in currency units per minute) that was divided on length of a minute in seconds (60 seconds), and (in case of calls that are longer than Initial Interval <dialpeer_initial_interval>{.interpreted-text role="ref"}) price of next interval of call that is calculated as multiplication amount of Next Intervals <dialpeer_next_interval>{.interpreted-text role="ref"} of Dialpeer <dialpeers>{.interpreted-text role="ref"} record that was selected for this call that were placed in the duration of the call after Initial Interval <dialpeer_initial_interval>{.interpreted-text role="ref"} to the Next Rate <dialpeer_next_rate> (in currency units per minute) that was divided on length of a minute in seconds (60 seconds);

::: note ::: title Note :::

Important notice:

In normal mode changing Customer's and Vendor's balance at billing subsystem will be made by subtraction of the Customer's price that was calculated on this step from the Customer's balance <account_balance> and by addition Vendor's price to the Vendor's balance <account_balance>. But in case of enabling Reverse billing <destination_reverse_billing>{.interpreted-text role="ref"} flag of Destination <destinations>{.interpreted-text role="ref"} record that was selected for this call - Yeti will add Customer's price that was calculated on this step to the Customer's balance <account_balance>{.interpreted-text role="ref"}, and in case of enabling Reverse billing <dialpeer_reverse_billing>{.interpreted-text role="ref"} flag of Dialpeer <dialpeers>{.interpreted-text role="ref"} record that was selected for this call - Yeti will subtract Vendor's price from the Vendor's balance <account_balance>. Following formula is used for calculation both Customer's and Vendor's prices:

$$\begin{equation} Price = (CF + II(\frac{IR}{60}) + [\frac{(CD-II)}{NI}]NI(\frac{NR}{60}))(1 + \frac{VAT}{100}) \end{equation}$$

where:
  • Price - Customer's or Vendor's price;
  • CF - Connect Fee of Destination <destinations> (for Customer's price) or Dialpeer <dialpeers> (for Vendor's price), currency units;
  • II - Initial Interval of Destination <destinations> (for Customer's price) or Dialpeer <dialpeers> (for Vendor's price), seconds;
  • IR - Initial Rate of Destination <destinations> (for Customer's price) or Dialpeer <dialpeers> (for Vendor's price), currency units per minute;
  • CD - Call duration, seconds;
  • NI - Next Interval of Destination <destinations> (for Customer's price) or Dialpeer <dialpeers> (for Vendor's price), seconds;
  • NR - Next Rate of Destination <destinations> (for Customer's price) or Dialpeer <dialpeers> (for Vendor's price), currency units per minute;
  • VAT - Value-added tax, percents. VAT = 0 for calculating Vendor's price. ::: :::
  • Disconnect from Originator (Step 12.6).

YETI WEB interface - Routing menu description.

::: {.toctree maxdepth="1"} customers-auths yeti-ui-routing-rateplans rate_groups yeti-ui-routing-destinations yeti-ui-routing-routing_groups yeti-ui-routing-dialpeers yeti-ui-routing-routing_plans yeti-ui-routing-routing_plan_static_routes yeti-ui-routing-routing_plan_lnp_rules yeti-ui-routing-lnp_caches numberlists numberlist-items yeti-ui-routing-routing_tags yeti-ui-routing-areas yeti-ui-routing-area_prefixes yeti-ui-routing-routing_tag_detection_rules yeti-ui-routing-routing_simulation yeti-ui-routing-tags_truth_table yeti-ui-routing-prefix_truth_table :::