diff --git a/.travis.yml b/.travis.yml index 312914d634..368fe33e31 100644 --- a/.travis.yml +++ b/.travis.yml @@ -100,12 +100,10 @@ install: - python setup.py --quiet install - # TODO : remove when iris doesn't do an integration test requiring iris-grib. - # test against the latest version of python-eccodes. - # Conda-forge versioning is out of order (0.9.* is later than 2.12.*). + # Docs builds and examples tests also need grib, for gallery examples. - > - if [[ "${TEST_MINIMAL}" != true ]]; then - conda install --quiet -n ${ENV_NAME} python-eccodes">=0.9.1, <2"; + if [[ "${TEST_TARGET}" == 'docstest' || "${TEST_TARGET}" == 'example' ]]; then + conda install --quiet -n ${ENV_NAME} python-eccodes; conda install --quiet -n ${ENV_NAME} --no-deps iris-grib; fi diff --git a/docs/iris/example_tests/test_polar_stereo.py b/docs/iris/example_tests/test_polar_stereo.py index 63581e7707..963d5729fe 100644 --- a/docs/iris/example_tests/test_polar_stereo.py +++ b/docs/iris/example_tests/test_polar_stereo.py @@ -15,7 +15,6 @@ ) -@tests.skip_grib class TestPolarStereo(tests.GraphicsTest): """Test the polar_stereo example code.""" diff --git a/docs/iris/src/conf.py b/docs/iris/src/conf.py index 98c12d2cb2..0e4c53bccc 100644 --- a/docs/iris/src/conf.py +++ b/docs/iris/src/conf.py @@ -140,7 +140,6 @@ intersphinx_mapping = { "cartopy": ("http://scitools.org.uk/cartopy/docs/latest/", None), - "iris-grib": ("http://iris-grib.readthedocs.io/en/latest/", None), "matplotlib": ("http://matplotlib.org/", None), "numpy": ("http://docs.scipy.org/doc/numpy/", None), "python": ("http://docs.python.org/2.7", None), diff --git a/docs/iris/src/userguide/saving_iris_cubes.rst b/docs/iris/src/userguide/saving_iris_cubes.rst index ecf2210810..f14f83006e 100644 --- a/docs/iris/src/userguide/saving_iris_cubes.rst +++ b/docs/iris/src/userguide/saving_iris_cubes.rst @@ -6,8 +6,8 @@ Saving Iris cubes Iris supports the saving of cubes and cube lists to: -* CF netCDF (1.5) -* GRIB (edition 2) +* CF netCDF (version 1.6) +* GRIB edition 2 (if `iris-grib `_ is installed) * Met Office PP @@ -57,7 +57,6 @@ The :py:func:`iris.save` function passes all other keywords through to the saver See * :py:func:`iris.fileformats.netcdf.save` -* :py:func:`iris.fileformats.grib.save_grib2` * :py:func:`iris.fileformats.pp.save` for more details on supported arguments for the individual savers. @@ -70,14 +69,14 @@ When saving to GRIB or PP, the save process may be intercepted between the trans For example, a GRIB2 message with a particular known long_name may need to be saved to a specific parameter code and type of statistical process. This can be achieved by:: def tweaked_messages(cube): - for cube, grib_message in iris.fileformats.grib.as_pairs(cube): + for cube, grib_message in iris_grib.save_pairs_from_cube(cube): # post process the GRIB2 message, prior to saving if cube.name() == 'carefully_customised_precipitation_amount': gribapi.grib_set_long(grib_message, "typeOfStatisticalProcess", 1) gribapi.grib_set_long(grib_message, "parameterCategory", 1) gribapi.grib_set_long(grib_message, "parameterNumber", 1) yield grib_message - iris.fileformats.grib.save_messages(tweaked_messages(cubes[0]), '/tmp/agrib2.grib2') + iris_grib.save_messages(tweaked_messages(cubes[0]), '/tmp/agrib2.grib2') Similarly a PP field may need to be written out with a specific value for LBEXP. This can be achieved by:: diff --git a/lib/iris/tests/__init__.py b/lib/iris/tests/__init__.py index 66966daaf4..8602defa16 100644 --- a/lib/iris/tests/__init__.py +++ b/lib/iris/tests/__init__.py @@ -76,13 +76,6 @@ else: GDAL_AVAILABLE = True -try: - from iris_grib.message import GribMessage - - GRIB_AVAILABLE = True -except ImportError: - GRIB_AVAILABLE = False - try: import iris_sample_data # noqa except ImportError: @@ -1181,12 +1174,6 @@ class MyPlotTests(test.GraphicsTest): return skip(fn) -skip_grib = unittest.skipIf( - not GRIB_AVAILABLE, - 'Test(s) require "iris-grib" package, ' "which is not available.", -) - - skip_sample_data = unittest.skipIf( not SAMPLE_DATA_AVAILABLE, ('Test(s) require "iris-sample-data", ' "which is not available."), diff --git a/lib/iris/tests/integration/format_interop/__init__.py b/lib/iris/tests/integration/format_interop/__init__.py deleted file mode 100644 index b9024f2f39..0000000000 --- a/lib/iris/tests/integration/format_interop/__init__.py +++ /dev/null @@ -1,6 +0,0 @@ -# Copyright Iris contributors -# -# This file is part of Iris and is released under the LGPL license. -# See COPYING and COPYING.LESSER in the root of the repository for full -# licensing details. -"""Integration tests for format interoperability.""" diff --git a/lib/iris/tests/integration/format_interop/test_name_grib.py b/lib/iris/tests/integration/format_interop/test_name_grib.py deleted file mode 100644 index 63889b879d..0000000000 --- a/lib/iris/tests/integration/format_interop/test_name_grib.py +++ /dev/null @@ -1,115 +0,0 @@ -# Copyright Iris contributors -# -# This file is part of Iris and is released under the LGPL license. -# See COPYING and COPYING.LESSER in the root of the repository for full -# licensing details. -"""Integration tests for NAME to GRIB2 interoperability.""" - -# Import iris.tests first so that some things can be initialised before -# importing anything else. -import iris.tests as tests - -import numpy as np -import warnings - -import iris - - -def name_cb(cube, field, filename): - # NAME files give the time point at the end of the range but Iris' - # GRIB loader creates it in the middle (the GRIB file itself doesn't - # encode a time point). Here we make them consistent so we can - # easily compare them. - t_coord = cube.coord("time") - t_coord.points = t_coord.bounds[0][1] - fp_coord = cube.coord("forecast_period") - fp_coord.points = fp_coord.bounds[0][1] - # NAME contains extra vertical meta-data. - z_coord = cube.coords("height") - if z_coord: - z_coord[0].standard_name = "height" - z_coord[0].long_name = "height above ground level" - - -@tests.skip_grib -class TestNameToGRIB(tests.IrisTest): - def check_common(self, name_cube, grib_cube): - self.assertTrue(np.allclose(name_cube.data, name_cube.data)) - self.assertTrue( - np.allclose( - name_cube.coord("latitude").points, - grib_cube.coord("latitude").points, - ) - ) - self.assertTrue( - np.allclose( - name_cube.coord("longitude").points, - grib_cube.coord("longitude").points - 360, - ) - ) - - for c in ["height", "time"]: - if name_cube.coords(c): - self.assertEqual(name_cube.coord(c), grib_cube.coord(c)) - - @tests.skip_data - def test_name2_field(self): - filepath = tests.get_data_path(("NAME", "NAMEII_field.txt")) - name_cubes = iris.load(filepath) - - # There is a known load/save problem with numerous - # gribapi/eccodes versions and - # zero only data, where min == max. - # This may be a problem with data scaling. - for i, name_cube in enumerate(name_cubes): - data = name_cube.data - if np.min(data) == np.max(data): - msg = ( - 'NAMEII cube #{}, "{}" has empty data : ' - "SKIPPING test for this cube, as save/load will " - "not currently work." - ) - warnings.warn(msg.format(i, name_cube.name())) - continue - - with self.temp_filename(".grib2") as temp_filename: - iris.save(name_cube, temp_filename) - grib_cube = iris.load_cube(temp_filename, callback=name_cb) - self.check_common(name_cube, grib_cube) - self.assertCML( - grib_cube, - tests.get_result_path( - ( - "integration", - "name_grib", - "NAMEII", - "{}_{}.cml".format(i, name_cube.name()), - ) - ), - ) - - @tests.skip_data - def test_name3_field(self): - filepath = tests.get_data_path(("NAME", "NAMEIII_field.txt")) - name_cubes = iris.load(filepath) - for i, name_cube in enumerate(name_cubes): - with self.temp_filename(".grib2") as temp_filename: - iris.save(name_cube, temp_filename) - grib_cube = iris.load_cube(temp_filename, callback=name_cb) - - self.check_common(name_cube, grib_cube) - self.assertCML( - grib_cube, - tests.get_result_path( - ( - "integration", - "name_grib", - "NAMEIII", - "{}_{}.cml".format(i, name_cube.name()), - ) - ), - ) - - -if __name__ == "__main__": - tests.main() diff --git a/lib/iris/tests/integration/format_interop/test_pp_grib.py b/lib/iris/tests/integration/format_interop/test_pp_grib.py deleted file mode 100644 index 70d89f834a..0000000000 --- a/lib/iris/tests/integration/format_interop/test_pp_grib.py +++ /dev/null @@ -1,50 +0,0 @@ -# Copyright Iris contributors -# -# This file is part of Iris and is released under the LGPL license. -# See COPYING and COPYING.LESSER in the root of the repository for full -# licensing details. -"""Integration tests for PP/GRIB interoperability.""" - -# Import iris.tests first so that some things can be initialised before -# importing anything else. -import iris.tests as tests - -import iris - - -@tests.skip_grib -class TestBoundedTime(tests.IrisTest): - @tests.skip_data - def test_time_and_forecast_period_round_trip(self): - pp_path = tests.get_data_path( - ("PP", "meanMaxMin", "200806081200__qwpb.T24.pp") - ) - # Choose the first time-bounded Cube in the PP dataset. - original = [ - cube - for cube in iris.load(pp_path) - if cube.coord("time").has_bounds() - ][0] - # Save it to GRIB2 and re-load. - with self.temp_filename(".grib2") as grib_path: - iris.save(original, grib_path) - from_grib = iris.load_cube(grib_path) - # Avoid the downcasting warning when saving to PP. - from_grib.data = from_grib.data.astype("f4") - # Re-save to PP and re-load. - with self.temp_filename(".pp") as pp_path: - iris.save(from_grib, pp_path) - from_pp = iris.load_cube(pp_path) - self.assertEqual(original.coord("time"), from_grib.coord("time")) - self.assertEqual( - original.coord("forecast_period"), - from_grib.coord("forecast_period"), - ) - self.assertEqual(original.coord("time"), from_pp.coord("time")) - self.assertEqual( - original.coord("forecast_period"), from_pp.coord("forecast_period") - ) - - -if __name__ == "__main__": - tests.main() diff --git a/lib/iris/tests/results/integration/name_grib/NAMEII/0_TRACER_AIR_CONCENTRATION.cml b/lib/iris/tests/results/integration/name_grib/NAMEII/0_TRACER_AIR_CONCENTRATION.cml deleted file mode 100644 index b0daf50907..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEII/0_TRACER_AIR_CONCENTRATION.cml +++ /dev/null @@ -1,37 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEII/1_TRACER_DOSAGE.cml b/lib/iris/tests/results/integration/name_grib/NAMEII/1_TRACER_DOSAGE.cml deleted file mode 100644 index aef4988ce6..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEII/1_TRACER_DOSAGE.cml +++ /dev/null @@ -1,37 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEII/3_TRACER_DRY_DEPOSITION.cml b/lib/iris/tests/results/integration/name_grib/NAMEII/3_TRACER_DRY_DEPOSITION.cml deleted file mode 100644 index 5787c19643..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEII/3_TRACER_DRY_DEPOSITION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEII/4_TRACER_TOTAL_DEPOSITION.cml b/lib/iris/tests/results/integration/name_grib/NAMEII/4_TRACER_TOTAL_DEPOSITION.cml deleted file mode 100644 index 5787c19643..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEII/4_TRACER_TOTAL_DEPOSITION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEIII/0_TRACER_AIR_CONCENTRATION.cml b/lib/iris/tests/results/integration/name_grib/NAMEIII/0_TRACER_AIR_CONCENTRATION.cml deleted file mode 100644 index 1a31427de0..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEIII/0_TRACER_AIR_CONCENTRATION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEIII/1_TRACER_AIR_CONCENTRATION.cml b/lib/iris/tests/results/integration/name_grib/NAMEIII/1_TRACER_AIR_CONCENTRATION.cml deleted file mode 100644 index 7007836e62..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEIII/1_TRACER_AIR_CONCENTRATION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEIII/2_TRACER_DRY_DEPOSITION.cml b/lib/iris/tests/results/integration/name_grib/NAMEIII/2_TRACER_DRY_DEPOSITION.cml deleted file mode 100644 index 850ef89ed2..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEIII/2_TRACER_DRY_DEPOSITION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEIII/3_TRACER_WET_DEPOSITION.cml b/lib/iris/tests/results/integration/name_grib/NAMEIII/3_TRACER_WET_DEPOSITION.cml deleted file mode 100644 index ade4cea92d..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEIII/3_TRACER_WET_DEPOSITION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/results/integration/name_grib/NAMEIII/4_TRACER_DEPOSITION.cml b/lib/iris/tests/results/integration/name_grib/NAMEIII/4_TRACER_DEPOSITION.cml deleted file mode 100644 index 088b622c46..0000000000 --- a/lib/iris/tests/results/integration/name_grib/NAMEIII/4_TRACER_DEPOSITION.cml +++ /dev/null @@ -1,34 +0,0 @@ - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - diff --git a/lib/iris/tests/runner/_runner.py b/lib/iris/tests/runner/_runner.py index 41d27bbfe3..8175e7b19f 100644 --- a/lib/iris/tests/runner/_runner.py +++ b/lib/iris/tests/runner/_runner.py @@ -143,10 +143,7 @@ def run(self): regexp_pat, "--process-timeout=180", ] - try: - import gribapi # noqa - except ImportError: - args.append("--exclude=^grib$") + if self.stop: args.append("--stop") diff --git a/lib/iris/tests/stock/__init__.py b/lib/iris/tests/stock/__init__.py index 9bb1c4626f..ea6d03a442 100644 --- a/lib/iris/tests/stock/__init__.py +++ b/lib/iris/tests/stock/__init__.py @@ -721,12 +721,6 @@ def realistic_4d_w_missing_data(): return cube -def global_grib2(): - path = tests.get_data_path(("GRIB", "global_t", "global.grib2")) - cube = iris.load_cube(path) - return cube - - def ocean_sigma_z(): """ Return a sample cube with an diff --git a/lib/iris/tests/system_test.py b/lib/iris/tests/system_test.py index 207bd700a3..a98a83768a 100644 --- a/lib/iris/tests/system_test.py +++ b/lib/iris/tests/system_test.py @@ -65,8 +65,6 @@ def horiz_cs(): ) filetypes = (".nc", ".pp") - if tests.GRIB_AVAILABLE: - filetypes += (".grib2",) for filetype in filetypes: saved_tmpfile = iris.util.create_temp_filename(suffix=filetype) iris.save(cm, saved_tmpfile) diff --git a/setup.cfg b/setup.cfg index 6e8bd69f88..a87902cbfd 100644 --- a/setup.cfg +++ b/setup.cfg @@ -12,7 +12,6 @@ exclude = */iris/std_names.py,\ */iris/io/format_picker.py,\ */iris/tests/__init__.py,\ */iris/tests/pp.py,\ - */iris/tests/stock.py,\ */iris/tests/system_test.py,\ */iris/tests/test_analysis.py,\ */iris/tests/test_analysis_calculus.py,\ @@ -28,8 +27,6 @@ exclude = */iris/std_names.py,\ */iris/tests/test_cube_to_pp.py,\ */iris/tests/test_file_load.py,\ */iris/tests/test_file_save.py,\ - */iris/tests/test_grib_save.py,\ - */iris/tests/test_grib_save_rules.py,\ */iris/tests/test_hybrid.py,\ */iris/tests/test_intersect.py,\ */iris/tests/test_io_init.py,\