Skip to content

Account Budget Documentation

Overview

The Account Budget model (account.budget) provides budget planning and tracking functionality. It allows organizations to define budgets for specific time periods with line items for different accounts, enabling comparison of budgeted vs actual amounts.


Model Information

Model Name: account.budget Display Name: Budget Key Fields: name (unique budget name)

Features

  • ❌ Audit logging enabled (_audit_log)
  • ❌ Multi-company support (company_id)
  • ❌ Full-text content search (_content_search)
  • ✅ Unique key constraint on name
  • ✅ Line item support for detailed budgeting
  • ✅ Date range for budget period

Key Fields Reference

All Fields

Field Type Required Description
name Char Budget name (unique identifier)
date_from Date Budget period start date
date_to Date Budget period end date
lines One2Many Budget line items

Unique Key Constraint

_key = ["name"]

The budget name must be unique across all budgets in the system.


Default Ordering

Records are ordered alphabetically by name:

_order = "name"

API Methods

1. Create Budget

Method: create(vals, context)

Creates a new budget record.

Parameters:

vals = {
    "name": "2024 Operating Budget",    # Required: Unique name
    "date_from": "2024-01-01",          # Optional: Start date
    "date_to": "2024-12-31",            # Optional: End date
    "lines": [                          # Optional: Budget lines
        ("create", {
            "account_id": account_id,
            "budget_amount": 50000.00,
        })
    ]
}

Returns: int - New record ID

Example:

budget_id = get_model("account.budget").create({
    "name": "Q1 2024 Marketing Budget",
    "date_from": "2024-01-01",
    "date_to": "2024-03-31",
    "lines": [
        ("create", {
            "account_id": advertising_account_id,
            "budget_amount": 25000.00,
        }),
        ("create", {
            "account_id": events_account_id,
            "budget_amount": 15000.00,
        }),
        ("create", {
            "account_id": pr_account_id,
            "budget_amount": 10000.00,
        })
    ]
})


2. Search Budgets

Method: search(condition, context)

Search for budget records.

Example:

# Find all budgets
all_budgets = get_model("account.budget").search([])

# Find budget by name
budget_ids = get_model("account.budget").search([["name", "=", "2024 Operating Budget"]])

# Find budgets for a period
budget_ids = get_model("account.budget").search([
    ["date_from", ">=", "2024-01-01"],
    ["date_to", "<=", "2024-12-31"]
])


3. Browse Budgets

Method: browse(ids, context)

Retrieve budget records for reading.

Example:

budgets = get_model("account.budget").browse(budget_ids)
for budget in budgets:
    print(f"Budget: {budget.name}")
    print(f"Period: {budget.date_from} to {budget.date_to}")
    print("Lines:")
    for line in budget.lines:
        print(f"  {line.account_id.name}: {line.budget_amount}")


4. Update Budget

Method: write(ids, vals, context)

Update existing budget records.

Example:

# Update budget period
get_model("account.budget").write([budget_id], {
    "date_to": "2024-06-30"  # Extend budget period
})

# Add new line
get_model("account.budget").write([budget_id], {
    "lines": [
        ("create", {
            "account_id": new_account_id,
            "budget_amount": 5000.00,
        })
    ]
})


5. Delete Budget

Method: delete(ids, context)

Delete budget records (also deletes associated lines due to cascade).

Example:

get_model("account.budget").delete([budget_id])


Model Relationship Description
account.budget.line One2Many (lines) Budget line items with account allocations

Common Use Cases

Use Case 1: Create Annual Department Budget

# Create annual budget for IT department
it_budget_id = get_model("account.budget").create({
    "name": "2024 IT Department Budget",
    "date_from": "2024-01-01",
    "date_to": "2024-12-31",
    "lines": [
        ("create", {
            "account_id": software_licenses_id,
            "budget_amount": 50000.00,
        }),
        ("create", {
            "account_id": hardware_id,
            "budget_amount": 75000.00,
        }),
        ("create", {
            "account_id": cloud_services_id,
            "budget_amount": 120000.00,
        }),
        ("create", {
            "account_id": training_id,
            "budget_amount": 15000.00,
        }),
    ]
})

Use Case 2: Create Quarterly Budgets

# Create quarterly budgets
quarters = [
    ("Q1 2024", "2024-01-01", "2024-03-31"),
    ("Q2 2024", "2024-04-01", "2024-06-30"),
    ("Q3 2024", "2024-07-01", "2024-09-30"),
    ("Q4 2024", "2024-10-01", "2024-12-31"),
]

for name, start, end in quarters:
    get_model("account.budget").create({
        "name": f"Sales {name}",
        "date_from": start,
        "date_to": end,
        "lines": [
            ("create", {"account_id": sales_expense_id, "budget_amount": 25000.00}),
            ("create", {"account_id": travel_id, "budget_amount": 10000.00}),
        ]
    })

Use Case 3: Budget Summary Report

# Get budget summary with actuals
budget = get_model("account.budget").browse([budget_id])[0]

print(f"Budget: {budget.name}")
print(f"Period: {budget.date_from} to {budget.date_to}")
print("-" * 60)

total_budget = 0
total_actual = 0
total_variance = 0

for line in budget.lines:
    total_budget += line.budget_amount or 0
    total_actual += line.actual_amount or 0
    total_variance += line.variance or 0

    status = "Over" if line.variance > 0 else "Under"
    print(f"{line.account_id.name}:")
    print(f"  Budget: {line.budget_amount:,.2f}")
    print(f"  Actual: {line.actual_amount:,.2f}")
    print(f"  Variance: {line.variance:,.2f} ({status})")

print("-" * 60)
print(f"Total Budget: {total_budget:,.2f}")
print(f"Total Actual: {total_actual:,.2f}")
print(f"Total Variance: {total_variance:,.2f}")

Use Case 4: Copy Budget to New Period

# Copy existing budget to new period
source = get_model("account.budget").browse([source_budget_id])[0]

# Create new budget with same structure
new_budget_id = get_model("account.budget").create({
    "name": source.name.replace("2024", "2025"),
    "date_from": "2025-01-01",
    "date_to": "2025-12-31",
    "lines": [
        ("create", {
            "account_id": line.account_id.id,
            "track_id": line.track_id.id if line.track_id else None,
            "contact_id": line.contact_id.id if line.contact_id else None,
            "budget_amount": line.budget_amount * 1.05,  # 5% increase
        })
        for line in source.lines
    ]
})

Best Practices

1. Use Meaningful Names

# Good: Descriptive and unique
budget = get_model("account.budget").create({
    "name": "2024 Q1 Marketing - Digital Campaigns",
})

# Bad: Generic name
budget = get_model("account.budget").create({
    "name": "Budget 1",
})

2. Always Set Date Ranges

# Good: Clear period definition
budget = get_model("account.budget").create({
    "name": "Annual Budget 2024",
    "date_from": "2024-01-01",
    "date_to": "2024-12-31",
})

# Bad: No dates (actuals won't calculate correctly)
budget = get_model("account.budget").create({
    "name": "Annual Budget",
})

3. Break Down Large Budgets

# Good: Separate budgets for tracking
budgets = [
    "2024 Operations Budget",
    "2024 Marketing Budget",
    "2024 IT Budget",
    "2024 HR Budget",
]

# Each department can manage and track their own budget

Troubleshooting

"Key already exists: name"

Cause: Creating budget with a name that already exists Solution: Use a unique name or update the existing budget

"Actual amounts not calculating"

Cause: Budget date range not set Solution: Set date_from and date_to for proper actual calculation

"Budget lines not showing"

Cause: No lines added to budget Solution: Add budget lines with account allocations


Testing Examples

Unit Test: Create and Query Budget

def test_budget_creation():
    # Create budget
    budget_id = get_model("account.budget").create({
        "name": "Test Budget 2024",
        "date_from": "2024-01-01",
        "date_to": "2024-12-31",
        "lines": [
            ("create", {
                "account_id": test_account_id,
                "budget_amount": 10000.00,
            })
        ]
    })

    # Verify
    budget = get_model("account.budget").browse([budget_id])[0]
    assert budget.name == "Test Budget 2024"
    assert len(budget.lines) == 1
    assert budget.lines[0].budget_amount == 10000.00

    # Cleanup
    get_model("account.budget").delete([budget_id])

Security Considerations

Permission Model

  • Typically restricted to finance/management
  • View access may be granted to department heads

Data Access

  • Budget data is sensitive financial information
  • Consider role-based access for different budget categories

Version History

Last Updated: December 2024 Model Version: account_budget.py Framework: Netforce


Additional Resources

  • Budget Line Documentation: account.budget.line
  • Account Documentation: account.account
  • Tracking Category Documentation: account.track.categ

This documentation is generated for developer onboarding and reference purposes.