taxa 0.1.0 → 0.3.1

Sign up to get free protection for your applications and to get access to all the features.
Files changed (43) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +0 -0
  3. data/.rubocop.yml +0 -0
  4. data/.ruby-version +1 -0
  5. data/.travis.yml +0 -0
  6. data/CHANGELOG.md +29 -1
  7. data/CODE_OF_CONDUCT.md +0 -0
  8. data/Gemfile +0 -0
  9. data/Gemfile.lock +8 -6
  10. data/LICENSE.txt +0 -0
  11. data/README.md +15 -2
  12. data/Rakefile +0 -0
  13. data/lib/taxa.rb +3 -0
  14. data/lib/taxa/eol_classic/client.rb +65 -0
  15. data/lib/taxa/open_tree_of_life/client.rb +0 -1
  16. data/lib/taxa/open_tree_of_life/label_format_helper.rb +0 -0
  17. data/lib/taxa/open_tree_of_life/studies/base.rb +0 -0
  18. data/lib/taxa/open_tree_of_life/studies/find_studies.rb +0 -1
  19. data/lib/taxa/open_tree_of_life/studies/find_trees.rb +0 -1
  20. data/lib/taxa/open_tree_of_life/studies/properties.rb +0 -1
  21. data/lib/taxa/open_tree_of_life/studies/study.rb +0 -1
  22. data/lib/taxa/open_tree_of_life/studies/tree.rb +0 -1
  23. data/lib/taxa/open_tree_of_life/taxonomy/about.rb +0 -1
  24. data/lib/taxa/open_tree_of_life/taxonomy/base.rb +0 -0
  25. data/lib/taxa/open_tree_of_life/taxonomy/mrca.rb +2 -3
  26. data/lib/taxa/open_tree_of_life/taxonomy/subtree.rb +0 -1
  27. data/lib/taxa/open_tree_of_life/taxonomy/taxon_info.rb +0 -1
  28. data/lib/taxa/open_tree_of_life/tnrs/autocomplete_name.rb +0 -1
  29. data/lib/taxa/open_tree_of_life/tnrs/base.rb +0 -0
  30. data/lib/taxa/open_tree_of_life/tnrs/contexts.rb +0 -1
  31. data/lib/taxa/open_tree_of_life/tnrs/infer_context.rb +0 -1
  32. data/lib/taxa/open_tree_of_life/tnrs/match_names.rb +5 -6
  33. data/lib/taxa/open_tree_of_life/tree_of_life/about.rb +0 -1
  34. data/lib/taxa/open_tree_of_life/tree_of_life/base.rb +0 -0
  35. data/lib/taxa/open_tree_of_life/tree_of_life/induced_subtree.rb +0 -1
  36. data/lib/taxa/open_tree_of_life/tree_of_life/mrca.rb +0 -1
  37. data/lib/taxa/open_tree_of_life/tree_of_life/node_info.rb +0 -1
  38. data/lib/taxa/open_tree_of_life/tree_of_life/subtree.rb +0 -1
  39. data/lib/taxa/plants_of_the_world_online/client.rb +63 -0
  40. data/lib/taxa/utils.rb +14 -0
  41. data/lib/taxa/version.rb +1 -1
  42. data/taxa.gemspec +1 -1
  43. metadata +8 -4
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: bc7d986ed381cdb8284eec26e8f84e85d0ef803c00faf6b4f89cd178524b099c
4
- data.tar.gz: e6edb9b337a03a9cb3ecfb16b81022044029dcb753009fe9526dcae10e5ff21a
3
+ metadata.gz: 0c3d0340e64965b829135fd758847296d007e8293d5229fd2485fccb40abe0be
4
+ data.tar.gz: 9c053380d21709436c7bf9b4e0a9198eecdedab7e0e578b4c50b992dcb4bd76e
5
5
  SHA512:
6
- metadata.gz: c93fe05a6e816d72009f9c8178edb6d7a012fadcf309bdfee2cb37f886a1a0142a1245415eb620fadab6d057c55d3b342c5eddc0ce2e27763cac9ebfce9077fd
7
- data.tar.gz: bf4b4afe570f496caf9b537b198223eb52a3fbc4e7cca4e36723bd019f817879f6ad0e877d647d63eff95f4dcb78acbd9b3222229b3b7e38210696efad95dcb2
6
+ metadata.gz: 99741a996cd69e5d57b2da6af6d0c4acf04a429db6258f6cdefbeb21d3b062aeba41a6537e7f5a3c6ff78d5941c533448b7263751ec134029bb9bad2538a29a3
7
+ data.tar.gz: 01d2cee9562d2f2845fc0866c3a8a68a279e548b5eb6f1913b41aa43110e8a13cc379b980e5ce524dc8165d5b18e7d003bd74cc09ad09425a5f466fdae8e3230
data/.gitignore CHANGED
File without changes
data/.rubocop.yml CHANGED
File without changes
data/.ruby-version ADDED
@@ -0,0 +1 @@
1
+ 2.7.2
data/.travis.yml CHANGED
File without changes
data/CHANGELOG.md CHANGED
@@ -1 +1,29 @@
1
- nothing yet
1
+ # Taxa Changelog
2
+
3
+ ## [0.1.0]
4
+
5
+ ### Highlights
6
+ Support for Open Tree of Life API v3
7
+ https://github.com/OpenTreeOfLife/germinator/wiki/Open-Tree-of-Life-Web-APIs
8
+
9
+ ## [0.2.0]
10
+
11
+ ### Highlights
12
+ Support for the classic API for EOL
13
+ https://eol.org/docs/what-is-eol/classic-apis
14
+
15
+ ## [0.2.1]
16
+
17
+ ### Highlights
18
+ Update JSON gem to 2.5.x
19
+
20
+ ## [0.3.0]
21
+
22
+ ### Highlights
23
+ Support for Plants of the World Online
24
+ http://plantsoftheworldonline.org/
25
+
26
+ ## [0.3.1]
27
+
28
+ ### Highlights
29
+ Fixed a bug related to Plants of The World Online filter validation
data/CODE_OF_CONDUCT.md CHANGED
File without changes
data/Gemfile CHANGED
File without changes
data/Gemfile.lock CHANGED
@@ -1,18 +1,20 @@
1
1
  PATH
2
2
  remote: .
3
3
  specs:
4
- taxa (0.1.0)
4
+ taxa (0.3.0)
5
5
  faraday (~> 1.1)
6
- json (~> 1.8)
6
+ json (~> 2.5)
7
7
 
8
8
  GEM
9
9
  remote: https://rubygems.org/
10
10
  specs:
11
11
  ast (2.4.1)
12
- faraday (1.1.0)
12
+ faraday (1.3.0)
13
+ faraday-net_http (~> 1.0)
13
14
  multipart-post (>= 1.2, < 3)
14
15
  ruby2_keywords
15
- json (1.8.6)
16
+ faraday-net_http (1.0.1)
17
+ json (2.5.1)
16
18
  minitest (5.14.2)
17
19
  multipart-post (2.1.1)
18
20
  parallel (1.20.1)
@@ -34,7 +36,7 @@ GEM
34
36
  rubocop-ast (1.3.0)
35
37
  parser (>= 2.7.1.5)
36
38
  ruby-progressbar (1.10.1)
37
- ruby2_keywords (0.0.2)
39
+ ruby2_keywords (0.0.4)
38
40
  unicode-display_width (1.7.0)
39
41
 
40
42
  PLATFORMS
@@ -47,4 +49,4 @@ DEPENDENCIES
47
49
  taxa!
48
50
 
49
51
  BUNDLED WITH
50
- 2.1.4
52
+ 2.2.3
data/LICENSE.txt CHANGED
File without changes
data/README.md CHANGED
@@ -1,6 +1,6 @@
1
1
  # Taxa
2
2
 
3
- Taxa allows users to search multiple taxonomic data sources. Currently only Open Tree of Life is implemented.
3
+ Taxa allows users to search multiple taxonomic data sources. Currently only Open Tree of Life and EOL classic APIs are implemented.
4
4
 
5
5
  ## Installation
6
6
 
@@ -19,8 +19,21 @@ Or install it yourself as:
19
19
  $ gem install taxa
20
20
 
21
21
  ## Usage
22
+ ```ruby
23
+ tol_client = Taxa::OpenTreeOfLife::Client.new
24
+ tol_client.tnrs.match_names('Cotyledon') # can be an array or a string
25
+
26
+ eol_client = Taxa::EOLClassic::Client.new
27
+ eol_client.hierarchy_entries(7834469)
28
+
29
+ powo_client = Taxa::PlantsOfTheWorldOnline::Client.new
30
+ powo_client.search('Crassula alata')
31
+ powo_client.search('Crassula', ['species_f', 'has_images'])
32
+ powo_client.search('family:Crassulaceae', ['species_f', 'has_images'])
33
+ ```
22
34
 
23
- client = Taxa::OpenTreeOfLife::Client.new
35
+ For Plants of the World Online please see their official python library for available search terms:
36
+ https://github.com/RBGKew/pykew#available-search-terms-1
24
37
 
25
38
  ## Development
26
39
 
data/Rakefile CHANGED
File without changes
data/lib/taxa.rb CHANGED
@@ -1,7 +1,10 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require 'taxa/version'
4
+ require 'faraday'
4
5
  require_relative './taxa/open_tree_of_life/client'
6
+ require_relative './taxa/eol_classic/client'
7
+ require_relative './taxa/plants_of_the_world_online/client'
5
8
 
6
9
  module Taxa
7
10
  # include OpenTreeOfLife
@@ -0,0 +1,65 @@
1
+ # frozen_string_literal: true
2
+
3
+ module Taxa
4
+ module EOLClassic
5
+ # API client for Open Tree of Life
6
+ class Client
7
+ attr_accessor :options
8
+ attr_reader :http_client
9
+
10
+ def initialize(**options)
11
+ @options = options
12
+
13
+ @http_client = options[:http_client] || Faraday.new
14
+ end
15
+
16
+ def search(query, **parameters)
17
+ raise ArgumentError, 'query can not be nil' if query.nil?
18
+
19
+ url = 'https://eol.org/api/search/1.0.json'
20
+ response = @http_client.get(url, { q: query }.merge(parameters), { 'Accept' => 'application/json' })
21
+ parse_response(response)
22
+ end
23
+
24
+ def collections(id, **parameters)
25
+ raise ArgumentError, 'id can not be nil' if id.nil?
26
+
27
+ url = "https://eol.org/api/collections/1.0/#{id}.json"
28
+ response = @http_client.get(url, parameters, { 'Accept' => 'application/json' })
29
+ parse_response(response)
30
+ end
31
+
32
+ def pages(id, **parameters)
33
+ raise ArgumentError, 'id can not be nil' if id.nil?
34
+
35
+ url = "https://eol.org/api/pages/1.0/#{id}.json"
36
+ response = @http_client.get(url, parameters, { 'Accept' => 'application/json' })
37
+ parse_response(response)
38
+ end
39
+
40
+ def data_objects(id, **parameters)
41
+ raise ArgumentError, 'id can not be nil' if id.nil?
42
+
43
+ url = "https://eol.org/api/data_objects/1.0/#{id}.json"
44
+ response = @http_client.get(url, parameters, { 'Accept' => 'application/json' })
45
+ parse_response(response)
46
+ end
47
+
48
+ def hierarchy_entries(id, **parameters)
49
+ raise ArgumentError, 'id can not be nil' if id.nil?
50
+
51
+ url = "https://eol.org/api/hierarchy_entries/1.0/#{id}.json"
52
+ response = @http_client.get(url, parameters, { 'Accept' => 'application/json' })
53
+ parse_response(response)
54
+ end
55
+
56
+ private
57
+
58
+ def parse_response(response)
59
+ JSON.parse(response.body)
60
+ rescue StandardError
61
+ nil
62
+ end
63
+ end
64
+ end
65
+ end
@@ -4,7 +4,6 @@ require_relative './tnrs/base'
4
4
  require_relative './tree_of_life/base'
5
5
  require_relative './taxonomy/base'
6
6
  require_relative './studies/base'
7
- require 'faraday'
8
7
 
9
8
  module Taxa
10
9
  module OpenTreeOfLife
File without changes
File without changes
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
File without changes
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -10,10 +9,10 @@ module Taxa
10
9
  module Mrca
11
10
  def mrca(ott_ids)
12
11
  raise ArgumentError, 'ott_ids required' if ott_ids.nil?
13
- raise ArgumentError, 'ott_ids expected to be an array' unless ott_ids.is_a?(Array)
14
12
 
15
13
  url = 'https://api.opentreeoflife.org/v3/taxonomy/mrca'
16
- response = @http_client.post(url, JSON.generate({ ott_ids: ott_ids }), 'Content-Type' => 'application/json')
14
+ response = @http_client.post(url, JSON.generate({ ott_ids: Array(ott_ids) }),
15
+ 'Content-Type' => 'application/json')
17
16
  JSON.parse(response.body)
18
17
  end
19
18
  end
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
File without changes
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -8,20 +7,20 @@ module Taxa
8
7
  class TNRS
9
8
  # tnrs match_names api endpoint
10
9
  module MatchNames
11
- def match_names(**parameters)
12
- names = parameters[:names]
13
- raise ArgumentError if names.nil?
10
+ def match_names(names, **parameters)
11
+ raise ArgumentError, 'names is required' if names.nil?
14
12
 
15
13
  context_name = parameters[:context_name]
16
14
  do_approximate_matching = parameters[:do_approximate_matching] || false
17
15
  include_suppressed = parameters[:include_suppressed]
18
16
 
19
17
  payload = {
20
- names: names,
18
+ names: Array(names),
21
19
  context_name: context_name,
22
20
  do_approximate_matching: do_approximate_matching,
23
21
  include_suppressed: include_suppressed
24
- }
22
+ }.compact
23
+
25
24
  url = 'https://api.opentreeoflife.org/v3/tnrs/match_names'
26
25
  response = @http_client.post(url, JSON.generate(payload), 'Content-Type' => 'application/json')
27
26
  JSON.parse(response.body)
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
File without changes
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -1,6 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- require 'faraday'
4
3
  require 'json'
5
4
 
6
5
  module Taxa
@@ -0,0 +1,63 @@
1
+ # frozen_string_literal: true
2
+
3
+ require_relative '../utils'
4
+ module Taxa
5
+ module PlantsOfTheWorldOnline
6
+ # API client for Open Tree of Life
7
+ class Client
8
+ attr_accessor :options
9
+ attr_reader :http_client
10
+
11
+ POWO_URL = 'http://www.plantsoftheworldonline.org/api/2'
12
+
13
+ FILTERS = %w[accepted_names has_images families_f genus_f species_f infraspecific_f].freeze
14
+
15
+ def initialize(**options)
16
+ @options = options
17
+ @http_client = options[:http_client] || Faraday.new
18
+ end
19
+
20
+ def search(query, options = {})
21
+ options.transform_keys!(&:to_sym)
22
+
23
+ page = options[:page] || 0
24
+ filters = Array.wrap(options[:filters])
25
+ validate_search_parameters(query, page, filters)
26
+
27
+ payload = { q: query, p: page }
28
+ payload.merge!({ f: filters.join(',') }) unless filters.empty?
29
+ response = @http_client.get("#{POWO_URL}/search", payload, { 'Accept' => 'application/json' })
30
+ parse_response(response)
31
+ end
32
+
33
+ def lookup(id, include = nil)
34
+ raise ArgumentError, 'id can not be nil' if id.nil?
35
+
36
+ include = Array.wrap(include)
37
+ payload = {}
38
+ payload.merge!({ fields: include.join(',') }) unless include.empty?
39
+ response = @http_client.get("#{POWO_URL}/taxon/#{id}", payload, { 'Accept' => 'application/json' })
40
+ parse_response(response)
41
+ end
42
+
43
+ private
44
+
45
+ def validate_search_parameters(query, page, filters)
46
+ raise ArgumentError, 'query can not be nil' if query.nil?
47
+
48
+ if !filters.empty? && !filters.all? { |f| FILTERS.include? f }
49
+ raise ArgumentError,
50
+ "filter is invalid. It must be one of these: #{FILTERS.join(', ')} can not be nil"
51
+ end
52
+
53
+ raise ArgumentError, 'page must be an integer' unless page.is_a?(Integer)
54
+ end
55
+
56
+ def parse_response(response)
57
+ JSON.parse(response.body)
58
+ rescue StandardError
59
+ nil
60
+ end
61
+ end
62
+ end
63
+ end
data/lib/taxa/utils.rb ADDED
@@ -0,0 +1,14 @@
1
+ # frozen_string_literal: true
2
+
3
+ # https://stackoverflow.com/questions/18358717/ruby-elegantly-convert-variable-to-an-array-if-not-an-array-already
4
+ class Array
5
+ def self.wrap(object)
6
+ if object.nil?
7
+ []
8
+ elsif object.respond_to?(:to_ary)
9
+ object.to_ary || [object]
10
+ else
11
+ [object]
12
+ end
13
+ end
14
+ end
data/lib/taxa/version.rb CHANGED
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module Taxa
4
- VERSION = '0.1.0'
4
+ VERSION = '0.3.1'
5
5
  end
data/taxa.gemspec CHANGED
@@ -28,5 +28,5 @@ Gem::Specification.new do |spec|
28
28
  spec.require_paths = ['lib']
29
29
  spec.add_development_dependency 'rubocop', '~> 1.6'
30
30
  spec.add_dependency 'faraday', '~> 1.1'
31
- spec.add_dependency 'json', '~> 1.8'
31
+ spec.add_dependency 'json', '~> 2.5'
32
32
  end
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: taxa
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.1.0
4
+ version: 0.3.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Shane Sherman
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2020-12-27 00:00:00.000000000 Z
11
+ date: 2021-03-18 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rubocop
@@ -44,14 +44,14 @@ dependencies:
44
44
  requirements:
45
45
  - - "~>"
46
46
  - !ruby/object:Gem::Version
47
- version: '1.8'
47
+ version: '2.5'
48
48
  type: :runtime
49
49
  prerelease: false
50
50
  version_requirements: !ruby/object:Gem::Requirement
51
51
  requirements:
52
52
  - - "~>"
53
53
  - !ruby/object:Gem::Version
54
- version: '1.8'
54
+ version: '2.5'
55
55
  description: Wrapper around a bunch of taxonomy databases.
56
56
  email:
57
57
  - shane.sherman@gmail.com
@@ -61,6 +61,7 @@ extra_rdoc_files: []
61
61
  files:
62
62
  - ".gitignore"
63
63
  - ".rubocop.yml"
64
+ - ".ruby-version"
64
65
  - ".travis.yml"
65
66
  - CHANGELOG.md
66
67
  - CODE_OF_CONDUCT.md
@@ -72,6 +73,7 @@ files:
72
73
  - bin/console
73
74
  - bin/setup
74
75
  - lib/taxa.rb
76
+ - lib/taxa/eol_classic/client.rb
75
77
  - lib/taxa/open_tree_of_life/client.rb
76
78
  - lib/taxa/open_tree_of_life/label_format_helper.rb
77
79
  - lib/taxa/open_tree_of_life/studies/base.rb
@@ -96,6 +98,8 @@ files:
96
98
  - lib/taxa/open_tree_of_life/tree_of_life/mrca.rb
97
99
  - lib/taxa/open_tree_of_life/tree_of_life/node_info.rb
98
100
  - lib/taxa/open_tree_of_life/tree_of_life/subtree.rb
101
+ - lib/taxa/plants_of_the_world_online/client.rb
102
+ - lib/taxa/utils.rb
99
103
  - lib/taxa/version.rb
100
104
  - taxa.gemspec
101
105
  homepage: https://github.com/ssherman/taxa