From 43cfdf4197b4610d285f70ef363bde027449383f Mon Sep 17 00:00:00 2001 From: Bill Little Date: Thu, 23 Mar 2017 12:08:13 +0000 Subject: [PATCH 1/2] Supporting netCDF conventions test changes. --- lib/iris/fileformats/netcdf.py | 13 ++++---- lib/iris/tests/integration/test_netcdf.py | 30 ++++++++++++++----- .../netcdf_save_load_ndim_auxiliary.cml | 2 +- .../netcdf/netcdf_save_ndim_auxiliary.cdl | 2 +- lib/iris/tests/test_netcdf.py | 13 ++------ .../unit/fileformats/netcdf/test_save.py | 19 +++++++++--- 6 files changed, 49 insertions(+), 30 deletions(-) diff --git a/lib/iris/fileformats/netcdf.py b/lib/iris/fileformats/netcdf.py index 3f47a7c7f7..551d414f98 100644 --- a/lib/iris/fileformats/netcdf.py +++ b/lib/iris/fileformats/netcdf.py @@ -1,4 +1,4 @@ -# (C) British Crown Copyright 2010 - 2016, Met Office +# (C) British Crown Copyright 2010 - 2017, Met Office # # This file is part of Iris. # @@ -2246,6 +2246,10 @@ def is_valid_packspec(p): conventions = CF_CONVENTIONS_VERSION + # Prioritise cube attributes conventions over the default. + if 'Conventions' in cube.attributes: + conventions = cube.attributes['Conventions'] + # Perform a CF patch of the conventions attribute. cf_profile_available = (iris.site_configuration.get('cf_profile') not in [None, False]) @@ -2260,12 +2264,7 @@ def is_valid_packspec(p): warnings.warn(msg) # Add conventions attribute. - if (cube.attributes.has_key('Conventions')): - msg = 'Keeping conventions from original netcdf file' - warnings.warn(msg) - sman.update_global_attributes(Conventions=cube.attributes.get('Conventions')) - else: - sman.update_global_attributes(Conventions=conventions) + sman.update_global_attributes(Conventions=conventions) def _no_unlim_dep_warning(): diff --git a/lib/iris/tests/integration/test_netcdf.py b/lib/iris/tests/integration/test_netcdf.py index 20e1e95bbd..21869284a7 100644 --- a/lib/iris/tests/integration/test_netcdf.py +++ b/lib/iris/tests/integration/test_netcdf.py @@ -179,22 +179,38 @@ def update(config): class TestConventionsAttributes(tests.IrisTest): - def test_patching_conventions_attribute(self): - # Ensure that user defined conventions are wiped and those which are + def test_patching_conventions_attribute_user_existing(self): + # Ensure that user defined conventions pass-thru and those which are # saved patched through site_config can be loaded without an exception # being raised. + conventions = 'some user defined conventions' cube = Cube([1.0], standard_name='air_temperature', units='K', - attributes={'Conventions': - 'some user defined conventions'}) + attributes=dict(Conventions=conventions)) # Patch the site configuration dictionary. with _patch_site_configuration(), self.temp_filename('.nc') as nc_path: iris.save(cube, nc_path) res = iris.load_cube(nc_path) - self.assertEqual(res.attributes['Conventions'], - '{}, {}, {}'.format(CF_CONVENTIONS_VERSION, - 'convention1', 'convention2')) + expected = '{}, {}, {}'.format(conventions, + 'convention1', + 'convention2') + self.assertEqual(res.attributes['Conventions'], expected) + + def test_patching_conventions_attribute_user_missing(self): + # Ensure that conventions which are saved patched through site_config + # can be loaded without an exception being raised. + cube = Cube([1.0], standard_name='air_temperature', units='K') + + # Patch the site configuration dictionary. + with _patch_site_configuration(), self.temp_filename('.nc') as nc_path: + iris.save(cube, nc_path) + res = iris.load_cube(nc_path) + + expected = '{}, {}, {}'.format(CF_CONVENTIONS_VERSION, + 'convention1', + 'convention2') + self.assertEqual(res.attributes['Conventions'], expected) class TestLazySave(tests.IrisTest): diff --git a/lib/iris/tests/results/netcdf/netcdf_save_load_ndim_auxiliary.cml b/lib/iris/tests/results/netcdf/netcdf_save_load_ndim_auxiliary.cml index 772c37808c..f7118af577 100644 --- a/lib/iris/tests/results/netcdf/netcdf_save_load_ndim_auxiliary.cml +++ b/lib/iris/tests/results/netcdf/netcdf_save_load_ndim_auxiliary.cml @@ -2,7 +2,7 @@ - + diff --git a/lib/iris/tests/results/netcdf/netcdf_save_ndim_auxiliary.cdl b/lib/iris/tests/results/netcdf/netcdf_save_ndim_auxiliary.cdl index ee172ace82..cf23a3e82c 100644 --- a/lib/iris/tests/results/netcdf/netcdf_save_ndim_auxiliary.cdl +++ b/lib/iris/tests/results/netcdf/netcdf_save_ndim_auxiliary.cdl @@ -50,5 +50,5 @@ variables: :history = "Thu Nov 29 10:45:50 2012: /project/ukmo/rhel6/nco/bin/ncks -d time,0,3 new_rotPole_precipitation.nc small_rotPole_precipitation.nc" ; :institution = "DMI" ; :source = "HIRHAM" ; - :Conventions = "CF-1.5" ; + :Conventions = "CF-1.0" ; } diff --git a/lib/iris/tests/test_netcdf.py b/lib/iris/tests/test_netcdf.py index 6463122409..853c9152ff 100644 --- a/lib/iris/tests/test_netcdf.py +++ b/lib/iris/tests/test_netcdf.py @@ -699,13 +699,10 @@ def test_attributes(self): # Should be global attributes. aglobals = {'history': 'A long time ago...', 'title': 'Attribute test', - 'foo': 'bar'} + 'foo': 'bar', + 'Conventions': 'TEST'} for k, v in six.iteritems(aglobals): self.cube.attributes[k] = v - # Should be overriden. - aover = {'Conventions': 'TEST'} - for k, v in six.iteritems(aover): - self.cube.attributes[k] = v # Should be data varible attributes. avars = {'standard_error_multiplier': 23, 'flag_masks': 'a', @@ -724,11 +721,7 @@ def test_attributes(self): if getattr(ds, gkey) != aglobals.get(gkey): exceptions.append('{} != {}'.format(getattr(ds, gkey), aglobals.get(gkey))) - # Should be overriden. - for okey in aover: - if getattr(ds, okey) == aover.get(okey): - exceptions.append('{} != {}'.format(getattr(ds, okey), - avars.get(okey))) + dv = ds['temp'] # Should be data varible attributes; # except STASH -> um_stash_source. diff --git a/lib/iris/tests/unit/fileformats/netcdf/test_save.py b/lib/iris/tests/unit/fileformats/netcdf/test_save.py index b1b76f56ce..55b1fb5715 100644 --- a/lib/iris/tests/unit/fileformats/netcdf/test_save.py +++ b/lib/iris/tests/unit/fileformats/netcdf/test_save.py @@ -33,11 +33,9 @@ class Test_attributes(tests.IrisTest): - def test_custom_conventions(self): - # Ensure that we drop existing conventions attributes and replace with - # CF convention. + def test_default_conventions(self): + # Ensure that cube with missing conventions use default. cube = Cube([0]) - cube.attributes['Conventions'] = 'convention1 convention2' with self.temp_filename('.nc') as nc_path: save(cube, nc_path, 'NETCDF4') @@ -46,6 +44,19 @@ def test_custom_conventions(self): ds.close() self.assertEqual(res, CF_CONVENTIONS_VERSION) + def test_custom_conventions(self): + # Ensure that existing conventions attributes pass-thru. + cube = Cube([0]) + conventions = 'convention1 convention2' + cube.attributes['Conventions'] = conventions + + with self.temp_filename('.nc') as nc_path: + save(cube, nc_path, 'NETCDF4') + ds = nc.Dataset(nc_path) + res = ds.getncattr('Conventions') + ds.close() + self.assertEqual(res, conventions) + def test_attributes_arrays(self): # Ensure that attributes containing NumPy arrays can be equality # checked and their cubes saved as appropriate. From 3691d323636168c2d3647d8a5f1a8e349eb0a992 Mon Sep 17 00:00:00 2001 From: Bill Little Date: Thu, 23 Mar 2017 23:56:30 +0000 Subject: [PATCH 2/2] Fix license headers. --- lib/iris/tests/integration/test_netcdf.py | 2 +- lib/iris/tests/test_netcdf.py | 2 +- lib/iris/tests/unit/fileformats/netcdf/test_save.py | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/lib/iris/tests/integration/test_netcdf.py b/lib/iris/tests/integration/test_netcdf.py index 21869284a7..9b3ef1b914 100644 --- a/lib/iris/tests/integration/test_netcdf.py +++ b/lib/iris/tests/integration/test_netcdf.py @@ -1,4 +1,4 @@ -# (C) British Crown Copyright 2014 - 2016, Met Office +# (C) British Crown Copyright 2014 - 2017, Met Office # # This file is part of Iris. # diff --git a/lib/iris/tests/test_netcdf.py b/lib/iris/tests/test_netcdf.py index 853c9152ff..55dc4d28c7 100644 --- a/lib/iris/tests/test_netcdf.py +++ b/lib/iris/tests/test_netcdf.py @@ -1,4 +1,4 @@ -# (C) British Crown Copyright 2010 - 2016, Met Office +# (C) British Crown Copyright 2010 - 2017, Met Office # # This file is part of Iris. # diff --git a/lib/iris/tests/unit/fileformats/netcdf/test_save.py b/lib/iris/tests/unit/fileformats/netcdf/test_save.py index 55b1fb5715..903855e75f 100644 --- a/lib/iris/tests/unit/fileformats/netcdf/test_save.py +++ b/lib/iris/tests/unit/fileformats/netcdf/test_save.py @@ -1,4 +1,4 @@ -# (C) British Crown Copyright 2014 - 2016, Met Office +# (C) British Crown Copyright 2014 - 2017, Met Office # # This file is part of Iris. #