nanoc-core 4.12.9 → 4.12.11

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.
Files changed (39) hide show
  1. checksums.yaml +4 -4
  2. data/lib/nanoc/core/action_sequence.rb +1 -4
  3. data/lib/nanoc/core/action_sequence_builder.rb +8 -10
  4. data/lib/nanoc/core/basic_item_view.rb +1 -1
  5. data/lib/nanoc/core/basic_outdatedness_checker.rb +135 -0
  6. data/lib/nanoc/core/checksum_collection.rb +3 -1
  7. data/lib/nanoc/core/checksum_store.rb +11 -1
  8. data/lib/nanoc/core/compilation_stages/determine_outdatedness.rb +6 -1
  9. data/lib/nanoc/core/compilation_stages/load_stores.rb +5 -12
  10. data/lib/nanoc/core/configuration.rb +15 -0
  11. data/lib/nanoc/core/dependency_props.rb +2 -2
  12. data/lib/nanoc/core/dependency_store.rb +15 -13
  13. data/lib/nanoc/core/document.rb +5 -1
  14. data/lib/nanoc/core/executor.rb +2 -1
  15. data/lib/nanoc/core/identifiable_collection.rb +16 -33
  16. data/lib/nanoc/core/identifiable_collection_view.rb +54 -10
  17. data/lib/nanoc/core/item.rb +1 -1
  18. data/lib/nanoc/core/item_collection.rb +0 -6
  19. data/lib/nanoc/core/item_rep.rb +18 -0
  20. data/lib/nanoc/core/item_rep_builder.rb +4 -4
  21. data/lib/nanoc/core/item_rep_selector.rb +69 -17
  22. data/lib/nanoc/core/layout.rb +1 -1
  23. data/lib/nanoc/core/layout_collection.rb +0 -6
  24. data/lib/nanoc/core/mutable_document_view_mixin.rb +16 -7
  25. data/lib/nanoc/core/outdatedness_checker.rb +57 -123
  26. data/lib/nanoc/core/outdatedness_rule.rb +31 -3
  27. data/lib/nanoc/core/outdatedness_rules/attributes_modified.rb +6 -6
  28. data/lib/nanoc/core/outdatedness_rules/code_snippets_modified.rb +6 -6
  29. data/lib/nanoc/core/outdatedness_rules/content_modified.rb +3 -3
  30. data/lib/nanoc/core/outdatedness_rules/item_added.rb +3 -3
  31. data/lib/nanoc/core/outdatedness_rules/layout_added.rb +3 -3
  32. data/lib/nanoc/core/outdatedness_rules/not_written.rb +9 -9
  33. data/lib/nanoc/core/outdatedness_rules/rules_modified.rb +12 -10
  34. data/lib/nanoc/core/outdatedness_rules/uses_always_outdated_filter.rb +2 -2
  35. data/lib/nanoc/core/outdatedness_status.rb +6 -1
  36. data/lib/nanoc/core/store.rb +56 -23
  37. data/lib/nanoc/core/version.rb +1 -1
  38. data/lib/nanoc/core.rb +8 -0
  39. metadata +4 -3
@@ -8,23 +8,62 @@ module Nanoc
8
8
  @reps = reps
9
9
  end
10
10
 
11
- class MicroGraph
11
+ # An iterator (FIFO) over an array, with ability to ignore certain
12
+ # elements.
13
+ class ItemRepIgnorableIterator
14
+ def initialize(array)
15
+ @array = array.dup
16
+ end
17
+
18
+ def next_ignoring(ignored)
19
+ elem = @array.shift
20
+ elem = @array.shift while ignored.include?(elem)
21
+ elem
22
+ end
23
+ end
24
+
25
+ # A priority queue that tracks dependencies and can detect circular
26
+ # dependencies.
27
+ class ItemRepPriorityQueue
12
28
  def initialize(reps)
13
- @reps = Set.new(reps)
29
+ # Prio A: most important; prio C: least important.
30
+ @prio_a = []
31
+ @prio_b = ItemRepIgnorableIterator.new(reps)
32
+ @prio_c = []
33
+
34
+ # Stack of things that depend on each other. This is used for
35
+ # detecting and reporting circular dependencies.
14
36
  @stack = []
37
+
38
+ # List of reps that we’ve already seen. Reps from `reps` will end up
39
+ # in here. Reps can end up in here even *before* they come from
40
+ # `reps`, when they are part of a dependency.
41
+ @seen = Set.new
15
42
  end
16
43
 
17
44
  def next
18
- if @stack.any?
19
- @stack.last
20
- elsif @reps.any?
21
- @reps.each { |rep| break rep }.tap do |rep|
22
- @reps.delete(rep)
23
- @stack.push(rep)
24
- end
25
- else
26
- nil
45
+ # Read prio A
46
+ @this = @prio_a.pop
47
+ if @this
48
+ @stack.push(@this)
49
+ return @this
27
50
  end
51
+
52
+ # Read prio B
53
+ @this = @prio_b.next_ignoring(@seen)
54
+ if @this
55
+ @stack.push(@this)
56
+ return @this
57
+ end
58
+
59
+ # Read prio C
60
+ @this = @prio_c.pop
61
+ if @this
62
+ @stack.push(@this)
63
+ return @this
64
+ end
65
+
66
+ nil
28
67
  end
29
68
 
30
69
  def mark_ok
@@ -36,26 +75,39 @@ module Nanoc
36
75
  raise Nanoc::Core::Errors::DependencyCycle.new(@stack + [dep])
37
76
  end
38
77
 
39
- @reps.delete(dep)
40
- @stack.push(dep)
78
+ # `@this` depends on `dep`, so `dep` has to be compiled first. Thus,
79
+ # move `@this` into priority C, and `dep` into priority A.
80
+
81
+ # Put `@this` (item rep that needs `dep` to be compiled first) into
82
+ # priority C (lowest prio).
83
+ @prio_c.push(@this)
84
+
85
+ # Put `dep` (item rep that needs to be compiled first, before
86
+ # `@this`) into priority A (highest prio).
87
+ @prio_a.push(dep)
88
+
89
+ # Remember that we’ve prioritised `dep`. This particular element will
90
+ # come from @prio_b at some point in the future, so we’ll have to skip
91
+ # it then.
92
+ @seen << dep
41
93
  end
42
94
  end
43
95
 
44
96
  def each
45
- mg = MicroGraph.new(@reps)
97
+ pq = ItemRepPriorityQueue.new(@reps)
46
98
 
47
99
  loop do
48
- rep = mg.next
100
+ rep = pq.next
49
101
  break if rep.nil?
50
102
 
51
103
  begin
52
104
  yield(rep)
53
- mg.mark_ok
105
+ pq.mark_ok
54
106
  rescue => e
55
107
  actual_error = e.is_a?(Nanoc::Core::Errors::CompilationError) ? e.unwrap : e
56
108
 
57
109
  if actual_error.is_a?(Nanoc::Core::Errors::UnmetDependency)
58
- mg.mark_failed(actual_error.rep)
110
+ pq.mark_failed(actual_error.rep)
59
111
  else
60
112
  raise(e)
61
113
  end
@@ -4,7 +4,7 @@ module Nanoc
4
4
  module Core
5
5
  class Layout < ::Nanoc::Core::Document
6
6
  def reference
7
- "layout:#{identifier}"
7
+ @_reference ||= "layout:#{identifier}"
8
8
  end
9
9
  end
10
10
  end
@@ -9,12 +9,6 @@ module Nanoc
9
9
  initialize_basic(config, objects, 'layouts')
10
10
  end
11
11
 
12
- # contract C::Any => C::Maybe[C::RespondTo[:identifier]]
13
- def get_memoized(arg)
14
- get_unmemoized(arg)
15
- end
16
- memo_wise :get_memoized
17
-
18
12
  def reference
19
13
  'layouts'
20
14
  end
@@ -26,13 +26,7 @@ module Nanoc
26
26
  #
27
27
  # @see Hash#[]=
28
28
  def []=(key, value)
29
- disallowed_value_classes = Set.new([
30
- Nanoc::Core::Item,
31
- Nanoc::Core::Layout,
32
- Nanoc::Core::CompilationItemView,
33
- Nanoc::Core::LayoutView,
34
- ])
35
- if disallowed_value_classes.include?(value.class)
29
+ if disallowed_value_class?(value.class)
36
30
  raise DisallowedAttributeValueError.new(value)
37
31
  end
38
32
 
@@ -55,6 +49,21 @@ module Nanoc
55
49
  hash.each { |k, v| _unwrap.set_attribute(k, v) }
56
50
  self
57
51
  end
52
+
53
+ private
54
+
55
+ def disallowed_value_class?(klass)
56
+ # NOTE: We’re explicitly disabling Style/MultipleComparison, because
57
+ # the suggested alternative (Array#include?) carries a measurable
58
+ # performance penatly.
59
+ #
60
+ # rubocop:disable Style/MultipleComparison
61
+ klass == Nanoc::Core::Item ||
62
+ klass == Nanoc::Core::Layout ||
63
+ klass == Nanoc::Core::CompilationItemView ||
64
+ klass == Nanoc::Core::LayoutView
65
+ # rubocop:enable Style/MultipleComparison
66
+ end
58
67
  end
59
68
  end
60
69
  end
@@ -6,92 +6,6 @@ module Nanoc
6
6
  #
7
7
  # @api private
8
8
  class OutdatednessChecker
9
- class Basic
10
- include Nanoc::Core::ContractsSupport
11
-
12
- Rules = Nanoc::Core::OutdatednessRules
13
-
14
- RULES_FOR_ITEM_REP =
15
- [
16
- Rules::ItemAdded,
17
- Rules::RulesModified,
18
- Rules::ContentModified,
19
- Rules::AttributesModified,
20
- Rules::NotWritten,
21
- Rules::CodeSnippetsModified,
22
- Rules::UsesAlwaysOutdatedFilter,
23
- ].freeze
24
-
25
- RULES_FOR_LAYOUT =
26
- [
27
- Rules::LayoutAdded,
28
- Rules::RulesModified,
29
- Rules::ContentModified,
30
- Rules::AttributesModified,
31
- Rules::UsesAlwaysOutdatedFilter,
32
- ].freeze
33
-
34
- RULES_FOR_CONFIG =
35
- [
36
- Rules::AttributesModified,
37
- ].freeze
38
-
39
- C_OBJ_MAYBE_REP = C::Or[Nanoc::Core::Item, Nanoc::Core::ItemRep, Nanoc::Core::Configuration, Nanoc::Core::Layout, Nanoc::Core::ItemCollection, Nanoc::Core::LayoutCollection]
40
-
41
- contract C::KeywordArgs[outdatedness_checker: OutdatednessChecker, reps: Nanoc::Core::ItemRepRepo] => C::Any
42
- def initialize(outdatedness_checker:, reps:)
43
- @outdatedness_checker = outdatedness_checker
44
- @reps = reps
45
-
46
- # Memoize
47
- @_outdatedness_status_for = {}
48
- end
49
-
50
- contract C_OBJ_MAYBE_REP => C::Maybe[Nanoc::Core::OutdatednessStatus]
51
- def outdatedness_status_for(obj)
52
- @_outdatedness_status_for[obj] ||=
53
- case obj
54
- when Nanoc::Core::ItemRep
55
- apply_rules(RULES_FOR_ITEM_REP, obj)
56
- when Nanoc::Core::Item
57
- apply_rules_multi(RULES_FOR_ITEM_REP, @reps[obj])
58
- when Nanoc::Core::Layout
59
- apply_rules(RULES_FOR_LAYOUT, obj)
60
- when Nanoc::Core::Configuration
61
- apply_rules(RULES_FOR_CONFIG, obj)
62
- when Nanoc::Core::ItemCollection, Nanoc::Core::LayoutCollection
63
- # Collections are never outdated. Objects inside them might be,
64
- # however.
65
- apply_rules([], obj)
66
- else
67
- raise Nanoc::Core::Errors::InternalInconsistency, "do not know how to check outdatedness of #{obj.inspect}"
68
- end
69
- end
70
-
71
- private
72
-
73
- contract C::ArrayOf[Class], C_OBJ_MAYBE_REP, Nanoc::Core::OutdatednessStatus => C::Maybe[Nanoc::Core::OutdatednessStatus]
74
- def apply_rules(rules, obj, status = Nanoc::Core::OutdatednessStatus.new)
75
- rules.inject(status) do |acc, rule|
76
- if acc.useful_to_apply?(rule)
77
- reason = rule.instance.call(obj, @outdatedness_checker)
78
- if reason
79
- acc.update(reason)
80
- else
81
- acc
82
- end
83
- else
84
- acc
85
- end
86
- end
87
- end
88
-
89
- contract C::ArrayOf[Class], C::ArrayOf[C_OBJ_MAYBE_REP] => C::Maybe[Nanoc::Core::OutdatednessStatus]
90
- def apply_rules_multi(rules, objs)
91
- objs.inject(Nanoc::Core::OutdatednessStatus.new) { |acc, elem| apply_rules(rules, elem, acc) }
92
- end
93
- end
94
-
95
9
  include Nanoc::Core::ContractsSupport
96
10
 
97
11
  attr_reader :checksum_store
@@ -107,7 +21,15 @@ module Nanoc
107
21
  C_ITEM_OR_REP = C::Or[Nanoc::Core::Item, Nanoc::Core::ItemRep]
108
22
  C_ACTION_SEQUENCES = C::HashOf[C_OBJ => Nanoc::Core::ActionSequence]
109
23
 
110
- contract C::KeywordArgs[site: Nanoc::Core::Site, checksum_store: Nanoc::Core::ChecksumStore, checksums: Nanoc::Core::ChecksumCollection, dependency_store: Nanoc::Core::DependencyStore, action_sequence_store: Nanoc::Core::ActionSequenceStore, action_sequences: C_ACTION_SEQUENCES, reps: Nanoc::Core::ItemRepRepo] => C::Any
24
+ contract C::KeywordArgs[
25
+ site: Nanoc::Core::Site,
26
+ checksum_store: Nanoc::Core::ChecksumStore,
27
+ checksums: Nanoc::Core::ChecksumCollection,
28
+ dependency_store: Nanoc::Core::DependencyStore,
29
+ action_sequence_store: Nanoc::Core::ActionSequenceStore,
30
+ action_sequences: C_ACTION_SEQUENCES,
31
+ reps: Nanoc::Core::ItemRepRepo
32
+ ] => C::Any
111
33
  def initialize(site:, checksum_store:, checksums:, dependency_store:, action_sequence_store:, action_sequences:, reps:)
112
34
  @site = site
113
35
  @checksum_store = checksum_store
@@ -120,20 +42,11 @@ module Nanoc
120
42
  @objects_outdated_due_to_dependencies = {}
121
43
  end
122
44
 
123
- def action_sequence_for(rep)
124
- @action_sequences.fetch(rep)
125
- end
126
-
127
- contract C_OBJ => C::Bool
128
- def outdated?(obj)
129
- outdatedness_reasons_for(obj).any?
130
- end
131
-
132
45
  contract C_OBJ => C::IterOf[Reasons::Generic]
133
46
  def outdatedness_reasons_for(obj)
134
- reasons = basic.outdatedness_status_for(obj).reasons
135
- if reasons.any?
136
- reasons
47
+ basic_reasons = basic_outdatedness_statuses.fetch(obj).reasons
48
+ if basic_reasons.any?
49
+ basic_reasons
137
50
  elsif outdated_due_to_dependencies?(obj)
138
51
  [Reasons::DependenciesOutdated]
139
52
  else
@@ -143,9 +56,28 @@ module Nanoc
143
56
 
144
57
  private
145
58
 
146
- contract C::None => Basic
59
+ def basic_outdatedness_statuses
60
+ @_basic_outdatedness_statuses ||= {}.tap do |tmp|
61
+ collections = [[@site.config], @site.layouts, @site.items, @reps]
62
+ collections.each do |collection|
63
+ collection.each do |obj|
64
+ tmp[obj] = basic.outdatedness_status_for(obj)
65
+ end
66
+ end
67
+ end
68
+ end
69
+
70
+ contract C::None => BasicOutdatednessChecker
147
71
  def basic
148
- @_basic ||= Basic.new(outdatedness_checker: self, reps: @reps)
72
+ @_basic ||= BasicOutdatednessChecker.new(
73
+ site: @site,
74
+ checksum_store: @checksum_store,
75
+ checksums: @checksums,
76
+ dependency_store: @dependency_store,
77
+ action_sequence_store: @action_sequence_store,
78
+ action_sequences: @action_sequences,
79
+ reps: @reps,
80
+ )
149
81
  end
150
82
 
151
83
  contract C_OBJ, Hamster::Set => C::Bool
@@ -191,12 +123,12 @@ module Nanoc
191
123
  raw_content_prop_causes_outdatedness?(all_objects, dependency.props.raw_content) ||
192
124
  attributes_prop_causes_outdatedness?(all_objects, dependency.props.attributes)
193
125
  else
194
- status = basic.outdatedness_status_for(dependency.from)
126
+ status = basic_outdatedness_statuses.fetch(dependency.from)
195
127
 
196
128
  active = status.props.active & dependency.props.active
197
129
  active.delete(:attributes) if attributes_unaffected?(status, dependency)
198
130
 
199
- active.any?
131
+ !active.empty?
200
132
  end
201
133
  end
202
134
 
@@ -217,8 +149,7 @@ module Nanoc
217
149
  when Enumerable
218
150
  # If the `raw_content` dependency prop is a collection, then this
219
151
  # is a dependency on specific objects, given by the patterns.
220
- patterns = raw_content_prop.map { |r| Nanoc::Core::Pattern.from(r) }
221
- patterns.flat_map { |pat| objects.select { |obj| pat.match?(obj.identifier) } }
152
+ raw_content_prop.flat_map { |pat| objects.find_all(pat) }
222
153
  else
223
154
  raise(
224
155
  Nanoc::Core::Errors::InternalInconsistency,
@@ -236,7 +167,7 @@ module Nanoc
236
167
  # accessed), then another dependency will exist that will cause
237
168
  # outdatedness.
238
169
  matching_objects.any? do |obj|
239
- status = basic.outdatedness_status_for(obj)
170
+ status = basic_outdatedness_statuses.fetch(obj)
240
171
  status.reasons.any? { |r| Nanoc::Core::OutdatednessReasons::DocumentAdded == r }
241
172
  end
242
173
  end
@@ -265,27 +196,30 @@ module Nanoc
265
196
  objects.any? do |object|
266
197
  # Find old and new attribute checksums for the object
267
198
  old_object_checksums = checksum_store.attributes_checksum_for(object)
268
- next false unless old_object_checksums
269
-
270
199
  new_object_checksums = checksums.attributes_checksum_for(object)
271
200
 
272
- # Ignore any attribute not mentioned in the dependency
273
- old_object_checksums = old_object_checksums.select { |k, _v| dep_checksums.key?(k) }
274
- new_object_checksums = new_object_checksums.select { |k, _v| dep_checksums.key?(k) }
275
-
276
201
  dep_checksums.any? do |key, dep_value|
277
- # Get old and new checksum for this particular attribute
278
- old_value = old_object_checksums[key]
279
- new_value = new_object_checksums[key]
280
-
281
- # If either the old or new vale match the value in the dependency,
282
- # then a potential change is relevant to us, and can cause
283
- # outdatedness.
284
- is_match = [old_value, new_value].include?(dep_value)
285
-
286
- is_changed = old_value != new_value
202
+ if old_object_checksums
203
+ # Get old and new checksum for this particular attribute
204
+ old_value = old_object_checksums[key]
205
+ new_value = new_object_checksums[key]
206
+
207
+ # If the old and new checksums are identical, then the attribute
208
+ # is unchanged and can’t cause outdatedness.
209
+ next false unless old_value != new_value
210
+
211
+ # We already know that the old value and new value are different.
212
+ # This attribute will cause outdatedness if either of those
213
+ # checksums is identical to the one in the prop.
214
+ old_value == dep_value || new_value == dep_value
215
+ else
216
+ # We don’t have the previous checksums, which means this item is
217
+ # newly added. In this case, we can compare the value in the
218
+ # dependency with the new checksum.
287
219
 
288
- is_match && is_changed
220
+ new_value = new_object_checksums[key]
221
+ new_value == dep_value
222
+ end
289
223
  end
290
224
  end
291
225
  end
@@ -23,11 +23,39 @@ module Nanoc
23
23
  end
24
24
 
25
25
  def self.affects_props(*names)
26
- @affected_props = Set.new(names)
26
+ @affects_raw_content = false
27
+ @affects_attributes = false
28
+ @affects_compiled_content = false
29
+ @affects_path = false
30
+
31
+ names.each do |name|
32
+ case name
33
+ when :raw_content
34
+ @affects_raw_content = true
35
+ when :attributes
36
+ @affects_attributes = true
37
+ when :compiled_content
38
+ @affects_compiled_content = true
39
+ when :path
40
+ @affects_path = true
41
+ end
42
+ end
43
+ end
44
+
45
+ def self.affects_raw_content?
46
+ @affects_raw_content
47
+ end
48
+
49
+ def self.affects_attributes?
50
+ @affects_attributes
51
+ end
52
+
53
+ def self.affects_compiled_content?
54
+ @affects_compiled_content
27
55
  end
28
56
 
29
- def self.affected_props
30
- @affected_props
57
+ def self.affects_path?
58
+ @affects_path
31
59
  end
32
60
  end
33
61
  end
@@ -8,22 +8,22 @@ module Nanoc
8
8
 
9
9
  affects_props :attributes, :compiled_content
10
10
 
11
- contract C::Or[Nanoc::Core::ItemRep, Nanoc::Core::Item, Nanoc::Core::Configuration, Nanoc::Core::Layout], C::Named['Nanoc::Core::OutdatednessChecker'] => C::Maybe[Nanoc::Core::OutdatednessReasons::Generic]
12
- def apply(obj, outdatedness_checker)
11
+ contract C::Or[Nanoc::Core::ItemRep, Nanoc::Core::Item, Nanoc::Core::Configuration, Nanoc::Core::Layout], C::Named['Nanoc::Core::BasicOutdatednessChecker'] => C::Maybe[Nanoc::Core::OutdatednessReasons::Generic]
12
+ def apply(obj, basic_outdatedness_checker)
13
13
  case obj
14
14
  when Nanoc::Core::ItemRep
15
- apply(obj.item, outdatedness_checker)
15
+ apply(obj.item, basic_outdatedness_checker)
16
16
  when Nanoc::Core::Item, Nanoc::Core::Layout, Nanoc::Core::Configuration
17
- if outdatedness_checker.checksum_store[obj] == outdatedness_checker.checksums.checksum_for(obj)
17
+ if basic_outdatedness_checker.checksum_store[obj] == basic_outdatedness_checker.checksums.checksum_for(obj)
18
18
  return nil
19
19
  end
20
20
 
21
- old_checksums = outdatedness_checker.checksum_store.attributes_checksum_for(obj)
21
+ old_checksums = basic_outdatedness_checker.checksum_store.attributes_checksum_for(obj)
22
22
  unless old_checksums
23
23
  return Nanoc::Core::OutdatednessReasons::AttributesModified.new(true)
24
24
  end
25
25
 
26
- new_checksums = outdatedness_checker.checksums.attributes_checksum_for(obj)
26
+ new_checksums = basic_outdatedness_checker.checksums.attributes_checksum_for(obj)
27
27
 
28
28
  attributes = Set.new(old_checksums.keys) + Set.new(new_checksums.keys)
29
29
  changed_attributes = attributes.reject { |a| old_checksums[a] == new_checksums[a] }
@@ -10,18 +10,18 @@ module Nanoc
10
10
 
11
11
  affects_props :raw_content, :attributes, :compiled_content, :path
12
12
 
13
- def apply(_obj, outdatedness_checker)
14
- if any_snippets_modified?(outdatedness_checker)
13
+ def apply(_obj, basic_outdatedness_checker)
14
+ if any_snippets_modified?(basic_outdatedness_checker)
15
15
  Nanoc::Core::OutdatednessReasons::CodeSnippetsModified
16
16
  end
17
17
  end
18
18
 
19
19
  private
20
20
 
21
- def any_snippets_modified?(outdatedness_checker)
22
- outdatedness_checker.site.code_snippets.any? do |cs|
23
- ch_old = outdatedness_checker.checksum_store[cs]
24
- ch_new = outdatedness_checker.checksums.checksum_for(cs)
21
+ def any_snippets_modified?(basic_outdatedness_checker)
22
+ basic_outdatedness_checker.site.code_snippets.any? do |cs|
23
+ ch_old = basic_outdatedness_checker.checksum_store[cs]
24
+ ch_new = basic_outdatedness_checker.checksums.checksum_for(cs)
25
25
  ch_old != ch_new
26
26
  end
27
27
  end
@@ -6,11 +6,11 @@ module Nanoc
6
6
  class ContentModified < Nanoc::Core::OutdatednessRule
7
7
  affects_props :raw_content, :compiled_content
8
8
 
9
- def apply(obj, outdatedness_checker)
9
+ def apply(obj, basic_outdatedness_checker)
10
10
  obj = obj.item if obj.is_a?(Nanoc::Core::ItemRep)
11
11
 
12
- ch_old = outdatedness_checker.checksum_store.content_checksum_for(obj)
13
- ch_new = outdatedness_checker.checksums.content_checksum_for(obj)
12
+ ch_old = basic_outdatedness_checker.checksum_store.content_checksum_for(obj)
13
+ ch_new = basic_outdatedness_checker.checksums.content_checksum_for(obj)
14
14
  if ch_old != ch_new
15
15
  Nanoc::Core::OutdatednessReasons::ContentModified
16
16
  end
@@ -6,9 +6,9 @@ module Nanoc
6
6
  class ItemAdded < Nanoc::Core::OutdatednessRule
7
7
  affects_props :raw_content
8
8
 
9
- contract Nanoc::Core::ItemRep, C::Named['Nanoc::Core::OutdatednessChecker'] => C::Maybe[Nanoc::Core::OutdatednessReasons::Generic]
10
- def apply(obj, outdatedness_checker)
11
- if outdatedness_checker.dependency_store.new_items.include?(obj.item)
9
+ contract Nanoc::Core::ItemRep, C::Named['Nanoc::Core::BasicOutdatednessChecker'] => C::Maybe[Nanoc::Core::OutdatednessReasons::Generic]
10
+ def apply(obj, basic_outdatedness_checker)
11
+ if basic_outdatedness_checker.dependency_store.new_items.include?(obj.item)
12
12
  Nanoc::Core::OutdatednessReasons::DocumentAdded
13
13
  end
14
14
  end
@@ -6,9 +6,9 @@ module Nanoc
6
6
  class LayoutAdded < Nanoc::Core::OutdatednessRule
7
7
  affects_props :raw_content
8
8
 
9
- contract Nanoc::Core::Layout, C::Named['Nanoc::Core::OutdatednessChecker'] => C::Maybe[Nanoc::Core::OutdatednessReasons::Generic]
10
- def apply(obj, outdatedness_checker)
11
- if outdatedness_checker.dependency_store.new_layouts.include?(obj)
9
+ contract Nanoc::Core::Layout, C::Named['Nanoc::Core::BasicOutdatednessChecker'] => C::Maybe[Nanoc::Core::OutdatednessReasons::Generic]
10
+ def apply(obj, basic_outdatedness_checker)
11
+ if basic_outdatedness_checker.dependency_store.new_layouts.include?(obj)
12
12
  Nanoc::Core::OutdatednessReasons::DocumentAdded
13
13
  end
14
14
  end
@@ -6,30 +6,30 @@ module Nanoc
6
6
  class NotWritten < Nanoc::Core::OutdatednessRule
7
7
  affects_props :raw_content, :attributes, :compiled_content, :path
8
8
 
9
- def apply(obj, outdatedness_checker)
10
- if obj.raw_paths.values.flatten.compact.any? { |fn| !exist?(fn, outdatedness_checker) }
9
+ def apply(obj, basic_outdatedness_checker)
10
+ if obj.raw_paths.values.flatten.compact.any? { |fn| !exist?(fn, basic_outdatedness_checker) }
11
11
  Nanoc::Core::OutdatednessReasons::NotWritten
12
12
  end
13
13
  end
14
14
 
15
15
  private
16
16
 
17
- def exist?(fn, outdatedness_checker)
18
- all(outdatedness_checker).include?(fn)
17
+ def exist?(fn, basic_outdatedness_checker)
18
+ all(basic_outdatedness_checker).include?(fn)
19
19
  end
20
20
 
21
- def all(outdatedness_checker)
21
+ def all(basic_outdatedness_checker)
22
22
  # NOTE: Cached per outdatedness checker, so that unrelated invocations
23
23
  # later on don’t reuse an old cache.
24
24
 
25
25
  @all ||= {}
26
- @all[outdatedness_checker] ||= Set.new(
27
- Dir.glob("#{site_root(outdatedness_checker)}/**/*", File::FNM_DOTMATCH),
26
+ @all[basic_outdatedness_checker] ||= Set.new(
27
+ Dir.glob("#{site_root(basic_outdatedness_checker)}/**/*", File::FNM_DOTMATCH),
28
28
  )
29
29
  end
30
30
 
31
- def site_root(outdatedness_checker)
32
- outdatedness_checker.site.config.output_dir
31
+ def site_root(basic_outdatedness_checker)
32
+ basic_outdatedness_checker.site.config.output_dir
33
33
  end
34
34
  end
35
35
  end
@@ -6,15 +6,15 @@ module Nanoc
6
6
  class RulesModified < Nanoc::Core::OutdatednessRule
7
7
  affects_props :compiled_content, :path
8
8
 
9
- def apply(obj, outdatedness_checker)
9
+ def apply(obj, basic_outdatedness_checker)
10
10
  # Check rules of obj itself
11
- if rules_modified?(obj, outdatedness_checker)
11
+ if rules_modified?(obj, basic_outdatedness_checker)
12
12
  return Nanoc::Core::OutdatednessReasons::RulesModified
13
13
  end
14
14
 
15
15
  # Check rules of layouts used by obj
16
- layouts = layouts_touched_by(obj, outdatedness_checker)
17
- if layouts.any? { |layout| rules_modified?(layout, outdatedness_checker) }
16
+ layouts = layouts_touched_by(obj, basic_outdatedness_checker)
17
+ if layouts.any? { |layout| rules_modified?(layout, basic_outdatedness_checker) }
18
18
  return Nanoc::Core::OutdatednessReasons::RulesModified
19
19
  end
20
20
 
@@ -23,20 +23,22 @@ module Nanoc
23
23
 
24
24
  private
25
25
 
26
- def rules_modified?(obj, outdatedness_checker)
27
- seq_old = outdatedness_checker.action_sequence_store[obj]
28
- seq_new = outdatedness_checker.action_sequence_for(obj).serialize
26
+ def rules_modified?(obj, basic_outdatedness_checker)
27
+ seq_old = basic_outdatedness_checker.action_sequence_store[obj]
28
+ seq_new = basic_outdatedness_checker.action_sequence_for(obj).serialize
29
29
 
30
30
  !seq_old.eql?(seq_new)
31
31
  end
32
32
 
33
- def layouts_touched_by(obj, outdatedness_checker)
34
- actions = outdatedness_checker.action_sequence_store[obj]
33
+ def layouts_touched_by(obj, basic_outdatedness_checker)
34
+ actions = basic_outdatedness_checker.action_sequence_store[obj]
35
35
  layout_actions = actions.select { |a| a.first == :layout }
36
36
 
37
+ layouts = basic_outdatedness_checker.site.layouts
38
+
37
39
  layout_actions.map do |layout_action|
38
40
  layout_pattern = layout_action[1]
39
- outdatedness_checker.site.layouts[layout_pattern]
41
+ layouts.object_with_identifier(layout_pattern) || layouts.object_matching_glob(layout_pattern)
40
42
  end.compact
41
43
  end
42
44
  end
@@ -6,8 +6,8 @@ module Nanoc
6
6
  class UsesAlwaysOutdatedFilter < Nanoc::Core::OutdatednessRule
7
7
  affects_props :raw_content, :attributes, :path
8
8
 
9
- def apply(obj, outdatedness_checker)
10
- seq = outdatedness_checker.action_sequence_for(obj)
9
+ def apply(obj, basic_outdatedness_checker)
10
+ seq = basic_outdatedness_checker.action_sequence_for(obj)
11
11
  if any_always_outdated?(seq)
12
12
  Nanoc::Core::OutdatednessReasons::UsesAlwaysOutdatedFilter
13
13
  end