Skip to content

fix: reduce battery drain from polling in embedded mode#6

Merged
KoheiYamashita merged 2 commits intomainfrom
fix/battery-drain-polling
Mar 1, 2026
Merged

fix: reduce battery drain from polling in embedded mode#6
KoheiYamashita merged 2 commits intomainfrom
fix/battery-drain-polling

Conversation

@KoheiYamashita
Copy link
Member

📝 Description

組み込み版(embedded)で2つのポーリング機構がCPUを常時起こし続け、バッテリー消費の原因になっていた問題を修正。

  1. ヘルスチェック停止: GatewayProcessManager.pollHealth()RUNNING 状態遷移後も500ms間隔でHTTPポーリングを継続していたのを、RUNNING 到達時点でコルーチンを終了するよう変更
  2. Cronサービスのタイマー化: 1秒間隔のティッカーを廃止し、time.Timer + getNextWakeMS() で次のジョブの実行時刻まで正確にスリープする方式に変更。ジョブ0件時はCPU消費ゼロで完全スリープ

🗣️ Type of Change

  • 🐞 Bug fix (non-breaking change which fixes an issue)

📚 Technical Context (Skip for Docs)

  • Reasoning: 組み込み版ではGoバックエンドがAndroidアプリのフォアグラウンドサービス内で動作するため、ポーリングによるCPU起床がDozeモードを妨げバッテリー消費に直結していた

ヘルスチェック (Android/Kotlin)

  • pollHealth()RUNNING 遷移後に return を追加し、コルーチンを自然終了
  • stopProcess() の既存キャンセル処理は完了済みJobに対してno-opなので安全

Cronサービス (Go)

  • rescheduleCh chan struct{} (バッファ1) を追加し、ジョブの追加/削除/変更時にタイマーを即座に再計算
  • nil チャネルの select ブロック特性を利用し、ジョブなし時は完全スリープ
  • AddJob, UpdateJob, RemoveJob, EnableJob, executeJobByID の全mutationメソッドに notifyReschedule() を追加

🧪 Test Environment & Hardware

  • Hardware: Android (arm64)
  • OS: Android 14
  • Test Results: go test ./pkg/cron/ -v -count=1 — 全29テスト PASS(既存27件 + 新規2件)

☑️ Checklist

  • My code/docs follow the style of this project.
  • I have performed a self-review of my own changes.
  • I have updated the documentation accordingly.

🤖 Generated with Claude Code

Stop health check polling after backend reaches RUNNING state, and
replace cron service's 1-second ticker with timer-based scheduling
that sleeps until the next job is due.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@gemini-code-assist
Copy link

Summary of Changes

Hello, I'm Gemini Code Assist1! I'm currently reviewing this pull request and will post my feedback shortly. In the meantime, here's a summary to help you and other reviewers quickly get up to speed!

組み込み環境、特にAndroidアプリのフォアグラウンドサービス内で動作するGoバックエンドにおいて、バッテリー消費の主要因となっていた2つのポーリング機構を最適化しました。これにより、CPUが不必要に起動し続けることを防ぎ、Dozeモードへの移行を妨げないことで、全体的なバッテリー寿命の改善に貢献します。

Highlights

  • ヘルスチェックの最適化: GatewayProcessManager.pollHealth() が RUNNING 状態に遷移した時点でHTTPポーリングを停止するように変更し、不要なCPU活動を削減しました。
  • Cronサービスの省電力化: 1秒間隔のティッカーを廃止し、time.Timer を使用して次のジョブ実行時刻まで正確にスリープする方式に移行しました。ジョブがない場合はCPU消費ゼロで完全にスリープします。

🧠 New Feature in Public Preview: You can now enable Memory to help Gemini Code Assist learn from your team's feedback. This makes future code reviews more consistent and personalized to your project's style. Click here to enable Memory in your admin console.

Changelog
  • android/backend/loader/src/main/java/io/clawdroid/backend/loader/GatewayProcessManager.kt
    • pollHealth() メソッド内で、バックエンドが RUNNING 状態に遷移した際にコルーチンを終了する return ステートメントを追加しました。
  • pkg/cron/service.go
    • CronService 構造体に rescheduleCh (チャネル) を追加しました。
    • Start() メソッドで rescheduleCh を初期化し、runLoop に渡すように変更しました。
    • Stop() メソッドで rescheduleCh を nil に設定するように変更しました。
    • runLoop 関数を大幅に改修し、1秒ティッカーを time.Timer に置き換え、getNextWakeMS() を利用して次のジョブ実行時刻までスリープするようにしました。また、rescheduleCh を監視してタイマーを再計算するロジックを追加しました。
    • notifyReschedule() ヘルパー関数を追加し、rescheduleCh にシグナルを送ることで runLoop にタイマーの再計算を促すようにしました。
    • executeJobByID, AddJob, UpdateJob, removeJobUnsafe, EnableJob の各メソッドでジョブの変更後に notifyReschedule() を呼び出すようにしました。
  • pkg/cron/service_test.go
    • タイマーベースの runLoop がジョブを正しく実行するかを検証する TestRunLoop_TimerBasedExecution テストを追加しました。
    • ジョブ追加時に runLoop がタイマーを再スケジュールするかを検証する TestRunLoop_RescheduleOnAddJob テストを追加しました。
Activity
  • このプルリクエストには、現時点ではコメントやレビュー活動は記録されていません。
Using Gemini Code Assist

The full guide for Gemini Code Assist can be found on our documentation page, here are some quick tips.

Invoking Gemini

You can request assistance from Gemini at any point by creating a comment using either /gemini <command> or @gemini-code-assist <command>. Below is a summary of the supported commands on the current page.

Feature Command Description
Code Review /gemini review Performs a code review for the current pull request in its current state.
Pull Request Summary /gemini summary Provides a summary of the current pull request in its current state.
Comment @gemini-code-assist Responds in comments when explicitly tagged, both in pull request comments and review comments.
Help /gemini help Displays a list of available commands.

Customization

To customize Gemini Code Assist for GitHub experience, repository maintainers can create a configuration file and/or provide a custom code review style guide (such as PEP-8 for Python) by creating and adding files to a .gemini/ folder in the base of the repository. Detailed instructions can be found here.

Limitations & Feedback

Gemini Code Assist may make mistakes. Please leave feedback on any instances where its feedback is incorrect or counter productive. You can react with 👍 and 👎 on @gemini-code-assist comments. If you're interested in giving your feedback about your experience with Gemini Code Assist for Github and other Google products, sign up here.

You can also get AI-powered code generation, chat, as well as code reviews directly in the IDE at no cost with the Gemini Code Assist IDE Extension.

Footnotes

  1. Review the Privacy Notices, Generative AI Prohibited Use Policy, Terms of Service, and learn how to configure Gemini Code Assist in GitHub here. Gemini can make mistakes, so double check it and use code with caution.

Copy link

@gemini-code-assist gemini-code-assist bot left a comment

Choose a reason for hiding this comment

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

Code Review

このプルリクエストは、ポーリングに起因するバッテリー消費を削減するための重要な修正です。Kotlin側のヘルスチェックの停止と、Go側のcronサービスをタイマーベースの実行に切り替える変更は、どちらも適切に実装されています。特に、GoのrunLoopにおけるtime.Timernilチャネルを組み合わせた省電力化の実装は、効率的でGoの言語特性をうまく活かしています。また、関連するテストケースが追加されている点も素晴らしいです。全体として、コードの品質は高く、問題は見つかりませんでした。

Add SIGTERM handling to Go gateway so proc.destroy() triggers graceful
shutdown and immediate port release. Add Mutex to GatewayProcessManager
to prevent concurrent start/stop races between watchdog and settings
observer. Add port release polling after process termination. Catch
InterruptedIOException in log forwarding to prevent crash on shutdown.
Defer settingsStore.update() until after setup complete API returns to
avoid killing the gateway mid-request.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
@KoheiYamashita KoheiYamashita merged commit 59953e0 into main Mar 1, 2026
16 checks passed
@KoheiYamashita KoheiYamashita deleted the fix/battery-drain-polling branch March 1, 2026 13:38
KoheiYamashita added a commit that referenced this pull request Mar 8, 2026
- Merge duplicate parameter descriptions in buildParameters (#1)
- Use map for DisabledActions lookup in isActionEnabled (#2)
- Add URL scheme whitelist (http/https only) for open_url (#3)
- Escape SQL LIKE wildcards in ContactsActionHandler (#4)
- Fix JSON tag inconsistency: web_actions -> web (#5)
- Add comprehensive tests for android tool (#6)

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
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