Skip to content

Conversation

@MarkGodwin
Copy link
Contributor

@MarkGodwin MarkGodwin commented Dec 8, 2024

The N20 Plus has a cyclone vacuum base station for emptying the deebot.

This comes with some an additional resettable counter for an internal filter inside the base station, which I added as a new resettable Lifespan type.

I also found a way to invoke an emptying of the Deebot, as well as an event that gets sent out during the automated vacuum process, which would maybe be useful to have if creating an automation to warn when the bin has been sucked out 20 times or something.

I couldn't see any existing Deebots that had any base-station functionality implemented, so I tried adding some of the configuration to allow this.

I'm a bit unsure as to what the implications of adding to the Capability classes really is - I'm sort of coding a bit blind, but it worked in a test script. Happy to change it further if this wasn't right.

Summary by CodeRabbit

Release Notes

  • New Features

    • Introduced base station functionalities, including actions and events.
    • Added support for handling station state messages.
    • Enhanced device capabilities for the Deebot N20 Plus, including battery management and cleaning actions.
    • Expanded command handling to include StationAction for base station operations.
  • Bug Fixes

    • Enhanced error handling for device operations.
  • Tests

    • Expanded test coverage for new message types related to base station actions.
    • Added tests for the new device identifier and its capabilities.

These updates enhance the device's operational capabilities, allowing for more efficient management and interaction with base station features.

@coderabbitai
Copy link
Contributor

coderabbitai bot commented Dec 8, 2024

Walkthrough

The changes in this pull request involve the introduction of new classes and modifications to existing classes within the deebot_client module, specifically enhancing functionalities related to base station actions. New dataclasses CapabilityBaseStationAction and CapabilityBaseStation are added, along with the StationAction command for handling base station actions. Additionally, event handling is improved with new enumerations and classes, including BaseStationEvent and OnStationState, which manage the state and actions of the base station. A new file for the Deebot N20 Plus capabilities is also introduced.

Changes

File Change Summary
deebot_client/capabilities.py Added classes CapabilityBaseStationAction, CapabilityBaseStation, and field base_station.
deebot_client/commands/json/__init__.py Introduced StationAction and updated __all__ and _COMMANDS lists.
deebot_client/commands/json/station_action.py Added class StationAction for handling base station actions.
deebot_client/events/__init__.py Added BaseStationEvent, BaseStationAction, BaseStationStatus, and updated LifeSpan.
deebot_client/hardware/deebot/buom7k.py Introduced capabilities for the Deebot N20 Plus, including various functionalities and events.
deebot_client/messages/json/__init__.py Added OnStationState to __all__ and _MESSAGES lists.
deebot_client/messages/json/base_station.py Created OnStationState class for handling base station state messages.
tests/messages/test_get_messages.py Added test case for onStationState message type in test_get_messages function.
tests/hardware/test_init.py Added device identifier "buom7k" and updated expected commands for class "p95mgv".

Possibly related PRs

  • Refactor to have one Capabilities and a DeviceType #518: This PR modifies the Capabilities class in deebot_client/capabilities.py, which is directly related to the changes made in the main PR that also involves modifications to the Capabilities class by adding a new field for base_station.
  • Add Deebot N20 Pro Plus #608: This PR introduces a new device configuration that likely utilizes the CapabilityBaseStation class added in the main PR, as it defines capabilities for a robotic vacuum device, which may include base station functionalities.
  • adding Deebot N30 Omni support (zwkcqc) #622: This PR adds support for the Deebot N30 Omni, which may involve capabilities related to base station operations, aligning with the new classes introduced in the main PR.

Suggested labels

pr: new-feature, pr: refactor

Suggested reviewers

  • edenhaus

🐰 In the land of code where bunnies play,
New features hop in, brightening the day!
With base stations buzzing and actions galore,
Our Deebot's now smarter than ever before!
So let’s cheer for the changes, both big and small,
For a cleaner tomorrow, we’ll conquer it all! 🌟


Thank you for using CodeRabbit. We offer it for free to the OSS community and would appreciate your support in helping us grow. If you find it useful, would you consider giving us a shout-out on your favorite social media?

❤️ Share
🪧 Tips

Chat

There are 3 ways to chat with CodeRabbit:

  • Review comments: Directly reply to a review comment made by CodeRabbit. Example:
    • I pushed a fix in commit <commit_id>, please review it.
    • Generate unit testing code for this file.
    • Open a follow-up GitHub issue for this discussion.
  • Files and specific lines of code (under the "Files changed" tab): Tag @coderabbitai in a new review comment at the desired location with your query. Examples:
    • @coderabbitai generate unit testing code for this file.
    • @coderabbitai modularize this function.
  • PR comments: Tag @coderabbitai in a new PR comment to ask questions about the PR branch. For the best results, please provide a very specific query, as very limited context is provided in this mode. Examples:
    • @coderabbitai gather interesting stats about this repository and render them as a table. Additionally, render a pie chart showing the language distribution in the codebase.
    • @coderabbitai read src/utils.ts and generate unit testing code.
    • @coderabbitai read the files in the src/scheduler package and generate a class diagram using mermaid and a README in the markdown format.
    • @coderabbitai help me debug CodeRabbit configuration file.

Note: Be mindful of the bot's finite context window. It's strongly recommended to break down tasks such as reading entire modules into smaller chunks. For a focused discussion, use review comments to chat about specific files and their changes, instead of using the PR comments.

CodeRabbit Commands (Invoked using PR comments)

  • @coderabbitai pause to pause the reviews on a PR.
  • @coderabbitai resume to resume the paused reviews.
  • @coderabbitai review to trigger an incremental review. This is useful when automatic reviews are disabled for the repository.
  • @coderabbitai full review to do a full review from scratch and review all the files again.
  • @coderabbitai summary to regenerate the summary of the PR.
  • @coderabbitai resolve resolve all the CodeRabbit review comments.
  • @coderabbitai configuration to show the current CodeRabbit configuration for the repository.
  • @coderabbitai help to get help.

Other keywords and placeholders

  • Add @coderabbitai ignore anywhere in the PR description to prevent this PR from being reviewed.
  • Add @coderabbitai summary to generate the high-level summary at a specific location in the PR description.
  • Add @coderabbitai anywhere in the PR title to generate the title automatically.

CodeRabbit Configuration File (.coderabbit.yaml)

  • You can programmatically configure CodeRabbit by adding a .coderabbit.yaml file to the root of your repository.
  • Please see the configuration documentation for more information.
  • If your editor has YAML language server enabled, you can add the path at the top of this file to enable auto-completion and validation: # yaml-language-server: $schema=https://coderabbit.ai/integrations/schema.v2.json

Documentation and Community

  • Visit our Documentation for detailed information on how to use CodeRabbit.
  • Join our Discord Community to get help, request features, and share feedback.
  • Follow us on X/Twitter for updates and announcements.

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

🧹 Outside diff range and nitpick comments (4)
deebot_client/commands/json/station_action.py (3)

5-5: Remove unused import Any from typing

The Any type is imported but not used in the code. Removing it will clean up the codebase by eliminating unnecessary imports.

Apply this diff to remove the unused import:

-from typing import TYPE_CHECKING, Any
+from typing import TYPE_CHECKING
🧰 Tools
🪛 Ruff (0.8.0)

5-5: typing.Any imported but unused

Remove unused import: typing.Any

(F401)


11-11: Remove unused import CODE from .const

The CODE constant is imported but not utilized in the file. It's best practice to remove unused imports to maintain code cleanliness.

Apply this diff to remove the unused import:

-from .const import CODE
🧰 Tools
🪛 Ruff (0.8.0)

11-11: .const.CODE imported but unused

Remove unused import: .const.CODE

(F401)


14-14: Remove unused import EventBus from deebot_client.event_bus

The EventBus class is imported for type checking but isn't used in this file. Eliminating unused imports reduces clutter.

Apply this diff to remove the unused import:

 if TYPE_CHECKING:
-    from deebot_client.event_bus import EventBus
🧰 Tools
🪛 Ruff (0.8.0)

14-14: deebot_client.event_bus.EventBus imported but unused

Remove unused import: deebot_client.event_bus.EventBus

(F401)

deebot_client/capabilities.py (1)

152-157: Consider adding validation for base station capabilities

The CapabilityBaseStation class might benefit from validation to ensure that the action capability is properly configured when events are enabled.

 @dataclass(frozen=True, kw_only=True)
 class CapabilityBaseStation:
     """Capabilities for base station."""
 
     action: CapabilityBaseStationAction
     event: CapabilityEvent[BaseStationEvent] | None = None
+
+    def __post_init__(self) -> None:
+        """Validate base station capabilities configuration."""
+        if self.event and not isinstance(self.action, CapabilityBaseStationAction):
+            raise ValueError("Base station event requires action capability")
📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

📥 Commits

Reviewing files that changed from the base of the PR and between e0fde3d and 85a3a28.

📒 Files selected for processing (8)
  • deebot_client/capabilities.py (3 hunks)
  • deebot_client/commands/json/__init__.py (3 hunks)
  • deebot_client/commands/json/station_action.py (1 hunks)
  • deebot_client/events/__init__.py (2 hunks)
  • deebot_client/hardware/deebot/buom7k.py (1 hunks)
  • deebot_client/messages/json/__init__.py (3 hunks)
  • deebot_client/messages/json/base_station.py (1 hunks)
  • tests/messages/test_get_messages.py (2 hunks)
🧰 Additional context used
🪛 Ruff (0.8.0)
deebot_client/commands/json/station_action.py

5-5: typing.Any imported but unused

Remove unused import: typing.Any

(F401)


11-11: .const.CODE imported but unused

Remove unused import: .const.CODE

(F401)


14-14: deebot_client.event_bus.EventBus imported but unused

Remove unused import: deebot_client.event_bus.EventBus

(F401)

🔇 Additional comments (12)
deebot_client/hardware/deebot/buom7k.py (2)

161-162: Verify compatibility of MultimapStateEvent with SetMultimapState

In the multi_state capability of the map section, ensure that the SetMultimapState command is compatible with the MultimapStateEvent. Verify that enabling or disabling multimap functionality works as intended on the device.


171-175: Confirm device support for CarpetAutoFanBoost settings

The carpet_auto_fan_boost setting is implemented using CapabilitySetEnable. Please confirm that the Deebot N20 Plus supports this feature and that the commands GetCarpetAutoFanBoost and SetCarpetAutoFanBoost function correctly.

deebot_client/messages/json/__init__.py (1)

10-10: Addition of OnStationState is consistent and correct

Including OnStationState in the imports, __all__, and _MESSAGES lists properly integrates the new message type into the message handling system, ensuring it will be recognized and processed appropriately.

Also applies to: 19-19, 28-29

tests/messages/test_get_messages.py (1)

10-10: Ensure the test case for onStationState is functioning correctly

Adding ("onStationState", DataType.JSON, OnStationState) to the test parameters extends coverage to the new message type. Verify that the test properly checks message retrieval for OnStationState.

Also applies to: 22-22

deebot_client/events/__init__.py (4)

144-144: LGTM: LifeSpan enum extension

The new BASE_STATION_FILTER value follows the existing naming pattern and uses a consistent string value format.


152-158: LGTM: BaseStationStatus enum

The status values are logically structured with UNKNOWN as -1, IDLE as 0, and EMPTYING as 1, following standard enum patterns.


160-164: LGTM: BaseStationEvent class

The event class follows the established pattern of other event classes in the module.


146-151: Consider adding more base station actions

The BaseStationAction enum currently only supports EMPTY_DUSTBIN. Consider if other actions like CLEAN_FILTER or SELF_CLEAN might be needed in the future.

deebot_client/capabilities.py (3)

14-15: LGTM: New imports

The imports are correctly ordered alphabetically and specifically import only the needed types.


146-151: LGTM: CapabilityBaseStationAction class

The class follows the established pattern of other capability classes and provides a clean interface for executing base station actions.


228-228: LGTM: Optional base station capability

The base_station field is correctly marked as optional with None as default, allowing for devices without base station support.

deebot_client/commands/json/__init__.py (1)

45-45: LGTM: Command registration

The StationAction command is properly registered in all required locations:

  • Import statement
  • all list
  • _COMMANDS list (maintaining alphabetical order)

Also applies to: 126-126, 231-233

Comment on lines 137 to 138
LifeSpan.BASE_STATION_FILTER
),
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

Ensure BASE_STATION_FILTER is defined in LifeSpan enumeration

The LifeSpan enumeration includes LifeSpan.BASE_STATION_FILTER, but it's crucial to confirm that BASE_STATION_FILTER is a valid member of the LifeSpan enum. If it's not defined, this will lead to an AttributeError at runtime.

Also applies to: 147-148

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: 0

🧹 Outside diff range and nitpick comments (3)
deebot_client/events/__init__.py (3)

34-34: Export new base station enums

While BaseStationEvent is correctly exported, consider adding BaseStationAction and BaseStationStatus to __all__ as they might be needed by external code working with base station functionality.

 __all__ = [
+    "BaseStationAction",
     "BaseStationEvent",
+    "BaseStationStatus",
     "BatteryEvent",

144-144: Consider aligning enum value with naming convention

The value "spHeap" for BASE_STATION_FILTER doesn't follow the snake_case pattern used by other enum values (e.g., "dust_bag", "cleaning_fluid"). Consider using "sp_heap" for consistency.


146-147: Remove extra blank line

The file consistently uses one blank line between definitions, but here there are two blank lines.

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

📥 Commits

Reviewing files that changed from the base of the PR and between 85a3a28 and dfa3c23.

📒 Files selected for processing (3)
  • deebot_client/commands/json/station_action.py (1 hunks)
  • deebot_client/events/__init__.py (2 hunks)
  • deebot_client/messages/json/__init__.py (3 hunks)
🚧 Files skipped from review as they are similar to previous changes (2)
  • deebot_client/messages/json/init.py
  • deebot_client/commands/json/station_action.py
🔇 Additional comments (3)
deebot_client/events/__init__.py (3)

147-151: LGTM!

The enum is well-structured with proper documentation and value assignment.


154-160: LGTM!

The enum provides a comprehensive set of states with logical value assignments.


163-167: LGTM!

The event class follows the established patterns and is properly documented.

@MarkGodwin
Copy link
Contributor Author

N20 Pro Plus was added recently - this should probably point here too, instead of to the N20.

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: 0

🧹 Outside diff range and nitpick comments (1)
tests/hardware/test_init.py (1)

Line range hint 92-190: Add test cases for buom7k in test_capabilities_event_extraction

The test_capabilities_event_extraction function does not currently include the new device buom7k. To ensure comprehensive test coverage, consider adding test cases for buom7k to validate its event-command mappings.

📜 Review details

Configuration used: CodeRabbit UI
Review profile: CHILL

📥 Commits

Reviewing files that changed from the base of the PR and between dfa3c23 and 5bf0afc.

📒 Files selected for processing (4)
  • deebot_client/capabilities.py (3 hunks)
  • deebot_client/hardware/deebot/buom7k.py (1 hunks)
  • deebot_client/messages/json/base_station.py (1 hunks)
  • tests/hardware/test_init.py (1 hunks)
🚧 Files skipped from review as they are similar to previous changes (1)
  • deebot_client/messages/json/base_station.py
🔇 Additional comments (7)
deebot_client/hardware/deebot/buom7k.py (2)

137-138: Ensure BASE_STATION_FILTER is defined in LifeSpan enumeration

The LifeSpan enumeration includes LifeSpan.BASE_STATION_FILTER, but it's crucial to confirm that BASE_STATION_FILTER is a valid member of the LifeSpan enum. If it's not defined, this will lead to an AttributeError at runtime.

Also applies to: 147-148


92-198: Capabilities for Deebot N20 Plus are correctly implemented

The device capabilities for the Deebot N20 Plus are well-defined and integrated into the DEVICES dictionary. The use of appropriate commands and events aligns with the existing architecture.

deebot_client/capabilities.py (4)

14-15: Imports for base station capabilities are correctly added

The new imports BaseStationAction and BaseStationEvent are properly included, ensuring that the base station functionalities can be utilized without naming conflicts.


147-153: Definition of CapabilityBaseStationAction is appropriate

The CapabilityBaseStationAction class is well-defined, encapsulating the command necessary for base station actions. The use of Callable[[BaseStationAction], Command] accurately represents the expected function signature.


154-160: Definition of CapabilityBaseStation is appropriate

The CapabilityBaseStation class correctly includes the action and optional event attributes to represent base station capabilities. This aligns with the structure of other capability classes.


231-231: Integration of base_station into Capabilities class

Adding base_station: CapabilityBaseStation | None = None to the Capabilities class appropriately extends the capabilities framework to include base station functionalities.

tests/hardware/test_init.py (1)

269-269: Device buom7k correctly added to model tests

The addition of "buom7k" to the list of device models ensures that the Deebot N20 Plus is included in the test suite, which is important for validating device initialization.

@MarkGodwin
Copy link
Contributor Author

Ah - Just found #603 . Some of my changes need to be updated to fit into the new station capability set that was added there. I can do that once #603 is merged.
I think the new auto-empty settings added there are probably valid for the N20 Plus too.

@edenhaus edenhaus added the pr: new-feature PR, which adds a new feature label Dec 10, 2024
@codecov
Copy link

codecov bot commented Dec 10, 2024

Codecov Report

Attention: Patch coverage is 96.82540% with 2 lines in your changes missing coverage. Please review.

Project coverage is 87.02%. Comparing base (4022545) to head (494a1ca).
Report is 1 commits behind head on dev.

✅ All tests successful. No failed tests found.

Files with missing lines Patch % Lines
deebot_client/messages/json/station_state.py 86.66% 1 Missing and 1 partial ⚠️
Additional details and impacted files
@@            Coverage Diff             @@
##              dev     #645      +/-   ##
==========================================
+ Coverage   86.87%   87.02%   +0.15%     
==========================================
  Files         101      105       +4     
  Lines        3679     3737      +58     
  Branches      318      320       +2     
==========================================
+ Hits         3196     3252      +56     
- Misses        426      427       +1     
- Partials       57       58       +1     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

Copy link
Member

@edenhaus edenhaus left a comment

Choose a reason for hiding this comment

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

Thanks @MarkGodwin 👍

I refactored the code a little bit and added tests for the new functionality

@edenhaus edenhaus changed the title Add Deebot N20 Plus with base station functions Add base station functions Dec 20, 2024
@edenhaus edenhaus merged commit 260db3f into DeebotUniverse:dev Dec 20, 2024
9 checks passed
@MarkGodwin
Copy link
Contributor Author

I tried out your new changes with my N20 Plus, it all looks good. Thanks!
We've lost the setting for the Base station filter lifecycle parameter ("spHeap") in the config. Is that because the HA integration needs to be updated first?

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

Labels

pr: new-feature PR, which adds a new feature

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants