Back to Bouraq

Real optical transfer · no account required

Send this Python file from your screen to your phone.

An isolated test bench stops responding. This Python script turns its logs into an incident report with a timeline, anomaly detection and identifier redaction. Scan 18 QR codes across three pages of six to receive the verified 41.2 KB source file.

How are you trying it?

You need a computer screen and a phone. No account or installation.

  1. Open the scanner on your phone

    Scan this link QR with your phone’s usual camera, then open the link.

  2. Allow the phone camera

    On your phone, tap Start camera and allow access. Keep this page open on your computer.

  3. Play the three QR pages

    Start the transfer on your computer, then point your phone at all six codes. The three pages loop; every code only needs to be read once.

The original file
PYairgap_incident_report.py41,231 B
#!/usr/bin/env python3
"""The isolated test bench stopped at 02:17. Your colleague needs the evidence.

AIR-GAP INCIDENT REPORT: turn local logs into a brief you can carry through QR.
A useful example for OT engineers, lab teams and developers on restricted PCs.
No USB, network connection, package installation or equipment access required.

Try the SYNTHETIC acceptance-bench incident (no real plant or customer data):
    python airgap_incident_report.py --demo --output bench-brief
    # Open bench-brief/report.html locally. No web server is needed.
    # A crash, repeated PLC reconnects and rising temperature become a timeline.

For approved exports:
    python airgap_incident_report.py --input controller.csv \
        --input service.jsonl --output incident-brief

Required fields: timestamp, asset, event. Use --schema for supported values.
Timestamps require Z or an explicit UTC offset. Input: UTF-8 CSV or JSONL.
Output: escaped HTML, JSON summary, source and handoff SHA-256 manifests.
Identifiers are pseudonymised by default. Review free text before sharing;
redaction cannot recognise every secret. --keep-identifiers is local-use only.
Correlation is not causation. This is triage, not safety approval or control.
Python 3.10+; standard library only. The web demo transfers, never runs, this file.
"""
from __future__ import annotations

import argparse
import csv
import hashlib
import io
import ipaddress
import json
import math
import re
import statistics
import sys
from collections import Counter, defaultdict
from dataclasses import dataclass, field
from datetime import datetime, timedelta, timezone
from html import escape
Preview · first 40 lines
The live QR stream
18 QR · 3 × 6
Page 1 / 3Ready to send. Press Play, then scan with your phone.
Three pages. Six QR codes per page.

Set up your phone above, then start the transfer.

Three pages of six QR codes loop until you pause. Start at 6 seconds per page, or choose 2.5 or 4 seconds if your camera keeps up. Missing a page is fine: it comes around again.

Public sample only (41231 bytes). Camera images and file reconstruction stay in your browser. The Python source is displayed and downloaded, never executed. A Bouraq account is required to transfer your own files.