50% rule operating expense estimate
The 50% rule says about half of a rental's gross rent goes to operating expenses, mortgage excluded: 2,000 a month in rent means roughly 1,000 in expenses and 1,000 left before debt payments. Free in your browser.
- Free
- Runs in your browser
- No sign-up
- Your data stays on your device
Run — free
Worked example
- Monthly rent
- 2,000
- Estimated opex
- 1,000
- Estimated cash before debt
- 1,000
- Opex ratio
- 0.5
Rough rule: operating expenses ≈ 50% of gross rent (excluding mortgage). Search intent: fifty percent rule. No network calls, no random seeds, and no server state are required for a correct answer. Failed jobs are not billed. Landings
What the 50% rule estimates
The 50% rule is a rough rule of thumb for rental property: about half of the gross rent goes to operating expenses, and the mortgage is not part of that half. The calculation is a single step. Multiply the gross monthly rent by 0.5 to get the estimated operating expenses, and the other half is the cash left before debt payments. A unit renting for 2,000 a month therefore shows about 1,000 in operating expenses and 1,000 before the mortgage. Results are rounded once, to the number of decimals you choose.
Mistakes to avoid with the rule
The most common slip is to count the mortgage inside the 50%. The rule leaves it out, so the loan payment has to come out of the remaining half, and the cash before debt is not profit. Another is to start from rent after expenses, while the rule starts from gross rent, the full amount tenants pay. Finally, it is an approximation: use it as a quick first look at a rental and replace it with real expense figures once you have them.
When to use it
Use when the search intent matches this tool. Rough rule: operating expenses ≈ 50% of gross rent (excluding mortgage). No network calls, no random seeds, and no server state are required for a correct answer.
Failed jobs are not billed. Landings target the stated search intent with precise keywords. Prefer explicit units and ranges over silent coercion of bad types.
When a field is optional, defaults are documented in params and echoed in the output. This keeps
FAQ
Locales?
EN-only delivery; Nitro hydrates the other seven languages.
Does the 50% include the mortgage payment?
No. The rule leaves the mortgage out of operating expenses, so the loan payment has to come out of the other half of the rent, the part left before debt payments.
What is the cash before debt figure?
It is the gross rent minus the estimated operating expenses. With 2,000 of monthly rent, 1,000 remains, and the mortgage still has to be paid from that amount.
Should I enter gross rent or net rent?
Gross rent: the full monthly rent tenants pay, before any expense is taken off. If you enter a figure that is already net, the rule would subtract expenses twice.
Is the 50% rule accurate for every property?
It is an approximation, not a budget. Use it for a quick first look at a rental and replace it with real expense figures as soon as you have them.
Related tools
For developers — API access
Everything on this page is available programmatically. This section is for teams who want to wire it into their own systems; everyone else can just use the tool above.
API endpoint
Prefer to automate it? One authenticated POST creates the task; the result comes back by webhook or a signed link. The same capability also runs here on the web, by email and from Telegram — and soon from our app too.
Call it from your stack
curl -X POST https://api.kit.forhosting.com/finance/fifty-percent-rule \
-H "Authorization: Bearer $KIT_KEY" \
-H "Content-Type: application/json" \
-d '{"monthly_rent":2000}'const res = await fetch("https://api.kit.forhosting.com/finance/fifty-percent-rule", {
method: "POST",
headers: {
"Authorization": `Bearer ${process.env.KIT_KEY}`,
"Content-Type": "application/json"
},
body: JSON.stringify({
"monthly_rent": 2000
})
});
const { task_id } = await res.json();import os, requests
res = requests.post(
"https://api.kit.forhosting.com/finance/fifty-percent-rule",
headers={"Authorization": f"Bearer {os.environ['KIT_KEY']}"},
json={
"monthly_rent": 2000
},
)
task_id = res.json()["task_id"]<?php
$res = file_get_contents("https://api.kit.forhosting.com/finance/fifty-percent-rule", false, stream_context_create([
"http" => [
"method" => "POST",
"header" => "Authorization: Bearer " . getenv("KIT_KEY") . "\r\nContent-Type: application/json",
"content" => '{"monthly_rent":2000}',
],
]));
$task = json_decode($res, true);body := bytes.NewBufferString(`{"monthly_rent":2000}`)
req, _ := http.NewRequest("POST", "https://api.kit.forhosting.com/finance/fifty-percent-rule", body)
req.Header.Set("Authorization", "Bearer "+os.Getenv("KIT_KEY"))
req.Header.Set("Content-Type", "application/json")
res, _ := http.DefaultClient.Do(req)Example request
{
"monthly_rent": 2000
}Example response
{
"task_id": "tsk_a1b2c3d4e5f6a1b2c3d4e5f6",
"type": "finance.fifty_percent_rule",
"status": "queued",
"_links": {
"result": "/tasks/tsk_…/result"
}
}The API is asynchronous: the call returns a task_id immediately and the result arrives by webhook. Polling is capped at 1 req/s per task.
Pricing
Published price — no tokens, no invented credits. A failed task is never charged.
Errors
| HTTP | Code | Meaning |
|---|---|---|
401 | unauthorized | Missing or invalid API key. |
402 | insufficient_balance | Your balance doesn't cover the task price. |
404 | unknown_type | That task type doesn't exist. |
429 | rate_limited | Too many requests. Use the webhook instead of polling. |
Technical notes
The calculator is free in the browser, deterministic, and identical in the API path. Inputs are validated before any arithmetic so invalid payloads fail with invalid_input. Half-up rounding is applied once from raw IEEE results when decimals are requested. Use the same JSON contract from spreadsheets, CMS hooks, automation, or teaching demos.
How it works
No network calls, no random seeds, and no server state are required for a correct answer. Failed jobs are not billed. Landings target the stated search intent with precise keywords. Prefer explicit units and ranges over silent coercion of bad types. When a field is optional, defaults are documented in params and echoed in the output. Rough rule: operating expenses ≈ 50% of gross rent (excluding mortgage). opex = 0.5 × monthly_rent. The calculator is free in the browser, deterministic, and identical in the API path. Inputs are validated before any arithmetic so invalid payloads fail with invalid_input. Half-up rounding is applied once from raw IEEE results when decimals are requested. Use the same JSON contract from spreadsheets, CMS hooks, automation, or teaching demos.
Inputs, limits and rounding
Outputs echo inputs for logging. No network calls, no random seeds, and no server state are required for a correct answer. Failed jobs are not billed. Landings target the stated search intent with precise keywords. Prefer explicit units and ranges over silent coercion of bad types. When a field is optional, defaults are documented in params and echoed in the output. Provide required JSON fields. Optional decimals use half-up once from raw IEEE values. Invalid types or ranges raise invalid_input. The calculator is free in the browser, deterministic, and identical in the API path. Inputs are validated before any arithmetic so invalid payloads fail with invalid_input. Half-up rounding is applied once from raw IEEE results when decimals are requested. Use the same JSON contract from spreadsheets, CMS hooks, automation, or teaching demos.
When to use it
The calculator is free in the browser, deterministic, and identical in the API path. Inputs are validated before any arithmetic so invalid payloads fail with invalid_input. Half-up rounding is applied once from raw IEEE results when decimals are requested. Use the same JSON contract from spreadsheets, CMS hooks, automation, or teaching demos.
Integration use cases
Quick check
Use the free widget to verify a formula before production.
Automation
Call the API with the same JSON contract from scripts or CMS.
Teaching
Show pinned golden examples without proprietary software.
Technical questions
Is the browser widget free?
Yes. Tier A is free client-side with the same core as the API.
Does it use the network?
No. Computation is local and deterministic.
What on bad input?
invalid_input is thrown; failed jobs are not billed.
API compatible?
Yes — same JSON fields as params.json.