try:
from nrgpy import logger
except ImportError:
pass
from datetime import datetime
import os
import subprocess
import time
import traceback
from nrgpy.api.convert import nrg_api_convert
from nrgpy.utils.utilities import (
check_platform,
windows_folder_path,
affirm_directory,
count_files,
is_sympro_running,
)
[docs]class local:
"""For handling NRG SymphoniePRO Data Logger raw data files in the *.rld format.
This method uses locally installed SymphoniePRO Desktop software to convert *.rld
files to txt format (tab-delimited-text).
Parameters
----------
rld_dir : str, optional (path-like)
specify directory. Note for unc values, you
will need to escape all forward slashes, e.g.
rld_dir = "\\\\network\\techsupport\\data\\"
or use the r'\\path\to\dir' approach
out_dir : str, optional (path-like)
see note for rld_dir.
encryption_pass : str
specify data encryption password if logger is set up for that.
hex_key : str
specify if using hex data encryption key
sympro_path : str
default is "C:\Program Files (x86)\Renewable NRG Systems\SymPRO Desktop\SymPRODesktop.exe"
process_type : str
[convert], or import
convert_type : str
'meas', alternately specify 'comm', 'diag', 'sample', or 'events'
nec : str
path to nec file
site_filter : str
specify part or all of the file you'd like to filter on, like site_filter='123456_2018-09'
would filter on site 123456 and only the month of September in 2018.
site_file : bool or str
set to True to use local ndb site file, or set to path to an alternate ndb site file
Examples
--------
Convert a folder of RLD files to Text with SymphoniePRO Desktop Software
>>> from nrgpy.convert_rld import local
>>> converter = local(
rld_dir='/path/to/rld/files',
out_dir=/path/to/txt/outputs,
file_filter='123456_2020-01', # for files from January 2020
)
>>> converter.convert()
"""
def __init__(
self,
rld_dir: str="",
out_dir: str="",
encryption_pass: str="",
hex_key: str="",
filename: str="",
sympro_path: str=r'"C:/Program Files (x86)/Renewable NRG Systems/SymPRO Desktop/SymPRODesktop.exe"',
process_type: str="convert",
convert_type: str="meas",
nec: str="",
site_filter: str="",
site_file: str="",
**kwargs,
):
self.rld_dir = windows_folder_path(rld_dir)
self.out_dir = windows_folder_path(out_dir)
self.encryption_pass = encryption_pass
self.hex_key = hex_key
self.sympro_path = sympro_path
self.process_type = process_type
self.convert_type = convert_type
self.nec = nec
self.site_filter = site_filter
self.site_file = site_file
if "file_filter" in kwargs and site_filter == "":
self.file_filter = kwargs.get("file_filter")
self.site_filter = self.file_filter
if check_platform() == "win32":
if is_sympro_running():
print(
"SymphoniePRO Desktop is already running. Please close it and try again."
)
logger.error(
"SymphoniePRO Desktop is already running so it could not be run"
)
elif filename:
affirm_directory(self.out_dir)
self.single_file(filepath=filename)
else:
print(
"""
convert_rld.local() method ONLY compatible with Windows OS.
Please use nrgpy.cloud_convert() method instead.
Alternately, follow the instructions for using SymphoniePRO Desktop
with wine here:
https://github.com/nrgpy/nrgpy/blob/master/SymPRODeskop_Linux_README.md
"""
)
[docs] def directory(self):
"""processes all rld files in self.rld_dir, outputs to txt files to out_dir"""
affirm_directory(self.out_dir)
try:
if self.encryption_pass:
encryption = '/pass "{0}"'.format(self.encryption_pass)
else:
encryption = ""
except Exception:
print("could not parse encryption_pass")
try:
if self.hex_key:
encryption_key = '/key "{0}"'.format(self.hex_key)
else:
encryption_key = ""
except Exception:
print("could not parse hex_key")
try:
if self.nec:
nec = '/config "{0}"'.format(self.nec)
else:
nec = ""
except Exception:
print("could not parse encryption_pass")
try:
if self.site_file:
site_file = "/site "
elif self.site_file:
site_file = '/site "{0}"'.format(self.site_file)
else:
site_file = ""
except Exception:
print("could not parse encryption_pass")
try:
rld_count = count_files(self.rld_dir, self.site_filter, "rld")
self.start_time = time.time()
logger.info("converting {0} files from {1}".format(rld_count, self.rld_dir))
print("\nConverting {0} files from {1}\n".format(rld_count, self.rld_dir))
print("Saving outputs to {0}".format(self.out_dir))
cmd = [
self.sympro_path,
"/cmd",
self.process_type,
"/file",
'"' + "\\".join([self.rld_dir, "*" + self.site_filter]) + '*.rld"',
encryption,
encryption_key,
nec,
site_file,
"/type",
'"' + self.convert_type + '"',
"/outputdir",
'"' + self.out_dir[:-1] + '"',
]
# print('\nUsing command line script:\n{}'.format(" ".join(cmd)))
self.cmd = cmd
self.start = datetime.now()
subprocess.run(" ".join(cmd), stdout=subprocess.PIPE)
self.end = datetime.now()
self.convert_time = str(self.end - self.start)
logger.info("TXT files saved in {0}".format(self.out_dir))
print("\nTXT files saved in {0}\n".format(self.out_dir))
txt_count = count_files(
self.out_dir, self.site_filter, "txt", start_time=self.start_time
)
log_count, log_files = count_files(
self.out_dir,
self.site_filter,
"log",
show_files=True,
start_time=self.start_time,
)
logger.info(f"IN: {rld_count}, OUT: {txt_count}, FAILED: {log_count}")
print("RLDs in : {}".format(rld_count))
print("TXTs out : {}".format(txt_count))
print("LOGs out : {}".format(log_count))
if len(log_files) > 0:
print("Log files created:")
for _filename in log_files:
print("\t{}".format(_filename))
print(
"----------------\nDifference : {}".format(
rld_count - (txt_count + log_count)
)
)
except FileNotFoundError:
logger.error(
"SymphoniePRO Desktop Application not found: {0}".format(
self.sympro_path
)
)
print(
"""
No instance of SymphoniePRO Desktop Application found.
Please follow the link below to download and install this software:
https://www.nrgsystems.com/support/product-support/software/symphoniepro-desktop-application
"""
)
except Exception:
logger.error("unable to process files in {0}".format(self.rld_dir))
logger.debug(traceback.format_exc())
print("Unable to process files in directory")
[docs] def convert(self):
self.directory()
[docs] def process(self):
self.directory()
[docs] def rename_rlds(self, **kwargs):
"""uses SymPRO utility NrgRldSiteSerialRename.exe to rename files with site number and logger serial number.
This function is only compatible with Windows>=7 AND
a local installation of SymphoniePRO Desktop software
"""
try:
renamer_path = kwargs.get(
"renamer_path",
r"C:/Program Files (x86)/Renewable NRG Systems/SymPRO Desktop/Default Application Files/Utilities/NrgRldSiteSerialRename.exe",
)
for f in os.listdir(self.rld_dir):
filepath = self.rld_dir + f
if f[-4:].lower() == ".rld" and self.site_filter in f:
rename_cmd = [renamer_path, '"' + filepath + '"']
try:
subprocess.run(" ".join(rename_cmd), stdout=subprocess.PIPE)
except:
logger.error("unable to rename {0}".format(f))
print("Unable to rename {0}".format(f))
pass
else:
pass
except Exception:
logger.error("Could not rename files")
logger.debug(traceback.format_exc())
print("Could not rename files")
[docs] def single_file(self, filepath=""):
self.filepath = filepath.replace("/", "\\")
try:
if self.encryption_pass:
encryption = '/pass "{0}"'.format(self.encryption_pass)
else:
encryption = ""
except Exception:
print("could not parse encryption_pass")
try:
if self.hex_key:
encryption_key = '/key "{0}"'.format(self.hex_key)
else:
encryption_key = ""
except Exception:
print("could not parse hex_key")
try:
if self.nec:
nec = '/config "{0}"'.format(self.nec)
else:
nec = ""
except Exception:
print("could not get nec file")
try:
if self.site_file:
site_file = '/site "{0}"'.format(self.site_file)
else:
site_file = ""
except Exception:
print("could not get site file")
cmd = [
self.sympro_path,
"/cmd",
"convert",
"/file",
'"' + self.filepath + '"',
encryption,
encryption_key,
nec,
site_file,
"/type",
'"' + self.convert_type + '"',
"/outputdir",
'"' + self.out_dir[:-1] + '"',
]
self.cmd = cmd
try:
print("{0} ... \t".format(filepath), end="", flush=True)
p = subprocess.run(
" ".join(cmd), stderr=subprocess.PIPE, stdout=subprocess.PIPE
)
if (
"File does not" in p.stdout.decode()
or "Decryption failed" in p.stdout.decode()
):
print("[FAILED]")
print(f"{p.stdout.decode()}")
logger.error(f"{p.stdout.decode()}")
else:
logger.info(f"{p.stdout.decode()}")
print("[DONE]")
except Exception:
logger.error("processing {0} FAILED".format(filepath))
logger.debug(traceback.format_exc())
print("\n\t processing {0} [FAILED]".format(filepath))
pass
logger.info("files in {0} processed OK".format(self.rld_dir))
logger.info("TXT files saved to {0}".format(self.out_dir))
nrg_convert_api = nrg_api_convert