Entity attributes

Entity attributes are specified as class attributes inside the entity class using the syntax attr_name = kind(type, options):

  1. class Customer(db.Entity):
  2. name = Required(str)
  3. email = Required(str, unique=True)

In the parentheses, after the attribute type, you can specify attribute options.

Each attribute can be one of the following kinds:

  • Required

  • Optional

  • PrimaryKey

  • Set

Required and Optional

Usually most entity attributes are of Required or Optional kind. If an attribute is defined as Required then it must have a value at all times, while Optional attributes can be empty.

If you need the value of an attribute to be unique then you can set the attribute option unique=True.

PrimaryKey

PrimaryKey defines an attribute which is used as a primary key in the database table. Each entity should always have a primary key. If the primary key is not specified explicitly, Pony will create it implicitly. Let’s consider the following example:

  1. class Product(db.Entity):
  2. name = Required(str, unique=True)
  3. price = Required(Decimal)
  4. description = Optional(str)

The entity definition above will be equal to the following:

  1. class Product(db.Entity):
  2. id = PrimaryKey(int, auto=True)
  3. name = Required(str, unique=True)
  4. price = Required(Decimal)
  5. description = Optional(str)

The primary key attribute which Pony adds automatically always will have the name id and int type. The option auto=True means that the value for this attribute will be assigned automatically using the database’s incremental counter or a sequence.

If you specify the primary key attribute yourself, it can have any name and type. For example, we can define the entity Customer and have customer’s email as the primary key:

  1. class Customer(db.Entity):
  2. email = PrimaryKey(str)
  3. name = Required(str)

Set

A Set attribute represents a collection. Also we call it a relationship, because such attribute relates to an entity. You need to specify an entity as the type for the Set attribute. This is the way to define one side for the to-many relationships. As of now, Pony doesn’t allow the use of Set with primitive types. We plan to add this feature later.

We will talk in more detail about this attribute type in the Entity relationships chapter.

Composite keys

Pony fully supports composite keys. In order to declare a composite primary key you need to specify all the parts of the key as Required and then combine them into a composite primary key:

  1. class Example(db.Entity):
  2. a = Required(int)
  3. b = Required(str)
  4. PrimaryKey(a, b)

Here PrimaryKey(a, b) doesn’t create an attribute, but combines the attributes specified in the parenthesis into a composite primary key. Each entity can have only one primary key.

In order to declare a secondary composite key you need to declare attributes as usual and then combine them using the composite_key directive:

  1. class Example(db.Entity):
  2. a = Required(str)
  3. b = Optional(int)
  4. composite_key(a, b)

In the database composite_key(a, b) will be represented as the UNIQUE ("a", "b") constraint.

If have just one attribute, which represents a unique key, you can create such a key by specifying unique=True by an attribute:

  1. class Product(db.Entity):
  2. name = Required(str, unique=True)

Composite indexes

Using the composite_index() directive you can create a composite index for speeding up data retrieval. It can combine two or more attributes:

  1. class Example(db.Entity):
  2. a = Required(str)
  3. b = Optional(int)
  4. composite_index(a, b)

You can use the attribute or the attribute name:

  1. class Example(db.Entity):
  2. a = Required(str)
  3. b = Optional(int)
  4. composite_index(a, 'b')

If you want to create a non-unique index for just one column, you can specify the index option of an attribute.

The composite index can include a discriminator attribute used for inheritance.