Skip to content

feat: canister logs extensions#414

Draft
lwshang wants to merge 13 commits intomainfrom
lwshang/log-extensions
Draft

feat: canister logs extensions#414
lwshang wants to merge 13 commits intomainfrom
lwshang/log-extensions

Conversation

@lwshang
Copy link
Contributor

@lwshang lwshang commented Mar 6, 2026

Warning

icp-cli with this feature will not work with the current IC mainnet or any networks that haven't enabled the "Canister Logs Extensions" feature. Commands that call the management canister's canister_status method will fail because the new log_memory_limit field is missing from the response.

Summary

  • Update to ic-agent/ic-utils 0.46 and add reqwest features
  • Add --since, --until, --since-index, --until-index filter flags to icp canister logs
  • Support log_memory_limit canister setting in icp canister settings update, icp canister settings sync, and icp canister status

Test plan

  • cargo check passes
  • Unit tests pass (cargo test -p icp-cli --bin icp)
  • Integration test on a network with Canister Logs Extensions enabled

🤖 Generated with Claude Code

lwshang and others added 9 commits March 6, 2026 13:28
- Add `json` and `stream` features to reqwest (required for
  `.json()` and `.bytes_stream()` on responses in reqwest 0.12)
- Update snapshot management calls: canister_id is now embedded in
  the args structs, removing the separate &canister_id parameter
- Add new required fields to TakeCanisterSnapshotArgs
  (uninstall_code, sender_canister_version)
- Replace removed `with_optional_*` builder methods on
  UpdateSettingsBuilder with conditional `with_*` calls
- Add log filter support in canister logs command using new
  FetchCanisterLogsArgs and CanisterLogFilter from ic-utils 0.46

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
…--since-index

When only --until or --until-index is provided, default the start to 0
so users can filter logs up to a given point without specifying a start.
Also add missing conflicts_with for --follow on all filter flags.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add the log_memory_limit field to the Settings model, canister settings
update command, settings sync operation, and canister status display.

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
aws-lc-sys (OpenSSL licensed) was pulled in via:
aws-lc-sys -> aws-lc-rs -> rustls -> hyper-rustls -> reqwest -> ic-agent

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

Copilot AI left a comment

Choose a reason for hiding this comment

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

Pull request overview

Adds support for the Internet Computer “Canister Logs Extensions” feature across icp-cli, including new log filtering flags and the new log_memory_limit canister setting, alongside dependency upgrades needed for the updated management canister APIs.

Changes:

  • Upgrades ic-agent/ic-utils and adjusts call sites for updated management canister method signatures.
  • Extends icp canister logs with timestamp/index filtering (--since/--until/--since-index/--until-index) and follow-mode lookback behavior.
  • Adds log_memory_limit support to settings update/sync, schemas, and CLI reference docs.

Reviewed changes

Copilot reviewed 16 out of 17 changed files in this pull request and generated 2 comments.

Show a summary per file
File Description
docs/schemas/icp-yaml-schema.json Adds log_memory_limit to the ICP YAML schema.
docs/schemas/environment-yaml-schema.json Adds log_memory_limit to environment YAML schema.
docs/schemas/canister-yaml-schema.json Adds log_memory_limit to canister YAML schema and defaults.
docs/reference/cli.md Documents new canister logs filters and --log-memory-limit flag.
deny.toml Allows OpenSSL license for new/updated transitive deps.
crates/icp/src/canister/mod.rs Adds log_memory_limit to canister Settings.
crates/icp-cli/src/operations/snapshot_transfer.rs Updates snapshot transfer calls to new mgmt canister arg-based APIs.
crates/icp-cli/src/operations/settings.rs Syncs log_memory_limit and adapts update-settings builder usage.
crates/icp-cli/src/commands/canister/status.rs Displays log_memory_limit in status output.
crates/icp-cli/src/commands/canister/snapshot/create.rs Updates snapshot creation args/calls for new API fields/signatures.
crates/icp-cli/src/commands/canister/snapshot/restore.rs Updates restore call signature for new API.
crates/icp-cli/src/commands/canister/snapshot/delete.rs Updates delete call signature for new API.
crates/icp-cli/src/commands/canister/settings/update.rs Adds --log-memory-limit and wires it into settings updates.
crates/icp-cli/src/commands/canister/logs.rs Adds filtering flags, filter construction, timestamp parsing, and tests.
Cargo.toml Bumps IC crates and enables additional reqwest features.
Cargo.lock Locks updated dependency graph for new crate versions.
CHANGELOG.md Notes new logs filtering and log_memory_limit support.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

lwshang and others added 3 commits March 6, 2026 15:45
… logs

- Use unix_timestamp_nanos() instead of manual arithmetic in parse_timestamp
  to prevent silent overflow/wrapping for pre-epoch or far-future timestamps
- Validate that --since/--until and --since-index/--until-index ranges are
  not inverted, returning a clear error instead of empty or confusing results

Co-Authored-By: Claude Opus 4.6 <noreply@anthropic.com>
Add unit tests for build_filter and parse_timestamp edge cases, integration
tests for --since-index/--until-index and --since/--until filtering, unit
tests for log_memory_limit suffix parsing, and a comment explaining why
log_memory_limit is not covered in canister_settings_tests (PocketIC
does not yet support it).

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

Copilot AI left a comment

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 18 out of 19 changed files in this pull request and generated 3 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines +47 to +56
fn parse_timestamp(s: &str) -> Result<u64, String> {
// Try raw nanoseconds first
if let Ok(nanos) = s.parse::<u64>() {
return Ok(nanos);
}
// Fall back to RFC3339
let dt = OffsetDateTime::parse(s, &Rfc3339)
.map_err(|_| format!("'{s}' is not a valid nanosecond timestamp or RFC3339 datetime"))?;
let nanos = dt.unix_timestamp_nanos();
u64::try_from(nanos).map_err(|_| {
Copy link

Copilot AI Mar 7, 2026

Choose a reason for hiding this comment

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

parse_timestamp falls back to RFC3339 parsing on any u64 parse error, which means a purely numeric timestamp that overflows u64 will produce the generic “not a valid … or RFC3339” message rather than an explicit overflow error. Consider detecting numeric overflow first (e.g., parse as u128/i128 and check bounds) so users get a clearer error when they pass an out-of-range nanosecond value.

Copilot uses AI. Check for mistakes.
// First fetch: look back 1 hour from now
let now_nanos = std::time::SystemTime::now()
.duration_since(std::time::UNIX_EPOCH)
.map(|d| d.as_nanos() as u64)
Copy link

Copilot AI Mar 7, 2026

Choose a reason for hiding this comment

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

now_nanos is computed with d.as_nanos() as u64, which will silently truncate if the system clock is far enough in the future to exceed u64::MAX nanoseconds since epoch. Prefer a checked conversion (e.g., u64::try_from(...) with a clamp/fallback) to avoid producing an incorrect timestamp range when the local clock is misconfigured.

Suggested change
.map(|d| d.as_nanos() as u64)
.map(|d| u64::try_from(d.as_nanos()).unwrap_or(u64::MAX))

Copilot uses AI. Check for mistakes.
@@ -100,7 +100,7 @@ zeroize = "1.8.1"
[workspace.dependencies.reqwest]
version = "0.12.15"
Copy link

Copilot AI Mar 7, 2026

Choose a reason for hiding this comment

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

The workspace pins reqwest to 0.12.x, but after bumping ic-agent/ic-utils the lockfile now includes an additional reqwest 0.13.x as a transitive dependency. If feasible, consider aligning the workspace reqwest version with the transitive one to avoid shipping two major versions (larger build + duplicated TLS/HTTP stacks).

Suggested change
version = "0.12.15"
version = "0.13"

Copilot uses AI. Check for mistakes.
- Use 0-based message names to match 0-based log indices
- Fix --since timestamp to use valid u64 value (was overflowing)
- Document expected --until-index inclusive behavior vs current
  PocketIC exclusive implementation

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.

2 participants