#pragma once

/*
 * Odyssey.
 *
 * Scalable PostgreSQL connection pooler.
 */

typedef struct od_rule_pool od_rule_pool_t;

typedef enum {
	OD_RULE_POOL_SESSION,
	OD_RULE_POOL_TRANSACTION,
	OD_RULE_POOL_STATEMENT,
} od_rule_pool_type_t;

typedef enum {
	OD_RULE_POOL_INTERNAL,
	OD_RULE_POOL_CLIENT_VISIBLE,
} od_rule_routing_type_t;

typedef enum {
	OD_POOL_CLIENT_UNDEF,
	OD_POOL_CLIENT_INTERNAL,
	OD_POOL_CLIENT_EXTERNAL,
} od_pool_client_type_t;

struct od_rule_pool {
	od_rule_pool_type_t pool_type;
	od_rule_routing_type_t routing;

	char *pool_type_str;
	char *routing_type;
	char *discard_query;

	int min_size;
	int size;
	int timeout;
	int ttl;
	int discard;
	int smart_discard;
	int cancel;
	int rollback;
	int pin_on_listen;
	int notice_after_waiting_ms;
	int attach_check;
	uint64_t reset_timeout_ms;

	/* --------  makes sense only for transaction pooling --------------------------- */
	int reserve_prepared_statement;
	/* ------------------------------------------------------------------------------ */

	/* --------  makes sense only for session pooling ------------------------------- */
	uint64_t client_idle_timeout;
	uint64_t idle_in_transaction_timeout;
	/* ------------------------------------------------------------------------------ */
};

od_rule_pool_t *od_rule_pool_alloc(void);

int od_rule_pool_free(od_rule_pool_t *pool);

int od_rule_pool_compare(od_rule_pool_t *a, od_rule_pool_t *b);

int od_rule_matches_client(od_rule_pool_t *pool, od_pool_client_type_t t);

int od_rule_pool_can_add(const od_rule_pool_t *pool, int size);
