Giter Club home page Giter Club logo

fq's Introduction

fq.

Coverity Scan Build Status

fq is a brokered message queue using a publish subscribe model. It is architected for performance and isn't (today) designed for large numbers of connected clients.

+------------+                        +-----------+
|- exchange -|<-- (msg publication) --|- client0 -|
+------------+                        +-----------+
|- routemap -|
+------------+
    |      |              +---------+
    |      +--------------|- queue -|
    |                     +---------+
+---------+                  |
|- queue -|                  |   +-----------+
+---------+                  +---|- client1 -|
        |                        +-----------+
        |  +-----------+
        +--|- client2 -|
        |  +-----------+
        |
   +-----------+
   |- client3 -|
   +-----------+

Terminology

Broker

The fqd process. The daemon through which all knowledge passes.

Peers

Peers are connected fqd processes. It is important to note that peers are unidirectional. If A peers with B, then A will act as a client to B. If you want bidirectional peering, you must specify that A peers with B and B peers with A. The system aims to prevent cyclic delivery of messages efficiently.

Adding peers is done directly via fqd's sqlite DB store:

; sqlite3 /var/lib/fq/fqd.sqlite
sqlite> INSERT INTO "upstream"
              (host, port, source, password, exchange, program, permanent_binding)
        VALUES('peerB',8765,'fqd-peera//mem:drop,private,backlog=4096','none','logging','prefix:"http.access.json."','false');

Client

A client is an applications connection to fq over TCP/IP to send or receive messages. A client makes two TCP/IP connections to fq. An application can present itself to fq as multiple clients at one time (by opening new pairs of connections). See Queues for reasons why.

Exchanges

Exchanges are like buses on which messages may be sent. You cannot send a message without doing so on an exchange. Exchanges are created within fq on-demand.

Queues

Queues are queues. If you stick something in one end, you should expect it to come out the other. A single queue may have multiple clients subscribed. When a client connects, it is attached to one and only one queue. If an application wishes to attach to more than one queue, it should present as multiple clients. Queues use a competitive consumption model meaning that if multiple clients are attached to a single queue, the messages sent to that queue will be distributed over the clients such that no two clients will see the same message.

Queue Types

Queues can be of type mem or disk. The contents of memory queues will not survive restarts.

Various parameters can be set on a queue using the syntax type:param1,param2.

Sharing

Queues with the public parameter can have multiple clients connected to them (in which case they compete for messages). If you want a private queue you can specify the private parameter.

Policy

Queues can either have a block or drop policy. The drop policy means that messages that would be routed to a queue that is full will be dropped and never delivered. The block policy will cause the publisher to wait until there is room in the queue. The block policy makes no sense on a disk queue.

Backlog

The backlog=<number> parameter will specify how many messages may be held in the queue before the block or drop policies are applied.

Permanence

If you want a queue to be remembered by fqd, you can specify permanent as a flag. If you'd like for fqd to forget the queue after all clients have disconnected, you can specify the transient flag. If neither flag is specified, then an existing queue will retain its previous permanence setting or a new transient queue will be created.

Examples:

A queue called bob will be in memory, allowed to have multiple clients connected to it, with a drop policy and an allowable message backlog of 100000 messages: bob/mem:public,drop,backlog=100000

A connection client will specify username/queue. A user "USER" connecting to the aforementioned queue would connect as USER/bob/mem:public,drop,backlog=100000

Messages

Messages are, of course, a payload and metadata.

Message metadata

Some are set by the broker.

  • sender [set by the broker]
  • hops (a list of fqd via which the message passed)

Others are set by the sender.

  • exchange (up to 127 bytes)
  • route (up to 127 bytes)
  • id (128 bits). The first 64 bits the sender shall control, the latter 64bits the broker might control.

Routes and Programs

Routes and programs define how messages sent on exchanges are placed in queues:

  • A receiver that connects to an fq-broker specifies a program that filters the messages on the exchange.
  • A sender specifies a route for every message as part of the metadata

Programs follow the following syntax (cf. fqd.h):

PROGRAM: <prefix|exact>:string RULES*
RULE: (RULE)
RULE: (RULE && RULE)
RULE: (RULE || RULE)
RULE: EXPR
EXPR: function(args)
args: arg
args: arg, args
arg: "string"
arg: true|false
arg: [0-9][0-9]*(?:.[0-9]*)

functions are dynamically loadable with type signature
strings: s, booleans: b, integers: d
function: substr_eq(9.3,10,"tailorings",true)
C symbol: fqd_route_prog__substr_eq__ddsb(int nargs, valnode_t *args);

In particular:

  • Every program starts with either prefix: or exact:
  • The program prefix: matches all rules
  • The program string is matched against the message route

The following rule functions are defined in fq_prog.c:

  • fqd_route_prog__sample__d() -- subsample the stream
  • fqd_route_prog__route_contains__s() -- check if route contains a string
  • fqd_route_prog__payload_prefix__s() -- check if payload starts with prefix
  • fqd_route_prog__payload_contains__s() -- check if payload contains a string
  • fqd_route_prog__true__() -- always true

Examples:

  • prefix: -- matches all messages
  • prefix:bla or prefix:"bla" -- matches all messages with rules starting with the sting 'bla'
  • prefix: payload_prefix("M") -- matches messages where the payload starts with 'M'
  • prefix:foo (payload_prefix("M") && route_contains("bar")) -- matches messages where the payload starts with 'M' and route starts with "foo" and moreover contains "bar"

Protocol

Information on command and message protocol is found in docs/fq_protocol.md

HTTP superposition

The Fq protocol also acts as a non-compliant HTTP server (though compliant enough of most clients and browsers). Fq ships with a web UI that allows inspecting real-time state and performance.

GET /stats.json

exposes current exchange, queue, and client information.

POST /submit

An endpoint allowing message submission without a full and stateful Fq connection. It expects the following headers:

  • X-Fq-User,
  • X-Fq-Route, and
  • X-Fq-Exchange.

The HTTP client MUST provide a Content-Length header corresponding to the payload content (no chunked submission). The payload is treated as the raw message box without any special encoding.

Example:

curl -X POST -H "X-Fq-User: user" -H 'X-Fq-Route: bla' -H 'X-Fq-Exchange: test' localhost:8765/submit --data "TEST"

Building

Requirements:

  • C compiler
  • GNU make
  • libuuid
  • sqlite3
  • jlog
  • libbcd (optional, for crash tracing)

Generally:

make
make install

To build without libbcd support:

NO_BCD=1 make

Debugging

FQ can be run in debug mode from the command line.

To run FQ in debug mode, kill any and all existing FQ processes, then enter the following command:

fq -g fq FQ_DEBUG=<flag values> <path to fqd>/fqd -D -c <path to fqd.sqlite>/fqd.sqlite -p <port number>

Flag values determine debug output type and can have the following values:

FQ_DEBUG_MEM =     0x00000001,
FQ_DEBUG_MSG =     0x00000002,
FQ_DEBUG_ROUTE =   0x00000004,
FQ_DEBUG_IO =      0x00000008,
FQ_DEBUG_CONN =    0x00000010,
FQ_DEBUG_CONFIG =  0x00000020,
FQ_DEBUG        =  0x00000040,
FQ_DEBUG_PEER =    0x00000080,
FQ_DEBUG_HTTP =    0x00000100,
FQ_DEBUG_PANIC =   0x40000000

To debug more than one flag, simply OR the flag values. For example, to output connection, configuration, and route information, set FQ_DEBUG equal to 0x00000034 (FQ_DEBUG_CONFIG|FQ_DEBUG_CONN|FQ_DEBUG_ROUTE).

For example, you can run FQ in debug mode with the variables shown below to output configuration, connection, and route information to the console:

fq -g fq FQ_DEBUG=0x00000034  /opt/circonus/sbin/fqd -D -c /opt/circonus/var/lib/fq/fqd.sqlite -p 8765

fq's People

Contributors

bdunavant avatar esproul avatar gallison93 avatar heinrichhartmann avatar ipstatic avatar iukpocirconus avatar jonaskunze avatar mranney avatar pamaddox avatar pjulien avatar postwait avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

fq's Issues

message free message stacks used after gone

If a message arrives in a publisher thread, the message is allocated from a TLS free stack. Once that message is done it is deallocated back to the free stack on the original thread to speed future, similar sized msg allocation requests. This is awesome for performance.

When the thread terminates, the cleanup function will correctly tear down the free stacks. However, when the thread exits, that memory is now available for reuse and the message could still point into the free stacks and attempt to return messages into it.

Basically once the thread exits, any live message with a cleanup_stack points into that TLS has a dangling, invalid pointer that it will use as soon as fq_msg_free is called.

implement auth

Currently auth is present in the protocol, but implemented as an "allow all." Implement a backend for the auth.

Build Error: unknown pseudo-op: `.reference'

I met the error while trying to build fq:

fqd_listener.c: Assembler messages:
fqd_listener.c:134: Error: unknown pseudo-op: `.reference'
fqd_listener.c:134: Error: unknown pseudo-op: `.reference'
fqd_listener.c:80: Error: unknown pseudo-op: `.reference'
fqd_listener.c:80: Error: unknown pseudo-op: `.reference'
Makefile:138: recipe for target 'fqd_listener.o' failed
make: *** [fqd_listener.o] Error 1

My compiler version is:

gcc --version
gcc (GCC) 5.1.1 20150618 (Red Hat 5.1.1-4)
Copyright (C) 2015 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

Make install fails on OmniOS

I get the following error on OmniOS06

$ sudo gmake install
install -d //usr/local/include
install -m 0444 fq.h //usr/local/include/fq.h
find: stat() error //usr/local/include/fq.h: No such file or directory
find: cycle detected for /lib/secure/32/
find: cycle detected for /lib/crypto/32/
find: cycle detected for /lib/32/
find: cycle detected for /usr/lib/32/
find: cycle detected for /usr/lib/secure/32/
find: cycle detected for /usr/lib/elfedit/32/
find: cycle detected for /usr/lib/lwp/32/
find: cycle detected for /usr/lib/link_audit/32/
install: fq.h was not found anywhere!
gmake: *** [install] Error 2

This can be fixed by using /usr/gnu/bin/install instead of /usr/sbin/install for installation in the Makefile. (cf. http://zero-knowledge.org/post/80/)
Not sure how to make this portable, though.

linking on linux leads to libraries

after installing ck and jlog (./configure && make && sudo make install), fq is able to find all of its dependencies, and complies cleanly (aside from loads of warnings)
however, upon installation, we run fqd, and get

/usr/local/sbin/fqd: error while loading shared libraries: libck.so.0: cannot open shared object file: No such file or directory

ldd shows:

        linux-vdso.so.1 =>  (0x00007ffe629c0000)
        libck.so.0 => not found
        libpthread.so.0 => /lib/x86_64-linux-gnu/libpthread.so.0 (0x00007fd47bec1000)
        libdl.so.2 => /lib/x86_64-linux-gnu/libdl.so.2 (0x00007fd47bcbd000)
        libuuid.so.1 => /lib/x86_64-linux-gnu/libuuid.so.1 (0x00007fd47bab8000)
        librt.so.1 => /lib/x86_64-linux-gnu/librt.so.1 (0x00007fd47b8b0000)
        libjlog.so.2 => not found
        libsqlite3.so.0 => /usr/lib/x86_64-linux-gnu/libsqlite3.so.0 (0x00007fd47b5ea000)
        libc.so.6 => /lib/x86_64-linux-gnu/libc.so.6 (0x00007fd47b220000)
        /lib64/ld-linux-x86-64.so.2 (0x00007fd47c0df000)

readelf -d


Dynamic section at offset 0x23db8 contains 31 entries:
  Tag        Type                         Name/Value
 0x0000000000000001 (NEEDED)             Shared library: [libck.so.0]
 0x0000000000000001 (NEEDED)             Shared library: [libpthread.so.0]
 0x0000000000000001 (NEEDED)             Shared library: [libdl.so.2]
 0x0000000000000001 (NEEDED)             Shared library: [libuuid.so.1]
 0x0000000000000001 (NEEDED)             Shared library: [librt.so.1]
 0x0000000000000001 (NEEDED)             Shared library: [libjlog.so.2]
 0x0000000000000001 (NEEDED)             Shared library: [libsqlite3.so.0]
 0x0000000000000001 (NEEDED)             Shared library: [libc.so.6]
 0x000000000000000c (INIT)               0x4042c0
 0x000000000000000d (FINI)               0x41cf74
 0x0000000000000019 (INIT_ARRAY)         0x623da0
 0x000000000000001b (INIT_ARRAYSZ)       8 (bytes)
 0x000000000000001a (FINI_ARRAY)         0x623da8
 0x000000000000001c (FINI_ARRAYSZ)       8 (bytes)
 0x000000006ffffef5 (GNU_HASH)           0x400298
 0x0000000000000005 (STRTAB)             0x402198
 0x0000000000000006 (SYMTAB)             0x400788
 0x000000000000000a (STRSZ)              4575 (bytes)
 0x000000000000000b (SYMENT)             24 (bytes)
 0x0000000000000015 (DEBUG)              0x0
 0x0000000000000003 (PLTGOT)             0x624000
 0x0000000000000002 (PLTRELSZ)           3024 (bytes)
 0x0000000000000014 (PLTREL)             RELA
 0x0000000000000017 (JMPREL)             0x4036f0
 0x0000000000000007 (RELA)               0x4036a8
 0x0000000000000008 (RELASZ)             72 (bytes)
 0x0000000000000009 (RELAENT)            24 (bytes)
 0x000000006ffffffe (VERNEED)            0x4035a8
 0x000000006fffffff (VERNEEDNUM)         5
 0x000000006ffffff0 (VERSYM)             0x403378
 0x0000000000000000 (NULL)               0x0

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.