|
|
3604df |
From dca6f06c6b49ba92c1f2278e806c615a1a6b4b16 Mon Sep 17 00:00:00 2001
|
|
|
3604df |
From: Avra Sengupta <asengupt@redhat.com>
|
|
|
3604df |
Date: Fri, 26 Aug 2016 14:05:07 +0530
|
|
|
3604df |
Subject: [PATCH 67/79] snapshot/eventsapi: Integrate snapshot events with eventsapi
|
|
|
3604df |
|
|
|
3604df |
Backport of http://review.gluster.org/#/c/15329/
|
|
|
3604df |
|
|
|
3604df |
1. EVENT_SNAPSHOT_CREATED : snapshot_name=snap1 volume_name=test_vol
|
|
|
3604df |
snapshot_uuid=26dd6c52-6021-40b1-a507-001a80401d70
|
|
|
3604df |
2. EVENT_SNAPSHOT_CREATE_FAILED : snapshot_name=snap1 volume_name=test_vol
|
|
|
3604df |
error=Snapshot snap1 already exists
|
|
|
3604df |
3. EVENT_SNAPSHOT_ACTIVATED : snapshot_name=snap1
|
|
|
3604df |
snapshot_uuid=26dd6c52-6021-40b1-a507-001a80401d70
|
|
|
3604df |
4. EVENT_SNAPSHOT_ACTIVATE_FAILED: snapshot_name=snap1
|
|
|
3604df |
error=Snapshot snap1 is already activated.
|
|
|
3604df |
5. EVENT_SNAPSHOT_DEACTIVATED : snapshot_name=snap1
|
|
|
3604df |
snapshot_uuid=26dd6c52-6021-40b1-a507-001a80401d70
|
|
|
3604df |
6. EVENT_SNAPSHOT_DEACTIVATE_FAILED : snapshot_name=snap3
|
|
|
3604df |
error=Snapshot (snap3) does not exist.
|
|
|
3604df |
7. EVENT_SNAPSHOT_SOFT_LIMIT_REACHED : volume_name=test_vol
|
|
|
3604df |
volume_id=2ace2616-5591-4b9b-be2a-38592dda5758
|
|
|
3604df |
8. EVENT_SNAPSHOT_HARD_LIMIT_REACHED : volume_name=test_vol
|
|
|
3604df |
volume_id=2ace2616-5591-4b9b-be2a-38592dda5758
|
|
|
3604df |
9. EVENT_SNAPSHOT_RESTORED : snapshot_name=snap1 volume_name=test_vol
|
|
|
3604df |
snapshot_uuid=3a840ec5-08da-4f2b-850d-1d5539a5d14d
|
|
|
3604df |
10. EVENT_SNAPSHOT_RESTORE_FAILED : snapshot_name=snap10
|
|
|
3604df |
error=Snapshot (snap10) does not exist
|
|
|
3604df |
11. EVENT_SNAPSHOT_DELETED : snapshot_name=snap1
|
|
|
3604df |
snapshot_uuid=d9ff3d4f-f579-4345-a4da-4f9353f0950c
|
|
|
3604df |
12. EVENT_SNAPSHOT_DELETE_FAILED : snapshot_name=snap2
|
|
|
3604df |
error=Snapshot (snap2) does not exist
|
|
|
3604df |
13. EVENT_SNAPSHOT_CLONED : clone_uuid=93ba9f06-cb9c-4ace-aa52-2616e7f31022
|
|
|
3604df |
snapshot_name=snap1 clone_name=clone2
|
|
|
3604df |
14. EVENT_SNAPSHOT_CLONE_FAILED : snapshot_name=snap1 clone_name=clone2
|
|
|
3604df |
error=Volume with name:clone2 already exists
|
|
|
3604df |
15. EVENT_SNAPSHOT_CONFIG_UPDATED : auto-delete=enable config_type=system_config
|
|
|
3604df |
config_type=volume_config hard_limit=100
|
|
|
3604df |
16. EVENT_SNAPSHOT_CONFIG_UPDATE_FAILED :
|
|
|
3604df |
error=Invalid snap-max-soft-limit 110. Expected range 1 - 100
|
|
|
3604df |
17. EVENT_SNAPSHOT_SCHEDULER_INITIALISED : status=Success
|
|
|
3604df |
18. EVENT_SNAPSHOT_SCHEDULER_INIT_FAILED
|
|
|
3604df |
19. EVENT_SNAPSHOT_SCHEDULER_ENABLED : status=Successfuly Enabled
|
|
|
3604df |
20. EVENT_SNAPSHOT_SCHEDULER_ENABLE_FAILED :
|
|
|
3604df |
error=Snapshot scheduler is already enabled.
|
|
|
3604df |
21. EVENT_SNAPSHOT_SCHEDULER_SCHEDULE_ADDED : status=Successfuly added job job1
|
|
|
3604df |
22. EVENT_SNAPSHOT_SCHEDULER_SCHEDULE_ADD_FAILED :
|
|
|
3604df |
status=Failed to add job job1 error=The job already exists.
|
|
|
3604df |
23. EVENT_SNAPSHOT_SCHEDULER_SCHEDULE_EDITED :
|
|
|
3604df |
status=Successfuly edited job job1
|
|
|
3604df |
24. EVENT_SNAPSHOT_SCHEDULER_SCHEDULE_EDIT_FAILED :
|
|
|
3604df |
status=Failed to edit job job2
|
|
|
3604df |
error=The job cannot be found.
|
|
|
3604df |
25. EVENT_SNAPSHOT_SCHEDULER_SCHEDULE_DELETED :
|
|
|
3604df |
status=Successfuly deleted job job1
|
|
|
3604df |
26. EVENT_SNAPSHOT_SCHEDULER_SCHEDULE_DELETE_FAILED :
|
|
|
3604df |
status=Failed to delete job job1
|
|
|
3604df |
error=The job cannot be found.
|
|
|
3604df |
27. EVENT_SNAPSHOT_SCHEDULER_DISABLED : status=Successfuly Disabled
|
|
|
3604df |
28. EVENT_SNAPSHOT_SCHEDULER_DISABLE_FAILED :
|
|
|
3604df |
error=Snapshot scheduler is already disabled.
|
|
|
3604df |
|
|
|
3604df |
Also excluded conf.py for client build
|
|
|
3604df |
|
|
|
3604df |
> Reviewed-on: http://review.gluster.org/15329
|
|
|
3604df |
> Tested-by: Aravinda VK <avishwan@redhat.com>
|
|
|
3604df |
> Smoke: Gluster Build System <jenkins@build.gluster.org>
|
|
|
3604df |
> NetBSD-regression: NetBSD Build System <jenkins@build.gluster.org>
|
|
|
3604df |
> CentOS-regression: Gluster Build System <jenkins@build.gluster.org>
|
|
|
3604df |
> Reviewed-by: Rajesh Joseph <rjoseph@redhat.com>
|
|
|
3604df |
|
|
|
3604df |
(cherry picked from commit c1278de9a5fb6a64455f42b8b17a8d05b74c2420)
|
|
|
3604df |
|
|
|
3604df |
Change-Id: I3479cc3fb7af3c76ded67cf289f99547d0a55d21
|
|
|
3604df |
BUG: 1361184
|
|
|
3604df |
Signed-off-by: Avra Sengupta <asengupt@redhat.com>
|
|
|
3604df |
Reviewed-on: https://code.engineering.redhat.com/gerrit/84811
|
|
|
3604df |
Reviewed-by: Milind Changire <mchangir@redhat.com>
|
|
|
3604df |
Tested-by: Atin Mukherjee <amukherj@redhat.com>
|
|
|
3604df |
Reviewed-by: Atin Mukherjee <amukherj@redhat.com>
|
|
|
3604df |
---
|
|
|
3604df |
cli/src/cli-rpc-ops.c | 384 ++++++++++++++++++--
|
|
|
3604df |
configure.ac | 1 +
|
|
|
3604df |
extras/snap_scheduler/Makefile.am | 4 +-
|
|
|
3604df |
extras/snap_scheduler/conf.py.in | 11 +
|
|
|
3604df |
extras/snap_scheduler/snap_scheduler.py | 77 ++++-
|
|
|
3604df |
glusterfs.spec.in | 5 +
|
|
|
3604df |
.../mgmt/glusterd/src/glusterd-snapshot-utils.c | 1 +
|
|
|
3604df |
xlators/mgmt/glusterd/src/glusterd-snapshot.c | 105 +++++-
|
|
|
3604df |
9 files changed, 550 insertions(+), 39 deletions(-)
|
|
|
3604df |
create mode 100644 extras/snap_scheduler/conf.py.in
|
|
|
3604df |
|
|
|
3604df |
diff --git a/cli/src/cli-rpc-ops.c b/cli/src/cli-rpc-ops.c
|
|
|
3604df |
index dcf2a12..e8fc658 100644
|
|
|
3604df |
--- a/cli/src/cli-rpc-ops.c
|
|
|
3604df |
+++ b/cli/src/cli-rpc-ops.c
|
|
|
3604df |
@@ -39,6 +39,7 @@
|
|
|
3604df |
#include "cli-quotad-client.h"
|
|
|
3604df |
#include "run.h"
|
|
|
3604df |
#include "quota-common-utils.h"
|
|
|
3604df |
+#include "events.h"
|
|
|
3604df |
|
|
|
3604df |
enum gf_task_types {
|
|
|
3604df |
GF_TASK_TYPE_REBALANCE,
|
|
|
3604df |
@@ -10316,6 +10317,334 @@ out:
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
int
|
|
|
3604df |
+gf_cli_generate_snapshot_event (gf_cli_rsp *rsp, dict_t *dict,
|
|
|
3604df |
+ int32_t type, char *snap_name,
|
|
|
3604df |
+ char *volname, char *snap_uuid,
|
|
|
3604df |
+ char *clone_name)
|
|
|
3604df |
+{
|
|
|
3604df |
+ int ret = -1;
|
|
|
3604df |
+ int config_command = 0;
|
|
|
3604df |
+ int32_t delete_cmd = -1;
|
|
|
3604df |
+ uint64_t hard_limit = 0;
|
|
|
3604df |
+ uint64_t soft_limit = 0;
|
|
|
3604df |
+ char *auto_delete = NULL;
|
|
|
3604df |
+ char *snap_activate = NULL;
|
|
|
3604df |
+ char msg[PATH_MAX] = {0, };
|
|
|
3604df |
+ char option[PATH_MAX] = {0, };
|
|
|
3604df |
+
|
|
|
3604df |
+ GF_VALIDATE_OR_GOTO ("cli", dict, out);
|
|
|
3604df |
+ GF_VALIDATE_OR_GOTO ("cli", rsp, out);
|
|
|
3604df |
+
|
|
|
3604df |
+ switch (type) {
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_CREATE:
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get snap name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!volname) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get volume name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_CREATE_FAILED,
|
|
|
3604df |
+ "snapshot_name=%s;volume_name=%s;error=%s",
|
|
|
3604df |
+ snap_name, volname,
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_uuid) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get snap uuid");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_CREATED, "snapshot_name=%s;"
|
|
|
3604df |
+ "volume_name=%s;snapshot_uuid=%s", snap_name,
|
|
|
3604df |
+ volname, snap_uuid);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_ACTIVATE:
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get snap name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_ACTIVATE_FAILED,
|
|
|
3604df |
+ "snapshot_name=%s;error=%s", snap_name,
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_uuid) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get snap uuid");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_ACTIVATED, "snapshot_name=%s;"
|
|
|
3604df |
+ "snapshot_uuid=%s", snap_name, snap_uuid);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_DEACTIVATE:
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get snap name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_DEACTIVATE_FAILED,
|
|
|
3604df |
+ "snapshot_name=%s;error=%s", snap_name,
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_uuid) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get snap uuid");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_DEACTIVATED, "snapshot_name=%s;"
|
|
|
3604df |
+ "snapshot_uuid=%s", snap_name, snap_uuid);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_RESTORE:
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get snap name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_RESTORE_FAILED,
|
|
|
3604df |
+ "snapshot_name=%s;error=%s", snap_name,
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_uuid) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get snap uuid");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!volname) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get volname");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_RESTORED, "snapshot_name=%s;"
|
|
|
3604df |
+ "snapshot_uuid=%s;volume_name=%s",
|
|
|
3604df |
+ snap_name, snap_uuid, volname);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_DELETE:
|
|
|
3604df |
+ ret = dict_get_int32 (dict, "sub-cmd", &delete_cmd);
|
|
|
3604df |
+ if (ret) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Could not get sub-cmd");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ /*
|
|
|
3604df |
+ * Need not generate any event (success or failure) for delete *
|
|
|
3604df |
+ * all, as it will trigger individual delete for all snapshots *
|
|
|
3604df |
+ */
|
|
|
3604df |
+ if (delete_cmd == GF_SNAP_DELETE_TYPE_ALL) {
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get snap name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_DELETE_FAILED,
|
|
|
3604df |
+ "snapshot_name=%s;error=%s", snap_name,
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_uuid) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get snap uuid");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_DELETED, "snapshot_name=%s;"
|
|
|
3604df |
+ "snapshot_uuid=%s", snap_name, snap_uuid);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_CLONE:
|
|
|
3604df |
+ if (!clone_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get clone name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to get snapname name");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_CLONE_FAILED,
|
|
|
3604df |
+ "snapshot_name=%s;clone_name=%s;"
|
|
|
3604df |
+ "error=%s", snap_name, clone_name,
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!snap_uuid) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to get snap uuid");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_CLONED, "snapshot_name=%s;"
|
|
|
3604df |
+ "clone_name=%s;clone_uuid=%s",
|
|
|
3604df |
+ snap_name, clone_name, snap_uuid);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ case GF_SNAP_OPTION_TYPE_CONFIG:
|
|
|
3604df |
+ if (rsp->op_ret != 0) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_CONFIG_UPDATE_FAILED,
|
|
|
3604df |
+ "error=%s",
|
|
|
3604df |
+ rsp->op_errstr ? rsp->op_errstr :
|
|
|
3604df |
+ "Please check log file for details");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = dict_get_int32 (dict, "config-command", &config_command);
|
|
|
3604df |
+ if (ret) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Could not fetch config type");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ if (config_command == GF_SNAP_CONFIG_DISPLAY) {
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ /* These are optional parameters therefore ignore the error */
|
|
|
3604df |
+ ret = dict_get_uint64 (dict, "snap-max-hard-limit",
|
|
|
3604df |
+ &hard_limit);
|
|
|
3604df |
+ ret = dict_get_uint64 (dict, "snap-max-soft-limit",
|
|
|
3604df |
+ &soft_limit);
|
|
|
3604df |
+ ret = dict_get_str (dict, "auto-delete",
|
|
|
3604df |
+ &auto_delete);
|
|
|
3604df |
+ ret = dict_get_str (dict, "snap-activate-on-create",
|
|
|
3604df |
+ &snap_activate);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (!hard_limit && !soft_limit &&
|
|
|
3604df |
+ !auto_delete && !snap_activate) {
|
|
|
3604df |
+ ret = -1;
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "At least one option from "
|
|
|
3604df |
+ "snap-max-hard-limit, snap-max-soft-limit, "
|
|
|
3604df |
+ "auto-delete and snap-activate-on-create "
|
|
|
3604df |
+ "should be set");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ volname = NULL;
|
|
|
3604df |
+ ret = dict_get_str (dict, "volname", &volname);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (hard_limit || soft_limit) {
|
|
|
3604df |
+ snprintf (option, sizeof(option), "%s=%"PRIu64,
|
|
|
3604df |
+ hard_limit ? "hard_limit" : "soft_limit",
|
|
|
3604df |
+ hard_limit ? hard_limit:soft_limit);
|
|
|
3604df |
+ } else if (auto_delete || snap_activate) {
|
|
|
3604df |
+ snprintf (option, sizeof(option), "%s=%s",
|
|
|
3604df |
+ auto_delete ? "auto-delete" : "snap-activate",
|
|
|
3604df |
+ auto_delete ? auto_delete:snap_activate);
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ snprintf (msg, sizeof(msg), "config_type=%s;%s",
|
|
|
3604df |
+ volname?"volume_config":"system_config", option);
|
|
|
3604df |
+
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_CONFIG_UPDATED, "%s", msg);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ break;
|
|
|
3604df |
+
|
|
|
3604df |
+ default:
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_WARNING,
|
|
|
3604df |
+ "Cannot generate event for unknown type.");
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+out:
|
|
|
3604df |
+ return ret;
|
|
|
3604df |
+}
|
|
|
3604df |
+
|
|
|
3604df |
+/*
|
|
|
3604df |
+ * Fetch necessary data from dict at one place instead of *
|
|
|
3604df |
+ * repeating the same code again and again. *
|
|
|
3604df |
+ */
|
|
|
3604df |
+int
|
|
|
3604df |
+gf_cli_snapshot_get_data_from_dict (dict_t *dict, char **snap_name,
|
|
|
3604df |
+ char **volname, char **snap_uuid,
|
|
|
3604df |
+ int8_t *soft_limit_flag,
|
|
|
3604df |
+ char **clone_name)
|
|
|
3604df |
+{
|
|
|
3604df |
+ int ret = -1;
|
|
|
3604df |
+
|
|
|
3604df |
+ GF_VALIDATE_OR_GOTO ("cli", dict, out);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (snap_name)
|
|
|
3604df |
+ ret = dict_get_str (dict, "snapname", snap_name);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (volname)
|
|
|
3604df |
+ ret = dict_get_str (dict, "volname1", volname);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (snap_uuid)
|
|
|
3604df |
+ ret = dict_get_str (dict, "snapuuid", snap_uuid);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (soft_limit_flag)
|
|
|
3604df |
+ ret = dict_get_int8 (dict, "soft-limit-reach",
|
|
|
3604df |
+ soft_limit_flag);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (clone_name)
|
|
|
3604df |
+ ret = dict_get_str (dict, "clonename", clone_name);
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = 0;
|
|
|
3604df |
+out:
|
|
|
3604df |
+ return ret;
|
|
|
3604df |
+}
|
|
|
3604df |
+
|
|
|
3604df |
+int
|
|
|
3604df |
gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
int count, void *myframe)
|
|
|
3604df |
{
|
|
|
3604df |
@@ -10329,6 +10658,7 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
gf_boolean_t snap_driven = _gf_false;
|
|
|
3604df |
int8_t soft_limit_flag = -1;
|
|
|
3604df |
char *volname = NULL;
|
|
|
3604df |
+ char *snap_uuid = NULL;
|
|
|
3604df |
|
|
|
3604df |
GF_ASSERT (myframe);
|
|
|
3604df |
|
|
|
3604df |
@@ -10363,6 +10693,24 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
+ ret = gf_cli_snapshot_get_data_from_dict (dict, &snap_name, &volname,
|
|
|
3604df |
+ &snap_uuid, &soft_limit_flag,
|
|
|
3604df |
+ &clone_name);
|
|
|
3604df |
+ if (ret) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR, "Failed to fetch data from dict.");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+#if (USE_EVENTS)
|
|
|
3604df |
+ ret = gf_cli_generate_snapshot_event (&rsp, dict, type, snap_name,
|
|
|
3604df |
+ volname, snap_uuid, clone_name);
|
|
|
3604df |
+ if (ret) {
|
|
|
3604df |
+ gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
+ "Failed to generate snapshot event");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+#endif
|
|
|
3604df |
+
|
|
|
3604df |
/* Snapshot status and delete command is handled separately */
|
|
|
3604df |
if (global_state->mode & GLUSTER_MODE_XML &&
|
|
|
3604df |
GF_SNAP_OPTION_TYPE_STATUS != type &&
|
|
|
3604df |
@@ -10386,19 +10734,13 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_str (dict, "snapname", &snap_name);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get snap name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- /* TODO : Instead of using volname1 directly use
|
|
|
3604df |
- * volname$i in loop once snapshot of multiple
|
|
|
3604df |
- * volumes are supported
|
|
|
3604df |
- */
|
|
|
3604df |
- ret = dict_get_str (dict, "volname1", &volname);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!volname) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get volume name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
@@ -10407,8 +10749,6 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
cli_out ("snapshot create: success: Snap %s created "
|
|
|
3604df |
"successfully", snap_name);
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_int8 (dict, "soft-limit-reach",
|
|
|
3604df |
- &soft_limit_flag);
|
|
|
3604df |
if (soft_limit_flag == 1) {
|
|
|
3604df |
cli_out ("Warning: Soft-limit of volume (%s) is "
|
|
|
3604df |
"reached. Snapshot creation is not possible "
|
|
|
3604df |
@@ -10426,15 +10766,13 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_str (dict, "clonename", &clone_name);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!clone_name) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get clone name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_str (dict, "snapname", &snap_name);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get snapname name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
@@ -10447,9 +10785,6 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
break;
|
|
|
3604df |
|
|
|
3604df |
case GF_SNAP_OPTION_TYPE_RESTORE:
|
|
|
3604df |
- /* TODO: Check if rsp.op_ret needs to be checked here. Or is
|
|
|
3604df |
- * it ok to check this in the start of the function where we
|
|
|
3604df |
- * get rsp.*/
|
|
|
3604df |
if (rsp.op_ret) {
|
|
|
3604df |
cli_err("snapshot restore: failed: %s",
|
|
|
3604df |
rsp.op_errstr ? rsp.op_errstr :
|
|
|
3604df |
@@ -10458,8 +10793,7 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_str (dict, "snapname", &snap_name);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get snap name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
@@ -10471,9 +10805,6 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
ret = 0;
|
|
|
3604df |
break;
|
|
|
3604df |
case GF_SNAP_OPTION_TYPE_ACTIVATE:
|
|
|
3604df |
- /* TODO: Check if rsp.op_ret needs to be checked here. Or is
|
|
|
3604df |
- * it ok to check this in the start of the function where we
|
|
|
3604df |
- * get rsp.*/
|
|
|
3604df |
if (rsp.op_ret) {
|
|
|
3604df |
cli_err("snapshot activate: failed: %s",
|
|
|
3604df |
rsp.op_errstr ? rsp.op_errstr :
|
|
|
3604df |
@@ -10482,8 +10813,7 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_str (dict, "snapname", &snap_name);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get snap name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
@@ -10496,9 +10826,6 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
break;
|
|
|
3604df |
|
|
|
3604df |
case GF_SNAP_OPTION_TYPE_DEACTIVATE:
|
|
|
3604df |
- /* TODO: Check if rsp.op_ret needs to be checked here. Or is
|
|
|
3604df |
- * it ok to check this in the start of the function where we
|
|
|
3604df |
- * get rsp.*/
|
|
|
3604df |
if (rsp.op_ret) {
|
|
|
3604df |
cli_err("snapshot deactivate: failed: %s",
|
|
|
3604df |
rsp.op_errstr ? rsp.op_errstr :
|
|
|
3604df |
@@ -10507,8 +10834,7 @@ gf_cli_snapshot_cbk (struct rpc_req *req, struct iovec *iov,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
- ret = dict_get_str (dict, "snapname", &snap_name);
|
|
|
3604df |
- if (ret) {
|
|
|
3604df |
+ if (!snap_name) {
|
|
|
3604df |
gf_log ("cli", GF_LOG_ERROR,
|
|
|
3604df |
"Failed to get snap name");
|
|
|
3604df |
goto out;
|
|
|
3604df |
diff --git a/configure.ac b/configure.ac
|
|
|
3604df |
index 94e195c..011cf14 100644
|
|
|
3604df |
--- a/configure.ac
|
|
|
3604df |
+++ b/configure.ac
|
|
|
3604df |
@@ -43,6 +43,7 @@ AC_CONFIG_FILES([Makefile
|
|
|
3604df |
geo-replication/src/peer_mountbroker
|
|
|
3604df |
extras/peer_add_secret_pub
|
|
|
3604df |
geo-replication/syncdaemon/configinterface.py
|
|
|
3604df |
+ extras/snap_scheduler/conf.py
|
|
|
3604df |
glusterfsd/Makefile
|
|
|
3604df |
glusterfsd/src/Makefile
|
|
|
3604df |
rpc/Makefile
|
|
|
3604df |
diff --git a/extras/snap_scheduler/Makefile.am b/extras/snap_scheduler/Makefile.am
|
|
|
3604df |
index 896595f..ffc1579 100644
|
|
|
3604df |
--- a/extras/snap_scheduler/Makefile.am
|
|
|
3604df |
+++ b/extras/snap_scheduler/Makefile.am
|
|
|
3604df |
@@ -1,7 +1,7 @@
|
|
|
3604df |
snap_schedulerdir = $(sbindir)/
|
|
|
3604df |
|
|
|
3604df |
-snap_scheduler_SCRIPTS = gcron.py snap_scheduler.py
|
|
|
3604df |
+snap_scheduler_SCRIPTS = gcron.py snap_scheduler.py conf.py
|
|
|
3604df |
|
|
|
3604df |
-EXTRA_DIST = gcron.py snap_scheduler.py
|
|
|
3604df |
+EXTRA_DIST = gcron.py snap_scheduler.py conf.py
|
|
|
3604df |
|
|
|
3604df |
CLEANFILES =
|
|
|
3604df |
diff --git a/extras/snap_scheduler/conf.py.in b/extras/snap_scheduler/conf.py.in
|
|
|
3604df |
new file mode 100644
|
|
|
3604df |
index 0000000..6dcca05
|
|
|
3604df |
--- /dev/null
|
|
|
3604df |
+++ b/extras/snap_scheduler/conf.py.in
|
|
|
3604df |
@@ -0,0 +1,11 @@
|
|
|
3604df |
+#
|
|
|
3604df |
+# Copyright (c) 2016 Red Hat, Inc. <http://www.redhat.com>
|
|
|
3604df |
+# This file is part of GlusterFS.
|
|
|
3604df |
+
|
|
|
3604df |
+# This file is licensed to you under your choice of the GNU Lesser
|
|
|
3604df |
+# General Public License, version 3 or any later version (LGPLv3 or
|
|
|
3604df |
+# later), or the GNU General Public License, version 2 (GPLv2), in all
|
|
|
3604df |
+# cases as published by the Free Software Foundation.
|
|
|
3604df |
+#
|
|
|
3604df |
+
|
|
|
3604df |
+GLUSTERFS_LIBEXECDIR = '@GLUSTERFS_LIBEXECDIR@'
|
|
|
3604df |
diff --git a/extras/snap_scheduler/snap_scheduler.py b/extras/snap_scheduler/snap_scheduler.py
|
|
|
3604df |
index af092e2..23d5aa3 100755
|
|
|
3604df |
--- a/extras/snap_scheduler/snap_scheduler.py
|
|
|
3604df |
+++ b/extras/snap_scheduler/snap_scheduler.py
|
|
|
3604df |
@@ -19,7 +19,10 @@ import logging.handlers
|
|
|
3604df |
import sys
|
|
|
3604df |
import shutil
|
|
|
3604df |
from errno import EEXIST
|
|
|
3604df |
-
|
|
|
3604df |
+from conf import GLUSTERFS_LIBEXECDIR
|
|
|
3604df |
+sys.path.insert(1, GLUSTERFS_LIBEXECDIR)
|
|
|
3604df |
+from events.gf_event import gf_event
|
|
|
3604df |
+from events import eventtypes
|
|
|
3604df |
|
|
|
3604df |
SCRIPT_NAME = "snap_scheduler"
|
|
|
3604df |
scheduler_enabled = False
|
|
|
3604df |
@@ -55,6 +58,42 @@ INVALID_SCHEDULE = 15
|
|
|
3604df |
INVALID_ARG = 16
|
|
|
3604df |
VOLUME_DOES_NOT_EXIST = 17
|
|
|
3604df |
|
|
|
3604df |
+def print_error (error_num):
|
|
|
3604df |
+ if error_num == INTERNAL_ERROR:
|
|
|
3604df |
+ return "Internal Error"
|
|
|
3604df |
+ elif error_num == SHARED_STORAGE_DIR_DOESNT_EXIST:
|
|
|
3604df |
+ return "The shared storage directory ("+SHARED_STORAGE_DIR+")" \
|
|
|
3604df |
+ " does not exist."
|
|
|
3604df |
+ elif error_num == SHARED_STORAGE_NOT_MOUNTED:
|
|
|
3604df |
+ return "The shared storage directory ("+SHARED_STORAGE_DIR+")" \
|
|
|
3604df |
+ " is not mounted."
|
|
|
3604df |
+ elif error_num == ANOTHER_TRANSACTION_IN_PROGRESS:
|
|
|
3604df |
+ return "Another transaction is in progress."
|
|
|
3604df |
+ elif error_num == INIT_FAILED:
|
|
|
3604df |
+ return "Initialisation failed."
|
|
|
3604df |
+ elif error_num == SCHEDULING_ALREADY_DISABLED:
|
|
|
3604df |
+ return "Snapshot scheduler is already disabled."
|
|
|
3604df |
+ elif error_num == SCHEDULING_ALREADY_ENABLED:
|
|
|
3604df |
+ return "Snapshot scheduler is already enabled."
|
|
|
3604df |
+ elif error_num == NODE_NOT_INITIALISED:
|
|
|
3604df |
+ return "The node is not initialised."
|
|
|
3604df |
+ elif error_num == ANOTHER_SCHEDULER_ACTIVE:
|
|
|
3604df |
+ return "Another scheduler is active."
|
|
|
3604df |
+ elif error_num == JOB_ALREADY_EXISTS:
|
|
|
3604df |
+ return "The job already exists."
|
|
|
3604df |
+ elif error_num == JOB_NOT_FOUND:
|
|
|
3604df |
+ return "The job cannot be found."
|
|
|
3604df |
+ elif error_num == INVALID_JOBNAME:
|
|
|
3604df |
+ return "The job name is invalid."
|
|
|
3604df |
+ elif error_num == INVALID_VOLNAME:
|
|
|
3604df |
+ return "The volume name is invalid."
|
|
|
3604df |
+ elif error_num == INVALID_SCHEDULE:
|
|
|
3604df |
+ return "The schedule is invalid."
|
|
|
3604df |
+ elif error_num == INVALID_ARG:
|
|
|
3604df |
+ return "The argument is invalid."
|
|
|
3604df |
+ elif error_num == VOLUME_DOES_NOT_EXIST:
|
|
|
3604df |
+ return "The volume does not exist."
|
|
|
3604df |
+
|
|
|
3604df |
def output(msg):
|
|
|
3604df |
print("%s: %s" % (SCRIPT_NAME, msg))
|
|
|
3604df |
|
|
|
3604df |
@@ -499,6 +538,7 @@ def initialise_scheduler():
|
|
|
3604df |
|
|
|
3604df |
log.info("Successfully initialised snapshot scheduler for this node")
|
|
|
3604df |
output("Successfully initialised snapshot scheduler for this node")
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_INITIALISED, status="Success")
|
|
|
3604df |
|
|
|
3604df |
ret = 0
|
|
|
3604df |
return ret
|
|
|
3604df |
@@ -545,6 +585,8 @@ def perform_operation(args):
|
|
|
3604df |
ret = initialise_scheduler()
|
|
|
3604df |
if ret != 0:
|
|
|
3604df |
output("Failed to initialise snapshot scheduling")
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_INIT_FAILED,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
# Disable snapshot scheduler
|
|
|
3604df |
@@ -552,6 +594,11 @@ def perform_operation(args):
|
|
|
3604df |
ret = disable_scheduler()
|
|
|
3604df |
if ret == 0:
|
|
|
3604df |
subprocess.Popen(["touch", "-h", GCRON_TASKS])
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_DISABLED,
|
|
|
3604df |
+ status="Successfuly Disabled")
|
|
|
3604df |
+ else:
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_DISABLE_FAILED,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
# Check if the symlink to GCRON_TASKS is properly set in the shared storage
|
|
|
3604df |
@@ -582,6 +629,11 @@ def perform_operation(args):
|
|
|
3604df |
ret = enable_scheduler()
|
|
|
3604df |
if ret == 0:
|
|
|
3604df |
subprocess.Popen(["touch", "-h", GCRON_TASKS])
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_ENABLED,
|
|
|
3604df |
+ status="Successfuly Enabled")
|
|
|
3604df |
+ else:
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_ENABLE_FAILED,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
# Disable snapshot scheduler
|
|
|
3604df |
@@ -589,6 +641,11 @@ def perform_operation(args):
|
|
|
3604df |
ret = disable_scheduler()
|
|
|
3604df |
if ret == 0:
|
|
|
3604df |
subprocess.Popen(["touch", "-h", GCRON_TASKS])
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_DISABLED,
|
|
|
3604df |
+ status="Successfuly Disabled")
|
|
|
3604df |
+ else:
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_DISABLE_FAILED,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
# List snapshot schedules
|
|
|
3604df |
@@ -604,6 +661,12 @@ def perform_operation(args):
|
|
|
3604df |
ret = add_schedules(args.jobname, args.schedule, args.volname)
|
|
|
3604df |
if ret == 0:
|
|
|
3604df |
subprocess.Popen(["touch", "-h", GCRON_TASKS])
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_SCHEDULE_ADDED,
|
|
|
3604df |
+ status="Successfuly added job "+args.jobname)
|
|
|
3604df |
+ else:
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_SCHEDULE_ADD_FAILED,
|
|
|
3604df |
+ status="Failed to add job "+args.jobname,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
# Delete snapshot schedules
|
|
|
3604df |
@@ -614,6 +677,12 @@ def perform_operation(args):
|
|
|
3604df |
ret = delete_schedules(args.jobname)
|
|
|
3604df |
if ret == 0:
|
|
|
3604df |
subprocess.Popen(["touch", "-h", GCRON_TASKS])
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_SCHEDULE_DELETED,
|
|
|
3604df |
+ status="Successfuly deleted job "+args.jobname)
|
|
|
3604df |
+ else:
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_SCHEDULE_DELETE_FAILED,
|
|
|
3604df |
+ status="Failed to delete job "+args.jobname,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
# Edit snapshot schedules
|
|
|
3604df |
@@ -624,6 +693,12 @@ def perform_operation(args):
|
|
|
3604df |
ret = edit_schedules(args.jobname, args.schedule, args.volname)
|
|
|
3604df |
if ret == 0:
|
|
|
3604df |
subprocess.Popen(["touch", "-h", GCRON_TASKS])
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_SCHEDULE_EDITED,
|
|
|
3604df |
+ status="Successfuly edited job "+args.jobname)
|
|
|
3604df |
+ else:
|
|
|
3604df |
+ gf_event (eventtypes.SNAPSHOT_SCHEDULER_SCHEDULE_EDIT_FAILED,
|
|
|
3604df |
+ status="Failed to edit job "+args.jobname,
|
|
|
3604df |
+ error=print_error(ret))
|
|
|
3604df |
return ret
|
|
|
3604df |
|
|
|
3604df |
ret = INVALID_ARG
|
|
|
3604df |
diff --git a/glusterfs.spec.in b/glusterfs.spec.in
|
|
|
3604df |
index 7d3f2da..5982b1f 100644
|
|
|
3604df |
--- a/glusterfs.spec.in
|
|
|
3604df |
+++ b/glusterfs.spec.in
|
|
|
3604df |
@@ -1053,6 +1053,7 @@ exit 0
|
|
|
3604df |
%exclude %{_sbindir}/glusterd
|
|
|
3604df |
%exclude %{_sbindir}/snap_scheduler.py
|
|
|
3604df |
%exclude %{_datadir}/glusterfs/scripts/stop-all-gluster-processes.sh
|
|
|
3604df |
+%exclude %{_sbindir}/conf.py
|
|
|
3604df |
%if 0%{?_tmpfilesdir:1}
|
|
|
3604df |
%exclude %{_tmpfilesdir}/gluster.conf
|
|
|
3604df |
%endif
|
|
|
3604df |
@@ -1325,6 +1326,7 @@ exit 0
|
|
|
3604df |
# snap_scheduler
|
|
|
3604df |
%{_sbindir}/snap_scheduler.py
|
|
|
3604df |
%{_sbindir}/gcron.py
|
|
|
3604df |
+%{_sbindir}/conf.py
|
|
|
3604df |
|
|
|
3604df |
# /var/lib/glusterd, e.g. hookscripts, etc.
|
|
|
3604df |
%ghost %attr(0644,-,-) %config(noreplace) %{_sharedstatedir}/glusterd/glusterd.info
|
|
|
3604df |
@@ -2007,6 +2009,9 @@ end
|
|
|
3604df |
%endif
|
|
|
3604df |
|
|
|
3604df |
%changelog
|
|
|
3604df |
+* Fri Sep 16 2016 Avra Sengupta <asengupt@redhat.com>
|
|
|
3604df |
+- Added conf.py for snap scheduler
|
|
|
3604df |
+
|
|
|
3604df |
* Fri Sep 16 2016 Jiffin Tony Thottan <jthottan@redhat.com>
|
|
|
3604df |
- Remove ganesha.so from client xlators
|
|
|
3604df |
|
|
|
3604df |
diff --git a/xlators/mgmt/glusterd/src/glusterd-snapshot-utils.c b/xlators/mgmt/glusterd/src/glusterd-snapshot-utils.c
|
|
|
3604df |
index 2fa9a59..81b9aa0 100644
|
|
|
3604df |
--- a/xlators/mgmt/glusterd/src/glusterd-snapshot-utils.c
|
|
|
3604df |
+++ b/xlators/mgmt/glusterd/src/glusterd-snapshot-utils.c
|
|
|
3604df |
@@ -4041,6 +4041,7 @@ glusterd_is_snap_soft_limit_reached (glusterd_volinfo_t *volinfo, dict_t *dict)
|
|
|
3604df |
"set soft limit exceed flag in "
|
|
|
3604df |
"response dictionary");
|
|
|
3604df |
}
|
|
|
3604df |
+
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
ret = 0;
|
|
|
3604df |
diff --git a/xlators/mgmt/glusterd/src/glusterd-snapshot.c b/xlators/mgmt/glusterd/src/glusterd-snapshot.c
|
|
|
3604df |
index 85f2a3f..70595ef 100644
|
|
|
3604df |
--- a/xlators/mgmt/glusterd/src/glusterd-snapshot.c
|
|
|
3604df |
+++ b/xlators/mgmt/glusterd/src/glusterd-snapshot.c
|
|
|
3604df |
@@ -61,6 +61,7 @@
|
|
|
3604df |
#include "xdr-generic.h"
|
|
|
3604df |
|
|
|
3604df |
#include "lvm-defaults.h"
|
|
|
3604df |
+#include "events.h"
|
|
|
3604df |
|
|
|
3604df |
char snap_mount_dir[PATH_MAX];
|
|
|
3604df |
struct snap_create_args_ {
|
|
|
3604df |
@@ -7961,6 +7962,7 @@ glusterd_handle_snap_limit (dict_t *dict, dict_t *rsp_dict)
|
|
|
3604df |
int i = 0;
|
|
|
3604df |
char *volname = NULL;
|
|
|
3604df |
char key[PATH_MAX] = {0, };
|
|
|
3604df |
+ char msg[PATH_MAX] = {0, };
|
|
|
3604df |
glusterd_volinfo_t *volinfo = NULL;
|
|
|
3604df |
uint64_t limit = 0;
|
|
|
3604df |
int64_t count = 0;
|
|
|
3604df |
@@ -8035,6 +8037,10 @@ glusterd_handle_snap_limit (dict_t *dict, dict_t *rsp_dict)
|
|
|
3604df |
"Deleting snapshot %s.", limit, volinfo->volname,
|
|
|
3604df |
snap->snapname);
|
|
|
3604df |
|
|
|
3604df |
+ snprintf (msg, sizeof(msg), "snapshot_name=%s;"
|
|
|
3604df |
+ "snapshot_uuid=%s", snap->snapname,
|
|
|
3604df |
+ uuid_utoa(snap->snap_id));
|
|
|
3604df |
+
|
|
|
3604df |
LOCK (&snap->lock);
|
|
|
3604df |
{
|
|
|
3604df |
snap->snap_status = GD_SNAP_STATUS_DECOMMISSION;
|
|
|
3604df |
@@ -8057,6 +8063,13 @@ glusterd_handle_snap_limit (dict_t *dict, dict_t *rsp_dict)
|
|
|
3604df |
snap->snapname);
|
|
|
3604df |
}
|
|
|
3604df |
unlock: UNLOCK (&snap->lock);
|
|
|
3604df |
+ if (is_origin_glusterd (dict) == _gf_true) {
|
|
|
3604df |
+ if (ret)
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_DELETE_FAILED,
|
|
|
3604df |
+ "%s", msg);
|
|
|
3604df |
+ else
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_DELETED, "%s", msg);
|
|
|
3604df |
+ }
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
out:
|
|
|
3604df |
@@ -8142,13 +8155,20 @@ int32_t
|
|
|
3604df |
glusterd_snapshot_create_postvalidate (dict_t *dict, int32_t op_ret,
|
|
|
3604df |
char **op_errstr, dict_t *rsp_dict)
|
|
|
3604df |
{
|
|
|
3604df |
- xlator_t *this = NULL;
|
|
|
3604df |
- glusterd_conf_t *priv = NULL;
|
|
|
3604df |
- int ret = -1;
|
|
|
3604df |
- int32_t cleanup = 0;
|
|
|
3604df |
- glusterd_snap_t *snap = NULL;
|
|
|
3604df |
- char *snapname = NULL;
|
|
|
3604df |
- char *auto_delete = NULL;
|
|
|
3604df |
+ xlator_t *this = NULL;
|
|
|
3604df |
+ glusterd_conf_t *priv = NULL;
|
|
|
3604df |
+ int ret = -1;
|
|
|
3604df |
+ int32_t cleanup = 0;
|
|
|
3604df |
+ glusterd_snap_t *snap = NULL;
|
|
|
3604df |
+ char *snapname = NULL;
|
|
|
3604df |
+ char *auto_delete = NULL;
|
|
|
3604df |
+ char *volname = NULL;
|
|
|
3604df |
+ glusterd_volinfo_t *volinfo = NULL;
|
|
|
3604df |
+ uint64_t opt_hard_max = GLUSTERD_SNAPS_MAX_HARD_LIMIT;
|
|
|
3604df |
+ uint64_t opt_max_soft = GLUSTERD_SNAPS_DEF_SOFT_LIMIT_PERCENT;
|
|
|
3604df |
+ int64_t effective_max_limit = 0;
|
|
|
3604df |
+ int64_t soft_limit = 0;
|
|
|
3604df |
+ int32_t snap_activate = _gf_false;
|
|
|
3604df |
|
|
|
3604df |
this = THIS;
|
|
|
3604df |
|
|
|
3604df |
@@ -8215,6 +8235,77 @@ glusterd_snapshot_create_postvalidate (dict_t *dict, int32_t op_ret,
|
|
|
3604df |
goto out;
|
|
|
3604df |
}
|
|
|
3604df |
|
|
|
3604df |
+ /*
|
|
|
3604df |
+ * If activate_on_create was enabled, and we have reached this *
|
|
|
3604df |
+ * section of the code, that means, that after successfully *
|
|
|
3604df |
+ * creating the snapshot, we have also successfully started the *
|
|
|
3604df |
+ * snapshot bricks on all nodes. So from originator node we can *
|
|
|
3604df |
+ * send EVENT_SNAPSHOT_ACTIVATED event. *
|
|
|
3604df |
+ * *
|
|
|
3604df |
+ * Also check, if hard limit and soft limit is reached in case *
|
|
|
3604df |
+ * of successfuly creating the snapshot, and generate the event *
|
|
|
3604df |
+ */
|
|
|
3604df |
+ if (is_origin_glusterd (dict) == _gf_true) {
|
|
|
3604df |
+ snap_activate = dict_get_str_boolean (priv->opts,
|
|
|
3604df |
+ GLUSTERD_STORE_KEY_SNAP_ACTIVATE,
|
|
|
3604df |
+ _gf_false);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (snap_activate == _gf_true) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_ACTIVATED, "snapshot_name=%s;"
|
|
|
3604df |
+ "snapshot_uuid=%s", snap->snapname,
|
|
|
3604df |
+ uuid_utoa(snap->snap_id));
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = dict_get_str (dict, "volname1", &volname);
|
|
|
3604df |
+ if (ret) {
|
|
|
3604df |
+ gf_msg (this->name, GF_LOG_ERROR, 0,
|
|
|
3604df |
+ GD_MSG_DICT_GET_FAILED,
|
|
|
3604df |
+ "Failed to get volname.");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ ret = glusterd_volinfo_find (volname, &volinfo);
|
|
|
3604df |
+ if (ret) {
|
|
|
3604df |
+ gf_msg (this->name, GF_LOG_ERROR, 0,
|
|
|
3604df |
+ GD_MSG_VOL_NOT_FOUND,
|
|
|
3604df |
+ "Failed to get volinfo.");
|
|
|
3604df |
+ goto out;
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
+ /* config values snap-max-hard-limit and snap-max-soft-limit are
|
|
|
3604df |
+ * optional and hence we are not erroring out if values are not
|
|
|
3604df |
+ * present
|
|
|
3604df |
+ */
|
|
|
3604df |
+ gd_get_snap_conf_values_if_present (priv->opts, &opt_hard_max,
|
|
|
3604df |
+ &opt_max_soft);
|
|
|
3604df |
+
|
|
|
3604df |
+ if (volinfo->snap_max_hard_limit < opt_hard_max)
|
|
|
3604df |
+ effective_max_limit = volinfo->snap_max_hard_limit;
|
|
|
3604df |
+ else
|
|
|
3604df |
+ effective_max_limit = opt_hard_max;
|
|
|
3604df |
+
|
|
|
3604df |
+ /*
|
|
|
3604df |
+ * Check for hard limit. If it is reached after taking *
|
|
|
3604df |
+ * this snapshot, then generate event for the same. If *
|
|
|
3604df |
+ * it is not reached, then check for the soft limit, *
|
|
|
3604df |
+ * and generate event accordingly. *
|
|
|
3604df |
+ */
|
|
|
3604df |
+ if (volinfo->snap_count >= effective_max_limit) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_HARD_LIMIT_REACHED,
|
|
|
3604df |
+ "volume_name=%s;volume_id=%s",
|
|
|
3604df |
+ volname,
|
|
|
3604df |
+ uuid_utoa(volinfo->volume_id));
|
|
|
3604df |
+ } else {
|
|
|
3604df |
+ soft_limit = (opt_max_soft * effective_max_limit)/100;
|
|
|
3604df |
+ if (volinfo->snap_count >= soft_limit) {
|
|
|
3604df |
+ gf_event (EVENT_SNAPSHOT_SOFT_LIMIT_REACHED,
|
|
|
3604df |
+ "volume_name=%s;volume_id=%s",
|
|
|
3604df |
+ volname,
|
|
|
3604df |
+ uuid_utoa(volinfo->volume_id));
|
|
|
3604df |
+ }
|
|
|
3604df |
+ }
|
|
|
3604df |
+ }
|
|
|
3604df |
+
|
|
|
3604df |
/* "auto-delete" might not be set by user explicitly,
|
|
|
3604df |
* in that case it's better to consider the default value.
|
|
|
3604df |
* Hence not erroring out if Key is not found.
|
|
|
3604df |
--
|
|
|
3604df |
1.7.1
|
|
|
3604df |
|