Rick Carlino

Lead software developer and co-founding member @ Farmbot, Inc.

Co-founder @ Fox.Build Makerspace, St. Charles, IL.

Reddit Twitter GitHub LinkedIn Stack Overflow Email Updates

Persistent Key/Value Storage via Ruby Standard Lib

June 06 2015

Key value storage can come up for a variety of reasons when you’re writing an application. Sometimes it’s for simple configuration values while other times it can be for massive datasets shared across multiple machines.

Ruby developers have a number of options for this sort of thing.

Typical solutions include:

Somewhere in between these options lies Ruby’s PStore Library. It’s a read optimized file backed key/value storage mechanism. It stores Ruby objects in a marshaled binary file format that is lighter on disk space than standard serialization methods. It also lets you store real ruby objects to disk. You’re not confined to usual 6 data types seen with other serialization formats.

When Should I Use PStore?

PStore is a good choice if:

When NOT To Use PStore

How Do I Use It?

Basic CRUD operations in PStore are simple.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
require 'pstore'
store = PStore.new('my_file.pstore')
store.transaction do
# Write a value to disk.
store[:value1] = "Saved on disk."
# Most Ruby objects can be stored
# directly to disk. Some objects
# can not be stored (such as `Proc`).
store[:value2] = [{}, [], :sym, ""]
# Delete values
store.delete(:value2)
# View all key names:
store.roots
# => :value1
# Read a value:
store[:value1]
# => "Saved on disk."
end
fetch_a_value = store.transaction { store[:value1] }
# => "Saved on disk."
store.transaction do
# Commit()ing transactions- optional, but useful
# if you want to save before finishing a full
# transaction.
store[:value1] = "This string will be saved "\
"because I call commit()"
store.commit
# abort()ing transactions will halt execution and
# revert all changes.
store[:value1] = "This string will never be "\
"saved because I call abort()"
store.abort
store[:never_reached] = "Abort() halts execution."\
"This code is never run."
end

As you can see, PStore has a very straightforward API. Aside from a few options like thread_safe and ultra_safe, there’s not much overhead to get started.

PStore is a simple solution that just might save you the burden of writing an object caching system by hand. For the right use case, it is very effective.

I hope you give this lesser known corner of the Ruby library a look. Questions and comments are always welcome.

(C) 2017 Rick Carlino