Skip to main content
discount · azure

Always-on Azure VMs with 60+ days of steady use and no reservation or savings plan

resource types
1
rule IDs covered
1
severity
low

What does ZopNight detect here?

ZopNight flags a running Azure VM that is production-named or tagged, or has simply never been stopped, when it has at least 60 days of history, at least 70% uptime and average `Percentage CPU` of 30% or more, yet no reservation or savings plan covers it. A 1-year Reserved VM Instance for that size and region is the suggested fix.

Signal and threshold

How ZopNight evaluates Always-on Azure VMs with 60+ days of steady use and no reservation or savings plan.
Field Value
Rule IDsRC-211
Categorydiscount
Severitylow
MetricPercentage CPU
Threshold60+ days history, 70%+ uptime, 30%+ average CPU
SourceZopNight
Permissions usedMicrosoft.Compute/virtualMachines/read · Microsoft.Insights/Metrics/Read · Microsoft.Capacity/reservationorders/read

How a Reserved VM Instance discounts a running VM

A Reserved VM Instance is a one- or three-year commitment to a VM size in a region. You do not attach it to a VM: the discount lands automatically on running VMs that match the reservation’s scope and attributes, and with instance size flexibility (on by default) it can spread across sizes in the same size group. It covers compute only. For Windows VMs the license part of the meter is billed separately and is not included.

The catch is that a reservation is use-it-or-lose-it: any hour without a matching running VM is lost and cannot be carried forward. That is why the candidates worth reserving are the VMs that are on nearly all the time.

Listing running VMs to size a reservation

Terminal window
az vm list -d \
--query "[?powerState=='VM running'].{name:name, rg:resourceGroup, size:hardwareProfile.vmSize, location:location}" \
-o table

Group by size and region. Microsoft advises checking daily usage in the usage file, and using the AdditionalInfo field rather than meter names to read the true VM size.

Evidence a VM must show

  1. The VM is running.
  2. No reservation or savings plan already covers it, and it has no reserved=true tag.
  3. It is not a Databricks-managed VM and not a member of a scale set.
  4. Either a production signal (a prod, production, prd or live name, or a production environment tag), or a record of running continuously: no stop events and a name that does not look like dev or test.
  5. At least 60 days of cost history, at least 70% measured uptime, and a measured utilization signal, in practice average CPU, of at least 30%. A VM below that level is treated as a rightsizing candidate first, not as a commitment.

When ZopNight holds back

Missing history, unknown uptime or no CPU data all mean no finding; the check fails closed because the downside of a wrong answer is a year of billing. If the break-even comparison shows the reservation costing as much as or more than the VM costs now, ZopNight stays silent too.

Break-even saving on measured hours

Terminal window
current month = what the VM is billed now, for the hours it actually ran
reserved month = 1-year reserved hourly rate x 730
saving = current month - reserved month

Because the current cost already reflects the hours the VM ran, a VM that is off part of the month is not credited with a full-time discount. The 1-year term is the smaller commitment; a 3-year term is priced lower again. Without those rates, ZopNight falls back to the current cost times a discount derived from the rate tiers, provided uptime is still high enough.

Buying and checking the reservation

  1. Confirm the VM will run at this size for at least 12 months.
  2. In the portal, open Reservations, select Add and Virtual machine, and pick the size, region, scope and 1-year term.
  3. Leave instance size flexibility on unless you need the discount pinned to one size.
  4. A few days later, check utilization under Reservations; the az consumption reservation summary list --grain daily --reservation-order-id <id> command returns the same data.

See it fire on your bill.

Connect an account read-only. The first findings land in minutes.

472 rule families across 353 resource types on 22 platforms. Every threshold, metric, and IAM action is documented on these pages before you grant anything.

472 rule families documented
353 resource types covered
read-only default access level
Multi-cloud automation· Production-ready in 30 min· SOC 2 · ISO 27001· 20–60% off the bill, first month· 4 platforms · 1 console· Multi-cloud automation· Production-ready in 30 min· SOC 2 · ISO 27001· 20–60% off the bill, first month· 4 platforms · 1 console·