def load_dummy_context(): berth_lease = BerthLeaseFactory.build() ws_lease = WinterStorageLeaseFactory.build() dummy_context.update({ NotificationType.AUTOMATIC_INVOICING_EMAIL_ADMINS: { "subject": NotificationType.AUTOMATIC_INVOICING_EMAIL_ADMINS.label, "exited_with_errors": False, "successful_orders": randint(100, 500), "failed_orders": randint(0, 10), }, NotificationType.BERTH_LEASE_TERMINATED_LEASE_NOTICE: { "subject": NotificationType.BERTH_LEASE_TERMINATED_LEASE_NOTICE.label, "cancelled_at": format_date(today(), locale="fi"), "lease": berth_lease, }, NotificationType.WINTER_STORAGE_LEASE_TERMINATED_LEASE_NOTICE: { "subject": NotificationType.WINTER_STORAGE_LEASE_TERMINATED_LEASE_NOTICE. label, "cancelled_at": format_date(today(), locale="fi"), "lease": ws_lease, }, })
def test_query_send_berth_invoice_preview(api_client): lease = BerthLeaseFactory( boat=None, status=LeaseStatus.PAID, start_date=calculate_season_start_date(today() - relativedelta(years=1)), end_date=calculate_season_end_date(today() - relativedelta(years=1)), ) lease.contract = BerthContractFactory() lease.contract.save() BerthLeaseFactory( boat=None, status=LeaseStatus.REFUSED, start_date=calculate_season_start_date(today() - relativedelta(years=1)), end_date=calculate_season_end_date(today() - relativedelta(years=1)), ) BerthProductFactory( min_width=lease.berth.berth_type.width - 1, max_width=lease.berth.berth_type.width + 1, ) executed = api_client.execute(QUERY_SEND_BERTH_INVOICE_PREVIEW) assert executed["data"]["sendBerthInvoicePreview"] == {"expectedLeases": 1}
def _get_additional_product_order_context( subject: str = "Additional product order"): return { "subject": subject, "order": { "lease": { "start_date": today().date(), "end_date": today().date(), "berth": { "pier": { "harbor": { "name": "Satama" } } }, }, "total_price": Decimal("100.00"), "due_date": today().date(), }, "additional_product": { "name": "Product name", "season": "2020 - 2021" }, "payment_url": "http://foo.com", }
def test_approve_order_default_due_date( api_client, order: Order, payment_provider, notification_template_orders_approved, ): order.status = OrderStatus.DRAFTED order.save(update_fields=["status"]) order.due_date = today().date() order.save() variables = { "orders": [{ "orderId": to_global_id(OrderNode, order.id), "email": order.lease.application.email, }], } expected_due_date = today().date() + relativedelta(weeks=2) assert order.due_date != expected_due_date with mock.patch( "customers.services.profile.requests.post", side_effect=mocked_response_profile(count=1, data=None, use_edges=False), ): api_client.execute(APPROVE_ORDER_MUTATION, input=variables) order = Order.objects.get(id=order.id) assert order.due_date == expected_due_date
def parse_datetime(x): x = x.split('at')[0].replace(' ·', '') if 'Yesterday' in x: return utils.today() - relativedelta.relativedelta(days=1) if 'hr' in x or 'mins' in x: return utils.today() else: return parser.parse(x + " " + str(utils.today().year))
def current(self): if self.metadata["end_date"]: # This council has a known end data, check if it's in the past if parse(self.metadata["end_date"]) < today(): return False if parse(self.metadata["start_date"]) > today(): return False return True
def test_send_berth_invoices_basic(notification_template_orders_approved): lease = _lease_with_contract( boat=None, status=LeaseStatus.PAID, start_date=calculate_season_start_date(today() - relativedelta(years=1)), end_date=calculate_season_end_date(today() - relativedelta(years=1)), ) customer = lease.customer user = UserFactory() data = { "id": to_global_id(ProfileNode, customer.id), "first_name": user.first_name, "last_name": user.last_name, "primary_email": { "email": user.email }, "primary_phone": { "phone": faker.phone_number() }, } assert Order.objects.count() == 0 invoicing_service = _send_invoices(data) assert Order.objects.count() == 1 assert len(invoicing_service.successful_orders) == 1 assert len(invoicing_service.failed_orders) == 0 assert len(invoicing_service.failed_leases) == 0 assert Order.objects.first().id == invoicing_service.successful_orders[0] leases = BerthLease.objects.exclude(id=lease.id) assert leases.count() == 1 lease: BerthLease = leases.first() assert lease.status == LeaseStatus.OFFERED assert lease.start_date.isoformat() == "2020-06-10" assert lease.end_date.isoformat() == "2020-09-14" orders = Order.objects.all() assert orders.count() == 1 order: Order = orders.first() assert invoicing_service.successful_orders[0] == order.id assert order.lease == lease assert order.customer.id == customer.id assert order.status == OrderStatus.OFFERED assert len(mail.outbox) == 1 msg = mail.outbox[0] assert msg.subject == f"test order approved subject, event: {order.order_number}!" assert order.order_number in msg.body
def test_send_berth_invoices_invalid_example_email( notification_template_orders_approved, ): lease = _lease_with_contract( boat=None, status=LeaseStatus.PAID, start_date=today() - relativedelta(years=1), end_date=today() + relativedelta(years=-1, months=5), ) customer = lease.customer user = UserFactory() data = { "id": to_global_id(ProfileNode, customer.id), "first_name": user.first_name, "last_name": user.last_name, "primary_email": { "email": "*****@*****.**" }, "primary_phone": { "phone": faker.phone_number() }, } assert Order.objects.count() == 0 invoicing_service = _send_invoices(data) assert len(invoicing_service.successful_orders) == 0 assert len(invoicing_service.failed_orders) == 1 assert len( invoicing_service.failed_leases) == 1 # both order and lease fail assert Order.objects.count() == 1 order = Order.objects.first() assert order.status == OrderStatus.ERROR assert order.comment == "01-01-2020 10:00:00: Missing customer email" assert order.id in invoicing_service.failed_orders[0].keys() assert order.due_date is None assert invoicing_service.failed_orders[0].get( order.id) == "Missing customer email" assert len(mail.outbox) == 0 leases = BerthLease.objects.exclude(id=lease.id) assert leases.count() == 1 lease: BerthLease = leases.first() assert lease.status == LeaseStatus.ERROR assert "Error with the order, check the order first" in lease.comment assert lease.start_date.isoformat() == "2020-06-10" assert lease.end_date.isoformat() == "2020-09-14"
def test_send_berth_invoices_invalid_limit_reached( notification_template_orders_approved, ): first_lease = _lease_with_contract( boat=None, status=LeaseStatus.PAID, start_date=today() - relativedelta(years=1), end_date=today() + relativedelta(years=-1, months=5), ) for _ in range(2): _lease_with_contract( boat=None, status=LeaseStatus.PAID, start_date=today() - relativedelta(years=1), end_date=today() + relativedelta(years=-1, months=5), ) customer = first_lease.customer BerthProductFactory( min_width=first_lease.berth.berth_type.width - 1, max_width=first_lease.berth.berth_type.width + 1, ) user = UserFactory() data = { "id": to_global_id(ProfileNode, customer.id), "first_name": user.first_name, "last_name": user.last_name, "primary_email": { "email": "*****@*****.**" }, "primary_phone": { "phone": faker.phone_number() }, } assert Order.objects.count() == 0 invoicing_service = BerthInvoicingService( request=RequestFactory().request(), profile_token="token") with mock.patch( "customers.services.profile.requests.post", side_effect=mocked_response_profile(count=1, data=data), ): with mock.patch.object( invoicing_service, "email_admins", wraps=invoicing_service.email_admins, ) as email_admins_mock: invoicing_service.MAXIMUM_FAILURES = 1 invoicing_service.send_invoices() email_admins_mock.assert_called_once_with( True) # called with exited_with_errors=True assert invoicing_service.failure_count == 1
def test_non_invoiceable_berth(notification_template_orders_approved): berth = BerthFactory(is_invoiceable=False) lease_with_non_invoiceable_berth = _lease_with_contract( berth=berth, boat=None, status=LeaseStatus.PAID, start_date=calculate_season_start_date(today() - relativedelta(years=1)), end_date=calculate_season_end_date(today() - relativedelta(years=1)), ) customer = lease_with_non_invoiceable_berth.customer lease_with_invoiceable_berth = _lease_with_contract( customer=customer, boat=None, status=LeaseStatus.PAID, start_date=calculate_season_start_date(today() - relativedelta(years=1)), end_date=calculate_season_end_date(today() - relativedelta(years=1)), ) expected_product = BerthProduct.objects.get_in_range( lease_with_invoiceable_berth.berth.berth_type.width, get_berth_lease_pricing_category(lease_with_invoiceable_berth), ) user = UserFactory() data = { "id": to_global_id(ProfileNode, customer.id), "first_name": user.first_name, "last_name": user.last_name, "primary_email": { "email": user.email }, "primary_phone": { "phone": faker.phone_number() }, } assert Order.objects.count() == 0 invoicing_service = _send_invoices(data) assert len(invoicing_service.successful_orders) == 1 assert len(invoicing_service.failed_orders) == 0 assert len(invoicing_service.failed_leases) == 0 assert Order.objects.count() == 1 order = Order.objects.first() assert order.id == invoicing_service.successful_orders[0] assert order.product == expected_product
def index(request): chart_data = { 'monthly': { 'bugs': [], 'features': [], }, 'daily': { 'bugs': [], 'features': [], }, } one_year_ago = today() + relativedelta(months=-12) for i in range(12): one_year_ago = one_year_ago + relativedelta(months=+1) chart_data['monthly']['bugs'].append( get_model_count_for_date_range( BugWork, datetime_range(one_year_ago, 'month'))) chart_data['monthly']['features'].append( get_model_count_for_date_range( FeatureWork, datetime_range(one_year_ago, 'month'))) one_week_ago = today() + relativedelta(weeks=-1) for i in range(7): one_week_ago = one_week_ago + relativedelta(days=+1) chart_data['daily']['bugs'].append( get_model_count_for_date_range(BugWork, datetime_range(one_week_ago, 'day'))) chart_data['daily']['features'].append( get_model_count_for_date_range(FeatureWork, datetime_range(one_week_ago, 'day'))) bugs = Bug.objects.annotate( votecount=Count('bugvote')).order_by('-votecount') features = Feature.objects.annotate( votecount=Count('featurevote')).order_by('-votecount') mostvoted = { 'bug': bugs[:1][0] if bugs.count() > 0 else [], 'feature': features[:1][0] if features.count() > 0 else [], } return render(request, 'index.html', { 'chart_data': json.dumps(chart_data), 'mostvoted': mostvoted })
def test_approve_order_one_success_one_failure( superuser_api_client, order: Order, payment_provider, notification_template_orders_approved, ): order.status = OrderStatus.DRAFTED order.save(update_fields=["status"]) due_date = (today() + relativedelta(days=14)).date() failure_order_id = to_global_id(OrderNode, uuid.uuid4()) variables = { "dueDate": due_date, "orders": [ { "orderId": failure_order_id, "email": "*****@*****.**" }, { "orderId": to_global_id(OrderNode, order.id), "email": order.lease.application.email, }, ], } with mock.patch( "customers.services.profile.requests.post", side_effect=mocked_response_profile(count=1, data=None, use_edges=False), ): executed = superuser_api_client.execute(APPROVE_ORDER_MUTATION, input=variables) payment_url = payment_provider.get_payment_email_url( order, lang=order.lease.application.language) order = Order.objects.get(id=order.id) assert len(executed["data"]["approveOrders"]["failedOrders"]) == 1 assert executed["data"]["approveOrders"]["failedOrders"][0] == { "id": failure_order_id, "error": "Order matching query does not exist.", } assert order.due_date == due_date assert order.lease.status == LeaseStatus.OFFERED assert order.lease.application.status == ApplicationStatus.OFFER_SENT assert len(mail.outbox) == 1 assert (mail.outbox[0].subject == f"test order approved subject, event: {order.order_number}!") assert mail.outbox[0].body == f"{ order.order_number } { payment_url }" assert mail.outbox[0].to == [order.lease.application.email] assert mail.outbox[0].alternatives == [ (f"<b>{ order.order_number } { payment_url }</b>", "text/html") ]
def __init__(self, plot_config): self.top = plot_config['top'] self.left = plot_config['left'] self.bottom = plot_config['bottom'] self.right = plot_config['right'] self.track_height = plot_config['track_height'] self.track_gap = plot_config['track_gap'] self.min_activity_text_width = plot_config['activity_text_width'] self.milestone_text_width = plot_config['milestone_text_width'] self.text_margin = plot_config['text_margin'] self.milestone_width = plot_config['milestone_width'] self.activity_shape = VisualElementShape[ plot_config['activity_shape'].upper()] self.milestone_shape = VisualElementShape[ plot_config['milestone_shape'].upper()] if 'today' in plot_config: self.today = plot_config['today'] else: self.today = today() min_start_date = plot_config['min_start_date'] if pd.isnull(min_start_date): self.min_start_date = None # Will get calculated from plan data later else: self.min_start_date = min_start_date max_end_date = plot_config['max_end_date'] if pd.isnull(max_end_date): self.max_end_date = None # Will get calculated from plan data later else: self.max_end_date = max_end_date self.plot_area_width = self.right - self.left
def test_assign_new_sticker_number_resets_posted_date( sticker_sequences, superuser_api_client, winter_storage_lease, winter_storage_application, ): lease_id = to_global_id(WinterStorageLeaseNode, winter_storage_lease.id) variables = {"leaseId": lease_id} winter_storage_application.area_type = ApplicationAreaType.UNMARKED winter_storage_application.save() date_to_test = today() winter_storage_lease.status = LeaseStatus.PAID winter_storage_lease.application = winter_storage_application winter_storage_lease.sticker_posted = date_to_test winter_storage_lease.save() executed = superuser_api_client.execute(QUERY_WINTER_STORAGE_LEASE % lease_id) assert executed["data"]["winterStorageLease"]["stickerPosted"] == str( date_to_test.date()) superuser_api_client.execute(CONFIRM_PAYMENT_MUTATION, input=variables) executed = superuser_api_client.execute(QUERY_WINTER_STORAGE_LEASE % lease_id) assert executed["data"]["winterStorageLease"]["stickerPosted"] is None
def mutate_and_get_payload(cls, root, info, **input): failed_orders = [] due_date = input.get("due_date", today().date() + relativedelta(weeks=2)) profile_token = input.get("profile_token", None) for order_input in input.get("orders"): order_id = order_input.get("order_id") try: with transaction.atomic(): order = get_node_from_global_id( info, order_id, only_type=OrderNode, nullable=False, ) email = order_input.get("email") profile = (ProfileService(profile_token).get_profile( order.customer.id) if profile_token else None) approve_order(order, email, due_date, profile, info.context) except ( AnymailError, OSError, Order.DoesNotExist, ValidationError, VenepaikkaGraphQLError, ) as e: failed_orders.append(FailedOrderType(id=order_id, error=str(e))) return ApproveOrderMutation(failed_orders=failed_orders)
def mutate_and_get_payload(cls, root, info, offer_number, is_accepted, **input): offer = BerthSwitchOffer.objects.get(offer_number=offer_number) if is_accepted: if offer.status == OfferStatus.ACCEPTED: # do not proceed with db updates in exchange_berth_for_lease raise VenepaikkaGraphQLError(_("Offer is already accepted")) offer.set_status(OfferStatus.ACCEPTED) old_lease, new_lease = exchange_berth_for_lease( old_lease=offer.lease, new_berth=offer.berth, switch_date=max(today().date(), offer.lease.start_date), old_lease_comment=_( "Lease terminated due to a berth switch offer"), new_lease_comment=_("Lease created from a berth switch offer"), ) new_lease.application = offer.application new_lease.save() if old_lease.order: new_lease.orders.add(old_lease.order) else: # Reject offer offer.set_status(OfferStatus.REJECTED) return AcceptBerthSwitchOfferMutation()
def get_data_from_yahoo(reload_etf=True): if reload_etf: tickers = save_us_etf_tickers() else: with open("us_etfs.pickle", "rb") as f: tickers = pickle.load(f) if not os.path.exists('us_etf_dfs'): os.makedirs('us_etf_dfs') start = start_date end = today() for ticker in tickers: ticker = ticker.replace(".", "-") if not os.path.exists('us_etf_dfs/{}.csv'.format(ticker)): try: print('us_etf_dfs/{}.csv'.format(ticker)) df = web.DataReader(ticker, 'yahoo', start, end) df.to_csv('us_etf_dfs/{}.csv'.format(ticker)) except: print("Error finding " + ticker) else: if os.path.isfile('us_etf_dfs/{}.csv'.format(ticker)): print(f"File existing, saving without header") df.to_csv('us_etf_dfs/{}.csv'.format(ticker), mode='a', header=False) else: print('Already have {}'.format(ticker))
def test_preview_page(erm_user, django_app): """ Test the preview page. The preview page is just the edit page redisplayed with the updated values rendered in the same form as the details page and the form fields are hidden. """ instance = baker.make(Policy, condition="# heading", next_review=None) year = str(today().year + 1) edit_page = django_app.get(instance.get_edit_url(), user=erm_user) edit_form = edit_page.forms[1] edit_form["next_review"] = year edit_form["condition_type"] = Policy.CONDITION_TYPES.general edit_form["ages"] = [Policy.AGE_GROUPS.antenatal] edit_form["condition"] = "# updated" preview_page = edit_form.submit(name="preview") preview_form = preview_page.forms[1] assert preview_form["next_review"].attrs["type"] == "hidden" assert preview_form["next_review"].value == year assert preview_form["condition"].attrs["type"] == "hidden" assert preview_form["condition"].value == "# updated" assert preview_page.context.get("preview") == "preview" assert preview_page.context.get("publish") is None
def test_update_order_berth_product(api_client, status_choice, berth_lease): order = OrderFactory(lease=berth_lease, status=OrderStatus.OFFERED,) global_id = to_global_id(OrderNode, order.id) due_date = today() # only valid state transitions variables = { "orders": [ { "id": global_id, "comment": "foobar", "dueDate": due_date, "status": OrderStatusEnum.get(status_choice.value).name, } ] } assert Order.objects.count() == 1 executed = api_client.execute(UPDATE_ORDERS_MUTATION, input=variables) assert Order.objects.count() == 1 assert len(executed["data"]["updateOrders"]["failedOrders"]) == 0 assert len(executed["data"]["updateOrders"]["successfulOrders"]) == 1 assert executed["data"]["updateOrders"]["successfulOrders"][0] == { "id": global_id, "comment": "foobar", "price": str(order.product.price_for_tier(berth_lease.berth.pier.price_tier)), "taxPercentage": str(order.product.tax_percentage), "dueDate": str(due_date.date()), "status": OrderStatusEnum.get(status_choice.value).name, "customer": {"id": to_global_id(ProfileNode, order.customer.id)}, "product": {"id": to_global_id(BerthProductNode, order.product.id)}, "lease": {"id": to_global_id(BerthLeaseNode, berth_lease.id)}, }
def test_approve_order_sms_not_sent( api_client, order: Order, payment_provider, notification_template_orders_approved, ): order.status = OrderStatus.DRAFTED order.save(update_fields=["status"]) order.customer_phone = None order.save() due_date = (today() + relativedelta(days=14)).date() variables = { "dueDate": due_date, "orders": [{ "orderId": to_global_id(OrderNode, order.id), "email": order.lease.application.email, }], } with mock.patch( "customers.services.profile.requests.post", side_effect=mocked_response_profile(count=1, data=None, use_edges=False), ), mock.patch.object(SMSNotificationService, "send", return_value=None) as mock_send_sms: api_client.execute(APPROVE_ORDER_MUTATION, input=variables) # Assert that the SMS is not sent mock_send_sms.assert_not_called()
def test_usage_summary_mix(self): r1 = Resource.objects.create(price_member=10, price_not_member=20, name='resource1') r2 = Resource.objects.create(price_member=100, price_not_member=200, name='resource2') m = Member.objects.create(name='Member', is_member=True) u1 = Usage.objects.create(member=m, resource=r1, qty=5) u2 = Usage.objects.create(member=m, resource=r2, qty=8) u3 = Usage.objects.create(member=m, resource=r2, qty=4) i1 = Invoice.objects.create(member=m, invoice_number=1, date_paid=today()) u1.invoice = i1 u1.save() i2 = Invoice.objects.create(member=m, invoice_number=2) u2.invoice = i2 u2.save() self.client.force_login(self.super_user) response = self.client.get( reverse('admin:invoicing_usagesummary_changelist')) self.assertEqual(response.status_code, 200) summary = response.context['summary'] self.assertEqual(len(summary), 2) print(summary) for resource in summary: if resource['resource__name'] == 'resource1': self.assertDictEqual( resource, { 'resource__name': 'resource1', 'resource__unit__name': None, 'qty_used': 5, 'total_used': 50, 'total_invoiced': 50, 'total_paid': 50 }) elif resource['resource__name'] == 'resource2': self.assertDictEqual( resource, { 'resource__name': 'resource2', 'resource__unit__name': None, 'qty_used': 12, 'total_used': 1200, 'total_invoiced': 800, 'total_paid': None }) else: self.fail('Missing resource in summary')
def test_order_winter_storage_lease_right_price_for_partial_year( winter_storage_area): services = { "summer_storage_for_docking_equipment": True, "summer_storage_for_trailers": random_bool(), } day_offset = 100 for service, create in services.items(): if create: # Using PriceUnits.AMOUNT to simplify testing AdditionalProductFactory( service=ProductServiceType(service), price_unit=PriceUnits.AMOUNT, period=PeriodType.YEAR, ) section = WinterStorageSectionFactory(**services, area=winter_storage_area) lease = WinterStorageLeaseFactory( place=WinterStoragePlaceFactory(winter_storage_section=section), start_date=today(), end_date=today() + timedelta(days=day_offset), ) order = OrderFactory(lease=lease) for service, create in services.items(): if create: product = AdditionalProduct.objects.filter( service=ProductServiceType(service), price_unit=PriceUnits.AMOUNT, period=PeriodType.YEAR, ).first() OrderLine.objects.create(order=order, product=product) assert order.lease.start_date != calculate_berth_lease_start_date() assert order.lease.end_date != calculate_berth_lease_end_date() for service, created in services.items(): if created: order_line = OrderLine.objects.filter( order=order, product__service=ProductServiceType(service)).first() partial_product_price = calculate_product_partial_year_price( order_line.product.price_value, order.lease.start_date, order.lease.end_date, ) order_price = order_line.price assert partial_product_price == order_price
def check_all_headers(path=root, headers_template=default_tmpl, action='inject', single=False): """ :param path: :param headers_template: :param remove: :return: """ headers_tmpl = "" with open(headers_template) as f: for line in f.readlines(): headers_tmpl += "# %s" % line if line != "\n" else "#\n" # note: the year now disappeared, everything is redirected to the LICENSE file at the root headers_regex = re.compile(re.escape(headers_tmpl).replace("\\{", "{").replace("\\}", "}").format(year=".*")) headers = headers_tmpl.format(year=today().year) # rel_root = relpath(abspath(root), getcwd()) for f in glob("%s/**/*.py" % path, recursive=True): # skip meta tests if "meta" in f: print("skipping file %s" % f) continue # read file with open(f, mode="rt") as contents: src = contents.read() # skip empty files if src.strip() == "": print("skipping file %s as it is empty" % f) continue if action == 'inject': if src.startswith(headers): continue match = headers_regex.match(src) if match: # different year. remove the existing header and re-apply src = src[match.end():] new_contents = headers + src elif action == 'remove': if src.startswith(headers): new_contents = src[len(headers):] else: match = headers_regex.match(src) if match: new_contents = src[match.end():] else: continue else: raise ValueError("invalid action: %s" % action) with open(f, mode="wt") as contents: contents.write(new_contents) if single: print("single file modded '%s' - exiting" % f) break
def _get_query(self, model): config = self.CONFIGS[model._meta.label] return get_unreferenced_objects_query(model).filter( **{ f'{config.date_field}__lt': today(tzinfo=utc) - config.age_threshold }, ).order_by(f'-{config.date_field}', )
def __init__(self, request: HttpRequest, profile_token: str, due_date: date = None): # Default the due date to 14 days from the date when the task is executed self.request = request self.profile_token = profile_token self.due_date = due_date or (today() + relativedelta(days=14)).date()
def post(self, request, *args, **kwargs): print(self.kwargs.get('pk')) if Group.objects.get(id=self.kwargs.get('pk')): m1 = Membership(person=request.user, group=Group.objects.get(id=self.kwargs.get('pk')), date_joined=today()) m1.save() return redirect('groups')
def get_queryset(self): """ The QuerySet annotates whether a place is available or not. For this, it considers the following criteria: - If there are leases associated to the place - If any lease ends during the current or the last season (previous year) + If a lease ends during the current season: * It needs to have a "valid" status (DRAFTED, OFFERED, PAID, ERROR) + If a lease ended during the last season: * It should not have been renewed for the next season * It needs to have a "valid" status (PAID) """ from leases.models import WinterStorageLease season_end = calculate_winter_storage_lease_end_date() current_date = today().date() # If today is before the season ends but during the same year if current_date < season_end and current_date.year == season_end.year: last_year = current_date.year - 1 else: last_year = current_date.year in_current_season = Q(end_date__gte=season_end) in_last_season = Q(end_date__year=last_year) active_current_status = Q(status__in=ACTIVE_LEASE_STATUSES) paid_status = Q(status=LeaseStatus.PAID) # In case the renewed leases for the upcoming season haven't been sent # or some of the leases that had to be fixed (also for the upcoming season) # are pending, we check for leases on the previous season that have already been paid, # which in most cases means that the customer will keep the berth for the next season as well. # # Pre-filter the leases for the upcoming/current season renewed_leases = WinterStorageLease.objects.filter( in_current_season, place=OuterRef("place"), customer=OuterRef("customer"), ) # Filter the leases from the previous season that have already been renewed previous_leases = WinterStorageLease.objects.exclude( Exists(renewed_leases)).filter(in_last_season, paid_status, place=OuterRef("pk")) # For the leases that have been renewed or are valid during the current season. # Filter the leases on the current season that have not been rejected current_leases = WinterStorageLease.objects.filter( in_current_season, active_current_status, place=OuterRef("pk")) # A berth is NOT available when it already has a lease on the current (or upcoming) season # or when the previous season lease has been paid and the new leases have not been sent is_available = ~Exists(previous_leases | current_leases) return super().get_queryset().annotate(is_available=is_available)
def test_date_parsing_start_no_end_dates(self): ''' Validate that the function correctly parses dates when there is no end date supplied. ''' parsed_start, parsed_end = tools.parse_arg_dates(self.start_date_string) self.assertEqual(self.start_date, parsed_start) self.assertEqual(utils.today(), parsed_end)
def create_record(): """ Create a random record """ ts = (today() - relativedelta(days=random.randint(1, 30), seconds=random.randint(0, 86400))).isoformat() return dict( id=str(random.randint(10100, 10200)), data=create_fake_data(), ts=ts + "." + str(random.randint(111, 999)) + "Z", )
def test_set_stickers_posted_error_when_no_sticker_number( superuser_api_client, winter_storage_lease): lease_id = to_global_id(WinterStorageLeaseNode, winter_storage_lease.id) variables = {"leaseIds": [lease_id], "date": today()} executed = superuser_api_client.execute(SET_STICKERS_POSTED_MUTATION, input=variables) assert_in_errors("All leases must have an assigned sticker number", executed)
def testTodayTzInfo(self): self.assertEqual(utils.today(NYC), datetime(2014, 12, 15, 0, 0, 0, tzinfo=NYC))
def testToday(self): self.assertEqual(utils.today(), datetime(2014, 12, 15, 0, 0, 0))
def testTodayTzInfoDifferentDay(self): self.assertEqual(utils.today(UTC), datetime(2014, 12, 16, 0, 0, 0, tzinfo=UTC))