title: In Domain-Driven Design, how to determine if sending an email is an application level or domain level concern?
body: <p>Suppose you have a simple application called "Next in Line". Any business who has long waiting lines may want your software to give customers a better line queue experience.</p>
  
  <p>Stakeholder says "<strong>When</strong> a customer wants a ticket, they walk up to our computer console and enter their email address. Then they will receive an email that contains their ticket number and unique access login to our app for more ticket queue features". Sending the email with the ticket number (and access to the app) is integral to the business.</p>
  
  <p>Our Command Handler (application level) may look like this:</p>
  
  <pre><code>class TakeTicketCommandHandler
  {
     private $repo;
  
     public function __construct(TicketRepository $repo)
     {
         $this-&gt;repo = $repo;
     }
  
     public function handle(TakeTicketCommand $command) 
     {
        $ticket = new Ticket(new EmailValueObject($command-&gt;getEmail()));
  
        DB::transaction(function () {
             // Send email here from the command handler? 
             // Seems domain "leaky" because Ticket Aggregate Root is responsible for this?
             ...
  
             $this-&gt;repo-&gt;persist($ticket);
        }
     }
  }
  </code></pre>
  
  <p>Our Ticket Aggregate Root may look like this:</p>
  
  <pre><code>class Ticket extends AggregateRoot
  {
      private $id;
      private $email;
  
      public function __construct(EmailValueObject $email)
      {
          $this-&gt;id = new GUID();
          $this-&gt;email = $email;
  
          // Maybe some more domain logic here
          ...
  
          // Send email here?
          // Should I have injected an interface for sending an email here?
          ...
      }        
  
  }
  </code></pre>
  
  <p><strong>Questions:</strong></p>
  
  <ol>
  <li>How should the email requirement from stakeholder be implemented in a Domain-Driven Design app? (use code above to demonstrate how you would do it and explain why). How do we know when something is an application level requirement versus a domain level requirement?</li>
  <li>Notice the email is in a transaction, however transactions rollback for persistence here and not services like emailing. If the ticket persistance fails, what can we do about the email? (Should we provide an undo action like sending out another email informing user of the error?)</li>
  <li>Say we want to have Ticket also raise an event like <code>TicketQueuedEvent</code>. In the event handler for this event, another Aggegrate Root is updated. Is this bad practice/modelling? If the application level services are meant to orchestrate the domain, then is Aggregate Root to Root communication through Events a valid approach to DDD?</li>
  </ol>