Class: Access::YAMLBase

Inherits:
Object
  • Object
show all
Includes:
Enumerable
Defined in:
lib/access/yamlbase.rb

Overview

An Access compatible storage backend, based on YAML

Instance Attribute Summary collapse

Instance Method Summary collapse

Methods included from Enumerable

#join

Constructor Details

#initialize(extender, path = nil) ⇒ YAMLBase

extender: a module that will extend this instance and provide additional

functionality

framework: the Access instance this data-storage is tied to path: the path to the data



28
29
30
31
32
33
34
35
# File 'lib/access/yamlbase.rb', line 28

def initialize(extender, path=nil)
  extend(extender) if extender
  @path      = path || default_path # default_path comes from the extender
  @data      = {}
  @lock      = Mutex.new

  raise "Path must be a directory (#@path)" unless File.directory?(@path)
end

Instance Attribute Details

#accessObject

The access instance this base is tied to



22
23
24
# File 'lib/access/yamlbase.rb', line 22

def access
  @access
end

Instance Method Details

#<<(record) ⇒ Object Also known as: add

Add a record to the storage



84
85
86
87
88
89
# File 'lib/access/yamlbase.rb', line 84

def <<(record)
  @lock.synchronize {
    @data[record.oid] = record
    save(record.oid)
  }
end

#[](oid, force_load = false) ⇒ Object

Retrieve the object with oid, if force_load cache will be ignored.



73
74
75
76
77
78
79
80
81
# File 'lib/access/yamlbase.rb', line 73

def [](oid, force_load=false)
  @lock.synchronize {
    if force_load then
      @data[oid] = load(oid)
    else
      @data[oid] ||= load(oid)
    end
  }
end

#cache_allObject

Loads all entries into cache



61
62
63
64
65
66
67
68
69
# File 'lib/access/yamlbase.rb', line 61

def cache_all
  slice = (@path.length+1)..-6
  @lock.synchronize {
    Dir.glob("#{@path}/*.yaml") { |path| # /**
      oid = path[slice]
      @data[oid] ||= load(oid)
    }
  }
end

#delete(record) ⇒ Object

Delete a record from the storage



101
102
103
# File 'lib/access/yamlbase.rb', line 101

def delete(record)
  delete_oid(record.oid)
end

#delete_oid(oid) ⇒ Object

Delete a record from the storage



93
94
95
96
97
98
# File 'lib/access/yamlbase.rb', line 93

def delete_oid(oid)
  @lock.synchronize {
    @data.delete(oid)
    File.delete(filename(oid))
  }
end

#eachObject

Iterate over records, yielding oid and object



106
107
108
109
110
111
112
# File 'lib/access/yamlbase.rb', line 106

def each
  slice = (@path.length+1)..-6
  Dir.glob("#{@path}/*.yaml") { |path|
    oid = path[slice]
    yield(oid, @data[oid] || load(oid))
  }
end

#each_keyObject

Iterate over records, yielding oid



115
116
117
118
119
# File 'lib/access/yamlbase.rb', line 115

def each_key
  Dir.glob("#{@path}/*.yaml") { |path|
    yield(path2oid(path))
  }
end

#escape(oid) ⇒ Object

Escapes path names



43
44
45
# File 'lib/access/yamlbase.rb', line 43

def escape(oid)
  oid.gsub(/[\x00-\x1f.%]/) { |m| "%%%02x"%m }.gsub("/", ".")
end

#exists?(oid) ⇒ Boolean Also known as: exist?

Check existency of an object.

Returns:

  • (Boolean)


129
130
131
# File 'lib/access/yamlbase.rb', line 129

def exists?(oid)
  @data.has_key?(oid) || File.exists?(filename(oid))
end

#filename(oid) ⇒ Object

The full path and filename to the data object belonging to oid



38
39
40
# File 'lib/access/yamlbase.rb', line 38

def filename(oid)
  "#{@path}/#{escape(oid)}.yaml"
end

#keysObject

All record oid’s



122
123
124
125
126
# File 'lib/access/yamlbase.rb', line 122

def keys
  Dir.glob("#{@path}/*.yaml").map { |path|
    path2oid(path)
  }
end

#load(oid) ⇒ Object

Load an entry, will not write to cache, returns nil if entry doesn’t exist



53
54
55
56
57
58
# File 'lib/access/yamlbase.rb', line 53

def load(oid)
  file = filename(oid)
  YAML.load_file(file)
rescue Errno::ENOENT
  nil
end

#path2oid(path) ⇒ Object

Extracts the record-oid from a path



48
49
50
# File 'lib/access/yamlbase.rb', line 48

def path2oid(path)
  path[(@path.length+1)..-6].gsub(".", "/").gsub(/%([\dA-Fa-f]{2})/) { $1.to_i(16).chr }
end

#save(oid = nil) ⇒ Object

Synchronize data-cache with filesystem.



135
136
137
138
139
140
141
142
143
# File 'lib/access/yamlbase.rb', line 135

def save(oid=nil)
  if @data.has_key?(oid) then
    File.open(filename(oid), 'w') { |fh| fh.write(@data[oid].storable.to_yaml) }
  elsif oid.nil? then
    @data.each_key { |key| save(key) }
  else
    raise "Could not save '#{oid}' since it's not in @data"
  end
end