title: Typescript: How to work with structural subtyping and inheritance
body: <p>Consider the following Typescript classes:</p>
  
  <pre><code>abstract class EnforcedString
  {
      private minLength: number;
      private maxLength: number;
      private value: string;
      protected identifier: string;
  
      constructor(minLength: number, maxLength: number, identifier: string)
      {
          this.minLength = minLength;
          this.maxLength = maxLength;
          this.identifier = identifier;
      }
  
      public setValue(value: string): void
      {
          if (typeof value !== 'string') {
              throw(new Error(this.identifier + ' must be a valid string'));
          }        
  
          if (value.length &gt; this.maxLength) {
              throw new Error(this.identifier + ' must have a maximum length of: ' + this.maxLength);
          }
  
          if (this.minLength &gt; 0) {
              if (value.length &lt; this.minLength) {
              const characterString = (this.minLength === 1) ? 'character' : 'characters';
              throw new Error(this.identifier + ' must have at least ' + this.minLength + ' ' + characterString);
          }
      }
  
          this.value = value;
      }
  
      public getValue(): string
      {
          return this.value;
      }
  
      public isEmpty(): boolean
      {
          return this.value.length === 0;
      }
  }
  
  class String255 extends EnforcedString
  {
      constructor(value: string, identifier: string)
      {        
          super(0, 255, identifier);
          this.setValue(value);
      }
  }
  
  class String255Required extends EnforcedString
  {   
      constructor(value: string, identifier: string)
      {        
          super(1, 255, identifier);
          this.setValue(value);
      }
  }
  </code></pre>
  
  <p>Due to Typescript's structural subtyping system, this means that "firstName" in the constructor below is not reported as an error, even though we're assigning a String255 class to a String255Required attribute.</p>
  
  <pre><code>class User 
  {
      private id: UserId;
      private username: Username;
      private firstName: String255Required;
      private lastName: String255Required;
  
      constructor(
          id: UserId,
          username: Username,
          firstName: String255,
          lastName: String255Required
      ) {
          this.id = id;
          this.username = username;
          this.firstName = firstName;
          this.lastName = lastName;
      }
  }
  </code></pre>
  
  <p>So the question is, what's the best practice for dealing with structural subtyping.  I can introduce useless properties in classes that "fixes" the problem, e.g.</p>
  
  <pre><code>class String255Required extends EnforcedString
  {   
      private nope: boolean;      
  
      constructor(value: string, identifier: string)
      {        
          super(1, 255, identifier);
          this.setValue(value);
      }
  }
  </code></pre>
  
  <p>The compiler now reports the error I was expecting because String255Required has different attributes to String255, however this is obviously not desirable.  What are people doing to avoid these kinds of problems?  Note, I'm trying to use classes to enfore type-based business rules.</p>