1+ """
2+ For a given Avid bin,
3+
4+ NOTE: This example requires the `pyavb` package. Install via `pip install pyavb`
5+ NOTE: This example requires the `pybinlock` package. Install via `pip install pybinlock`
6+ """
7+
8+ import sys , pathlib , datetime
9+ import binhistory
10+ import binlock
11+
12+ USAGE = f"Usage: { pathlib .Path (__file__ ).name } avidbin.avb"
13+
14+ try :
15+ import avb
16+ except ImportError :
17+ print ("`pyavb` package is required for this example, but was not found. Please `pip install pyavb` before using." , file = sys .stderr )
18+ sys .exit (1 )
19+
20+ def get_log_entry_for_timestamp (log :binhistory .BinLog , timestamp :datetime .datetime ) -> binhistory .BinLog :
21+ """Get the closest log entry for a given timestamp"""
22+
23+ last = None
24+ for log_entry in log :
25+ if log_entry .timestamp > timestamp :
26+ last = log_entry
27+
28+ return last
29+
30+ def build_change_list (log :binhistory .BinLog , sequences :list [avb .trackgroups .Composition ]) -> dict [binhistory .BinLogEntry , list [avb .trackgroups .Composition ]]:
31+ """Determine who changed what"""
32+
33+ changes :dict [binhistory .BinLogEntry , list [avb .trackgroups .Composition ]] = dict ()
34+
35+ for sequence in sorted (sequences , key = lambda s : s .last_modified , reverse = True ):
36+ log_entry = get_log_entry_for_timestamp (log , sequence .last_modified )
37+ if log_entry not in changes :
38+ changes [log_entry ] = []
39+ changes [log_entry ].append (sequence )
40+
41+ return changes
42+
43+
44+ if __name__ == "__main__" :
45+
46+ # Validate bin path
47+ if not len (sys .argv ) > 1 :
48+ print (USAGE , file = sys .stderr )
49+ sys .exit (2 )
50+
51+ path_bin = pathlib .Path (sys .argv [1 ])
52+
53+ if not path_bin .is_file () or not path_bin .suffix .lower () == ".avb" :
54+ print (f"Not a valid Avid bin (.avb): { sys .argv [1 ]} " , file = sys .stderr )
55+ sys .exit (3 )
56+
57+ # Get the log
58+ try :
59+ log = binhistory .BinLog .from_bin (sys .argv [1 ])
60+ except binhistory .exceptions .BinLogNotFoundError :
61+ print ("No `.log` file exists for this bin; nothing to do" )
62+ sys .exit ()
63+ except binhistory .exceptions .BinLogParseError as e :
64+ print (f"Error parsing log: { e } " , file = sys .stderr )
65+
66+ if not log :
67+ print ("The `.log` file for this bin is empty; nothing to do" )
68+ sys .exit ()
69+
70+ # Lock the bin and open it
71+ print (f"Reading bin { path_bin .name } ..." )
72+ try :
73+ with binlock .BinLock ("zAutomation" ).hold_bin (path_bin ), avb .open (path_bin ) as avb_handle :
74+ sequences = list (avb_handle .content .toplevel ())
75+ if not sequences :
76+ print ("No sequences found in bin; nothing to do" )
77+ sys .exit ()
78+
79+ sorted_log = sorted (log , key = lambda l :l .timestamp , reverse = True )
80+ changes = build_change_list (sorted_log , sequences )
81+
82+ except binlock .exceptions .BinLockExistsError as e :
83+ print ("The bin is currently locked. Changes must not be made while reading." , file = sys .stderr )
84+ sys .exit (4 )
85+
86+
0 commit comments