import re
import sys
from pathlib import Path
[docs]def options_from_command(command):
p = re.compile('^-+([^=]+)=?(.*)')
return {
p.match(val).group(1): p.match(val).group(2)
for val in command.split()
if val.startswith('-')
}
[docs]def arguments_from_command(command):
command = re.sub(r'command_line:', '', command)
return [arg for arg in command.split()[1:] if not arg.startswith('-')]
[docs]def model_paths(path, pattern, subpath='m1'):
path = Path(path) / subpath
model_paths = list(path.glob(pattern))
model_paths.sort(key=lambda name: int(re.sub(r'\D', '', str(name))))
return model_paths
[docs]def psn_directory_list(path, drop_tools=list()):
path = Path(path)
folder_list = [{'name': p.name, 'tool': tool_name(p)} for p in path.iterdir() if p.is_dir()]
return [d for d in folder_list if d['tool'] is not None and not d['tool'] in drop_tools]
[docs]def psn_command(path):
path = Path(path)
if not path.is_dir():
return None
try:
with open(path / 'command.txt') as meta:
return next(meta)
except FileNotFoundError:
pass
try:
with open(path / 'meta.yaml') as meta:
cmd = None
for row in meta:
if row.startswith('command_line: '):
cmd = row.strip()
elif cmd is not None:
# command can be split over multiple lines
if row.startswith('common_options:'):
return cmd
elif re.match(r'\s', row): # continuation is indented
cmd += row.strip()
if cmd is not None:
return cmd
except FileNotFoundError:
pass
[docs]def cmd_line_model_path(path):
path = Path(path)
with open(path / 'meta.yaml') as meta:
for row in meta:
row = row.strip()
if row.startswith('model_files:'):
row = next(meta).strip()
return Path(re.sub(r'^-\s*', '', row))
[docs]def template_model_string(datafile=None, ignore=list(), drop=list(), label='TEMPLATE'):
variables = ''
indent = r' '
ignores = indent + 'IGNORE=@'
if len(ignore) > 0:
ignores += '\n' + '\n'.join([indent + f'IGNORE=({ign})' for ign in ignore])
if datafile is None:
datafile = 'dummydata.csv'
else:
datafile = Path(datafile)
try:
with open(datafile) as data:
row = next(data)
row = row.strip()
if re.match(r'[A-Z]', row):
names = row.split(r',')
variables = ' '
start = 0
while start < len(names):
stop = min(start + 10, len(names))
variables += (
' '.join([n if n not in drop else 'DROP' for n in names[start:stop]])
+ '\n '
)
start = stop
else:
pass # unsupported header type
except FileNotFoundError:
pass
return '\n'.join(
[
'$PROBLEM ' + label,
'$INPUT' + variables,
f'$DATA {str(datafile)}',
ignores,
'$SUBROUTINE ADVAN1 TRANS2',
'',
'$PK',
'CL=THETA(1)*EXP(ETA(1))',
'V=THETA(2)*EXP(ETA(2))',
'S1=V',
'',
'$ERROR',
'Y=F+F*EPS(1)',
'',
'$THETA (0, 1) ; TVCL',
'$THETA (0, 5) ; TVV',
'$OMEGA 0.1 ; IVCL',
'$OMEGA 0.1 ; IVV',
'$SIGMA 0.025 ; RUV',
'',
'$ESTIMATION METHOD=1 INTERACTION',
'$COVARIANCE PRINT=E MATRIX=S UNCONDITIONAL',
]
)
[docs]def pharmpy_wrapper():
"""Command line wrapper for PsN to call pharmpy"""
args = sys.argv[1:]
locs = dict()
exec(args[0], globals(), locs)