Skip to content

Logging: add freshness_limit (cfl) and current_age (cca) log fields#13168

Open
sheikh-saifi wants to merge 1 commit into
apache:masterfrom
sheikh-saifi:feature/log-freshness-limit-current-age
Open

Logging: add freshness_limit (cfl) and current_age (cca) log fields#13168
sheikh-saifi wants to merge 1 commit into
apache:masterfrom
sheikh-saifi:feature/log-freshness-limit-current-age

Conversation

@sheikh-saifi
Copy link
Copy Markdown

@sheikh-saifi sheikh-saifi commented May 16, 2026

Summary

Adds two new log fields to enable cache content modelling:

  • cfl (freshness_limit): written on cache hit and cache write
  • cca (current_age): written when serving from cache

Both are computed from internal state without reading headers.

Changes

  • HttpTransact: propagate freshness_limit and current_age into t_state
  • LogAccess: implement marshallers + register field tags
  • Docs: document new fields in log-formats.en.rst

Testing

  • Existing ctest log tests pass
  • Manual verification via custom logging.yaml format

Fixes: #13127

Log the freshness_limit when objects are served from or written to the
cache, and current_age when serving. Both values are derived from
internal HttpTransact state without reading response headers.

New log fields:
  cfl - cache freshness limit in seconds (-1 if not applicable)
  cca - cache current age in seconds (-1 if not applicable)
@bneradt
Copy link
Copy Markdown
Contributor

bneradt commented May 18, 2026

[approve ci]

Copy link
Copy Markdown
Contributor

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 cache freshness and age values as custom log fields for ATS transaction logging, wiring cache state through HttpTransact, TransactionLogData, and LogAccess, and documenting the new field tags.

Changes:

  • Adds freshness_limit and current_age members to cache transaction state.
  • Registers and marshals new cfl and cca log fields.
  • Documents the new cache log fields.

Reviewed changes

Copilot reviewed 8 out of 8 changed files in this pull request and generated 6 comments.

Show a summary per file
File Description
src/proxy/http/HttpTransact.cc Captures freshness limit and current age during cache freshness evaluation.
include/proxy/http/HttpTransact.h Adds cache state storage for the new values.
src/proxy/logging/TransactionLogData.cc Exposes the new cache state values to logging.
include/proxy/logging/TransactionLogData.h Declares the new logging data getters.
src/proxy/logging/LogAccess.cc Adds marshallers for the new integer log fields.
include/proxy/logging/LogAccess.h Declares the new marshalling methods.
src/proxy/logging/Log.cc Registers cfl and cca as log field symbols.
doc/admin-guide/logging/formatting.en.rst Adds documentation for the new cache log fields.

Comment on lines +7586 to +7592
s->cache_info.freshness_limit = fresh_limit; // save for logging
ink_assert(fresh_limit >= 0);

current_age = HttpTransactCache::calculate_document_age(s->request_sent_time, s->response_received_time, cached_obj_response,
response_date, s->current.now);

s->cache_info.current_age = current_age;
Comment on lines +197 to +199
time. Computed from internal state without reading
response headers. Value is ``-1`` if not applicable.

Comment thread src/proxy/logging/Log.cc
Comment on lines +725 to +731
field = new LogField("cache_freshness_limit", "cfl", LogField::sINT, &LogAccess::marshal_cache_freshness_limit,
&LogAccess::unmarshal_int_to_str);
global_field_list.add(field, false);
field_symbol_hash.emplace("cfl", field);

field = new LogField("cache_current_age", "cca", LogField::sINT, &LogAccess::marshal_cache_current_age,
&LogAccess::unmarshal_int_to_str);
Comment on lines 972 to 973
// ===== Retry attempts =====

Comment on lines +493 to +494
int freshness_limit = -1; // seconds; -1 = not yet set
ink_time_t current_age = -1; // seconds; -1 = not yet set
Comment on lines +7586 to +7592
s->cache_info.freshness_limit = fresh_limit; // save for logging
ink_assert(fresh_limit >= 0);

current_age = HttpTransactCache::calculate_document_age(s->request_sent_time, s->response_received_time, cached_obj_response,
response_date, s->current.now);

s->cache_info.current_age = current_age;
@bneradt
Copy link
Copy Markdown
Contributor

bneradt commented May 18, 2026

The format issues can be fixed locally by running the --target format cmake target.

Here's the failed format job report, in case it's helpful:

diff --git a/doc/admin-guide/logging/formatting.en.rst b/doc/admin-guide/logging/formatting.en.rst
index c2f2bc8aa0..58e5ae5fe6 100644
--- a/doc/admin-guide/logging/formatting.en.rst
+++ b/doc/admin-guide/logging/formatting.en.rst
@@ -196,7 +196,7 @@ cfl   Proxy Cache    Freshness limit (in seconds) for the cached object.
 cca   Proxy Cache    Current age (in seconds) of the cached object at serve
                      time. Computed from internal state without reading
                      response headers. Value is ``-1`` if not applicable.
-                     
+
 ===== ============== ==========================================================
 
 .. _admin-logging-fields-txn:
diff --git a/include/proxy/http/HttpTransact.h b/include/proxy/http/HttpTransact.h
index 6db51b97dc..056e6df2ca 100644
--- a/include/proxy/http/HttpTransact.h
+++ b/include/proxy/http/HttpTransact.h
@@ -490,8 +490,8 @@ public:
     HTTPInfo         transform_store;
     CacheDirectives  directives;
     HTTPInfo        *object_read          = nullptr;
-    int              freshness_limit      = -1;  // seconds; -1 = not yet set
-    ink_time_t       current_age          = -1;              // seconds; -1 = not yet set
+    int              freshness_limit      = -1;      // seconds; -1 = not yet set
+    ink_time_t       current_age          = -1;      // seconds; -1 = not yet set
     HTTPInfo        *stale_fallback       = nullptr; // Saved stale object for action 6 fallback during retry
     CacheWriteLock_t write_lock_state     = CacheWriteLock_t::INIT;
     int              lookup_count         = 0;
diff --git a/include/proxy/logging/TransactionLogData.h b/include/proxy/logging/TransactionLogData.h
index 7c3a9d3463..18618b9cd0 100644
--- a/include/proxy/logging/TransactionLogData.h
+++ b/include/proxy/logging/TransactionLogData.h
@@ -159,13 +159,13 @@ public:
   int64_t   get_congestion_control_crat() const;
 
   // ===== Cache state =====
-  int get_cache_write_code() const;
-  int get_cache_transform_write_code() const;
-  int get_cache_open_read_tries() const;
-  int get_cache_open_write_tries() const;
-  int get_freshness_limit() const;
+  int     get_cache_write_code() const;
+  int     get_cache_transform_write_code() const;
+  int     get_cache_open_read_tries() const;
+  int     get_cache_open_write_tries() const;
+  int     get_freshness_limit() const;
   int64_t get_current_age() const;
-  int get_max_cache_open_write_retries() const;
+  int     get_max_cache_open_write_retries() const;
 
   // ===== Retry attempts =====
   int64_t get_simple_retry_attempts() const;
diff --git a/src/proxy/http/HttpTransact.cc b/src/proxy/http/HttpTransact.cc
index 452cd60c65..5ab141bdc1 100644
--- a/src/proxy/http/HttpTransact.cc
+++ b/src/proxy/http/HttpTransact.cc
@@ -7581,14 +7581,14 @@ HttpTransact::what_is_document_freshness(State *s, HTTPHdr *client_request, HTTP
     return Freshness_t::STALE;
   }
 
-  response_date = cached_obj_response->get_date();
-  fresh_limit   = calculate_document_freshness_limit(s, cached_obj_response, response_date, &heuristic);
-  s->cache_info.freshness_limit = fresh_limit;  // save for logging
+  response_date                 = cached_obj_response->get_date();
+  fresh_limit                   = calculate_document_freshness_limit(s, cached_obj_response, response_date, &heuristic);
+  s->cache_info.freshness_limit = fresh_limit; // save for logging
   ink_assert(fresh_limit >= 0);
 
   current_age = HttpTransactCache::calculate_document_age(s->request_sent_time, s->response_received_time, cached_obj_response,
                                                           response_date, s->current.now);
-                                                      
+
   s->cache_info.current_age = current_age;
 
   // First check overflow status
diff --git a/src/proxy/logging/Log.cc b/src/proxy/logging/Log.cc
index 0647309ceb..7e401b0fd7 100644
--- a/src/proxy/logging/Log.cc
+++ b/src/proxy/logging/Log.cc
@@ -722,8 +722,8 @@ Log::init_fields()
   global_field_list.add(field, false);
   field_symbol_hash.emplace("chm", field);
 
-  field = new LogField("cache_freshness_limit", "cfl", LogField::sINT, &LogAccess::marshal_cache_freshness_limit, 
-                      &LogAccess::unmarshal_int_to_str);
+  field = new LogField("cache_freshness_limit", "cfl", LogField::sINT, &LogAccess::marshal_cache_freshness_limit,
+                       &LogAccess::unmarshal_int_to_str);
   global_field_list.add(field, false);
   field_symbol_hash.emplace("cfl", field);
 
diff --git a/src/proxy/logging/LogAccess.cc b/src/proxy/logging/LogAccess.cc
index 3adeaf2316..0ac1bb045e 100644
--- a/src/proxy/logging/LogAccess.cc
+++ b/src/proxy/logging/LogAccess.cc
@@ -2610,7 +2610,6 @@ LogAccess::marshal_cache_hit_miss(char *buf)
   return INK_MIN_ALIGN;
 }
 
-
 int
 LogAccess::marshal_cache_freshness_limit(char *buf)
 {

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

Labels

Projects

Status: No status

Development

Successfully merging this pull request may close these issues.

Add ability to log "freshness_limit" and "current_age"

4 participants