import pytest
from django.urls import reverse
from rest_framework import status
from decimal import Decimal
from restaurant.models import Booking, DeliveryContract, DeliveryCommissionLedger

@pytest.mark.django_db
class TestDeliveryPartnerAPI:
    def test_contract_request_and_approval(self, api_client, create_restaurant_owner, create_delivery_partner, create_restaurant):
        # Setup
        owner = create_restaurant_owner()
        partner = create_delivery_partner()
        restaurant = create_restaurant(owner)
        
        # 1. Partner sends connection request
        api_client.force_authenticate(user=partner)
        url = reverse('delivery-contract-request')
        data = {
            'restaurant': restaurant.id,
            'commission_type': 'FLAT_FEE',
            'commission_value': '40.00'
        }
        res = api_client.post(url, data)
        assert res.status_code == status.HTTP_201_CREATED
        contract_id = res.data['id']
        
        # 2. Owner approves connection request
        api_client.force_authenticate(user=owner)
        manage_url = reverse('delivery-contract-manage', kwargs={'pk': contract_id})
        res_manage = api_client.patch(manage_url, {'status': 'ACTIVE'})
        assert res_manage.status_code == status.HTTP_200_OK
        
        # Verify contract is active
        contract = DeliveryContract.objects.get(id=contract_id)
        assert contract.status == 'ACTIVE'

    def test_order_acceptance_and_delivery(self, api_client, create_restaurant_owner, create_delivery_partner, create_customer, create_restaurant):
        # Setup
        owner = create_restaurant_owner()
        partner = create_delivery_partner()
        customer = create_customer()
        restaurant = create_restaurant(owner)
        
        # Setup Active Contract
        DeliveryContract.objects.create(
            restaurant=restaurant,
            delivery_partner=partner,
            commission_type='FLAT_FEE',
            commission_value=Decimal('50.00'),
            status='ACTIVE'
        )
        
        # Create an Order (Booking)
        order = Booking.objects.create(
            user=customer,
            restaurant=restaurant,
            booking_type='DELIVERY',
            status='PREPARING',
            total_amount=Decimal('500.00'),
            subtotal=Decimal('450.00')
        )
        
        # 1. Partner fetches available orders
        api_client.force_authenticate(user=partner)
        url_available = reverse('delivery-available-orders')
        res_av = api_client.get(url_available)
        assert res_av.status_code == status.HTTP_200_OK
        assert len(res_av.data) == 1
        assert res_av.data[0]['id'] == order.id
        
        # 2. Partner accepts the order
        url_accept = reverse('delivery-accept-order', kwargs={'pk': order.id})
        res_ac = api_client.post(url_accept)
        assert res_ac.status_code == status.HTTP_200_OK
        
        # Verify assignment
        order.refresh_from_db()
        assert order.delivery_partner == partner
        assert order.status == 'PARTNER_ASSIGNED'
        
        # 3. Partner marks order as delivered
        url_deliver = reverse('delivery-complete-order', kwargs={'pk': order.id})
        res_del = api_client.post(url_deliver)
        assert res_del.status_code == status.HTTP_200_OK
        assert res_del.data['commission_earned'] == '50.00'
        
        # Verify ledger
        ledger = DeliveryCommissionLedger.objects.get(booking=order)
        assert ledger.delivery_partner == partner
        assert ledger.commission_amount == Decimal('50.00')
        assert ledger.is_settled == False
