vorburger / opendaylight-etcd

etcd as OpenDaylight (ODL) DataBroker database store
Eclipse Public License 1.0
6 stars 2 forks source link

THIS REPOSITORY IS ARCHIVED BECAUSE THIS PROJECT NOW LIVES ON INSIDE THE etcd/ DIRECTORY OF THE alt-datastores GIT REPOSITORY ON git.opendaylight.org - see https://git.opendaylight.org/gerrit/gitweb?p=alt-datastores.git;a=summary (also mirrored on https://github.com/opendaylight/alt-datastores).

This project started as a personal POC by Michael Vorburger.ch to evaluate the feasibility of using etcd as data store for YANG data in OpenDaylight (ODL), instead of its current "home made" CDS based on Akka.

See this presentation given in 2018.09 at the ODL DDF during ONS Europe in Amsterdam for some background.

How to build? Build Status

  1. To get a more recent version of jetcd-core than the currently used 0.0.3, just git clone https://github.com/coreos/jetcd.git ; cd jetcd ; mvn [-DskipTests] clean install and change POMs in bom/, features/odl-mdsal-broker/ & features/odl-etcd-demo-restconf/.

  2. If you're hitting an NPE in org.apache.maven.plugins:maven-javadoc-plugin:3.0.0:jar, just use mvn -Dmaven.javadoc.skip=true -Dduplicate-finder.skip -DskipTests -Dcheckstyle.skip clean install to work around it; it's possibly related to not having JAVA_HOME environment variable (what's weird is that this NPE does not seem to happen with other OpenDaylight builds).

Architecture Design

A cluster of Etcd servers appears as a single logical server to clients like this. Details about its internal clustering, Raft implementation etc. are transparent.

The EtcdDataStore implements DOMStore and internally uses a YANG DataTree, just like the sal-distributed-datastore (CDS) does.

On commit(), the put/merge/delete writes from DataTreeModification / DataTreeCandidate are sent to etcd. Each DataTreeCandidateNode is stored as an individual sub key/value - without their respective child nodes. This allows for fine-grained future updates and deletes. Changes from DataTreeCandidate are sent atomically to etcd (using TXN, not PUT).

The data is stored in a compact binary serialization format (not e.g. XML or JSON). The communication from the etcd client in ODL to the etcd server/s is similarly compact binary, not text-based over HTTP.

We watch etcd, and update our internal DataTree as and when we receive change events. Changes from watch events are applied atomically to the DataTree.

To guarantee strong consistency, we (remote) check the current revision on etcd, for a every new transaction, and await having received and processed watch events at least up to that current revision. This is what blocks reads.

If DataBroker offered an eventual consistency read API to applications, then it would be trivial to offer (optionally) blazing fast reads (directly from the local DataTree), without any remoting.

We never do any GET on etcd to read data, but always serve directly from the DataTree. There is no ser/der and tree-reconstruction overhead for reads (but there is when processing watch events).

This approach also guarantees that we have up-to-date data for validation.

Distributed Data Change Listeners also work as expected with this mechanism.

Deployment Considerations

etcd instances would typically best be localhost co-located with the ODL nodes.

Demos

Make sure you have at least 1 etcd server running:

sudo dnf install etcd
sudo systemctl start etcd
systemctl status etcd
ETCDCTL_API=3 etcdctl get --from-key ''

or even just start it directly, without systemd, in the foreground in another terminal tab:

cd /tmp
etcd

tree /tmp/default.etcd/
ETCDCTL_API=3 etcdctl get --from-key ''

TODO Document how to best easily start test cluster of 3 etcd servers locally...

If you used etcd before you may want to completely wipe it:

ETCDCTL_API=3 etcdctl del "" --from-key=true

Beware that ETCDCTL_API=3 etcdctl get --from-key '' outputs binary, so better use our own:

java -jar demo/target/*.jar read http://localhost:2379

RESTCONF

Here is how to run the asciinema POC v0.2:

Configure the etcd connection URL (TODO this is a hack which will change to be a real configuration file later):

mkdir karaf/target/assembly/../../jetcd-launcher-maven-plugin/
echo http://localhost:2379 >karaf/target/assembly/../../jetcd-launcher-maven-plugin/endpoint

Now start ODL and make sure it's happy:

./karaf/target/assembly/bin/karaf
opendaylight-user@root>feature:list -i
opendaylight-user@root>diag

Note how there is no karaf/target/assembly/etc/org.opendaylight.controller.cluster.datastore.cfg now, thus "proving" that we don't run the existing ODL datastore anymore. You can now use RESTCONF as usual - but it runs on etcd! Open apidoc/explorer (admin/admin), and watch the logs (tail -f karaf/target/assembly/data/log/karaf.log) to understand what happens when you e.g. do:

http -a admin:admin GET http://localhost:8181/restconf/config/opendaylight-etcd-test:HelloWorldContainer
echo '<HelloWorldContainer xmlns="urn:opendaylight:etcd:test"><name>hello, world</name></HelloWorldContainer>' >put.xml
http -v -a admin:admin PUT :8181/restconf/config/opendaylight-etcd-test:HelloWorldContainer @put.xml
http -a admin:admin GET :8181/restconf/config/opendaylight-etcd-test:HelloWorldContainer
java -jar demo/target/*.jar read http://localhost:2379
http -a admin:admin DELETE :8181/restconf/config/opendaylight-etcd-test:HelloWorldContainer
http -a admin:admin GET :8181/restconf/config/opendaylight-etcd-test:HelloWorldContainer

Standalone

Here is how to run the asciinema POC v0.1:

Now run this project's demo:

java -jar demo/target/*.jar write http://localhost:4001

or if you started etcd directly without systemd then:

java -jar demo/target/*.jar write http://localhost:2379

and have a closer look at the logs this will print to understand what happened, and read it via:

java -jar demo/target/*.jar read http://localhost:2379

FAQ

About this project

About some typical objections

About alternatives

About etcd

History

This project originally included a more generic "DOM-to-KV" abstraction layer, with the idea of also supporting other KV stores than etcd. That code was moved out into https://github.com/vorburger/dom2kv and removed from this repo in 154bd8aace51395c7d58f6e2905b2101187fd5b8.