Skip to content

Commit 90e2c28

Browse files
Merge pull request #139 from mhearne-usgs/countryfix
Countryfix
2 parents b84ae92 + 91724d5 commit 90e2c28

11 files changed

Lines changed: 486 additions & 103 deletions

bin/getcsv

Lines changed: 103 additions & 26 deletions
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,9 @@ import argparse
33
import sys
44

55
from libcomcat.search import search, count
6-
from libcomcat.utils import maketime
6+
from libcomcat.utils import (maketime, check_ccode,
7+
get_country_bounds, filter_by_country,
8+
BUFFER_DISTANCE_KM)
79
from libcomcat.dataframes import (get_detail_data_frame,
810
get_summary_data_frame)
911

@@ -97,6 +99,18 @@ def get_parser():
9799
metavar=('lonmin', 'lonmax', 'latmin', 'latmax'),
98100
dest='bounds', type=float, nargs=4,
99101
help=helpstr)
102+
103+
country_str = '''Specify three character country code and earthquakes
104+
from inside country polygon (50m resolution) will be returned. Earthquakes
105+
in the ocean likely will NOT be returned.'''
106+
parser.add_argument('--country', help=country_str)
107+
108+
buffer_str = '''Use in conjunction with --country. Specify a buffer in km
109+
around country border where events will be selected.
110+
'''
111+
parser.add_argument('--buffer', help=buffer_str,
112+
type=int, default=BUFFER_DISTANCE_KM)
113+
100114
helpstr = 'Search radius in KM (use instead of bounding box)'
101115
parser.add_argument('-r', '--radius', dest='radius',
102116
metavar=('lat', 'lon', 'rmax'),
@@ -180,10 +194,17 @@ def main():
180194
parser = get_parser()
181195
args = parser.parse_args()
182196

197+
tsum = (args.bounds is not None) + \
198+
(args.radius is not None) + (args.country is not None)
199+
if tsum != 1:
200+
print('Please specify a bounding box, radius, or country code.')
201+
sys.exit(1)
202+
183203
latitude = None
184204
longitude = None
185205
radiuskm = None
186206
lonmin = latmin = lonmax = latmax = None
207+
bounds = None
187208
if args.radius:
188209
latitude = args.radius[0]
189210
longitude = args.radius[1]
@@ -196,6 +217,17 @@ def main():
196217
lonmin -= 360
197218
else:
198219
lonmin, lonmax, latmin, latmax = None, None, None, None
220+
bounds = (lonmin, lonmax, latmin, latmax)
221+
222+
if args.country:
223+
ccode = args.country
224+
if not check_ccode(ccode):
225+
curl = 'https://en.wikipedia.org/wiki/ISO_3166-1_alpha-2'
226+
fmt = '%s is not a valid ISO 3166 country code. See %s for the list.'
227+
tpl = (ccode, curl)
228+
print(fmt % tpl)
229+
sys.exit(1)
230+
bounds = get_country_bounds(ccode, args.buffer) # this returns a list
199231

200232
minmag = 0.0
201233
maxmag = 9.9
@@ -204,7 +236,46 @@ def main():
204236
maxmag = args.magRange[1]
205237

206238
if args.getCount:
207-
nevents = count(starttime=args.startTime,
239+
if isinstance(bounds, tuple) or bounds is None:
240+
nevents = count(starttime=args.startTime,
241+
endtime=args.endTime,
242+
updatedafter=args.after,
243+
minlatitude=latmin,
244+
maxlatitude=latmax,
245+
minlongitude=lonmin,
246+
maxlongitude=lonmax,
247+
latitude=latitude,
248+
longitude=longitude,
249+
maxradiuskm=radiuskm,
250+
catalog=args.catalog,
251+
contributor=args.contributor,
252+
maxmagnitude=maxmag,
253+
minmagnitude=minmag,
254+
producttype=args.limitByProductType,
255+
verbose=args.verbose)
256+
else:
257+
for lonmin, lonmax, latmin, latmax in bounds:
258+
nevents = 0
259+
nevents += count(starttime=args.startTime,
260+
endtime=args.endTime,
261+
updatedafter=args.after,
262+
minlatitude=latmin,
263+
maxlatitude=latmax,
264+
minlongitude=lonmin,
265+
maxlongitude=lonmax,
266+
latitude=latitude,
267+
longitude=longitude,
268+
maxradiuskm=radiuskm,
269+
catalog=args.catalog,
270+
contributor=args.contributor,
271+
maxmagnitude=maxmag,
272+
minmagnitude=minmag,
273+
producttype=args.limitByProductType,
274+
verbose=args.verbose)
275+
print('There are %i events matching input criteria.' % nevents)
276+
sys.exit(0)
277+
if isinstance(bounds, tuple) or bounds is None:
278+
events = search(starttime=args.startTime,
208279
endtime=args.endTime,
209280
updatedafter=args.after,
210281
minlatitude=latmin,
@@ -219,31 +290,34 @@ def main():
219290
maxmagnitude=maxmag,
220291
minmagnitude=minmag,
221292
producttype=args.limitByProductType,
293+
host=args.host,
222294
verbose=args.verbose)
223-
print('There are %i events matching input criteria.' % nevents)
224-
sys.exit(0)
225-
226-
if args.bounds and args.radius:
227-
print('Please specify either a bounding box OR radius search.')
228-
sys.exit(1)
229-
230-
events = search(starttime=args.startTime,
231-
endtime=args.endTime,
232-
updatedafter=args.after,
233-
minlatitude=latmin,
234-
maxlatitude=latmax,
235-
minlongitude=lonmin,
236-
maxlongitude=lonmax,
237-
latitude=latitude,
238-
longitude=longitude,
239-
maxradiuskm=radiuskm,
240-
catalog=args.catalog,
241-
contributor=args.contributor,
242-
maxmagnitude=maxmag,
243-
minmagnitude=minmag,
244-
producttype=args.limitByProductType,
245-
host=args.host,
246-
verbose=args.verbose)
295+
else:
296+
events = []
297+
for i, tbounds in enumerate(bounds):
298+
lonmin, lonmax, latmin, latmax = tbounds
299+
if args.verbose:
300+
fmt = 'Checking bounds %i of %i for %s...\n'
301+
tpl = (i + 1, len(bounds), ccode)
302+
sys.stderr.write(fmt % tpl)
303+
tevents = search(starttime=args.startTime,
304+
endtime=args.endTime,
305+
updatedafter=args.after,
306+
minlatitude=latmin,
307+
maxlatitude=latmax,
308+
minlongitude=lonmin,
309+
maxlongitude=lonmax,
310+
latitude=latitude,
311+
longitude=longitude,
312+
maxradiuskm=radiuskm,
313+
catalog=args.catalog,
314+
contributor=args.contributor,
315+
maxmagnitude=maxmag,
316+
minmagnitude=minmag,
317+
producttype=args.limitByProductType,
318+
host=args.host,
319+
verbose=args.verbose)
320+
events += tevents
247321

248322
if not len(events):
249323
print('No events found matching your search criteria. Exiting.')
@@ -272,6 +346,9 @@ def main():
272346
col_list.remove(column)
273347
df = df[first_columns + col_list]
274348

349+
if args.country:
350+
df = filter_by_country(df, ccode, buffer_km=args.buffer)
351+
275352
if args.verbose:
276353
sys.stderr.write('Created table...saving %i records to %s.\n' %
277354
(len(df), args.filename))

bin/getproduct

Lines changed: 92 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -8,12 +8,20 @@ from datetime import datetime, timedelta
88

99
# local imports
1010
from libcomcat.search import search, get_event_by_id
11-
from libcomcat.utils import maketime, makedict
11+
from libcomcat.utils import (maketime, makedict, check_ccode,
12+
get_country_bounds, filter_by_country,
13+
BUFFER_DISTANCE_KM)
1214
from libcomcat.classes import VersionOption
1315

1416
# third party imports
1517
import numpy as np
1618
import pandas as pd
19+
from shapely.geometry import Point
20+
21+
22+
class MyFormatter(argparse.RawTextHelpFormatter,
23+
argparse.ArgumentDefaultsHelpFormatter):
24+
pass
1725

1826

1927
def _get_product_from_detail(detail, product, contents, folder,
@@ -91,7 +99,7 @@ def get_parser():
9199
%(prog)s finite-fault .mr -o ~/tmp/chile -b -76.509 -49.804 -67.72 -17.427 -s 2007-01-01 -e 2016-05-01 -m 6.5 9.9
92100
'''
93101
parser = argparse.ArgumentParser(
94-
description=desc, formatter_class=argparse.RawDescriptionHelpFormatter)
102+
description=desc, formatter_class=MyFormatter)
95103
# positional arguments
96104
parser.add_argument('product', metavar='PRODUCT',
97105
help='The name of the desired product (shakemap, dyfi, etc.)')
@@ -103,6 +111,18 @@ def get_parser():
103111
parser.add_argument('-b', '--bounds', metavar=('lonmin', 'lonmax', 'latmin', 'latmax'),
104112
dest='bounds', type=float, nargs=4,
105113
help='Bounds to constrain event search [lonmin lonmax latmin latmax]')
114+
115+
country_str = '''Specify three character country code and earthquakes
116+
from inside country polygon (50m resolution) will be returned. Earthquakes
117+
in the ocean likely will NOT be returned.'''
118+
parser.add_argument('--country', help=country_str)
119+
120+
buffer_str = '''Use in conjunction with --country. Specify a buffer in km
121+
around country border where events will be selected.
122+
'''
123+
parser.add_argument('--buffer', help=buffer_str,
124+
type=int, default=BUFFER_DISTANCE_KM)
125+
106126
parser.add_argument('-r', '--radius', dest='radius', metavar=('lat', 'lon', 'rmax'), type=float,
107127
nargs=3, help='Search radius in KM (use instead of bounding box)')
108128
parser.add_argument('-s', '--start-time', dest='startTime', type=maketime,
@@ -149,8 +169,10 @@ def main():
149169
args.source, list_only=args.list_only)
150170
sys.exit(0)
151171

152-
if args.bounds and args.radius:
153-
print('Please specify either a bounding box OR radius search.')
172+
tsum = (args.bounds is not None) + \
173+
(args.radius is not None) + (args.country is not None)
174+
if tsum != 1:
175+
print('Please specify a bounding box, radius, or country code.')
154176
sys.exit(1)
155177

156178
latitude = None
@@ -172,6 +194,7 @@ def main():
172194
else:
173195
endtime = args.endTime
174196

197+
bounds = None
175198
if args.radius:
176199
latitude = args.radius[0]
177200
longitude = args.radius[1]
@@ -182,38 +205,86 @@ def main():
182205
# fix longitude bounds when crossing dateline
183206
if lonmin > lonmax and lonmax >= -180:
184207
lonmin -= 360
208+
else:
209+
lonmin, lonmax, latmin, latmax = None, None, None, None
210+
bounds = (lonmin, lonmax, latmin, latmax)
211+
212+
if args.country:
213+
ccode = args.country
214+
if not check_ccode(ccode):
215+
curl = 'https://en.wikipedia.org/wiki/ISO_3166-1_alpha-2'
216+
fmt = '%s is not a valid ISO 3166 country code. See %s for the list.'
217+
tpl = (ccode, curl)
218+
print(fmt % tpl)
219+
sys.exit(1)
220+
bounds = get_country_bounds(ccode, args.buffer) # this returns a list
185221

186222
minmag = 0.0
187223
maxmag = 9.9
188224
if args.magRange:
189225
minmag = args.magRange[0]
190226
maxmag = args.magRange[1]
191227

192-
events = search(starttime=starttime,
193-
endtime=endtime,
194-
updatedafter=args.after,
195-
minlatitude=latmin,
196-
maxlatitude=latmax,
197-
minlongitude=lonmin,
198-
maxlongitude=lonmax,
199-
latitude=latitude,
200-
longitude=longitude,
201-
maxradiuskm=radiuskm,
202-
catalog=args.catalog,
203-
contributor=args.contributor,
204-
producttype=args.product,
205-
eventtype=args.eventType,
206-
maxmagnitude=maxmag,
207-
minmagnitude=minmag,
208-
host=args.host)
228+
if isinstance(bounds, tuple) or bounds is None:
229+
events = search(starttime=starttime,
230+
endtime=endtime,
231+
updatedafter=args.after,
232+
minlatitude=latmin,
233+
maxlatitude=latmax,
234+
minlongitude=lonmin,
235+
maxlongitude=lonmax,
236+
latitude=latitude,
237+
longitude=longitude,
238+
maxradiuskm=radiuskm,
239+
catalog=args.catalog,
240+
contributor=args.contributor,
241+
producttype=args.product,
242+
eventtype=args.eventType,
243+
maxmagnitude=maxmag,
244+
minmagnitude=minmag,
245+
host=args.host)
246+
else:
247+
events = []
248+
for i, tbounds in enumerate(bounds):
249+
lonmin, lonmax, latmin, latmax = tbounds
250+
tevents = search(starttime=starttime,
251+
endtime=endtime,
252+
updatedafter=args.after,
253+
minlatitude=latmin,
254+
maxlatitude=latmax,
255+
minlongitude=lonmin,
256+
maxlongitude=lonmax,
257+
latitude=latitude,
258+
longitude=longitude,
259+
maxradiuskm=radiuskm,
260+
catalog=args.catalog,
261+
contributor=args.contributor,
262+
producttype=args.product,
263+
eventtype=args.eventType,
264+
maxmagnitude=maxmag,
265+
minmagnitude=minmag,
266+
host=args.host)
267+
events += tevents
209268

210269
if not len(events):
211270
print('No events found matching your search criteria. Exiting.')
212271
sys.exit(0)
213272

273+
if args.country:
274+
ids = [event.id for event in events]
275+
lats = [event.latitude for event in events]
276+
lons = [event.longitude for event in events]
277+
df = pd.DataFrame({'id': ids, 'latitude': lats, 'longitude': lons})
278+
df2 = filter_by_country(df, ccode, buffer_km=args.buffer)
279+
events = [event for event in events if event.id in df2['id'].unique()]
280+
214281
for event in events:
215282
if not event.hasProduct(args.product):
216283
continue
284+
if args.country:
285+
elon = event.longitude
286+
elat = event.latitude
287+
point = Point(elon, elat)
217288
try:
218289
detail = event.getDetailEvent(includesuperseded=True)
219290
except Exception as e:
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
UTF-8
534 KB
Binary file not shown.
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1 @@
1+
GEOGCS["GCS_WGS_1984",DATUM["D_WGS_1984",SPHEROID["WGS_1984",6378137,298.257223563]],PRIMEM["Greenwich",0],UNIT["Degree",0.017453292519943295]]
1.54 MB
Binary file not shown.
1.98 KB
Binary file not shown.

0 commit comments

Comments
 (0)