Skip to content
/ server Public

MDEV-18386: Add server_audit_timestamp_format to customize audit log timestamps#4633

Open
abhishek593 wants to merge 8 commits intoMariaDB:mainfrom
abhishek593:MDEV-18386
Open

MDEV-18386: Add server_audit_timestamp_format to customize audit log timestamps#4633
abhishek593 wants to merge 8 commits intoMariaDB:mainfrom
abhishek593:MDEV-18386

Conversation

@abhishek593
Copy link

This PR adds a new global system variable, server_audit_timestamp_format, to the MariaDB Audit Plugin.

Key changes:

  • Users can now specify a custom strftime format string for audit log timestamps.
  • Default behavior is preserved if the variable is left empty.
  • Added a new test case server_audit_timestamp.test to verify custom formats, including timezone offsets (%z).
  • Updated existing audit tests to reflect the new system variable.

@gkodinov gkodinov added the External Contribution All PRs from entities outside of MariaDB Foundation, Corporation, Codership agreements. label Feb 9, 2026
@gkodinov gkodinov self-assigned this Feb 11, 2026
Copy link
Member

@gkodinov gkodinov left a comment

Choose a reason for hiding this comment

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

This is a preliminary review. Thank you for your contribution!

Copy link
Member

@gkodinov gkodinov left a comment

Choose a reason for hiding this comment

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

it was a good first iteration. Thanks for working on that. Another round of comments coming up.

Copy link
Member

@gkodinov gkodinov left a comment

Choose a reason for hiding this comment

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

LGTM after fixing the below. Please expect a final review.

NULL, NULL, 1024, 0, 0x7FFFFFFF, 1);
static MYSQL_SYSVAR_STR(timestamp_format, timestamp_format,
PLUGIN_VAR_RQCMDARG,
"The format string the strftime() routine applies with its format argument",
Copy link
Member

Choose a reason for hiding this comment

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

I'd say: a format string used to print the timestamp into the audit log messages. The format used is the same as strftime. Default is empty, meaning use the existing hard-coded format.

Copy link
Author

Choose a reason for hiding this comment

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

Done

if (timestamp_format_buffer[0])
ts_len= strftime(ts_tmp, sizeof(ts_tmp), timestamp_format_buffer, &tm_time);

if (ts_len == 0)
Copy link
Member

Choose a reason for hiding this comment

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

just do "else" here. Easier to read.

Copy link
Author

Choose a reason for hiding this comment

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

Done

{
if (!(is_active= (logger_write(logfile, message, len) == (int) len)))
struct tm tm_time;
char ts_tmp[TIMESTAMP_OUTPUT_LENGTH];
Copy link
Member

Choose a reason for hiding this comment

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

256 bytes in the stack ... this is a bit much. I'd allocate a buffer outside of the lock and pass it down. Or, better, it's going at the start of message anyway, can't you just print it there directly instead of using a temp buffer and then memcpy() into it?

Copy link
Author

Choose a reason for hiding this comment

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

Yeah, so here's what I changed. Removed the temp buffer, and directly stored the output of strftime in message buffer at the beginning, then used memmove to shift the output from the start to the end of reserved space.

/**
Write to the log, acquiring the lock.
*/
*/
Copy link
Member

Choose a reason for hiding this comment

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

don't do white-space only changes please!

Copy link
Author

Choose a reason for hiding this comment

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

Done

const char *userip, unsigned int userip_len,
unsigned int connection_id, unsigned int port,
long long query_id, const char *operation)
const char *serverhost, size_t serverhost_len,
Copy link
Member

Choose a reason for hiding this comment

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

no white-space only changes please

Copy link
Author

Choose a reason for hiding this comment

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

Done

time_t ctime;
size_t csize;
char message[1024];
char raw_message[1024 + TIMESTAMP_OUTPUT_LENGTH];
Copy link
Member

Choose a reason for hiding this comment

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

I'd use some named const size_t for the 1k constant

Copy link
Author

Choose a reason for hiding this comment

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

Done


(void) time(&ctime);
csize= log_header(message, sizeof(message)-1, &ctime,
csize= log_header(message, 1024-1,
Copy link
Member

Choose a reason for hiding this comment

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

why do you need to do this? Can't you just pass the actual length as you used to do? And then do the calculation inside this func?

Copy link
Author

Choose a reason for hiding this comment

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

Previously message was a fixed size array (1024). In the new version, its a pointer to an offset within a large buffer, so we must explicitly pass the correct size (MAX_AUDIT_PAYLOAD_LENGTH).

time_t ctime;
size_t csize;
char message[1024];
char raw_message[1024 + TIMESTAMP_OUTPUT_LENGTH];
Copy link
Member

Choose a reason for hiding this comment

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

same here: use a named constant for 1k

Copy link
Author

Choose a reason for hiding this comment

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

Done

@gkodinov gkodinov assigned vuvova and unassigned gkodinov Feb 13, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

External Contribution All PRs from entities outside of MariaDB Foundation, Corporation, Codership agreements.

Development

Successfully merging this pull request may close these issues.

3 participants