OpenStack Icehouse Reset Incorrect Quota Count for Nova

Page content

Sometimes when VM is deleted in not-so-correct way quota counters displayed in Dashboard => Project => Overview may not update correctly as well.

You may see that number of VMs/vcpus/RAM for tenant displayed on this page does not match actual values. For example it may display “Instances used 8 of 10” while you have only 5 VMs in this tenant.

The problem is that there is no easy way to reset these counters. You can assign -1 to the particular counter as it’s suggested here and wait until OpenStack recalculates and resets counters. The pitfall is that OpenStack only recalculates counter value when particular user spawns/deletes VM. Counters will display 0 until each user in tenant boots/deletes VM changing -1 to actual values. You should be… ehm… very patient. Or recalculate and assign values manually.

You can use script below, it only works with counters in nova.quota_usages table, namely number of instances, number of vCPUs, total RAM. As I understand previously security group counters were stored in nova database as well, but in Icehouse they are fetched from neutron database. I didn’t dig further because I have never had problems with networking/volume counters.

#!/usr/bin/env bash
set -o pipefail

DBUSER='root' # Assuming there is a correct password for DBUSER in ~/.my.cnf
DBNAME='nova'
DBHOST='localhost'

# Set number of instances, ram, core usage to 0 for all users in all tenants, otherwise end result may not be correct:

mysql -u${DBUSER} -h ${DBHOST} -e "use ${DBNAME}; update quota_usages, (select user_id, project_id from instances group by user_id, project_id) as r set in_use='0' where quota_usages.user_id=r.user_id and quota_usages.project_id=r.project_id and resource='instances';"
mysql -u${DBUSER} -h ${DBHOST} -e "use ${DBNAME}; update quota_usages, (select user_id, project_id from instances group by user_id, project_id) as r set in_use='0' where quota_usages.user_id=r.user_id and quota_usages.project_id=r.project_id and resource='ram';"
mysql -u${DBUSER} -h ${DBHOST} -e "use ${DBNAME}; update quota_usages, (select user_id, project_id from instances group by user_id, project_id) as r set in_use='0' where quota_usages.user_id=r.user_id and quota_usages.project_id=r.project_id and resource='cores';"

# Calculate number of instances for each of users in each tenant and update data in quota_usages table:

mysql -u${DBUSER} -h ${DBHOST} -e "use ${DBNAME}; update quota_usages, (select user_id, project_id, COUNT(*) as sum from instances where project_id in (select project_id from quota_usages group by project_id) and deleted!=id group by user_id, project_id) as r set quota_usages.in_use = r.sum where quota_usages.user_id = r.user_id and quota_usages.project_id = r.project_id and resource='instances';"

mysql -u${DBUSER} -h ${DBHOST} -e "use ${DBNAME}; update quota_usages, (select user_id, project_id, SUM(memory_mb) as sum from instances where project_id in (select project_id from quota_usages group by project_id) and deleted!=id group by user_id, project_id) as r set quota_usages.in_use = r.sum where quota_usages.user_id = r.user_id and quota_usages.project_id = r.project_id and resource='ram';"

mysql -u${DBUSER} -h ${DBHOST} -e "use ${DBNAME}; update quota_usages, (select user_id, project_id, SUM(vcpus) as sum from instances where project_id in (select project_id from quota_usages group by project_id) and deleted!=id group by user_id, project_id) as r set quota_usages.in_use = r.sum where quota_usages.user_id = r.user_id and quota_usages.project_id = r.project_id and resource='cores';"

The script worked for me but it’s a raw SQL and I won’t be very surprised if it accidentally spawns Cthulhu or fucks your girlfriend grinding through a database. Use at your own risk and backup nova database before you start any manipulations.