Skip to content

feat: Stringy v1.0 -- pipeline architecture, CLI hardening, and comprehensive testing - #141

Merged
mergify[bot] merged 72 commits into
mainfrom
finish_epic_v1
Mar 11, 2026
Merged

mergify[bot] merged 72 commits into
mainfrom
finish_epic_v1

Conversation

@unclesp1d3r

@unclesp1d3r unclesp1d3r commented Mar 10, 2026 •

Copy link
Copy Markdown
Member

Summary

This PR delivers the complete v1.0 implementation of Stringy, transforming it from a prototype into a production-ready binary string extraction tool. The work spans 56 commits across 132 files (+7,963 / -6,477 lines), organized into five major workstreams.

610 tests pass (23 platform-skipped), zero clippy warnings, all pre-commit hooks green.

What Changed

1. Pipeline Architecture (New)

Introduced a modular pipeline orchestrator that replaces ad-hoc extraction logic:

  • Pipeline::new(config).run(&path) -- single entry point for all analysis
  • PipelineConfig with builder pattern for extraction, filtering, output, and debug options
  • FilterEngine for tag inclusion/exclusion, encoding, min-length, and top-N filtering
  • Score normalizer with 0-100 display scores and section weight / semantic boost / noise penalty breakdown
  • mmap-guard integration for safe memory-mapped file I/O (replaces raw memmap2)
  • Graceful fallback for unknown formats (raw byte scanning with Info diagnostic)
  • Processing warnings via env-var injection for testable error paths

Key files: src/pipeline/mod.rs, src/pipeline/config.rs, src/pipeline/filter.rs, src/pipeline/normalizer.rs

2. CLI Hardening

Complete rewrite of the CLI layer with production-quality UX:

  • Typed exit codes: 0=success, 2=config/validation, 3=not-found, 4=permission-denied, 1=other
  • Short flags: -j (json), -m (min-len), -t (top), -e (enc)
  • Actionable error messages with fix suggestions
  • NO_COLOR env var support (no-color.org spec)
  • Graceful spinner fallback (no .expect(), hidden when non-TTY or NO_COLOR)
  • stdin support via patharg::InputArg with progress feedback
  • --notags renamed to --no-tags (kebab-case consistency)
  • --summary, --debug, --raw modes with proper conflict declarations
  • Help text with EXAMPLES section and all 21 tag names listed

Key files: src/main.rs, src/types/error.rs

3. Core Data Model Improvements

  • FoundString::new() + builder methods replace struct literals (forward-compatible)
  • StringContext constructors for cleaner extraction code
  • SectionInfo made #[non_exhaustive] with with_* builders
  • OutputMetadata with analysis duration, top tag distribution, builder pattern
  • FilterContext with builder methods for test ergonomics
  • ExtractionConfig::with_min_length() builder
  • Container parsers split into module directories (elf/, pe/, macho/) with separate test files

Key files: src/types/constructors.rs, src/types/found_string.rs, src/types/mod.rs

4. Output Enhancements

  • Plain text: Full C0 control character sanitization (not just newlines)
  • TTY table: Analysis duration with minute-level formatting, summary banner
  • JSON: Debug-only fields (section_weight, semantic_boost, noise_penalty) via skip_serializing_if
  • YARA: Long string skip behavior with deterministic comments
  • display_score always present in non-raw mode; forced to 0 in raw mode

Key files: src/output/table/plain.rs, src/output/table/tty.rs, src/output/json.rs

5. Build & Infrastructure

  • Zig cross-compilation replaces Docker for test fixtures (ELF, PE, Mach-O)
  • Release profile optimization: strip = true, codegen-units = 1, lto = "thin" (release) / "fat" (dist)
  • mmap-guard dependency for safe memory-mapped I/O
  • cargo-dist version bump to 0.31.0
  • GOTCHAS.md added as living documentation for edge cases
  • CI workflow updates (action versions, scorecard)

Test Plan

  • 610 tests pass across 25 test files (597 previously + 13 new short-flag tests)
  • cargo clippy --all-targets -- -D warnings clean
  • cargo fmt --check clean
  • All pre-commit hooks pass (fmt, clippy, cargo-check, mdformat, cargo-audit)
  • Integration test coverage for all CLI flags, exit codes, and conflict combinations
  • Score determinism verified across consecutive runs
  • Warning emission tested via debug-build env var injection
  • Unknown/empty binary fallback paths tested
  • Short flag equivalence verified (-j = --json, -m = --min-len, etc.)
  • NO_COLOR env var tested
  • stdin pipe tested with ELF binary and empty input
  • Permission denied exit code 4 tested (Unix)

New Test Files in This PR

File Tests Coverage Area
integration_flows_1_5.rs 16 Quick analysis, filtering, top-N, JSON, YARA
integration_flows_6_7.rs 11 Plain text output, summary mode
integration_flow8_errors.rs 11 Argument conflicts, validation failures
integration_flow8_diagnostics.rs 13 Warnings, fallback, score determinism, debug
integration_cli_errors.rs 10 Exit codes, error messages
integration_cli_coverage.rs 18 Encoding, stdin, combined filters, permissions
integration_cli_short_flags.rs 13 Short flags, NO_COLOR, OR logic, edge cases
integration_flow1_minlen.rs 2 Min-length default and explicit filter
integration_flows_5_yara.rs 1 YARA long string deterministic skip

Breaking Changes

  • --notags renamed to --no-tags (CLI flag)
  • FoundString struct fields are no longer public for direct construction (use FoundString::new() + builders)
  • SectionInfo is #[non_exhaustive] (external crate consumers must use constructors)
  • Exit codes changed: file-not-found is now 3 (was 1), permission-denied is now 4 (was 1)

Risk Assessment

Risk Level: Medium

Factor Assessment
Size Large (132 files), but most changes are additive
Breaking changes CLI flag rename + exit code changes -- documented above
Test coverage Strong -- 610 tests covering all new paths
Dependencies +mmap-guard (thin wrapper), +patharg (stdin handling)
Security #![forbid(unsafe_code)] maintained, no new unsafe

Reviewer Notes

  • The pipeline module (src/pipeline/) is entirely new -- start review there
  • Container parser splits (elf.rs -> elf/mod.rs + elf/tests.rs) are mechanical moves with no logic changes
  • Documentation changes are extensive but mostly rewrites for accuracy
  • GOTCHAS.md is a new file worth reading for context on edge cases

Generated with Claude Code

unclesp1d3r and others added 30 commits March 7, 2026 16:57
- Deleted the `concept.md` file which outlined the Stringy tool's principles, architecture, and features.
- Removed the `2026-02-16-extraction-refactor-and-cli.md` plan detailing the refactor of the extraction module and CLI integration tasks.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…stency

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…ction functions

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
… documentation

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…rors

- Add assert_cmd + predicates for declarative CLI integration tests
- Add patharg for idiomatic file/stdin input (supports "-" for stdin)
- Rewrite and expand CLI tests from 4 to 18 covering help, version,
  validation, format conflicts, tag filters, and multi-format binaries
- Enrich UnsupportedFormat error to list supported formats (ELF, PE, Mach-O)
- Include file path context in I/O error messages
- Add author, long_about, and usage examples to --help output

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Add exit code verification tests (code 2 for clap errors, code 1 for
runtime errors). Add SerializationError variant to StringyError and
migrate JSON serialization errors from ConfigError to the new variant
for more precise error categorization.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…action and filtering

- Added `pipeline` module with configuration, filtering, and normalization functionalities.
- Implemented `Pipeline` struct to orchestrate the entire string extraction process.
- Created `FilterEngine` to apply post-extraction filters based on length, encoding, and tags.
- Added `ScoreNormalizer` to normalize internal scores for user-friendly display.
- Enhanced CLI to support new filtering options and output formats.
- Updated output metadata to include binary format and summary options.
- Refactored extraction and output logic to integrate with the new pipeline structure.
- Added tests for new features and ensured existing functionality remains intact.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
… for common pitfalls

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Replace std::fs::read() with mmap_guard::map_file() for zero-copy
read-only access with advisory locking. Empty files are short-circuited
to an empty buffer to preserve graceful pipeline behavior.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…troubleshooting

- Updated quick start guide to reflect current and planned features, improved output examples, and clarified usage instructions.
- Revised ranking algorithm documentation to simplify scoring formula, enhance section weight descriptions, and clarify semantic boosts and noise penalties.
- Streamlined troubleshooting section by removing outdated solutions, clarifying error messages, and improving performance issue guidance.
- Enhanced consistency in command examples and output formatting across all documentation sections.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Replace bare '|' assertion with ' | ' table separator check to avoid
false positives from legitimate strings containing pipe characters.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Replace all Docker-based build instructions with Zig cross-compilation
commands. Update AGENTS.md and GOTCHAS.md to reflect the new toolchain.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Add -v flag to zig cc and /v flag to zig rc so gen-fixtures shows
linker invocations instead of running silently.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Compiled fixtures (ELF, PE, Mach-O) were already in .gitignore but
still tracked. Remove them from the index so gitignore takes effect.
Add test_empty.bin and test_unknown.bin as committed static fixtures.

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…alysis duration

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…warnings

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…ntent

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…p examples

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…ess and content details

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
…mbol extraction test

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Copilot AI review requested due to automatic review settings March 11, 2026 07:48
@mergify

mergify Bot commented Mar 11, 2026

Copy link
Copy Markdown
Contributor

⚠️ The sha of the head commit of this PR conflicts with #140. Mergify cannot evaluate rules on this PR. Once #140 is merged or closed, Mergify will resume processing this PR. ⚠️

@unclesp1d3r unclesp1d3r linked an issue Mar 11, 2026 that may be closed by this pull request
10 tasks

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 115 out of 124 changed files in this pull request and generated 5 comments.

Comment thread README.md

Basic functionality is implemented with the full interface in development:
# Exclude noisy tags
stringy --no-tags format_string target_binary

Copilot AI Mar 11, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The README example uses --no-tags format_string, but Tag::from_str only accepts fmt for format strings (and serde renames the variant to "fmt"). Update the example to a supported tag value so users can copy/paste it successfully.

Suggested change
stringy --no-tags format_string target_binary
stringy --no-tags fmt target_binary

Copilot uses AI. Check for mistakes.
Comment thread README.md
@@ -142,10 +143,12 @@ Score Offset Section Tags String
"encoding": "utf-8",

Copilot AI Mar 11, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The JSON output example shows "encoding": "utf-8", but Encoding derives Serialize without serde(rename), so it serializes as "Utf8" (and similarly "Ascii", "Utf16Le", etc.). Please update the README example to match the actual JSON schema.

Suggested change
"encoding": "utf-8",
"encoding": "Utf8",

Copilot uses AI. Check for mistakes.
Comment on lines +111 to +112
// NOTE: --summary non-TTY exit 1 is covered in integration_flows_6_7.rs
// (flow7_summary_non_tty_exit_1).

Copilot AI Mar 11, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This comment says the non-TTY --summary path exits 1 and references flow7_summary_non_tty_exit_1, but the actual test is flow7_summary_non_tty_exit_2 (validation error -> exit code 2). Update the comment to reflect the current contract to avoid confusion when maintaining the flow matrix.

Copilot uses AI. Check for mistakes.
Comment thread src/types/found_string.rs
Comment on lines +110 to +113
/// Sets the display score (debug mode)
#[must_use]
pub fn with_display_score(mut self, score: i32) -> Self {
self.display_score = Some(score);

Copilot AI Mar 11, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

with_display_score is documented as "(debug mode)", but display_score is also used in normal (non-raw) output after score normalization (e.g., TTY table prefers display_score). Please update the doc comment to avoid implying it is debug-only.

Copilot uses AI. Check for mistakes.
Comment thread README.md
# Output formats
stringy --json target_binary
stringy --yara target_binary
stringy --json target_binary | jq '.[] | select(.tags[] | contains("Url"))'

Copilot AI Mar 11, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The README pipes --json output into jq '.[] | ...', but stringy --json emits JSONL (one JSON object per line), not a JSON array. Update the example to a JSONL-compatible jq invocation (e.g., processing input line-by-line) so it works as written.

Suggested change
stringy --json target_binary | jq '.[] | select(.tags[] | contains("Url"))'
stringy --json target_binary | jq 'select(.tags[]? | contains("Url"))'

Copilot uses AI. Check for mistakes.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (5)
tests/integration_pe.rs (5)

554-556: ⚠️ Potential issue | 🟡 Minor

Another tautology: is_empty() || !is_empty() is always true.

The comment indicates the intent is to verify no panic occurs. If that's the goal, remove the assertion entirely - the test passing without panic is sufficient.

Proposed fix
     let strings = stringy::extraction::extract_resource_strings(&pe_data);
-    // Should return empty Vec without panicking
-    assert!(strings.is_empty() || !strings.is_empty()); // Either is fine, just no panic
+    // Should return without panicking - either empty or populated Vec is acceptable
+    let _ = strings; // Silence unused warning; test passes if no panic
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/integration_pe.rs` around lines 554 - 556, The assertion
assert!(strings.is_empty() || !strings.is_empty()) is a tautology and should be
removed; simply call stringy::extraction::extract_resource_strings(&pe_data) and
either drop or bind the result (e.g., let _ = strings;) so the test verifies "no
panic" by completing without assertions—update the test around the variable
strings (from extract_resource_strings) accordingly.

121-124: ⚠️ Potential issue | 🟡 Minor

Tautological assertion provides no value.

is_some() || is_none() is always true for an Option. This assertion cannot fail and doesn't verify anything meaningful. Either remove it or assert something specific about the expected state.

Proposed fix
-        // Verify resources field exists (may be None for simple binaries)
-        assert!(
-            container_info.resources.is_some() || container_info.resources.is_none(),
-            "Resources field should exist in ContainerInfo"
-        );
+        // Resources may be None for simple binaries - no assertion needed,
+        // the type system guarantees the field exists.
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/integration_pe.rs` around lines 121 - 124, The assertion uses a
tautology (container_info.resources.is_some() ||
container_info.resources.is_none()) which can never fail; replace or remove it.
Update the test in integration_pe.rs to assert a concrete expectation about
ContainerInfo::resources (for example,
assert!(container_info.resources.is_some(), "expected resources to be present")
or assert_eq!(container_info.resources, None) as appropriate) or remove the
assertion entirely if no specific state is required; reference the
container_info variable and its resources field when making the meaningful
assertion.

138-146: 🧹 Nitpick | 🔵 Trivial

Inconsistent fixture-missing behavior across tests.

Tests like test_pe_resource_enumeration and test_pe_resource_strings_empty_binary silently return early when fixtures are missing, while others (e.g., test_pe_resource_extraction_with_resources) assert fixture presence with detailed build instructions.

Silent returns mask CI misconfigurations. Prefer consistent behavior: either all tests assert fixture presence, or use #[ignore] with a reason for optional fixtures.

Also applies to: 546-551

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/integration_pe.rs` around lines 138 - 146, The test currently swallows
a missing PE fixture by printing and returning early (the match on
fs::read(&fixture_path) in tests/integration_pe.rs), causing inconsistent
behavior across tests; update this test (and the other early-return cases such
as in test_pe_resource_enumeration and test_pe_resource_strings_empty_binary) to
assert fixture presence instead of silently returning: replace the Err branch
with an assert!(false, "...") or panic! containing the same detailed message and
build instructions used by test_pe_resource_extraction_with_resources, or
alternatively mark the test with #[ignore = "..."] if the fixture is
optional—apply the same change consistently to the other affected blocks (lines
around the second occurrence) so all tests behave uniformly.

187-190: ⚠️ Potential issue | 🟡 Minor

Same tautological assertion pattern here.

Identical issue as line 121-124. Option<T> is always either Some or None by definition.

Proposed fix
-    // Verify the structure is correct even if empty
-    assert!(
-        container_info.resources.is_some() || container_info.resources.is_none(),
-        "Resources field should exist in ContainerInfo"
-    );
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/integration_pe.rs` around lines 187 - 190, The current assertion checks
a tautology on the Option type (container_info.resources.is_some() ||
container_info.resources.is_none()), which always succeeds; replace it with a
meaningful check: either assert that resources is present when the test expects
it (use container_info.resources.is_some()) or remove the assertion if absence
is acceptable — reference container_info.resources and the ContainerInfo test
expectation to make the correct choice and update the assert message
accordingly.

1-557: 🧹 Nitpick | 🔵 Trivial

File exceeds 500-line limit (557 lines).

Per coding guidelines, files should stay under 500 lines. Consider splitting into focused modules:

  • integration_pe_parsing.rs (detection, section classification, imports/exports)
  • integration_pe_resources.rs (resource enumeration, VERSIONINFO, STRINGTABLE extraction)

This also improves test isolation and parallel execution.

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@tests/integration_pe.rs` around lines 1 - 557, The file is over the 500-line
limit—split tests into two focused integration files: move
detection/section/imports/exports/symbol snapshot tests (functions
test_pe_import_export_extraction, test_pe_section_classification,
test_pe_symbol_extraction_snapshot) into a new tests/integration_pe_parsing.rs
and move resource-related tests (test_pe_resource_enumeration,
test_pe_resource_extraction_with_resources,
test_pe_version_info_string_extraction, test_pe_string_table_extraction,
test_pe_resource_string_extraction_snapshot,
test_pe_resource_strings_empty_binary) into tests/integration_pe_resources.rs;
duplicate or extract the shared helper get_fixture_path and necessary use/import
lines into both files (or create a small tests/common util and duplicate if
simpler), delete the oversized tests/integration_pe.rs, and run cargo test to
ensure names (PeParser, stringy::extraction::extract_resource_strings, and the
test function names) still compile and tests run in parallel.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.

Outside diff comments:
In `@tests/integration_pe.rs`:
- Around line 554-556: The assertion assert!(strings.is_empty() ||
!strings.is_empty()) is a tautology and should be removed; simply call
stringy::extraction::extract_resource_strings(&pe_data) and either drop or bind
the result (e.g., let _ = strings;) so the test verifies "no panic" by
completing without assertions—update the test around the variable strings (from
extract_resource_strings) accordingly.
- Around line 121-124: The assertion uses a tautology
(container_info.resources.is_some() || container_info.resources.is_none()) which
can never fail; replace or remove it. Update the test in integration_pe.rs to
assert a concrete expectation about ContainerInfo::resources (for example,
assert!(container_info.resources.is_some(), "expected resources to be present")
or assert_eq!(container_info.resources, None) as appropriate) or remove the
assertion entirely if no specific state is required; reference the
container_info variable and its resources field when making the meaningful
assertion.
- Around line 138-146: The test currently swallows a missing PE fixture by
printing and returning early (the match on fs::read(&fixture_path) in
tests/integration_pe.rs), causing inconsistent behavior across tests; update
this test (and the other early-return cases such as in
test_pe_resource_enumeration and test_pe_resource_strings_empty_binary) to
assert fixture presence instead of silently returning: replace the Err branch
with an assert!(false, "...") or panic! containing the same detailed message and
build instructions used by test_pe_resource_extraction_with_resources, or
alternatively mark the test with #[ignore = "..."] if the fixture is
optional—apply the same change consistently to the other affected blocks (lines
around the second occurrence) so all tests behave uniformly.
- Around line 187-190: The current assertion checks a tautology on the Option
type (container_info.resources.is_some() || container_info.resources.is_none()),
which always succeeds; replace it with a meaningful check: either assert that
resources is present when the test expects it (use
container_info.resources.is_some()) or remove the assertion if absence is
acceptable — reference container_info.resources and the ContainerInfo test
expectation to make the correct choice and update the assert message
accordingly.
- Around line 1-557: The file is over the 500-line limit—split tests into two
focused integration files: move detection/section/imports/exports/symbol
snapshot tests (functions test_pe_import_export_extraction,
test_pe_section_classification, test_pe_symbol_extraction_snapshot) into a new
tests/integration_pe_parsing.rs and move resource-related tests
(test_pe_resource_enumeration, test_pe_resource_extraction_with_resources,
test_pe_version_info_string_extraction, test_pe_string_table_extraction,
test_pe_resource_string_extraction_snapshot,
test_pe_resource_strings_empty_binary) into tests/integration_pe_resources.rs;
duplicate or extract the shared helper get_fixture_path and necessary use/import
lines into both files (or create a small tests/common util and duplicate if
simpler), delete the oversized tests/integration_pe.rs, and run cargo test to
ensure names (PeParser, stringy::extraction::extract_resource_strings, and the
test function names) still compile and tests run in parallel.

ℹ️ Review info
⚙️ Run configuration

Configuration used: Path: .coderabbit.yml

Review profile: ASSERTIVE

Plan: Pro

Run ID: f9a14bd1-cd3a-4fc7-9b4c-210e194f34a0

📥 Commits

Reviewing files that changed from the base of the PR and between 5cab95a and 4787717.

⛔ Files ignored due to path filters (1)
  • tests/snapshots/integration_pe__pe_symbol_extraction.snap is excluded by !**/*.snap, !**/tests/snapshots/**
📒 Files selected for processing (2)
  • Cargo.toml
  • tests/integration_pe.rs

…talled

Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
Signed-off-by: UncleSp1d3r <unclesp1d3r@evilbitlabs.io>
@codecov

codecov Bot commented Mar 11, 2026

Copy link
Copy Markdown

@unclesp1d3r
unclesp1d3r enabled auto-merge (squash) March 11, 2026 08:14
@unclesp1d3r
unclesp1d3r disabled auto-merge March 11, 2026 08:14
@unclesp1d3r

Copy link
Copy Markdown
Member Author

@Mergifyio queue

@mergify

mergify Bot commented Mar 11, 2026 •

Copy link
Copy Markdown
Contributor

Merge Queue Status

This pull request spent 12 minutes in the queue, including 11 minutes 47 seconds running CI.

Required conditions to merge
  • check-success = coverage
  • check-success = msrv (stable minus 1 releases)
  • check-success = msrv (stable minus 2 releases)
  • check-success = msrv (stable minus 3 releases)
  • check-success = msrv (stable minus 4 releases)
  • check-success = msrv (stable)
  • check-success = quality
  • check-success = test
  • check-success = test-cross-platform (macos-latest, macOS)
  • check-success = test-cross-platform (ubuntu-latest, Linux)
  • check-success = test-cross-platform (windows-latest, Windows)
  • all of [🛡 Merge Protections rule CI must pass]:
    • check-success = coverage
    • check-success = msrv (stable minus 1 releases)
    • check-success = msrv (stable minus 2 releases)
    • check-success = msrv (stable minus 3 releases)
    • check-success = msrv (stable minus 4 releases)
    • check-success = msrv (stable)
    • check-success = quality
    • check-success = test
    • check-success = test-cross-platform (macos-latest, macOS)
    • check-success = test-cross-platform (ubuntu-latest, Linux)
    • check-success = test-cross-platform (windows-latest, Windows)
  • all of [🛡 Merge Protections rule Do not merge outdated PRs]:
  • all of [🛡 Merge Protections rule Enforce conventional commit]:
  • any of [🛡 GitHub repository ruleset rule main]:
    • check-neutral = Mergify Merge Protections
    • check-skipped = Mergify Merge Protections
    • check-success = Mergify Merge Protections

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

documentation Improvements or additions to documentation enhancement New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Create Classifier Trait and Classification Pipeline Architecture

2 participants