diff --git a/.github/workflows/testing.yml b/.github/workflows/testing.yml index b4cedfc69..72da8f3e4 100644 --- a/.github/workflows/testing.yml +++ b/.github/workflows/testing.yml @@ -1,7 +1,4 @@ -# This workflow will install Python dependencies, run tests and lint with a single version of Python -# For more information see: https://docs.github.com/en/actions/automating-builds-and-tests/building-and-testing-python - -name: Python application +name: Test GeoClaw on: push: @@ -12,43 +9,47 @@ on: permissions: contents: read +env: + CLAW: ${{ github.workspace }} + jobs: build: - runs-on: ubuntu-latest - steps: - name: Set up Python 3.10 uses: actions/setup-python@v5 with: python-version: "3.10" - - name: Checkout clawpack - uses: actions/checkout@v4.1.5 - with: - repository: clawpack/clawpack - name: Install dependencies run: | sudo apt-get update sudo apt-get install gfortran liblapack-pic liblapack-dev libnetcdf-dev libnetcdff-dev python -m pip install --upgrade pip - pip install flake8 pytest - - name: Setup clawpack super repository - run: | - git submodule init - git submodule update - pip install --user -e . - - name: Setup geoclaw + pip install flake8 meson-python ninja pytest numpy pandas xarray netCDF4 + # if [ -f requirements.txt ]; then pip install -r requirements.txt; fi + + - name: Checkout Clawpack + uses: actions/checkout@v4.1.5 + with: + repository: clawpack/clawpack + submodules: true + - name: Checkout GeoClaw branch + uses: actions/checkout@v4.1.5 + with: + path: geoclaw + + - name: Install clawpack run: | - cd geoclaw - git checkout ${{ github.ref }} + pip install --no-build-isolation --editable . + - name: Lint with flake8 run: | - cd geoclaw + cd ${CLAW}/geoclaw # stop the build if there are Python syntax errors or undefined names flake8 . --count --select=E9,F63,F7,F82 --show-source --statistics --exclude old_dtopotools.py # exit-zero treats all errors as warnings. The GitHub editor is 127 chars wide flake8 . --count --exit-zero --max-complexity=10 --max-line-length=127 --statistics - name: Test with pytest run: | - cd geoclaw + cd ${CLAW}/geoclaw pytest diff --git a/README.md b/README.md new file mode 100644 index 000000000..0112a6a32 --- /dev/null +++ b/README.md @@ -0,0 +1,6 @@ +# GeoClaw - Geophysical Shallow Flow Package + +[![Test GeoClaw](https://github.com/clawpack/geoclaw/actions/workflows/testing.yml/badge.svg)](https://github.com/clawpack/geoclaw/actions/workflows/testing.yml) + +This repository hosts the source code for GeoClaw. + diff --git a/README.txt b/README.txt deleted file mode 100644 index cbfb9ef1a..000000000 --- a/README.txt +++ /dev/null @@ -1 +0,0 @@ -This repository will host the GeoClaw code. diff --git a/examples/multi-layer/bowl-radial/setplot.py b/examples/multi-layer/bowl-radial/setplot.py index da62ac9e4..995405ced 100644 --- a/examples/multi-layer/bowl-radial/setplot.py +++ b/examples/multi-layer/bowl-radial/setplot.py @@ -74,15 +74,15 @@ def pcolor_afteraxes(current_data): # bathy_ref_lines(current_data) gauge_locations(current_data) - def contour_afteraxes(current_data): - # gauge_locations(current_data) - # m_to_km_labels() - plt.hold(True) - pos = -80.0 * (23e3 / 180) + 500e3 - 5e3 - plt.plot([pos,pos],[-300e3,300e3],'b',[pos-5e3,pos-5e3],[-300e3,300e3],'y') - plt.hold(False) - wind_contours(current_data) - bathy_ref_lines(current_data) + # def contour_afteraxes(current_data): + # # gauge_locations(current_data) + # # m_to_km_labels() + # plt.hold(True) + # pos = -80.0 * (23e3 / 180) + 500e3 - 5e3 + # plt.plot([pos,pos],[-300e3,300e3],'b',[pos-5e3,pos-5e3],[-300e3,300e3],'y') + # plt.hold(False) + # wind_contours(current_data) + # bathy_ref_lines(current_data) def profile_afteraxes(current_data): pass @@ -259,23 +259,6 @@ def gaugetopo(current_data): plotitem.plot_var = gaugetopo plotitem.plotstyle = 'g-' - def add_zeroline(current_data): - from pylab import plot, legend, xticks, floor, axis, xlabel - t = current_data.t - gaugeno = current_data.gaugeno - - if gaugeno == 32412: - try: - plot(TG32412[:,0], TG32412[:,1], 'r') - legend(['GeoClaw','Obs'],loc='lower right') - except: pass - axis((0,t.max(),-0.3,0.3)) - - plot(t, 0*t, 'k') - n = int(floor(t.max()/3600.) + 2) - xticks([3600*i for i in range(n)], ['%i' % i for i in range(n)]) - xlabel('time (hours)') - #----------------------------------------- diff --git a/examples/multi-layer/plane_wave/setplot.py b/examples/multi-layer/plane_wave/setplot.py index f338e70c4..4056aff06 100644 --- a/examples/multi-layer/plane_wave/setplot.py +++ b/examples/multi-layer/plane_wave/setplot.py @@ -76,7 +76,7 @@ def transform_p2c(x, y, x0, y0, theta): plotdata.clearfigures() plotdata.save_frames = False - plotdata.format = 'ascii' + # plotdata.format = 'ascii' # ======================================================================== # Generic helper functions @@ -88,7 +88,6 @@ def contour_afteraxes(current_data): pos = -80.0 * (23e3 / 180) + 500e3 - 5e3 axes.plot([pos, pos], [-300e3, 300e3], 'b', [pos-5e3, pos-5e3], [-300e3, 300e3], 'y') - wind_contours(current_data) bathy_ref_lines(current_data) def profile_afteraxes(current_data): @@ -105,7 +104,6 @@ def bathy_ref_lines(current_data): # ======================================================================== # Axis limits - xlimits = [-0.5, 0.5] ylimits = [-0.5, 0.5] eta = [multilayer_data.eta[0], multilayer_data.eta[1]] @@ -129,8 +127,6 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.afteraxes = pcolor_afteraxes ml_plot.add_surface_elevation(plotaxes,1,bounds=top_surface_limits) - # ml_plot.add_surface_elevation(plotaxes,1,bounds=[-0.06,0.06]) - # ml_plot.add_surface_elevation(plotaxes,1) ml_plot.add_land(plotaxes, 1) # Bottom surface @@ -141,9 +137,7 @@ def bathy_ref_lines(current_data): plotaxes.xlimits = xlimits plotaxes.ylimits = ylimits plotaxes.afteraxes = pcolor_afteraxes - # ml_plot.add_surface_elevation(plotaxes,2,bounds=[-300-0.5,-300+0.5]) ml_plot.add_surface_elevation(plotaxes,2,bounds=internal_surface_limits) - # ml_plot.add_surface_elevation(plotaxes,2) ml_plot.add_land(plotaxes, 2) # ======================================================================== @@ -177,6 +171,7 @@ def bathy_ref_lines(current_data): # ======================================================================== # Water Speed + # ======================================================================== plotfigure = plotdata.new_plotfigure(name='speed') plotfigure.show = True plotfigure.kwargs = {'figsize': (14, 4)} @@ -200,9 +195,7 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.axescmd = 'subplot(1,2,2)' plotaxes.afteraxes = pcolor_afteraxes - # add_speed(plotaxes,2,bounds=[0.0,1e-10]) ml_plot.add_speed(plotaxes,2,bounds=internal_speed_limits) - # add_speed(plotaxes,2) ml_plot.add_land(plotaxes, 2) # Individual components @@ -218,7 +211,6 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.axescmd = 'subplot(2,2,1)' plotaxes.afteraxes = pcolor_afteraxes - # add_x_velocity(plotaxes,1,bounds=[-1e-10,1e-10]) ml_plot.add_x_velocity(plotaxes,1) ml_plot.add_land(plotaxes, 1) @@ -229,7 +221,6 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.axescmd = 'subplot(2,2,2)' plotaxes.afteraxes = pcolor_afteraxes - # add_y_velocity(plotaxes,1,bounds=[-0.000125,0.000125]) ml_plot.add_y_velocity(plotaxes,1) ml_plot.add_land(plotaxes, 1) @@ -241,7 +232,6 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.axescmd = 'subplot(2,2,3)' plotaxes.afteraxes = pcolor_afteraxes - # add_x_velocity(plotaxes,2,bounds=[-1e-10,1e-10]) ml_plot.add_x_velocity(plotaxes,2) ml_plot.add_land(plotaxes, 2) @@ -252,10 +242,9 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.axescmd = 'subplot(2,2,4)' plotaxes.afteraxes = pcolor_afteraxes - # add_y_velocity(plotaxes,2,bounds=[-0.8e-6,.8e-6]) ml_plot.add_y_velocity(plotaxes,2) - ml_plot.add_land(plotaxes, 2) + # ======================================================================== # Profile Plots # Note that these are not currently plotted by default - set @@ -274,39 +263,40 @@ def bathy_ref_lines(current_data): # Internal surface def bathy_profile(current_data): - return current_data.x[:, slice_index], b(current_data)[:, slice_index] + return current_data.x[:, slice_index], \ + ml_plot.b(current_data)[:, slice_index] def lower_surface(current_data): if multilayer_data.init_type == 2: return current_data.x[:, slice_index], \ - eta2(current_data)[:, slice_index] + ml_plot.eta2(current_data)[:, slice_index] elif multilayer_data.init_type == 6: return current_data.y[slice_index, :], \ - eta2(current_data)[slice_index, :] + ml_plot.eta2(current_data)[slice_index, :] def upper_surface(current_data): if multilayer_data.init_type == 2: return current_data.x[:, slice_index], \ - eta1(current_data)[:, slice_index] + ml_plot.eta1(current_data)[:, slice_index] elif multilayer_data.init_type == 6: return current_data.y[slice_index, :], \ - eta1(current_data)[slice_index, :] + ml_plot.eta1(current_data)[slice_index, :] def top_speed(current_data): if multilayer_data.init_type == 2: return current_data.x[:, slice_index], \ - water_u1(current_data)[:, slice_index] + ml_plot.water_u1(current_data)[:, slice_index] elif multilayer_data.init_type == 6: return current_data.y[slice_index, :], \ - water_u1(current_data)[slice_index, :] + ml_plot.water_u1(current_data)[slice_index, :] def bottom_speed(current_data): if multilayer_data.init_type == 2: return current_data.x[:, slice_index], \ - water_u2(current_data)[:, slice_index] + ml_plot.water_u2(current_data)[:, slice_index] elif multilayer_data.init_type == 6: return current_data.y[slice_index, :], \ - water_u2(current_data)[slice_index, :] + ml_plot.water_u2(current_data)[slice_index, :] # Bathy plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') diff --git a/examples/multi-layer/plane_wave/setrun.py b/examples/multi-layer/plane_wave/setrun.py index 7fd9a7514..021bbc1c6 100644 --- a/examples/multi-layer/plane_wave/setrun.py +++ b/examples/multi-layer/plane_wave/setrun.py @@ -4,9 +4,9 @@ that will be read in by the Fortran code. """ -from __future__ import absolute_import -from __future__ import print_function -import numpy +import os + +import numpy as np import clawpack.geoclaw.data import clawpack.geoclaw.topotools as tt @@ -14,12 +14,12 @@ # Rotation transformations def transform_c2p(x,y,x0,y0,theta): - return ((x+x0)*numpy.cos(theta) - (y+y0)*numpy.sin(theta), - (x+x0)*numpy.sin(theta) + (y+y0)*numpy.cos(theta)) + return ((x+x0)*np.cos(theta) - (y+y0)*np.sin(theta), + (x+x0)*np.sin(theta) + (y+y0)*np.cos(theta)) def transform_p2c(x,y,x0,y0,theta): - return ( x*numpy.cos(theta) + y*numpy.sin(theta) - x0, - -x*numpy.sin(theta) + y*numpy.cos(theta) - y0) + return ( x*np.cos(theta) + y*np.sin(theta) - x0, + -x*np.sin(theta) + y*np.cos(theta) - y0) # Class containing some setup for the qinit especially for multilayer tests @@ -300,15 +300,15 @@ def setrun(claw_pkg='geoclaw'): # Do not checkpoint at all pass - elif numpy.abs(clawdata.checkpt_style) == 1: + elif np.abs(clawdata.checkpt_style) == 1: # Checkpoint only at tfinal. pass - elif numpy.abs(clawdata.checkpt_style) == 2: + elif np.abs(clawdata.checkpt_style) == 2: # Specify a list of checkpoint times. clawdata.checkpt_times = [0.1,0.15] - elif numpy.abs(clawdata.checkpt_style) == 3: + elif np.abs(clawdata.checkpt_style) == 3: # Checkpoint every checkpt_interval timesteps (on Level 1) # and at the final time. clawdata.checkpt_interval = 5 @@ -384,8 +384,8 @@ def setrun(claw_pkg='geoclaw'): for (i,x_c) in enumerate(gauge_locations): # y0 = (self.run_data.clawdata.yupper - self.run_data.clawdata.ylower) / 2.0 # x_p,y_p = transform_c2p(x_c,0.0,location[0],location[1],angle) - x_p = x_c * numpy.cos(0.0) - y_p = x_c * numpy.sin(0.0) + x_p = x_c * np.cos(0.0) + y_p = x_c * np.sin(0.0) # print "+=====+" # print x_c,0.0 # print x_p,y_p @@ -487,10 +487,10 @@ def write_topo_file(run_data, out_file, **kwargs): # Make topography topo_func = lambda x, y: bathy_step(x, y, **kwargs) topo = tt.Topography(topo_func=topo_func) - topo.x = numpy.linspace(run_data.clawdata.lower[0], + topo.x = np.linspace(run_data.clawdata.lower[0], run_data.clawdata.upper[0], run_data.clawdata.num_cells[0] + 8) - topo.y = numpy.linspace(run_data.clawdata.lower[1], + topo.y = np.linspace(run_data.clawdata.lower[1], run_data.clawdata.upper[1], run_data.clawdata.num_cells[1] + 8) topo.write(out_file) diff --git a/src/2d/bouss/setrun_changes.py b/src/2d/bouss/setrun_changes.py deleted file mode 100644 index 95e7fdfc9..000000000 --- a/src/2d/bouss/setrun_changes.py +++ /dev/null @@ -1,33 +0,0 @@ - -# OLD: - - #------------------------------------------------------------------ - # Problem-specific parameters to be written to setprob.data: - #------------------------------------------------------------------ - - probdata = rundata.new_UserData(name='probdata',fname='setprob.data') - probdata.add_param('minLevelBouss', 1,' minlevel for Bouss terms') - probdata.add_param('maxLevelBouss', 10,' maxlevel for Bouss terms') - probdata.add_param('deepBouss', 5,' min water depth for Bouss terms') - probdata.add_param('solver', 3, ' 1=GMRES, 2=Pardiso, 3=PETSc') - probdata.add_param('equations', 2, ' 1=MadsenSchaffer, 2=SGN') - probdata.add_param('alpha', 1.153, ' If using SGN, else ignore') - probdata.add_param('startWithBouss', True, 'Take numSWEsteps of SWE first') - probdata.add_param('numSWEsteps', 0, ' Take this many SWE steps first') - - -# NEW: - - # To use Boussinesq solver, add bouss_data parameters here - # Also make sure to use the correct Makefile pointing to bouss version - from clawpack.geoclaw.data import BoussData - rundata.add_data(BoussData(),'bouss_data') - - # CHECK ORDER! - - rundata.bouss_data.bouss_equations = 2 # 0=SWE, 1=MS, 2=SGN - rundata.bouss_data.bouss_min_level = 1 # coarsest level to apply bouss - rundata.bouss_data.bouss_max_level = 10 # finest level to apply bouss - rundata.bouss_data.bouss_min_depth = 10. # depth to switch to SWE - rundata.bouss_data.bouss_solver = 3 # 1=GMRES, 2=Pardiso, 3=PETSc - rundata.bouss_data.bouss_tstart = 0. # time to switch from SWE diff --git a/src/python/geoclaw/dtopotools.py b/src/python/geoclaw/dtopotools.py index 37abc634f..82b89c7fe 100644 --- a/src/python/geoclaw/dtopotools.py +++ b/src/python/geoclaw/dtopotools.py @@ -3151,7 +3151,7 @@ def __init__(self, strike=0, length=1000e3): if strike not in [0, 180]: msg = "strike should be 0 for top at right or 180 for top at left\n" msg = msg + " strike = %s not allowed in 1d" % strike - raise InputError(msg) + raise ValueError(msg) self.strike = strike r"""rake=90, so top at right if strike=0, at left if strike=180""" @@ -3218,7 +3218,7 @@ def read(self, path=None, dtopo_type=None, verbose=False): dZvals = numpy.array(numpy.loadtxt(path, skiprows=6), ndmin=2) if dtopo_type==2: - dZ = reshape(dZvals,(mt,mx)) + dZ = numpy.reshape(dZvals,(mt,mx)) elif dtopo_type==3: dZ = dZvals diff --git a/src/python/geoclaw/fgmax_tools.py b/src/python/geoclaw/fgmax_tools.py index 224d7878b..baca3c5c4 100644 --- a/src/python/geoclaw/fgmax_tools.py +++ b/src/python/geoclaw/fgmax_tools.py @@ -375,10 +375,10 @@ def read_output(self, fgno=None, outdir=None, verbose=True, elif indexing == 'ij': reshape_order = 'F' else: - raise InputError("*** indexing must by 'xy' or 'ij'") + raise ValueError("*** indexing must by 'xy' or 'ij'") if self.point_style is None: - raise InputError("*** point_style is not set, need to read input?") + raise ValueError("*** point_style is not set, need to read input?") point_style = self.point_style if fgno is not None: diff --git a/src/python/geoclaw/multilayer/plot.py b/src/python/geoclaw/multilayer/plot.py index a37963d51..748f11fef 100644 --- a/src/python/geoclaw/multilayer/plot.py +++ b/src/python/geoclaw/multilayer/plot.py @@ -346,182 +346,182 @@ def add_land(plotaxes, surface, plot_type='pcolor', bounds=[-10, 10]): raise NotImplementedError("Plot type %s not implemented" % plot_type) -def add_combined_profile_plot(plot_data, slice_value, direction='x', - figno=120): - def slice_index(cd): - if direction == 'x': - if cd.grid.y.lower < slice_value < cd.grid.y.upper: - return int((slice_value - cd.grid.y.lower) / cd.dy - 0.5) - else: - return None - elif direction == 'y': - if cd.grid.x.lower < slice_value < cd.grid.x.upper: - return int((slice_value - cd.grid.x.lower) / cd.dx - 0.5) - else: - return None - - def bathy_profile(current_data): - index = slice_index(current_data) - if direction == 'x': - if index: - return current_data.x[:, index], b(current_data)[:, index] - else: - return None - elif direction == 'y': - if index: - return current_data.y[index, :], b(current_data)[index, :] - else: - return None - - def lower_surface(current_data): - index = slice_index(current_data) - if direction == 'x': - if index: - return current_data.x[:, index], eta2(current_data)[:, index] - else: - return None - elif direction == 'y': - if index: - return current_data.y[index, :], eta2(current_data)[index, :] - else: - return None - - def upper_surface(current_data): - index = slice_index(current_data) - if direction == 'x': - if index: - return current_data.x[:, index], eta1(current_data)[:, index] - else: - return None - elif direction == 'y': - if index: - return current_data.y[index, :], eta1(current_data)[index, :] - else: - return None - - # Surfaces - plotfigure = plotdata.new_plotfigure(name='combined_surface_%s' % figno, - figno=figno) - plotfigure.show = True - plotfigure.kwargs = {'figsize': (6, 6)} - - # Top surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.axescmd = 'subplot(2,1,1)' - plotaxes.title = 'Surfaces Profile %s at %s' % (direction, slice_value) - if multilayer_data.init_type == 2: - plotaxes.xlimits = xlimits - elif multilayer_data.init_type == 6: - plotaxes.xlimits = ylimits - - plotaxes.ylimits = top_surf_zoomed - - def top_surf_afteraxes(cd): - axes = plt.gca() - axes.set_xlabel('') - locs, labels = plt.xticks() - labels = ['' for i in range(len(locs))] - plt.xticks(locs, labels) - axes.plot([multilayer_data.bathy_location, - multilayer_data.bathy_location], top_surf_zoomed, '--k') - axes.set_ylabel('m') - - plotaxes.afteraxes = top_surf_afteraxes - plotitem = plotaxes.new_plotitem(plot_type="1d_from_2d_data") - plotitem.map_2d_to_1d = upper_surface - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.show = True - - # Internal surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.axescmd = 'subplot(2,1,2)' - plotaxes.title = '' - if multilayer_data.init_type == 2: - plotaxes.xlimits = xlimits - elif multilayer_data.init_type == 6: - plotaxes.xlimits = ylimits - plotaxes.ylimits = bottom_surf_zoomed - - def internal_surf_afteraxes(cd): - axes = plt.gca() - axes.set_title('') - axes.set_ylabel('m') - axes.subplots_adjust(hspace=0.05) - axes.plot([multilayer_data.bathy_location, - multilayer_data.bathy_location], bottom_surf_zoomed, '--k') - plotaxes.afteraxes = internal_surf_afteraxes - plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') - plotitem.map_2d_to_1d = lower_surface - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.color = 'k' - plotitem.show = True - - -def add_velocities_profile_plot(plot_data, slice_value, direction='x', - figno=130): - - def slice_index(cd): - if cd.grid.y.lower < slice_value < cd.grid.y.upper: - return int((slice_value - cd.grid.y.lower) / cd.dy - 0.5) - else: - return None - - def upper_surface(current_data): - index = slice_index(current_data) - if index: - return current_data.x[:, index], eta1(current_data)[:, index] - else: - return None - - def top_speed(current_data): - index = slice_index(current_data) - if index: - return current_data.x[:, index], water_u1(current_data)[:, index] - else: - return None, None - - def bottom_speed(current_data): - index = slice_index(current_data) - if index: - return current_data.x[:, index], water_u2(current_data)[:, index] - else: - return None, None - - # Velocities - plotfigure = plotdata.new_plotfigure(name='combined_velocities_%s' - % figno, figno=figno) - plotfigure.show = True - - # Top surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Velocities Profile %s at %s' % (direction, slice_value) - if multilayer_data.init_type == 2: - plotaxes.xlimits = xlimits - elif multilayer_data.init_type == 6: - plotaxes.xlimits = ylimits - plotaxes.ylimits = velocities_zoomed - - def velocity_afteraxes(cd): - axes = plt.gca() - axes.set_xlabel('') - locs, labels = plt.xticks() - labels = ['' for i in range(len(locs))] - plt.xticks(locs, labels) - axes.plot([multilayer_data.bathy_location, - multilayer_data.bathy_location], velocities_zoomed, '--k') - axes.set_ylabel('m/s') - plotaxes.afteraxes = velocity_afteraxes - - plotitem = plotaxes.new_plotitem(plot_type="1d_from_2d_data") - plotitem.map_2d_to_1d = top_speed - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.show = True - - plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') - plotitem.map_2d_to_1d = bottom_speed - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.color = 'k' - plotitem.show = True +# def add_combined_profile_plot(plot_data, slice_value, direction='x', +# figno=120): +# def slice_index(cd): +# if direction == 'x': +# if cd.grid.y.lower < slice_value < cd.grid.y.upper: +# return int((slice_value - cd.grid.y.lower) / cd.dy - 0.5) +# else: +# return None +# elif direction == 'y': +# if cd.grid.x.lower < slice_value < cd.grid.x.upper: +# return int((slice_value - cd.grid.x.lower) / cd.dx - 0.5) +# else: +# return None + +# def bathy_profile(current_data): +# index = slice_index(current_data) +# if direction == 'x': +# if index: +# return current_data.x[:, index], b(current_data)[:, index] +# else: +# return None +# elif direction == 'y': +# if index: +# return current_data.y[index, :], b(current_data)[index, :] +# else: +# return None + +# def lower_surface(current_data): +# index = slice_index(current_data) +# if direction == 'x': +# if index: +# return current_data.x[:, index], eta2(current_data)[:, index] +# else: +# return None +# elif direction == 'y': +# if index: +# return current_data.y[index, :], eta2(current_data)[index, :] +# else: +# return None + +# def upper_surface(current_data): +# index = slice_index(current_data) +# if direction == 'x': +# if index: +# return current_data.x[:, index], eta1(current_data)[:, index] +# else: +# return None +# elif direction == 'y': +# if index: +# return current_data.y[index, :], eta1(current_data)[index, :] +# else: +# return None + +# # Surfaces +# plotfigure = plotdata.new_plotfigure(name='combined_surface_%s' % figno, +# figno=figno) +# plotfigure.show = True +# plotfigure.kwargs = {'figsize': (6, 6)} + +# # Top surface +# plotaxes = plotfigure.new_plotaxes() +# plotaxes.axescmd = 'subplot(2,1,1)' +# plotaxes.title = 'Surfaces Profile %s at %s' % (direction, slice_value) +# if multilayer_data.init_type == 2: +# plotaxes.xlimits = xlimits +# elif multilayer_data.init_type == 6: +# plotaxes.xlimits = ylimits + +# plotaxes.ylimits = top_surf_zoomed + +# def top_surf_afteraxes(cd): +# axes = plt.gca() +# axes.set_xlabel('') +# locs, labels = plt.xticks() +# labels = ['' for i in range(len(locs))] +# plt.xticks(locs, labels) +# axes.plot([multilayer_data.bathy_location, +# multilayer_data.bathy_location], top_surf_zoomed, '--k') +# axes.set_ylabel('m') + +# plotaxes.afteraxes = top_surf_afteraxes +# plotitem = plotaxes.new_plotitem(plot_type="1d_from_2d_data") +# plotitem.map_2d_to_1d = upper_surface +# plotitem.amr_plotstyle = ['-', '+', 'x'] +# plotitem.show = True + +# # Internal surface +# plotaxes = plotfigure.new_plotaxes() +# plotaxes.axescmd = 'subplot(2,1,2)' +# plotaxes.title = '' +# if multilayer_data.init_type == 2: +# plotaxes.xlimits = xlimits +# elif multilayer_data.init_type == 6: +# plotaxes.xlimits = ylimits +# plotaxes.ylimits = bottom_surf_zoomed + +# def internal_surf_afteraxes(cd): +# axes = plt.gca() +# axes.set_title('') +# axes.set_ylabel('m') +# axes.subplots_adjust(hspace=0.05) +# axes.plot([multilayer_data.bathy_location, +# multilayer_data.bathy_location], bottom_surf_zoomed, '--k') +# plotaxes.afteraxes = internal_surf_afteraxes +# plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') +# plotitem.map_2d_to_1d = lower_surface +# plotitem.amr_plotstyle = ['-', '+', 'x'] +# plotitem.color = 'k' +# plotitem.show = True + + +# def add_velocities_profile_plot(plot_data, slice_value, direction='x', +# figno=130): + +# def slice_index(cd): +# if cd.grid.y.lower < slice_value < cd.grid.y.upper: +# return int((slice_value - cd.grid.y.lower) / cd.dy - 0.5) +# else: +# return None + +# def upper_surface(current_data): +# index = slice_index(current_data) +# if index: +# return current_data.x[:, index], eta1(current_data)[:, index] +# else: +# return None + +# def top_speed(current_data): +# index = slice_index(current_data) +# if index: +# return current_data.x[:, index], water_u1(current_data)[:, index] +# else: +# return None, None + +# def bottom_speed(current_data): +# index = slice_index(current_data) +# if index: +# return current_data.x[:, index], water_u2(current_data)[:, index] +# else: +# return None, None + +# # Velocities +# plotfigure = plotdata.new_plotfigure(name='combined_velocities_%s' +# % figno, figno=figno) +# plotfigure.show = True + +# # Top surface +# plotaxes = plotfigure.new_plotaxes() +# plotaxes.title = 'Velocities Profile %s at %s' % (direction, slice_value) +# if multilayer_data.init_type == 2: +# plotaxes.xlimits = xlimits +# elif multilayer_data.init_type == 6: +# plotaxes.xlimits = ylimits +# plotaxes.ylimits = velocities_zoomed + +# def velocity_afteraxes(cd): +# axes = plt.gca() +# axes.set_xlabel('') +# locs, labels = plt.xticks() +# labels = ['' for i in range(len(locs))] +# plt.xticks(locs, labels) +# axes.plot([multilayer_data.bathy_location, +# multilayer_data.bathy_location], velocities_zoomed, '--k') +# axes.set_ylabel('m/s') +# plotaxes.afteraxes = lambda cd: velocity_afteraxes(cd, velocities_zoomed) + +# plotitem = plotaxes.new_plotitem(plot_type="1d_from_2d_data") +# plotitem.map_2d_to_1d = top_speed +# plotitem.amr_plotstyle = ['-', '+', 'x'] +# plotitem.show = True + +# plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') +# plotitem.map_2d_to_1d = bottom_speed +# plotitem.amr_plotstyle = ['-', '+', 'x'] +# plotitem.color = 'k' +# plotitem.show = True diff --git a/src/python/geoclaw/surge/plot.py b/src/python/geoclaw/surge/plot.py index c2ada663f..4186d2d72 100644 --- a/src/python/geoclaw/surge/plot.py +++ b/src/python/geoclaw/surge/plot.py @@ -249,7 +249,7 @@ def add_surface_elevation(plotaxes, plot_type='pcolor', bounds=None, plot_type='2d_contourf') plotitem.plot_var = geoplot.surface_or_depth if bounds is not None: - contours = numpy.linspace(bounds[0], bounds[1], 11) + contours = np.linspace(bounds[0], bounds[1], 11) plotitem.contour_levels = contours plotitem.fill_cmin = bounds[0] plotitem.fill_cmax = bounds[1] @@ -310,7 +310,7 @@ def add_speed(plotaxes, plot_type='pcolor', bounds=None, contours=None, plotitem.colorbar_shrink = shrink plotitem.fill_cmap = plt.get_cmap('PuBu') if bounds is not None: - plotitem.contour_levels = numpy.linspace(bounds[0], bounds[1], 11) + plotitem.contour_levels = np.linspace(bounds[0], bounds[1], 11) plotitem.fill_cmin = bounds[0] plotitem.fill_cmap = bounds[1] elif contours is not None: diff --git a/src/python/geoclaw/surge/storm.py b/src/python/geoclaw/surge/storm.py index dbcfad3ff..912d6a388 100644 --- a/src/python/geoclaw/surge/storm.py +++ b/src/python/geoclaw/surge/storm.py @@ -101,17 +101,17 @@ # Warning for formats that have yet to have a default way to determine crticial # radii from the input data -missing_data_warning_str = """*** Cannot yet automatically determine the - maximum wind radius. Will write out GeoClaw - formats but note that these will not work - when running GeoClaw currently without a custom - `max_wind_radius_fill` function passed as argument - to the `write` function.""" +missing_data_warning_str = ("Cannot yet automatically determine the" + + "maximum wind radius. Will write out GeoClaw" + + "formats but note that these will not work" + + "when running GeoClaw currently without a custom" + + "`max_wind_radius_fill` function passed as " + + "argument to the `write` function.") # Warning for not having any time points with both a max wind speed and central # pressure observation -missing_necessary_data_warning_str = """No storm points in the input file - had both a max wind speed and a central pressure observation.""" +missing_necessary_data_warning_str = ("No storm points in the input file" + + "had both a max wind speed and a central pressure observation.") class NoDataError(ValueError): @@ -416,6 +416,9 @@ def num_converter(x): self.wind_speeds[:, 1] = units.convert( self.wind_speeds[:, 1], 'nmi', 'm') + # Set time offset to first time as a default + self.time_offset = self.t[0] + def read_hurdat(self, path, verbose=False): r"""Read in HURDAT formatted storm file @@ -679,6 +682,7 @@ def func(x): return agency_map[x] # convert datetime64 to datetime.datetime self.t = [] for d in ds.time: + print(d) t = d.dt self.t.append(datetime.datetime(t.year, t.month, t.day, t.hour, t.minute, t.second)) @@ -1013,33 +1017,33 @@ def write_atcf(self, path, verbose=False): """ raise NotImplementedError(("Writing out ATCF files is not implemented ", "yet but is planned for a future release.")) - try: - with open(path, 'w') as data_file: - for n in range(len(self.t)): - data_file.write("".join((", " * 2, - "%s" % seconds2date(self.t[n]), - ", " * 4, - "%s" % (int(self.eye_location[n, 0] * - 10.0)), - ", ", - "%s" % (int(self.eye_location[n, 1] * - 10.0)), - ", ", - "%s" % self.max_wind_speed[n], - ", ", - "%s" % self.central_pressure[n], - ", ", - ", " * 8, - "%s" % self.storm_radius[n], - ", ", - "%s" % self.max_wind_radius[n], - ", " * 10, - "\n"))) - except Exception as e: - # Remove possiblly partially generated file if not successful - if os.path.exists(path): - os.remove(path) - raise e + # try: + # with open(path, 'w') as data_file: + # for n in range(len(self.t)): + # data_file.write("".join((", " * 2, + # "%s" % seconds2date(self.t[n]), + # ", " * 4, + # "%s" % (int(self.eye_location[n, 0] * + # 10.0)), + # ", ", + # "%s" % (int(self.eye_location[n, 1] * + # 10.0)), + # ", ", + # "%s" % self.max_wind_speed[n], + # ", ", + # "%s" % self.central_pressure[n], + # ", ", + # ", " * 8, + # "%s" % self.storm_radius[n], + # ", ", + # "%s" % self.max_wind_radius[n], + # ", " * 10, + # "\n"))) + # except Exception as e: + # # Remove possiblly partially generated file if not successful + # if os.path.exists(path): + # os.remove(path) + # raise e def write_hurdat(self, path, verbose=False): r"""Write out a HURDAT formatted storm file @@ -1051,50 +1055,50 @@ def write_hurdat(self, path, verbose=False): raise NotImplementedError(("Writing out hurdat files is not ", "implemented yet but is planned for a ", "future release.")) - try: - with open(path, 'w') as data_file: - data_file.write('%s %s %s' % ("Date", "Hurricane Name", - "Indicator")) - for n in range(self.t.shape[0]): - - latitude = float(self.eye_location[n, 0]) - longitude = float(self.eye_location[n, 1]) - - # Convert latitude to proper Hurdat format e.g 12.0N - if latitude > 0: - latitude = str(np.abs(latitude)) + 'N' - else: - latitude = str(np.abs(latitude)) + 'S' - - # Convert longitude to proper Hurdat format e.g 12.0W - if longitude > 0: - longitude = str(np.abs(longitude)) + 'E' - else: - longitude = str(np.abs(longitude)) + 'W' - - data_file.write("".join(("%s" % self.seconds2date( - self.t[n])[0:-2], - "%s00" % self.seconds2date( - self.t[n])[-2:], - ", " * 3, - "%s" % (latitude), - ", ", - "%s" % (longitude), - ", ", - "%s" % self.max_wind_speed[n], - ", ", - "%s" % self.central_pressure[n], - ", ", - "%s" % self.storm_radius[n], - ", ", - "%s" % self.max_wind_radius[n], - ", " * 10, - "\n"))) - except Exception as e: - # Remove possiblly partially generated file if not successful - if os.path.exists(path): - os.remove(path) - raise e + # try: + # with open(path, 'w') as data_file: + # data_file.write('%s %s %s' % ("Date", "Hurricane Name", + # "Indicator")) + # for n in range(self.t.shape[0]): + + # latitude = float(self.eye_location[n, 0]) + # longitude = float(self.eye_location[n, 1]) + + # # Convert latitude to proper Hurdat format e.g 12.0N + # if latitude > 0: + # latitude = str(numpy.abs(latitude)) + 'N' + # else: + # latitude = str(numpy.abs(latitude)) + 'S' + + # # Convert longitude to proper Hurdat format e.g 12.0W + # if longitude > 0: + # longitude = str(numpy.abs(longitude)) + 'E' + # else: + # longitude = str(numpy.abs(longitude)) + 'W' + + # data_file.write("".join(("%s" % self.seconds2date( + # self.t[n])[0:-2], + # "%s00" % self.seconds2date( + # self.t[n])[-2:], + # ", " * 3, + # "%s" % (latitude), + # ", ", + # "%s" % (longitude), + # ", ", + # "%s" % self.max_wind_speed[n], + # ", ", + # "%s" % self.central_pressure[n], + # ", ", + # "%s" % self.storm_radius[n], + # ", ", + # "%s" % self.max_wind_radius[n], + # ", " * 10, + # "\n"))) + # except Exception as e: + # # Remove possiblly partially generated file if not successful + # if os.path.exists(path): + # os.remove(path) + # raise e def write_jma(self, path, verbose=False): r"""Write out a JMA formatted storm file @@ -1105,32 +1109,33 @@ def write_jma(self, path, verbose=False): """ raise NotImplementedError(("Writing out JMA files is not implemented ", "yet but is planned for a future release.")) - try: - with open(path, 'w') as data_file: - for n in range(self.t.shape[0]): - data_file.write("".join(("%s" % self.seconds2date(self.t[n]), - " " * 4, - "%s" % (int(self.eye_location[n, 0] * - 10.0)), - ", ", - "%s" % (int(self.eye_location[n, 1] * - 10.0)), - ", ", - "%s" % self.max_wind_speed[n], - ", ", - "%s" % self.central_pressure[n], - ", ", - ", " * 8, - "%s" % self.storm_radius[n], - ", ", - "%s" % self.max_wind_radius[n], - ", " * 10, - "\n"))) - except Exception as e: - # Remove possiblly partially generated file if not successful - if os.path.exists(path): - os.remove(path) - raise e + + # try: + # with open(path, 'w') as data_file: + # for n in range(self.t.shape[0]): + # data_file.write("".join(("%s" % self.seconds2date(self.t[n]), + # " " * 4, + # "%s" % (int(self.eye_location[n, 0] * + # 10.0)), + # ", ", + # "%s" % (int(self.eye_location[n, 1] * + # 10.0)), + # ", ", + # "%s" % self.max_wind_speed[n], + # ", ", + # "%s" % self.central_pressure[n], + # ", ", + # ", " * 8, + # "%s" % self.storm_radius[n], + # ", ", + # "%s" % self.max_wind_radius[n], + # ", " * 10, + # "\n"))) + # except Exception as e: + # # Remove possiblly partially generated file if not successful + # if os.path.exists(path): + # os.remove(path) + # raise e def write_imd(self, path, verbose=False): r"""Write out an IMD formatted storm file @@ -1274,7 +1279,7 @@ def construct_fields(storm, r, t, model="holland_1980"): if model.lower() not in _supported_models.keys(): raise ValueError("Model %s not available." % model) - return getattr(sys.modules[__name__], model.lower())(storm, x, t) + return getattr(sys.modules[__name__], model.lower())(storm, r, t) # Specific implementations @@ -1415,12 +1420,15 @@ def available_models(): def make_multi_structure(path): r"""Create a dictionary of Storm objects for ATCF files with multiple storm tracks in them """ + raise NotImplementedError("Extracing multiple tracks from ATCF files is " + + "not supported yet.") with open(path, 'r') as f: lines = f.readlines() curTime = "test" curTrack = "test" os.mkdir("Clipped_ATCFs") stormDict = {} + fileWrite = None for line in lines: lineArr = line.split(", ") if curTime in lineArr[2]: diff --git a/src/python/geoclaw/test.py b/src/python/geoclaw/test.py index c3685e973..c6700deda 100644 --- a/src/python/geoclaw/test.py +++ b/src/python/geoclaw/test.py @@ -30,6 +30,9 @@ for path in glob.glob(os.path.join(lib_path,"*.mod")): os.remove(path) +# Scratch directory for GeoClaw +scratch_path = os.path.abspath(os.path.join(CLAW, 'scratch')) + class GeoClawRegressionTest(clawpack.clawutil.test.ClawpackRegressionTest): diff --git a/src/python/geoclaw/topotools.py b/src/python/geoclaw/topotools.py index 1743e1ae6..ad3a8911a 100644 --- a/src/python/geoclaw/topotools.py +++ b/src/python/geoclaw/topotools.py @@ -931,7 +931,7 @@ def read_header(self): raise e data = gdal.Open(self.path) - # z = data.GetRasterBand(1).ReadAsArray() + z = data.GetRasterBand(1).ReadAsArray() transform = data.GetGeoTransform() x_origin = transform[0] y_origin = transform[3] @@ -940,9 +940,9 @@ def read_header(self): # self._Z = numpy.flipud(z) self._x = numpy.linspace(x_origin, - x_origin + (z.shape[0] - 1) * dx, z.shape[0]) + x_origin + (z.shape[0] - 1) * dx, z.shape[0]) self._y = numpy.linspace(y_origin - (z.shape[0] - 1) * dy, - y_origin, z.shape[1]) + y_origin, z.shape[1]) else: raise IOError("Cannot read header for topo_type %s" % self.topo_type) diff --git a/src/python/geoclaw/util.py b/src/python/geoclaw/util.py index b358c9546..cbb41b802 100644 --- a/src/python/geoclaw/util.py +++ b/src/python/geoclaw/util.py @@ -197,7 +197,7 @@ def bearing(x0, y0, x1, y1, units='degrees', bearing_units='degrees'): return beta def gctransect(x1,y1,x2,y2,npts,coords='W',units='degrees',Rearth=Rearth): - """ + r""" Given (longitude,latitude) pairs (x1,y1), (x2,y2) and npts Compute (x,y) for npts equally spaced points on the great circle connecting them. diff --git a/tests/bowl_slosh/__init__.py b/tests/bowl_slosh/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/tests/bowl_slosh/setrun.py b/tests/bowl_slosh/setrun.py index 1d2120913..1f9288b33 100644 --- a/tests/bowl_slosh/setrun.py +++ b/tests/bowl_slosh/setrun.py @@ -360,8 +360,6 @@ def setgeo(rundata): # Refinement data refinement_data = rundata.refinement_data refinement_data.wave_tolerance = 1.e-2 - refinement_data.deep_depth = 1e2 - refinement_data.max_level_deep = 3 refinement_data.variable_dt_refinement_ratios = True # == settopo.data values == diff --git a/tests/bowl_slosh/regression_tests.py b/tests/bowl_slosh/test_bowl_slosh.py similarity index 100% rename from tests/bowl_slosh/regression_tests.py rename to tests/bowl_slosh/test_bowl_slosh.py diff --git a/tests/chile2010_adjoint/__init__.py b/tests/chile2010_adjoint/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/tests/chile2010_adjoint/adjoint/setrun.py b/tests/chile2010_adjoint/adjoint/setrun.py index 950182709..05286d667 100644 --- a/tests/chile2010_adjoint/adjoint/setrun.py +++ b/tests/chile2010_adjoint/adjoint/setrun.py @@ -382,8 +382,6 @@ def setgeo(rundata): refinement_data = rundata.refinement_data refinement_data.variable_dt_refinement_ratios = True refinement_data.wave_tolerance = 1.e-1 - refinement_data.deep_depth = 1e2 - refinement_data.max_level_deep = 3 # == settopo.data values == topo_data = rundata.topo_data @@ -405,13 +403,6 @@ def setgeo(rundata): # [fname] rundata.qinit_data.qinitfiles.append(['hump.xyz']) - - # == setfixedgrids.data values == - fixed_grids = rundata.fixed_grid_data - # for fixed grids append lines of the form - # [t1,t2,noutput,x1,x2,y1,y2,xpoints,ypoints,\ - # ioutarrivaltimes,ioutsurfacemax] - return rundata # end of function setgeo # ---------------------- diff --git a/tests/chile2010_adjoint/setrun.py b/tests/chile2010_adjoint/setrun.py index e4d246c90..c63bcdda6 100644 --- a/tests/chile2010_adjoint/setrun.py +++ b/tests/chile2010_adjoint/setrun.py @@ -430,8 +430,6 @@ def setgeo(rundata): refinement_data = rundata.refinement_data refinement_data.variable_dt_refinement_ratios = True refinement_data.wave_tolerance = 1.e-1 # not used for adjoint flagging - refinement_data.deep_depth = 1e2 - refinement_data.max_level_deep = 3 # == settopo.data values == topo_data = rundata.topo_data @@ -455,12 +453,6 @@ def setgeo(rundata): # for qinit perturbations, append lines of the form: (<= 1 allowed for now!) # [minlev, maxlev, fname] - # == setfixedgrids.data values == - fixed_grids = rundata.fixed_grid_data - # for fixed grids append lines of the form - # [t1,t2,noutput,x1,x2,y1,y2,xpoints,ypoints,\ - # ioutarrivaltimes,ioutsurfacemax] - return rundata # end of function setgeo # ---------------------- diff --git a/tests/chile2010_adjoint/regression_tests.py b/tests/chile2010_adjoint/test_chile2010_adjoint.py similarity index 84% rename from tests/chile2010_adjoint/regression_tests.py rename to tests/chile2010_adjoint/test_chile2010_adjoint.py index 934c03466..3b6a980d7 100644 --- a/tests/chile2010_adjoint/regression_tests.py +++ b/tests/chile2010_adjoint/test_chile2010_adjoint.py @@ -16,8 +16,6 @@ import clawpack.geoclaw.test as test import clawpack.geoclaw.topotools as topotools -from clawpack.clawutil.test import wip - try: CLAW = os.environ['CLAW'] @@ -49,23 +47,16 @@ def setUp(self): # run adjoint code os.chdir(temp_adjoint_path) - #print('+++ Running adjoint in directory ',os.getcwd()) - #print('+++ contents: ', os.listdir('.')) os.system('make -s topo') os.system('make -s data') os.system('make -s new') os.system('make .output > output.txt') - #print('+++ contents of _output: ', os.listdir('_output')) # set up forward code shutil.copy(os.path.join(self.test_path, "maketopo.py"), self.temp_path) os.chdir(self.temp_path) - #print('+++ Running forward in directory ',os.getcwd()) - #print('+++ contents: ', os.listdir()) os.system('python maketopo.py') - #print('+++ scratch directory: ', scratch_dir) - #print('+++ contents of scratch: ', os.listdir(scratch_dir)) os.chdir(start_dir) diff --git a/tests/dtopo1/__init__.py b/tests/dtopo1/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/tests/dtopo1/setrun.py b/tests/dtopo1/setrun.py index 906af6574..0cbc8491c 100644 --- a/tests/dtopo1/setrun.py +++ b/tests/dtopo1/setrun.py @@ -375,8 +375,6 @@ def setgeo(rundata): # Refinement data refinement_data = rundata.refinement_data refinement_data.wave_tolerance = 1.e-2 - refinement_data.deep_depth = 1e2 - refinement_data.max_level_deep = 3 refinement_data.variable_dt_refinement_ratios = True # == settopo.data values == @@ -401,12 +399,6 @@ def setgeo(rundata): # for qinit perturbations, append lines of the form: (<= 1 allowed for now!) # [fname] - # == setfixedgrids.data values == - fixedgrids = rundata.fixed_grid_data - # for fixed grids append lines of the form - # [t1,t2,noutput,x1,x2,y1,y2,xpoints,ypoints,\ - # ioutarrivaltimes,ioutsurfacemax] - return rundata # end of function setgeo # ---------------------- diff --git a/tests/dtopo1/regression_tests.py b/tests/dtopo1/test_dtopo.py similarity index 100% rename from tests/dtopo1/regression_tests.py rename to tests/dtopo1/test_dtopo.py diff --git a/tests/multilayer/__init__.py b/tests/multilayer/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/tests/multilayer/setplot.py b/tests/multilayer/setplot.py index eee13adeb..2f45e2966 100644 --- a/tests/multilayer/setplot.py +++ b/tests/multilayer/setplot.py @@ -82,17 +82,6 @@ def transform_p2c(x, y, x0, y0, theta): def pcolor_afteraxes(current_data): bathy_ref_lines(current_data) - def contour_afteraxes(current_data): - axes = plt.gca() - pos = -80.0 * (23e3 / 180) + 500e3 - 5e3 - axes.plot([pos, pos], [-300e3, 300e3], 'b', - [pos-5e3, pos-5e3], [-300e3, 300e3], 'y') - wind_contours(current_data) - bathy_ref_lines(current_data) - - def profile_afteraxes(current_data): - pass - def bathy_ref_lines(current_data): axes = plt.gca() for ref_line in ref_lines: @@ -128,8 +117,6 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.afteraxes = pcolor_afteraxes ml_plot.add_surface_elevation(plotaxes,1,bounds=top_surface_limits) - # ml_plot.add_surface_elevation(plotaxes,1,bounds=[-0.06,0.06]) - # ml_plot.add_surface_elevation(plotaxes,1) ml_plot.add_land(plotaxes, 1) # Bottom surface @@ -140,38 +127,7 @@ def bathy_ref_lines(current_data): plotaxes.xlimits = xlimits plotaxes.ylimits = ylimits plotaxes.afteraxes = pcolor_afteraxes - # ml_plot.add_surface_elevation(plotaxes,2,bounds=[-300-0.5,-300+0.5]) ml_plot.add_surface_elevation(plotaxes,2,bounds=internal_surface_limits) - # ml_plot.add_surface_elevation(plotaxes,2) - ml_plot.add_land(plotaxes, 2) - - # ======================================================================== - # Depths - # ======================================================================== - plotfigure = plotdata.new_plotfigure(name='Depths', figno=42) - plotfigure.show = False - plotfigure.kwargs = {'figsize':(14,4)} - - # Top surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Top Layer Depth' - plotaxes.axescmd = 'subplot(1,2,1)' - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.afteraxes = pcolor_afteraxes - ml_plot.add_layer_depth(plotaxes,1,bounds=[-0.1,1.1]) - ml_plot.add_land(plotaxes, 1) - - # Bottom surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Bottom Layer Depth' - plotaxes.axescmd = 'subplot(1,2,2)' - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.afteraxes = pcolor_afteraxes - ml_plot.add_layer_depth(plotaxes,2,bounds=[-0.1,0.7]) ml_plot.add_land(plotaxes, 2) # ======================================================================== @@ -199,233 +155,8 @@ def bathy_ref_lines(current_data): plotaxes.ylimits = ylimits plotaxes.axescmd = 'subplot(1,2,2)' plotaxes.afteraxes = pcolor_afteraxes - # add_speed(plotaxes,2,bounds=[0.0,1e-10]) ml_plot.add_speed(plotaxes,2,bounds=internal_speed_limits) - # add_speed(plotaxes,2) - ml_plot.add_land(plotaxes, 2) - - # Individual components - plotfigure = plotdata.new_plotfigure(name='speed_components',figno=401) - plotfigure.show = False - plotfigure.kwargs = {'figsize':(14,14)} - - # Top layer - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = "X-Velocity - Top Layer" - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.axescmd = 'subplot(2,2,1)' - plotaxes.afteraxes = pcolor_afteraxes - # add_x_velocity(plotaxes,1,bounds=[-1e-10,1e-10]) - ml_plot.add_x_velocity(plotaxes,1) - ml_plot.add_land(plotaxes, 1) - - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = "Y-Velocity - Top Layer" - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.axescmd = 'subplot(2,2,2)' - plotaxes.afteraxes = pcolor_afteraxes - # add_y_velocity(plotaxes,1,bounds=[-0.000125,0.000125]) - ml_plot.add_y_velocity(plotaxes,1) - ml_plot.add_land(plotaxes, 1) - - # Bottom layer - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = "X-Velocity - Bottom Layer" - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.axescmd = 'subplot(2,2,3)' - plotaxes.afteraxes = pcolor_afteraxes - # add_x_velocity(plotaxes,2,bounds=[-1e-10,1e-10]) - ml_plot.add_x_velocity(plotaxes,2) - ml_plot.add_land(plotaxes, 2) - - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = "Y-Velocity - Bottom Layer" - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.axescmd = 'subplot(2,2,4)' - plotaxes.afteraxes = pcolor_afteraxes - # add_y_velocity(plotaxes,2,bounds=[-0.8e-6,.8e-6]) - ml_plot.add_y_velocity(plotaxes,2) - ml_plot.add_land(plotaxes, 2) - # ======================================================================== - # Profile Plots - # Note that these are not currently plotted by default - set - # `plotfigure.show = True` is you want this to be plotted - plotfigure = plotdata.new_plotfigure(name='profile') - plotfigure.show = False - - # Top surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.xlimits = xlimits - plotaxes.ylimits = [-1.1, 0.1] - plotaxes.title = "Profile of depth" - plotaxes.afteraxes = profile_afteraxes - - slice_index = 30 - - # Internal surface - def bathy_profile(current_data): - return current_data.x[:, slice_index], b(current_data)[:, slice_index] - - def lower_surface(current_data): - if multilayer_data.init_type == 2: - return current_data.x[:, slice_index], \ - eta2(current_data)[:, slice_index] - elif multilayer_data.init_type == 6: - return current_data.y[slice_index, :], \ - eta2(current_data)[slice_index, :] - - def upper_surface(current_data): - if multilayer_data.init_type == 2: - return current_data.x[:, slice_index], \ - eta1(current_data)[:, slice_index] - elif multilayer_data.init_type == 6: - return current_data.y[slice_index, :], \ - eta1(current_data)[slice_index, :] - - def top_speed(current_data): - if multilayer_data.init_type == 2: - return current_data.x[:, slice_index], \ - water_u1(current_data)[:, slice_index] - elif multilayer_data.init_type == 6: - return current_data.y[slice_index, :], \ - water_u1(current_data)[slice_index, :] - - def bottom_speed(current_data): - if multilayer_data.init_type == 2: - return current_data.x[:, slice_index], \ - water_u2(current_data)[:, slice_index] - elif multilayer_data.init_type == 6: - return current_data.y[slice_index, :], \ - water_u2(current_data)[slice_index, :] - - # Bathy - plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') - plotitem.map_2d_to_1d = bathy_profile - plotitem.plot_var = 0 - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.color = 'k' - plotitem.show = True - - # Internal Interface - plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') - plotitem.map_2d_to_1d = lower_surface - plotitem.plot_var = 7 - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.color = 'b' - plotitem.show = True - - # Upper Interface - plotitem = plotaxes.new_plotitem(plot_type='1d_from_2d_data') - plotitem.map_2d_to_1d = upper_surface - plotitem.plot_var = 6 - plotitem.amr_plotstyle = ['-', '+', 'x'] - plotitem.color = (0.2, 0.8, 1.0) - plotitem.show = True - - # Set up for axes in this figure: - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Y-Velocity' - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.afteraxes = pcolor_afteraxes - - # Water - # plotitem = plotaxes.new_plotitem(plot_type='2d_pcolor') - # # plotitem.plot_var = geoplot.surface - # plotitem.plot_var = water_v - # plotitem.pcolor_cmap = colormaps.make_colormap({1.0:'r',0.5:'w',0.0:'b'}) - # # plotitem.pcolor_cmin = -1.e-10 - # # plotitem.pcolor_cmax = 1.e-10 - # # plotitem.pcolor_cmin = -2.5 # -3.0 - # # plotitem.pcolor_cmax = 2.5 # 3.0 - # plotitem.add_colorbar = True - # plotitem.amr_celledges_show = [0,0,0] - # plotitem.amr_patchedges_show = [1,1,1] - - # Land - ml_plot.add_land(plotaxes, 1) - - # ======================================================================== - # Contour plot for surface - # ======================================================================== - plotfigure = plotdata.new_plotfigure(name='contour_surface',figno=15) - plotfigure.show = False - plotfigure.kwargs = {'figsize':(14,4)} - - # Set up for axes in this figure: - - # Top Surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Top Surface' - plotaxes.axescmd = 'subplot(1,2,1)' - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.afteraxes = contour_afteraxes - ml_plot.add_surface_elevation(plotaxes,plot_type='contour',surface=1,bounds=[-2.5,-1.5,-0.5,0.5,1.5,2.5]) - ml_plot.add_land(plotaxes, 1, plot_type='contour') - - # Internal Surface - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Internal Surface' - plotaxes.axescmd = 'subplot(1,2,2)' - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.afteraxes = contour_afteraxes - ml_plot.add_surface_elevation(plotaxes,plot_type='contour',surface=2,bounds=[-2.5,-1.5,-0.5,0.5,1.5,2.5]) - ml_plot.add_land(plotaxes, 2, plot_type='contour') - - # ======================================================================== - # Contour plot for speed - # ======================================================================== - plotfigure = plotdata.new_plotfigure(name='contour_speed',figno=16) - plotfigure.show = False - plotfigure.kwargs = {'figsize':(14,4)} - - # Set up for axes in this figure: - plotaxes = plotfigure.new_plotaxes() - plotaxes.title = 'Current' - plotaxes.scaled = True - plotaxes.xlimits = xlimits - plotaxes.ylimits = ylimits - plotaxes.afteraxes = contour_afteraxes - - # Surface - plotitem = plotaxes.new_plotitem(plot_type='2d_contour') - plotitem.plot_var = ml_plot.water_speed_depth_ave - plotitem.kwargs = {'linewidths':1} - # plotitem.contour_levels = [1.0,2.0,3.0,4.0,5.0,6.0] - plotitem.contour_levels = [0.5,1.5,3,4.5,6.0] - plotitem.amr_contour_show = [1,1,1] - plotitem.amr_celledges_show = [0,0,0] - plotitem.amr_patchedges_show = [1,1,1] - plotitem.amr_contour_colors = 'k' - # plotitem.amr_contour_colors = ['r','k','b'] # color on each level - # plotitem.amr_grid_bgcolor = ['#ffeeee', '#eeeeff', '#eeffee'] - plotitem.show = True - - # Land - plotitem = plotaxes.new_plotitem(plot_type='2d_contour') - plotitem.plot_var = geoplot.land - plotitem.contour_nlevels = 40 - plotitem.contour_min = 0.0 - plotitem.contour_max = 100.0 - plotitem.amr_contour_colors = ['g'] # color on each level - plotitem.amr_patch_bgcolor = ['#ffeeee', '#eeeeff', '#eeffee'] - plotitem.amr_celledges_show = 0 - plotitem.amr_patchedges_show = 0 - plotitem.show = True # ======================================================================== # Grid Cells @@ -446,40 +177,6 @@ def bottom_speed(current_data): plotitem.amr_patch_bgcolor = ['#ffeeee', '#eeeeff', '#eeffee'] plotitem.amr_celledges_show = [1,1,1] plotitem.amr_patchedges_show = [1,1,1] - - # ======================================================================== - # Vorticity Plot - # ======================================================================== - # plotfigure = plotdata.new_plotfigure(name='vorticity',figno=17) - # plotfigure.show = False - # plotaxes = plotfigure.new_plotaxes() - # plotaxes.title = "Vorticity" - # plotaxes.scaled = True - # plotaxes.xlimits = xlimits - # plotaxes.ylimits = ylimits - # plotaxes.afteraxes = pcolor_afteraxes - # - # # Vorticity - # plotitem = plotaxes.new_plotitem(plot_type='2d_imshow') - # plotitem.plot_var = 9 - # plotitem.imshow_cmap = plt.get_cmap('PRGn') - # # plotitem.pcolor_cmap = plt.get_cmap('PuBu') - # # plotitem.pcolor_cmin = 0.0 - # # plotitem.pcolor_cmax = 6.0 - # plotitem.imshow_cmin = -1.e-2 - # plotitem.imshow_cmax = 1.e-2 - # plotitem.add_colorbar = True - # plotitem.amr_celledges_show = [0,0,0] - # plotitem.amr_patchedges_show = [1] - # - # # Land - # plotitem = plotaxes.new_plotitem(plot_type='2d_pcolor') - # plotitem.plot_var = geoplot.land - # plotitem.pcolor_cmap = geoplot.land_colors - # plotitem.pcolor_cmin = 0.0 - # plotitem.pcolor_cmax = 80.0 - # plotitem.add_colorbar = False - # plotitem.amr_celledges_show = [0,0,0] # ======================================================================== # Figures for gauges diff --git a/tests/multilayer/setrun.py b/tests/multilayer/setrun.py index 472cf02d8..226a506d8 100644 --- a/tests/multilayer/setrun.py +++ b/tests/multilayer/setrun.py @@ -448,14 +448,12 @@ def setgeo(rundata): refinement_data = rundata.refinement_data refinement_data.variable_dt_refinement_ratios = True refinement_data.wave_tolerance = 1.e-1 - refinement_data.deep_depth = 1e2 - refinement_data.max_level_deep = 3 # == settopo.data values == topo_data = rundata.topo_data # for topography, append lines of the form # [topotype, minlevel, maxlevel, t1, t2, fname] - topo_data.topofiles.append([2, 1, 5, 0.0, 1e10, 'jump_topo.topotype2']) + topo_data.topofiles.append([2, 'jump_topo.topotype2']) # == setdtopo.data values == dtopo_data = rundata.dtopo_data diff --git a/tests/multilayer/regression_tests.py b/tests/multilayer/test_multilayer.py similarity index 100% rename from tests/multilayer/regression_tests.py rename to tests/multilayer/test_multilayer.py diff --git a/tests/netcdf_topo/Makefile b/tests/netcdf_topo/Makefile index 11cccb22f..c06dfd918 100644 --- a/tests/netcdf_topo/Makefile +++ b/tests/netcdf_topo/Makefile @@ -23,8 +23,8 @@ RESTART = False # Environment variable FC should be set to fortran compiler, e.g. gfortran # Compiler flags can be specified here or set as an environment variable -FFLAGS += -DNETCDF -lnetcdf -I$(NETCDF4_DIR)/include -L$(NETCDF4_DIR)/lib -LFLAGS += $(FFLAGS) -lnetcdff +FFLAGS += -DNETCDF $(shell nf-config --fflags) +LFLAGS += $(FFLAGS) -L$(shell nc-config --libdir) $(shell nf-config --flibs) # --------------------------------- @@ -66,4 +66,4 @@ include $(CLAWMAKE) .PHONY: netcdf_test netcdf_test: netcdf_test.f90 - $(FC) netcdf_test.f90 $(FFLAGS) $(LFLAGS) -o netcdf_test \ No newline at end of file + $(shell nf-config --fc) netcdf_test.f90 $(FFLAGS) $(LFLAGS) -o netcdf_test \ No newline at end of file diff --git a/tests/netcdf_topo/__init__.py b/tests/netcdf_topo/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/tests/netcdf_topo/setrun.py b/tests/netcdf_topo/setrun.py index 88a1d8b93..adb08e904 100644 --- a/tests/netcdf_topo/setrun.py +++ b/tests/netcdf_topo/setrun.py @@ -357,15 +357,13 @@ def setgeo(rundata): # Refinement data refinement_data = rundata.refinement_data refinement_data.wave_tolerance = 1.e-2 - refinement_data.deep_depth = 1e2 - refinement_data.max_level_deep = 3 refinement_data.variable_dt_refinement_ratios = True # == settopo.data values == topo_data = rundata.topo_data # for topography, append lines of the form # [topotype, minlevel, maxlevel, t1, t2, fname] - topo_data.topofiles.append([4, 1, 10, 0., 1.e10, 'bowl.nc']) + topo_data.topofiles.append([4, 'bowl.nc']) # topo_data.topofiles.append([2, 1, 10, 0., 1.e10, 'bowl.tt2']) # == setdtopo.data values == @@ -378,12 +376,6 @@ def setgeo(rundata): rundata.qinit_data.qinitfiles = [] # for qinit perturbations, append lines of the form: (<= 1 allowed for now!) # [minlev, maxlev, fname] - - # == setfixedgrids.data values == - fixedgrids = rundata.fixed_grid_data - # for fixed grids append lines of the form - # [t1,t2,noutput,x1,x2,y1,y2,xpoints,ypoints,\ - # ioutarrivaltimes,ioutsurfacemax] # == fgmax.data values == fgmax_files = rundata.fgmax_data.fgmax_files diff --git a/tests/netcdf_topo/regression_tests.py b/tests/netcdf_topo/test_netcdf.py similarity index 91% rename from tests/netcdf_topo/regression_tests.py rename to tests/netcdf_topo/test_netcdf.py index e8c54ca24..f26eda5a4 100644 --- a/tests/netcdf_topo/regression_tests.py +++ b/tests/netcdf_topo/test_netcdf.py @@ -17,7 +17,7 @@ import numpy import xarray as xr -import nose +import pytest import clawpack.geoclaw.test as test import clawpack.geoclaw.topotools as topotools @@ -35,6 +35,8 @@ def __init__(self, methodName="runTest"): def setUp(self): + netCDF4 = pytest.importorskip("netCDF4", reason=build_failure_str) + self.temp_path = tempfile.mkdtemp() self.stdout = open(os.path.join(self.temp_path, "run_output.txt"), "w") @@ -74,10 +76,9 @@ def setUp(self): topo.x = numpy.linspace(-3.1, 3.1, 310) topo.y = numpy.linspace(-3.5,2.5, 300) - try: - import netCDF4 - this_path = os.path.join(self.temp_path, 'bowl.nc') + this_path = os.path.join(self.temp_path, 'bowl.nc') + try: # now mess with the order of the dimension IDs (lat, then lon) with netCDF4.Dataset(this_path,'w') as out: lat = out.createDimension('lat',len(topo.y)) @@ -91,18 +92,13 @@ def setUp(self): longitudes[:] = topo.x elevations[:] = topo.Z - - except ImportError: - # Assume that NetCDF is not installed and move on - raise nose.SkipTest(build_failure_str) - except RuntimeError as e: - print(e.message) - raise nose.SkipTest("NetCDF topography test skipped due to " + - "runtime failure.") + pytest.skip(("NetCDF topography test skipped due to runtime failure.")) + raise e else: self.build_executable() + def build_executable(self): try: self.stdout.write("Teting NetCDF output:\n") @@ -110,10 +106,10 @@ def build_executable(self): stdout=self.stdout, stderr=self.stderr, shell=True) - except subprocess.CalledProcessError: - + except subprocess.CalledProcessError as e: self.stdout.write(build_failure_str) - raise nose.SkipTest(build_failure_str) + pytest.skip(build_failure_str) + raise e else: # Force recompilation of topo_module to add NetCDF flags diff --git a/tests/old_topotools.py b/tests/old_topotools.py index fd3dbad42..5ff4cd035 100644 --- a/tests/old_topotools.py +++ b/tests/old_topotools.py @@ -3,8 +3,6 @@ import numpy import re -import nose - def topo1writer(outfile, topo, xlower, xupper, ylower, yupper, nxpoints, nypoints): fout=open(outfile, 'w') diff --git a/tests/particles/setrun.py b/tests/particles/setrun.py index 9f5852dfd..8b51c56f7 100644 --- a/tests/particles/setrun.py +++ b/tests/particles/setrun.py @@ -392,11 +392,6 @@ def setgeo(rundata): # [fname] rundata.qinit_data.qinitfiles.append(['qinit.xyz']) - # == setfixedgrids.data values == - fixedgrids = rundata.fixed_grid_data.fixedgrids - # for fixed grids append lines of the form - # [t1,t2,noutput,x1,x2,y1,y2,xpoints,ypoints,\ - # ioutarrivaltimes,ioutsurfacemax] return rundata # end of function setgeo diff --git a/tests/particles/regression_tests.py b/tests/particles/test_particles.py similarity index 100% rename from tests/particles/regression_tests.py rename to tests/particles/test_particles.py diff --git a/tests/storm_surge/__init__.py b/tests/storm_surge/__init__.py deleted file mode 100644 index e69de29bb..000000000 diff --git a/tests/storm_surge/setrun.py b/tests/storm_surge/setrun.py index 24fb6dd9f..c148c4ac9 100644 --- a/tests/storm_surge/setrun.py +++ b/tests/storm_surge/setrun.py @@ -384,8 +384,6 @@ def setgeo(rundata): refine_data = rundata.refinement_data refine_data.wave_tolerance = 1.0 refine_data.speed_tolerance = [1.0,2.0,3.0,4.0] - refine_data.deep_depth = 300.0 - refine_data.max_level_deep = 4 refine_data.variable_dt_refinement_ratios = True # == settopo.data values == @@ -395,8 +393,8 @@ def setgeo(rundata): # [topotype, minlevel, maxlevel, t1, t2, fname] # See regions for control over these regions, need better bathy data for the # smaller domains - topo_data.topofiles.append([3, 1, 5, rundata.clawdata.t0, rundata.clawdata.tfinal, - 'gulf_caribbean.tt3']) + topo_data.topofiles.append([3, 'gulf_caribbean.tt3']) + # == setdtopo.data values == dtopo_data = rundata.dtopo_data dtopo_data.dtopofiles = [] @@ -409,12 +407,6 @@ def setgeo(rundata): # for qinit perturbations, append lines of the form: (<= 1 allowed for now!) # [minlev, maxlev, fname] - # == setfixedgrids.data values == - rundata.fixed_grid_data.fixedgrids = [] - # for fixed grids append lines of the form - # [t1,t2,noutput,x1,x2,y1,y2,xpoints,ypoints,\ - # ioutarrivaltimes,ioutsurfacemax] - return rundata # end of function setgeo # ---------------------- diff --git a/tests/storm_surge/regression_tests.py b/tests/storm_surge/test_ike.py similarity index 56% rename from tests/storm_surge/regression_tests.py rename to tests/storm_surge/test_ike.py index ac7ae66a9..52a9edff7 100644 --- a/tests/storm_surge/regression_tests.py +++ b/tests/storm_surge/test_ike.py @@ -2,27 +2,22 @@ """Regression test for GeoClaw's storm surge functionality""" -from __future__ import absolute_import import sys import os import unittest +import pytest import gzip -import nose - -try: - # For Python 3.0 and later - from urllib.error import URLError -except ImportError: - # Fall back to Python 2's urllib2 - from urllib2 import URLError +import urllib.error +import pytest import numpy -import clawpack.geoclaw.test as test +import clawpack.geoclaw.test import clawpack.geoclaw.topotools +import clawpack.clawutil from clawpack.geoclaw.surge import storm -class IkeTest(test.GeoClawRegressionTest): +class IkeTest(clawpack.geoclaw.test.GeoClawRegressionTest): r"""Hurricane Ike regression test""" @@ -34,8 +29,9 @@ def setUp(self): remote_url = "http://ftp.nhc.noaa.gov/atcf/archive/2008/bal092008.dat.gz" try: path = self.get_remote_file(remote_url, unpack=False) - except URLError: - raise nose.SkipTest("Could not fetch remote file, skipping test.") + except urllib.error.URLError as e: + pytest.skip("Could not fetch remote file, skipping test.") + raise e storm_path = os.path.join(os.path.dirname(path), 'ike.storm') @@ -51,8 +47,8 @@ def setUp(self): ike_storm.write(storm_path) # Download file - #self.get_remote_file( - # "http://www.columbia.edu/~ktm2132/bathy/gulf_caribbean.tt3.tar.bz2") + # clawpack.clawutil.data.get_remote_file( + # "https://depts.washington.edu/clawpack/geoclaw/topo/gulf_caribbean.tt3.tar.bz2") # Create synthetic bathymetry - needs more work topo = clawpack.geoclaw.topotools.Topography() @@ -63,7 +59,7 @@ def setUp(self): topo_type=2, Z_format="%22.15e") - def runTest(self, save=False, indices=(2, 3)): + def runTest(self, save=False, indices=range(4)): r"""Storm Surge Regression Test :Input: @@ -89,39 +85,6 @@ def runTest(self, save=False, indices=(2, 3)): self.success = True - # def check_gauges(self, save=False, indices=(2, 3)): - # r"""Basic test to assert gauge equality - - # :Input: - # - *save* (bool) - If *True* will save the output from this test to - # the file *regresion_data.txt*. Default is *False*. - # - *indices* (tuple) - Contains indices to compare in the gague - # comparison. Defaults to *(2, 3)*. - # """ - - # # Get gauge data - # data = numpy.loadtxt(os.path.join(self.temp_path, 'fort.gauge')) - # data_sum = [] - # for index in indices: - # data_sum.append(data[:, index].sum()) - - # # Get (and save) regression comparison data - # regression_data_file = os.path.join(self.test_path, "regression_data.txt") - # if save: - # numpy.savetxt(regression_data_file, data) - # regression_data = numpy.loadtxt(regression_data_file) - # regression_sum = [] - # for index in indices: - # regression_sum.append(regression_data[:, index].sum()) - # # regression_sum = regression_data - - # # Compare data - # tolerance = 1e-14 - # assert numpy.allclose(data_sum, regression_sum, tolerance), \ - # "\n data: %s, \n expected: %s" % (data_sum, regression_sum) - # # assert numpy.allclose(data, regression_data, tolerance), \ - # # "Full gauge match failed." - if __name__=="__main__": if len(sys.argv) > 1: if bool(sys.argv[1]): diff --git a/tests/test_dtopotools.py b/tests/test_dtopotools.py index cef88420b..c565e6d7e 100644 --- a/tests/test_dtopotools.py +++ b/tests/test_dtopotools.py @@ -8,7 +8,7 @@ import time import numpy -import nose +import pytest import clawpack.geoclaw.dtopotools as dtopotools @@ -220,8 +220,9 @@ def test_dtopo_io(): except AssertionError as e: test_dump_path = os.path.join(os.getcwd(), "test_dtopo_io") - shutil.mkdir(test_dump_path) - shutil.copy(temp_path, test_dump_path) + if os.path.exists(test_dump_path): + shutil.rmtree(test_dump_path) + shutil.copytree(temp_path, test_dump_path) raise e finally: shutil.rmtree(temp_path) @@ -284,7 +285,7 @@ def test_geometry(): def test_vs_old_dtopo(): r"""Test new dtopotools with old version from 5.2""" - raise nose.SkipTest("Skipping comparison with old tools.") + pytest.skip("Skipping comparison with old tools.") from . import old_dtopotools @@ -469,13 +470,12 @@ def test_subdivided_plane_fault(verbose=False, plot=False): pass elif bool(sys.argv[1]): save = True - try: - test_read_csv_make_dtopo(save=save) - test_read_ucsb_make_dtopo(save=save) - test_read_sift_make_dtopo(save=save) - test_SubdividedPlaneFault_make_dtopo(save=save) - test_dtopo_io() - test_geometry() - test_vs_old_dtopo() - except nose.SkipTest as e: - print(e.message) + + test_read_csv_make_dtopo(save=save) + test_read_ucsb_make_dtopo(save=save) + test_read_sift_make_dtopo(save=save) + test_SubdividedPlaneFault_make_dtopo(save=save) + test_dtopo_io() + test_geometry() + test_vs_old_dtopo() + \ No newline at end of file diff --git a/tests/test_etopo1.py b/tests/test_etopo1.py index c8e588919..bbe0e8212 100644 --- a/tests/test_etopo1.py +++ b/tests/test_etopo1.py @@ -1,11 +1,10 @@ #!/usr/bin/env python -from __future__ import print_function import os import numpy -import nose -import os +import pytest import warnings + from clawpack.geoclaw import topotools @@ -18,10 +17,7 @@ def test_etopo1_topo(make_plot=False, save=False): - try: - import netCDF4 - except ImportError: - raise nose.SkipTest("netCDF4 not installed, skipping test") + netCDF4 = pytest.importorskip('netCDF4', reason="netCDF4 not installed, skipping test") try: topo1 = topotools.read_netcdf('etopo1', extent=extent, verbose=True) @@ -29,7 +25,8 @@ def test_etopo1_topo(make_plot=False, save=False): coarsen=10, verbose=True) except (OSError, RuntimeError): warnings.warn('Could not read etopo1 data, check if thredds server up') - raise nose.SkipTest("Reading etopo1 failed, skipping test") + pytest.skip("Reading etopo1 failed, skipping test") + # raise nose.SkipTest("Reading etopo1 failed, skipping test") testdata_path = os.path.join(os.path.dirname(__file__), 'data', 'etopo1_10min.asc') if save: @@ -57,10 +54,8 @@ def test_etopo1_topo(make_plot=False, save=False): def test_etopo1_xarray(): - try: - import xarray - except ImportError: - raise nose.SkipTest("xarray not installed, skipping test") + xarray = pytest.importorskip("xarray", + reason="xarray not installed, skipping test") try: topo10,topo10_xarray = topotools.read_netcdf('etopo1', extent=extent, @@ -68,7 +63,7 @@ def test_etopo1_xarray(): coarsen=10, verbose=True) except (OSError, RuntimeError): warnings.warn('Could not read etopo1 data, check if thredds server up') - raise nose.SkipTest("Reading etopo1 failed, skipping test") + pytest.skip("Reading etopo1 failed, skipping test") testdata_path = os.path.join(testdir, 'data', 'etopo1_10min.asc') topo10input = topotools.Topography() @@ -86,8 +81,6 @@ def test_etopo1_xarray(): elif bool(sys.argv[1]): test_etopo1_topo(save=True) else: - # Run tests test_etopo1_topo() test_etopo1_xarray() - print("All tests passed.") diff --git a/tests/test_storm.py b/tests/test_storm.py index 1099bbc61..2ee368513 100644 --- a/tests/test_storm.py +++ b/tests/test_storm.py @@ -11,6 +11,7 @@ import os import sys import datetime +import pytest import numpy @@ -43,6 +44,7 @@ def check_geoclaw(paths, check_header=False): """ if check_header: + data_file = [None, None] with open(paths[0], 'r') as data_file[0], open(paths[1], 'r') as data_file[1]: # Check for number of lines assert(int(data_file[0].readline()) == int(data_file[1].readline())) @@ -93,22 +95,16 @@ def test_storm_IO(save=False): for file_format in file_format_tests: if file_format=='ibtracs': file_suffix = 'nc' - # Check here to see if we have xarray - try: - import xarray - except ImportError as e: - print("Skipping IBTrACS IO test, missing xarray.") - continue + xarray = pytest.importorskip("xarray", + reason="Skipping IBTrACS IO test, missing xarray.") + pytest.skip("IBTrACS test skipped.") elif file_format == 'atcf': file_suffix = 'txt' - # Check here to see if we have pandas - try: - import pandas - except ImportError as e: - print("Skipping ATCF IO test, missing pandas.") - continue + pandas = pytest.importorskip("pandas", + reason="Skipping ATCF IO test, missing pandas.") else: file_suffix = 'txt' + input_path = os.path.join(testdir, "data", "storm", "%s.%s" % (file_format,file_suffix)) out_path = os.path.join(temp_path, '%s_geoclaw.txt' % file_format) check_path = os.path.join(testdir, "data", "storm", diff --git a/tests/test_topotools.py b/tests/test_topotools.py index b7b89aa9f..d050bc5df 100644 --- a/tests/test_topotools.py +++ b/tests/test_topotools.py @@ -4,18 +4,11 @@ import sys import tempfile import shutil - -try: - # For Python 3.0 and later - from urllib.error import URLError -except ImportError: - # Fall back to Python 2's urllib2 - from urllib2 import URLError +import pytest +import urllib.error import numpy -import nose - import clawpack.geoclaw.topotools as topotools import clawpack.clawutil.data @@ -200,9 +193,9 @@ def test_netcdf(): try: # Fetch comparison data - url = "".join(('https://raw.githubusercontent.com/rjleveque/geoclaw/', - '5f675256c043e59e5065f9f3b5bdd41c2901702c/src/python/', - 'geoclaw/tests/kahului_sample_1s.tt2')) + url = ('https://raw.githubusercontent.com/rjleveque/geoclaw/' + + '5f675256c043e59e5065f9f3b5bdd41c2901702c/src/python/' + + 'geoclaw/tests/kahului_sample_1s.tt2') clawpack.clawutil.data.get_remote_file(url, output_dir=temp_path, force=True) @@ -233,13 +226,14 @@ def test_netcdf(): raise e except ImportError as e: - raise nose.SkipTest("Skipping test since NetCDF support not found.") + pytest.skip("Skipping test since NetCDF support not found.") except RuntimeError as e: - raise nose.SkipTest("NetCDF topography test skipped due to " + - "runtime failure.") - except URLError: - raise nose.SkipTest("Could not fetch remote file, skipping test.") + pytest.skip("NetCDF topography test skipped due to " + + "runtime failure.") + + except urllib.error.URLError: + pytest.skip("Could not fetch remote file, skipping test.") finally: shutil.rmtree(temp_path) @@ -251,8 +245,8 @@ def test_get_remote_file(): temp_path = tempfile.mkdtemp() try: - url = "".join(('https://raw.githubusercontent.com/rjleveque/geoclaw/', - '5f675256c043e59e5065f9f3b5bdd41c2901702c/src/python/', + url = "".join(('https://raw.githubusercontent.com/rjleveque/geoclaw/' + + '5f675256c043e59e5065f9f3b5bdd41c2901702c/src/python/' + 'geoclaw/tests/kahului_sample_1s.tt2')) clawpack.clawutil.data.get_remote_file(url, output_dir=temp_path, force=True) @@ -269,8 +263,8 @@ def test_get_remote_file(): shutil.copy(local_path, os.path.join(os.getcwd(), "remote_file.tt2")) raise e - except URLError: - raise nose.SkipTest("Could not fetch remote file, skipping test.") + except urllib.error.URLError: + pytest.skip("Could not fetch remote file, skipping test.") finally: shutil.rmtree(temp_path) @@ -278,10 +272,8 @@ def test_get_remote_file(): def test_unstructured_topo(save=False, plot=False): - try: - import scipy - except: - raise nose.SkipTest("Skipping test since scipy not found") + scipy = pytest.importorskip('scipy', + reason="Skipping test since scipy not found") # Create random test data def func(x, y): @@ -340,10 +332,13 @@ def plot_topo_bowl_hill(): Note that center of bowl should be at (0,0). """ - try: - import matplotlib - except ImportError: - raise nose.SkipTest("Skipping test since matplotlib not found.") + matplotlib = pytest.importorskip('matplotlib', + reason="Skipping test since matplotlib not found.") + + # try: + # import matplotlib + # except ImportError: + # raise nose.SkipTest("Skipping test since matplotlib not found.") matplotlib.use("Agg") # use image backend -- needed for Travis tests import matplotlib.pyplot as plt @@ -357,14 +352,12 @@ def plot_topo_bowl_hill(): topo.plot() fname = "bowl_hill.png" plt.savefig(fname) - print("Created ",fname) topo2 = topo.crop([0.5, 1.5, 0., 2.]) topo2.plot() plt.title("Cropped topography") fname = "bowl_hill_crop.png" plt.savefig(fname) - print("Created ",fname) def plot_kahului(): @@ -377,10 +370,8 @@ def plot_kahului(): illustrate how to do a contour data of the data directly. """ - try: - import matplotlib - except ImportError: - raise nose.SkipTest("Skipping test since matplotlib not found.") + matplotlib = pytest.importorskip('matplotlib', + reason="Skipping test since matplotlib not found.") matplotlib.use("Agg") # use image backend -- needed for Travis tests import matplotlib.pyplot as plt @@ -393,7 +384,6 @@ def plot_kahului(): plt.title("Kahului Harbor at 1 second resolution") fname = "kahului_imshow.png" plt.savefig(fname) - print("Created ",fname) assert K.Z.shape == (46, 65), "*** K.Z is wrong shape" assert numpy.allclose(K.Z[:3,:3], \ @@ -422,7 +412,6 @@ def plot_kahului(): fontsize=12) fname = "kahului_contour.png" plt.savefig(fname) - print("Created ",fname) if __name__ == "__main__": @@ -442,5 +431,3 @@ def plot_kahului(): test_get_remote_file() test_unstructured_topo() test_netcdf() - - print("All tests passed.") diff --git a/tests/test_util.py b/tests/test_util.py index 6e72e69df..4c07cd7f0 100644 --- a/tests/test_util.py +++ b/tests/test_util.py @@ -5,7 +5,7 @@ import shutil import tempfile -from nose.tools import raises +import pytest import numpy as np import clawpack.geoclaw.util as util @@ -89,37 +89,37 @@ def test_api_error(self): d,w,p = fetch_noaa_tide_data(self.station, self.begin_date, self.end_date, cache_dir=cache_dir) assert d == None, '*** expected d == None' - - @raises(ValueError) + def test_date_time_range_mismatch(self): - cache_dir = os.path.join(self.temp_dir, - self.test_date_time_range_mismatch.__name__) - - # missing first two entries - water_level_response = \ - ('Date Time, Water Level, Sigma, O or I (for verified), F, R, L, Quality\n' - '2000-10-30 12:12,1.003,0.003,0,0,0,0,v\n' - '2000-10-30 12:18,1.004,0.004,0,0,0,0,v\n' - '2000-10-30 12:24,1.005,0.005,0,0,0,0,v\n') - - # missing last two entries - predictions_response = ('Date Time, Prediction\n' - '2000-10-30 12:00,1.101\n' - '2000-10-30 12:06,1.102\n' - '2000-10-30 12:12,1.103\n') - - # monkey patch urllib to return mock data - def mock_read_response(url): - if 'product=water_level' in url: - return water_level_response - if 'product=predictions' in url: - return predictions_response - raise AssertionError - self._monkey_patch_urlopen(mock_read_response) - - # should raise ValueError - fetch_noaa_tide_data(self.station, self.begin_date, self.end_date, - cache_dir=cache_dir) + with pytest.raises(ValueError): + cache_dir = os.path.join(self.temp_dir, + self.test_date_time_range_mismatch.__name__) + + # missing first two entries + water_level_response = \ + ('Date Time, Water Level, Sigma, O or I (for verified), F, R, L, Quality\n' + '2000-10-30 12:12,1.003,0.003,0,0,0,0,v\n' + '2000-10-30 12:18,1.004,0.004,0,0,0,0,v\n' + '2000-10-30 12:24,1.005,0.005,0,0,0,0,v\n') + + # missing last two entries + predictions_response = ('Date Time, Prediction\n' + '2000-10-30 12:00,1.101\n' + '2000-10-30 12:06,1.102\n' + '2000-10-30 12:12,1.103\n') + + # monkey patch urllib to return mock data + def mock_read_response(url): + if 'product=water_level' in url: + return water_level_response + if 'product=predictions' in url: + return predictions_response + raise AssertionError + self._monkey_patch_urlopen(mock_read_response) + + # should raise ValueError + fetch_noaa_tide_data(self.station, self.begin_date, self.end_date, + cache_dir=cache_dir) def test_missing_values(self): cache_dir = os.path.join(self.temp_dir,