Есть ли ограничения для одновременных транзакций в MariaDB? - PullRequest
0 голосов
/ 10 октября 2019

Существует сервер Centos 7 с Asterisk PBX 11.25.3 и mysql Ver 15.1 Distrib 10.3.18-MariaDB, для Linux (x86_64).

extensions.conf:

[from-main-asterisk]
exten => _9XXXXXXXXXXXX,1,MYSQL(Connect connid localhost root rootpasswd mydatabase)
exten => _9XXXXXXXXXXXX,n,GotoIf($["${connid}" = ""]?error,1)
exten => _9XXXXXXXXXXXX,n(select_sim),MYSQL(Query RESULTID ${connid} set autocommit=0)
exten => _9XXXXXXXXXXXX,n,MYSQL(Query RESULTID ${connid} START TRANSACTION)
exten => _9XXXXXXXXXXXX,n,MYSQL(Query RESULTID ${connid} SELECT sim_name FROM  sim_stat  where status = 'FREE'  order by rand() limit 1 ) 
exten => _9XXXXXXXXXXXX,n(sqlresult),MYSQL(Fetch fetchid ${RESULTID} SIM_NAME)
exten => _9XXXXXXXXXXXX,n,MYSQL(Clear ${RESULTID})
exten => _9XXXXXXXXXXXX,n,MYSQL(Query RESULTID ${connid} UPDATE sim_stat set status = "BUSY" where sim_name = "${SIM_NAME}") 
exten => _9XXXXXXXXXXXX,n,MYSQL(Query RESULTID ${connid} COMMIT)
exten => _9XXXXXXXXXXXX,n,Dial(SIP/gsm-${SIM_NAME}#${EXTEN:1},,g)
exten => _9XXXXXXXXXXXX,n,Hangup

exten => h,1,MYSQL(Query RESULTID ${connid} UPDATE sim_stat set status = "FREE"  where sim_name = "${SIM_NAME}")
exten => h,n,MYSQL(Query RESULTID ${connid} COMMIT)
exten => h,n,MYSQL(Disconnect ${connid})

exten => error,1,NoOp(Database connection error!)
exten => error,n,Hangup

sip.conf:

[from-main-asterisk]
type=friend
host=x.x.x.x
qualify=yes
qualifyfreq=60
canreinvite=no
disallow=all
allow=alaw
context=from-main-asterisk

При одновременном поступлении более 15-20 вызовов из транкая получил сообщение:

WARNING[2239][C-00000389] app_mysql.c: aMYSQL_query: mysql_query failed. Error: Lock wait timeout exceeded; try restarting transaction

Есть ли ограничения для одновременных транзакций в MariaDB?

Ответы [ 2 ]

0 голосов
/ 17 октября 2019

Количество транзакций ограничено до 96К. См. https://mariadb.com/kb/en/library/innodb-limitations/

INDEX(status, sim_name) (в таком порядке) может ускорить длительный запрос в вашей транзакции.

Или вы можете избежать сканирования таблицы, требуемого ORDER BY rand()используя один из методов, приведенных здесь: http://mysql.rjweb.org/doc.php/random

Другой подход заключается в изменении дизайна вашего приложения, чтобы получить, скажем, 10 случайных имен sim_name, пометить их как занятые вашим процессом, выйти из транзакции. Затем обработайте их и, наконец, отпустите их в других транзакциях.

Этот подход пометки и выпуска не является частью транзакции, содержащей действие - это особенно полезно, когда действиезанимает много времени.

Захват 10 так же быстр, как захват 1;следовательно, это дает вам скорость.

0 голосов
/ 10 октября 2019
  1. Используйте func_odbc, он корректно обрабатывает соединения
  2. Порядок с помощью rand () сканирует всю таблицу ВСЕГДА
  3. Если ваша таблица имеет тип myisam, любое сканирование таблицы блокирует всю таблицу.
...