Skip to content
/ ballot Public

Consul based leader election with tagging support and hooks

License

Notifications You must be signed in to change notification settings

ncode/ballot

Repository files navigation

Ballot

Go Go Report Card License codecov

Consul-based leader election tool with tagging support and hooks for automated tasks on leadership changes.

What is it?

Ballot fills a gap in Consul's functionality by providing a built-in feature for leader election among registered services. It designates a leader among multiple services, marks the chosen leader with a specified tag, and allows for the execution of a script whenever a leader election occurs.

How does it work?

Ballot leverages Consul's session and key-value (KV) store APIs to perform leader election:

  1. Session Creation: Each service instance creates a Consul session.
  2. Lock Acquisition: Instances attempt to acquire a lock on a predefined Consul KV key using their session.
  3. Leader Election: The instance that successfully acquires the lock is elected as the leader.
  4. Tagging the Leader: The leader is tagged with a specified tag (e.g., primary) in the Consul catalog.
  5. Health Checks: The leader's health is continuously monitored. If the leader becomes unhealthy, the lock is released, and a new election occurs.
  6. Hooks Execution: Custom scripts or commands can be executed when a service is promoted to leader or demoted. More information about Consul sessions and leader elections can be found in https://developer.hashicorp.com/consul/tutorials/developer-configuration/application-leader-elections.

How do try it?

  1. Install Ballot
$ git clone https://github.com/ncode/ballot
$ cd configs/development
  1. Run the development setup
$ make &
  1. Open consul ui http://127.0.0.1:8500/ui/dc1/services/my-service/instances
  2. Play with the health checks and see the election happening and moving
$ find consul/state
consul/state
consul/state/ready1
consul/state/ready3
consul/state/ready2
$ rm consul/state/ready1
$ sleep 10
$ touch consul/state/ready1
$ rm consul/state/ready2
$ sleep 10
$ touch consul/state/ready2
$ rm consul/state/ready3
$ sleep 10
$ touch consul/state/ready3

Environment variables

During the call of execOnPromote and execOnDemote a few environment variables are injected incase you need to use the and port of the service for an intended automation.

$ADDRESS   # IP Address of the current service elected
$PORT      # Port of the service
$SESSIONID # Current SessionID of the elected master

Configuration

The configuration file is a yaml file with the following structure:

consul:
  token:                                    # Consul token
election:
  enabled:
    - my-service-name                       # Name of the service enabled for election
  services:
    my-service-name:                        # Name of the service
      id: my-service-name                   # ID of the service
      key: my-service-name                  # Key to be used for the lock in Consul, this should be the same across all nodes
      token:                                # Token to be used for the session in Consul
      serviceChecks:                        # List of checks to be used to determine the health of the service
        - ping                              # Name of the check
      primaryTag: primary                   # Tag to be used to mark the leader
      execOnPromote: '/bin/echo primary'    # Command to be executed when the service is elected as leader
      execOnDemote: '/bin/echo secondary'   # Command to be executed when the service is demoted as leader
      ttl: 10s                              # TTL for the session
      lockDelay: 5s                         # Lock delay for the session

Development and examples

Examples of configuration files and service definitions can be found inside config/development

Contributing

Contributions are welcome! Please open an issue or submit a pull request for any improvements, bug fixes, or new features.

TODO

  • Write more tests
  • Allow to pre-define the preferred leader

License

This project is licensed under the Apache License 2.0. See the LICENSE file for details.

About

Consul based leader election with tagging support and hooks

Resources

License

Stars

Watchers

Forks

Languages