title: how to build aggregate in ddd, passing VO or raw data?
body: <p>What is the correct way of designing aggregate in DDD, for exmaple you need to create some user, and to create it we need to have id, email, living address and born address.
  So we can do it like this (I'll use PHP as it's my main language):</p>
  <pre><code>  class User {
       private function __construct(
           private UserId $id,
           private Email $email,
           private Address $livingAddress,
           private Address $bornAddress
       ) {}
  
       public static create(
            string $uuid, 
            string $email, 
            string $city, 
            string $country, 
            string $address,
            string $bornCity, 
            string $bornCountry, 
            string $bornAddress,
       ) {
          return new self (
              UsesId::fromString($uuid),
              new Email($email),
              new Address($city, $country, $address),
              new Address($bornCity, $bornCountry, $bornAddress)
          );
       }
    }
  </code></pre>
  <p>in this case we following a rule that aggregate root responsible of checking all invariants , because he creating all VO's and they has own validation. But it's adding complexity to actual <code>User</code> class, we have to many parameters passed etc.</p>
  <p>Another possible solution is to build it like this:</p>
  <pre><code>  class User {
       private function __construct(
           private UserId $id,
           private Email $email,
           private Address $livingAddress,
           private Address $bornAddress
       ) {}
  
       public static create(
            UserId $id, 
            Email $email, 
            Address $livingAddress,
            Address $bornAddress
       ) {
          return new self (
              id,
              $email,
              $livingAddress,
              $bornAddress
          );
       }
    }
  </code></pre>
  <p>now <code>User</code> object is smaller, maybe even more &quot;elegant&quot;, but we breaking the rule that aggregate should check all invariants.</p>
  <p>And the third option is probably to use Factory, I'll not provide code here but explain how I see it. Basically factory takes a row data, create VO, and passing it to aggregate, so aggregate creation will look like in the second example. Again aggregate is not responsible for all invariants, but Factory is on one of allowed patterns by DDD so I think thats fine.</p>
  <p>I know probably there is no a right way, but I want to hear some best practices and suggestions from someone who has distinct knowledge in DDD about how to do it right.</p>