doc updates
John Napiorkowski [Wed, 15 Oct 2008 20:49:45 +0000 (20:49 +0000)]
specification.pod

index 6269551..d9a0bbc 100644 (file)
@@ -8,7 +8,7 @@ Specification for extra, declaritive hinting to type constrain definitions.
 
 =head1 INTRODUCTION
 
-We'd like to be able to add additional 'hints' when declaring our type 
+We'd like to be able to add additional 'facets' when declaring our type 
 constraints.  These hints would form an extention to the core types built into
 Moose, such as Str, Object, etc. as well as form the foundation for authors of
 Type Constraint extentions to also add these hints.  The idea is these hints
@@ -37,6 +37,15 @@ Therefore, it will be important to make sure the hinting system can degrade or
 cast gracefully, that way hints defined at the application level will work
 neatly with those defined at a possible database level.
 
+=head1 PROPOSED SYNTAX
+
+The following is proposed syntax for the faceted types:
+
+       subtype MyType,
+        is Str,
+        which hasMinLenth(5), hasMaxLength(20),
+        where {};
+
 =head1 USE CASES
 
 The following are possible use cases.
@@ -52,11 +61,11 @@ To create a string of 10 characters or less.  Since this constraint is captured
 in the code block it is not introspecable.  A possible syntax to declare a Str
 type constraint with a maximum length hint might be:
 
-       my $tc = subtype MaxStr10, as Str[MaxLengthInclusive=>10];
+       my $tc = subtype MaxStr10, as Str, which hasMaxInclusiveLength(10);
 
-this information might be instrospectable via something like:
+this information might be introspectable via something like:
 
-       $tc->meta->hints->max_length_inclusive; ## returns 10
+       $tc->meta->facets->max_length_inclusive; ## returns 10
 
 =head2 DataTime and coercion possibilities
 
@@ -67,10 +76,12 @@ be hooked into the hint system to allow more finely tuned coercions:
        use MooseX::Types::DateTime qw(DateTime);
        
        subtype USEasternDataTime,
-        is DateTime[TimeZone=>'US/Eastern'];
+        is DateTime,
+        which hasTimeZone('US/Eastern');
         
        coerce USEasternDataTime,
-        from DateTime[TimeZone=>'Floating'];
+        from DateTime,
+         which hasTimeZone('Floating')
         via {$_->timezone('US/Eastern')};
         
 The created subtype USEasternDataTime would only pass if the DateTime object
@@ -79,26 +90,93 @@ information to the canonical type.
 
 =head2 Code generation and mapping
 
-Given a type constraint such as: 
-       
-       subtype MaxStr10, as Str[MaxLengthInclusive=>10];
+Given a type constraint such as:
+
+       subtype ValidName, 
+        as Str, 
+        which hasMaxInclusiveLength(45), isAlpha(), 
        
 That becomes part of a class definition:
 
        package MyApp::Person;
        ...
-       has 'short_name' => (isa=>MaxStr10);
+       has 'name' => (isa=>ValidName, required=>1);
 
 A code generator or interpreter could introspect the metadata on the attribute
 'short_name' to create a table like:
 
        CREATE TABLE Person (
-               short_name varchar(10)
+               short_name varchar(45)
+       );
+       
+Please note how the code generator would need to aggregate meta information from
+both the attribute options as well as it's type constraint, since in this case
+the attribute is required.  Here's another, more complicated option.
+
+       package MyApp::Types::StatisticsPeople;
+       
+       ## both types are limited to 45 alphabetical characters that define a
+       ## single word (no whitespace before or after), like "John", but not allow
+       ## "   John", "  John  ", "john123", etc.
+       
+       subtype FirstName, 
+        as Str, 
+        which hasMaxInclusiveLength(45), isAlpha(), isWord();
+
+       subtype ValidName, 
+        as Str, 
+        which hasMaxInclusiveLength(45), isAlpha(), isWord();
+        
+       package MyApp::Person;
+        
+       use Moose;
+       use MyApp::Types::StatisticsPeople (qw/FirstName LastName/);
+        
+       has first_name => (isa=>FirstName, required=>1);
+       has last_name => (isa=>LastName, required=>1);
+       
+The above might be generated into sql like so (let's assume a database that
+has schema support, like Postgresql,
+
+       CREATE TABLE StatisticsPeople.FirstName (
+               first_name_id uuid,
+               value varchar(45),
+               PRIMARY KEY('first_name_id')
+       );
+
+       CREATE TABLE StatisticsPeople.LastName (
+               last_name_id uuid,
+               value varchar(45),
+               PRIMARY KEY('last_name_id')
+       );
+       
+       CREATE TABLE PersonFirstName (
+               fk_person_id uuid,
+               fk_first_name_id uuid,
+               PRIMARY KEY('fk_person_id', 'fk_first_name_id'),
+       )
+       
+       CREATE TABLE Person (
+               person_id uuid,
+               fk_first_name_id uuid,
+               fk_last_name_id uuid,           
+               PRIMARY KEY ('person_id')
+               CONSTRAINT 'person_validname' 
+                       FOREIGN KEY ('fk_last_name_id') 
+                       REFERENCES 'ValidName' ('valid_name_id'),
        );
        
+       my $person = model('Person')->create({
+               person_first_name => { first_name => {value=>'John'} },
+               ...
+       });
+
+Probably an extreme options, but if we have types with all this meta data, why
+not have it reflect down to the database model?
+
 [Addional Code examples to follow]
        
-=head1 CORE TYPES AND HINT HEIRARCHY
+=head1 CORE TYPES AND FACET HEIRARCHY
 
 The following is an outline of the possible hints associated with core Moose
 type constraints.  Hints are assumed to be inherited.
@@ -130,12 +208,13 @@ DDUNCAN
                 Int[
                     Signed
                     UnSigned
+                    Even
+                    Odd
                 ]
-                    SmallInt
-                    BigInt
               Str[
                   ASCII*
                   Printable*
+                  isDigits*  (That is, a string that is a number like "123")
                   Word (must be a single 'word')
                   MaxLength
                   MinLength
@@ -152,6 +231,8 @@ DDUNCAN
               ArrayRef[`a][
                   MaxElements
                   MinElements
+                  hasDuplicates
+                  hasOnlyUnique
               ]
               HashRef[`a][
                   HasAllKeys
@@ -168,3 +249,7 @@ DDUNCAN
                       Requires
                       Does
                   ]
+
+**
+Might like to have some stuff from the Math packages, like to validate if a
+value matches a given function, or is in the domain or range of a function.
\ No newline at end of file