Problem
The mails table has a mail_class column (added in the migration, included in $fillable), but it's never populated. The code in LogMail::getMandatoryAttributes() has it commented out:
// 'mail_class' => $this->getMailClassHeaderValue($event),
And getMailClassHeaderValue() doesn't exist in the codebase — it was likely removed at some point.
This means there's no way to filter logged emails by their mailable class (e.g. "show me all OrderConfirmation emails"), which is a very useful feature for debugging and monitoring.
Proposed Solution
Laravel's MessageSending and MessageSent events include $event->data['__laravel_mailable'] which contains the fully qualified class name of the mailable (e.g. App\Mail\OrderConfirmation). This is set by Laravel's mail system automatically.
Changes to LogMail
In getDefaultLogAttributes(), add:
'mail_class' => $event->data['__laravel_mailable'] ?? null,
In getMandatoryAttributes(), uncomment/replace the existing line:
'mail_class' => $event->data['__laravel_mailable'] ?? null,
Using getMandatoryAttributes() is preferred since mail_class should always be logged when available (not gated by the logging.attributes config — similar to uuid, sent_at, and mailer).
Why getDefaultLogAttributes alone isn't enough
If mail_class is only in getDefaultLogAttributes(), users would need to add 'mail_class' to their logging.attributes config to enable it. Putting it in getMandatoryAttributes() makes it automatic, matching the behavior of other metadata fields.
Backwards compatible
- The column already exists and is nullable, so existing records are unaffected
- No migration needed
- Records created before this change simply have
mail_class = null
Related: SMTP sent_at bug (#41)
While investigating this, we noticed that the MessageSent listener's UUID lookup ($mail->firstWhere('uuid', $this->getCustomUuid($event))) returns null for SMTP because AttachUuid skips providers without a matching driver class. This means sent_at is never set on SMTP-sent emails.
A separate issue, but worth noting since it affects the same LogMail flow. A fix could be to always attach UUIDs regardless of provider (the UUID is only used internally for record matching, not for webhook tracking).
Problem
The
mailstable has amail_classcolumn (added in the migration, included in$fillable), but it's never populated. The code inLogMail::getMandatoryAttributes()has it commented out:// 'mail_class' => $this->getMailClassHeaderValue($event),And
getMailClassHeaderValue()doesn't exist in the codebase — it was likely removed at some point.This means there's no way to filter logged emails by their mailable class (e.g. "show me all OrderConfirmation emails"), which is a very useful feature for debugging and monitoring.
Proposed Solution
Laravel's
MessageSendingandMessageSentevents include$event->data['__laravel_mailable']which contains the fully qualified class name of the mailable (e.g.App\Mail\OrderConfirmation). This is set by Laravel's mail system automatically.Changes to
LogMailIn
getDefaultLogAttributes(), add:In
getMandatoryAttributes(), uncomment/replace the existing line:Using
getMandatoryAttributes()is preferred sincemail_classshould always be logged when available (not gated by thelogging.attributesconfig — similar touuid,sent_at, andmailer).Why
getDefaultLogAttributesalone isn't enoughIf
mail_classis only ingetDefaultLogAttributes(), users would need to add'mail_class'to theirlogging.attributesconfig to enable it. Putting it ingetMandatoryAttributes()makes it automatic, matching the behavior of other metadata fields.Backwards compatible
mail_class = nullRelated: SMTP
sent_atbug (#41)While investigating this, we noticed that the
MessageSentlistener's UUID lookup ($mail->firstWhere('uuid', $this->getCustomUuid($event))) returnsnullfor SMTP becauseAttachUuidskips providers without a matching driver class. This meanssent_atis never set on SMTP-sent emails.A separate issue, but worth noting since it affects the same
LogMailflow. A fix could be to always attach UUIDs regardless of provider (the UUID is only used internally for record matching, not for webhook tracking).