"""Test the pi models."""
from unittest import mock

from django.test import TestCase
from django.utils.timezone import now

from pi.models import PiLog


class PiLogTest(TestCase):
    """Test pi models."""

    def test_hit_calculation(self):
        """Test that x,y combinations are properly considered inside or outside the circle."""
        hit_item = PiLog(simulation_x=0.0, simulation_y=0.0, total_count=0, total_count_inside=0)
        miss_item = PiLog(simulation_x=1.0, simulation_y=1.0, total_count=0, total_count_inside=0)

        self.assertTrue(hit_item.hit)
        self.assertFalse(miss_item.hit)

    def test_value_calculation(self):
        """Test that a simulation's value of pi can be calculated."""
        item = PiLog(simulation_x=0.0, simulation_y=0.0, total_count=1000, total_count_inside=788)
        zero_item = PiLog(simulation_x=0.0, simulation_y=0.0, total_count=0, total_count_inside=0)

        self.assertEqual(item.value, 3.152)
        self.assertEqual(zero_item.value, 0.0)

    def test_string_repr(self):
        """Test the string repr of a simulation log entry."""
        item = PiLog(simulation_x=0.0, simulation_y=0.0, total_count=1000, total_count_inside=788,
                     created=now())

        self.assertIn("(788/1000) @ ", str(item))

    def test_simulation_inside_determination(self):
        """Test that running a simulation passes the proper inside value."""
        # get at least one simulation in the DB
        original_item, _, _ = PiLog.objects.simulate()

        with mock.patch('random.random', return_value=1.0):
            miss_item, _, _ = PiLog.objects.simulate()
        self.assertEqual(miss_item.total_count_inside, original_item.total_count_inside)

        with mock.patch('random.random', return_value=0.0):
            hit_item, _, _ = PiLog.objects.simulate()
        self.assertGreater(hit_item.total_count_inside, original_item.total_count_inside)