cartocss_helper 1.2.1 → 4.0.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -1,11 +1,12 @@
1
1
  module CartoCSSHelper
2
2
  class StyleSpecificData
3
- attr_reader :min_z, :max_z, :list_of_documented_tags, :list_of_documented_compositions
4
- def initialize(min_z, max_z, list_of_documented_tags, list_of_documented_compositions)
3
+ attr_reader :min_z, :max_z, :list_of_documented_tags, :list_of_documented_compositions, :name_label_is_not_required
4
+ def initialize(min_z, max_z, list_of_documented_tags, list_of_documented_compositions, name_label_is_not_required)
5
5
  @min_z = min_z
6
6
  @max_z = max_z
7
7
  @list_of_documented_tags = list_of_documented_tags
8
8
  @list_of_documented_compositions = list_of_documented_compositions
9
+ @name_label_is_not_required = name_label_is_not_required
9
10
  end
10
11
  end
11
- end
12
+ end
@@ -6,12 +6,13 @@ include CartoCSSHelper::Heuristic
6
6
  module CartoCSSHelper
7
7
  class TagRenderingStatus
8
8
  attr_accessor :key, :value, :state, :composite
9
- def initialize(key, value, state, composite=nil)
9
+ def initialize(key, value, state, composite = nil)
10
10
  @key = key
11
11
  @value = value
12
12
  @state = state
13
13
  @composite = composite
14
14
  end
15
+
15
16
  def print
16
17
  composite_string = ''
17
18
  if composite
@@ -19,60 +20,103 @@ module CartoCSSHelper
19
20
  end
20
21
  puts "#{@key}=#{@value} #{@state} #{composite_string}"
21
22
  end
23
+
22
24
  def code_print
23
25
  string = "Status.new('#{@key}', '#{@value}', :#{@state}"
24
- if @composite != nil
25
- string << ", #{@composite.to_s}"
26
- end
26
+ string << ", #{@composite}" if @composite != nil
27
27
  string << '),'
28
28
  puts string
29
29
  end
30
30
  end
31
31
 
32
32
  class Info
33
- def get_expected_composite(key, value)
34
- CartoCSSHelper::Configuration.get_style_specific_data.list_of_documented_tags.each { |documented|
35
- if documented.key == key
36
- if documented.value == value
37
- return documented.composite
38
- end
39
- end
40
- }
33
+ def self.get_expected_state(key, value)
34
+ CartoCSSHelper::Configuration.get_style_specific_data.list_of_documented_tags.each do |documented|
35
+ next unless documented.key == key
36
+ return documented.state if documented.value == value
37
+ end
38
+ return nil
39
+ end
40
+
41
+ def self.get_expected_composite(key, value)
42
+ CartoCSSHelper::Configuration.get_style_specific_data.list_of_documented_tags.each do |documented|
43
+ next unless documented.key == key
44
+ return documented.composite if documented.value == value
45
+ end
41
46
  return nil
42
47
  end
43
48
 
44
49
  def print_render_state_of_tags(git_branch)
45
50
  Git.checkout git_branch
46
- get_render_state_of_tags.each { |state|
51
+ get_render_state_of_tags.each do |state|
47
52
  state.code_print
48
- }
53
+ end
49
54
  end
50
55
 
51
- def get_render_state_of_tags
56
+ def get_render_state_of_tags(quick_and_more_prone_to_errors)
52
57
  states = []
53
58
  @last_composite = nil
54
- Heuristic.get_tags.each { |tag|
59
+ Heuristic.get_tags.each do |tag|
55
60
  key = tag[0]
56
61
  value = tag[1]
57
- #print_render_state_of_tag key, value
58
- state = get_render_state_of_tag(key, value)
62
+ # print_render_state_of_tag key, value
63
+ state = get_render_state_of_tag(key, value, quick_and_more_prone_to_errors)
59
64
  states.push(TagRenderingStatus.new(key, value, state, @last_composite))
60
- }
65
+ end
61
66
  return states
62
67
  end
63
68
 
64
- def get_render_state_of_tag(key, value)
65
- if is_rendered key, value
69
+ def get_render_state_of_tag(key, value, quick_and_more_prone_to_errors)
70
+ if Info.get_expected_state(key, value) == :ignored
66
71
  @last_composite = nil
72
+ return :ignored
73
+ end
74
+ zlevels = [22, 13] # TODO: - this is specially tuned for Default
75
+ expected_composite = Info.get_expected_composite(key, value)
76
+ if quick_and_more_prone_to_errors
77
+ return get_render_state_of_tag_quick_heurestic(key, value, expected_composite, zlevels)
78
+ end
79
+ return get_render_state_of_tag_thorough(key, value, expected_composite, zlevels)
80
+ end
81
+
82
+ def get_render_state_of_tag_quick_heurestic
83
+ if expected_composite != nil
84
+ return assume_that_only_this_composite_can_match(key, value, zlevels, expected_composite)
85
+ else
86
+ return asssume_that_no_composite_will_match(key, value, zlevels)
87
+ end
88
+ end
89
+
90
+ def assume_that_only_this_composite_can_match(key, value, zlevels, expected_composite)
91
+ if is_rendered_as_composite key, value, expected_composite, zlevels
92
+ @last_composite = how_rendered_as_composite key, value, expected_composite, zlevels
93
+ return :composite
94
+ else
95
+ @last_composite = nil
96
+ return :ignored
97
+ end
98
+ end
99
+
100
+ def asssume_that_no_composite_will_match(key, value, zlevels)
101
+ @last_composite = nil
102
+ if is_rendered key, value, zlevels
67
103
  return :primary
68
104
  else
69
- if is_rendered_as_composite key, value, get_expected_composite(key, value)
70
- @last_composite = how_rendered_as_composite key, value, get_expected_composite(key, value)
71
- return :composite
72
- else
73
- @last_composite = nil
74
- return :ignored
75
- end
105
+ return :ignored
106
+ end
107
+ end
108
+
109
+ def get_render_state_of_tag_thorough(key, value, expected_composite, zlevels)
110
+ if is_rendered key, value, zlevels
111
+ @last_composite = nil
112
+ return :primary
113
+ end
114
+ if is_rendered_as_composite key, value, expected_composite
115
+ @last_composite = how_rendered_as_composite key, value, expected_composite
116
+ return :composite
117
+ else
118
+ @last_composite = nil
119
+ return :ignored
76
120
  end
77
121
  end
78
122
 
@@ -83,82 +127,69 @@ module CartoCSSHelper
83
127
  puts "#{key}=#{value} - primary generic tag value"
84
128
  elsif is_key_rendered_and_value_ignored(key, value)
85
129
  puts "#{key}=#{value} - primary, but rendering the same as generic value"
86
- elsif
87
- puts "#{key}=#{value} - primary"
88
- end
89
- else
90
- if is_rendered_as_composite key, value, @last_composite
91
- @last_composite = how_rendered_as_composite key, value, @last_composite
92
- puts "#{key}=#{value} - composite with #{@last_composite} - and maybe other tags"
93
130
  else
94
- @last_composite = nil
95
- puts "#{key}=#{value} - not displayed"
131
+ puts "#{key}=#{value} - primary"
96
132
  end
133
+ elsif is_rendered_as_composite key, value, @last_composite
134
+ @last_composite = how_rendered_as_composite key, value, @last_composite
135
+ puts "#{key}=#{value} - composite with #{@last_composite} - and maybe other tags"
136
+ else
137
+ @last_composite = nil
138
+ puts "#{key}=#{value} - not displayed"
97
139
  end
98
140
  end
99
141
 
100
142
  def is_key_rendered_and_value_ignored(key, value)
101
- if not is_rendered key,get_generic_tag_value
102
- return false
103
- end
104
- [false, true].each { |on_water|
105
- [Configuration.get_max_z].each { |zlevel|
106
- ['area', 'closed_way', 'way', 'node'].each{ |type|
107
- if CartoCSSHelper::Info.rendered_on_zlevel({key => value}, type, zlevel, on_water)
108
- if !is_key_rendered_and_value_ignored_set(key, value, type, zlevel, on_water)
109
- return false
110
- end
143
+ return false if notis_rendered key, get_generic_tag_value
144
+ [false, true].each do |on_water|
145
+ [Configuration.get_max_z].each do |zlevel|
146
+ ['area', 'closed_way', 'way', 'node'].each do |type|
147
+ next unless CartoCSSHelper::Info.rendered_on_zlevel({ key => value }, type, zlevel, on_water)
148
+ unless is_key_rendered_and_value_ignored_set(key, value, type, zlevel, on_water)
149
+ return false
111
150
  end
112
- }
113
- }
114
- }
151
+ end
152
+ end
153
+ end
115
154
  return true
116
155
  end
117
156
 
118
157
  def is_key_rendered_and_value_ignored_set(key, value, type, zlevel, on_water)
119
- with_tested_value = Scene.new({key => value}, zlevel, on_water, type)
120
- with_generic_value = Scene.new({key => get_generic_tag_value}, zlevel, on_water, type)
158
+ with_tested_value = Scene.new({ key => value }, zlevel, on_water, type, true)
159
+ with_generic_value = Scene.new({ key => get_generic_tag_value }, zlevel, on_water, type, true)
121
160
  return !with_tested_value.is_output_different(with_generic_value)
122
161
  end
123
162
 
124
- def is_rendered(key, value)
125
- [false, true].each { |on_water|
126
- [Configuration.get_max_z].each { |zlevel| #TODO - note that some tags may be rendered up to X zoom level, but checking all zlevels would take too much time
127
- ['area', 'closed_way', 'way', 'node'].each{ |type|
128
- if CartoCSSHelper::Info.rendered_on_zlevel({key => value}, type, zlevel, on_water)
163
+ def is_rendered(key, value, zlevels = [Configuration.get_max_z]) # TODO: - note that some tags may be rendered up to X zoom level, but checking all zlevels would take too much time
164
+ [false, true].each do |on_water|
165
+ zlevels.each do |zlevel| #
166
+ ['area', 'closed_way', 'way', 'node'].each do |type|
167
+ if CartoCSSHelper::Info.rendered_on_zlevel({ key => value }, type, zlevel, on_water)
129
168
  return true
130
169
  end
131
- }
132
- }
133
- }
170
+ end
171
+ end
172
+ end
134
173
  return false
135
174
  end
136
175
 
137
- def is_rendered_as_composite(key, value, suggested_composite=nil)
138
- reason = how_rendered_as_composite key, value, suggested_composite
139
- if reason == nil
140
- return false
141
- end
176
+ def is_rendered_as_composite(key, value, suggested_composite = nil, zlevels = [Configuration.get_max_z]) # TODO: - note that some tags may be rendered up to X zoom level, but checking all zlevels would take too much time
177
+ reason = how_rendered_as_composite key, value, suggested_composite, zlevels
178
+ return false if reason == nil
142
179
  return true
143
180
  end
144
181
 
145
- def how_rendered_as_composite(key, value, suggested_composite)
146
- [false, true].each { |on_water|
147
- [Configuration.get_max_z].each { |zlevel|
148
- result = how_rendered_on_zlevel_as_composite({key => value}, 'closed_way', zlevel, on_water, suggested_composite)
149
- if result != nil
150
- return result
151
- end
152
- result = how_rendered_on_zlevel_as_composite({key => value}, 'way', zlevel, on_water, suggested_composite)
153
- if result != nil
154
- return result
155
- end
156
- result = how_rendered_on_zlevel_as_composite({key => value}, 'node', zlevel, on_water, suggested_composite)
157
- if result != nil
158
- return result
159
- end
160
- }
161
- }
182
+ def how_rendered_as_composite(key, value, suggested_composite, zlevels = [Configuration.get_max_z]) # TODO: - note that some tags may be rendered up to X zoom level, but checking all zlevels would take too much time
183
+ [false, true].each do |on_water|
184
+ zlevels.each do |zlevel|
185
+ result = how_rendered_on_zlevel_as_composite({ key => value }, 'closed_way', zlevel, on_water, suggested_composite)
186
+ return result if result != nil
187
+ result = how_rendered_on_zlevel_as_composite({ key => value }, 'way', zlevel, on_water, suggested_composite)
188
+ return result if result != nil
189
+ result = how_rendered_on_zlevel_as_composite({ key => value }, 'node', zlevel, on_water, suggested_composite)
190
+ return result if result != nil
191
+ end
192
+ end
162
193
  if suggested_composite != nil
163
194
  return how_rendered_as_composite key, value, nil
164
195
  end
@@ -166,8 +197,8 @@ module CartoCSSHelper
166
197
  end
167
198
 
168
199
  def self.rendered_on_zlevel(tags, type, zlevel, on_water)
169
- empty = Scene.new({}, zlevel, on_water, type)
170
- tested = Scene.new(tags, zlevel, on_water, type)
200
+ empty = Scene.new({}, zlevel, on_water, type, true)
201
+ tested = Scene.new(tags, zlevel, on_water, type, true)
171
202
  return tested.is_output_different(empty)
172
203
  end
173
204
 
@@ -180,44 +211,37 @@ module CartoCSSHelper
180
211
  end
181
212
  return nil
182
213
  end
183
- CartoCSSHelper::Configuration.get_style_specific_data.list_of_documented_compositions.each { |composite|
214
+ CartoCSSHelper::Configuration.get_style_specific_data.list_of_documented_compositions.each do |composite|
184
215
  if is_rendered_with_this_composite tags, type, composite, zlevel, on_water
185
216
  return composite
186
217
  end
187
- }
218
+ end
188
219
  return nil
189
220
  end
190
221
 
222
+ def deep_clone(input)
223
+ return Marshal.load(Marshal.dump(input))
224
+ end
225
+
191
226
  def is_rendered_with_this_composite(tags, type, provided_composite, zlevel, on_water)
192
- #puts "<<<\n#{tags}\n#{composite}<<<\n\n"
193
- # noinspection RubyResolve
194
- # see https://youtrack.jetbrains.com/issue/RUBY-16061
195
- tags_with_composite = Marshal.load(Marshal.dump(tags))
196
- # noinspection RubyResolve
197
- # see https://youtrack.jetbrains.com/issue/RUBY-16061
198
- composite = Marshal.load(Marshal.dump(provided_composite))
199
- composite.each { |key, value|
227
+ tags_with_composite = deep_clone(tags)
228
+ composite = deep_clone(provided_composite)
229
+ composite.each do |key, value|
200
230
  if tags_with_composite[key] != nil
201
- return false #shadowing
231
+ return false # shadowing
202
232
  end
203
233
  tags_with_composite[key] = value
204
- }
205
- with_composite = Scene.new(tags_with_composite, zlevel, on_water, type)
206
- only_composite = Scene.new(composite, zlevel, on_water, type)
207
- empty = Scene.new({}, zlevel, on_water, type)
208
- if with_composite.is_output_different(empty)
209
- if with_composite.is_output_different(only_composite)
210
- if composite['area'] != nil
211
- return true
212
- end
213
- composite['area'] = 'yes'
214
- composite_interpreted_as_area = Scene.new(composite, zlevel, on_water, type)
215
- if with_composite.is_output_different(composite_interpreted_as_area)
216
- return true
217
- end
218
- end
219
234
  end
220
- return false
235
+ with_composite = Scene.new(tags_with_composite, zlevel, on_water, type, true)
236
+ only_composite = Scene.new(composite, zlevel, on_water, type, true)
237
+ empty = Scene.new({}, zlevel, on_water, type, true)
238
+ return false if with_composite.is_output_identical(empty)
239
+ return false if with_composite.is_output_identical(only_composite)
240
+ return true if composite['area'] != nil
241
+ composite['area'] = 'yes'
242
+ composite_interpreted_as_area = Scene.new(composite, zlevel, on_water, type, true)
243
+ return false if with_composite.is_output_identical(composite_interpreted_as_area)
244
+ return true
221
245
  end
222
246
  end
223
- end
247
+ end
@@ -3,4 +3,4 @@ module FileHelper
3
3
  def self.make_string_usable_as_filename(string)
4
4
  return string.gsub(/[\x00\/\\:\*\?\"<>\|]/, '_')
5
5
  end
6
- end
6
+ end
@@ -0,0 +1,49 @@
1
+ require_relative 'generic_downloader.rb'
2
+
3
+ class GenericCachedDownloader
4
+ def initialize(timeout: 20, error_message: nil, stop_on_timeout: true, wrapper: RestClientWrapper.new)
5
+ @request_timeout = timeout
6
+ @error_message = error_message
7
+ @stop_on_timeout = stop_on_timeout
8
+ @wrapper = wrapper
9
+ end
10
+
11
+ def get_specified_resource(url, cache_filename, description: nil, invalidate_cache: false)
12
+ cache = read_from_cache(cache_filename)
13
+ cache = nil if invalidate_cache
14
+ return cache if cache != nil
15
+ response = download(url, description)
16
+ write_cache(response, cache_filename)
17
+
18
+ return response
19
+ end
20
+
21
+ def read_from_cache(cache_filename)
22
+ if File.exist?(cache_filename)
23
+ file = File.new(cache_filename)
24
+ cached = file.read
25
+ file.close
26
+ return cached
27
+ end
28
+ return nil
29
+ end
30
+
31
+ def get_cache_timestamp(cache_filename)
32
+ return nil unless File.exist?(cache_filename)
33
+ f = File.new(cache_filename)
34
+ timestamp = f.mtime.to_i
35
+ f.close
36
+ return timestamp
37
+ end
38
+
39
+ def download(url, description)
40
+ downloader = GenericDownloader.new(timeout: @request_timeout, error_message: @error_message, stop_on_timeout: @stop_on_timeout, wrapper: @wrapper)
41
+ return downloader.get_specified_resource(url, description: description)
42
+ end
43
+
44
+ def write_cache(response, cache_filename)
45
+ file = File.new(cache_filename, 'w')
46
+ file.write response
47
+ file.close
48
+ end
49
+ end
@@ -0,0 +1,65 @@
1
+ require 'ruby-progressbar'
2
+ require_relative 'rest-client_wrapper.rb'
3
+ require_relative 'logger.rb'
4
+
5
+ class BuggyRestClient < StandardError
6
+ end
7
+
8
+ class ExceptionWithResponse < StandardError
9
+ attr_accessor :http_code, :response
10
+ end
11
+
12
+ class ExceptionWithoutResponse < StandardError
13
+ attr_accessor :http_code, :response
14
+ end
15
+
16
+ class RequestTimeout < StandardError
17
+ end
18
+
19
+ class GenericDownloader
20
+ def initialize(timeout: 20, error_message: nil, stop_on_timeout: true, wrapper: RestClientWrapper.new)
21
+ @request_timeout = timeout
22
+ @retry_count = 0
23
+ @error_message = error_message
24
+ @stop_on_timeout = stop_on_timeout
25
+ @wrapper = wrapper
26
+ end
27
+
28
+ def max_retry_count
29
+ 5
30
+ end
31
+
32
+ def output_shared_error_part(url, e)
33
+ Log.warn @error_message unless @error_message.nil?
34
+ Log.warn
35
+ Log.warn url
36
+ Log.warn
37
+ Log.warn e.class
38
+ Log.warn e
39
+ end
40
+
41
+ def retry_allowed(exception_with_response)
42
+ raise exception_with_response if @retry_count > max_retry_count
43
+ if @stop_on_timeout
44
+ raise exception_with_response if exception_with_response.is_a?(RequestTimeout)
45
+ end
46
+ if [429, 503, 504].include?(exception_with_response.http_code)
47
+ @retry_count += 1
48
+ return true
49
+ end
50
+ raise exception_with_response
51
+ end
52
+
53
+ def get_specified_resource(url, description: nil)
54
+ Log.info description if description
55
+ return @wrapper.fetch_data_from_url(url, @request_timeout)
56
+ rescue ExceptionWithResponse => e
57
+ output_shared_error_part(url, e)
58
+ Log.warn e.response
59
+ Log.warn e.http_code
60
+ get_specified_resource(url) if retry_allowed(e)
61
+ rescue ExceptionWithoutResponse => e
62
+ output_shared_error_part(url, e)
63
+ raise e
64
+ end
65
+ end