mirror of
https://github.com/ansible-collections/community.general.git
synced 2024-09-14 20:13:21 +02:00
* influxdb_retention_policy: ensure duration parameters are idempotent (#2281) * add changelog for pr #2284
This commit is contained in:
parent
1b79440896
commit
aea12899cc
2 changed files with 105 additions and 30 deletions
|
@ -0,0 +1,4 @@
|
|||
bugfixes:
|
||||
- influxdb_retention_policy - ensure idempotent module execution with different
|
||||
duration and shard duration parameter values
|
||||
(https://github.com/ansible-collections/community.general/issues/2281).
|
|
@ -31,7 +31,9 @@ options:
|
|||
type: str
|
||||
duration:
|
||||
description:
|
||||
- Determines how long InfluxDB should keep the data.
|
||||
- Determines how long InfluxDB should keep the data. If specified, it
|
||||
should be C(INF) or at least one hour. If not specified, C(INF) is
|
||||
assumed. Supports complex duration expressions with multiple units.
|
||||
required: true
|
||||
type: str
|
||||
replication:
|
||||
|
@ -46,9 +48,10 @@ options:
|
|||
default: false
|
||||
shard_group_duration:
|
||||
description:
|
||||
- Determines the size of a shard group.
|
||||
- Value needs to be integer literal followed immediately (with no spaces) by a duration unit.
|
||||
Supported duration units are C(h) for hours, C(d) for days, and C(w) for weeks. For example C(10d), C(1h), C(2w).
|
||||
- Determines the time range covered by a shard group. If specified it
|
||||
must be at least one hour. If none, it's determined by InfluxDB by
|
||||
the rentention policy's duration. Supports complex duration expressions
|
||||
with multiple units.
|
||||
type: str
|
||||
version_added: '2.0.0'
|
||||
extends_documentation_fragment:
|
||||
|
@ -96,6 +99,17 @@ EXAMPLES = r'''
|
|||
ssl: no
|
||||
validate_certs: no
|
||||
shard_group_duration: 1w
|
||||
|
||||
- name: Create retention policy with complex durations
|
||||
community.general.influxdb_retention_policy:
|
||||
hostname: "{{influxdb_ip_address}}"
|
||||
database_name: "{{influxdb_database_name}}"
|
||||
policy_name: test
|
||||
duration: 5d1h30m
|
||||
replication: 1
|
||||
ssl: no
|
||||
validate_certs: no
|
||||
shard_group_duration: 1d10h30m
|
||||
'''
|
||||
|
||||
RETURN = r'''
|
||||
|
@ -115,6 +129,51 @@ from ansible_collections.community.general.plugins.module_utils.influxdb import
|
|||
from ansible.module_utils._text import to_native
|
||||
|
||||
|
||||
VALID_DURATION_REGEX = re.compile(r'^(\d+(ns|u|µ|ms|s|m|h|d|w))+$')
|
||||
|
||||
DURATION_REGEX = re.compile(r'(\d+)(ns|u|µ|ms|s|m|h|d|w)')
|
||||
EXTENDED_DURATION_REGEX = re.compile(r'(?:(\d+)(ns|u|µ|ms|m|h|d|w)|(\d+(?:\.\d+)?)(s))')
|
||||
|
||||
|
||||
def check_duration_literal(value):
|
||||
return VALID_DURATION_REGEX.search(value) is not None
|
||||
|
||||
|
||||
def parse_duration_literal(value, extended=False):
|
||||
duration = 0.0
|
||||
|
||||
if value == "INF":
|
||||
return duration
|
||||
|
||||
lookup = (EXTENDED_DURATION_REGEX if extended else DURATION_REGEX).findall(value)
|
||||
|
||||
for duration_literal in lookup:
|
||||
if extended and duration_literal[3] == 's':
|
||||
duration_val = float(duration_literal[2])
|
||||
duration += duration_val * 1000 * 1000 * 1000
|
||||
else:
|
||||
duration_val = int(duration_literal[0])
|
||||
|
||||
if duration_literal[1] == 'ns':
|
||||
duration += duration_val
|
||||
elif duration_literal[1] == 'u' or duration_literal[1] == 'µ':
|
||||
duration += duration_val * 1000
|
||||
elif duration_literal[1] == 'ms':
|
||||
duration += duration_val * 1000 * 1000
|
||||
elif duration_literal[1] == 's':
|
||||
duration += duration_val * 1000 * 1000 * 1000
|
||||
elif duration_literal[1] == 'm':
|
||||
duration += duration_val * 1000 * 1000 * 1000 * 60
|
||||
elif duration_literal[1] == 'h':
|
||||
duration += duration_val * 1000 * 1000 * 1000 * 60 * 60
|
||||
elif duration_literal[1] == 'd':
|
||||
duration += duration_val * 1000 * 1000 * 1000 * 60 * 60 * 24
|
||||
elif duration_literal[1] == 'w':
|
||||
duration += duration_val * 1000 * 1000 * 1000 * 60 * 60 * 24 * 7
|
||||
|
||||
return duration
|
||||
|
||||
|
||||
def find_retention_policy(module, client):
|
||||
database_name = module.params['database_name']
|
||||
policy_name = module.params['policy_name']
|
||||
|
@ -129,6 +188,11 @@ def find_retention_policy(module, client):
|
|||
break
|
||||
except requests.exceptions.ConnectionError as e:
|
||||
module.fail_json(msg="Cannot connect to database %s on %s : %s" % (database_name, hostname, to_native(e)))
|
||||
|
||||
if retention_policy is not None:
|
||||
retention_policy["duration"] = parse_duration_literal(retention_policy["duration"], extended=True)
|
||||
retention_policy["shardGroupDuration"] = parse_duration_literal(retention_policy["shardGroupDuration"], extended=True)
|
||||
|
||||
return retention_policy
|
||||
|
||||
|
||||
|
@ -140,6 +204,21 @@ def create_retention_policy(module, client):
|
|||
default = module.params['default']
|
||||
shard_group_duration = module.params['shard_group_duration']
|
||||
|
||||
if not check_duration_literal(duration):
|
||||
module.fail_json(msg="Failed to parse value of duration")
|
||||
|
||||
influxdb_duration_format = parse_duration_literal(duration)
|
||||
if influxdb_duration_format != 0 and influxdb_duration_format < 3600000000000:
|
||||
module.fail_json(msg="duration value must be at least 1h")
|
||||
|
||||
if shard_group_duration is not None:
|
||||
if not check_duration_literal(shard_group_duration):
|
||||
module.fail_json(msg="Failed to parse value of shard_group_duration")
|
||||
|
||||
influxdb_shard_group_duration_format = parse_duration_literal(shard_group_duration)
|
||||
if influxdb_shard_group_duration_format < 3600000000000:
|
||||
module.fail_json(msg="shard_group_duration value must be at least 1h")
|
||||
|
||||
if not module.check_mode:
|
||||
try:
|
||||
if shard_group_duration:
|
||||
|
@ -159,38 +238,30 @@ def alter_retention_policy(module, client, retention_policy):
|
|||
replication = module.params['replication']
|
||||
default = module.params['default']
|
||||
shard_group_duration = module.params['shard_group_duration']
|
||||
duration_regexp = re.compile(r'(\d+)([hdw]{1})|(^INF$){1}')
|
||||
|
||||
changed = False
|
||||
|
||||
duration_lookup = duration_regexp.search(duration)
|
||||
if not check_duration_literal(duration):
|
||||
module.fail_json(msg="Failed to parse value of duration")
|
||||
|
||||
if duration_lookup.group(2) == 'h':
|
||||
influxdb_duration_format = '%s0m0s' % duration
|
||||
elif duration_lookup.group(2) == 'd':
|
||||
influxdb_duration_format = '%sh0m0s' % (int(duration_lookup.group(1)) * 24)
|
||||
elif duration_lookup.group(2) == 'w':
|
||||
influxdb_duration_format = '%sh0m0s' % (int(duration_lookup.group(1)) * 24 * 7)
|
||||
elif duration == 'INF':
|
||||
influxdb_duration_format = '0'
|
||||
influxdb_duration_format = parse_duration_literal(duration)
|
||||
if influxdb_duration_format != 0 and influxdb_duration_format < 3600000000000:
|
||||
module.fail_json(msg="duration value must be at least 1h")
|
||||
|
||||
if shard_group_duration:
|
||||
shard_group_duration_lookup = duration_regexp.search(shard_group_duration)
|
||||
if not shard_group_duration_lookup:
|
||||
module.fail_json(
|
||||
msg="Failed to parse value of shard_group_duration. Please see the documentation for valid values")
|
||||
if shard_group_duration_lookup.group(2) == 'h':
|
||||
influxdb_shard_group_duration_format = '%s0m0s' % duration
|
||||
elif shard_group_duration_lookup.group(2) == 'd':
|
||||
influxdb_shard_group_duration_format = '%sh0m0s' % (int(shard_group_duration_lookup.group(1)) * 24)
|
||||
elif shard_group_duration_lookup.group(2) == 'w':
|
||||
influxdb_shard_group_duration_format = '%sh0m0s' % (int(shard_group_duration_lookup.group(1)) * 24 * 7)
|
||||
if shard_group_duration is None:
|
||||
influxdb_shard_group_duration_format = retention_policy["shardGroupDuration"]
|
||||
else:
|
||||
influxdb_shard_group_duration_format = retention_policy['shardGroupDuration']
|
||||
if not check_duration_literal(shard_group_duration):
|
||||
module.fail_json(msg="Failed to parse value of shard_group_duration")
|
||||
|
||||
if (not retention_policy['duration'] == influxdb_duration_format or
|
||||
not retention_policy['replicaN'] == int(replication) or
|
||||
not retention_policy['shardGroupDuration'] == influxdb_shard_group_duration_format or
|
||||
not retention_policy['default'] == default):
|
||||
influxdb_shard_group_duration_format = parse_duration_literal(shard_group_duration)
|
||||
if influxdb_shard_group_duration_format < 3600000000000:
|
||||
module.fail_json(msg="shard_group_duration value must be at least 1h")
|
||||
|
||||
if (retention_policy['duration'] != influxdb_duration_format or
|
||||
retention_policy['shardGroupDuration'] != influxdb_shard_group_duration_format or
|
||||
retention_policy['replicaN'] != int(replication) or
|
||||
retention_policy['default'] != default):
|
||||
if not module.check_mode:
|
||||
try:
|
||||
client.alter_retention_policy(policy_name, database_name, duration, replication, default,
|
||||
|
|
Loading…
Reference in a new issue