{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "
\n", "
\n", "
\n", "
ObsPy Tutorial
\n", "
Downloading Data
\n", "
\n", "
\n", "
\n", "image: User:Abbaszade656 / Wikimedia Commons / CC-BY-SA-4.0" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## Workshop for the \"Training in Network Management Systems and Analytical Tools for Seismic\"\n", "### Baku, October 2018\n", "\n", "Seismo-Live: http://seismo-live.org\n", "\n", "##### Authors:\n", "* Lion Krischer ([@krischer](https://github.com/krischer))\n", "* Tobias Megies ([@megies](https://github.com/megies))\n", "---" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "![](images/obspy_logo_full_524x179px.png)" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "%matplotlib inline\n", "from __future__ import print_function\n", "import matplotlib.pyplot as plt\n", "plt.style.use('ggplot')\n", "plt.rcParams['figure.figsize'] = 12, 8" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "ObsPy has clients to directly fetch data via...\n", "\n", "- FDSN webservices (IRIS, Geofon/GFZ, USGS, NCEDC, SeisComp3 instances, ...)\n", "- ArcLink (EIDA, ...)\n", "- Earthworm\n", "- SeedLink (near-realtime servers)\n", "- NERIES/NERA/seismicportal.eu\n", "- NEIC\n", "- SeisHub (local seismological database)\n", "\n", "This introduction shows how to use the FDSN webservice client. The FDSN webservice definition is by now the default web service implemented by many data centers world wide. Clients for other protocols work similar to the FDSN client.\n", "\n", "#### Waveform Data" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "import obspy\n", "from obspy.clients.fdsn import Client\n", "\n", "client = Client(\"IRIS\")\n", "t = obspy.UTCDateTime(\"2014-08-24T10:20:44.0\") # South Napa Earthquake\n", "st = client.get_waveforms(\"II\", \"PFO\", \"00\", \"LHZ\",\n", " t - 5 * 60, t + 20 * 60)\n", "print(st)\n", "st.plot()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "- again, waveform data is returned as a Stream object\n", "- for all custom processing workflows it does not matter if the data originates from a local file or from a web service\n", "\n", "#### Event Metadata\n", "\n", "The FDSN client can also be used to request event metadata:" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "t = obspy.UTCDateTime(\"2014-08-24T10:20:44.0\") # South Napa earthquake\n", "catalog = client.get_events(starttime=t - 100, endtime=t + 3600,\n", " minmagnitude=6)\n", "print(catalog)\n", "catalog.plot();" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Requests can have a wide range of constraints (see [ObsPy Documentation](http://docs.obspy.org/packages/autogen/obspy.clients.fdsn.client.Client.get_events.html)):\n", "\n", "- time range\n", "- geographical (lonlat-box, circular by distance)\n", "- depth range\n", "- magnitude range, type\n", "- contributing agency" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### Station Metadata\n", "\n", "Finally, the FDSN client can be used to request station metadata. Stations can be looked up using a wide range of constraints (see [ObsPy documentation](http://docs.obspy.org/packages/autogen/obspy.clients.fdsn.client.Client.get_stations.html)):\n", "\n", " * network/station code\n", " * time range of operation\n", " * geographical (lonlat-box, circular by distance)" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "event = catalog[0]\n", "origin = event.origins[0]\n", "\n", "# Livermore\n", "lon = -121.768005\n", "lat = 37.681873\n", "\n", "# Get currently active stations in 5 km radius around Livermore.\n", "inventory = client.get_stations(longitude=lon, latitude=lat,\n", " maxradius=0.05, level=\"station\", \n", " starttime=obspy.UTCDateTime())\n", "print(inventory)\n", "inventory.plot(projection=\"local\", resolution=\"i\");" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The **`level=...`** keyword is used to specify the level of detail in the requested inventory\n", "\n", "- `\"network\"`: only return information on networks matching the criteria\n", "- `\"station\"`: return information on all matching stations\n", "- `\"channel\"`: return information on available channels in all stations networks matching the criteria\n", "- `\"response\"`: include instrument response for all matching channels (large result data size!)" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "inventory = client.get_stations(network=\"II\", station=\"PFO\",\n", " level=\"station\")\n", "print(inventory)" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "inventory = client.get_stations(network=\"II\", station=\"PFO\",\n", " level=\"channel\")\n", "print(inventory)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "For waveform requests that include instrument correction, the appropriate instrument response information also has to be downloaded." ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "t = obspy.UTCDateTime(\"2014-08-24T10:20:44.0\") # South Napa earthquake\n", "st = client.get_waveforms(\"II\", \"PFO\", \"00\", \"LHZ\",\n", " t - 10 * 60, t + 20 * 60)\n", "inv = client.get_stations(network=\"II\", station=\"PFO\", location=\"00\", channel=\"LHZ\",\n", " level=\"response\", starttime=t - 10, endtime=t + 10)\n", "st.plot()\n", "\n", "st.remove_response(inventory=inv)\n", "st.plot()" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "All data requested using the FDSN client can be directly saved to file using the **`filename=\"...\"`** option. The data is then stored exactly as it is served by the data center, i.e. without first parsing by ObsPy and outputting by ObsPy." ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [ "client.get_events(starttime=t-100, endtime=t+24*3600, minmagnitude=5,\n", " filename=\"/tmp/requested_events.xml\")\n", "client.get_stations(network=\"II\", station=\"PFO\", level=\"station\",\n", " filename=\"/tmp/requested_stations.xml\")\n", "client.get_waveforms(\"II\", \"PFO\", \"00\", \"LHZ\", t - 10 * 60, t + 20 * 60,\n", " filename=\"/tmp/requested_waveforms.mseed\")\n", "!ls -lrt /tmp/requested*" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### FDSN Client Exercise\n", "\n", "Use the FDSN client to assemble a small waveform dataset for on event.\n", "\n", "- search for a large earthquake (e.g. by depth or in a region of your choice, use option **`limit=5`** to keep network traffic down)" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [] }, { "cell_type": "markdown", "metadata": {}, "source": [ "- search for stations to look at waveforms for the event. stations should..\n", " * be available at the time of the event\n", " * use a vertical 1 Hz stream (\"LHZ\", to not overpower our network..)\n", " * be in a narrow angular distance around the event (e.g. 90-91 degrees)\n", " * adjust your search so that only a small number of stations (e.g. 3-6) match your search criteria\n", " * Once you found a good set of stations, please use `level=\"response\"` as you will need the response later on." ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [] }, { "cell_type": "markdown", "metadata": {}, "source": [ "- for each of these stations download data of the event, e.g. a couple of minutes before to half an hour after the event\n", "- put all data together in one stream (put the `get_waveforms()` call in a try/except/pass block to silently skip stations that actually have no data available)\n", "- print stream info, plot the raw data" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [] }, { "cell_type": "markdown", "metadata": {}, "source": [ "- correct the instrument response for all stations and plot the corrected data" ] }, { "cell_type": "code", "execution_count": null, "metadata": { "collapsed": true }, "outputs": [], "source": [] }, { "cell_type": "markdown", "metadata": {}, "source": [ "If you have time, assemble and plot another similar dataset (e.g. like before stations at a certain distance from a big event, or use Transportable Array data for a big event, etc.)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "#### Routed/Federated Clients\n", "\n", "Finally, all of the above queries can not only be directed at one specific data center, but instead can be sent to either ..\n", "\n", " * [IRIS Federator](https://service.iris.edu/irisws/fedcatalog/1/), or\n", " * [EIDA routing](http://www.orfeus-eu.org/data/eida/webservices/routing/) service\n", "\n", ".. to query data across all existing FDSN web service data centers (or at least those registered with IRIS/EIDA).\n", "These federation/routing services support station lookup and waveform request queries.\n", "\n", "This example queries the IRIS Federator which in turn combines data from all other FDSN web service data centers." ] }, { "cell_type": "code", "execution_count": null, "metadata": {}, "outputs": [], "source": [ "from obspy.clients.fdsn import RoutingClient\n", "\n", "client = RoutingClient('iris-federator') # or use 'eida-routing' for the EIDA routing service\n", "\n", "# Tohoku Earthquake\n", "t = obspy.UTCDateTime('2011-03-11T14:46:24+09')\n", "\n", "st = client.get_waveforms(\n", " channel=\"LHZ\", starttime=t, endtime=t+20,\n", " latitude=50, longitude=14, maxradius=10) \n", "print(st)" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.6.2" } }, "nbformat": 4, "nbformat_minor": 1 }