arduino-library 0.3.2 → 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA1:
3
- metadata.gz: 3b5c76ad31ff11fa46db661d9c15bdd0491d371a
4
- data.tar.gz: 15c6b0b9857623d65d41bd3f6b0364f42ffc34c6
3
+ metadata.gz: a59d64cfdecdeda3f42ddc545b3f55cce2edd407
4
+ data.tar.gz: a4c1df07773fb1e7934c70716eb574fe0a5d1836
5
5
  SHA512:
6
- metadata.gz: 233b52e36e5128b7ca9dc5373d5d2f5254e79c25226261d8c0cbbdaf5257275b1d2649e1fcddfc83f1928fc94274826b94ed26cdc8775f68fb9cdaee4930dbfa
7
- data.tar.gz: 4ccc781670970f5ba2178842e08cbe9233c5415c8bf226e8e5b26e7b08ac364449b980a3a33802c93b2ee6e65018fb611ecf146cd11622ff27fa0f2a17ef27e2
6
+ metadata.gz: 06e70b8fd17d082f88ee8b82881c408dc70bae39848038a998ba7b0f4f3c486980d377f8012cb6e17344ddeec32c430236c0d3e9ca741751c8c82c038758e282
7
+ data.tar.gz: db35e120cdb2f0560427da52ce67db60148814eaec96966c3c0533ef397974fc47f27a75274d4a97895ecfa43ee09c794d4b09812252df9ceb14a6ab759cf181
data/README.md CHANGED
@@ -39,29 +39,33 @@ Current version only contains Ruby-based API and is meant to be consumed by othe
39
39
  ### Configuration
40
40
 
41
41
  The gem database can be configured to download the default database from a custom URL,
42
- keep a local cache in a custom file. It always downloads the index locally, and next time
43
- it's invoked, the local file is used (if and only if it's size is identical
44
- to the remote file).
42
+ and to cache it in a local file. Next time the lookup is invoked local file is checked first. Library automatically checks the size of the remote index file, and re-downloads it if the file has changed.
45
43
 
46
- You can change the configuration in two ways:
44
+ You can modify the source of the default database and the local cache location using one of two methods:
47
45
 
48
- 1. Set environment variables before invoking the gem
49
- 2. Configure the `DefaultDatabase` class variables
46
+ 1. By settin the environment variables before invoking the gem;
47
+ 2. Or by configuring the `DefaultDatabase` class variables.
50
48
 
51
- #### Environment Variables
49
+ #### Setting Environment Variables
52
50
 
53
51
  * `ARDUINO_CUSTOM_LIBRARY_PATH` can be used to change local top-level path to the libraries folder.
54
52
  * `ARDUINO_LIBRARY_INDEX_PATH` can be used to change the location of the cached index file.
55
53
 
56
- #### Class Variables
54
+ #### Change Class Variables for `DefaultDatabase` Class
55
+
56
+ The following class variables can be changed, like so:
57
57
 
58
58
  ```ruby
59
- require 'arduino/library'
60
- Arduino::Library::DefaultDatabase.library_index_path =
61
- Arduino::Library::DefaultDatabase.library_index_url =
62
- Arduino::Library::DefaultDatabase.library_path =
59
+ Arduino::Library::DefaultDatabase.library_index_url = ''
60
+ ```
61
+
62
+ * `library_index_url` — URL to download compressed JSON index.
63
+ * `library_index_path` — local path to the cached compressed JSON index.
64
+ * `library_path` — local top-level folder where your Arduino libraries are.
65
+
66
+ If you change any of the above, please reload the database with:
63
67
 
64
- # then reload the database:
68
+ ```ruby
65
69
  Arduino::Library::DefaultDatabase.instance.setup
66
70
  ```
67
71
 
@@ -79,26 +83,29 @@ DEFAULT_ARDUINO_LIBRARY_INDEX_PATH =
79
83
  (ENV['HOME'] + '/Documents/Arduino/Libraries/index.json.gz')
80
84
  ```
81
85
 
82
- ### Using the top-level module
86
+ ### Finding and Resolving Arduino Libraries
83
87
 
84
- If you prefer not to have hard-coded dependencies on the `Arduino::Library::*` sub-classes and sub-modules, you can use the top level module, which proxies several shortcut methods.
88
+ Top level module `Arduino::Library` provides a convenient Facáde into the library functionality. Therefore you can use the library by calling these methods directly, such as `Arduino::Library.library_from(..)` or by including the module in your current context.
85
89
 
86
- You can access these methods in two different ways:
90
+ Below we'll include the top level module, and use the shortcut methods to explore available functionality. That said, if you prefer not to include the top level module, you can call the same functions directly on the module itself.
87
91
 
88
- 1. As class methods on `Arduino::Library`, for example `Arduino::Library.db_default`
89
- 2. By including the top-level module in your context, and using methods as instance methods in the current context, eg. `#db_default`
92
+ There are two ways to include the DSL in your context:
90
93
 
91
- Below we'll focus on the second usage, but if you prefer to use the first syntax, it's there and available for you.
94
+ ```ruby
95
+ require 'arduino/library'
96
+ class Foo
97
+ include Arduino::Library::InstanceMethods
98
+ end
99
+ ```
92
100
 
93
- You can require the library for use in the DSL:
101
+ Or, perhaps easier:
94
102
 
95
103
  ```ruby
96
104
  class Foo
97
- # this loads the library, and includes its methods in the current context
98
105
  require 'arduino/library/include
99
106
  end
100
107
  ```
101
-
108
+ ### Facáde Methods
102
109
 
103
110
  #### Using `db_from`
104
111
 
@@ -150,6 +157,15 @@ search(database = db_default, **opts)
150
157
 
151
158
  **Examples**
152
159
 
160
+ Here is searching for 'AudioZero' and sorting results by the version number:
161
+
162
+ ```ruby
163
+ search(name: 'AudioZero').sort.first.version #=> "1.0.0"
164
+ search(name: 'AudioZero').sort.last.version #=> "1.1.1"
165
+ ```
166
+
167
+ You can search by any attribute, not just name and number:
168
+
153
169
  ```ruby
154
170
  results = search(
155
171
  # direct string equality
@@ -32,4 +32,5 @@ Gem::Specification.new do |spec|
32
32
  spec.add_development_dependency 'rake', '~> 10.0'
33
33
  spec.add_development_dependency 'rspec', '~> 3.0'
34
34
  spec.add_development_dependency 'rspec-its'
35
+ spec.add_development_dependency 'irbtools'
35
36
  end
@@ -2,13 +2,15 @@ require 'open-uri'
2
2
 
3
3
  module Arduino
4
4
  module Library
5
- DEFAULT_ARDUINO_LIBRARY_INDEX_URL =
6
- 'http://downloads.arduino.cc/libraries/library_index.json.gz'
7
- DEFAULT_ARDUINO_LIBRARY_PATH =
8
- ENV['ARDUINO_CUSTOM_LIBRARY_PATH'] || (ENV['HOME'] + '/Documents/Arduino/Libraries')
9
- DEFAULT_ARDUINO_LIBRARY_INDEX_PATH =
10
- ENV['ARDUINO_LIBRARY_INDEX_PATH'] ||
11
- (ENV['HOME'] + '/Documents/Arduino/Libraries/index.json.gz')
5
+ unless defined?(DEFAULT_ARDUINO_LIBRARY_INDEX_URL)
6
+ DEFAULT_ARDUINO_LIBRARY_INDEX_URL =
7
+ 'http://downloads.arduino.cc/libraries/library_index.json.gz'
8
+ DEFAULT_ARDUINO_LIBRARY_PATH =
9
+ ENV['ARDUINO_CUSTOM_LIBRARY_PATH'] || (ENV['HOME'] + '/Documents/Arduino/Libraries')
10
+ DEFAULT_ARDUINO_LIBRARY_INDEX_PATH =
11
+ ENV['ARDUINO_LIBRARY_INDEX_PATH'] ||
12
+ (ENV['HOME'] + '/Documents/Arduino/Libraries/index.json.gz')
13
+ end
12
14
  end
13
15
  end
14
16
 
@@ -19,44 +21,12 @@ require 'arduino/library/types'
19
21
  require 'arduino/library/model'
20
22
  require 'arduino/library/database'
21
23
  require 'arduino/library/default_database'
24
+ require 'arduino/library/resolver'
25
+ require 'arduino/library/instance_methods'
22
26
 
23
27
  module Arduino
24
28
  module Library
25
- # @param [String] file_or_url — either a local file, or URL, can be gzipped
26
- def db_from(file_or_url)
27
- Database.new(file_or_url)
28
- end
29
-
30
- def db_default
31
- DefaultDatabase.instance
32
- end
33
-
34
- #
35
- # +file_or_url+ can be a JSON file name, a .properties file name, or
36
- # a URL to either of the above.
37
- #
38
- # @param [String] file_or_url
39
- def library_from(file_or_url)
40
- Arduino::Library::Model.from(file_or_url)
41
- end
42
-
43
- # +opts+ is a Hash that you can use to pass attributes with values, any
44
- # number of them. All matching results are returned as models.
45
- #
46
- # name: 'AudioZero'
47
- # author: /konstantin/i - regexp supported
48
- # architectures: [ 'avr' ] - array is matched if it's a subset
49
- # version: proc do |value| — or a proc for max flexibility
50
- # value.start_with?('1.') )
51
- # end
52
- #
53
- # @param [Database] database db instance (or skip it to use the default)
54
- # @param [Hash] opts hash of attribute names and values to match
55
- # @return Array<Model> array of models that match
56
- def search(database = db_default, **opts)
57
- Arduino::Library::Model.database = database
58
- database.search(**opts)
59
- end
29
+ include InstanceMethods
60
30
  end
61
31
  end
62
32
 
@@ -1,3 +1,3 @@
1
1
  require 'arduino/library'
2
2
 
3
- include Arduino::Library
3
+ include Arduino::Library::InstanceMethods
@@ -0,0 +1,43 @@
1
+ require 'arduino/library'
2
+
3
+ module Arduino
4
+ module Library
5
+ module InstanceMethods
6
+ # @param [String] file_or_url — either a local file, or URL, can be gzipped
7
+ def db_from(file_or_url)
8
+ Database.new(file_or_url)
9
+ end
10
+
11
+ def db_default
12
+ DefaultDatabase.instance
13
+ end
14
+
15
+ #
16
+ # +file_or_url+ can be a JSON file name, a .properties file name, or
17
+ # a URL to either of the above.
18
+ #
19
+ # @param [String] file_or_url
20
+ def library_from(file_or_url)
21
+ Arduino::Library::Model.from(file_or_url)
22
+ end
23
+
24
+ # +opts+ is a Hash that you can use to pass attributes with values, any
25
+ # number of them. All matching results are returned as models.
26
+ #
27
+ # name: 'AudioZero'
28
+ # author: /konstantin/i - regexp supported
29
+ # architectures: [ 'avr' ] - array is matched if it's a subset
30
+ # version: proc do |value| — or a proc for max flexibility
31
+ # value.start_with?('1.') )
32
+ # end
33
+ #
34
+ # @param [Database] database db instance (or skip it to use the default)
35
+ # @param [Hash] opts hash of attribute names and values to match
36
+ # @return Array<Model> array of models that match
37
+ def search(database = db_default, **opts)
38
+ Arduino::Library::Model.database = database
39
+ database.search(**opts)
40
+ end
41
+ end
42
+ end
43
+ end
@@ -1,5 +1,7 @@
1
1
  require_relative 'types'
2
2
  require_relative 'utilities'
3
+ require_relative 'instance_methods'
4
+ require_relative 'resolver'
3
5
  require 'json'
4
6
 
5
7
  module Arduino
@@ -7,6 +9,7 @@ module Arduino
7
9
  # This class represents a single entry into the library-index.json file,
8
10
  # in other words — a `library.properties` file.
9
11
  class Model < Dry::Struct
12
+ include Comparable
10
13
 
11
14
  # noinspection RubyResolve
12
15
  constructor_type :symbolized
@@ -15,8 +18,30 @@ module Arduino
15
18
  self.attribute field, eval(type)
16
19
  end
17
20
 
21
+ # Instance Methods
22
+
23
+ # Convert a version such as '1.44.3' into a number '1044003' for easy
24
+ # sorting and comparison.
25
+ def version_to_i
26
+ if version
27
+ first, second, third = version.split(/\./).map(&:to_i)
28
+ 10**6 * (first || 0) + 10**3 * (second || 0) + (third || 0)
29
+ else
30
+ 0
31
+ end
32
+ rescue
33
+ 0
34
+ end
35
+
36
+ def <=>(another)
37
+ self.version_to_i <=> another.version_to_i
38
+ end
39
+
40
+ # Class Methods
41
+
18
42
  class << self
19
43
  include Utilities
44
+ include InstanceMethods
20
45
 
21
46
  attr_writer :database
22
47
 
@@ -29,7 +54,7 @@ module Arduino
29
54
  end
30
55
 
31
56
  def from_json_file(file_or_url)
32
- file = read_file_or_url(file_or_url)
57
+ file = read_file_or_url(file_or_url)
33
58
  from_json(file.read)
34
59
  end
35
60
 
@@ -75,26 +100,26 @@ module Arduino
75
100
  #
76
101
  # @return [Model | Array<Model> ] — array for search, otherwise a model
77
102
  def from(source = nil, **opts)
78
- case source
79
- when Hash
80
- from_hash(source)
81
- when String
82
- if source =~ /^{/m
83
- from_json(source)
84
- elsif File.exist?(source)
85
- if source =~ /\.json(\.gz)?$/i
86
- from_json_file(source)
87
- elsif source =~ /\.properties(\.gz)?$/i
88
- from_properties_file(source)
89
- end
90
- end
91
- when NilClass
92
- if opts && opts[:name] && opts[:version]
93
- search(**opts)
94
- end
95
- end
103
+ model = case source
104
+ when Hash
105
+ from_hash(source)
106
+ when String
107
+ if source =~ /^{/m
108
+ from_json(source)
109
+ elsif File.exist?(source)
110
+ if source =~ /\.json(\.gz)?$/i
111
+ from_json_file(source)
112
+ elsif source =~ /\.properties(\.gz)?$/i
113
+ from_properties_file(source)
114
+ end
115
+ end
116
+ when NilClass
117
+ if opts && opts[:name] && opts[:version]
118
+ search(**opts)
119
+ end
120
+ end
121
+ model ? Resolver.resolve(model) : model
96
122
  end
97
-
98
123
  end
99
124
  end
100
125
  end
@@ -60,4 +60,3 @@ module Arduino
60
60
  end
61
61
  end
62
62
  end
63
-
@@ -0,0 +1,62 @@
1
+ require 'arduino/library'
2
+ require 'arduino/library/instance_methods'
3
+ require 'arduino/library/model'
4
+
5
+ module Arduino
6
+ module Library
7
+ # This method is used internally by the Model class's #from method.
8
+ module Resolver
9
+ class << self
10
+ include ::Arduino::Library::InstanceMethods
11
+
12
+ # Resolves a given model without a URL by performing a
13
+ # search in the Ardiuino Library for the library name and version.
14
+ #
15
+ # model = Arduino::Library::Resolver.resolve({ name: 'AudioZero'} )
16
+ # # => <Arduino::Library::Model#0x3242gfa2...>
17
+ #
18
+ # model.url # => 'https://github.com/.......'
19
+ #
20
+ # @param [Model] model with a partial information only, such as the name.
21
+ # @return [Model] a resolved model with #url provided, if found, nil otherwise.
22
+ def resolve(model)
23
+ raise ArgumentError, 'Model argument is required' unless model
24
+ model = Model.from(model) unless model.is_a?(Model)
25
+ return model if model && model.url
26
+
27
+ query = construct_query(model)
28
+ return nil if query.empty?
29
+
30
+ latest_version_by(query)
31
+ end
32
+
33
+ # Given a model with partial information, constructs a query
34
+ # by name and version.
35
+ # @param [Model] model a library model with name, and optionally version
36
+ # @return [Hash] query to be passed to #search. (See Arduino::Library::InstanceMethods#search)
37
+ def construct_query(model)
38
+ query = {}
39
+ query.merge!(name: model.name) if model.name
40
+ query.merge!(version: model.version) if model.version
41
+ query
42
+ end
43
+
44
+ # Executes a given query, and if more than one version is returned
45
+ # returns the last most recent version of the library.
46
+ #
47
+ # @param [Hash] query model attributes to search for, eg, +name: 'AudioZero'
48
+ # @return <Model> search result, or the most recent version if many match
49
+ def latest_version_by(query)
50
+ results = if query.key?(:name)
51
+ Model.find(**query).sort
52
+ else
53
+ Model.find(**query)
54
+ end
55
+ return nil if results.size == 0
56
+ return results.first if results.size == 1
57
+ results.last
58
+ end
59
+ end
60
+ end
61
+ end
62
+ end
@@ -39,6 +39,8 @@ module Arduino
39
39
  end
40
40
 
41
41
  def download(url, path)
42
+ debug "dowloading from [#{url.to_s.bold.red}]"
43
+ debug " to [#{path.to_s.bold.green}]"
42
44
  open(path, 'wb') do |file|
43
45
  file << open(url).read
44
46
  end
@@ -1,6 +1,6 @@
1
1
  module Arduino
2
2
  module Library
3
- VERSION = '0.3.2'
3
+ VERSION = '0.4.0'
4
4
  DESCRIPTION = <<-eof
5
5
  This gem encapsulates many concepts related to how Arduino Libraries are indexed, how their metadata is validated, or .properties file generated. It supports searching the Arduino library database for any terms. This gem is used by Arli — Arduino Installer CLI toolkit.
6
6
  eof
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: arduino-library
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.3.2
4
+ version: 0.4.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Konstantin Gredeskoul
8
8
  autorequire:
9
9
  bindir: exe
10
10
  cert_chain: []
11
- date: 2017-10-23 00:00:00.000000000 Z
11
+ date: 2017-11-03 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: dry-configurable
@@ -150,6 +150,20 @@ dependencies:
150
150
  - - ">="
151
151
  - !ruby/object:Gem::Version
152
152
  version: '0'
153
+ - !ruby/object:Gem::Dependency
154
+ name: irbtools
155
+ requirement: !ruby/object:Gem::Requirement
156
+ requirements:
157
+ - - ">="
158
+ - !ruby/object:Gem::Version
159
+ version: '0'
160
+ type: :development
161
+ prerelease: false
162
+ version_requirements: !ruby/object:Gem::Requirement
163
+ requirements:
164
+ - - ">="
165
+ - !ruby/object:Gem::Version
166
+ version: '0'
153
167
  description: " This gem encapsulates many concepts related to how Arduino Libraries
154
168
  are indexed, how their metadata is validated, or .properties file generated. It
155
169
  supports searching the Arduino library database for any terms. This gem is used
@@ -174,8 +188,10 @@ files:
174
188
  - lib/arduino/library/database.rb
175
189
  - lib/arduino/library/default_database.rb
176
190
  - lib/arduino/library/include.rb
191
+ - lib/arduino/library/instance_methods.rb
177
192
  - lib/arduino/library/model.rb
178
193
  - lib/arduino/library/presenters/properties.rb
194
+ - lib/arduino/library/resolver.rb
179
195
  - lib/arduino/library/types.rb
180
196
  - lib/arduino/library/utilities.rb
181
197
  - lib/arduino/library/version.rb