def createExpenseItemsForVenueRental(request=None, datetimeTuple=None, rule=None, event=None):
<EOL>submissionUser = getattr(request, '<STR_LIT:user>', None)<EOL>rental_category = getConstant('<STR_LIT>')<EOL>generate_count = <NUM_LIT:0><EOL>rule_filters = Q(disabled=False) & Q(rentalRate__gt=<NUM_LIT:0>) &(Q(locationrentalinfo__isnull=False) | Q(roomrentalinfo__isnull=False))<EOL>if rule:<EOL><INDENT>rule_filters = rule_filters & Q(id=rule.id)<EOL><DEDENT>rulesToCheck = RepeatedExpenseRule.objects.filter(rule_filters).distinct()<EOL>event_timefilters = Q()<EOL>if datetimeTuple and len(datetimeTuple) == <NUM_LIT:2>:<EOL><INDENT>timelist = list(datetimeTuple)<EOL>timelist.sort()<EOL>event_timefilters = event_timefilters & (<EOL>Q(startTime__gte=timelist[<NUM_LIT:0>]) & Q(startTime__lte=timelist[<NUM_LIT:1>])<EOL>)<EOL><DEDENT>if event:<EOL><INDENT>event_timefilters = event_timefilters & Q(id=event.id)<EOL><DEDENT>for rule in rulesToCheck:<EOL><INDENT>venue = (<EOL>getattr(rule, '<STR_LIT:location>', None) if<EOL>isinstance(rule, RoomRentalInfo) else<EOL>getattr(rule, '<STR_LIT:location>', None)<EOL>)<EOL>loc = getattr(venue, '<STR_LIT:location>') if isinstance(venue, Room) else venue<EOL>event_locfilter = Q(room=venue) if isinstance(venue, Room) else Q(location=venue)<EOL>loc_party = TransactionParty.objects.get_or_create(<EOL>location=loc, defaults={'<STR_LIT:name>': loc.name}<EOL>)[<NUM_LIT:0>]<EOL>if rule.advanceDays:<EOL><INDENT>if rule.advanceDaysReference == RepeatedExpenseRule.MilestoneChoices.end:<EOL><INDENT>event_timefilters = event_timefilters &Q(endTime__lte=timezone.now() + timedelta(days=rule.advanceDays))<EOL><DEDENT>elif rule.advanceDaysReference == RepeatedExpenseRule.MilestoneChoices.start:<EOL><INDENT>event_timefilters = event_timefilters &Q(startTime__lte=timezone.now() + timedelta(days=rule.advanceDays))<EOL><DEDENT><DEDENT>if rule.priorDays:<EOL><INDENT>if rule.priorDaysReference == RepeatedExpenseRule.MilestoneChoices.end:<EOL><INDENT>event_timefilters = event_timefilters &Q(endTime__gte=timezone.now() - timedelta(days=rule.priorDays))<EOL><DEDENT>elif rule.priorDaysReference == RepeatedExpenseRule.MilestoneChoices.start:<EOL><INDENT>event_timefilters = event_timefilters &Q(startTime__gte=timezone.now() - timedelta(days=rule.priorDays))<EOL><DEDENT><DEDENT>if rule.startDate:<EOL><INDENT>event_timefilters = event_timefilters & Q(<EOL>event__startTime__gte=timezone.now().replace(<EOL>year=rule.startDate.year, month=rule.startDate.month, day=rule.startDate.day,<EOL>hour=<NUM_LIT:0>, minute=<NUM_LIT:0>, second=<NUM_LIT:0>, microsecond=<NUM_LIT:0>,<EOL>)<EOL>)<EOL><DEDENT>if rule.endDate:<EOL><INDENT>event_timefilters = event_timefilters & Q(<EOL>event__startTime__lte=timezone.now().replace(<EOL>year=rule.endDate.year, month=rule.endDate.month, day=rule.endDate.day,<EOL>hour=<NUM_LIT:0>, minute=<NUM_LIT:0>, second=<NUM_LIT:0>, microsecond=<NUM_LIT:0>,<EOL>)<EOL>)<EOL><DEDENT>replacements = {<EOL>'<STR_LIT:type>': _('<STR_LIT>'),<EOL>'<STR_LIT>': _('<STR_LIT>'),<EOL>'<STR_LIT:location>': venue.name,<EOL>'<STR_LIT>': _('<STR_LIT>'),<EOL>}<EOL>events = Event.objects.filter(event_locfilter & event_timefilters).exclude(<EOL>Q(expenseitem__expenseRule=rule)).distinct()<EOL>if rule.applyRateRule == rule.RateRuleChoices.hourly:<EOL><INDENT>for this_event in events:<EOL><INDENT>replacements['<STR_LIT:name>'] = this_event.name<EOL>replacements['<STR_LIT>'] = this_event.localStartTime.strftime('<STR_LIT>')<EOL>if (<EOL>event.localStartTime.strftime('<STR_LIT>') !=this_event.localEndTime.strftime('<STR_LIT>')<EOL>):<EOL><INDENT>replacements['<STR_LIT>'] += '<STR_LIT>' % (<EOL>_('<STR_LIT:to>'), this_event.localEndTime.strftime('<STR_LIT>')<EOL>)<EOL><DEDENT>ExpenseItem.objects.create(<EOL>event=this_event,<EOL>category=rental_category,<EOL>payTo=loc_party,<EOL>expenseRule=rule,<EOL>description='<STR_LIT>' %replacements,<EOL>submissionUser=submissionUser,<EOL>total=this_event.duration * rule.rentalRate,<EOL>accrualDate=this_event.startTime,<EOL>)<EOL>generate_count += <NUM_LIT:1><EOL><DEDENT><DEDENT>else:<EOL><INDENT>intervals = [<EOL>(x.localStartTime, x.localEndTime) for x inEventOccurrence.objects.filter(event__in=events)<EOL>]<EOL>remaining_intervals = rule.getWindowsAndTotals(intervals)<EOL>for startTime, endTime, total, description in remaining_intervals:<EOL><INDENT>replacements['<STR_LIT>'] = description<EOL>ExpenseItem.objects.create(<EOL>category=rental_category,<EOL>payTo=loc_party,<EOL>expenseRule=rule,<EOL>periodStart=startTime,<EOL>periodEnd=endTime,<EOL>description='<STR_LIT>' % replacements,<EOL>submissionUser=submissionUser,<EOL>total=total,<EOL>accrualDate=startTime,<EOL>)<EOL>generate_count += <NUM_LIT:1><EOL><DEDENT><DEDENT><DEDENT>rulesToCheck.update(lastRun=timezone.now())<EOL>return generate_count<EOL>
For each Location or Room-related Repeated Expense Rule, look for Events
in the designated time window that do not already have expenses associated
with them.  For hourly rental expenses, then generate new expenses that are
associated with this rule.  For non-hourly expenses, generate new expenses
based on the non-overlapping intervals of days, weeks or months for which
there is not already an ExpenseItem associated with the rule in question.