-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathexperiment_utils.py
More file actions
96 lines (83 loc) · 2.89 KB
/
Copy pathexperiment_utils.py
File metadata and controls
96 lines (83 loc) · 2.89 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
from contextlib import contextmanager
from datetime import datetime, timezone
from pathlib import Path
from importlib import metadata
import json
import logging
import platform
import shutil
import sys
import time
PACKAGE_NAMES = [
'matplotlib', 'numpy', 'pandas', 'scikit-learn', 'seaborn',
'tensorflow', 'tqdm',
]
def installed_package_versions():
versions = {}
for package_name in PACKAGE_NAMES:
try:
versions[package_name] = metadata.version(package_name)
except metadata.PackageNotFoundError:
versions[package_name] = None
return versions
def configure_logging(level=logging.INFO):
logger = logging.getLogger('fall_detection')
if not logger.handlers:
handler = logging.StreamHandler()
handler.setFormatter(logging.Formatter(
'%(asctime)s | %(levelname)s | %(message)s',
datefmt='%H:%M:%S'))
logger.addHandler(handler)
logger.setLevel(level)
logger.propagate = False
return logger
def stage_directory(source, destination, logger=None):
"""Optionally copy a dataset directory to faster local storage."""
source = Path(source)
destination = Path(destination)
if not source.exists():
raise FileNotFoundError(f'Staging source does not exist: {source}')
if source.resolve() == destination.resolve():
return source
logger = logger or configure_logging()
if destination.exists():
logger.info('Using existing local dataset stage: %s', destination)
return destination
logger.info('Staging %s to %s', source, destination)
destination.parent.mkdir(parents=True, exist_ok=True)
shutil.copytree(source, destination)
logger.info('Dataset staging completed: %s', destination)
return destination
class RunTracker:
def __init__(self, logger=None):
self.logger = logger or configure_logging()
self.started_at = datetime.now(timezone.utc).isoformat()
self.timings = {}
@contextmanager
def stage(self, name):
self.logger.info('%s started', name)
started = time.perf_counter()
try:
yield
finally:
duration = time.perf_counter() - started
self.timings[name] = duration
self.logger.info('%s finished in %.2f seconds', name, duration)
def save_manifest(self, path, config=None, dataset=None, extra=None):
manifest = {
'started_at_utc': self.started_at,
'finished_at_utc': datetime.now(timezone.utc).isoformat(),
'platform': platform.platform(),
'python_version': sys.version.split()[0],
'package_versions': installed_package_versions(),
'timings_seconds': self.timings,
'config': config or {},
'dataset': dataset or {},
'extra': extra or {},
}
path = Path(path)
path.parent.mkdir(parents=True, exist_ok=True)
with path.open('w', encoding='utf-8') as manifest_file:
json.dump(manifest, manifest_file, indent=2, default=str)
self.logger.info('Run manifest saved to %s', path)
return manifest