Skip to content

Conversation

Brendonovich
Copy link
Member

@Brendonovich Brendonovich commented Oct 9, 2025

Summary by CodeRabbit

  • New Features

    • None
  • Bug Fixes

    • None
  • Refactor

    • Unified in-progress recording state so Instant and Studio behave consistently when starting/stopping.
    • Consolidated shared recording metadata to simplify access to inputs and recording location.
    • Integrated camera and microphone feed locks for more reliable media capture and cleaner initialization.
  • Chores

    • Preparatory changes for maintainability and future recording improvements.

Copy link
Contributor

coderabbitai bot commented Oct 9, 2025

Pre-merge checks and finishing touches

❌ Failed checks (1 warning)
Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 42.86% which is insufficient. The required threshold is 80.00%. You can run @coderabbitai generate docstrings to improve docstring coverage.
✅ Passed checks (2 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title Check ✅ Passed The title accurately describes the primary change, which is to maintain camera and microphone locks throughout the recording lifecycle, and it is clear, concise, and directly tied to the modifications made in both the desktop app and recording crates.
✨ Finishing touches
  • 📝 Generate docstrings
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Post copyable unit tests in a comment
  • Commit unit tests in branch audio-recording-early-unlock

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between db748d0 and e2d442a.

📒 Files selected for processing (2)
  • apps/desktop/src-tauri/src/recording.rs (8 hunks)
  • crates/recording/src/instant_recording.rs (1 hunks)
🧰 Additional context used
📓 Path-based instructions (4)
crates/**/src/**/*.rs

📄 CodeRabbit inference engine (CLAUDE.md)

For desktop IPC, use tauri_specta derive/macros on Rust types/events; do not hand-roll bindings

Files:

  • crates/recording/src/instant_recording.rs
**/*.{ts,tsx,js,jsx,rs}

📄 CodeRabbit inference engine (CLAUDE.md)

Do not add inline, block, or docstring comments in any language; code must be self-explanatory

Files:

  • crates/recording/src/instant_recording.rs
  • apps/desktop/src-tauri/src/recording.rs
**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

**/*.rs: Format Rust code using rustfmt and ensure all Rust code passes workspace-level clippy lints.
Rust modules should be named with snake_case, and crate directories should be in kebab-case.

Files:

  • crates/recording/src/instant_recording.rs
  • apps/desktop/src-tauri/src/recording.rs
crates/*/src/**/*

📄 CodeRabbit inference engine (AGENTS.md)

Rust crates should place tests within the src/ and/or a sibling tests/ directory for each crate inside crates/*.

Files:

  • crates/recording/src/instant_recording.rs
🧬 Code graph analysis (1)
apps/desktop/src-tauri/src/recording.rs (2)
apps/desktop/src/utils/tauri.ts (2)
  • StartRecordingInputs (462-462)
  • VideoUploadInfo (481-481)
crates/recording/src/feeds/microphone.rs (8)
  • handle (245-365)
  • handle (371-383)
  • handle (389-391)
  • handle (397-417)
  • handle (433-467)
  • handle (473-485)
  • handle (491-507)
  • handle (513-526)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (4)
  • GitHub Check: Clippy
  • GitHub Check: Build Desktop (aarch64-apple-darwin, macos-latest)
  • GitHub Check: Build Desktop (x86_64-pc-windows-msvc, windows-latest)
  • GitHub Check: Analyze (rust)
🔇 Additional comments (4)
apps/desktop/src-tauri/src/recording.rs (4)

11-12: LGTM! Imports support the new lock-holding mechanism.

These imports are now required for the InProgressRecordingCommon struct fields (camera_feed and mic_feed), which hold the locks for the duration of the recording.


58-64: LGTM! InProgressRecordingCommon correctly holds locks throughout recording lifecycle.

This struct consolidates shared recording state and—critically—holds Arc<CameraFeedLock> and Arc<MicrophoneFeedLock> for the recording's lifetime. By storing these locks in the InProgressRecording enum (which lives in App state), they won't be dropped until the recording is stopped or cancelled, fulfilling the PR objective.


66-77: LGTM! Enum refactor properly integrates InProgressRecordingCommon.

Both Instant and Studio variants now include the common field, ensuring consistent lock-holding behavior across recording modes. The locks will be automatically dropped when stop() or cancel() consume self (lines 115-148).


454-460: LGTM! Lock construction ensures they're held until recording completion.

By constructing InProgressRecordingCommon with the acquired locks and embedding it in the InProgressRecording enum (lines 494, 534), the locks remain valid until the recording is cleared from App state. This prevents premature unlock signals to the feed actors.

RecordingBaseInputs,
capture_pipeline::{MakeCapturePipeline, ScreenCaptureMethod, Stop, create_screen_capture},
feeds::microphone::MicrophoneFeedLock,
feeds::{camera::CameraFeedLock, microphone::MicrophoneFeedLock},
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Unused import: CameraFeedLock is not referenced in this file.

CameraFeedLock is imported but never used. Instant recording doesn't currently support camera feeds (camera_feed is hardcoded to None at line 255 in RecordingBaseInputs), so this import is unnecessary.

Apply this diff to remove the unused import:

-    feeds::{camera::CameraFeedLock, microphone::MicrophoneFeedLock},
+    feeds::microphone::MicrophoneFeedLock,
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
feeds::{camera::CameraFeedLock, microphone::MicrophoneFeedLock},
feeds::microphone::MicrophoneFeedLock,
🤖 Prompt for AI Agents
In crates/recording/src/instant_recording.rs around line 4, the import
feeds::{camera::CameraFeedLock, microphone::MicrophoneFeedLock} includes
CameraFeedLock which is unused because instant recording hardcodes camera_feed
to None; remove CameraFeedLock from the use/import list so only
MicrophoneFeedLock is imported to eliminate the unused-import warning.

Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 1

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between e2d442a and 1f6b8cb.

📒 Files selected for processing (3)
  • apps/desktop/src-tauri/src/recording.rs (8 hunks)
  • crates/recording/src/sources/camera.rs (3 hunks)
  • crates/recording/src/sources/microphone.rs (2 hunks)
🧰 Additional context used
📓 Path-based instructions (4)
crates/**/src/**/*.rs

📄 CodeRabbit inference engine (CLAUDE.md)

For desktop IPC, use tauri_specta derive/macros on Rust types/events; do not hand-roll bindings

Files:

  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
**/*.{ts,tsx,js,jsx,rs}

📄 CodeRabbit inference engine (CLAUDE.md)

Do not add inline, block, or docstring comments in any language; code must be self-explanatory

Files:

  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
  • apps/desktop/src-tauri/src/recording.rs
**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

**/*.rs: Format Rust code using rustfmt and ensure all Rust code passes workspace-level clippy lints.
Rust modules should be named with snake_case, and crate directories should be in kebab-case.

Files:

  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
  • apps/desktop/src-tauri/src/recording.rs
crates/*/src/**/*

📄 CodeRabbit inference engine (AGENTS.md)

Rust crates should place tests within the src/ and/or a sibling tests/ directory for each crate inside crates/*.

Files:

  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
🧬 Code graph analysis (2)
crates/recording/src/sources/microphone.rs (2)
crates/recording/src/sources/camera.rs (1)
  • setup (17-39)
crates/recording/src/feeds/microphone.rs (1)
  • audio_info (173-175)
apps/desktop/src-tauri/src/recording.rs (2)
apps/desktop/src/utils/tauri.ts (1)
  • StartRecordingInputs (462-462)
crates/recording/src/feeds/microphone.rs (8)
  • handle (245-365)
  • handle (371-383)
  • handle (389-391)
  • handle (397-417)
  • handle (433-467)
  • handle (473-485)
  • handle (491-507)
  • handle (513-526)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: Build Desktop (x86_64-pc-windows-msvc, windows-latest)
  • GitHub Check: Build Desktop (aarch64-apple-darwin, macos-latest)
  • GitHub Check: Analyze (rust)
🔇 Additional comments (5)
crates/recording/src/sources/camera.rs (1)

17-39: LGTM! Clean parameter rename for consistency.

The parameter rename from config to feed_lock improves clarity and aligns with the parallel changes in microphone.rs. The implementation correctly passes the feed lock through to AddSender and stores it in the struct to ensure it's held for the source's lifetime.

crates/recording/src/sources/microphone.rs (1)

10-44: LGTM! Lock now held for recording lifetime.

The struct now stores both AudioInfo and Arc<MicrophoneFeedLock> (previously just AudioInfo). This ensures the microphone lock is held for the entire lifetime of the Microphone source, preventing premature unlock. When the struct is dropped, the lock will be automatically released via the oneshot channel mechanism shown in the relevant code snippet.

apps/desktop/src-tauri/src/recording.rs (3)

58-62: LGTM! Good refactoring to eliminate duplication.

The new InProgressRecordingCommon struct consolidates shared fields (target_name, inputs, recording_dir) across both Instant and Studio variants, reducing duplication and making the code more maintainable.


64-154: LGTM! Consistent refactoring across all accessors and completion paths.

All methods correctly access the shared fields via common, and the stop/completion logic properly extracts target_name from common.target_name. The refactoring maintains the same behavior while improving code organization.


452-533: LGTM! Lock management correctly integrated.

The recording start flow now properly acquires camera and microphone locks (lines 435-445), passes them to the respective builders, and stores them in the sources. This ensures locks are held for the entire recording lifetime and released when the recording completes/fails.

Comment on lines +11 to +12
use cap_recording::feeds::camera::CameraFeedLock;
use cap_recording::feeds::microphone::MicrophoneFeedLock;
Copy link
Contributor

Choose a reason for hiding this comment

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

🛠️ Refactor suggestion | 🟠 Major

🧩 Analysis chain

Verify that the imports are actually needed.

The imports for CameraFeedLock and MicrophoneFeedLock are not explicitly referenced by name in the code shown (types are inferred at lines 436 and 442). These might be unused imports unless they're needed elsewhere in the file.

Run the following script to check if these types are explicitly used:


🏁 Script executed:

#!/bin/bash
# Check if CameraFeedLock and MicrophoneFeedLock are explicitly referenced in recording.rs

echo "Checking for explicit references to CameraFeedLock..."
rg -n 'CameraFeedLock' apps/desktop/src-tauri/src/recording.rs | grep -v '^11:' || echo "No references found outside import"

echo ""
echo "Checking for explicit references to MicrophoneFeedLock..."
rg -n 'MicrophoneFeedLock' apps/desktop/src-tauri/src/recording.rs | grep -v '^12:' || echo "No references found outside import"

Length of output: 182


Remove unused imports of CameraFeedLock and MicrophoneFeedLock
Neither type is referenced anywhere in apps/desktop/src-tauri/src/recording.rs; these imports can be deleted.

🤖 Prompt for AI Agents
In apps/desktop/src-tauri/src/recording.rs around lines 11 to 12, the file
imports CameraFeedLock and MicrophoneFeedLock from cap_recording but never uses
them; remove the two unused use lines (use
cap_recording::feeds::camera::CameraFeedLock; and use
cap_recording::feeds::microphone::MicrophoneFeedLock;) to clean up unused
imports and avoid compiler warnings.

@Brendonovich Brendonovich merged commit 506b3ef into main Oct 9, 2025
14 of 15 checks passed
Copy link
Contributor

@coderabbitai coderabbitai bot left a comment

Choose a reason for hiding this comment

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

Actionable comments posted: 2

📜 Review details

Configuration used: CodeRabbit UI

Review profile: CHILL

Plan: Pro

📥 Commits

Reviewing files that changed from the base of the PR and between e2d442a and 7007c9c.

📒 Files selected for processing (3)
  • apps/desktop/src-tauri/src/recording.rs (8 hunks)
  • crates/recording/src/sources/camera.rs (3 hunks)
  • crates/recording/src/sources/microphone.rs (2 hunks)
🧰 Additional context used
📓 Path-based instructions (4)
**/*.{ts,tsx,js,jsx,rs}

📄 CodeRabbit inference engine (CLAUDE.md)

Do not add inline, block, or docstring comments in any language; code must be self-explanatory

Files:

  • apps/desktop/src-tauri/src/recording.rs
  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
**/*.rs

📄 CodeRabbit inference engine (AGENTS.md)

**/*.rs: Format Rust code using rustfmt and ensure all Rust code passes workspace-level clippy lints.
Rust modules should be named with snake_case, and crate directories should be in kebab-case.

Files:

  • apps/desktop/src-tauri/src/recording.rs
  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
crates/**/src/**/*.rs

📄 CodeRabbit inference engine (CLAUDE.md)

For desktop IPC, use tauri_specta derive/macros on Rust types/events; do not hand-roll bindings

Files:

  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
crates/*/src/**/*

📄 CodeRabbit inference engine (AGENTS.md)

Rust crates should place tests within the src/ and/or a sibling tests/ directory for each crate inside crates/*.

Files:

  • crates/recording/src/sources/camera.rs
  • crates/recording/src/sources/microphone.rs
🧬 Code graph analysis (2)
apps/desktop/src-tauri/src/recording.rs (2)
apps/desktop/src/utils/tauri.ts (1)
  • StartRecordingInputs (462-462)
crates/recording/src/feeds/microphone.rs (8)
  • handle (245-365)
  • handle (371-383)
  • handle (389-391)
  • handle (397-417)
  • handle (433-467)
  • handle (473-485)
  • handle (491-507)
  • handle (513-526)
crates/recording/src/sources/microphone.rs (2)
crates/recording/src/sources/camera.rs (1)
  • setup (17-39)
crates/recording/src/feeds/microphone.rs (1)
  • audio_info (173-175)
⏰ Context from checks skipped due to timeout of 90000ms. You can increase the timeout in your CodeRabbit configuration to a maximum of 15 minutes (900000ms). (3)
  • GitHub Check: Build Desktop (x86_64-pc-windows-msvc, windows-latest)
  • GitHub Check: Build Desktop (aarch64-apple-darwin, macos-latest)
  • GitHub Check: Analyze (rust)
🔇 Additional comments (9)
crates/recording/src/sources/camera.rs (1)

17-38: LGTM!

The parameter rename from config to feed_lock improves clarity and establishes consistency with the microphone source pattern.

crates/recording/src/sources/microphone.rs (3)

10-10: LGTM!

Adding Arc<MicrophoneFeedLock> as a second field correctly implements the PR objective of holding the microphone lock while recording is active.


16-27: LGTM!

The parameter rename and updated usage are correct and consistent with the camera source.


43-43: LGTM!

The constructor correctly returns both fields, keeping the feed lock alive for the duration of the Microphone instance.

apps/desktop/src-tauri/src/recording.rs (5)

58-62: LGTM!

The InProgressRecordingCommon struct effectively eliminates field duplication between the Instant and Studio variants.


75-75: LGTM!

The Studio variant correctly adopts the common payload pattern.


87-92: LGTM!

The accessor methods correctly delegate to the common field, maintaining consistent behavior across both variants.

Also applies to: 108-113


115-134: LGTM!

The stop() method correctly accesses common.target_name for both variants. The destructuring preserves all fields appropriately.


454-458: LGTM!

The construction and propagation of InProgressRecordingCommon is correct. The Instant variant properly holds camera_feed to maintain the lock for the recording duration, implementing the PR objective.

Also applies to: 492-492, 532-533

Comment on lines +69 to +71
common: InProgressRecordingCommon,
// camera isn't used as part of recording pipeline so we hold lock here
camera_feed: Option<Arc<CameraFeedLock>>,
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Remove the comment to comply with coding guidelines.

The inline comment violates the guideline: "Do not add inline, block, or docstring comments in any language; code must be self-explanatory."

Apply this diff:

     common: InProgressRecordingCommon,
-    // camera isn't used as part of recording pipeline so we hold lock here
     camera_feed: Option<Arc<CameraFeedLock>>,

As per coding guidelines

📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
common: InProgressRecordingCommon,
// camera isn't used as part of recording pipeline so we hold lock here
camera_feed: Option<Arc<CameraFeedLock>>,
common: InProgressRecordingCommon,
camera_feed: Option<Arc<CameraFeedLock>>,
🤖 Prompt for AI Agents
In apps/desktop/src-tauri/src/recording.rs around lines 69 to 71, remove the
inline comment "// camera isn't used as part of recording pipeline so we hold
lock here" so the code complies with the guideline forbidding
inline/block/docstring comments; leave the field definition and surrounding
formatting unchanged.

feed_lock
.ask(microphone::AddSender(tx))
.await
.map_err(|e| anyhow!("Failed to add camera sender: {e}"))?;
Copy link
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Fix error message to reference microphone instead of camera.

The error message mentions "camera sender" but this code is for the microphone source.

Apply this diff to fix the message:

-            .map_err(|e| anyhow!("Failed to add camera sender: {e}"))?;
+            .map_err(|e| anyhow!("Failed to add microphone sender: {e}"))?;
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
.map_err(|e| anyhow!("Failed to add camera sender: {e}"))?;
.map_err(|e| anyhow!("Failed to add microphone sender: {e}"))?;
🤖 Prompt for AI Agents
In crates/recording/src/sources/microphone.rs around line 30, the error message
incorrectly says "Failed to add camera sender"; update the string to reference
the microphone (e.g., "Failed to add microphone sender: {e}") so the error
context matches this source, keeping the same map_err usage and error
interpolation.

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

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant