Skip to content

Commit

Permalink
Use catch_warnings from astropy (or at least try to)
Browse files Browse the repository at this point in the history
  • Loading branch information
djhoese committed Jul 17, 2016
1 parent 09b5929 commit 2e063b3
Show file tree
Hide file tree
Showing 2 changed files with 159 additions and 11 deletions.
23 changes: 12 additions & 11 deletions pyresample/test/test_geometry.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,12 @@

import numpy as np

import warnings
if sys.version_info < (2, 6):
warnings.simplefilter("ignore")
else:
warnings.simplefilter("always")
# import warnings
# if sys.version_info < (2, 6):
# warnings.simplefilter("ignore")
# else:
# warnings.simplefilter("always")
from pyresample.test.utils import catch_warnings

from pyresample import geometry, geo_filter

Expand Down Expand Up @@ -102,13 +103,13 @@ def test_base_lon_wrapping(self):
lons1 = np.arange(-135., +135, 50.)
lats = np.ones_like(lons1) * 70.

with warnings.catch_warnings(record=True) as w1:
with catch_warnings() as w1:
base_def1 = geometry.BaseDefinition(lons1, lats)
self.assertFalse(
len(w1) != 0, 'Got warning <%s>, but was not expecting one' % w1)

lons2 = np.where(lons1 < 0, lons1 + 360, lons1)
with warnings.catch_warnings(record=True) as w2:
with catch_warnings() as w2:
base_def2 = geometry.BaseDefinition(lons2, lats)
self.assertFalse(
len(w2) != 1, 'Failed to trigger a warning on longitude wrapping')
Expand All @@ -118,7 +119,7 @@ def test_base_lon_wrapping(self):
self.assertFalse(
base_def1 != base_def2, 'longitude wrapping to [-180:+180] did not work')

with warnings.catch_warnings(record=True) as w3:
with catch_warnings() as w3:
base_def3 = geometry.BaseDefinition(None, None)
self.assertFalse(
len(w3) != 0, 'Got warning <%s>, but was not expecting one' % w3)
Expand All @@ -145,7 +146,7 @@ def test_base_type(self):

# Test dtype is preserved with automatic longitude wrapping
lons2 = np.where(lons1 < 0, lons1 + 360, lons1)
with warnings.catch_warnings(record=True) as w:
with catch_warnings() as w:
basedef = geometry.BaseDefinition(lons2, lats)

lons, _ = basedef.get_lonlats()
Expand All @@ -154,7 +155,7 @@ def test_base_type(self):
(lons2.dtype, lons.dtype,))

lons2_ints = lons2.astype('int')
with warnings.catch_warnings(record=True) as w:
with catch_warnings() as w:
basedef = geometry.BaseDefinition(lons2_ints, lats)

lons, _ = basedef.get_lonlats()
Expand Down Expand Up @@ -184,7 +185,7 @@ def test_swath_wrap(self):
# (sys.version_info >= (3, 0) and sys.version_info < (3, 4))):
# swath_def = geometry.BaseDefinition(lons1, lats1)
# else:
with warnings.catch_warnings(record=True) as w1:
with catch_warnings() as w1:
swath_def = geometry.BaseDefinition(lons1, lats1)
self.assertFalse(
len(w1) != 1, 'Failed to trigger a warning on longitude wrapping')
Expand Down
147 changes: 147 additions & 0 deletions pyresample/test/utils.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,147 @@
#!/usr/bin/env python
# -*- coding: utf-8 -*-

# Copyright (c) 2014, 2015 Martin Raspaud

# Author(s):

# Martin Raspaud <martin.raspaud@smhi.se>

# This program is free software: you can redistribute it and/or modify it under
# the terms of the GNU Lesser General Public License as published by the Free
# Software Foundation, either version 3 of the License, or (at your option) any
# later version.

# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more
# details.

# You should have received a copy of the GNU Lesser General Public License along
# with this program. If not, see <http://www.gnu.org/licenses/>.

"""The test base.
"""
import sys
import six
import types
import warnings


_deprecations_as_exceptions = False


def treat_deprecations_as_exceptions():
"""
Turn all DeprecationWarnings (which indicate deprecated uses of
Python itself or Numpy, but not within Astropy, where we use our
own deprecation warning class) into exceptions so that we find
out about them early.
This completely resets the warning filters and any "already seen"
warning state.
"""
# First, totally reset the warning state
for module in list(six.itervalues(sys.modules)):
# We don't want to deal with six.MovedModules, only "real"
# modules.
if (isinstance(module, types.ModuleType) and
hasattr(module, '__warningregistry__')):
del module.__warningregistry__

if not _deprecations_as_exceptions:
return

warnings.resetwarnings()

# Hide the next couple of DeprecationWarnings
warnings.simplefilter('ignore', DeprecationWarning)
# Here's the wrinkle: a couple of our third-party dependencies
# (py.test and scipy) are still using deprecated features
# themselves, and we'd like to ignore those. Fortunately, those
# show up only at import time, so if we import those things *now*,
# before we turn the warnings into exceptions, we're golden.
try:
# A deprecated stdlib module used by py.test
import compiler # pylint: disable=W0611
except ImportError:
pass

try:
import scipy # pylint: disable=W0611
except ImportError:
pass

# Now, start over again with the warning filters
warnings.resetwarnings()
# Now, turn DeprecationWarnings into exceptions
warnings.filterwarnings("error", ".*", DeprecationWarning)

if sys.version_info[:2] >= (3, 4):
# py.test reads files with the 'U' flag, which is now
# deprecated in Python 3.4.
warnings.filterwarnings(
"ignore",
r"'U' mode is deprecated",
DeprecationWarning)

# BeautifulSoup4 triggers a DeprecationWarning in stdlib's
# html module.x
warnings.filterwarnings(
"ignore",
r"The strict argument and mode are deprecated\.",
DeprecationWarning)
warnings.filterwarnings(
"ignore",
r"The value of convert_charrefs will become True in 3\.5\. "
r"You are encouraged to set the value explicitly\.",
DeprecationWarning)

if sys.version_info[:2] >= (3, 5):
# py.test raises this warning on Python 3.5.
# This can be removed when fixed in py.test.
# See https://github.com/pytest-dev/pytest/pull/1009
warnings.filterwarnings(
"ignore",
r"inspect\.getargspec\(\) is deprecated, use "
r"inspect\.signature\(\) instead",
DeprecationWarning)


class catch_warnings(warnings.catch_warnings):
"""
A high-powered version of warnings.catch_warnings to use for testing
and to make sure that there is no dependence on the order in which
the tests are run.
This completely blitzes any memory of any warnings that have
appeared before so that all warnings will be caught and displayed.
``*args`` is a set of warning classes to collect. If no arguments are
provided, all warnings are collected.
Use as follows::
with catch_warnings(MyCustomWarning) as w:
do.something.bad()
assert len(w) > 0
"""
def __init__(self, *classes):
super(catch_warnings, self).__init__(record=True)
self.classes = classes

def __enter__(self):
warning_list = super(catch_warnings, self).__enter__()
treat_deprecations_as_exceptions()
if len(self.classes) == 0:
warnings.simplefilter('always')
else:
warnings.simplefilter('ignore')
for cls in self.classes:
warnings.simplefilter('always', cls)
return warning_list

def __exit__(self, type, value, traceback):
treat_deprecations_as_exceptions()


0 comments on commit 2e063b3

Please sign in to comment.