aboutsummaryrefslogtreecommitdiff
path: root/content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown
diff options
context:
space:
mode:
authorJulio Capote <jcapote@gmail.com>2018-11-06 03:03:41 +0000
committerJulio Capote <jcapote@gmail.com>2018-11-06 03:03:41 +0000
commit4b489a049a0063bbb1fd9f0c0f74ce1ee9f87a86 (patch)
tree98af5707e30150af482e297bed9cd4e9b5477e6a /content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown
parenta62a3e7755579d93ce3a87243dd277575930fffe (diff)
downloadcapotej.com-4b489a049a0063bbb1fd9f0c0f74ce1ee9f87a86.tar.gz
import old posts
Diffstat (limited to 'content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown')
-rw-r--r--content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown75
1 files changed, 75 insertions, 0 deletions
diff --git a/content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown b/content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown
new file mode 100644
index 0000000..a014a41
--- /dev/null
+++ b/content/post/2012-10-07-an-embedded-key-value-store-for-shell-scripts.markdown
@@ -0,0 +1,75 @@
+---
+layout: post
+title: "an embedded key / value store for shell scripts"
+date: 2012-10-07T10:06:00Z
+comments: true
+categories: ['shell scripting', 'databases']
+---
+
+UPDATE: this is now available as a [sub](http://github.com/37signals/sub) command, here: [kiev](http://github.com/capotej/kiev)
+
+Cooked this up last night when I needed a simple key/value store for use in a shell script:
+
+```sh db.sh
+#!/bin/sh
+
+DBFILE=example.db
+
+put(){
+ echo "export kv_$1=$2" >> $DBFILE
+}
+
+del(){
+ echo "unset kv_$1" >> $DBFILE
+}
+
+get(){
+ source $DBFILE
+ eval r=\$$(echo "kv_$1")
+ echo $r
+}
+
+list(){
+ source $DBFILE
+ for i in $(env | grep "kv_" | cut -d= -f1 ); do
+ eval r=\$$i; echo $(echo $i | sed -e 's/kv_//') $r;
+ done
+}
+
+## cmd dispatch
+
+if [ ${1:-0} == "set" ]; then
+ put $2 $3
+elif [ ${1:-0} == "get" ] ; then
+ get $2
+elif [ ${1:-0} == "list" ] ; then
+ list
+elif [ ${1:-0} == "del" ] ; then
+ del $2
+else
+ echo "unknown cmd"
+fi
+```
+
+Use it like so:
+
+
+`$ ./db.sh set foo bar`
+
+`$ ./db.sh get foo`
+
+`$ ./db.sh set foo baz`
+
+`$ ./db.sh get foo`
+
+`$ ./db.sh del foo`
+
+`$ ./db.sh list`
+
+
+## How it works
+
+Every time you update/set/delete a value, it writes a shell expression to an append-only log,
+exporting a shell variable (key) with that value. By sourcing the file every time we read a value, we
+replay the log, bringing our environment to a consistent state. Then, reading the value is just looking
+up that dynamic variable (key) in our shell environment.