def test_end_to_end_point_by_point_sites_realizations(self):
        """An example end-to-end calculation when a separate set of
        coefficients are computed for each site using the realizations as the
        predictor. This repeats the test elements above but all grouped together."""
        plugin = Plugin(predictor="realizations")
        calibrated_forecast_predictor, calibrated_forecast_var = plugin.process(
            self.current_forecast_spot_cube, self.coeffs_from_realizations_sites
        )

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data,
            self.expected_loc_param_realizations_sites,
        )
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data, self.expected_scale_param_realizations_sites
        )
        self.assertEqual(calibrated_forecast_predictor.dtype, np.float32)
class Test_process(SetupCoefficientsCubes, EnsembleCalibrationAssertions):

    """Test the process plugin."""

    def setUp(self):
        """Set-up the plugin for testing."""
        super().setUp()
        self.plugin = Plugin()

    @ManageWarnings(ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_diagnostic_match(self):
        """Test that an error is raised if the diagnostic_standard_name does
        not match when comparing a forecast cube and coefficients cubelist."""
        msg = "The forecast diagnostic"
        with self.assertRaisesRegex(ValueError, msg):
            self.plugin.process(
                self.current_wind_speed_forecast_cube, self.coeffs_from_mean
            )

    @ManageWarnings(ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_variable_setting(self):
        """Test that the cubes passed into the plugin are allocated to
        plugin variables appropriately."""

        _, _ = self.plugin.process(
            self.current_temperature_forecast_cube, self.coeffs_from_mean
        )
        self.assertEqual(
            self.current_temperature_forecast_cube, self.plugin.current_forecast
        )
        self.assertEqual(self.coeffs_from_mean, self.plugin.coefficients_cubelist)

    @ManageWarnings(ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_end_to_end(self):
        """An example end-to-end calculation. This repeats the test elements
        above but all grouped together."""
        calibrated_forecast_predictor, calibrated_forecast_var = self.plugin.process(
            self.current_temperature_forecast_cube, self.coeffs_from_mean
        )

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data, self.expected_loc_param_mean
        )
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data, self.expected_scale_param_mean
        )
        self.assertEqual(calibrated_forecast_predictor.dtype, np.float32)

    @ManageWarnings(ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_end_to_end_point_by_point(self):
        """An example end-to-end calculation when a separate set of
        coefficients are computed for each grid point. This repeats the test
        elements above but all grouped together."""
        calibrated_forecast_predictor, calibrated_forecast_var = self.plugin.process(
            self.current_temperature_forecast_cube, self.coeffs_from_mean_point_by_point
        )

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data, self.expected_loc_param_mean
        )
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data, self.expected_scale_param_mean
        )
        self.assertEqual(calibrated_forecast_predictor.dtype, np.float32)

    @ManageWarnings(ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_end_to_end_point_by_point_sites_realizations(self):
        """An example end-to-end calculation when a separate set of
        coefficients are computed for each site using the realizations as the
        predictor. This repeats the test elements above but all grouped together."""
        plugin = Plugin(predictor="realizations")
        calibrated_forecast_predictor, calibrated_forecast_var = plugin.process(
            self.current_forecast_spot_cube, self.coeffs_from_realizations_sites
        )

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data,
            self.expected_loc_param_realizations_sites,
        )
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data, self.expected_scale_param_realizations_sites
        )
        self.assertEqual(calibrated_forecast_predictor.dtype, np.float32)

    @ManageWarnings(ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_end_to_end_with_mask(self):
        """An example end-to-end calculation, but making sure that the
        areas that are masked within the landsea mask, are masked at the
        end."""

        # Construct a mask and encapsulate as a cube.
        mask = np.array([[1, 0, 0], [0, 1, 0], [0, 0, 1]])
        mask_cube = self.current_temperature_forecast_cube[0].copy(data=mask)
        # Convention for IMPROVER is that land points are ones and sea points
        # are zeros in land-sea masks. In this case we want to mask sea points.
        expected_mask = np.array(
            [[False, True, True], [True, False, True], [True, True, False]]
        )

        calibrated_forecast_predictor, calibrated_forecast_var = self.plugin.process(
            self.current_temperature_forecast_cube,
            self.coeffs_from_mean,
            landsea_mask=mask_cube,
        )

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data.data, self.expected_loc_param_mean
        )
        self.assertArrayEqual(calibrated_forecast_predictor.data.mask, expected_mask)
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data.data, self.expected_scale_param_mean
        )
        self.assertArrayEqual(calibrated_forecast_var.data.mask, expected_mask)
class Test_process(SetupCoefficientsCubes, EnsembleCalibrationAssertions):
    """Test the process plugin."""
    def setUp(self):
        """Set-up the plugin for testing."""
        super().setUp()
        self.plugin = Plugin()

    @ManageWarnings(
        ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_variable_setting(self):
        """Test that the cubes passed into the plugin are allocated to
        plugin variables appropriately."""

        _, _ = self.plugin.process(self.current_temperature_forecast_cube,
                                   self.coeffs_from_mean)
        self.assertEqual(self.current_temperature_forecast_cube,
                         self.plugin.current_forecast)
        self.assertEqual(self.coeffs_from_mean, self.plugin.coefficients_cube)

    @ManageWarnings(
        ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_end_to_end(self):
        """An example end-to-end calculation. This repeats the test elements
        above but all grouped together."""
        calibrated_forecast_predictor, calibrated_forecast_var = self.plugin.process(
            self.current_temperature_forecast_cube, self.coeffs_from_mean)

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data, self.expected_loc_param_mean)
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data, self.expected_scale_param_mean)
        self.assertEqual(calibrated_forecast_predictor.dtype, np.float32)

    @ManageWarnings(
        ignored_messages=["Collapsing a non-contiguous coordinate."])
    def test_end_to_end_with_mask(self):
        """An example end-to-end calculation, but making sure that the
        areas that are masked within the landsea mask, are masked at the
        end."""

        # Construct a mask and encapsulate as a cube.
        mask = np.array([[1, 0, 0], [0, 1, 0], [0, 0, 1]])
        mask_cube = self.current_temperature_forecast_cube[0].copy(data=mask)
        # Convention for IMPROVER is that land points are ones and sea points
        # are zeros in land-sea masks. In this case we want to mask sea points.
        expected_mask = np.array([[False, True, True], [True, False, True],
                                  [True, True, False]])

        calibrated_forecast_predictor, calibrated_forecast_var = self.plugin.process(
            self.current_temperature_forecast_cube,
            self.coeffs_from_mean,
            landsea_mask=mask_cube,
        )

        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_predictor.data.data,
            self.expected_loc_param_mean)
        self.assertArrayEqual(calibrated_forecast_predictor.data.mask,
                              expected_mask)
        self.assertCalibratedVariablesAlmostEqual(
            calibrated_forecast_var.data.data, self.expected_scale_param_mean)
        self.assertArrayEqual(calibrated_forecast_var.data.mask, expected_mask)