Release v0.29.0 — offset detector + false_trigger_reason + BlastMate serials (0.27.0→0.29.0) #36
@@ -62,12 +62,31 @@ _STEM = re.compile(r"^([B-Z])(\d{3})")
|
||||
_B36 = "0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ"
|
||||
|
||||
|
||||
def serial_of(name: str) -> str:
|
||||
"""`P036L318.C80H` -> `BE14036`. See CLAUDE.md, serial encoding."""
|
||||
_SERIAL_RE = re.compile(rb"\b([A-Z]{2}\d{3,6})\b")
|
||||
|
||||
|
||||
def serial_of(name: str, path=None) -> str:
|
||||
"""Real serial for a BW file.
|
||||
|
||||
The filename encodes only the NUMBER: `<letter><3 digits>` where
|
||||
letter = chr(ord('B') + serial // 1000). The two-letter family prefix
|
||||
("BE", "BA", ...) is **not** in the filename, so it must be read out of
|
||||
the file body. Four units in the DL2 archive are BA, not BE — assuming
|
||||
"BE" mislabels BA9229, BA10060, BA10895 and BA15957.
|
||||
"""
|
||||
m = _STEM.match(name)
|
||||
if not m:
|
||||
return "?"
|
||||
return f"BE{(ord(m.group(1)) - ord('B')) * 1000 + int(m.group(2))}"
|
||||
num = (ord(m.group(1)) - ord("B")) * 1000 + int(m.group(2))
|
||||
if path is not None:
|
||||
try:
|
||||
for s in _SERIAL_RE.findall(Path(path).read_bytes()):
|
||||
s = s.decode()
|
||||
if s[2:].lstrip("0") == str(num):
|
||||
return s
|
||||
except Exception:
|
||||
pass
|
||||
return f"BE{num}" # last-resort fallback; prefix unverified
|
||||
|
||||
|
||||
def stem_time(name: str):
|
||||
@@ -141,7 +160,7 @@ def scan(path_str: str):
|
||||
for ch, st in stats.items():
|
||||
others = [stats[o]["p5"] for o in stats if o != ch]
|
||||
rows.append({
|
||||
"serial": serial_of(p.name),
|
||||
"serial": serial_of(p.name, p),
|
||||
"timestamp": stamp,
|
||||
"filename": p.name,
|
||||
"channel": ch,
|
||||
|
||||
+26
-4
@@ -28,9 +28,31 @@ from minimateplus.event_file_io import read_blastware_file
|
||||
GEO=("Tran","Vert","Long"); K=10.0/32000.0
|
||||
_WAVE=re.compile(r"\.[A-Za-z0-9]{2}0[Ww]$"); _STEM=re.compile(r"^([B-Z])(\d{3})")
|
||||
|
||||
def serial_of(n):
|
||||
m=_STEM.match(n)
|
||||
return f"BE{(ord(m.group(1))-ord('B'))*1000+int(m.group(2))}" if m else "?"
|
||||
_SERIAL_RE = re.compile(rb"\b([A-Z]{2}\d{3,6})\b")
|
||||
|
||||
|
||||
def serial_of(name: str, path=None) -> str:
|
||||
"""Real serial for a BW file.
|
||||
|
||||
The filename encodes only the NUMBER: `<letter><3 digits>` where
|
||||
letter = chr(ord('B') + serial // 1000). The two-letter family prefix
|
||||
("BE", "BA", ...) is **not** in the filename, so it must be read out of
|
||||
the file body. Four units in the DL2 archive are BA, not BE — assuming
|
||||
"BE" mislabels BA9229, BA10060, BA10895 and BA15957.
|
||||
"""
|
||||
m = _STEM.match(name)
|
||||
if not m:
|
||||
return "?"
|
||||
num = (ord(m.group(1)) - ord("B")) * 1000 + int(m.group(2))
|
||||
if path is not None:
|
||||
try:
|
||||
for s in _SERIAL_RE.findall(Path(path).read_bytes()):
|
||||
s = s.decode()
|
||||
if s[2:].lstrip("0") == str(num):
|
||||
return s
|
||||
except Exception:
|
||||
pass
|
||||
return f"BE{num}" # last-resort fallback; prefix unverified
|
||||
|
||||
def scan(ps):
|
||||
p=Path(ps)
|
||||
@@ -48,7 +70,7 @@ def scan(ps):
|
||||
mid, end = a[t:2*t], a[2*t:]
|
||||
if not pre or not mid or not end: continue
|
||||
v=[statistics.median(x)*K for x in (pre,mid,end)]
|
||||
out.append({"serial":serial_of(p.name),"timestamp":stamp,
|
||||
out.append({"serial":serial_of(p.name, p),"timestamp":stamp,
|
||||
"filename":p.name,"channel":ch,
|
||||
"pretrig_n": pre_n or 0,
|
||||
"pre":round(v[0],4),"mid":round(v[1],4),"end":round(v[2],4),
|
||||
|
||||
Reference in New Issue
Block a user