|
|
| (16 intermediate revisions by 2 users not shown) |
| Line 2: |
Line 2: |
| [[Category:Troubleshooting]] | | [[Category:Troubleshooting]] |
|
| |
|
| This page provides troubleshooting guidance for VoIPmonitor database-related issues including SQL queue problems, CDR delays, MySQL performance tuning, and database errors. | | This page covers VoIPmonitor database troubleshooting: SQL queue issues, CDR delays, MySQL tuning, and database errors. |
|
| |
|
| {| class="wikitable" style="width:100%; background:#f8f9fa; border:2px solid #00A7E3; margin-bottom:20px;"
| | <kroki lang="mermaid"> |
| |-
| | %%{init: {'flowchart': {'nodeSpacing': 15, 'rankSpacing': 30}}}%% |
| ! colspan="3" style="background:#00A7E3; color:white; font-size:1.2em; padding:10px;" | Quick Navigation - Database Troubleshooting
| | flowchart TB |
| |-
| | START[CDRs Missing?] --> Q1{Service running?} |
| ! style="width:33%; background:#e0f4fc; padding:8px; vertical-align:top;" | SQL Queue Issues
| | Q1 -->|No| FIX1[systemctl start voipmonitor] |
| ! style="width:33%; background:#fef3e2; padding:8px; vertical-align:top;" | Database Errors
| | Q1 -->|Yes| Q2{SQLq/SQLf growing?} |
| ! style="width:33%; background:#f1f5f9; padding:8px; vertical-align:top;" | Performance & Migration
| | Q2 -->|Yes| Q3{CPU at 100%?} |
| |-
| | Q2 -->|No| Q4[Check timezone settings] |
| | style="vertical-align:top; padding:10px;" | | | Q3 -->|Yes| FIX2[Hardware upgrade needed] |
| '''CDR Visibility'''
| | Q3 -->|No| FIX3[Tune MySQL config] |
| * [[#Delay between active call and CDR view|CDR Delay Explained]]
| | </kroki> |
| * [[#Symptoms of Database Delays|Delay Symptoms]]
| |
| * [[#Quick CDR Visibility (Reduce Delay)|quick_save_cdr Option]]
| |
|
| |
|
| '''SQL Queue'''
| | = Service Not Running = |
| * [[#SQLq/SQLf|SQLq/SQLf Metrics]]
| |
| * [[#Clearing File Queue Backlog (qoq* Files)|qoq Files Backlog]]
| |
| * [[#Enable Disk-Based Query Queue (Prevent OOM)|query_cache Option]]
| |
| | style="vertical-align:top; padding:10px;" |
| |
| '''Error 1062'''
| |
| * [[#Troubleshooting: Database Error 1062 - Lookup Table Auto-Increment Limit|Error 1062 - 16777215]]
| |
| * [[#Identifying the Affected Table|Find Affected Table]]
| |
| * [[#Solution: Prevent New Unique Entries|Fix: cdr_reason_string_enable]]
| |
|
| |
|
| '''Related''' | | If Active Calls are visible but CDRs are missing after restart, the sniffer service likely didn't start. |
| * [[Upgrade_to_bigint|CDR Table INT Overflow]] (4B rows)
| |
| | style="vertical-align:top; padding:10px;" |
| |
| '''Tuning'''
| |
| * [[#More threads/connections to a db|Database Threads]]
| |
| * [[#MySQL/MariaDB Performance Tuning|MySQL Tuning]]
| |
|
| |
|
| '''Hardware'''
| | <syntaxhighlight lang="bash"> |
| * [[#When Configuration Tuning Is Not Enough: Hardware Upgrade Required|Hardware Upgrade Signs]]
| | # Check status |
| * [[#Migrating MySQL Data to Faster Storage|MySQL to SSD Migration]]
| | systemctl status voipmonitor |
| |}
| |
|
| |
|
| = SQL Queue and CDR Delays =
| | # Start if not running |
| | systemctl start voipmonitor |
|
| |
|
| == Delay between active call and CDR view ==
| | # Enable auto-start on boot |
| | systemctl enable voipmonitor |
| | </syntaxhighlight> |
|
| |
|
| The Active Calls view in the GUI displays the timestart of calls (INVITEs) obtained from the VoIPmonitor sniffer service, whereas the CDR view shows the stored CDRs (after the call ends) from the database.
| | {{Note|Active Calls come from sensor memory (real-time), while CDRs require the running service to write to database.}} |
|
| |
|
| == Symptoms of Database Delays == | | = SQL Queue and CDR Delays = |
|
| |
|
| When the database cannot keep up with CDR insertion rates, you may experience:
| | == Understanding SQLq/SQLf == |
|
| |
|
| * '''Slow CDR appearance in GUI''' - New calls take minutes to appear after they end
| | The '''SQLq/SQLf''' values in '''Settings → Sensors → Status''' show the queue size before CDRs are pushed to database. |
| * '''"Crontab log is too old" warning''' - The cron job runs slowly (every 5-10 minutes or more) instead of every minute due to database overload
| |
| * '''Lag between call end and reporting''' - Daily reports and alerts process outdated data
| |
|
| |
|
| To diagnose cron-related delays specifically, see [[Alerts#Crontab_Log_is_Too_Old_Warning_-_Database_Performance_Issues|"Crontab log is too old" troubleshooting]].
| | {| class="wikitable" |
| | |- |
| | ! Metric !! Meaning |
| | |- |
| | | '''Decreasing''' || Database catching up, CDRs will appear soon |
| | |- |
| | | '''Stuck/Growing''' || Database cannot keep up, needs tuning |
| | |- |
| | | '''Near zero''' || All queued CDRs processed |
| | |} |
|
| |
|
| == SQLq/SQLf == | | Monitor via logs: |
| | <syntaxhighlight lang="bash"> |
| | journalctl -u voipmonitor -f | grep SQLf |
| | </syntaxhighlight> |
|
| |
|
| In the service status (expanded status, status line) under GUI -> Settings -> Sensors : status, the SQLq/SQLf values represent the size of the queue before the CDRs are pushed to the database. When SQLq/SQLf is high, it usually indicates that the database is unable to process requests in a timely manner, causing them to queue.
| | == Quick CDR Visibility == |
|
| |
|
| See [[Logging#SQLq/SQLf]] for more details on these metrics.
| | Reduce delay between call end and CDR appearance in <code>/etc/voipmonitor.conf</code>: |
|
| |
|
| == Make sure that db config is not causing io overhead == | | {| class="wikitable" |
| | |- |
| | ! Setting !! Delay !! Impact |
| | |- |
| | | <code>quick_save_cdr = no</code> || 10s (default) || Lowest load |
| | |- |
| | | <code>quick_save_cdr = yes</code> || 3s || Moderate CPU/IO increase |
| | |- |
| | | <code>quick_save_cdr = quick</code> || 1s || High CPU/IO increase |
| | |} |
|
| |
|
| If the MySQL configuration already follows the recommendations from the scaling section of our documentation (especially innodb_flush_log_at_trx_commit and innodb_buffer_pool_size):
| | == Disk-Based Query Queue (OOM Prevention) == |
|
| |
|
| https://www.voipmonitor.org/doc/Scaling#SSDs
| | <syntaxhighlight lang="ini"> |
| | # /etc/voipmonitor.conf - KEEP THIS ENABLED |
| | query_cache = yes |
| | </syntaxhighlight> |
|
| |
|
| == Quick CDR Visibility (Reduce Delay) == | | {{Warning|1='''Never set <code>query_cache = no</code>''' — if database becomes unreachable and memory fills, OOM killer terminates VoIPmonitor and all queued CDRs are lost.}} |
|
| |
|
| If CDRs are taking too long to appear in the GUI after calls end (typically 30-60 seconds delay), you can reduce this delay by enabling quick CDR save mode. Add this parameter to <code>/etc/voipmonitor.conf</code>:
| | == qoq* Files Backlog == |
|
| |
|
| quick_save_cdr = yes
| | When database lags, SQL queries buffer to <code>qoq*</code> files in <code>/var/spool/voipmonitor</code>. |
|
| |
|
| This speeds up the visibility of calls in the GUI by reducing the buffering delay before CDRs are written to the database.
| | '''Solution 1 (Preferred):''' Wait for automatic processing — monitor SQLf decreasing. |
|
| |
|
| {{Warning|
| | '''Solution 2 (Emergency):''' Delete backlog (loses queued CDRs): |
| '''Performance Impact:''' Enabling <code>quick_save_cdr</code> increases CPU and I/O load on the database server by forcing more frequent CDR writes. Only use this if near-real-time CDR visibility is absolutely required. | | <syntaxhighlight lang="bash"> |
| }}
| | systemctl stop voipmonitor |
| | rm -f /var/spool/voipmonitor/qoq* |
| | systemctl start voipmonitor |
| | </syntaxhighlight> |
|
| |
|
| Available options:
| | == Increasing Database Threads == |
| * <code>no</code> (default) - 10 second delay, recommended for most deployments
| |
| * <code>yes</code> - 3 second delay, moderate performance impact
| |
| * <code>quick</code> - 1 second delay, high performance impact
| |
|
| |
|
| See [[Sniffer_configuration#Performance_.26_Schema|Sniffer Configuration]] for more details on this parameter.
| | <syntaxhighlight lang="ini"> |
| | | # /etc/voipmonitor.conf |
| == Enable Disk-Based Query Queue (Prevent OOM) ==
| | mysqlstore_max_threads_cdr = 8 |
| | | mysqlstore_max_threads_sip_msg = 8 |
| If your system is experiencing Out Of Memory (OOM) issues or if the SQL queue keeps growing during peak traffic, ensure that disk-based query queuing is enabled. Add or verify this parameter in <code>/etc/voipmonitor.conf</code>:
| |
| | |
| query_cache = yes
| |
| | |
| This is a '''critical''' feature. When enabled, SQL queries are first saved to disk-based queue files (qoq* files in the spool directory) before being sent to the database. This prevents OOM and data loss if the database is temporarily unavailable. The default is <code>yes</code>, but if it was previously set to <code>no</code>, changing it to <code>yes</code> will use disk storage instead of RAM for queued queries.
| |
| | |
| {{Note|
| |
| <strong>Do not set <code>query_cache = no</code> to improve performance.</strong> While disabling query cache reduces CDR delay by holding queries in RAM instead of writing to qoq files, this creates a severe risk: if the database becomes unreachable and memory fills up, OOM killer will terminate the VoIPmonitor process and all queued CDRs will be lost. Keep <code>query_cache = yes</code> for data safety, and use <code>quick_save_cdr</code> instead for faster CDR visibility.
| |
| }}
| |
| | |
| See [[Sniffer_configuration#Performance_.26_Schema|Sniffer Configuration]] for more details on this parameter.
| |
| | |
| == More threads/connections to a db ==
| |
| | |
| You can also increase the number of threads used for connection to a db for particular use like CDRs - the VoIPmonitor sniffer service in /etc/voipmonitor.conf uses the option:
| |
| | |
| mysqlstore_max_threads_cdr = 8
| |
| | |
| === Important: mysql_enable_set_id Limitation ===
| |
| | |
| If you are using <code>mysql_enable_new_store = per_query</code> or have enabled <code>mysql_enable_set_id = yes</code>, please note that this configuration '''limits your setup to a single sensor writing to the database'''. This option allows the central server to generate CDR IDs instead of waiting for MySQL's AUTO_INCREMENT, which can improve batch insert performance. However, this architecture only works when one sensor is responsible for all database writes. If you have multiple sensors writing to the same database, do not enable this option as it will cause ID conflicts and data corruption.
| |
| | |
| If you are processing a high volume of SIP OPTIONS, SUBSCRIBE, or NOTIFY messages and see the <code>sip_msg</code> queue growing, you can increase threads specifically for those messages:
| |
| | |
| mysqlstore_max_threads_sip_msg = 8
| |
| | |
| However, if the database is waiting for storage I/O, increasing the number of threads will not help.
| |
| | |
| == Clearing File Queue Backlog (qoq* Files) ==
| |
| | |
| When the file queue grows and recent calls are not appearing in CDR despite active calls being visible, you may have a backlog of qoq* files in the spool directory waiting to be processed.
| |
| | |
| === What are qoq* Files? ===
| |
| | |
| The VoIPmonitor sniffer creates <code>qoq*</code> (queue) files in the spool directory (default: <code>/var/spool/voipmonitor</code>) to buffer database operations. These files contain queued SQL commands waiting to be inserted into the database.
| |
| | |
| When the database cannot keep up with the insertion rate:
| |
| * Active calls are visible in the GUI (retrieved from sensor memory in real-time)
| |
| * Recent CDRs do not appear (waiting in qoq queue files)
| |
| * SQLq metric stays high or continues growing
| |
| | |
| === Solution 1: Wait for Queue Processing ===
| |
| | |
| The system will automatically process the qoq* files as the database catches up. Monitor the progress:
| |
| | |
| <syntaxhighlight lang="bash">
| |
| # Check the SQLf parameter in logs to monitor queue size
| |
| # SQLf should decrease over time as files are processed
| |
| | |
| # View current qoq files in spool directory
| |
| ls -lh /var/spool/voipmonitor/qoq* 2>/dev/null | wc -l
| |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| This is the preferred approach if losing older CDRs is not acceptable.
| | {{Note|Auto-scaling: When queue exceeds 1,000 items, threads automatically increase up to 99. However, if database waits for storage I/O, more threads won't help.}} |
|
| |
|
| === Solution 2: Delete qoq* Files (Emergency) === | | {{Warning|1=<code>mysql_enable_set_id = yes</code> limits setup to '''single sensor''' writing to database. Do not use with multiple sensors.}} |
|
| |
|
| If immediate access to recent CDRs is critical and you can afford to lose older CDRs, you can delete the qoq* files to clear the backlog:
| | = Timezone Issues = |
|
| |
|
| <syntaxhighlight lang="bash">
| | If CDRs stop appearing after time change but Active Calls work: |
| # WARNING: This will delete any CDRs still waiting in the files
| |
| # Stop the VoIPmonitor service first
| |
| systemctl stop voipmonitor
| |
|
| |
|
| # Delete all qoq* files from the spool directory
| | 1. Check '''Settings → Sensors → Status''': If SQLq/SQLf NOT growing and "last CDR stored" is current, it's a timezone issue |
| rm -f /var/spool/voipmonitor/qoq*
| | 2. Verify '''Settings → System Configuration → National''': |
| | * '''Timezone''' = GUI host timezone (for reports/alerts) |
| | * '''Sensors Timezone''' = CDR timestamp display timezone |
|
| |
|
| # Start the VoIPmonitor service | | Override in sensor config: |
| systemctl start voipmonitor
| | <syntaxhighlight lang="ini"> |
| | # /etc/voipmonitor.conf |
| | timezone = /usr/share/zoneinfo/Europe/London |
| | # OR for multi-timezone deployments: |
| | utc = yes |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| {{Warning|
| | = MySQL/MariaDB Tuning = |
| '''Data Loss Warning:''' Deleting qoq* files will delete any CDRs that were waiting in the queue files. Only use this method if:
| |
| * Immediate access to recent CDRs is critical
| |
| * Losing older CDRs is acceptable
| |
| * You have exhausted all other options (configuration tuning, hardware upgrade)
| |
| }}
| |
|
| |
|
| This clears the backlog and allows new CDRs to be written immediately without waiting for the old queue to process.
| | == Essential Configuration == |
| | |
| = MySQL/MariaDB Performance Tuning = | |
| | |
| == Optimize MySQL Performance == | |
| | |
| Tune the MySQL/MariaDB server for better write performance to handle the high insert rate from VoIPmonitor.
| |
| | |
| Edit your MySQL configuration file (typically <code>/etc/mysql/my.cnf</code> or <code>/etc/mysql/mariadb.conf.d/50-server.cnf</code>):
| |
|
| |
|
| <syntaxhighlight lang="ini"> | | <syntaxhighlight lang="ini"> |
| | # /etc/mysql/my.cnf or /etc/mysql/mariadb.conf.d/50-server.cnf |
| [mysqld] | | [mysqld] |
| # InnoDB buffer pool size - set to approximately 50-70% of available RAM on a dedicated database server | | # 50-70% of RAM on dedicated DB server, 30-50% if shared with VoIPmonitor |
| # On servers running VoIPmonitor and MySQL together, use approximately 30-50% of RAM
| |
| innodb_buffer_pool_size = 8G | | innodb_buffer_pool_size = 8G |
|
| |
|
| # Reduce transaction durability for faster writes (may lose up to 1 second of data on crash) | | # Faster writes (may lose up to 1s of data on crash) |
| innodb_flush_log_at_trx_commit = 2 | | innodb_flush_log_at_trx_commit = 2 |
| | |
| | # Disable slow query log if causing high memory (>90%) |
| | slow_query_log = 0 |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| Restart MySQL and VoIPmonitor: | | Restart services: |
| <syntaxhighlight lang="bash"> | | <syntaxhighlight lang="bash"> |
| systemctl restart mysql | | systemctl restart mysql && systemctl restart voipmonitor |
| systemctl restart voipmonitor | |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| {{Warning|Setting <code>innodb_flush_log_at_trx_commit</code> to <code>2</code> trades some data safety for performance. In the event of a power loss or crash, up to 1 second of the most recent transactions may be lost.}}
| | For detailed tuning, see [[Scaling#MySQL.2FMariaDB_Configuration|Scaling - MySQL Configuration]]. |
|
| |
|
| == When Configuration Tuning Is Not Enough: Hardware Upgrade Required == | | == Hardware Upgrade Signs == |
|
| |
|
| If you have applied all the configuration optimizations above and the SQL queue continues to grow or the database remains significantly behind the processing queue, the underlying issue may be insufficient hardware. | | If after all tuning optimizations: |
| | * CPU consistently at 100% |
| | * SQLq keeps growing |
| | * Large delay between "Last CDR in queue" and "Last CDR in database" |
|
| |
|
| === Signs That Hardware Upgrade Is Necessary ===
| | → '''Hardware upgrade required''' (modern CPU, NVMe SSD, more RAM). See [[Hardware]] for sizing. |
|
| |
|
| * '''CPU load is consistently at or near 100%''' on both the database and GUI servers, even during normal traffic patterns
| | == MySQL Data Migration to SSD == |
| * '''Old or aging hardware''' - Servers with CPUs more than several years old may lack the performance of modern processors
| |
| * '''Configuration tuning provides only marginal improvement''' - After applying MySQL and VoIPmonitor optimizations, the delay between the "Last CDR in processing queue" and "Last CDR in database" remains significant
| |
|
| |
|
| === Diagnosing Hardware Limitations === | | <syntaxhighlight lang="bash"> |
| | # 1. Stop MySQL |
| | systemctl stop mysql |
|
| |
|
| Monitor CPU usage on both the database and GUI servers:
| | # 2. Copy data (preserves permissions) |
| | | rsync -avx /var/lib/mysql/ /mnt/fast_storage/mysql/ |
| <syntaxhighlight lang="bash">
| |
| # Check CPU load during peak traffic | |
| top
| |
|
| |
|
| # Or use sar for historical data | | # 3. Update /etc/mysql/my.cnf |
| sar -u 1 10
| | # datadir = /mnt/fast_storage/mysql |
|
| |
|
| # Check CPU core usage per process | | # 4. Update AppArmor if applicable (Ubuntu/Debian) |
| mpstat -P ALL 1 5
| | # 5. Start MySQL |
| | systemctl start mysql |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| If the CPU load is consistently at or near 100% across multiple cores, the hardware cannot keep up with the traffic load. No amount of configuration tuning will solve this issue - the servers themselves need to be upgraded.
| | {{Note|No CDR loss — VoIPmonitor queues CDRs during MySQL downtime.}} |
| | |
| === Hardware Upgrade Recommendations ===
| |
| | |
| Upgrade to a more modern CPU architecture with significantly better performance:
| |
|
| |
|
| * '''CPU''' - Modern AMD EPYC or Intel Xeon Gold/Silver processors with more cores
| |
| * '''RAM''' - Ensure sufficient memory for the database buffer pool (see [[Scaling#Memory_Configuration|Memory Configuration]])
| |
| * '''Storage''' - Use NVMe SSDs for the database to eliminate I/O bottlenecks
| |
|
| |
|
| === Architecture Consideration: Merge GUI and Database ===
| |
|
| |
|
| In some cases, merging the GUI and database roles onto a single, powerful new server can be more efficient than maintaining separate, underpowered servers. A single modern server with sufficient CPU cores and RAM can often handle both workloads more effectively than multiple older servers.
| | === Long-Running Queries Blocking Operations === |
|
| |
|
| For hardware sizing examples, see the [[Hardware]] page, which includes real-world deployments for various call volumes.
| | If long-running dashboard queries (GROUP BY aggregations on millions of CDR rows) are blocking partition maintenance operations (creation/dropping of partitions): |
|
| |
|
| === Migrating MySQL Data to Faster Storage === | | {{Warning|1='''AuroraDB''' does '''not''' support the MySQL <code>KILL</code> command correctly and is '''not officially supported'''. Consider migrating to standard MySQL or MariaDB for production deployments.}} |
|
| |
|
| When upgrading from HDD or slow SATA SSDs to NVMe storage, you can migrate the MySQL data directory (`datadir`) while the system is running. There is no CDR loss expected with this method because the sniffer queues the CDRs internally and will process them after MySQL restarts.
| | === Solution Steps === |
|
| |
|
| '''Prerequisites:''' | | '''1. Implement query timeout via PHP script''' |
| * New SSD/NVMe storage installed and mounted
| |
| * Sufficient disk space on the new storage for the existing MySQL data
| |
| * MySQL/MariaDB service can be stopped briefly for the migration
| |
|
| |
|
| '''Migration Procedure:'''
| | Create a PHP script to automatically kill queries running longer than 3600 seconds (1 hour): |
|
| |
|
| <syntaxhighlight lang="bash"> | | <syntaxhighlight lang="bash"> |
| # 1. Prepare the new storage (if your SSD is hot-pluggable) | | # Example script: add to cron to run periodically |
| # Mount the new filesystem. Example:
| | # Queries running > 3600 seconds will be terminated to prevent lock issues |
| mount /dev/nvme0n1p1 /mnt/fast_storage
| | </syntaxhighlight> |
| mkdir /mnt/fast_storage/mysql
| |
|
| |
|
| # 2. Stop the MySQL service
| | '''2. Check network latency between GUI and database server''' |
| systemctl stop mysql
| |
| # Or for MariaDB:
| |
| # systemctl stop mariadb
| |
|
| |
|
| # 3. Copy the MySQL data directory to the new location
| | High latency can exacerbate query blocking issues. Ensure minimal network delay. |
| # The -a flag preserves permissions and ownership, -x skips other filesystems
| |
| rsync -avx /var/lib/mysql/ /mnt/fast_storage/mysql/
| |
|
| |
|
| # 4. Verify the copy
| | '''3. Set MySQL max_execution_time''' |
| ls -la /mnt/fast_storage/mysql/
| |
| # Check that all databases are present
| |
|
| |
|
| # 5. Update MySQL configuration to point to the new datadir location
| | Add to MySQL/MariaDB configuration: |
| # Edit /etc/mysql/my.cnf or /etc/my.cnf and change:
| |
| # datadir = /var/lib/mysql
| |
| # To:
| |
| # datadir = /mnt/fast_storage/mysql
| |
|
| |
|
| # Also update the socket location if needed:
| | <syntaxhighlight lang="ini"> |
| # socket = /tmp/mysql.sock (or your preferred location) | | # /etc/mysql/my.cnf or /etc/my.cnf.d/server.cnf |
| | [mysqld] |
| | max_execution_time = 3600000 # 1 hour in milliseconds |
| | </syntaxhighlight> |
|
| |
|
| # 6. Update AppArmor/SELinux (Ubuntu/Debian only)
| | '''4. Force internal MySQL grouping (fallback)''' |
| # Edit /etc/apparmor.d/usr.sbin.mysqld and update the paths:
| |
| # /var/lib/mysql/ r,
| |
| # /var/lib/mysql/** rwk,
| |
| # Change to:
| |
| # /mnt/fast_storage/mysql/ r,
| |
| # /mnt/fast_storage/mysql/** rwk,
| |
|
| |
|
| # Reload AppArmor:
| | If performance issues persist: |
| systemctl reload apparmor
| |
|
| |
|
| # 7. Start MySQL with the new datadir
| |
| systemctl start mysql
| |
|
| |
| # 8. Verify MySQL is running and databases are accessible
| |
| mysql -e "SHOW DATABASES;"
| |
| mysql -e "SELECT COUNT(*) FROM cdr;"
| |
|
| |
| # 9. Monitor the SQL queue in the VoIPmonitor GUI
| |
| # Navigate to GUI -> Settings -> Sensors -> Status
| |
| # The SQLq value should decrease as queued CDRs are processed
| |
| </syntaxhighlight>
| |
|
| |
| '''Important Notes:'''
| |
|
| |
| * '''No CDR Loss:''' The VoIPmonitor sniffer queues CDRs in memory during MySQL downtime. These will be processed after MySQL restarts.
| |
| * '''Backup First:''' Always take a backup of `/var/lib/mysql` before migration.
| |
| * '''Service Downtime:''' Plan for MySQL to be stopped for the duration of the copy operation (depends on database size and storage speed).
| |
| * '''Storage Mount Options:''' For the new database partition, mount with ext4 optimizations:
| |
| <pre>
| |
| /dev/nvme0n1p1 /mnt/fast_storage ext4 defaults,noatime,data=writeback,barrier=0 0 1
| |
| </pre>
| |
| * '''Permissions:''' Ensure the new datadir and all files are owned by the MySQL user (`mysql:mysql`).
| |
| * '''Symbolic Links Alternative:''' You can create a symbolic link instead of changing the datadir in my.cnf:
| |
| <syntaxhighlight lang="bash"> | | <syntaxhighlight lang="bash"> |
| # After stopping MySQL and copying data: | | # Delete charts binaries to force internal MySQL grouping |
| mv /var/lib/mysql /var/lib/mysql.old
| | rm -f /usr/local/sbin/charts* |
| ln -s /mnt/fast_storage/mysql /var/lib/mysql
| | systemctl restart voipmonitor |
| systemctl start mysql | |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
| = Database Errors = | | = Database Errors = |
|
| |
|
| == Troubleshooting: Database Error 1062 - Lookup Table Auto-Increment Limit == | | == Error 1062 - Lookup Table Limit (16777215) == |
|
| |
|
| If the sniffer logs show a database error `1062 - Duplicate entry '16777215' for key 'PRIMARY'` and new CDRs stop being stored, this is caused by a lookup table reaching its maximum auto-increment limit.
| | '''Symptom:''' <code>1062 - Duplicate entry '16777215' for key 'PRIMARY'</code> on lookup tables (<code>cdr_sip_response</code>, <code>cdr_reason</code>). |
|
| |
|
| === Symptoms ===
| | '''Cause:''' MEDIUMINT limit reached due to too many unique SIP response strings. |
|
| |
|
| * CDRs stop being inserted into the database
| | '''Fix (choose one):''' |
| * Sniffer logs show: `query error in [call __insert_10_0S1();]: 1062 - Duplicate entry '16777215' for key 'PRIMARY'`
| |
| * The error affects a lookup table (such as `cdr_sip_response` or `cdr_reason`)
| |
| * The value 16777215 (16,777,215) indicates the table is using `MEDIUMINT UNSIGNED` for the ID column
| |
|
| |
|
| === Root Cause === | | {| class="wikitable" |
| | |- |
| | ! Option !! Configuration !! Notes |
| | |- |
| | | '''Disable storage''' || <code>cdr_reason_string_enable = no</code> || Stops creating new entries |
| | |- |
| | | '''Enable normalization''' || <code>cdr_reason_normalisation = yes</code><br><code>cdr_sip_response_normalisation = yes</code><br><code>cdr_ua_normalisation = yes</code> || Reduces unique entries |
| | |- |
| | | '''Immediate fix''' || <code>TRUNCATE TABLE cdr_reason;</code> || Resets counter, loses lookup data |
| | |} |
|
| |
|
| VoIPmonitor uses lookup tables (like `cdr_sip_response` or `cdr_reason`) to store unique values such as SIP response reason strings or custom response text. These are used to normalize data and reduce storage in the main `cdr` table.
| | After config change, clear queued failed queries: |
| | <syntaxhighlight lang="bash"> |
| | systemctl stop voipmonitor |
| | rm -f /var/spool/voipmonitor/qoq-* |
| | systemctl start voipmonitor |
| | </syntaxhighlight> |
|
| |
|
| When the system receives many unique SIP response strings or reason messages (e.g., different error messages from various carriers, devices with custom SIP header formats, or PBX-specific responses), the lookup table's auto-increment ID can reach the `MEDIUMINT` limit of 16,777,215. Once this limit is hit, new unique values cannot be inserted, causing all subsequent CDRs to fail with error 1062.
| | {{Warning|1=This is '''NOT''' a schema issue — do not migrate to BIGINT. Different from main <code>cdr</code> table overflow (see [[Upgrade_to_bigint]]).}} |
|
| |
|
| === Identifying the Affected Table === | | == SUPER Privilege Error == |
|
| |
|
| Check which lookup table is hitting the limit:
| | '''Symptom:''' <code>ERROR 1227 (42000): Access denied; you need SUPER privilege(s)</code> |
|
| |
|
| | '''Fix:''' |
| <syntaxhighlight lang="sql"> | | <syntaxhighlight lang="sql"> |
| -- Check the current AUTO_INCREMENT value for lookup tables | | -- MySQL 5.7 / MariaDB |
| SELECT
| | GRANT SUPER ON *.* TO 'voipmonitor_user'@'%'; |
| TABLE_NAME,
| | |
| COLUMN_TYPE,
| | -- MySQL 8.0+ |
| AUTO_INCREMENT
| | GRANT SYSTEM_VARIABLES_ADMIN ON *.* TO 'voipmonitor_user'@'%'; |
| FROM
| | |
| INFORMATION_SCHEMA.TABLES
| | FLUSH PRIVILEGES; |
| JOIN
| |
| INFORMATION_SCHEMA.COLUMNS
| |
| USING (TABLE_SCHEMA, TABLE_NAME)
| |
| WHERE
| |
| TABLE_SCHEMA = 'voipmonitor' AND
| |
| (TABLE_NAME LIKE 'cdr_sip%' OR TABLE_NAME LIKE 'cdr_reason%') AND
| |
| COLUMN_KEY = 'PRI' AND
| |
| EXTRA LIKE '%auto_increment%'
| |
| ORDER BY AUTO_INCREMENT DESC;
| |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| Look for AUTO_INCREMENT values approaching or exceeding 16,000,000 in tables using `MEDIUMINT`.
| | {{Note|SUPER is a global privilege — database-specific grants (<code>ALL ON voipmonitor.*</code>) do NOT include it.}} |
|
| |
|
| === Solution: Prevent New Unique Entries === | | == Unknown Column Error (Schema Mismatch) == |
|
| |
|
| The most effective solution is to configure VoIPmonitor to stop storing or normalize the unique SIP response text that is causing the rapid growth of the lookup table.
| | '''Symptom:''' <code>Unknown column 'from_time' in 'field list'</code>, qoq files accumulating. |
|
| |
|
| ==== Option 1: Disable SIP Response Text Storage ====
| | '''Cause:''' Sensor version newer than database schema. |
|
| |
|
| Edit `/etc/voipmonitor.conf` on the sniffer to disable storing SIP response reason text:
| | '''Fix:''' |
| | # '''GUI → Tools → System Status → Check MySQL Schema''' → Start Upgrade |
| | # If unavailable: backup with <code>mysqldump</code>, then recreate table (see [[Recovering_corrupted_database_tables]]) |
|
| |
|
| | '''Prevention (distributed setups):''' |
| <syntaxhighlight lang="ini"> | | <syntaxhighlight lang="ini"> |
| # Disable storing SIP response reason strings in lookup tables | | # On ALL sensors (not central server): |
| cdr_reason_string_enable = no
| | disable_partition_operations = yes |
| </syntaxhighlight> | | </syntaxhighlight> |
| | === Automatic Schema Upgrades and Production Safety === |
|
| |
|
| This prevents the system from creating new unique entries for SIP response reason strings. Restart the sniffer:
| | VoIPmonitor includes a '''built-in safety mechanism''' to prevent unexpected database schema modifications on production databases. |
| | |
| <syntaxhighlight lang="bash">
| |
| systemctl restart voipmonitor
| |
| </syntaxhighlight>
| |
|
| |
|
| ==== Option 2: Normalize Response Text ====
| | '''Safety Threshold:''' Automatic schema modifications (ALTER TABLE) only occur if the database contains fewer than '''1000 CDRs'''. |
|
| |
|
| If you need to keep some response text but reduce the number of unique entries, enable normalization in `/etc/voipmonitor.conf`:
| | {| class="wikitable" |
| | |- |
| | ! Database Size !! Behavior |
| | |- |
| | | '''< 1000 CDRs''' || Automatic schema upgrades applied on sniffer startup |
| | |- |
| | ! '''> 1000 CDRs'''''' || ALTER queries logged to '''syslog/messages/journalctl''' - manual execution required |
| | |} |
|
| |
|
| <syntaxhighlight lang="ini">
| | For production databases (>1000 CDRs), when a new sniffer version detects required schema changes: |
| # Normalize SIP response text to reduce unique entries
| |
| cdr_reason_normalisation = yes
| |
| cdr_sip_response_normalisation = yes
| |
| cdr_ua_normalisation = yes
| |
| </syntaxhighlight>
| |
|
| |
|
| Normalization transforms similar response strings into a single canonical form, significantly reducing the number of unique rows created. Include all three normalization options for maximum effectiveness.
| | # Review logged ALTER queries: <code>journalctl -u voipmonitor | grep ALTER</code> or <code>grep ALTER /var/log/syslog</code> |
| | # Execute manually during low-traffic period (e.g., overnight) to prevent table locking |
| | # Restart sniffer after schema changes complete |
|
| |
|
| ==== Option 3: Clear Queued SQL Queries ====
| | {{Warning|Never rely on <code>disable_dbupgradecheck</code> for production safety - it's unnecessary because the 1000 CDR threshold already protects large databases from automatic modifications.}} |
|
| |
|
| If error 1062 persists after applying the configuration changes and restarting the service, there may be a large backlog of failed SQL queries queued in the spool directory. Clearing this queue can eliminate the persistent 1062 errors that are caused by previously buffered failed inserts.
| | {{See Also|1=For connecting additional sensors to an existing database, see [[Multiple_sniffer_instancies|Multiple Sniffer Instances]] - ensure unique <code>id_sensor</code> values.}} |
| | == Row Size Too Large (cdr_stat_values) == |
|
| |
|
| {{Warning|This step will DELETE all buffered CDRs in the queue. These CDRs will be permanently lost.}}
| | '''Symptom:''' Calls don't appear in GUI until service restart, "Row size too large" errors. |
| | |
| To clear the SQL queue:
| |
|
| |
|
| | '''Fix (destructive):''' |
| <syntaxhighlight lang="bash"> | | <syntaxhighlight lang="bash"> |
| # 1. Stop the VoIPmonitor service
| |
| systemctl stop voipmonitor | | systemctl stop voipmonitor |
|
| |
|
| # 2. Remove the queued query files (qoq-* files) | | # Save structure for analysis |
| # The default spool directory is /var/spool/voipmonitor
| | mysqldump -u root -p -d voipmonitor cdr_stat_values > cdr_stat_backup.sql |
| rm -f /var/spool/voipmonitor/qoq-*
| |
|
| |
|
| # 3. Verify the files are removed | | # Recreate database |
| ls /var/spool/voipmonitor/qoq-*
| | mysql -u root -p -e "DROP DATABASE voipmonitor; CREATE DATABASE voipmonitor;" |
|
| |
|
| # 4. Restart the service
| |
| systemctl start voipmonitor | | systemctl start voipmonitor |
|
| |
| # 5. Check that service is running
| |
| systemctl status voipmonitor
| |
| </syntaxhighlight> | | </syntaxhighlight> |
|
| |
|
| After restarting, the service should no longer attempt to re-insert the previously failed 1062 queries from the queue. Monitor the logs to confirm the error has stopped.
| | {{Warning|This deletes all CDR data. Only use if data loss is acceptable.}} |
| | |
| ==== Option 4: Clean Existing Data (Immediate Fix) ====
| |
| | |
| The lookup table has reached its MEDIUMINT limit, preventing new CDRs from being stored. Truncating the table clears it and resets the auto-increment counter to 1, allowing CDRs to be written immediately.
| |
| | |
| {{Warning|TRUNCATE permanently deletes all data. This will remove the exact SIP response text display in the GUI for historical CDRs, but will not affect the main CDR records or call data. Only do this if you are certain you no longer need the original response text.}} | |
| | |
| <syntaxhighlight lang="sql">
| |
| -- Clear the cdr_reason table (adjust table name as needed based on error message)
| |
| TRUNCATE TABLE cdr_reason;
| |
| </syntaxhighlight>
| |
| | |
| === Verification ===
| |
| | |
| After applying the fix:
| |
| | |
| 1. Check that CDRs are being stored again by monitoring the sniffer logs
| |
| 2. Verify the lookup table AUTO_INCREMENT is no longer increasing rapidly:
| |
| <syntaxhighlight lang="sql">
| |
| SELECT AUTO_INCREMENT FROM INFORMATION_SCHEMA.TABLES
| |
| WHERE TABLE_NAME = 'cdr_sip_response' AND TABLE_SCHEMA = 'voipmonitor';
| |
| </syntaxhighlight>
| |
| 3. Monitor the error logs to confirm the 1062 error has stopped appearing
| |
|
| |
|
| === Important Note: NOT a Database Schema Issue === | | = See Also = |
|
| |
|
| This error is typically NOT solved by changing the database schema (e.g., migrating to BIGINT). The root cause is storing too many unique SIP response strings, which will continue to grow regardless of the ID column size. The correct solution is to configure VoIPmonitor to stop creating these unique entries via the `cdr_reason_string_enable` configuration option.
| | * [[Sniffer_configuration]] - Configuration parameters reference |
| | * [[Scaling]] - Performance tuning |
| | * [[Hardware]] - Hardware sizing |
| | * [[Upgrade_to_bigint]] - CDR table INT overflow (4B rows) |
| | * [[Recovering_corrupted_database_tables]] - Table corruption recovery |
| | * [[Sniffer_troubleshooting]] - Network/capture issues |
|
| |
|
| {{Warning|Do NOT confuse this with the unrelated `cdr` table integer overflow problem. The main `cdr` table may encounter limits around 4 billion rows (32-bit INT), which is addressed in the [[Upgrade_to_bigint]] guide. Lookup table issues at 16.7 million (MEDIUMINT) are solved by configuration, not schema migration.}}
| |
|
| |
|
| == See Also == | | = AI Summary for RAG = |
| * [[Sniffer_configuration]] - Complete configuration reference for voipmonitor.conf
| |
| * [[Scaling]] - Performance tuning and optimization
| |
| * [[Hardware]] - Hardware sizing guidelines
| |
| * [[Upgrade_to_bigint]] - Migrating CDR table to BIGINT (for main cdr table INT overflow)
| |
| * [[GUI_troubleshooting]] - GUI-specific issues
| |
| * [[Sniffer_troubleshooting]] - Sensor/sniffer issues (no calls, network problems)
| |
|
| |
|
| == AI Summary for RAG ==
| | '''Summary:''' VoIPmonitor database troubleshooting guide. SERVICE: If Active Calls visible but CDRs missing after restart, start voipmonitor service. SQL QUEUE: SQLq/SQLf in Settings→Sensors→Status shows DB queue size. Growing = DB cannot keep up. QUICK CDR: quick_save_cdr=yes (3s) or quick (1s) reduces CDR delay. QOQ FILES: SQL buffered to qoq* files in /var/spool/voipmonitor when DB lags. Emergency clear: rm qoq* (loses data). THREADS: mysqlstore_max_threads_cdr=8, auto-scales to 99 when queue>1000. mysql_enable_set_id=yes limits to single sensor. MYSQL TUNING: innodb_buffer_pool_size=50-70% RAM, innodb_flush_log_at_trx_commit=2. ERROR 1062: Lookup table (cdr_sip_response/cdr_reason) hit MEDIUMINT 16777215 limit. Fix: cdr_reason_string_enable=no or enable normalization. NOT a schema issue. SUPER PRIVILEGE: GRANT SUPER ON *.* (MySQL 5.7) or SYSTEM_VARIABLES_ADMIN (MySQL 8.0+). SCHEMA MISMATCH: Unknown column error = sensor newer than DB schema. Fix via GUI Check MySQL Schema tool. TIMEZONE: If CDRs disappear after time change, check Settings→System Configuration→National timezone settings. |
| '''Summary:''' This page covers VoIPmonitor database troubleshooting including SQL queue issues, CDR delays, MySQL performance tuning, and database errors. SQL QUEUE DELAYS: The Active Calls view shows real-time data from sniffer while CDR view shows database records - delays occur when database cannot keep up. Symptoms include slow CDR appearance, "Crontab log is too old" warning, lag in reporting. Monitor SQLq/SQLf metrics in GUI Settings -> Sensors -> Status. QUICK CDR VISIBILITY: Use quick_save_cdr=yes (3s delay) or quick_save_cdr=quick (1s delay) in voipmonitor.conf to reduce CDR appearance delay (default is 10s). Warning: increases CPU/I/O load. QOQ FILES: SQL queries are buffered in qoq* files in /var/spool/voipmonitor when database is slow. To clear backlog: either wait for automatic processing (preferred), or emergency delete: stop voipmonitor, rm -f /var/spool/voipmonitor/qoq*, start voipmonitor (loses queued CDRs). PREVENT OOM: Keep query_cache=yes (default) to store queries on disk instead of RAM - never set to no as it risks OOM and CDR loss. DATABASE THREADS: Increase mysqlstore_max_threads_cdr and mysqlstore_max_threads_sip_msg for high traffic (default 4, can increase to 8-16). Note: mysql_enable_set_id=yes limits setup to single sensor writing to database. MYSQL TUNING: Set innodb_buffer_pool_size=50-70% RAM on dedicated DB or 30-50% on shared server. Set innodb_flush_log_at_trx_commit=2 for faster writes (may lose 1 second of data on crash). HARDWARE UPGRADE: If CPU is consistently at 100% after tuning, hardware upgrade is needed - modern AMD EPYC or Intel Xeon with NVMe SSD. MYSQL TO SSD MIGRATION: Stop MySQL, rsync /var/lib/mysql to new SSD, update datadir in my.cnf, update AppArmor paths, start MySQL. No CDR loss expected as sniffer queues internally. ERROR 1062 - LOOKUP TABLE LIMIT: If logs show "1062 - Duplicate entry '16777215' for key 'PRIMARY'" and CDRs stop being stored, this is lookup table (cdr_sip_response, cdr_reason) hitting MEDIUMINT limit (16,777,215). NOT a schema issue. SOLUTION: Set cdr_reason_string_enable=no in voipmonitor.conf to disable storing SIP response strings, OR enable all three normalization options (cdr_reason_normalisation=yes, cdr_sip_response_normalisation=yes, cdr_ua_normalisation=yes). IMMEDIATE FIX: TRUNCATE TABLE cdr_reason to reset auto-increment. CLEAR QUEUE: If error persists after config change, stop service, rm -f /var/spool/voipmonitor/qoq-*, restart. Do NOT confuse with cdr table INT overflow (4B rows) which requires Upgrade_to_bigint guide. | |
|
| |
|
| '''Keywords:''' SQL queue, SQLq, SQLf, database delay, CDR delay, active calls, CDR view, mysqlstore_max_threads_cdr, mysqlstore_max_threads_sip_msg, quick_save_cdr, query_cache, qoq files, queue files, spool directory, database backlog, innodb_buffer_pool_size, innodb_flush_log_at_trx_commit, MySQL tuning, MariaDB tuning, hardware upgrade, CPU 100%, AMD EPYC, Intel Xeon, NVMe SSD, datadir migration, MySQL to SSD, rsync MySQL, AppArmor MySQL, symbolic link database, OOM, out of memory, 1062 duplicate entry, 16777215, lookup table, MEDIUMINT limit, cdr_sip_response, cdr_reason, cdr_reason_string_enable, auto-increment limit, normalization, cdr_reason_normalisation, cdr_sip_response_normalisation, cdr_ua_normalisation, TRUNCATE, database error, mysql_enable_set_id, mysql_enable_new_store, central writer, single sensor | | '''Keywords:''' SQLq, SQLf, database delay, CDR delay, quick_save_cdr, query_cache, qoq files, mysqlstore_max_threads_cdr, innodb_buffer_pool_size, error 1062, 16777215, lookup table limit, cdr_reason_string_enable, SUPER privilege, SYSTEM_VARIABLES_ADMIN, unknown column, schema mismatch, disable_partition_operations, timezone, MySQL tuning, SSD migration, hardware upgrade |
|
| |
|
| '''Key Questions:''' | | '''Key Questions:''' |
| * Why are CDRs delayed in the GUI? (Database cannot keep up with insertion rate - check SQLq/SQLf metrics) | | * Why are CDRs not appearing but Active Calls work? (Service not running or database lag) |
| * How do I reduce CDR delay in VoIPmonitor? (Set quick_save_cdr=yes or quick_save_cdr=quick in voipmonitor.conf) | | * What is SQLq/SQLf? (Queue size before CDRs pushed to database) |
| * What are qoq files in VoIPmonitor? (SQL queue files in spool directory buffering database operations) | | * How to reduce CDR delay? (quick_save_cdr=yes or quick) |
| * How do I clear SQL queue backlog? (Stop service, rm -f /var/spool/voipmonitor/qoq*, start service - loses queued CDRs) | | * What are qoq files? (SQL queue files buffering DB operations) |
| * Why is SQL queue growing? (Database cannot keep up - check MySQL performance, increase threads, upgrade hardware)
| | * How to fix error 1062 duplicate entry 16777215? (cdr_reason_string_enable=no, NOT schema migration) |
| * How do I increase database threads? (Set mysqlstore_max_threads_cdr=8 and mysqlstore_max_threads_sip_msg=8 in voipmonitor.conf)
| | * How to fix SUPER privilege error? (GRANT SUPER ON *.* or SYSTEM_VARIABLES_ADMIN) |
| * What causes error 1062 - Duplicate entry '16777215' for key 'PRIMARY'? (Lookup table hitting MEDIUMINT limit due to too many unique SIP response strings)
| | * How to fix unknown column error? (GUI Check MySQL Schema tool, prevent with disable_partition_operations on sensors) |
| * How do I fix error 1062 in cdr_sip_response or cdr_reason tables? (Set cdr_reason_string_enable=no in voipmonitor.conf, restart sniffer)
| | * Why do CDRs disappear after time change? (Timezone mismatch in GUI settings) |
| * How do I stop 1062 errors immediately? (TRUNCATE the affected lookup table to reset auto-increment counter) | | * How to tune MySQL for VoIPmonitor? (innodb_buffer_pool_size=50-70% RAM, innodb_flush_log_at_trx_commit=2) |
| * How do I prevent error 1062 from recurring? (Set cdr_reason_string_enable=no, or enable ALL THREE normalization options)
| | * When is hardware upgrade needed? (CPU at 100% after all tuning optimizations) |
| * Should I migrate lookup table to BIGINT to fix error 1062? (No, the root cause is storing too many unique strings - use configuration fix) | |
| * Why does error 1062 persist after configuration change? (Failed queries remain queued in qoq-* files - clear them) | |
| * How do I migrate MySQL to SSD? (Stop MySQL, rsync data to SSD, update datadir in my.cnf, start MySQL) | |
| * When should I upgrade database hardware? (When CPU is consistently at 100% after all tuning optimizations) | |
| * What is mysql_enable_set_id limitation? (Limits setup to single sensor writing to database - do not use with multiple sensors)
| |
| * How do I optimize MySQL for VoIPmonitor? (Set innodb_buffer_pool_size=50-70% RAM, innodb_flush_log_at_trx_commit=2)
| |
This page covers VoIPmonitor database troubleshooting: SQL queue issues, CDR delays, MySQL tuning, and database errors.
Service Not Running
If Active Calls are visible but CDRs are missing after restart, the sniffer service likely didn't start.
# Check status
systemctl status voipmonitor
# Start if not running
systemctl start voipmonitor
# Enable auto-start on boot
systemctl enable voipmonitor
ℹ️ Note: Active Calls come from sensor memory (real-time), while CDRs require the running service to write to database.
SQL Queue and CDR Delays
Understanding SQLq/SQLf
The SQLq/SQLf values in Settings → Sensors → Status show the queue size before CDRs are pushed to database.
| Metric |
Meaning
|
| Decreasing |
Database catching up, CDRs will appear soon
|
| Stuck/Growing |
Database cannot keep up, needs tuning
|
| Near zero |
All queued CDRs processed
|
Monitor via logs:
journalctl -u voipmonitor -f | grep SQLf
Quick CDR Visibility
Reduce delay between call end and CDR appearance in /etc/voipmonitor.conf:
| Setting |
Delay |
Impact
|
quick_save_cdr = no |
10s (default) |
Lowest load
|
quick_save_cdr = yes |
3s |
Moderate CPU/IO increase
|
quick_save_cdr = quick |
1s |
High CPU/IO increase
|
Disk-Based Query Queue (OOM Prevention)
# /etc/voipmonitor.conf - KEEP THIS ENABLED
query_cache = yes
⚠️ Warning: Never set query_cache = no — if database becomes unreachable and memory fills, OOM killer terminates VoIPmonitor and all queued CDRs are lost.
qoq* Files Backlog
When database lags, SQL queries buffer to qoq* files in /var/spool/voipmonitor.
Solution 1 (Preferred): Wait for automatic processing — monitor SQLf decreasing.
Solution 2 (Emergency): Delete backlog (loses queued CDRs):
systemctl stop voipmonitor
rm -f /var/spool/voipmonitor/qoq*
systemctl start voipmonitor
Increasing Database Threads
# /etc/voipmonitor.conf
mysqlstore_max_threads_cdr = 8
mysqlstore_max_threads_sip_msg = 8
ℹ️ Note: Auto-scaling: When queue exceeds 1,000 items, threads automatically increase up to 99. However, if database waits for storage I/O, more threads won't help.
⚠️ Warning: mysql_enable_set_id = yes limits setup to single sensor writing to database. Do not use with multiple sensors.
Timezone Issues
If CDRs stop appearing after time change but Active Calls work:
1. Check Settings → Sensors → Status: If SQLq/SQLf NOT growing and "last CDR stored" is current, it's a timezone issue
2. Verify Settings → System Configuration → National:
* Timezone = GUI host timezone (for reports/alerts)
* Sensors Timezone = CDR timestamp display timezone
Override in sensor config:
# /etc/voipmonitor.conf
timezone = /usr/share/zoneinfo/Europe/London
# OR for multi-timezone deployments:
utc = yes
MySQL/MariaDB Tuning
Essential Configuration
# /etc/mysql/my.cnf or /etc/mysql/mariadb.conf.d/50-server.cnf
[mysqld]
# 50-70% of RAM on dedicated DB server, 30-50% if shared with VoIPmonitor
innodb_buffer_pool_size = 8G
# Faster writes (may lose up to 1s of data on crash)
innodb_flush_log_at_trx_commit = 2
# Disable slow query log if causing high memory (>90%)
slow_query_log = 0
Restart services:
systemctl restart mysql && systemctl restart voipmonitor
For detailed tuning, see Scaling - MySQL Configuration.
Hardware Upgrade Signs
If after all tuning optimizations:
- CPU consistently at 100%
- SQLq keeps growing
- Large delay between "Last CDR in queue" and "Last CDR in database"
→ Hardware upgrade required (modern CPU, NVMe SSD, more RAM). See Hardware for sizing.
MySQL Data Migration to SSD
# 1. Stop MySQL
systemctl stop mysql
# 2. Copy data (preserves permissions)
rsync -avx /var/lib/mysql/ /mnt/fast_storage/mysql/
# 3. Update /etc/mysql/my.cnf
# datadir = /mnt/fast_storage/mysql
# 4. Update AppArmor if applicable (Ubuntu/Debian)
# 5. Start MySQL
systemctl start mysql
ℹ️ Note: No CDR loss — VoIPmonitor queues CDRs during MySQL downtime.
Long-Running Queries Blocking Operations
If long-running dashboard queries (GROUP BY aggregations on millions of CDR rows) are blocking partition maintenance operations (creation/dropping of partitions):
⚠️ Warning: AuroraDB does not support the MySQL KILL command correctly and is not officially supported. Consider migrating to standard MySQL or MariaDB for production deployments.
Solution Steps
1. Implement query timeout via PHP script
Create a PHP script to automatically kill queries running longer than 3600 seconds (1 hour):
# Example script: add to cron to run periodically
# Queries running > 3600 seconds will be terminated to prevent lock issues
2. Check network latency between GUI and database server
High latency can exacerbate query blocking issues. Ensure minimal network delay.
3. Set MySQL max_execution_time
Add to MySQL/MariaDB configuration:
# /etc/mysql/my.cnf or /etc/my.cnf.d/server.cnf
[mysqld]
max_execution_time = 3600000 # 1 hour in milliseconds
4. Force internal MySQL grouping (fallback)
If performance issues persist:
# Delete charts binaries to force internal MySQL grouping
rm -f /usr/local/sbin/charts*
systemctl restart voipmonitor
Database Errors
Error 1062 - Lookup Table Limit (16777215)
Symptom: 1062 - Duplicate entry '16777215' for key 'PRIMARY' on lookup tables (cdr_sip_response, cdr_reason).
Cause: MEDIUMINT limit reached due to too many unique SIP response strings.
Fix (choose one):
| Option |
Configuration |
Notes
|
| Disable storage |
cdr_reason_string_enable = no |
Stops creating new entries
|
| Enable normalization |
cdr_reason_normalisation = yes
cdr_sip_response_normalisation = yes
cdr_ua_normalisation = yes |
Reduces unique entries
|
| Immediate fix |
TRUNCATE TABLE cdr_reason; |
Resets counter, loses lookup data
|
After config change, clear queued failed queries:
systemctl stop voipmonitor
rm -f /var/spool/voipmonitor/qoq-*
systemctl start voipmonitor
⚠️ Warning: This is NOT a schema issue — do not migrate to BIGINT. Different from main cdr table overflow (see Upgrade_to_bigint).
SUPER Privilege Error
Symptom: ERROR 1227 (42000): Access denied; you need SUPER privilege(s)
Fix:
-- MySQL 5.7 / MariaDB
GRANT SUPER ON *.* TO 'voipmonitor_user'@'%';
-- MySQL 8.0+
GRANT SYSTEM_VARIABLES_ADMIN ON *.* TO 'voipmonitor_user'@'%';
FLUSH PRIVILEGES;
ℹ️ Note: SUPER is a global privilege — database-specific grants (ALL ON voipmonitor.*) do NOT include it.
Unknown Column Error (Schema Mismatch)
Symptom: Unknown column 'from_time' in 'field list', qoq files accumulating.
Cause: Sensor version newer than database schema.
Fix:
- GUI → Tools → System Status → Check MySQL Schema → Start Upgrade
- If unavailable: backup with
mysqldump, then recreate table (see Recovering_corrupted_database_tables)
Prevention (distributed setups):
# On ALL sensors (not central server):
disable_partition_operations = yes
Automatic Schema Upgrades and Production Safety
VoIPmonitor includes a built-in safety mechanism to prevent unexpected database schema modifications on production databases.
Safety Threshold: Automatic schema modifications (ALTER TABLE) only occur if the database contains fewer than 1000 CDRs.
| Database Size |
Behavior
|
| < 1000 CDRs |
Automatic schema upgrades applied on sniffer startup
|
| > 1000 CDRs' |
ALTER queries logged to syslog/messages/journalctl - manual execution required
|
For production databases (>1000 CDRs), when a new sniffer version detects required schema changes:
- Review logged ALTER queries:
journalctl -u voipmonitor | grep ALTER or grep ALTER /var/log/syslog
- Execute manually during low-traffic period (e.g., overnight) to prevent table locking
- Restart sniffer after schema changes complete
⚠️ Warning: Never rely on disable_dbupgradecheck for production safety - it's unnecessary because the 1000 CDR threshold already protects large databases from automatic modifications.
Template:See Also
Row Size Too Large (cdr_stat_values)
Symptom: Calls don't appear in GUI until service restart, "Row size too large" errors.
Fix (destructive):
systemctl stop voipmonitor
# Save structure for analysis
mysqldump -u root -p -d voipmonitor cdr_stat_values > cdr_stat_backup.sql
# Recreate database
mysql -u root -p -e "DROP DATABASE voipmonitor; CREATE DATABASE voipmonitor;"
systemctl start voipmonitor
⚠️ Warning: This deletes all CDR data. Only use if data loss is acceptable.
See Also
AI Summary for RAG
Summary: VoIPmonitor database troubleshooting guide. SERVICE: If Active Calls visible but CDRs missing after restart, start voipmonitor service. SQL QUEUE: SQLq/SQLf in Settings→Sensors→Status shows DB queue size. Growing = DB cannot keep up. QUICK CDR: quick_save_cdr=yes (3s) or quick (1s) reduces CDR delay. QOQ FILES: SQL buffered to qoq* files in /var/spool/voipmonitor when DB lags. Emergency clear: rm qoq* (loses data). THREADS: mysqlstore_max_threads_cdr=8, auto-scales to 99 when queue>1000. mysql_enable_set_id=yes limits to single sensor. MYSQL TUNING: innodb_buffer_pool_size=50-70% RAM, innodb_flush_log_at_trx_commit=2. ERROR 1062: Lookup table (cdr_sip_response/cdr_reason) hit MEDIUMINT 16777215 limit. Fix: cdr_reason_string_enable=no or enable normalization. NOT a schema issue. SUPER PRIVILEGE: GRANT SUPER ON *.* (MySQL 5.7) or SYSTEM_VARIABLES_ADMIN (MySQL 8.0+). SCHEMA MISMATCH: Unknown column error = sensor newer than DB schema. Fix via GUI Check MySQL Schema tool. TIMEZONE: If CDRs disappear after time change, check Settings→System Configuration→National timezone settings.
Keywords: SQLq, SQLf, database delay, CDR delay, quick_save_cdr, query_cache, qoq files, mysqlstore_max_threads_cdr, innodb_buffer_pool_size, error 1062, 16777215, lookup table limit, cdr_reason_string_enable, SUPER privilege, SYSTEM_VARIABLES_ADMIN, unknown column, schema mismatch, disable_partition_operations, timezone, MySQL tuning, SSD migration, hardware upgrade
Key Questions:
- Why are CDRs not appearing but Active Calls work? (Service not running or database lag)
- What is SQLq/SQLf? (Queue size before CDRs pushed to database)
- How to reduce CDR delay? (quick_save_cdr=yes or quick)
- What are qoq files? (SQL queue files buffering DB operations)
- How to fix error 1062 duplicate entry 16777215? (cdr_reason_string_enable=no, NOT schema migration)
- How to fix SUPER privilege error? (GRANT SUPER ON *.* or SYSTEM_VARIABLES_ADMIN)
- How to fix unknown column error? (GUI Check MySQL Schema tool, prevent with disable_partition_operations on sensors)
- Why do CDRs disappear after time change? (Timezone mismatch in GUI settings)
- How to tune MySQL for VoIPmonitor? (innodb_buffer_pool_size=50-70% RAM, innodb_flush_log_at_trx_commit=2)
- When is hardware upgrade needed? (CPU at 100% after all tuning optimizations)