Repository navigation
2.1.0 - 2026-03-27
Release Notes
Now ~25% faster than the old C implementation of OrfM (v1.4). Cleaned up API, fixed multi-line FASTA bug.
Added
- Correctly handle wrapped (multi-line) FASTA sequences. Previously
raw_seq()was
used which includes embedded newlines, producing incorrect ORFs for wrapped input. - FASTQ validation: the first record is checked character-by-character for
valid IUPAC DNA/RNA characters; subsequent records detect invalid characters
via the translation table (a codon containing a non-IUPAC byte produces the
sentinel value0, triggering a panic with position and character details). flate2switched to thezlib-ngbackend for all gzip decompression
(needletail and the fastq crate), roughly halving wall-clock time on
gzipped inputs compared to the previousminiz_oxidedefault.Orf::orfm_id()method returns the ORF identifier
({source_seq_name}_{start}_{frame}_{orf_number}).Orf::name()method returns the full ORF name (orfm_id plus comment if present).
Fixed
revcom_basenow handles all IUPAC ambiguity codes (R, Y, S, W, K, M, B, D, H, V)
and RNA uracil (U). Previously these were all mapped to N, losing information in
reverse-strand transcripts.- Parse errors in FASTA/FASTQ input now produce an error message and exit instead of
silently truncating output. Previouslywhile let Some(Ok(...))in the iterators
andprocess_with_needletailwould treat anyErras end-of-file.
Changed
- FASTQ parsing switched from needletail to the
fastqcrate (zero-copy,
callback-based). Format is auto-detected by inspecting the first byte of input;
FASTA input continues to use needletail. - Aho-Corasick automaton is now case-insensitive, removing a per-sequence uppercase
copy allocation. - Newline detection is integrated into the Aho-Corasick scan itself:
raw_seq()is
used optimistically (zero-copy), and if a newline is encountered during the stop
codon search, the sequence is re-processed viaseq(). Once a newline is detected,
all subsequent records in the file useseq()directly. find_orfsis now the public single-sequence entry point and always returns
Vec<Orf>(normalizing wrapped input automatically). See thefind_orfsdocs
for the performance trade-off vs. the iterator API.Orf.seq_namerenamed toOrf.source_seq_namefor clarity. Theheader()method
has been replaced byorfm_id()andname().Orf.seq_nameandOrf.seq_commentchanged fromStringtoArc<str>, reducing
per-ORF heap allocations to a cheap atomic reference count increment.- Library iterators (
OrfFileIter,OrfReaderIter) no longer clone eachOrfon
iteration; they yield owned values directly viaIntoIter. - Library API cleaned up:
version_at_least,get_codon_table,revcom_base,
andis_valid_iupacare no longer public. - Benchmark data files moved to
benchmark/data/. - Benchmark summary now prints a box-drawing table with C vs Rust wall-clock
times and ratio (median of 3 replicates).
Removed
-r VERSIONflag andversion_at_leastfunction (dead code).Orf::header()method — useorfm_id()orname()instead.
Install orfm 2.1.0
Install prebuilt binaries via shell script
curl --proto '=https' --tlsv1.2 -LsSf https://github.com/wwood/OrfM/releases/download/2.1.0/orfm-installer.sh | shInstall prebuilt binaries via powershell script
powershell -ExecutionPolicy Bypass -c "irm https://github.com/wwood/OrfM/releases/download/2.1.0/orfm-installer.ps1 | iex"Download orfm 2.1.0
| File | Platform | Checksum |
|---|---|---|
| orfm-aarch64-apple-darwin.tar.xz | Apple Silicon macOS | checksum |
| orfm-x86_64-apple-darwin.tar.xz | Intel macOS | checksum |
| orfm-x86_64-pc-windows-msvc.zip | x64 Windows | checksum |
| orfm-aarch64-unknown-linux-gnu.tar.xz | ARM64 Linux | checksum |
| orfm-x86_64-unknown-linux-gnu.tar.xz | x64 Linux | checksum |
| orfm-x86_64-unknown-linux-musl.tar.xz | x64 MUSL Linux | checksum |