stockboy 0.8.0 → 0.8.1

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: 90e9bfd03d069c571ffd1e6e03dd018cf477289c
4
- data.tar.gz: f0f88cdbbf0e65a8eadddf0e390d91f3c1a5f4c4
3
+ metadata.gz: e9478014be3b55b4e3c8c106a418e4f8fb9940bd
4
+ data.tar.gz: 46ca2d7e3bd6d567eca0f3ae26842a522c231d3b
5
5
  SHA512:
6
- metadata.gz: d0686581b72dd43ef079e93f8b3336669f50919e5f8adaa5019b198d4ce39b61771584ffcab122640cadbe1bdb372d4745bb4f444ee3d3d799833f2f73215b2f
7
- data.tar.gz: 1b11eae674ea31430894a4e4f050e91f2011841a94f72c6b580269f446eab4a5e4baacdda616c70e3b0a889b13fdd8fa51633fec9e936401bd01399f45857ab1
6
+ metadata.gz: 74ae4dc70a0676ef4677e7fc62f700e291a6681996b27e9dae7112a136ba5ccb835ac53c5cced0cfedf8d3b9bc21fa83052e70b1fd5dc0288bc57ae129648451
7
+ data.tar.gz: 4ae8f8e91b4368e3aa5cc1a486ffa4cff87e9eb9aa68f0c198d840d80fa0346c2ba2a012ae60f8d25ac94d080d50917b732725af67f8e22325a7c7dbea8ce0ae
data/CHANGELOG.md CHANGED
@@ -1,5 +1,10 @@
1
1
  # Changelog
2
2
 
3
+ ## 0.8.1 / 2014-04-24
4
+
5
+ * [BUGFIX] Support `data_size` for non-string providers
6
+ * [BUGFIX] Checks for nil data and nil configuration options
7
+
3
8
  ## 0.8.0 / 2014-04-02
4
9
 
5
10
  * [ENHANCEMENT] Expose `data_time` and `data_size` in repeater
data/README.md CHANGED
@@ -5,10 +5,10 @@
5
5
  [![Build Status](https://travis-ci.org/avit/stockboy.png)][travis]
6
6
  [![Code Climate](https://codeclimate.com/github/avit/stockboy.png)][climate]
7
7
 
8
- Stockboy helps you receive and unpack data onto your shelves. You might
9
- consider using it to synchronize data exported from external sources, or
10
- migrating your own data from legacy systems. (TL;DR, Stockboy is a Ruby
11
- [DSL][dsl] for doing [ETL][etl].)
8
+ Stockboy helps you receive and unpack data onto your shelves. It provides a DSL
9
+ for configuring data processing pipelines. You might consider using it to
10
+ synchronize data exported from external sources, as part of an [ETL][etl]
11
+ workflow, or migrating your own data from legacy systems.
12
12
 
13
13
  Full documentation available at [rdoc.info/gems/stockboy][rdoc]
14
14
 
data/lib/stockboy/job.rb CHANGED
@@ -116,6 +116,14 @@ module Stockboy
116
116
  provider.errors.empty?
117
117
  end
118
118
 
119
+ def data(&block)
120
+ provider.data(&block)
121
+ end
122
+
123
+ def data?(reduction=:all?)
124
+ provider.data?(reduction)
125
+ end
126
+
119
127
  # Count of all processed records
120
128
  #
121
129
  # @!attribute [r] total_records
@@ -209,6 +217,7 @@ module Stockboy
209
217
  def load_records
210
218
  reset
211
219
  load_all_records
220
+ return unless provider.data?
212
221
  partition_all_records
213
222
  @processed = true
214
223
  end
@@ -234,14 +243,20 @@ module Stockboy
234
243
  end
235
244
  end
236
245
 
246
+ # Allows for a data method that either yields or returns giving preference
247
+ # to the yield. It will ignore the data return value if it has yielded.
248
+ #
237
249
  def with_provider_data
238
250
  return to_enum(__method__) unless block_given?
239
251
  yielded = nil
240
252
  provider.data do |data|
241
- yielded = true
242
- yield data
253
+ if data
254
+ yielded = true
255
+ yield data
256
+ end
243
257
  end
244
- yield provider.data unless yielded
258
+ return if yielded
259
+ yield(provider.data) if provider.data
245
260
  end
246
261
 
247
262
  def record_partition(record)
@@ -81,8 +81,11 @@ module Stockboy
81
81
  @data
82
82
  end
83
83
 
84
- def data?
85
- @data_size && @data_size > 0
84
+ # Determine if there is returned data
85
+ #
86
+ def data?(_=nil)
87
+ return nil unless @data
88
+ @data && !@data.empty?
86
89
  end
87
90
 
88
91
  # Reset received data
@@ -5,22 +5,57 @@ module Stockboy
5
5
 
6
6
  YIELD_ONCE = proc { |output, provider| output << provider }
7
7
 
8
+ ProviderStats = Struct.new(:data_time, :data_size, :data_) do
9
+ def self.from(provider)
10
+ new(provider.data_time, provider.data_size, provider.data?)
11
+ end
12
+
13
+ alias :data? :data_ # 1.9 compatibility
14
+ end
15
+
8
16
  attr_reader :base_provider
9
- attr_reader :data_size
10
- attr_reader :data_time
11
17
 
12
18
  def initialize(provider, &yielder)
13
19
  @orig_provider = provider
14
20
  @base_provider = provider.dup
21
+ @iterations = []
15
22
  @yielder = yielder || YIELD_ONCE
16
23
  end
17
24
 
18
- def data?
19
- @data_size && @data_size > 0
25
+ # Determine if there was any returned data after processing iterations
26
+ # @param [:all?,:any?,:one?] reduction
27
+ # Specify if all iterations must return data to be valid, or just any
28
+ #
29
+ def data?(reduction = :all?)
30
+ return nil if data_iterations == 0
31
+ @iterations.send(reduction, &:data?)
32
+ end
33
+
34
+ # Get the total data size returned after processing iterations
35
+ #
36
+ def data_size
37
+ @iterations.reduce(nil) { |sum, source|
38
+ source.data_size ? source.data_size + sum.to_i : sum
39
+ }
40
+ end
41
+
42
+ # Get the last data time returned after processing iterations
43
+ #
44
+ def data_time
45
+ @iterations.reduce(nil) { |max, source|
46
+ source.data_time && (max.nil? || source.data_time > max) ? source.data_time : max
47
+ }
48
+ end
49
+
50
+ def data_iterations
51
+ @iterations.size
20
52
  end
21
53
 
22
54
  def data
23
- raise ArgumentError, "expects a block for yielding each data set" unless block_given?
55
+ unless block_given?
56
+ raise ArgumentError, "expect a block for yielding data iterations"
57
+ end
58
+
24
59
  each do |nth_provider|
25
60
  yield fetch_iteration_data(nth_provider)
26
61
  end
@@ -28,7 +63,7 @@ module Stockboy
28
63
 
29
64
  def clear
30
65
  @base_provider = @orig_provider.dup
31
- @data_time, @data_size = nil, nil
66
+ @iterations.clear
32
67
  super
33
68
  end
34
69
 
@@ -67,8 +102,7 @@ module Stockboy
67
102
 
68
103
  def fetch_iteration_data(provider)
69
104
  if provider.data
70
- @data_size = [@data_size, provider.data_size].compact.reduce(&:+)
71
- @data_time = [@data_time, provider.data_time].compact.max
105
+ @iterations << ProviderStats.from(provider)
72
106
  end
73
107
  provider.data
74
108
  end
@@ -116,6 +116,7 @@ module Stockboy::Providers
116
116
  rescue Net::FTPError => e
117
117
  errors << e.message
118
118
  logger.warn e.message
119
+ nil
119
120
  end
120
121
 
121
122
  def matching_file
@@ -61,7 +61,7 @@ module Stockboy::Providers
61
61
  dsl_attr :password
62
62
 
63
63
  def uri
64
- return nil if @uri.nil? || @uri.empty?
64
+ return nil if @uri.nil? || @uri.to_s.empty?
65
65
  URI(@uri).tap { |u| u.query = URI.encode_www_form(@query) if @query }
66
66
  end
67
67
 
@@ -126,18 +126,18 @@ module Stockboy::Providers
126
126
 
127
127
  def client
128
128
  orig_logger, HTTPI.logger = HTTPI.logger, logger
129
- req = HTTPI::Request.new(uri)
129
+ req = HTTPI::Request.new.tap { |c| c.url = uri }
130
130
  req.auth.basic(username, password) if username && password
131
- yield req if block_given?
131
+ block_given? ? yield(req) : req
132
+ ensure
132
133
  HTTPI.logger = orig_logger
133
- req
134
134
  end
135
135
 
136
136
  private
137
137
 
138
138
  def validate
139
- errors << "uri must be specified" if uri.blank?
140
- errors << "method (:get, :post) must be specified" if method.blank?
139
+ errors << "uri must be specified" unless uri
140
+ errors << "method (:get, :post) must be specified" unless method
141
141
  errors.empty?
142
142
  end
143
143
 
@@ -1,3 +1,3 @@
1
1
  module Stockboy
2
- VERSION = "0.8.0"
2
+ VERSION = "0.8.1"
3
3
  end
@@ -12,6 +12,7 @@ class TestProvider
12
12
  end
13
13
  def data_size; @data && @data.size end
14
14
  def data_time; @data && Time.now end
15
+ def data?; true end
15
16
  end
16
17
 
17
18
  class TestReader
@@ -79,7 +79,7 @@ module Stockboy
79
79
  its(:data_size) { should be_nil }
80
80
 
81
81
  context "after fetching" do
82
- before { provider.data }
82
+ before { provider.fetch_data }
83
83
  its(:data_size) { should be > 0 }
84
84
  end
85
85
  end
@@ -88,8 +88,8 @@ module Stockboy
88
88
  subject(:provider) { ProviderSubclass.new }
89
89
  its(:data_time) { should be_nil }
90
90
 
91
- context "after iterating" do
92
- before { provider.data }
91
+ context "after fetching" do
92
+ before { provider.fetch_data }
93
93
  its(:data_time) { should be_a Time }
94
94
  end
95
95
  end
@@ -98,8 +98,8 @@ module Stockboy
98
98
  subject(:provider) { ProviderSubclass.new }
99
99
  its(:data?) { should be_nil }
100
100
 
101
- context "after iterating" do
102
- before { provider.data }
101
+ context "after fetching" do
102
+ before { provider.fetch_data }
103
103
  its(:data?) { should be true }
104
104
  end
105
105
  end
@@ -72,6 +72,20 @@ module Stockboy
72
72
  end
73
73
  end
74
74
 
75
+ describe "#client" do
76
+ subject(:client) { provider.client }
77
+
78
+ before { provider.uri = "http://example.com/" }
79
+
80
+ it "should configure the base url" do
81
+ client.url.host.should == "example.com"
82
+ end
83
+
84
+ it "returns the value of the passed block" do
85
+ provider.client { |http| "DATA" }.should == "DATA"
86
+ end
87
+ end
88
+
75
89
  describe "#data" do
76
90
  let(:response) { HTTPI::Response.new(200, {}, '{"success":true}') }
77
91
 
metadata CHANGED
@@ -1,14 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: stockboy
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.8.0
4
+ version: 0.8.1
5
5
  platform: ruby
6
6
  authors:
7
7
  - Andrew Vit
8
8
  autorequire:
9
9
  bindir: bin
10
10
  cert_chain: []
11
- date: 2014-04-03 00:00:00.000000000 Z
11
+ date: 2014-04-24 00:00:00.000000000 Z
12
12
  dependencies:
13
13
  - !ruby/object:Gem::Dependency
14
14
  name: rake