Last active
March 3, 2019 13:30
-
-
Save jrkoiter/037acacc58a96753b2cc79dc7446a370 to your computer and use it in GitHub Desktop.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/home/joost/homeassistant/bin/python3 | |
# This script will make sure that no entity in your openzwave config cache file has a duplicate name. | |
# It will also create a backup of the file. | |
import xml.etree.ElementTree as ET | |
import copy | |
import re | |
import time | |
from shutil import copyfile | |
# Fill this dict with the unique name of your choice for each node id in your zwave network | |
node_names = { | |
"1": "Zwave Stick", | |
"2": "Fibaro Wall Plug 1", | |
"3": "Fibaro Wall Plug 2", | |
"4": "..." | |
} | |
# Enter correct path to zwcfg file here | |
zwcfg_file = '/home/joost/.homeassistant/zwcfg_0xxxxxxx.xml' | |
namespace = 'http://code.google.com/p/open-zwave/' | |
ET.register_namespace('', namespace) | |
tree = ET.parse(zwcfg_file) | |
def select_elements_with_same_label (haystack, needle): | |
elems = [] | |
for i in range(len(haystack)): | |
h = haystack[i] | |
if h.attrib['label'] == needle.attrib['label'] and h is not needle: | |
elems.append(h) | |
return elems | |
def get_element_desc(elem): | |
return 'label: '+elem.attrib['label']+' instance: '+elem.attrib['instance']+' index: '+elem.attrib['index'] | |
total_dup_count = 0 | |
node_rename_count = 0 | |
# Iterate config of all Zwave nodes | |
for node in tree.findall('./{'+namespace+'}Node'): | |
node_id = node.attrib['id'] | |
node_name = node.attrib.get('name', '') | |
print("Handling node " + node.attrib['id'] + " (" + node_name + ")") | |
if(node_id in node_names and node_names[node_id] != node_name): | |
print("Renaming node to: " + node_names[node_id]) | |
node.attrib['name'] = node_names[node_id] | |
node_rename_count += 1 | |
# Iterate all child elements in node having attributes 'instance', 'index' and 'label' | |
elems = node.findall('.//*[@instance][@index][@label]') | |
dup_count = 0 | |
visited = [] | |
for elem in elems: | |
if elem in visited: | |
continue | |
# find elements having same label | |
dups = select_elements_with_same_label(elems, elem) | |
if dups: | |
dups.append(elem) | |
dups.sort(key=lambda i: (i.attrib['instance'], i.attrib['index'])) | |
for dup in dups[1:]: | |
new_label = dup.attrib['label'] + ' ' + dup.attrib['instance'] + '_' + dup.attrib['index'] | |
print(' Renaming element <' + get_element_desc(dup) + '> to have label "' + new_label + '" (duplicate of <'+get_element_desc(dups[0])+'>)') | |
dup.attrib['label'] = new_label | |
dup_count += 1 | |
# to avoid visiting these nodes again | |
visited.extend(dups) | |
print('Number of renames: ' + str(dup_count)) | |
total_dup_count += dup_count | |
millis = int(round(time.time() * 1000)) | |
copyfile(zwcfg_file, zwcfg_file + '.' + str(millis) + '.xml') | |
tree.write(zwcfg_file, xml_declaration=True, encoding="utf-8") | |
print("Finished having renamed "+ str(node_rename_count) + " nodes and relabeled " + str(total_dup_count) + " elements") | |
exit(0) | |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment