[TransWarp] Constraints on model attributes

Roché Compaan roche at upfrontsystems.co.za
Tue Jul 29 03:41:23 EDT 2003

* Phillip J. Eby <pje at telecommunity.com> [2003-07-29 00:39]:
> >How do I set attributes on the referencedType that are needed for
> >normalization *without* subclassing the types.
> Eh?  That would be a *different* type.  So subclassing would be appropriate.
> >To be clear, let's
> >say I have a model.Attribute that only allows values in an enumerated
> >set and with a maximum length of 4 characters. For example on planet
> >Stepford, the beings there are only allowed names John, Mary and Pete
> >and their names may not be longer than 4 characters.
> Um, why would you do that?  They're already four characters long, so what's 
> the extra bit for?

Just an example of another constraint.

> >class Drone(model.Element):
> >
> >    class Name(model.Attribute):
> >        referencedType = Text
> >
> >        # Ugly, doesn't work and just to illustrate what I want to do.
> >        referencedType.max_length = 4
> >        referencedType.John = model.enum("John")
> >        referencedType.Mary = model.enum("Mary")
> >        referencedType.Pete = model.enum("Pete")
> >
> >        # or
> >        referencedType = Text(max_length=4,
> >            allowed_values=["John", "Mary", "Pete"])
> class DroneName(Enumeration):
>     John = Mary = Pete = model.enum()
> class Drone(model.Element):
>     referencedType = DroneName
> And that would be it.  Now, if you wanted to ensure that they were four 
> characters long, you could probably do something like:
> class DroneName(MinMaxLen, Enumeration, Type):
>     max_length = 4
>     John = Mary = Pete = model.enum()

The problem is that the sequence for the enumaration can be dynamically
computed, so subclassing won't work eg.:

class Customer(model.Element):

    class Category(model.Attribute):
        referencedType = Enumeration(values=func)

where func returns a list of categories the user created in the app.

> >This is where I got stuck previously and implemented what are now types
> >as model.Attributes.
> I'm not sure why you want to make types into constraints on features.  This 
> seems counterintuitive to me, since this is less reusable than just 
> creating a type explicitly.  Usually a type is available directly from a 
> module, whereas a feature is inside a class.

Yes, that's why I changed Enumeration, Text, MinMaxLen, etc to types -
they are not model.Attributes anymore. And as I said previously I agree
with you that they should be types - I just mentioned where I got stuck
the first time.

> I suppose I can imagine there being certain types that you don't want to 
> call out explicitly because they repeat a lot (e.g. bounded strings), but 
> I'd rather address such items on a case-by-case basis with e.g. functions 
> to create a new type on the fly.  Hm.  I suppose you could always create 
> constraints as IType/ITypeInfo implementations to wrap existing types, e.g.:
> class DroneName(Enumeration):
>     John = Mary = Pete = model.enum()
> class Drone(model.Element):
>     referencedType = MinMaxLen(DroneName, max_length=4)

This shows promise. Or MinMaxLen could be a type factory, then no
wrapping is needed?

I just want to make it as simple as possible for somebody using these
types. It should be as trivial as saying varchar[10] in SQL. Subclassing
shouldn't be required for simple constraints:

    class MemberPassword(model.Attribute):
        referencedType = Password(min_length=4)

    class Age(model.Attribute):
        referencedType = Integer(min=18)

    class Gender(model.Attribute):
        referencedType = Text(values=['male','female'])

    class SomeCategory(model.Attribute):
        referencedType = Enumeration(values=func_returning_categories)

Roché Compaan
Upfront Systems                 http://www.upfrontsystems.co.za

More information about the PEAK mailing list