Tangram::Schema(3pm)

πŸ“¦
version 2.12 Β· 3 versions
, in ubuntu noble, ubuntu resolute, ubuntu stonking

πŸ’– Tangram::Schema(3pm) β€” the glow-up guide πŸ’–

okay bestie, listen up β€” this is Tangram::Schema, from the User Contributed Perl Documentation corner of the universe, and it's literally the blueprint for how your whole persistence situation works. Think of it as the group chat where every persistent class gets introduced. 🫢


✨ NAME ✨

Tangram::Schema β€” describe a system of persistent classes πŸ’…


🌸 SYNOPSIS 🌸

use Tangram;

$schema = Tangram::Schema->new( $hashref );

Tangram::Relational->connect( $schema, ... );

# write SQL to FILE
$schema->deploy( \*FILE );

# write SQL to STDOUT
$schema->deploy();

πŸ¦‹ DESCRIPTION πŸ¦‹

A Schema holds all the tea about the persistent aspects of a system of classes. That info is what gets used to do the mapping between your OO constructs and a relational database. no cap.

Schema objects get initialized from a nested data structure called a schema hash. Its general structure is described right here, in this very page. πŸ‘‘

The Schema object that comes out of it becomes the owner of the schema hash you passed to new(). That hash may not be modified afterwards, and you can't make any assumptions about its content either. it's not yours anymore, bestie, it's the Schema's now. πŸ’€

note: No corresponding Perl classes are generated from calling Tangram::Schema->new. If you do want that, and you like the behaviour of the separately distributed Class::Tangram module, then pass that $hashref from the example above to the Class::Tangram::Generator->new() constructor instead. See Class::Tangram::Generator for more info. πŸ’–

πŸŽ€ CLASS METHODS πŸŽ€

πŸ’… new

$schema = Tangram::Schema->new( $hash );

Returns a brand new Schema object. ✨

The freshly created Schema object becomes the owner of the hash, which can no longer be modified or reused by client code. periodt. it's giving "handed over the aux cord, never getting it back". 🎧

The schema hash describes the persistent aspects of a system of classes. It's a multilevel data structure:

  1. The first level of the hash contains info that's relevant to the system as a whole.
  2. The second level contains info on a per-class basis.
  3. The third level contains info about the individual fields in a class. That info depends on the type of the field and is not documented here β€” see "field hash" for a list of predefined persistent types.

🌈 Global properties

The first level of the schema hash describes the aspects that are global to a system of persistent classes. It has the following vibe:

{
   classes =>
  [
     Identity =>
      {
         table => 'IdentityState',
      abstract => 1
      },

      NaturalPerson =>
      {
         bases => [ qw( Identity ) ],
      },

      LegalPerson =>
      {
         bases => [ qw( Identity ) ],
      },
   ],

   make_object => sub { ... },
   set_id => sub { ... }
   get_id => sub { ... }
   normalize => sub { ... },

   control => '...'

   sql => { ... },
}
  • classes is an array called the "class registry". It contains a description of each persistent class.
  • make_object holds a reference to a closure that returns a new object of a given class. This field is optional: by default, Tangram calls class method new().
  • set_id and get_id are used together to associate an object ID with a persistent object. By default, Tangram converts a reference to an object to a unique integer value by evaluating the expression 0 + $obj. That result is used as a key in a hash contained in the Storage object. The values in that hash are the object IDs.
  • If any of your classes use overloading, this approach will not work, and you'll need to supply your own get_id/set_id methods. 😭
  • control is the name of a table that has a single row. That row contains the major and minor version numbers of the Tangram that created the storage, plus the highest allocated object id. It defaults to 'Tangram'.
  • Optional field normalize contains a subroutine that's called to transform classnames and fieldnames into table and column names. The function is called with two arguments: the name to be transformed, and a 'type' argument (currently one of 'tablename' or 'fieldname'). The return value should be the transformed string.
  • Note that it's expected that the normalize sub will return identical strings with identical arguments, that normalize(normalize($string, $flag), $flag) eq normalize($string, $flag).

Optional field sql contains a hash that can be used to customize some of the SQL that Tangram generates. The options available are:

  • default_null β€” you can use this to deal with those databases that don't support the explicit 'NULL' specifier in column definitions. Defaults to 'NULL'. Note that this does not get automatically appended to attributes that have a SQL type explicitly declared. πŸ™ˆ
  • id β€” object ids encode the type of the object. Tangram assigns a class id to each persistent concrete class within a Schema. When an object is inserted, Tangram allocates a unique integer from a class-specific allocator, then appends the class id to it. So the object id for a NaturalPerson may look like 270005, where 0005 is the class id. Field id contains the SQL type that is used to map the rowid part of the object id. It defaults to 'INTEGER'.
  • oid_sequence β€” if set, this is the name of a sequence to use as the default OID generator, should a particular class not define one. Sequences are an alternate way of generating unique identifiers for rows. They're more scalable when you have high concurrency, but most people won't notice that. 🀷 It's also possible to define an OID sequence on a per-class level; see below for details. Sequences are emulated on pretend databases like MySQL. πŸ’…
  • make_id β€” this is a closure that's expected to return a unique ID. It's called like this:
$make_id->($class_id, $storage, $object)

Where $class_id is the Class identifier for the newly created object, and $storage is the Tangram::Storage object. The $object is the instance of the object to be inserted.

  • cid β€” field cid contains the SQL type that is used to map the class id part of the object id. It defaults to 'INTEGER'.
  • cid_size β€” field cid_size contains the number of decimal positions that the class id occupies within the object id. It defaults to '4'. This does not affect the database, only the in-memory representation of object IDs.
  • oid β€” historical spurious documentation bug. Documentation described the function that the id option performs. πŸ’€ (yes really. it's a ghost. πŸ‘»)
  • table_type β€” field table_type is a string that, if set, will be appended to all CREATE TABLE commands with TYPE=x. For instance, to use transactions with a MySQL database with InnoDB enabled, set table_type to "InnoDB", and (re)deploy your database. πŸ”₯
  • dumper β€” this field sets the default mechanism by which arbitrary structures are serialised to columns, in the absence of a portion of the Tangram schema covering their mapping. The default value is "Storable" (see Storable), seeing as Storable is something like the "native" serialisation mechanism for Perl. Currently, this setting only applies to the idbif mapping type (see Tangram::Type::Dump::Any). It would make more sense for the default to be "YAML", but unfortunately YAML doesn't support dumping the entire range of native Perl data types, which sucks immensely. 😭

The other fields are related to the SQL types that Tangram uses to store meta-information.


🧚 class registry

The class registry is an array containing one entry per persistent class. The array contains a list of key => value pairs. The key is the class name, and the value is a reference to a hash called the class hash. That hash contains the info on how to map the class. πŸ—ΊοΈ

The class hash can have the following fields:

  • abstract
  • bases
  • fields
  • table
  • table_type
  • id
  • oid_sequence
  • make_id
  • Field abstract contains a boolean that should be true if the class is abstract. If this field isn't present, the class is considered to be concrete.
  • Field bases contains a reference to an array of base classes.
  • Field fields contains a reference to the "field hash".
  • Field table sets the name of the table that Tangram should use to store the state of objects pertaining to this class. This field is optional: it defaults to the class name. If the class name isn't an acceptable SQL table identifier, you will need to set this field.
  • Field table_type sets the type of the table β€” for instance, the storage back-end to the RDBMS or the storage format. It specifies, on a per-table basis, what the table_type attribute of the schema defines. You almost certainly don't want to set this on a per-table basis. πŸ™ˆ
  • Field id contains an integer identifier for this class. That identifier must be unique within the same schema. If this field isn't present, Tangram sets it to the last class id plus one.
  • Fields oid_sequence and make_id are per-class versions of their schema-wide versions documented above. These should be inherited by their subclasses, but currently (as of 2.07_06) they aren't. 😭 To be safe, until this documentation gets fixed, define them in all subclasses.

πŸ“ field hash

Each persistent type is identified by a 'typetag', e.g. "int", "string" or "array".

All the persistent fields of a given type get grouped together inside the field hash, where the typetag is used as a key. The individual fields are specified in an array or a hash, whose layout is type-dependant. For example:

fields =>
{
   string   => [ qw( firstName name ) ],
   int      => [ qw( age ) ],
   ref      => { partner => { null => 1 } },
   array    => { children => 'NaturalPerson' },
},

The typetag doesn't just specify the type of a field β€” it also says how it should be mapped to SQL constructs. Sometimes the same Perl type lends itself to more than one mapping. For example, there are at least two plausible ways of mapping a Perl array (see Tangram::Type::Array::FromMany and Tangram::Type::Array::FromOne). 🀯

Tangram's persistent type system is extensible, allowing you to mount your own types and make them persistent. All you have to do is register your type and provide mapping code. See Tangram::Type. πŸ‘‘

Tangram comes with built-in support for the following types:

  • string, int, real: see Tangram::Type::Scalar
  • reference: see Tangram::Type::Ref::FromMany
  • array: see Tangram::Type::Array::FromMany, Tangram::Type::Array::FromOne
  • Set::Object: see Tangram::Type::Set::FromMany, Tangram::Type::Set::FromOne

πŸŽ€ INSTANCE METHODS πŸŽ€

these are the methods you'd call on an actual schema object, bestie. and uhh… spoiler alert: they're both deprecated, so this section is giving "museum exhibit" more than "main character". still gotta document them tho, the rules are the rules πŸ’…


deploy

deploy is deprecated. no cap, do not build your whole personality around it.

⚠️ heads up bestie: this one's deprecated. like, retired. the vibes have moved on.

if you were about to call deploy and feel all proud of yourself β€” stoppp πŸ™ˆ β€” the real move is to go read Tangram::Relational, because that's where the actual deploy behaviour lives now. it's giving "everything you wanted is over there" πŸ’«


retreat

retreat is also deprecated. yes, both of them. the whole pair. iconic in a historical way 🫢

⚠️ same energy as deploy: deprecated, don't @ me, go look at the new spot.

just like its sibling up there, retreat has been deprecated and you should be looking at Tangram::Relational instead. that's the whole tea β˜• β€” I'm not gonna invent extra behaviour that isn't in here, because ✨ accuracy is the vibe ✨.


✨ bye bestie ✨

okay that's the whole entire page, you made it to the end πŸŽ‰πŸ¦‹ go forth and not call deprecated methods, slay πŸ’–

this page came from the perl v5.36.0 distribution, dated 2022-10-16, and it's the one and only Tangram::Schema(3pm). mwah πŸ’…πŸŒΈ

πŸ“¦ where this page comes from