diff --git a/library/storage/syncthing/syncthing_device.py b/library/storage/syncthing/syncthing_device.py index bc8b4e9..0a18709 100644 --- a/library/storage/syncthing/syncthing_device.py +++ b/library/storage/syncthing/syncthing_device.py @@ -82,7 +82,7 @@ from xml.etree.ElementTree import parse from ansible.module_utils.basic import AnsibleModule from ansible.module_utils.urls import fetch_url, url_argument_spec -SYNCTHING_API_URI = "/rest/system/config" +SYNCTHING_API_URI = "/rest/config/devices" if platform.system() == 'Windows': DEFAULT_ST_CONFIG_LOCATION = '%localappdata%/Syncthing/config.xml' elif platform.system() == 'Darwin': @@ -91,8 +91,11 @@ else: DEFAULT_ST_CONFIG_LOCATION = '$HOME/.config/syncthing/config.xml' -def make_headers(host, api_key): - url = '{}{}'.format(host, SYNCTHING_API_URI) +def make_headers(host, api_key, device=None): + if device: + url = '{}{}/{}'.format(host, SYNCTHING_API_URI, device) + else: + url = '{}{}'.format(host, SYNCTHING_API_URI) headers = {'X-Api-Key': api_key } return url, headers @@ -112,11 +115,19 @@ def get_key_from_filesystem(module): "the API key manually.") # Fetch Syncthing configuration -def get_config(module): - url, headers = make_headers(module.params['host'], module.params['api_key']) +def remote_config(module, method='GET', config=None, result=None, device=None): + url, headers = make_headers(module.params['host'], module.params['api_key'], + device) + data = config + if config: + headers['Content-Type'] = 'application/json' + data = json.dumps(config) + if not result: + result = {} + resp, info = fetch_url( - module, url, data=None, headers=headers, - method='GET', timeout=module.params['timeout']) + module, url, data=data, headers=headers, + method=method, timeout=module.params['timeout']) if not info or info['status'] != 200: result['response'] = info @@ -131,19 +142,22 @@ def get_config(module): return json.loads(content) + +def get_device(module, device=None): + return remote_config(module, device=device) +def delete_device(module, device, result=None): + return remote_config(module, method='DELETE', device=device, result=result) + # Post the new configuration to Syncthing API -def post_config(module, config, result): - url, headers = make_headers(module.params['host'], module.params['api_key']) - headers['Content-Type'] = 'application/json' - - result['msg'] = config - resp, info = fetch_url( - module, url, data=json.dumps(config), headers=headers, - method='POST', timeout=module.params['timeout']) - - if not info or info['status'] != 200: - result['response'] = str(info) - module.fail_json(msg='Error occured while posting new config', **result) +def post_device(module, config, result=None, device=None): + return remote_config(module, method='POST', config=config, result=result, + device=device) +def put_device(module, config, result=None, device=None): + return remote_config(module, method='PUT', config=config, result=result, + device=device) +def patch_device(module, config, result=None, device=None): + return remote_config(module, method='PATCH', config=config, result=result, + device=device) # Returns an object of a new device def create_device(params): @@ -204,35 +218,26 @@ def run_module(): if not module.params['api_key']: module.params['api_key'] = get_key_from_filesystem(module) - config = get_config(module) + device = get_device(module, module.params['id']) + device_exists = False + if 'deviceID' in device and device['deviceID'] == module.params['id']: + device_exists = True + want_pause = module.params['state'] == 'pause' + if module.params['state'] == 'absent': - # Remove device from list, if found - for idx, device in enumerate(config['devices']): - if device['deviceID'] == module.params['id']: - config['devices'].pop(idx) - result['changed'] = True - break - else: - # Bail-out if device is already added - for device in config['devices']: - if device['deviceID'] == module.params['id']: - want_pause = module.params['state'] == 'pause' - if (want_pause and device['paused']) or \ - (not want_pause and not device['paused']): - module.exit_json(**result) - else: - device['paused'] = want_pause - result['changed'] = True - break - - # Append the new device into configuration - if not result['changed']: - device = create_device(module.params) - config['devices'].append(device) + if device_exists: + delete_device(module, device=device['deviceID'], result=result) result['changed'] = True - - if result['changed']: - post_config(module, config, result) + elif device_exists: # exists but maybe needs changing + if device['paused'] != want_pause: + device['paused'] = want_pause + patch_device(module, config=device, result=result, + device=device['deviceID']) + result['changed'] = True + else: # Doesn't exist but needs to be added + device = create_device(module.params) + post_device(module, config=device, result=result) + result['changed'] = True module.exit_json(**result)