Skip to content

koivunej/eventstore-tcp

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 

Repository files navigation

Build Status

Post 2017 update

Long story short: Apologies if you came here looking for a client library. You should look into YoEight's eventstore-tcp.

I originally started creating this related to my school work. Since then, tokio-proto with it's multiplexing support went away and I haven't really touched this in a long while. I haven't ever used this as a client library for anything, but instead I have used this crate to implement the server side of eventstore but then only using the pb types and adaptors on a custom multiplexing layer.


Tokio-based EventStore client API written in Rust

EventStore is an open-source immutable event database. EventStore allows writing to named event streams with optional optimistic locking and reading from a stream or a stream of all events in the database (not yet implemented in this project). This project aims to be a driver with similar features to the .NET client API but at the moment it has the simplest operations implemented:

  • read an event
  • read a stream forwards or backwards
  • read all events forwards or backwards
  • write events
  • delete stream

Supported server version: currently this has been developed against the latest stable 3.9.3.

The suffix -tcp refers to the fact that EventStore also has AtomPub-based HTTP API. There exists already a crate for that: http_event_store. The TCP protocol is multiplexed, custom framed with the payloads specified as protobuf messages. Some of the payloads are exposed by the current version of this API.

Examples and usage

Please see the documentation.

The repository also includes an aspiring command line client under testclient/.

This crate is not yet available on crates.io as it depends on a custom fork of tokio-proto but you can try it out by adding this to your Cargo.toml:

[dependencies]
eventstore-tcp = { git = "https://github.com/koivunej/eventstore-tcp.git" }

Unimplemented features

  1. read events from $all stream
  2. deleting a stream
  3. adapted interface for DeleteStreamCompleted
  4. volatile subscriptions:
  • refactoring to use tokio_proto::streaming::multiplex instead of tokio_proto::multiplex
  • current messages are ok as headers, but appeared events could probably be body chunks
  • maintaining a subscription by pumping events to a futures::sink::Sink, detecting overflows and dropping the subscription
  1. Less of directly using the protobuf messages in the API
  2. Cleaning up the message builders
  3. Hide the use of Package from users
  4. Add some "operation" API so that user does not need to match package.message {}
  5. Nice API which would not require users to run the `tokio_core::reactor::Core``

"Perhaps later" features

  1. persistent subscriptions (haven't researched this yet)
  2. competing consumers (?)
  3. long running transactions (???)

Contributing

Currently the code base is not formatted with rustfmt as the code generated by quick-protobuf is very slow to process by rustfmt. Later on hopefully rustfmt can be used, hopefully with default options which hopefully somewhat matches the current style.

As a fork of tokio-proto is currently used you need to clone this repository with --recursive:

git clone --recursive https://github.com/koivunej/eventstore-tcp.git

Building

cargo build will handle building, and testclient becomes usable after building it in it's own directory: cd testclient && cargo run -- --help.

Testing

Currently cargo test runs very primitive codec tests to ensure everything pretty much works. Also, I'm not sure if there is any point in aiming at 100% coverage en/decoding protobuf messages. Perhaps later on if server version differences are discovered these will make more sense.

The testclient/ contains test_with_inmemory_es.bash which will do some smoke testing against an EventStore instance expected to be running at 127.0.0.1:1113. The script also includes code to fetch but not run an inmemory instance as it's currently impossible to download EventStore binaries from an https:// host (if you know one, please let me know) and either way this should probably be done with some jailing/sandboxing to be accessible.

Simple no-brainer way to run the server is to spin-up a local ubuntu VM based on something similar to a VagrantFile below (assuming you have vagrant and VirtualBox ready to go):

Vagrant.configure(2) do |config|
  config.vm.box = "ubuntu/trusty64"
  config.vm.network "forwarded_port", guest: 1113, host: 1113
  config.vm.provider "virtualbox" do |vb|
    vb.gui = false
    vb.memory = "2048"
  end
end

Then download the latest EventStore tar.gz and execute it with ./run-node.sh --ext-ip 0.0.0.0 --mem-db.

Rebuilding the client_messages

  1. Obtain ClientMessageDTOs.proto or raw link
  2. Checkout latest quick-protobuf: git clone https://github.com/tafia/quick-protobuf
  3. cd quick-protobuf/codegen
  4. cargo run --single-mod --output $es_tcp_checkout/src/client_messages.rs ClientMessageDTOs.proto

Modify the generated file like:

-#[derive(Debug, Default, PartialEq, Clone)]
+#[derive(IntoOwned, Borrowed, Debug, Default, PartialEq, Clone)]

License

MIT.

About

Tokio-based EventStore client API in Rust

Topics

Resources

License

Stars

Watchers

Forks

Releases

No releases published

Packages

No packages published