mirror of
https://git.haproxy.org/git/haproxy.git/
synced 2026-03-14 03:22:06 +01:00
MINOR: proxy: define a basic "del backend" CLI
Add "del backend" handler which is restricted to admin level. Along with it, a new function be_check_for_deletion() is used to test if the backend is removable.
This commit is contained in:
parent
d166894fef
commit
08623228a1
@ -2124,6 +2124,16 @@ del acl <acl> [<key>|#<ref>]
|
||||
listing the content of the acl. Note that if the reference <acl> is a name and
|
||||
is shared with a map, the entry will be also deleted in the map.
|
||||
|
||||
del backend <name>
|
||||
Removes the backend proxy with the name <name>.
|
||||
|
||||
This operation is only possible for TCP or HTTP proxies. To succeed, the
|
||||
backend instance must have been first unpublished.
|
||||
|
||||
This command is restricted and can only be issued on sockets configured for
|
||||
level "admin". Moreover, this feature is still considered in development so it
|
||||
also requires experimental mode (see "experimental-mode on").
|
||||
|
||||
del map <map> [<key>|#<ref>]
|
||||
Delete all the map entries from the map <map> corresponding to the key <key>.
|
||||
<map> is the #<id> or the <name> returned by "show map". If the <ref> is used,
|
||||
|
||||
@ -101,6 +101,8 @@ void free_server_rules(struct list *srules);
|
||||
int proxy_init_per_thr(struct proxy *px);
|
||||
int proxy_finalize(struct proxy *px, int *err_code);
|
||||
|
||||
int be_check_for_deletion(const char *bename, struct proxy **pb, const char **pm);
|
||||
|
||||
/*
|
||||
* This function returns a string containing the type of the proxy in a format
|
||||
* suitable for error messages, from its capabilities.
|
||||
|
||||
94
src/proxy.c
94
src/proxy.c
@ -4970,6 +4970,99 @@ static int cli_parse_add_backend(char **args, char *payload, struct appctx *appc
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Test if the backend instance named <bename> can be deleted.
|
||||
*
|
||||
* Returns a positive integer if backend can be deleted. Else, 0 is returned if
|
||||
* backend should be deletable after some delay. A negative value indicates
|
||||
* that backend cannot be deleted without any external action.
|
||||
*
|
||||
* If <pb> is not NULL, it will be set to point to the backend instance if name
|
||||
* is found. If <pm> is not NULL, it will be used on error to point to the
|
||||
* description failure.
|
||||
*/
|
||||
int be_check_for_deletion(const char *bename, struct proxy **pb, const char **pm)
|
||||
{
|
||||
struct proxy *be = NULL;
|
||||
const char *msg = NULL;
|
||||
int ret;
|
||||
|
||||
/* First, unrecoverable errors */
|
||||
ret = -1;
|
||||
|
||||
if (!(be = proxy_be_by_name(bename))) {
|
||||
msg = "No such backend.";
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (be->cap & PR_CAP_FE) {
|
||||
msg = "Cannot delete a listen section.";
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (be->mode != PR_MODE_TCP && be->mode != PR_MODE_HTTP) {
|
||||
msg = "Only TCP or HTTP proxies can be removed at runtime.";
|
||||
goto out;
|
||||
}
|
||||
|
||||
if (!(be->flags & PR_FL_BE_UNPUBLISHED)) {
|
||||
msg = "Backend must be unpublished prior to its deletion.";
|
||||
goto out;
|
||||
}
|
||||
|
||||
/* Second, conditions that may change over time */
|
||||
ret = 0;
|
||||
|
||||
if (be->beconn) {
|
||||
msg = "Backend still has attached streams on it.";
|
||||
goto out;
|
||||
}
|
||||
|
||||
ret = 1;
|
||||
|
||||
out:
|
||||
if (pb)
|
||||
*pb = be;
|
||||
if (pm)
|
||||
*pm = msg;
|
||||
return ret;
|
||||
}
|
||||
|
||||
/* Handler for "delete backend". Runs under thread isolation. Always returns 1. */
|
||||
static int cli_parse_delete_backend(char **args, char *payload, struct appctx *appctx, void *private)
|
||||
{
|
||||
struct proxy *px;
|
||||
const char *msg;
|
||||
char *be_name;
|
||||
int ret;
|
||||
|
||||
if (!cli_has_level(appctx, ACCESS_LVL_ADMIN))
|
||||
return 1;
|
||||
|
||||
if (*args[3]) {
|
||||
cli_err(appctx, "Usage: del backend <name>.\n");
|
||||
return 1;
|
||||
}
|
||||
|
||||
thread_isolate_full();
|
||||
|
||||
be_name = args[2];
|
||||
ret = be_check_for_deletion(be_name, &px, &msg);
|
||||
if (ret <= 0) {
|
||||
cli_err(appctx, msg);
|
||||
goto out;
|
||||
}
|
||||
|
||||
thread_release();
|
||||
|
||||
ha_notice("Backend deleted.\n");
|
||||
cli_umsg(appctx, LOG_INFO);
|
||||
return 1;
|
||||
|
||||
out:
|
||||
thread_release();
|
||||
return 1;
|
||||
}
|
||||
|
||||
/* Parses the "disable frontend" directive, it always returns 1.
|
||||
*
|
||||
* Grabs the proxy lock.
|
||||
@ -5292,6 +5385,7 @@ static int cli_io_handler_show_errors(struct appctx *appctx)
|
||||
/* register cli keywords */
|
||||
static struct cli_kw_list cli_kws = {{ },{
|
||||
{ { "add", "backend", NULL }, "add backend <backend> : add a new backend", cli_parse_add_backend, NULL, NULL, NULL, ACCESS_EXPERIMENTAL },
|
||||
{ { "del", "backend", NULL }, "del backend <backend> : delete a backend", cli_parse_delete_backend, NULL, NULL, NULL, ACCESS_EXPERIMENTAL },
|
||||
{ { "disable", "frontend", NULL }, "disable frontend <frontend> : temporarily disable specific frontend", cli_parse_disable_frontend, NULL, NULL },
|
||||
{ { "enable", "frontend", NULL }, "enable frontend <frontend> : re-enable specific frontend", cli_parse_enable_frontend, NULL, NULL },
|
||||
{ { "publish", "backend", NULL }, "publish backend <backend> : mark backend as ready for traffic", cli_parse_publish_backend, NULL, NULL },
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user