# Path: quads/helpers.py
# def date_span(start, end, delta=timedelta(days=1)):
#     current = start
#     while current < end:
#         yield current
#         current += delta
# 
# def first_day_month(date):
#     return date - timedelta(days=date.day - 1)
# 
# def last_day_month(date):
#     next_month = date.replace(day=28) + timedelta(days=4)
#     return next_month - timedelta(days=next_month.day)
# 
# def month_delta_past(date, months):
#     years = months // 12
#     year = date.year - years
#     month_delta = months % 12
#     if not month_delta:
#         return date.replace(year=year)
#     if month_delta > date.month:
#         year -= 1
#         month = 12 - month_delta
#         day = min(date.day, calendar.monthrange(year, month)[1])
#         return date.replace(year=year, month=month, day=day)
#     else:
#         month = date.month - month_delta
#         if month:
#             day = min(date.day, calendar.monthrange(year, month)[1])
#             return date.replace(year=year, month=month, day=day)
#         return date.replace(year=year)
# 
# def date_to_object_id(date):
#     """
#     Create a dummy ObjectId instance with a specific datetime.
# 
#     This method is useful for doing range queries by oid creation date.
# 
#     .. _warning:
#            It is not safe to insert a document containing an ObjectId
#            generated using this method. This method deliberately
#            eliminates the uniqueness guarantee that ObjectIds
#            generally provide. ObjectIds generated with this method
#            should be used exclusively in queries.
#     """
#     timestamp = calendar.timegm(date.timetuple())
#     oid = struct.pack(">I", int(timestamp)) + b"\x00\x00\x00\x00\x00\x00\x00\x00"
#     return ObjectId(oid)
# 
# Path: quads/model.py
# class Vlan(Document):
# class CloudHistory(Document):
# class Cloud(Document):
# class Notification(Document):
# class Disk(EmbeddedDocument):
# class Interface(EmbeddedDocument):
# class Host(Document):
# class Counters(Document):
# class Schedule(Document):
#     def prep_data(data):
#     def prep_data(data):
#     def prep_data(data, fields=None, mod=False):
#     def prep_data(data):
#     def prep_data(data, fields=None):
#     def prep_data(data, fields=None):
#     def prep_data(data):
#     def get_next_sequence(name):
#     def insert_schedule(self, cloud, host, start, end):
#     def is_host_available(self, queryset, host, start, end, exclude=None):
#     def future_schedules(self, queryset, host=None, cloud=None):
#     def current_schedule(self, queryset, date=None, host=None, cloud=None):


import logging
import sys
from quads.helpers import (
    date_span,
    first_day_month,
    last_day_month,
    month_delta_past,
    date_to_object_id,
)
from quads.model import Schedule, Host, CloudHistory, Cloud, Q
from datetime import datetime, timedelta

    now = datetime.now()
    now = now.replace(year=year, hour=22, minute=0, second=0)
    if months:
        for month in range(months):
            process_scheduled(_logger, month, now)
    else:
        process_scheduled(_logger, months, now)


def process_scheduled(_logger, month, now):
    _date = now
    if month > 0:
        _date = month_delta_past(now, month)
    start = first_day_month(_date)
    start_id = date_to_object_id(start)
    end = last_day_month(_date)
    end_id = date_to_object_id(end)
    scheduled = (
        CloudHistory.objects(
            __raw__={
                "_id": {
                    "$lt": end_id,
                    "$gt": start_id,
                },
            }
        )
        .order_by("-_id")
        .count()
    )

# Path: quads/helpers.py
# def date_span(start, end, delta=timedelta(days=1)):
#     current = start
#     while current < end:
#         yield current
#         current += delta
# 
# def first_day_month(date):
#     return date - timedelta(days=date.day - 1)
# 
# def last_day_month(date):
#     next_month = date.replace(day=28) + timedelta(days=4)
#     return next_month - timedelta(days=next_month.day)
# 
# def month_delta_past(date, months):
#     years = months // 12
#     year = date.year - years
#     month_delta = months % 12
#     if not month_delta:
#         return date.replace(year=year)
#     if month_delta > date.month:
#         year -= 1
#         month = 12 - month_delta
#         day = min(date.day, calendar.monthrange(year, month)[1])
#         return date.replace(year=year, month=month, day=day)
#     else:
#         month = date.month - month_delta
#         if month:
#             day = min(date.day, calendar.monthrange(year, month)[1])
#             return date.replace(year=year, month=month, day=day)
#         return date.replace(year=year)
# 
# def date_to_object_id(date):
#     """
#     Create a dummy ObjectId instance with a specific datetime.
# 
#     This method is useful for doing range queries by oid creation date.
# 
#     .. _warning:
#            It is not safe to insert a document containing an ObjectId
#            generated using this method. This method deliberately
#            eliminates the uniqueness guarantee that ObjectIds
#            generally provide. ObjectIds generated with this method
#            should be used exclusively in queries.
#     """
#     timestamp = calendar.timegm(date.timetuple())
#     oid = struct.pack(">I", int(timestamp)) + b"\x00\x00\x00\x00\x00\x00\x00\x00"
#     return ObjectId(oid)
# 
# Path: quads/model.py
# class Vlan(Document):
# class CloudHistory(Document):
# class Cloud(Document):
# class Notification(Document):
# class Disk(EmbeddedDocument):
# class Interface(EmbeddedDocument):
# class Host(Document):
# class Counters(Document):
# class Schedule(Document):
#     def prep_data(data):
#     def prep_data(data):
#     def prep_data(data, fields=None, mod=False):
#     def prep_data(data):
#     def prep_data(data, fields=None):
#     def prep_data(data, fields=None):
#     def prep_data(data):
#     def get_next_sequence(name):
#     def insert_schedule(self, cloud, host, start, end):
#     def is_host_available(self, queryset, host, start, end, exclude=None):
#     def future_schedules(self, queryset, host=None, cloud=None):
#     def current_schedule(self, queryset, date=None, host=None, cloud=None):


# Path: quads/tools/reports.py
import logging
import sys
from quads.helpers import (
    date_span,
    first_day_month,
    last_day_month,
    month_delta_past,
    date_to_object_id,
)
from quads.model import Schedule, Host, CloudHistory, Cloud, Q
from datetime import datetime, timedelta


    now = datetime.now()
    now = now.replace(year=year, hour=22, minute=0, second=0)
    if months:
        for month in range(months):
            process_scheduled(_logger, month, now)
    else:
        process_scheduled(_logger, months, now)


def process_scheduled(_logger, month, now):
    _date = now
    if month > 0:
        _date = month_delta_past(now, month)
    start = first_day_month(_date)
    start_id = date_to_object_id(start)
    end = last_day_month(_date)
    end_id = date_to_object_id(end)
    scheduled = (
        CloudHistory.objects(
            __raw__={
                "_id": {
                    "$lt": end_id,
                    "$gt": start_id,
                },
            }
        )
        .order_by("-_id")
        .count()
    )

    hosts = Host.objects(