Skip to content

Add support for API interactions used to start and maintain a camera live stream - #28

Open
DavidValeri wants to merge 1 commit into
jhansche:mainfrom
DavidValeri:Add-support-for-livestream
Open

Add support for API interactions used to start and maintain a camera live stream#28
DavidValeri wants to merge 1 commit into
jhansche:mainfrom
DavidValeri:Add-support-for-livestream

Conversation

@DavidValeri

@DavidValeri DavidValeri commented Feb 3, 2025

Copy link
Copy Markdown

Introduces the methods mapping to the API interactions for initiating a stream, checking on the stream initiation status, and maintaining the stream in an active state.

Here is a use case in action https://github.com/DavidValeri/bb-streamer. The output can be fed to an NVR or another identification system.

Comment thread birdbuddy/client.py

LOGGER.debug(result)

while (result["__typename"] == "WatchingStartInProgressResult"):

Copy link
Copy Markdown
Author

Choose a reason for hiding this comment

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

This should probably include an optional timeout on this waiting loop.

@jhansche

Copy link
Copy Markdown
Owner

I initially did not go down the path of adding live streaming to the integration, because while the camera is in live streaming mode, it cannot detect bird visitors.

That said, I'm less opposed to adding support for this into the pybirdbuddy library itself (more opposed in the HA integration, because it restricts the primary purpose and intention of the BB).

@Erreon

Erreon commented Feb 21, 2026

Copy link
Copy Markdown

Code review

Found 2 issues:

  1. watching_start and watching_start_check declare feeder: Feeder but the method bodies handle the case where feeder is a plain string (else: feeder_id = feeder). Every other analogous method in the file uses feeder: Feeder | str (e.g., toggle_off_grid, toggle_audio_enabled, set_power_profile, update_firmware_start). The type annotation should be Feeder | str to match the implementation.

async def watching_start(self, feeder: Feeder) -> dict:
if isinstance(feeder, Feeder):

async def watching_start_check(self, feeder: Feeder) -> dict:
if isinstance(feeder, Feeder):

Compare with the existing pattern:

async def toggle_off_grid(
self,
feeder: Feeder | str,
is_off_grid: bool,

  1. The variables dict in both watching_start and watching_start_check includes a top-level "feederId" key, but neither the WATCHING_START nor WATCHING_START_CHECK GraphQL mutations declare a $feederId parameter -- they only declare $startWatchingInput: StartWatchingInput!. The extra undeclared variable is inconsistent with every other method in the file, where variables exactly match the mutation signature. Strict GraphQL servers will reject undeclared variables.

variables = {
"feederId": feeder_id,
"startWatchingInput": {
"feederId": feeder_id,
},
}

Mutation signature showing only $startWatchingInput is declared:

WATCHING_START = """
mutation watchingStartV2($startWatchingInput: StartWatchingInput!) {
watchingStartV2(startWatchingInput: $startWatchingInput) {

🤖 Generated with Claude Code

- If this code review was useful, please react with 👍. Otherwise, react with 👎.

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.

3 participants