Class: Middleman::CoreExtensions::Data::DataStore

Inherits:
Object
  • Object
show all
Includes:
Contracts
Defined in:
middleman-core/lib/middleman-core/core_extensions/data.rb

Overview

The core logic behind the data extension.

Constant Summary

Constants included from Contracts

Contracts::PATH_MATCHER, Contracts::ResourceList, Contracts::VectorOf

Instance Method Summary collapse

Methods included from Contracts

#Contract

Constructor Details

#initialize(app, data_file_matcher) ⇒ DataStore

Setup data store

Parameters:



56
57
58
59
60
61
62
63
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 56

def initialize(app, data_file_matcher)
  @app = app
  @data_file_matcher = data_file_matcher
  @local_data = {}
  @local_data_enhanced = nil
  @local_sources = {}
  @callback_sources = {}
end

Dynamic Method Handling

This class handles dynamic methods through the method_missing method

#method_missing(path) ⇒ Hash?

"Magically" find namespaces of data if they exist

Parameters:

  • path (String)

    The namespace to search for

Returns:



168
169
170
171
172
173
174
175
176
177
178
179
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 168

def method_missing(path)
  if @local_data.key?(path.to_s)
    # Any way to cache this?
    @local_data_enhanced ||= ::Middleman::Util.recursively_enhance(@local_data)
    return @local_data_enhanced[path.to_s]
  else
    result = data_for_path(path)
    return result if result
  end

  super
end

Instance Method Details

#[](key) ⇒ Hash?

Make DataStore act like a hash. Return requested data, or nil if data does not exist

Parameters:

  • key (String, Symbol)

    The name of the data namespace

Returns:



191
192
193
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 191

def [](key)
  __send__(key) if key?(key)
end

#callbacks(name = nil, proc = nil) ⇒ Object



82
83
84
85
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 82

def callbacks(name=nil, proc=nil)
  @callback_sources[name.to_s] = proc unless name.nil? || proc.nil?
  @callback_sources
end

#data_for_path(path) ⇒ Object



154
155
156
157
158
159
160
161
162
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 154

def data_for_path(path)
  response = if store.key?(path.to_s)
    store[path.to_s]
  elsif callbacks.key?(path.to_s)
    callbacks[path.to_s].call
  end

  ::Middleman::Util.recursively_enhance(response)
end

#HashHash

Convert all the data into a static hash

Returns:



204
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 204

Contract Hash

#key?(key) ⇒ Boolean Also known as: has_key?

Returns:

  • (Boolean)


195
196
197
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 195

def key?(key)
  (@local_data.keys + @local_sources.keys + @callback_sources.keys).include?(key.to_s)
end

#remove_file(file) ⇒ Object



132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 132

def remove_file(file)
  data_path = file[:relative_path]
  extension = File.extname(data_path)
  basename  = File.basename(data_path, extension)

  data_branch = @local_data

  path = data_path.to_s.split(File::SEPARATOR)[0..-2]
  path.each do |dir|
    data_branch = data_branch[dir]
  end

  data_branch.delete(basename) if data_branch.key?(basename)

  @local_data_enhanced = nil
end

#respond_to?(method, include_private = false) ⇒ Boolean

Needed so that method_missing makes sense

Returns:

  • (Boolean)


182
183
184
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 182

def respond_to?(method, include_private=false)
  super || key?(method)
end

#store(name = nil, content = nil) ⇒ Object



71
72
73
74
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 71

def store(name=nil, content=nil)
  @local_sources[name.to_s] = content unless name.nil? || content.nil?
  @local_sources
end

#SymbolHash

Store static data hash

Parameters:

  • name (Symbol)

    Name of the data, used for namespacing

  • content (Hash)

    The content for this data

Returns:



70
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 70

Contract Symbol, Or[Hash, Array] => Hash

#to_hObject



205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 205

def to_h
  data = {}

  store.each_key do |k|
    data[k] = data_for_path(k)
  end

  callbacks.each_key do |k|
    data[k] = data_for_path(k)
  end

  (@local_data || {}).each do |k, v|
    data[k] = v
  end

  data
end

#touch_file(file) ⇒ Object



100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 100

def touch_file(file)
  data_path = file[:relative_path]
  extension = File.extname(data_path)
  basename  = File.basename(data_path, extension)

  return unless %w(.yaml .yml .json).include?(extension)

  if %w(.yaml .yml).include?(extension)
    data, postscript = ::Middleman::Util::Data.parse(file, @app.config[:frontmatter_delims], :yaml)
    data[:postscript] = postscript if !postscript.nil? && data.is_a?(Hash)
  elsif extension == '.json'
    data, _postscript = ::Middleman::Util::Data.parse(file, @app.config[:frontmatter_delims], :json)
  end

  data_branch = @local_data

  path = data_path.to_s.split(File::SEPARATOR)[0..-2]
  path.each do |dir|
    data_branch[dir] ||= {}
    data_branch = data_branch[dir]
  end

  data_branch[basename] = data

  @local_data_enhanced = nil
end

#update_files(updated_files, removed_files) ⇒ Object



88
89
90
91
92
93
# File 'middleman-core/lib/middleman-core/core_extensions/data.rb', line 88

def update_files(updated_files, removed_files)
  updated_files.each(&method(:touch_file))
  removed_files.each(&method(:remove_file))

  @app.sitemap.rebuild_resource_list!(:touched_data_file)
end