seis_ruby 0.0.0

Sign up to get free protection for your applications and to get access to all the features.
data/bin/seis_ruby ADDED
@@ -0,0 +1,17 @@
1
+ #!/usr/bin/env ruby
2
+
3
+ require 'thor'
4
+ class SeisRubyRunner < Thor
5
+ require 'seis_ruby'
6
+ require 'ruby_patch'
7
+ require 'yaml'
8
+
9
+ desc 'gcmt_catalog_scrape URL', 'scrape cmtsolution data from GCMT catalog search result pages.'
10
+ def gcmt_catalog_scrape(url)
11
+ file = "#{__METHOD__}_#{Time.now.ymdhms}.yaml"
12
+ open(file, 'w').write(SeisRuby::Io::GcmtCatalog.scrape(url).to_yaml)
13
+ puts file
14
+ end
15
+ end
16
+
17
+ SeisRubyRunner.start
@@ -0,0 +1,62 @@
1
+ module SeisRuby
2
+ module Data
3
+ module Cmtsolution
4
+ require 'rainbow'
5
+ require 'ruby_patch/string'
6
+
7
+ ParseError = Class.new(StandardError)
8
+
9
+ module_function
10
+
11
+ def _preprocess_for_parse(text_for_one_event)
12
+ text_for_one_event\
13
+ .sub(/\A\n*/, '')\
14
+ .sub(/\n*\z/, '')\
15
+ .split("\n")
16
+ end
17
+
18
+ def _parse_lines(lines)
19
+ h = {hypocenter: {}, centroid: {}}
20
+
21
+ line0 = lines[0]
22
+ h[:hypocenter][:data_source] = line0[0..4].strip
23
+ line0_rest = line0[5..-1].split
24
+ [:year, :month, :day, :hour, :minute].each{|k|
25
+ raise ParseError if line0_rest.empty?
26
+ h[:hypocenter][k] = line0_rest.shift.to_i
27
+ }
28
+ [:second, :latitude, :longitude, :depth, :mb, :ms].each{|k|
29
+ raise ParseError if line0_rest.empty?
30
+ h[:hypocenter][k] = line0_rest.shift.to_f
31
+ }
32
+ h[:hypocenter][:region_name] = line0_rest.join(' ')
33
+ h[:event_name] = lines[1].split(':')[1].strip
34
+ values = lines[2..-1].map{|line| line.split(':')[1].to_f}
35
+ [
36
+ :time_shift, :half_duration,
37
+ :latitude, :longitude, :depth,
38
+ :mrr, :mtt, :mpp, :mrt, :mrp, :mtp,
39
+ ].zip(values).each{|k, v| h[:centroid][k] = v}
40
+
41
+
42
+ h
43
+ end
44
+
45
+ def parse(text_for_one_event)
46
+ begin
47
+ lines = _preprocess_for_parse(text_for_one_event)
48
+ _parse_lines(lines)
49
+ rescue
50
+ raise ParseError, text_for_one_event\
51
+ .split("\n")\
52
+ .map{|line| line.quote('|'.color(:red))}\
53
+ .join("\n")
54
+ end
55
+ end
56
+
57
+ def parse_list(events)
58
+ events.map{|ev| parse(ev)}
59
+ end
60
+ end
61
+ end
62
+ end
@@ -0,0 +1,6 @@
1
+ module SeisRuby
2
+ module Data
3
+ module Sac
4
+ end
5
+ end
6
+ end
@@ -0,0 +1,6 @@
1
+ module SeisRuby
2
+ module Data
3
+ require 'seis_ruby/data/cmtsolution'
4
+ require 'seis_ruby/data/sac'
5
+ end
6
+ end
@@ -0,0 +1,13 @@
1
+ module SeisRuby
2
+ module Io
3
+ module GcmtCatalog
4
+ require 'mechanize'
5
+
6
+ class CustomHtmlParser < ::Mechanize::Page
7
+ def initialize(uri = nil, response = nil, body = nil, code = nil, mech = nil)
8
+ super(uri, response, body.gsub(/<=/, '&lt;='), code, mech)
9
+ end
10
+ end
11
+ end
12
+ end
13
+ end
@@ -0,0 +1,42 @@
1
+ module SeisRuby
2
+ module Io
3
+ module GcmtCatalog
4
+ require 'rainbow'
5
+ require 'mechanize'
6
+ require 'seis_ruby/io/gcmt_catalog/custom_html_parser'
7
+ require 'seis_ruby/data/cmtsolution'
8
+
9
+ module_function
10
+
11
+ def scrape(url)
12
+ agent = Mechanize.new{|a|
13
+ a.pluggable_parser.html = ::SeisRuby::Io::GcmtCatalog::CustomHtmlParser
14
+ }
15
+
16
+ event_list = []
17
+ while url
18
+ agent.get(url)
19
+ agent.page.search('pre')\
20
+ .find{|e| e.text =~ /event name:/}\
21
+ .text.split("\n\n")\
22
+ .each{|event|
23
+ begin
24
+ event_list << ::SeisRuby::Data::Cmtsolution.parse(event) unless event.strip.empty?
25
+ rescue ::SeisRuby::Data::Cmtsolution::ParseError => e
26
+ $stderr.puts e.class.to_s.color(:red)
27
+ $stderr.puts e.message
28
+ end
29
+ }
30
+
31
+ url = nil
32
+ if next_link = agent.page.links\
33
+ .find{|e| e.text == 'More solutions'}
34
+ url = next_link.uri
35
+ end
36
+ end
37
+
38
+ event_list
39
+ end
40
+ end
41
+ end
42
+ end
@@ -0,0 +1,5 @@
1
+ module SeisRuby
2
+ module Io
3
+ require 'seis_ruby/io/gcmt_catalog'
4
+ end
5
+ end
@@ -0,0 +1,3 @@
1
+ module SeisRuby
2
+ VERSION = '0.0.0'
3
+ end
data/lib/seis_ruby.rb ADDED
@@ -0,0 +1,5 @@
1
+ module SeisRuby
2
+ require 'seis_ruby/version'
3
+ require 'seis_ruby/data'
4
+ require 'seis_ruby/io'
5
+ end
data/rakefile ADDED
@@ -0,0 +1,8 @@
1
+ require 'rspec/core/rake_task'
2
+
3
+ task default: :spec
4
+
5
+ desc "Run specs"
6
+ RSpec::Core::RakeTask.new(:spec){|s|
7
+ s.rspec_opts = '-c'
8
+ }
data/seis_ruby.gemspec ADDED
@@ -0,0 +1,18 @@
1
+ gem_name = File.basename(Dir.pwd)
2
+ require "./lib/#{gem_name}/version"
3
+
4
+ Gem::Specification.new do |s|
5
+ s.files = `git ls-files`.split
6
+ s.name = gem_name
7
+ s.summary = "Ruby library for earthquake science."
8
+ s.version = SeisRuby::VERSION
9
+ s.add_development_dependency 'rspec', '~> 2'
10
+ s.add_development_dependency 'simplecov', '~> 0'
11
+ s.add_runtime_dependency 'rainbow', '~>1'
12
+ s.add_runtime_dependency 'mechanize', '~>2'
13
+ s.add_runtime_dependency 'ruby_patch', ['>= 0.1.0', '< 1.0.0']
14
+ s.author = 'kshramt'
15
+ s.description = "Ruby library for earthquake science. Provides Parser for various data formats used in seismology."
16
+ s.required_ruby_version = '>= 1.9.0'
17
+ s.test_files.concat `git ls-files spec`.split.select{|path| path =~ /_spec\.rb/}
18
+ end
@@ -0,0 +1,98 @@
1
+ require 'spec_helper'
2
+ require 'seis_ruby/data/cmtsolution'
3
+
4
+ describe ::SeisRuby::Data::Cmtsolution do
5
+ before :each do
6
+ @valid_data = <<-EOS
7
+ 1980 12 7 17 37 9.70 36.0300 1.2300 10.0 0.0 0.0
8
+ event name: 120780A
9
+ time shift: 1.7000
10
+ half duration: 2.0000
11
+ latitude: 36.0200
12
+ longitude: 0.9400
13
+ depth: 25.8000
14
+ Mrr: 1.747000e+24
15
+ Mtt: -2.197000e+24
16
+ Mpp: 4.500000e+23
17
+ Mrt: 7.430000e+23
18
+ Mrp: 1.376000e+24
19
+ Mtp: -1.491000e+24
20
+ EOS
21
+
22
+ @parsed_valid_data = {
23
+ hypocenter: {
24
+ data_source: '',
25
+ year: 1980,
26
+ month: 12,
27
+ day: 7,
28
+ hour: 17,
29
+ minute: 37,
30
+ second: 9.70,
31
+ latitude: 36.03,
32
+ longitude: 1.23,
33
+ depth: 10.0,
34
+ mb: 0.0,
35
+ ms: 0.0,
36
+ region_name: ''
37
+ },
38
+ event_name: '120780A',
39
+ centroid: {
40
+ time_shift: 1.7,
41
+ half_duration: 2.0,
42
+ latitude: 36.02,
43
+ longitude: 0.94,
44
+ depth: 25.8,
45
+ mrr: 1.747e+24,
46
+ mtt: -2.197e+24,
47
+ mpp: 4.5e+23,
48
+ mrt: 7.43e+23,
49
+ mrp: 1.376e+24,
50
+ mtp: -1.491e+24,
51
+ },
52
+ }
53
+
54
+ @wrong_data = <<-EOS
55
+ 1980 12 7 17 37 9.70 36.0300 1.2300 10.0 0.0
56
+ event name: 120780A
57
+ time shift: 1.7000
58
+ half duration: 2.0000
59
+ latitude: 36.0200
60
+ longitude: 0.9400
61
+ depth: 25.8000
62
+ Mrr: 1.747000e+24
63
+ Mtt: -2.197000e+24
64
+ Mpp: 4.500000e+23
65
+ Mrt: 7.430000e+23
66
+ Mrp: 1.376000e+24
67
+ Mtp: -1.491000e+24
68
+ EOS
69
+ end
70
+
71
+ describe '.parse' do
72
+ context 'normal case' do
73
+ it do
74
+ ::SeisRuby::Data::Cmtsolution.parse(@valid_data).should == @parsed_valid_data
75
+ end
76
+ end
77
+
78
+ context 'wrong case' do
79
+ it do
80
+ lambda{::SeisRuby::Data::Cmtsolution.parse(@wrong_data)}.should raise_error(::SeisRuby::Data::Cmtsolution::ParseError)
81
+ end
82
+ end
83
+ end
84
+
85
+ describe '.parse_list' do
86
+ context 'normal case' do
87
+ it do
88
+ ::SeisRuby::Data::Cmtsolution.parse_list([@valid_data, @valid_data]).should == [@parsed_valid_data, @parsed_valid_data]
89
+ end
90
+ end
91
+
92
+ context 'wrong case' do
93
+ it do
94
+ lambda{::SeisRuby::Data::Cmtsolution.parse_list([@valid_data, @wrong_data])}.should raise_error(::SeisRuby::Data::Cmtsolution::ParseError)
95
+ end
96
+ end
97
+ end
98
+ end
@@ -0,0 +1,20 @@
1
+ require 'yaml'
2
+ require 'ruby_patch'
3
+ require 'spec_helper'
4
+ require 'seis_ruby'
5
+
6
+ describe ::SeisRuby::Io::GcmtCatalog do
7
+ describe '.scrape' do
8
+ context 'normal case' do
9
+ it do
10
+ ::SeisRuby::Io::GcmtCatalog.scrape('http://www.globalcmt.org/cgi-bin/globalcmt-cgi-bin/CMT4/form?itype=ymd&yr=1976&mo=1&day=1&oyr=1976&omo=1&oday=1&jyr=1976&jday=1&ojyr=1&ojday=1&otype=nd&nday=400&lmw=0&umw=10&lms=0&ums=10&lmb=0&umb=10&llat=-90&ulat=90&llon=-180&ulon=180&lhd=0&uhd=1000&lts=-9999&uts=9999&lpe1=0&upe1=90&lpe2=0&upe2=90&list=4').should == YAML.load_file(File.join(__DIR__, 'scrape.yaml'))
11
+ end
12
+
13
+ context 'wrong case' do
14
+ it do
15
+ lambda{::SeisRuby::Io::GcmtCatalog.scrape('http://www.globalcmt.org/cgi-bin/globalcmt-cgi-bin/CMT4/form?itype=ymd&yr=1976&mo=1&day=1&oyr=1976&omo=1&oday=1&jyr=1976&jday=1&ojyr=1&ojday=1&otype=nd&nday=400&lmw=0&umw=10&lms=0&ums=10&lmb=0&umb=10&llat=-90&ulat=90&llon=-180&ulon=180&lhd=0&uhd=1000&lts=-9999&uts=9999&lpe1=0&upe1=90&lpe2=0&upe2=90&list=3')}.should raise_error
16
+ end
17
+ end
18
+ end
19
+ end
20
+ end