protected function throwInvalidTypeException(string $property, array $types, bool $optional = false)
    {
        $str = "Expected '{{types}}' for {{optional}} property '{{property}}' in {{class}}, got '{{actualtype}}'";

        throw new InvalidTypeException(Str::format($str, [
            'types'     => trim(
                str_replace('optional', '', implode('|', array_values($types))), '|'
            ),
            'optional'  => $optional ? 'optional' : null,
            'property'  => $property,
            'class'     => get_class($this),
            'actualtype'=> gettype($this->{$property}),
        ]));
    }