Dave Jarvis' Repositories

git clone https://repo.autonoma.ca/repo/recipe-books.git

Fleshed out database design.

Author Dave Jarvis <email>
Date 2013-01-22 23:08:47 GMT-0800
Commit b67024b59edb7ef003d4c2117349cf09f1925738
Parent 50a29e2
Delta 1287 lines added, 1035 lines removed, 252-line increase
recipe-book.dbs
-<?xml version="1.0" encoding="UTF-8" ?>
-<project name="recipe" version="42" database="PostgreSQL" >
- <schema name="public" catalogname="recipe" schemaname="public" defo="y" >
- <table name="xpath_relations" >
- <comment>Map of tables and columns to XPaths for use in creating XML documents.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;xpath_relations_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies each row.]]> </comment>
- </column>
- <column name="table_name" type="varchar" length="64" jt="12" >
- <comment> <![CDATA[Name of a table.]]> </comment>
- </column>
- <column name="column_name" type="varchar" length="64" jt="12" >
- <comment> <![CDATA[Name of a column in the table.]]> </comment>
- </column>
- <column name="relation" type="varchar" length="3" jt="12" >
- <comment> <![CDATA[Type of relationship between the table_ and column_name and XPath expression. For example: >, ->, =>.]]> </comment>
- </column>
- <column name="expression" type="varchar" length="128" jt="12" >
- <comment> <![CDATA[Expression that defines how to construct the XML document. This is usually an XPath expression, but could also be a fully qualified PK in a PK-FK relationship.]]> </comment>
- </column>
- <column name="document_name" type="varchar" length="64" jt="12" >
- <comment> <![CDATA[GROUP BY condition for the mapping.]]> </comment>
- </column>
- <column name="schema_name" type="varchar" length="64" jt="12" >
- <comment> <![CDATA[Name of a schema in which the table exists.]]> </comment>
- </column>
- <index name="pk_xpath_relations" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <sequence name="xpath_relations_id_seq" start="1" />
- <function name="execute_xpath" >
- <string> <![CDATA[CREATE OR REPLACE FUNCTION public.execute_xpath(document_name text)
- RETURNS text
- LANGUAGE plpgsql
-AS $function$
-BEGIN
-
-END;
-$function$
-]]> </string>
- </function>
- </schema>
- <schema name="recipe" schemaname="recipe" defo="y" >
- <table name="account" >
- <comment>List of accounts used by people to author recipes.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;accounts_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies each account.]]> </comment>
- </column>
- <column name="email" type="varchar" length="256" jt="12" mandatory="y" >
- <comment> <![CDATA[Email address associated with the account.]]> </comment>
- </column>
- <column name="created" type="date" jt="91" mandatory="y" >
- <defo>(&#039;now&#039;::text)::date</defo>
- <comment> <![CDATA[Date the account was created.]]> </comment>
- </column>
- <column name="updated" type="date" jt="91" >
- <comment> <![CDATA[Date the account was last updated.]]> </comment>
- </column>
- <column name="deleted" type="date" jt="91" >
- <comment> <![CDATA[Date the account was deleted.]]> </comment>
- </column>
- <index name="pk_accounts" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="action" >
- <comment>Name of an action that begins any given step.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;action_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the action.]]> </comment>
- </column>
- <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
- <comment> <![CDATA[Name of this action (e.g., cut, fry, mash, slice).]]> </comment>
- </column>
- <index name="pk_action" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="cuisine" >
- <comment>All known cuisines.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;cuisine_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the known cuisines.]]> </comment>
- </column>
- <column name="label" type="varchar" length="30" jt="12" mandatory="y" />
- <index name="pk_cuisine" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_cuisine_label" unique="UNIQUE" >
- <column name="label" />
- </index>
- </table>
- <table name="description" >
- <comment>Meta data about the recipe.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;description_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies this row.]]> </comment>
- </column>
- <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;description_recipe_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
- </column>
- <column name="cuisine_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;description_cuisine_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the known cuisines.]]> </comment>
- </column>
- <column name="title" type="varchar" length="55" jt="12" mandatory="y" >
- <comment> <![CDATA[Recipe title.]]> </comment>
- </column>
- <column name="diet_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;description_diet_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the row.]]> </comment>
- </column>
- <index name="pk_description" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_description" unique="NORMAL" >
- <column name="recipe_id" />
- </index>
- <index name="idx_description_0" unique="NORMAL" >
- <column name="cuisine_id" />
- </index>
- <index name="idx_description_1" unique="NORMAL" >
- <column name="diet_id" />
- </index>
- <fk name="fk_description" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
- <fk_column name="recipe_id" pk="id" />
- </fk>
- <fk name="fk_description_cuisine" to_schema="recipe" to_table="cuisine" delete_action="CASCADE" >
- <fk_column name="cuisine_id" pk="id" />
- </fk>
- <fk name="fk_description_diet" to_schema="recipe" to_table="diet" delete_action="CASCADE" >
- <fk_column name="diet_id" pk="id" />
- </fk>
- </table>
- <table name="diet" >
- <comment>Types of diets.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;diet_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the row.]]> </comment>
- </column>
- <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
- <comment> <![CDATA[The diet's name.]]> </comment>
- </column>
- <index name="pk_diet" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="direction" >
- <comment>Represents a single step in the set of directions that belong to a direction group.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;direction_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies this instruction.]]> </comment>
- </column>
- <column name="instruction" type="varchar" length="100" jt="12" mandatory="y" >
- <comment> <![CDATA[Each step in the directions should be a short blurb that describes what to do with the action.]]> </comment>
- </column>
- <column name="min_time" type="int2" jt="5" mandatory="y" >
- <defo>1</defo>
- <comment> <![CDATA[The minimum amount of time the step requires.]]> </comment>
- </column>
- <column name="max_time" type="int2" jt="5" >
- <comment> <![CDATA[The maximum amount of time the step requires.]]> </comment>
- </column>
- <column name="action_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;direction_action_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the action.]]> </comment>
- </column>
- <column name="direction_group_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;direction_direction_group_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Associates a step in directions with a group of directions.]]> </comment>
- </column>
- <column name="seq" type="int2" jt="5" mandatory="y" >
- <defo>1</defo>
- <comment> <![CDATA[Sequence of steps to complete the directions.]]> </comment>
- </column>
- <index name="pk_direction" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_direction" unique="NORMAL" >
- <column name="action_id" />
- </index>
- <index name="idx_direction_0" unique="NORMAL" >
- <column name="direction_group_id" />
- </index>
- <fk name="fk_direction" to_schema="recipe" to_table="action" delete_action="CASCADE" >
- <fk_column name="action_id" pk="id" />
- </fk>
- <fk name="fk_direction_group_direction_id" to_schema="recipe" to_table="direction_group" delete_action="CASCADE" >
- <fk_column name="direction_group_id" pk="id" />
- </fk>
- </table>
- <table name="direction_group" >
- <comment>Joins ingredient groups to recipes.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_ingredient_group_0_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the row that associates a recipe with an ingredient group.]]> </comment>
- </column>
- <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_direction_group_recipe_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
- </column>
- <column name="label" type="varchar" length="30" jt="12" mandatory="y" >
- <comment> <![CDATA[Name of a set of directions.]]> </comment>
- </column>
- <index name="pk_recipe_ingredient_group_0" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_recipe_direction_group" unique="NORMAL" >
- <column name="recipe_id" />
- </index>
- <fk name="fk_recipe_direction_group" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
- <fk_column name="recipe_id" pk="id" />
- </fk>
- </table>
- <table name="equipment" >
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;equipment_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the type of equipment required by a recipe.]]> </comment>
- </column>
- <column name="name" type="varchar" length="30" jt="12" mandatory="y" >
- <comment> <![CDATA[Name of the piece of equipment required to make this recipe.]]> </comment>
- </column>
- <column name="abridge" type="varchar" length="15" jt="12" >
- <comment> <![CDATA[Shorter name for this piece of equipment (the alias, were alias not a keyword).]]> </comment>
- </column>
- <column name="equipment_group_id" type="serial" jt="4" mandatory="y" >
- <defo>nextval(&#039;equipment_equipment_group_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the type of equipment.]]> </comment>
- </column>
- <column name="seq" type="int2" jt="5" mandatory="y" >
- <defo>1</defo>
- <comment> <![CDATA[Uniquely defines the order of each equipment object, independent of group.]]> </comment>
- </column>
- <index name="pk_eqiupment" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_equipment" unique="NORMAL" >
- <column name="equipment_group_id" />
- </index>
- <index name="uk_equipment" unique="UNIQUE" >
- <column name="name" />
- <column name="equipment_group_id" />
- </index>
- <fk name="fk_equipment" to_schema="recipe" to_table="equipment_group" delete_action="CASCADE" >
- <fk_column name="equipment_group_id" pk="id" />
- </fk>
- </table>
- <table name="equipment_group" >
- <column name="id" type="serial" jt="4" mandatory="y" >
- <defo>nextval(&#039;equipment_class_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the type of equipment.]]> </comment>
- </column>
- <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
- <comment> <![CDATA[cookware, bakeware, kitchenware, utensils, etc.]]> </comment>
- </column>
- <index name="pk_equipment_class" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="ingredient" >
- <comment>An ingredient that belongs to an ingredient group, which, in turn, belongs to a recipe.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the ingredient.]]> </comment>
- </column>
- <column name="ingredient_name_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_ingredient_name_id_seq&#039;::regclass)</defo>
- </column>
- <column name="ingredient_group_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_ingredient_group_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[The ingredient group that links to this ingredient.]]> </comment>
- </column>
- <column name="min_quantity" type="float4" jt="7" mandatory="y" >
- <comment> <![CDATA[Indicates how much of the ingredient that the recipe requires.]]> </comment>
- </column>
- <column name="max_quantity" type="float4" jt="7" >
- <comment> <![CDATA[Indicates the maximum amount of this ingredient that the recipe requires.]]> </comment>
- </column>
- <column name="scalar" type="int2" jt="5" >
- <comment> <![CDATA[Weight or length (modified by the unit of measurement).]]> </comment>
- </column>
- <column name="unit_id" type="bigserial" length="19" jt="-5" >
- <defo>nextval(&#039;ingredient_unit_id_seq1&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies this ingredient unit.]]> </comment>
- </column>
- <column name="condition" type="varchar" length="30" jt="12" >
- <comment> <![CDATA[Comma-separated initial preparations for this food item (e.g., "peeled,chopped").]]> </comment>
- </column>
- <column name="required" type="bool" jt="-7" mandatory="y" >
- <defo>true</defo>
- <comment> <![CDATA[Indicates whether the ingredient is optional.]]> </comment>
- </column>
- <column name="seq" type="int2" jt="5" mandatory="y" >
- <defo>1</defo>
- <comment> <![CDATA[Ingredient order (spans ingredient groups).]]> </comment>
- </column>
- <index name="pk_ingredient" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_ingredient_1" unique="NORMAL" >
- <column name="unit_id" />
- </index>
- <index name="idx_ingredient_2" unique="NORMAL" >
- <column name="ingredient_name_id" />
- </index>
- <index name="idx_ingredient" unique="NORMAL" >
- <column name="ingredient_group_id" />
- </index>
- <fk name="fk_ingredient_1" to_schema="recipe" to_table="ingredient_unit" delete_action="CASCADE" >
- <fk_column name="unit_id" pk="id" />
- </fk>
- <fk name="fk_ingredient_2" to_schema="recipe" to_table="ingredient_name" delete_action="CASCADE" >
- <fk_column name="ingredient_name_id" pk="id" />
- </fk>
- <fk name="fk_ingredient_group_id" to_schema="recipe" to_table="ingredient_group" delete_action="CASCADE" >
- <fk_column name="ingredient_group_id" pk="id" />
- </fk>
- </table>
- <table name="ingredient_group" >
- <comment>Joins ingredient groups to recipes.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_ingredient_group_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the row that associates a recipe with an ingredient group.]]> </comment>
- </column>
- <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_ingredient_group_recipe_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
- </column>
- <column name="label" type="varchar" length="30" jt="12" mandatory="y" >
- <comment> <![CDATA[Name of this ingredient group.]]> </comment>
- </column>
- <index name="pk_recipe_ingredient_group" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_recipe_ingredient_group" unique="NORMAL" >
- <column name="recipe_id" />
- </index>
- <fk name="fk_recipe_ingredient_group" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
- <fk_column name="recipe_id" pk="id" />
- </fk>
- </table>
- <table name="ingredient_name" >
- <comment>List of all the ingredient names in the world.</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_name_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the ingredient.]]> </comment>
- </column>
- <column name="label" type="varchar" length="30" jt="12" mandatory="y" >
- <comment> <![CDATA[Ingredient name.]]> </comment>
- </column>
- <column name="abridge" type="varchar" length="15" jt="12" >
- <comment> <![CDATA[Shorter name for the ingredient.]]> </comment>
- </column>
- <index name="pk_ingredient_name" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="uk_ingredient_label" unique="UNIQUE" >
- <column name="label" />
- </index>
- </table>
- <table name="ingredient_substitute" >
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_substitute_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the row.]]> </comment>
- </column>
- <column name="ingredient_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_substitute_ingredient_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[The ingredient that has an associated substitution.]]> </comment>
- </column>
- <column name="substitute_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_substitute_substitute_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[The ingredient that substitutes for ingredient_id.]]> </comment>
- </column>
- <index name="pk_ingredient_substitute" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_ingredient_substitute" unique="NORMAL" >
- <column name="ingredient_id" />
- </index>
- <index name="idx_ingredient_substitute_0" unique="NORMAL" >
- <column name="substitute_id" />
- </index>
- <fk name="fk_ingredient_substitute_ingredient" to_schema="recipe" to_table="ingredient" delete_action="CASCADE" >
- <fk_column name="ingredient_id" pk="id" />
- </fk>
- <fk name="fk_ingredient_substitute_substitute" to_schema="recipe" to_table="ingredient" delete_action="CASCADE" >
- <fk_column name="substitute_id" pk="id" />
- </fk>
- </table>
- <table name="ingredient_unit" >
- <comment>List of possible units (e.g., cup, teaspoon).</comment>
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;ingredient_unit_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies this ingredient unit.]]> </comment>
- </column>
- <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
- <comment> <![CDATA[Name of the unit (e.g., teaspoon, tablespoon).]]> </comment>
- </column>
- <index name="pk_unit" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="preparation" >
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;preparation_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies each row.]]> </comment>
- </column>
- <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;preparation_recipe_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Recipe that requires a prehated oven.]]> </comment>
- </column>
- <column name="temperature" type="float4" jt="7" mandatory="y" >
- <comment> <![CDATA[Oven temperature setting.]]> </comment>
- </column>
- <column name="unit" type="varchar" length="1" jt="12" mandatory="y" >
- <comment> <![CDATA[F, C, or K.]]> </comment>
- </column>
- <index name="pk_preparation" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_preparation" unique="NORMAL" >
- <column name="recipe_id" />
- </index>
- <fk name="fk_preparation_recipe" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
- <fk_column name="recipe_id" pk="id" />
- </fk>
- </table>
- <table name="recipe" >
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
- </column>
- <column name="account_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_account_id_seq1&#039;::regclass)</defo>
- <comment> <![CDATA[Recipe author.]]> </comment>
- </column>
- <column name="created" type="date" jt="91" mandatory="y" >
- <defo>(&#039;now&#039;::text)::date</defo>
- <comment> <![CDATA[When the recipe was inserted into the system.]]> </comment>
- </column>
- <column name="updated" type="date" jt="91" >
- <comment> <![CDATA[When the recipe was changed in the system.]]> </comment>
- </column>
- <column name="deleted" type="date" jt="91" >
- <comment> <![CDATA[When the recipe was deleted from the system.]]> </comment>
- </column>
- <index name="pk_recipe" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_recipe" unique="NORMAL" >
- <column name="account_id" />
- </index>
- <fk name="fk_recipe_account" to_schema="recipe" to_table="account" delete_action="CASCADE" >
- <fk_column name="account_id" pk="id" />
- </fk>
- </table>
- <table name="recipe_equipment_group" >
- <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_equipment_group_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies each row that associates a set of equipment with a recipe.]]> </comment>
- </column>
- <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
- <defo>nextval(&#039;recipe_equipment_group_recipe_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
- </column>
- <column name="equipment_group_id" type="serial" jt="4" mandatory="y" >
- <defo>nextval(&#039;recipe_equipment_group_equipment_group_id_seq&#039;::regclass)</defo>
- <comment> <![CDATA[Uniquely identifies the type of equipment.]]> </comment>
- </column>
- <index name="pk_recipe_equipment_group" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_recipe_equipment_group" unique="NORMAL" >
- <column name="recipe_id" />
- </index>
- <index name="idx_recipe_equipment_group_0" unique="NORMAL" >
- <column name="equipment_group_id" />
- </index>
- <fk name="fk_recipe_equipment_group" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
- <fk_column name="recipe_id" pk="id" />
- </fk>
- <fk name="fk_recipe_equipment_group_0" to_schema="recipe" to_table="equipment_group" delete_action="CASCADE" >
- <fk_column name="equipment_group_id" pk="id" />
- </fk>
- </table>
- <table name="result" >
- <column name="xmlelement" type="xml" jt="1111" />
- </table>
- <sequence name="accounts_id_seq" start="1" />
- <sequence name="action_id_seq" start="1" />
- <sequence name="cuisine_id_seq" start="1" />
- <sequence name="description_cuisine_id_seq" start="1" />
- <sequence name="description_diet_id_seq" start="1" />
- <sequence name="description_id_seq" start="1" />
- <sequence name="description_recipe_id_seq" start="1" />
- <sequence name="diet_id_seq" start="1" />
- <sequence name="direction_action_id_seq" start="1" />
- <sequence name="direction_direction_group_id_seq" start="1" />
- <sequence name="direction_id_seq" start="1" />
- <sequence name="equipment_class_id_seq" start="1" />
- <sequence name="equipment_equipment_group_id_seq" start="1" />
- <sequence name="equipment_id_seq" start="1" />
- <sequence name="ingredient_id_seq" start="1" />
- <sequence name="ingredient_ingredient_group_id_seq" start="1" />
- <sequence name="ingredient_ingredient_name_id_seq" start="1" />
- <sequence name="ingredient_name_id_seq" start="1" />
- <sequence name="ingredient_substitute_id_seq" start="1" />
- <sequence name="ingredient_substitute_ingredient_id_seq" start="1" />
- <sequence name="ingredient_substitute_substitute_id_seq" start="1" />
- <sequence name="ingredient_unit_id_seq" start="1" />
- <sequence name="ingredient_unit_id_seq1" start="1" />
- <sequence name="preparation_id_seq" start="1" />
- <sequence name="preparation_recipe_id_seq" start="1" />
- <sequence name="recipe_account_id_seq1" start="1" />
- <sequence name="recipe_direction_group_recipe_id_seq" start="1" />
- <sequence name="recipe_equipment_group_equipment_group_id_seq" start="1" />
- <sequence name="recipe_equipment_group_id_seq" start="1" />
- <sequence name="recipe_equipment_group_recipe_id_seq" start="1" />
- <sequence name="recipe_id_seq" start="1" />
- <sequence name="recipe_ingredient_group_0_id_seq" start="1" />
- <sequence name="recipe_ingredient_group_id_seq" start="1" />
- <sequence name="recipe_ingredient_group_recipe_id_seq" start="1" />
- <function name="generate_equipment_xml" >
- <string> <![CDATA[CREATE OR REPLACE FUNCTION recipe.generate_equipment_xml(recipe_id integer)
- RETURNS text
- LANGUAGE plpgsql
-AS $function$
-DECLARE
- result TEXT;
-BEGIN
-SELECT
- xmlelement( name equipment, xmlconcat( array_to_string( array_agg( t.xmlelement ), '' )::xml ) )
-INTO
- result
-FROM
-(
-SELECT
- xmlelement( name "bakeware",
- xmlconcat(
- array_to_string( array_agg(
- xmlelement( name "object",
- xmlattributes( e.abridge AS "alias" ),
- e.name
- )
- ), '')::xml
- )
- )
-FROM
- recipe.equipment_group eg,
- recipe.equipment e,
- recipe.recipe_equipment_group reg
-WHERE
- eg.label='bakeware' AND
- eg.id = e.equipment_group_id AND
- eg.id = reg.equipment_group_id AND
- reg.recipe_id = recipe_id
-UNION ALL
-SELECT
- xmlelement( name "cookware",
- xmlconcat(
- array_to_string( array_agg(
- xmlelement( name "object",
- xmlattributes( e.abridge AS "alias" ),
- e.name
- )
- ), '')::xml
- )
- )
-FROM
- recipe.equipment_group eg,
- recipe.equipment e,
- recipe.recipe_equipment_group reg
-WHERE
- eg.label='cookware' AND
- eg.id = e.equipment_group_id AND
- eg.id = reg.equipment_group_id AND
- reg.recipe_id = recipe_id
-UNION ALL
-SELECT
- xmlelement( name "kitchenware",
- xmlconcat(
- array_to_string( array_agg(
- xmlelement( name "object",
- xmlattributes( e.abridge AS "alias" ),
- e.name
- )
- ), '')::xml
- )
- )
-FROM
- recipe.equipment_group eg,
- recipe.equipment e,
- recipe.recipe_equipment_group reg
-WHERE
- eg.label='kitchenware' AND
- eg.id = e.equipment_group_id AND
- eg.id = reg.equipment_group_id AND
- reg.recipe_id = recipe_id
-UNION ALL
-SELECT
- xmlelement( name "utensils",
- xmlconcat(
- array_to_string( array_agg(
- xmlelement( name "object",
- xmlattributes( e.abridge AS "alias" ),
- e.name
- )
- ), '')::xml
- )
- )
-FROM
- recipe.equipment_group eg,
- recipe.equipment e,
- recipe.recipe_equipment_group reg
-WHERE
- eg.label='utensils' AND
- eg.id = e.equipment_group_id AND
- eg.id = reg.equipment_group_id AND
- reg.recipe_id = recipe_id
-) t;
- RETURN result;
-END;
-$function$
-]]> </string>
- </function>
- <function name="generate_ingredients_xml" >
- <string> <![CDATA[CREATE OR REPLACE FUNCTION recipe.generate_ingredients_xml(recipe_id integer)
- RETURNS text
- LANGUAGE plpgsql
-AS $function$
-DECLARE
- recipe_group_id INTEGER;
- ingredients_xml TEXT;
- ingredient_list TEXT;
- result TEXT;
-BEGIN
- result = '';
- /**
- * Remove this loop. It should be possible to build the entire
- * list of ingredients with a single SQL statement. This is an
- * optimization to do later.
- */
- FOR recipe_group_id IN
- SELECT
- rig.id
- FROM
- recipe.ingredient_group rig
- WHERE
- rig.recipe_id = recipe_id
- LOOP
- /* Build the inner <ingredient> elements, one per ingredient group. */
- SELECT
- array_to_string(
- array_agg(
- xmlelement( name "ingredient",
- xmlattributes(
- ri.id AS "id",
- ri.min_quantity AS "min-quantity",
- ri.max_quantity AS "max-quantity",
- riu.label AS "unit",
- ri.condition AS "condition",
- not(ri.required) AS "optional",
- rin.abridge AS "alias",
- ris.substitute_id AS "subtitute" ),
- rin.label
- ) ), '' )
- INTO
- ingredient_list
- FROM
- recipe.ingredient ri
- LEFT OUTER JOIN recipe.ingredient_unit riu ON
- ri.unit_id = riu.id
- LEFT OUTER JOIN recipe.ingredient_substitute ris ON
- ri.id = ris.ingredient_id
- INNER JOIN recipe.ingredient_group rig ON
- rig.id = ri.ingredient_group_id AND
- rig.id = recipe_group_id
- INNER JOIN recipe.ingredient_name rin ON
- rin.id = ri.ingredient_name_id;
- /* Build the outer <ingredients> elements around the ingredients_list elements. */
- SELECT
- xmlelement( name "ingredients",
- xmlattributes( rig.label AS "label" ),
- xmlconcat( ingredient_list::xml )
- )
- INTO
- ingredients_xml
- FROM
- recipe.ingredient_group rig
- WHERE
- rig.id = recipe_group_id;
- /* Append all the <ingredients> elements together. */
- result = result || ingredients_xml;
- END LOOP;
- RETURN result;
-END;
-$function$
-]]> </string>
- </function>
- <function name="generate_xml" >
- <string> <![CDATA[CREATE OR REPLACE FUNCTION recipe.generate_xml(recipe_id integer)
- RETURNS text
- LANGUAGE plpgsql
-AS $function$
-DECLARE
- result TEXT;
-BEGIN
- SELECT
- xmlelement( name recipe,
- xmlelement( name description,
- xmlelement( name title, d.title ),
- xmlelement( name diet, diet.label ) ),
- xmlelement( name equipment,
- xmlconcat( ('<'||eg.label||'>')::xml,
- xmlelement( name object,
- xmlattributes( e.abridge AS "alias" ) )
- )
- )
- )
- INTO
- result
- FROM
- recipe.recipe r,
- recipe.description d,
- recipe.diet diet,
- recipe.equipment e,
- recipe.equipment_group eg,
- recipe.recipe_equipment_group reg
- WHERE
- r.id = recipe_id AND
- r.id = d.recipe_id AND
- d.diet_id = diet.id AND
- r.id = reg.recipe_id AND
- reg.equipment_group_id = eg.id AND
- e.equipment_group_id = eg.id;
- RETURN result;
-END;
-$function$
-]]> </string>
- </function>
- </schema>
- <schema name="recipe_book" schemaname="recipe_book" defo="y" >
- <comment>Defines operations and data stores for information related to generating books.</comment>
- <table name="book" >
- <comment>Defines the common items to every book.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="label" type="varchar" length="128" jt="12" mandatory="y" >
- <comment> <![CDATA[Book title.]]> </comment>
- </column>
- <column name="spine_label" type="varchar" length="128" jt="12" mandatory="y" >
- <comment> <![CDATA[Book spine label.]]> </comment>
- </column>
- <column name="dedication" type="text" jt="12" >
- <comment> <![CDATA[Text for the dedication.]]> </comment>
- </column>
- <column name="isbn" type="varchar" length="13" jt="12" >
- <comment> <![CDATA[International standard book number and EAN, can be null.]]> </comment>
- </column>
- <column name="created" type="timestamptz" jt="93" mandatory="y" >
- <defo>current_timestamp</defo>
- <comment> <![CDATA[Date the book was created.]]> </comment>
- </column>
- <column name="deleted" type="timestamptz" jt="93" >
- <comment> <![CDATA[Date the book was (or is to be?) deleted.]]> </comment>
- </column>
- <column name="updated" type="timestamptz" jt="93" >
- <comment> <![CDATA[Date the book was last updated.]]> </comment>
- </column>
- <index name="pk_book" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="book_account" >
- <comment>Associates a book with an account.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="book_id" type="int4" jt="4" mandatory="y" >
- <comment> <![CDATA[The book associated with an account.]]> </comment>
- </column>
- <column name="account_id" type="int4" jt="4" mandatory="y" >
- <comment> <![CDATA[The account associated with a book.]]> </comment>
- </column>
- <index name="pk_book_account" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_book_account" unique="NORMAL" >
- <column name="book_id" />
- </index>
- <index name="idx_book_account_0" unique="NORMAL" >
- <column name="account_id" />
- </index>
- <fk name="fk_book_account_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
- <fk_column name="book_id" pk="id" />
- </fk>
- <fk name="fk_book_account_account_id" to_schema="recipe" to_table="account" delete_action="CASCADE" >
- <fk_column name="account_id" pk="id" />
- </fk>
- </table>
- <table name="book_photograph" >
- <comment>Describes attributes about a photograph that can be used in the book.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="book_id" type="int4" length="256" jt="4" mandatory="y" >
- <comment> <![CDATA[The book to which this photograph belongs.]]> </comment>
- </column>
- <column name="image_url" type="varchar" length="256" jt="12" mandatory="y" >
- <comment> <![CDATA[The website address where the image can be retrieved.]]> </comment>
- </column>
- <column name="book_photograph_category_id" type="int4" jt="4" mandatory="y" >
- <comment> <![CDATA[The type of photograph (e.g., cover page, meal inset, divider page, category section page).]]> </comment>
- </column>
- <index name="pk_book_photograph" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_book_photograph" unique="NORMAL" >
- <column name="book_id" />
- </index>
- <index name="idx_book_photograph_0" unique="NORMAL" >
- <column name="book_photograph_category_id" />
- </index>
- <fk name="fk_book_photograph_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
- <fk_column name="book_id" pk="id" />
- </fk>
- <fk name="fk_book_photograph_book_photograph_category_id" to_schema="recipe_book" to_table="book_photograph_category" delete_action="CASCADE" >
- <fk_column name="book_photograph_category_id" pk="id" />
- </fk>
- </table>
- <table name="book_photograph_category" >
- <comment>Contains a list of categories for book photographs.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="label" type="varchar" jt="12" mandatory="y" >
- <comment> <![CDATA[Text to display to the user.]]> </comment>
- </column>
- <column name="description" type="varchar" length="128" jt="12" mandatory="y" >
- <comment> <![CDATA[Brief description regarding how the category is used.]]> </comment>
- </column>
- <index name="pk_book_photograph_category" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="book_preamble" >
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <index name="pk_book_preamble" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="book_preamble_category" >
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <index name="pk_book_preamble_category" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="book_preference" >
- <comment>Stores configuration parameters used to generate the book (e.g., layout, fonts, colours). The system must select default values for a book. This table allows users to override the defaults. This indirectly drives the settings for generating a book.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="book_id" type="int4" jt="4" mandatory="y" >
- <comment> <![CDATA[The preference's reference to a book.]]> </comment>
- </column>
- <column name="book_preference_code_id" type="int4" jt="4" mandatory="y" >
- <comment> <![CDATA[Reference to the book preference code table.]]> </comment>
- </column>
- <index name="pk_book_preference" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_book_preference" unique="NORMAL" >
- <column name="book_id" />
- </index>
- <fk name="fk_book_preference_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
- <fk_column name="book_id" pk="id" />
- </fk>
- <fk name="fk_book_preference_book_preference_code_id" to_schema="recipe_book" to_table="book_preference_code" delete_action="CASCADE" >
- <fk_column name="book_id" pk="id" />
- </fk>
- </table>
- <table name="book_preference_code" >
- <comment>List of domains, codes, and values related to book preferences. If later need arises, this table can be split into separate tables to establish foreign key constraints.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="domain" type="varchar" length="32" jt="12" mandatory="y" >
- <comment> <![CDATA[Grouping for codes and values (e.g., BOOK_LAYOUT).]]> </comment>
- </column>
- <column name="code" type="varchar" length="32" jt="12" mandatory="y" >
- <comment> <![CDATA[Unique identifier within a given domain.]]> </comment>
- </column>
- <column name="label" type="varchar" jt="12" mandatory="y" >
- <comment> <![CDATA[Text that can be displayed to the user.]]> </comment>
- </column>
- <column name="description" type="varchar" length="128" jt="12" mandatory="y" >
- <comment> <![CDATA[Brief description about how the code is used.]]> </comment>
- </column>
- <index name="pk_book_preference_code" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- </table>
- <table name="book_recipe" >
- <comment>Associates a book with a recipe.</comment>
- <column name="id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Primary key.]]> </comment>
- </column>
- <column name="book_id" type="int4" jt="4" mandatory="y" >
- <comment> <![CDATA[Reference to the book table.]]> </comment>
- </column>
- <column name="recipe_id" type="serial" jt="4" mandatory="y" >
- <comment> <![CDATA[Reference to the recipe table.]]> </comment>
- </column>
- <index name="pk_book_recipe" unique="PRIMARY_KEY" >
- <column name="id" />
- </index>
- <index name="idx_book_recipe" unique="NORMAL" >
- <column name="recipe_id" />
- </index>
- <index name="idx_book_recipe_0" unique="NORMAL" >
- <column name="book_id" />
- </index>
- <fk name="fk_book_recipe_recipe_id" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
- <fk_column name="recipe_id" pk="id" />
- </fk>
- <fk name="fk_book_recipe_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
- <fk_column name="book_id" pk="id" />
- </fk>
- </table>
- </schema>
- <connector name="recipe" database="PostgreSQL" driver_class="org.postgresql.Driver" driver_jar="postgresql-8.4-701.jdbc3.jar" host="localhost" port="5432" instance="recipe" user="recipe" schema_mapping="information_schema:null;pg_catalog:null;pg_toast_temp_1:null;pg_toast_temp_3:null;public:null;recipe:null;recipe_book:null" />
- <layout name="Chaos" >
- <entity schema="recipe" name="account" x="481" y="416" />
- <entity schema="recipe" name="action" x="351" y="416" />
- <entity schema="recipe" name="cuisine" x="689" y="78" />
- <entity schema="recipe" name="description" x="637" y="416" />
- <entity schema="recipe" name="direction" x="481" y="221" />
- <entity schema="recipe" name="direction_group" x="806" y="416" />
- <entity schema="recipe" name="equipment" x="637" y="598" />
- <entity schema="recipe" name="equipment_group" x="273" y="273" />
- <entity schema="recipe" name="ingredient" x="260" y="598" />
- <entity schema="recipe" name="ingredient_group" x="806" y="260" />
- <entity schema="recipe" name="ingredient_name" x="858" y="598" />
- <entity schema="recipe" name="ingredient_substitute" x="39" y="117" />
- <entity schema="recipe" name="ingredient_unit" x="156" y="416" />
- <entity schema="recipe" name="recipe" x="481" y="39" />
- <entity schema="recipe" name="recipe_equipment_group" x="858" y="767" />
- <entity schema="recipe" name="result" x="312" y="91" />
- <callout x="91" y="78" pointer="SV" >
- <comment> <![CDATA[Use this layer for database synch.]]> </comment>
- </callout>
- </layout>
- <layout name="recipe_book" >
- <entity schema="recipe" name="account" x="637" y="39" />
- <entity schema="recipe_book" name="book" x="312" y="39" />
- <entity schema="recipe_book" name="book_account" x="455" y="39" />
- <entity schema="recipe_book" name="book_photograph" x="39" y="39" />
- <entity schema="recipe_book" name="book_photograph_category" x="39" y="260" />
- <entity schema="recipe_book" name="book_preamble" x="611" y="338" />
- <entity schema="recipe_book" name="book_preamble_category" x="611" y="429" />
- <entity schema="recipe_book" name="book_preference" x="260" y="260" />
- <entity schema="recipe_book" name="book_preference_code" x="273" y="377" />
- <entity schema="recipe_book" name="book_recipe" x="468" y="143" />
- <entity schema="recipe" name="recipe" x="637" y="182" />
- <group name="Book" color="33cc00" >
- <entity schema="recipe_book" name="book_account" />
- <entity schema="recipe_book" name="book_photograph" />
- <entity schema="recipe_book" name="book" />
- <entity schema="recipe_book" name="book_photograph_category" />
- <entity schema="recipe_book" name="book_preference" />
- <entity schema="recipe_book" name="book_preference_code" />
- <entity schema="recipe_book" name="book_recipe" />
- </group>
- <group name="Recipe" color="0066ff" >
- <entity schema="recipe" name="account" />
- <entity schema="recipe" name="recipe" />
- </group>
- <group name="Latex" color="cc00ff" >
- <entity schema="recipe_book" name="book_preamble_category" />
- <entity schema="recipe_book" name="book_preamble" />
- </group>
- </layout>
- <layout name="recipe_zeal" >
- <entity schema="recipe" name="account" x="195" y="377" />
- <entity schema="recipe" name="action" x="793" y="494" />
- <entity schema="recipe" name="cuisine" x="468" y="533" />
- <entity schema="recipe" name="description" x="325" y="546" />
- <entity schema="recipe" name="diet" x="468" y="624" />
- <entity schema="recipe" name="direction" x="598" y="494" />
- <entity schema="recipe" name="direction_group" x="598" y="377" />
- <entity schema="recipe" name="equipment" x="39" y="117" />
- <entity schema="recipe" name="equipment_group" x="234" y="117" />
- <entity schema="recipe" name="ingredient" x="468" y="156" />
- <entity schema="recipe" name="ingredient_group" x="468" y="39" />
- <entity schema="recipe" name="ingredient_name" x="689" y="234" />
- <entity schema="recipe" name="ingredient_substitute" x="689" y="143" />
- <entity schema="recipe" name="ingredient_unit" x="689" y="39" />
- <entity schema="recipe" name="preparation" x="468" y="416" />
- <entity schema="recipe" name="recipe" x="325" y="377" />
- <entity schema="recipe" name="recipe_equipment_group" x="195" y="234" />
- <group name="Recipe" color="ccffcc" >
- <entity schema="recipe" name="preparation" />
- <entity schema="recipe" name="cuisine" />
- <entity schema="recipe" name="diet" />
- <entity schema="recipe" name="direction_group" />
- <entity schema="recipe" name="action" />
- <entity schema="recipe" name="direction" />
- </group>
- <group name="Equipment" color="99ffff" >
- <entity schema="recipe" name="recipe_equipment_group" />
- <entity schema="recipe" name="equipment_group" />
- <entity schema="recipe" name="equipment" />
- </group>
- <group name="Ingredient" color="ccccff" >
- <entity schema="recipe" name="ingredient_name" />
- <entity schema="recipe" name="ingredient_group" />
- <entity schema="recipe" name="ingredient_unit" />
- <entity schema="recipe" name="ingredient_substitute" />
- <entity schema="recipe" name="ingredient" />
- </group>
- </layout>
- <layout name="Public" >
- <entity schema="public" name="xpath_relations" x="39" y="39" />
- </layout>
-</project>
+
sql/recipe-book.dbs
-
+<?xml version="1.0" encoding="UTF-8" ?>
+<project name="recipe" database="PostgreSQL" >
+ <schema name="public" catalogname="recipe" schemaname="public" defo="y" >
+ <table name="xpath_relations" >
+ <comment>Map of tables and columns to XPaths for use in creating XML documents.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;xpath_relations_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies each row.]]> </comment>
+ </column>
+ <column name="table_name" type="varchar" length="64" jt="12" >
+ <comment> <![CDATA[Name of a table.]]> </comment>
+ </column>
+ <column name="column_name" type="varchar" length="64" jt="12" >
+ <comment> <![CDATA[Name of a column in the table.]]> </comment>
+ </column>
+ <column name="relation" type="varchar" length="3" jt="12" >
+ <comment> <![CDATA[Type of relationship between the table_ and column_name and XPath expression. For example: >, ->, =>.]]> </comment>
+ </column>
+ <column name="expression" type="varchar" length="128" jt="12" >
+ <comment> <![CDATA[Expression that defines how to construct the XML document. This is usually an XPath expression, but could also be a fully qualified PK in a PK-FK relationship.]]> </comment>
+ </column>
+ <column name="document_name" type="varchar" length="64" jt="12" >
+ <comment> <![CDATA[GROUP BY condition for the mapping.]]> </comment>
+ </column>
+ <column name="schema_name" type="varchar" length="64" jt="12" >
+ <comment> <![CDATA[Name of a schema in which the table exists.]]> </comment>
+ </column>
+ <index name="pk_xpath_relations" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <sequence name="xpath_relations_id_seq" start="1" />
+ <function name="execute_xpath" >
+ <string> <![CDATA[CREATE OR REPLACE FUNCTION public.execute_xpath(document_name text)
+ RETURNS text
+ LANGUAGE plpgsql
+AS $function$
+BEGIN
+
+END;
+$function$
+]]> </string>
+ </function>
+ </schema>
+ <schema name="recipe" schemaname="recipe" defo="y" >
+ <table name="account" >
+ <comment>List of accounts used by people to author recipes.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;accounts_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies each account.]]> </comment>
+ </column>
+ <column name="email" type="varchar" length="256" jt="12" mandatory="y" >
+ <comment> <![CDATA[Email address associated with the account.]]> </comment>
+ </column>
+ <column name="created" type="date" jt="91" mandatory="y" >
+ <defo>(&#039;now&#039;::text)::date</defo>
+ <comment> <![CDATA[Date the account was created.]]> </comment>
+ </column>
+ <column name="updated" type="date" jt="91" >
+ <comment> <![CDATA[Date the account was last updated.]]> </comment>
+ </column>
+ <column name="deleted" type="date" jt="91" >
+ <comment> <![CDATA[Date the account was deleted.]]> </comment>
+ </column>
+ <index name="pk_accounts" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="action" >
+ <comment>Name of an action that begins any given step.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;action_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the action.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
+ <comment> <![CDATA[Name of this action (e.g., cut, fry, mash, slice).]]> </comment>
+ </column>
+ <index name="pk_action" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="cuisine" >
+ <comment>All known cuisines.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;cuisine_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the known cuisines.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="30" jt="12" mandatory="y" />
+ <index name="pk_cuisine" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_cuisine_label" unique="UNIQUE" >
+ <column name="label" />
+ </index>
+ </table>
+ <table name="description" >
+ <comment>Meta data about the recipe.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;description_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies this row.]]> </comment>
+ </column>
+ <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;description_recipe_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
+ </column>
+ <column name="cuisine_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;description_cuisine_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the known cuisines.]]> </comment>
+ </column>
+ <column name="title" type="varchar" length="55" jt="12" mandatory="y" >
+ <comment> <![CDATA[Recipe title.]]> </comment>
+ </column>
+ <column name="diet_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;description_diet_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the row.]]> </comment>
+ </column>
+ <index name="pk_description" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_description" unique="NORMAL" >
+ <column name="recipe_id" />
+ </index>
+ <index name="idx_description_0" unique="NORMAL" >
+ <column name="cuisine_id" />
+ </index>
+ <index name="idx_description_1" unique="NORMAL" >
+ <column name="diet_id" />
+ </index>
+ <fk name="fk_description" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
+ <fk_column name="recipe_id" pk="id" />
+ </fk>
+ <fk name="fk_description_cuisine" to_schema="recipe" to_table="cuisine" delete_action="CASCADE" >
+ <fk_column name="cuisine_id" pk="id" />
+ </fk>
+ <fk name="fk_description_diet" to_schema="recipe" to_table="diet" delete_action="CASCADE" >
+ <fk_column name="diet_id" pk="id" />
+ </fk>
+ </table>
+ <table name="diet" >
+ <comment>Types of diets.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;diet_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the row.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
+ <comment> <![CDATA[The diet's name.]]> </comment>
+ </column>
+ <index name="pk_diet" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="direction" >
+ <comment>Represents a single step in the set of directions that belong to a direction group.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;direction_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies this instruction.]]> </comment>
+ </column>
+ <column name="instruction" type="varchar" length="100" jt="12" mandatory="y" >
+ <comment> <![CDATA[Each step in the directions should be a short blurb that describes what to do with the action.]]> </comment>
+ </column>
+ <column name="min_time" type="int2" jt="5" mandatory="y" >
+ <defo>1</defo>
+ <comment> <![CDATA[The minimum amount of time the step requires.]]> </comment>
+ </column>
+ <column name="max_time" type="int2" jt="5" >
+ <comment> <![CDATA[The maximum amount of time the step requires.]]> </comment>
+ </column>
+ <column name="action_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;direction_action_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the action.]]> </comment>
+ </column>
+ <column name="direction_group_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;direction_direction_group_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Associates a step in directions with a group of directions.]]> </comment>
+ </column>
+ <column name="seq" type="int2" jt="5" mandatory="y" >
+ <defo>1</defo>
+ <comment> <![CDATA[Sequence of steps to complete the directions.]]> </comment>
+ </column>
+ <index name="pk_direction" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_direction" unique="NORMAL" >
+ <column name="action_id" />
+ </index>
+ <index name="idx_direction_0" unique="NORMAL" >
+ <column name="direction_group_id" />
+ </index>
+ <fk name="fk_direction" to_schema="recipe" to_table="action" delete_action="CASCADE" >
+ <fk_column name="action_id" pk="id" />
+ </fk>
+ <fk name="fk_direction_group_direction_id" to_schema="recipe" to_table="direction_group" delete_action="CASCADE" >
+ <fk_column name="direction_group_id" pk="id" />
+ </fk>
+ </table>
+ <table name="direction_group" >
+ <comment>Joins ingredient groups to recipes.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_ingredient_group_0_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the row that associates a recipe with an ingredient group.]]> </comment>
+ </column>
+ <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_direction_group_recipe_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="30" jt="12" mandatory="y" >
+ <comment> <![CDATA[Name of a set of directions.]]> </comment>
+ </column>
+ <index name="pk_recipe_ingredient_group_0" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_recipe_direction_group" unique="NORMAL" >
+ <column name="recipe_id" />
+ </index>
+ <fk name="fk_recipe_direction_group" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
+ <fk_column name="recipe_id" pk="id" />
+ </fk>
+ </table>
+ <table name="equipment" >
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;equipment_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the type of equipment required by a recipe.]]> </comment>
+ </column>
+ <column name="name" type="varchar" length="30" jt="12" mandatory="y" >
+ <comment> <![CDATA[Name of the piece of equipment required to make this recipe.]]> </comment>
+ </column>
+ <column name="abridge" type="varchar" length="15" jt="12" >
+ <comment> <![CDATA[Shorter name for this piece of equipment (the alias, were alias not a keyword).]]> </comment>
+ </column>
+ <column name="equipment_group_id" type="serial" jt="4" mandatory="y" >
+ <defo>nextval(&#039;equipment_equipment_group_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the type of equipment.]]> </comment>
+ </column>
+ <column name="seq" type="int2" jt="5" mandatory="y" >
+ <defo>1</defo>
+ <comment> <![CDATA[Uniquely defines the order of each equipment object, independent of group.]]> </comment>
+ </column>
+ <index name="pk_eqiupment" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_equipment" unique="NORMAL" >
+ <column name="equipment_group_id" />
+ </index>
+ <index name="uk_equipment" unique="UNIQUE" >
+ <column name="name" />
+ <column name="equipment_group_id" />
+ </index>
+ <fk name="fk_equipment" to_schema="recipe" to_table="equipment_group" delete_action="CASCADE" >
+ <fk_column name="equipment_group_id" pk="id" />
+ </fk>
+ </table>
+ <table name="equipment_group" >
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <defo>nextval(&#039;equipment_class_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the type of equipment.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
+ <comment> <![CDATA[cookware, bakeware, kitchenware, utensils, etc.]]> </comment>
+ </column>
+ <index name="pk_equipment_class" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="ingredient" >
+ <comment>An ingredient that belongs to an ingredient group, which, in turn, belongs to a recipe.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the ingredient.]]> </comment>
+ </column>
+ <column name="ingredient_name_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_ingredient_name_id_seq&#039;::regclass)</defo>
+ </column>
+ <column name="ingredient_group_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_ingredient_group_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[The ingredient group that links to this ingredient.]]> </comment>
+ </column>
+ <column name="min_quantity" type="float4" jt="7" mandatory="y" >
+ <comment> <![CDATA[Indicates how much of the ingredient that the recipe requires.]]> </comment>
+ </column>
+ <column name="max_quantity" type="float4" jt="7" >
+ <comment> <![CDATA[Indicates the maximum amount of this ingredient that the recipe requires.]]> </comment>
+ </column>
+ <column name="scalar" type="int2" jt="5" >
+ <comment> <![CDATA[Weight or length (modified by the unit of measurement).]]> </comment>
+ </column>
+ <column name="unit_id" type="bigserial" length="19" jt="-5" >
+ <defo>nextval(&#039;ingredient_unit_id_seq1&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies this ingredient unit.]]> </comment>
+ </column>
+ <column name="condition" type="varchar" length="30" jt="12" >
+ <comment> <![CDATA[Comma-separated initial preparations for this food item (e.g., "peeled,chopped").]]> </comment>
+ </column>
+ <column name="required" type="bool" jt="-7" mandatory="y" >
+ <defo>true</defo>
+ <comment> <![CDATA[Indicates whether the ingredient is optional.]]> </comment>
+ </column>
+ <column name="seq" type="int2" jt="5" mandatory="y" >
+ <defo>1</defo>
+ <comment> <![CDATA[Ingredient order (spans ingredient groups).]]> </comment>
+ </column>
+ <index name="pk_ingredient" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_ingredient_1" unique="NORMAL" >
+ <column name="unit_id" />
+ </index>
+ <index name="idx_ingredient_2" unique="NORMAL" >
+ <column name="ingredient_name_id" />
+ </index>
+ <index name="idx_ingredient" unique="NORMAL" >
+ <column name="ingredient_group_id" />
+ </index>
+ <fk name="fk_ingredient_1" to_schema="recipe" to_table="ingredient_unit" delete_action="CASCADE" >
+ <fk_column name="unit_id" pk="id" />
+ </fk>
+ <fk name="fk_ingredient_2" to_schema="recipe" to_table="ingredient_name" delete_action="CASCADE" >
+ <fk_column name="ingredient_name_id" pk="id" />
+ </fk>
+ <fk name="fk_ingredient_group_id" to_schema="recipe" to_table="ingredient_group" delete_action="CASCADE" >
+ <fk_column name="ingredient_group_id" pk="id" />
+ </fk>
+ </table>
+ <table name="ingredient_group" >
+ <comment>Joins ingredient groups to recipes.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_ingredient_group_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the row that associates a recipe with an ingredient group.]]> </comment>
+ </column>
+ <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_ingredient_group_recipe_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="30" jt="12" mandatory="y" >
+ <comment> <![CDATA[Name of this ingredient group.]]> </comment>
+ </column>
+ <index name="pk_recipe_ingredient_group" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_recipe_ingredient_group" unique="NORMAL" >
+ <column name="recipe_id" />
+ </index>
+ <fk name="fk_recipe_ingredient_group" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
+ <fk_column name="recipe_id" pk="id" />
+ </fk>
+ </table>
+ <table name="ingredient_name" >
+ <comment>List of all the ingredient names in the world.</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_name_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the ingredient.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="30" jt="12" mandatory="y" >
+ <comment> <![CDATA[Ingredient name.]]> </comment>
+ </column>
+ <column name="abridge" type="varchar" length="15" jt="12" >
+ <comment> <![CDATA[Shorter name for the ingredient.]]> </comment>
+ </column>
+ <index name="pk_ingredient_name" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="uk_ingredient_label" unique="UNIQUE" >
+ <column name="label" />
+ </index>
+ </table>
+ <table name="ingredient_substitute" >
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_substitute_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the row.]]> </comment>
+ </column>
+ <column name="ingredient_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_substitute_ingredient_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[The ingredient that has an associated substitution.]]> </comment>
+ </column>
+ <column name="substitute_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_substitute_substitute_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[The ingredient that substitutes for ingredient_id.]]> </comment>
+ </column>
+ <index name="pk_ingredient_substitute" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_ingredient_substitute" unique="NORMAL" >
+ <column name="ingredient_id" />
+ </index>
+ <index name="idx_ingredient_substitute_0" unique="NORMAL" >
+ <column name="substitute_id" />
+ </index>
+ <fk name="fk_ingredient_substitute_ingredient" to_schema="recipe" to_table="ingredient" delete_action="CASCADE" >
+ <fk_column name="ingredient_id" pk="id" />
+ </fk>
+ <fk name="fk_ingredient_substitute_substitute" to_schema="recipe" to_table="ingredient" delete_action="CASCADE" >
+ <fk_column name="substitute_id" pk="id" />
+ </fk>
+ </table>
+ <table name="ingredient_unit" >
+ <comment>List of possible units (e.g., cup, teaspoon).</comment>
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;ingredient_unit_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies this ingredient unit.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="15" jt="12" mandatory="y" >
+ <comment> <![CDATA[Name of the unit (e.g., teaspoon, tablespoon).]]> </comment>
+ </column>
+ <index name="pk_unit" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="preparation" >
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;preparation_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies each row.]]> </comment>
+ </column>
+ <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;preparation_recipe_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Recipe that requires a prehated oven.]]> </comment>
+ </column>
+ <column name="temperature" type="float4" jt="7" mandatory="y" >
+ <comment> <![CDATA[Oven temperature setting.]]> </comment>
+ </column>
+ <column name="unit" type="varchar" length="1" jt="12" mandatory="y" >
+ <comment> <![CDATA[F, C, or K.]]> </comment>
+ </column>
+ <index name="pk_preparation" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_preparation" unique="NORMAL" >
+ <column name="recipe_id" />
+ </index>
+ <fk name="fk_preparation_recipe" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
+ <fk_column name="recipe_id" pk="id" />
+ </fk>
+ </table>
+ <table name="recipe" >
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
+ </column>
+ <column name="account_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_account_id_seq1&#039;::regclass)</defo>
+ <comment> <![CDATA[Recipe author.]]> </comment>
+ </column>
+ <column name="created" type="date" jt="91" mandatory="y" >
+ <defo>(&#039;now&#039;::text)::date</defo>
+ <comment> <![CDATA[When the recipe was inserted into the system.]]> </comment>
+ </column>
+ <column name="updated" type="date" jt="91" >
+ <comment> <![CDATA[When the recipe was changed in the system.]]> </comment>
+ </column>
+ <column name="deleted" type="date" jt="91" >
+ <comment> <![CDATA[When the recipe was deleted from the system.]]> </comment>
+ </column>
+ <index name="pk_recipe" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_recipe" unique="NORMAL" >
+ <column name="account_id" />
+ </index>
+ <fk name="fk_recipe_account" to_schema="recipe" to_table="account" delete_action="CASCADE" >
+ <fk_column name="account_id" pk="id" />
+ </fk>
+ </table>
+ <table name="recipe_equipment_group" >
+ <column name="id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_equipment_group_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies each row that associates a set of equipment with a recipe.]]> </comment>
+ </column>
+ <column name="recipe_id" type="bigserial" length="19" jt="-5" mandatory="y" >
+ <defo>nextval(&#039;recipe_equipment_group_recipe_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Every recipe is uniquely identified.]]> </comment>
+ </column>
+ <column name="equipment_group_id" type="serial" jt="4" mandatory="y" >
+ <defo>nextval(&#039;recipe_equipment_group_equipment_group_id_seq&#039;::regclass)</defo>
+ <comment> <![CDATA[Uniquely identifies the type of equipment.]]> </comment>
+ </column>
+ <index name="pk_recipe_equipment_group" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_recipe_equipment_group" unique="NORMAL" >
+ <column name="recipe_id" />
+ </index>
+ <index name="idx_recipe_equipment_group_0" unique="NORMAL" >
+ <column name="equipment_group_id" />
+ </index>
+ <fk name="fk_recipe_equipment_group" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
+ <fk_column name="recipe_id" pk="id" />
+ </fk>
+ <fk name="fk_recipe_equipment_group_0" to_schema="recipe" to_table="equipment_group" delete_action="CASCADE" >
+ <fk_column name="equipment_group_id" pk="id" />
+ </fk>
+ </table>
+ <table name="result" >
+ <column name="xmlelement" type="xml" jt="1111" />
+ </table>
+ <sequence name="accounts_id_seq" start="1" />
+ <sequence name="action_id_seq" start="1" />
+ <sequence name="cuisine_id_seq" start="1" />
+ <sequence name="description_cuisine_id_seq" start="1" />
+ <sequence name="description_diet_id_seq" start="1" />
+ <sequence name="description_id_seq" start="1" />
+ <sequence name="description_recipe_id_seq" start="1" />
+ <sequence name="diet_id_seq" start="1" />
+ <sequence name="direction_action_id_seq" start="1" />
+ <sequence name="direction_direction_group_id_seq" start="1" />
+ <sequence name="direction_id_seq" start="1" />
+ <sequence name="equipment_class_id_seq" start="1" />
+ <sequence name="equipment_equipment_group_id_seq" start="1" />
+ <sequence name="equipment_id_seq" start="1" />
+ <sequence name="ingredient_id_seq" start="1" />
+ <sequence name="ingredient_ingredient_group_id_seq" start="1" />
+ <sequence name="ingredient_ingredient_name_id_seq" start="1" />
+ <sequence name="ingredient_name_id_seq" start="1" />
+ <sequence name="ingredient_substitute_id_seq" start="1" />
+ <sequence name="ingredient_substitute_ingredient_id_seq" start="1" />
+ <sequence name="ingredient_substitute_substitute_id_seq" start="1" />
+ <sequence name="ingredient_unit_id_seq" start="1" />
+ <sequence name="ingredient_unit_id_seq1" start="1" />
+ <sequence name="preparation_id_seq" start="1" />
+ <sequence name="preparation_recipe_id_seq" start="1" />
+ <sequence name="recipe_account_id_seq1" start="1" />
+ <sequence name="recipe_direction_group_recipe_id_seq" start="1" />
+ <sequence name="recipe_equipment_group_equipment_group_id_seq" start="1" />
+ <sequence name="recipe_equipment_group_id_seq" start="1" />
+ <sequence name="recipe_equipment_group_recipe_id_seq" start="1" />
+ <sequence name="recipe_id_seq" start="1" />
+ <sequence name="recipe_ingredient_group_0_id_seq" start="1" />
+ <sequence name="recipe_ingredient_group_id_seq" start="1" />
+ <sequence name="recipe_ingredient_group_recipe_id_seq" start="1" />
+ <function name="generate_equipment_xml" >
+ <string> <![CDATA[CREATE OR REPLACE FUNCTION recipe.generate_equipment_xml(recipe_id integer)
+ RETURNS text
+ LANGUAGE plpgsql
+AS $function$
+DECLARE
+ result TEXT;
+BEGIN
+SELECT
+ xmlelement( name equipment, xmlconcat( array_to_string( array_agg( t.xmlelement ), '' )::xml ) )
+INTO
+ result
+FROM
+(
+SELECT
+ xmlelement( name "bakeware",
+ xmlconcat(
+ array_to_string( array_agg(
+ xmlelement( name "object",
+ xmlattributes( e.abridge AS "alias" ),
+ e.name
+ )
+ ), '')::xml
+ )
+ )
+FROM
+ recipe.equipment_group eg,
+ recipe.equipment e,
+ recipe.recipe_equipment_group reg
+WHERE
+ eg.label='bakeware' AND
+ eg.id = e.equipment_group_id AND
+ eg.id = reg.equipment_group_id AND
+ reg.recipe_id = recipe_id
+UNION ALL
+SELECT
+ xmlelement( name "cookware",
+ xmlconcat(
+ array_to_string( array_agg(
+ xmlelement( name "object",
+ xmlattributes( e.abridge AS "alias" ),
+ e.name
+ )
+ ), '')::xml
+ )
+ )
+FROM
+ recipe.equipment_group eg,
+ recipe.equipment e,
+ recipe.recipe_equipment_group reg
+WHERE
+ eg.label='cookware' AND
+ eg.id = e.equipment_group_id AND
+ eg.id = reg.equipment_group_id AND
+ reg.recipe_id = recipe_id
+UNION ALL
+SELECT
+ xmlelement( name "kitchenware",
+ xmlconcat(
+ array_to_string( array_agg(
+ xmlelement( name "object",
+ xmlattributes( e.abridge AS "alias" ),
+ e.name
+ )
+ ), '')::xml
+ )
+ )
+FROM
+ recipe.equipment_group eg,
+ recipe.equipment e,
+ recipe.recipe_equipment_group reg
+WHERE
+ eg.label='kitchenware' AND
+ eg.id = e.equipment_group_id AND
+ eg.id = reg.equipment_group_id AND
+ reg.recipe_id = recipe_id
+UNION ALL
+SELECT
+ xmlelement( name "utensils",
+ xmlconcat(
+ array_to_string( array_agg(
+ xmlelement( name "object",
+ xmlattributes( e.abridge AS "alias" ),
+ e.name
+ )
+ ), '')::xml
+ )
+ )
+FROM
+ recipe.equipment_group eg,
+ recipe.equipment e,
+ recipe.recipe_equipment_group reg
+WHERE
+ eg.label='utensils' AND
+ eg.id = e.equipment_group_id AND
+ eg.id = reg.equipment_group_id AND
+ reg.recipe_id = recipe_id
+) t;
+ RETURN result;
+END;
+$function$
+]]> </string>
+ </function>
+ <function name="generate_ingredients_xml" >
+ <string> <![CDATA[CREATE OR REPLACE FUNCTION recipe.generate_ingredients_xml(recipe_id integer)
+ RETURNS text
+ LANGUAGE plpgsql
+AS $function$
+DECLARE
+ recipe_group_id INTEGER;
+ ingredients_xml TEXT;
+ ingredient_list TEXT;
+ result TEXT;
+BEGIN
+ result = '';
+ /**
+ * Remove this loop. It should be possible to build the entire
+ * list of ingredients with a single SQL statement. This is an
+ * optimization to do later.
+ */
+ FOR recipe_group_id IN
+ SELECT
+ rig.id
+ FROM
+ recipe.ingredient_group rig
+ WHERE
+ rig.recipe_id = recipe_id
+ LOOP
+ /* Build the inner <ingredient> elements, one per ingredient group. */
+ SELECT
+ array_to_string(
+ array_agg(
+ xmlelement( name "ingredient",
+ xmlattributes(
+ ri.id AS "id",
+ ri.min_quantity AS "min-quantity",
+ ri.max_quantity AS "max-quantity",
+ riu.label AS "unit",
+ ri.condition AS "condition",
+ not(ri.required) AS "optional",
+ rin.abridge AS "alias",
+ ris.substitute_id AS "subtitute" ),
+ rin.label
+ ) ), '' )
+ INTO
+ ingredient_list
+ FROM
+ recipe.ingredient ri
+ LEFT OUTER JOIN recipe.ingredient_unit riu ON
+ ri.unit_id = riu.id
+ LEFT OUTER JOIN recipe.ingredient_substitute ris ON
+ ri.id = ris.ingredient_id
+ INNER JOIN recipe.ingredient_group rig ON
+ rig.id = ri.ingredient_group_id AND
+ rig.id = recipe_group_id
+ INNER JOIN recipe.ingredient_name rin ON
+ rin.id = ri.ingredient_name_id;
+ /* Build the outer <ingredients> elements around the ingredients_list elements. */
+ SELECT
+ xmlelement( name "ingredients",
+ xmlattributes( rig.label AS "label" ),
+ xmlconcat( ingredient_list::xml )
+ )
+ INTO
+ ingredients_xml
+ FROM
+ recipe.ingredient_group rig
+ WHERE
+ rig.id = recipe_group_id;
+ /* Append all the <ingredients> elements together. */
+ result = result || ingredients_xml;
+ END LOOP;
+ RETURN result;
+END;
+$function$
+]]> </string>
+ </function>
+ <function name="generate_xml" >
+ <string> <![CDATA[CREATE OR REPLACE FUNCTION recipe.generate_xml(recipe_id integer)
+ RETURNS text
+ LANGUAGE plpgsql
+AS $function$
+DECLARE
+ result TEXT;
+BEGIN
+ SELECT
+ xmlelement( name recipe,
+ xmlelement( name description,
+ xmlelement( name title, d.title ),
+ xmlelement( name diet, diet.label ) ),
+ xmlelement( name equipment,
+ xmlconcat( ('<'||eg.label||'>')::xml,
+ xmlelement( name object,
+ xmlattributes( e.abridge AS "alias" ) )
+ )
+ )
+ )
+ INTO
+ result
+ FROM
+ recipe.recipe r,
+ recipe.description d,
+ recipe.diet diet,
+ recipe.equipment e,
+ recipe.equipment_group eg,
+ recipe.recipe_equipment_group reg
+ WHERE
+ r.id = recipe_id AND
+ r.id = d.recipe_id AND
+ d.diet_id = diet.id AND
+ r.id = reg.recipe_id AND
+ reg.equipment_group_id = eg.id AND
+ e.equipment_group_id = eg.id;
+ RETURN result;
+END;
+$function$
+]]> </string>
+ </function>
+ </schema>
+ <schema name="recipe_book" schemaname="recipe_book" defo="y" >
+ <comment>Defines operations and data stores for information related to generating books.</comment>
+ <table name="book" >
+ <comment>Defines the common items to every book.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="128" jt="12" mandatory="y" >
+ <comment> <![CDATA[Book title.]]> </comment>
+ </column>
+ <column name="spine_label" type="varchar" length="128" jt="12" mandatory="y" >
+ <comment> <![CDATA[Book spine label.]]> </comment>
+ </column>
+ <column name="dedication" type="text" jt="12" >
+ <comment> <![CDATA[Text for the dedication.]]> </comment>
+ </column>
+ <column name="isbn" type="varchar" length="13" jt="12" >
+ <comment> <![CDATA[International standard book number and EAN, can be null.]]> </comment>
+ </column>
+ <column name="created" type="timestamptz" jt="93" mandatory="y" >
+ <defo>current_timestamp</defo>
+ <comment> <![CDATA[Date the book was created.]]> </comment>
+ </column>
+ <column name="deleted" type="timestamptz" jt="93" >
+ <comment> <![CDATA[Date the book was (or is to be?) deleted.]]> </comment>
+ </column>
+ <column name="updated" type="timestamptz" jt="93" >
+ <comment> <![CDATA[Date the book was last updated.]]> </comment>
+ </column>
+ <index name="pk_book" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="book_account" >
+ <comment>Associates a book with an account.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="book_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[The book associated with an account.]]> </comment>
+ </column>
+ <column name="account_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[The account associated with a book.]]> </comment>
+ </column>
+ <index name="pk_book_account" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_book_account" unique="NORMAL" >
+ <column name="book_id" />
+ </index>
+ <index name="idx_book_account_0" unique="NORMAL" >
+ <column name="account_id" />
+ </index>
+ <fk name="fk_book_account_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
+ <fk_column name="book_id" pk="id" />
+ </fk>
+ <fk name="fk_book_account_account_id" to_schema="recipe" to_table="account" delete_action="CASCADE" >
+ <fk_column name="account_id" pk="id" />
+ </fk>
+ </table>
+ <table name="book_photograph" >
+ <comment>Describes attributes about a photograph that can be used in the book.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="book_id" type="int4" length="256" jt="4" mandatory="y" >
+ <comment> <![CDATA[The book to which this photograph belongs.]]> </comment>
+ </column>
+ <column name="image_url" type="varchar" length="2048" jt="12" mandatory="y" >
+ <comment> <![CDATA[The website address where the image can be retrieved.]]> </comment>
+ </column>
+ <column name="book_photograph_category_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[The type of photograph (e.g., cover page, meal inset, divider page, category section page).]]> </comment>
+ </column>
+ <index name="pk_book_photograph" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_book_photograph" unique="NORMAL" >
+ <column name="book_id" />
+ </index>
+ <index name="idx_book_photograph_0" unique="NORMAL" >
+ <column name="book_photograph_category_id" />
+ </index>
+ <fk name="fk_book_photograph_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
+ <fk_column name="book_id" pk="id" />
+ </fk>
+ <fk name="fk_book_photograph_book_photograph_category_id" to_schema="recipe_book" to_table="book_photograph_category" delete_action="CASCADE" >
+ <fk_column name="book_photograph_category_id" pk="id" />
+ </fk>
+ </table>
+ <table name="book_photograph_category" >
+ <comment>Contains a list of categories for book photographs.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="label" type="varchar" jt="12" mandatory="y" >
+ <comment> <![CDATA[Text to display to the user.]]> </comment>
+ </column>
+ <column name="description" type="varchar" length="128" jt="12" mandatory="y" >
+ <comment> <![CDATA[Brief description regarding how the category is used.]]> </comment>
+ </column>
+ <index name="pk_book_photograph_category" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ </table>
+ <table name="book_latex" >
+ <comment>Associates LaTeX code with a book preference.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="book_preference_code_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[Associates LaTeX source code with a book preference code.]]> </comment>
+ </column>
+ <column name="latex" type="text" jt="12" mandatory="y" >
+ <comment> <![CDATA[Source code associated with a configurable preference.]]> </comment>
+ </column>
+ <index name="pk_book_preamble" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_book_latex" unique="NORMAL" >
+ <column name="book_preference_code_id" />
+ </index>
+ <fk name="fk_book_latex_book_preference_code" to_schema="recipe_book" to_table="book_preference_code" delete_action="CASCADE" >
+ <fk_column name="book_preference_code_id" pk="id" />
+ <comment> <![CDATA[Associates LaTeX code with a book preference.]]> </comment>
+ </fk>
+ </table>
+ <table name="book_preference" >
+ <comment>Stores configuration parameters used to generate the book (e.g., layout, fonts, colours). The system must select default values for a book. This table allows users to override the defaults. This indirectly drives the settings for generating a book.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="book_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[The preference's reference to a book.]]> </comment>
+ </column>
+ <column name="book_preference_code_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[Reference to the book preference code table.]]> </comment>
+ </column>
+ <index name="pk_book_preference" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_book_preference" unique="NORMAL" >
+ <column name="book_id" />
+ </index>
+ <fk name="fk_book_preference_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
+ <fk_column name="book_id" pk="id" />
+ </fk>
+ <fk name="fk_book_preference_book_preference_code_id" to_schema="recipe_book" to_table="book_preference_code" delete_action="CASCADE" >
+ <fk_column name="book_id" pk="id" />
+ </fk>
+ </table>
+ <table name="book_preference_code" >
+ <comment>List of domains, codes, and values related to book preferences. If later need arises, this table can be split into separate tables to establish foreign key constraints.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="domain" type="varchar" length="32" jt="12" mandatory="y" >
+ <comment> <![CDATA[Grouping for codes and values (e.g., COLOUR_SCHEME).]]> </comment>
+ </column>
+ <column name="code" type="varchar" length="32" jt="12" mandatory="y" >
+ <comment> <![CDATA[Unique identifier within a given domain (e.g., BLUEBERRY).]]> </comment>
+ </column>
+ <column name="label" type="varchar" length="32" jt="12" mandatory="y" >
+ <comment> <![CDATA[Text that can be displayed to the user (e.g., Blueberry).]]> </comment>
+ </column>
+ <column name="description" type="varchar" length="128" jt="12" mandatory="y" >
+ <comment> <![CDATA[Brief description about how the code is used.]]> </comment>
+ </column>
+ <index name="pk_book_preference_code" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_book_preference_code" unique="NORMAL" >
+ <column name="domain" />
+ </index>
+ <fk name="fk_book_preference_code_domain" to_schema="recipe_book" to_table="book_theme_name" delete_action="CASCADE" >
+ <fk_column name="domain" pk="domain" />
+ </fk>
+ </table>
+ <table name="book_recipe" >
+ <comment>Associates a book with a recipe.</comment>
+ <column name="id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="book_id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[Reference to the book table.]]> </comment>
+ </column>
+ <column name="recipe_id" type="serial" jt="4" mandatory="y" >
+ <comment> <![CDATA[Reference to the recipe table.]]> </comment>
+ </column>
+ <index name="pk_book_recipe" unique="PRIMARY_KEY" >
+ <column name="id" />
+ </index>
+ <index name="idx_book_recipe" unique="NORMAL" >
+ <column name="recipe_id" />
+ </index>
+ <index name="idx_book_recipe_0" unique="NORMAL" >
+ <column name="book_id" />
+ </index>
+ <fk name="fk_book_recipe_recipe_id" to_schema="recipe" to_table="recipe" delete_action="CASCADE" >
+ <fk_column name="recipe_id" pk="id" />
+ </fk>
+ <fk name="fk_book_recipe_book_id" to_schema="recipe_book" to_table="book" delete_action="CASCADE" >
+ <fk_column name="book_id" pk="id" />
+ </fk>
+ </table>
+ <table name="book_theme_name" >
+ <comment>Lists all the book theme names (e.g., maps MODERN_SQUARE to &quot;Modern Square&quot;).</comment>
+ <column name="id" type="int4" jt="4" mandatory="y" >
+ <comment> <![CDATA[Primary key.]]> </comment>
+ </column>
+ <column name="domain" type="varchar" length="32" jt="12" mandatory="y" >
+ <comment> <![CDATA[Uniquely identifies the theme. This is used by the book theme preferences.]]> </comment>
+ </column>
+ <column name="label" type="varchar" jt="12" mandatory="y" >
+ <comment> <![CDATA[Textual description of the book.]]> </comment>
+ </column>
+ <index name="pk_book_theme" unique="PRIMARY_KEY" >
+ <comment>Primary key.</comment>
+ <column name="id" />
+ </index>
+ <index name="uk_book_theme_name_code" unique="UNIQUE" >
+ <comment>Uniquely identifies each theme&#039;s code.</comment>
+ <column name="domain" />
+ </index>
+ </table>
+ </schema>
+ <connector name="recipe" database="PostgreSQL" driver_class="org.postgresql.Driver" driver_jar="postgresql-8.4-701.jdbc3.jar" host="localhost" port="5432" instance="recipe" user="recipe" schema_mapping="public:null;recipe:null;recipe_book:null" />
+ <layout name="Chaos" >
+ <entity schema="recipe" name="account" x="476" y="420" />
+ <entity schema="recipe" name="action" x="350" y="420" />
+ <entity schema="recipe" name="cuisine" x="686" y="84" />
+ <entity schema="recipe" name="description" x="644" y="420" />
+ <entity schema="recipe" name="direction" x="476" y="224" />
+ <entity schema="recipe" name="direction_group" x="812" y="420" />
+ <entity schema="recipe" name="equipment" x="644" y="602" />
+ <entity schema="recipe" name="equipment_group" x="280" y="280" />
+ <entity schema="recipe" name="ingredient" x="266" y="602" />
+ <entity schema="recipe" name="ingredient_group" x="812" y="266" />
+ <entity schema="recipe" name="ingredient_name" x="854" y="602" />
+ <entity schema="recipe" name="ingredient_substitute" x="42" y="112" />
+ <entity schema="recipe" name="ingredient_unit" x="154" y="420" />
+ <entity schema="recipe" name="recipe" x="476" y="42" />
+ <entity schema="recipe" name="recipe_equipment_group" x="854" y="770" />
+ <entity schema="recipe" name="result" x="308" y="84" />
+ <callout x="84" y="84" pointer="SV" >
+ <comment> <![CDATA[Use this layer for database synch.]]> </comment>
+ </callout>
+ </layout>
+ <layout name="Public" >
+ <entity schema="public" name="xpath_relations" x="42" y="42" />
+ </layout>
+ <layout name="recipe_book" >
+ <entity schema="recipe" name="account" x="630" y="42" />
+ <entity schema="recipe_book" name="book" x="308" y="42" />
+ <entity schema="recipe_book" name="book_account" x="448" y="42" />
+ <entity schema="recipe_book" name="book_recipe" x="462" y="154" />
+ <entity schema="recipe_book" name="book_preference" x="238" y="266" />
+ <entity schema="recipe" name="recipe" x="630" y="196" />
+ <entity schema="recipe_book" name="book_photograph_category" x="42" y="266" />
+ <entity schema="recipe_book" name="book_photograph" x="42" y="42" />
+ <entity schema="recipe_book" name="book_theme_name" x="84" y="406" />
+ <entity schema="recipe_book" name="book_latex" x="42" y="588" />
+ <entity schema="recipe_book" name="book_preference_code" x="280" y="406" />
+ <group name="Book" color="ffcccc" >
+ <entity schema="recipe_book" name="book_account" />
+ <entity schema="recipe_book" name="book_photograph" />
+ <entity schema="recipe_book" name="book" />
+ <entity schema="recipe_book" name="book_photograph_category" />
+ <entity schema="recipe_book" name="book_preference" />
+ <entity schema="recipe_book" name="book_preference_code" />
+ <entity schema="recipe_book" name="book_recipe" />
+ <entity schema="recipe_book" name="book_theme_name" />
+ </group>
+ <group name="Recipe" color="ccffcc" >
+ <entity schema="recipe" name="account" />
+ <entity schema="recipe" name="recipe" />
+ </group>
+ <group name="Latex" color="ffccff" >
+ <entity schema="recipe_book" name="book_latex" />
+ </group>
+ </layout>
+ <layout name="recipe_zeal" confirmed="y" >
+ <entity schema="recipe" name="account" x="154" y="406" />
+ <entity schema="recipe" name="cuisine" x="462" y="574" />
+ <entity schema="recipe" name="diet" x="462" y="672" />
+ <entity schema="recipe" name="direction_group" x="602" y="420" />
+ <entity schema="recipe" name="equipment" x="42" y="42" />
+ <entity schema="recipe" name="equipment_group" x="238" y="42" />
+ <entity schema="recipe" name="ingredient" x="462" y="154" />
+ <entity schema="recipe" name="ingredient_group" x="462" y="42" />
+ <entity schema="recipe" name="ingredient_unit" x="686" y="42" />
+ <entity schema="recipe" name="preparation" x="462" y="462" />
+ <entity schema="recipe" name="recipe_equipment_group" x="182" y="168" />
+ <entity schema="recipe" name="description" x="280" y="574" />
+ <entity schema="recipe" name="recipe" x="280" y="406" />
+ <entity schema="recipe" name="direction" x="602" y="602" />
+ <entity schema="recipe" name="action" x="798" y="602" />
+ <entity schema="recipe" name="ingredient_name" x="686" y="252" />
+ <entity schema="recipe" name="ingredient_substitute" x="686" y="154" />
+ <group name="Recipe" color="ccffcc" >
+ <entity schema="recipe" name="preparation" />
+ <entity schema="recipe" name="cuisine" />
+ <entity schema="recipe" name="diet" />
+ <entity schema="recipe" name="direction_group" />
+ <entity schema="recipe" name="action" />
+ <entity schema="recipe" name="direction" />
+ </group>
+ <group name="Equipment" color="99ffff" >
+ <entity schema="recipe" name="recipe_equipment_group" />
+ <entity schema="recipe" name="equipment_group" />
+ <entity schema="recipe" name="equipment" />
+ </group>
+ <group name="Ingredient" color="ccccff" >
+ <entity schema="recipe" name="ingredient_name" />
+ <entity schema="recipe" name="ingredient_group" />
+ <entity schema="recipe" name="ingredient_unit" />
+ <entity schema="recipe" name="ingredient_substitute" />
+ <entity schema="recipe" name="ingredient" />
+ </group>
+ </layout>
+</project>
sql/recipe-book.sql
+CREATE SCHEMA recipe_book;
+
+CREATE TABLE recipe_book.book (
+ id serial NOT NULL,
+ label varchar( 128 ) NOT NULL,
+ spine_label varchar( 128 ) NOT NULL,
+ dedication text,
+ isbn varchar( 13 ),
+ created timestamptz DEFAULT current_timestamp NOT NULL,
+ deleted timestamptz,
+ updated timestamptz,
+ CONSTRAINT pk_book PRIMARY KEY ( id )
+ );
+
+COMMENT ON TABLE recipe_book.book IS 'Defines the common items to every book.';
+
+COMMENT ON COLUMN recipe_book.book.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book.label IS 'Book title.';
+
+COMMENT ON COLUMN recipe_book.book.spine_label IS 'Book spine label.';
+
+COMMENT ON COLUMN recipe_book.book.dedication IS 'Text for the dedication.';
+
+COMMENT ON COLUMN recipe_book.book.isbn IS 'International standard book number and EAN, can be null.';
+
+COMMENT ON COLUMN recipe_book.book.created IS 'Date the book was created.';
+
+COMMENT ON COLUMN recipe_book.book.deleted IS 'Date the book was (or is to be?) deleted.';
+
+COMMENT ON COLUMN recipe_book.book.updated IS 'Date the book was last updated.';
+
+CREATE TABLE recipe_book.book_photograph_category (
+ id serial NOT NULL,
+ label varchar NOT NULL,
+ description varchar( 128 ) NOT NULL,
+ CONSTRAINT pk_book_photograph_category PRIMARY KEY ( id )
+ );
+
+COMMENT ON TABLE recipe_book.book_photograph_category IS 'Contains a list of categories for book photographs.';
+
+COMMENT ON COLUMN recipe_book.book_photograph_category.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_photograph_category.label IS 'Text to display to the user.';
+
+COMMENT ON COLUMN recipe_book.book_photograph_category.description IS 'Brief description regarding how the category is used.';
+
+CREATE TABLE recipe_book.book_theme_name (
+ id int4 NOT NULL,
+ domain varchar( 32 ) NOT NULL,
+ label varchar NOT NULL,
+ CONSTRAINT pk_book_theme PRIMARY KEY ( id ),
+ CONSTRAINT uk_book_theme_name_code UNIQUE ( domain )
+ );
+
+COMMENT ON TABLE recipe_book.book_theme_name IS 'Lists all the book theme names (e.g., maps MODERN_SQUARE to "Modern Square").';
+
+COMMENT ON COLUMN recipe_book.book_theme_name.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_theme_name.domain IS 'Uniquely identifies the theme. This is used by the book theme preferences.';
+
+COMMENT ON COLUMN recipe_book.book_theme_name.label IS 'Textual description of the book.';
+
+CREATE TABLE recipe_book.book_photograph (
+ id serial NOT NULL,
+ book_id int4 NOT NULL,
+ image_url varchar( 2048 ) NOT NULL,
+ book_photograph_category_id int4 NOT NULL,
+ CONSTRAINT pk_book_photograph PRIMARY KEY ( id ),
+ CONSTRAINT fk_book_photograph_book_id FOREIGN KEY ( book_id ) REFERENCES recipe_book.book( id ) ON DELETE CASCADE ,
+ CONSTRAINT fk_book_photograph_book_photograph_category_id FOREIGN KEY ( book_photograph_category_id ) REFERENCES recipe_book.book_photograph_category( id ) ON DELETE CASCADE
+ );
+
+CREATE INDEX idx_book_photograph ON recipe_book.book_photograph ( book_id );
+
+CREATE INDEX idx_book_photograph_0 ON recipe_book.book_photograph ( book_photograph_category_id );
+
+COMMENT ON TABLE recipe_book.book_photograph IS 'Describes attributes about a photograph that can be used in the book.';
+
+COMMENT ON COLUMN recipe_book.book_photograph.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_photograph.book_id IS 'The book to which this photograph belongs.';
+
+COMMENT ON COLUMN recipe_book.book_photograph.image_url IS 'The website address where the image can be retrieved.';
+
+COMMENT ON COLUMN recipe_book.book_photograph.book_photograph_category_id IS 'The type of photograph (e.g., cover page, meal inset, divider page, category section page).';
+
+CREATE TABLE recipe_book.book_preference_code (
+ id serial NOT NULL,
+ domain varchar( 32 ) NOT NULL,
+ code varchar( 32 ) NOT NULL,
+ label varchar( 32 ) NOT NULL,
+ description varchar( 128 ) NOT NULL,
+ CONSTRAINT pk_book_preference_code PRIMARY KEY ( id ),
+ CONSTRAINT fk_book_preference_code_domain FOREIGN KEY ( domain ) REFERENCES recipe_book.book_theme_name( domain ) ON DELETE CASCADE
+ );
+
+CREATE INDEX idx_book_preference_code ON recipe_book.book_preference_code ( domain );
+
+COMMENT ON TABLE recipe_book.book_preference_code IS 'List of domains, codes, and values related to book preferences. If later need arises, this table can be split into separate tables to establish foreign key constraints.';
+
+COMMENT ON COLUMN recipe_book.book_preference_code.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_preference_code.domain IS 'Grouping for codes and values (e.g., COLOUR_SCHEME).';
+
+COMMENT ON COLUMN recipe_book.book_preference_code.code IS 'Unique identifier within a given domain (e.g., BLUEBERRY).';
+
+COMMENT ON COLUMN recipe_book.book_preference_code.label IS 'Text that can be displayed to the user (e.g., Blueberry).';
+
+COMMENT ON COLUMN recipe_book.book_preference_code.description IS 'Brief description about how the code is used.';
+
+CREATE TABLE recipe_book.book_latex (
+ id serial NOT NULL,
+ book_preference_code_id int4 NOT NULL,
+ latex text NOT NULL,
+ CONSTRAINT pk_book_preamble PRIMARY KEY ( id ),
+ CONSTRAINT fk_book_latex_book_preference_code FOREIGN KEY ( book_preference_code_id ) REFERENCES recipe_book.book_preference_code( id ) ON DELETE CASCADE
+ );
+
+CREATE INDEX idx_book_latex ON recipe_book.book_latex ( book_preference_code_id );
+
+COMMENT ON TABLE recipe_book.book_latex IS 'Associates LaTeX code with a book preference.';
+
+COMMENT ON COLUMN recipe_book.book_latex.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_latex.book_preference_code_id IS 'Associates LaTeX source code with a book preference code.';
+
+COMMENT ON COLUMN recipe_book.book_latex.latex IS 'Source code associated with a configurable preference.';
+
+CREATE TABLE recipe_book.book_preference (
+ id serial NOT NULL,
+ book_id int4 NOT NULL,
+ book_preference_code_id int4 NOT NULL,
+ CONSTRAINT pk_book_preference PRIMARY KEY ( id ),
+ CONSTRAINT fk_book_preference_book_id FOREIGN KEY ( book_id ) REFERENCES recipe_book.book( id ) ON DELETE CASCADE ,
+ CONSTRAINT fk_book_preference_book_preference_code_id FOREIGN KEY ( book_id ) REFERENCES recipe_book.book_preference_code( id ) ON DELETE CASCADE
+ );
+
+CREATE INDEX idx_book_preference ON recipe_book.book_preference ( book_id );
+
+COMMENT ON TABLE recipe_book.book_preference IS 'Stores configuration parameters used to generate the book (e.g., layout, fonts, colours). The system must select default values for a book. This table allows users to override the defaults. This indirectly drives the settings for generating a book.';
+
+COMMENT ON COLUMN recipe_book.book_preference.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_preference.book_id IS 'The preference`s reference to a book.';
+
+COMMENT ON COLUMN recipe_book.book_preference.book_preference_code_id IS 'Reference to the book preference code table.';
+
+CREATE TABLE recipe_book.book_account (
+ id serial NOT NULL,
+ book_id int4 NOT NULL,
+ account_id int4 NOT NULL,
+ CONSTRAINT pk_book_account PRIMARY KEY ( id )
+ );
+
+CREATE INDEX idx_book_account ON recipe_book.book_account ( book_id );
+
+CREATE INDEX idx_book_account_0 ON recipe_book.book_account ( account_id );
+
+COMMENT ON TABLE recipe_book.book_account IS 'Associates a book with an account.';
+
+COMMENT ON COLUMN recipe_book.book_account.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_account.book_id IS 'The book associated with an account.';
+
+COMMENT ON COLUMN recipe_book.book_account.account_id IS 'The account associated with a book.';
+
+CREATE TABLE recipe_book.book_recipe (
+ id serial NOT NULL,
+ book_id int4 NOT NULL,
+ recipe_id serial NOT NULL,
+ CONSTRAINT pk_book_recipe PRIMARY KEY ( id )
+ );
+
+CREATE INDEX idx_book_recipe ON recipe_book.book_recipe ( recipe_id );
+
+CREATE INDEX idx_book_recipe_0 ON recipe_book.book_recipe ( book_id );
+
+COMMENT ON TABLE recipe_book.book_recipe IS 'Associates a book with a recipe.';
+
+COMMENT ON COLUMN recipe_book.book_recipe.id IS 'Primary key.';
+
+COMMENT ON COLUMN recipe_book.book_recipe.book_id IS 'Reference to the book table.';
+
+COMMENT ON COLUMN recipe_book.book_recipe.recipe_id IS 'Reference to the recipe table.';
+
+ALTER TABLE recipe_book.book_account ADD CONSTRAINT fk_book_account_book_id FOREIGN KEY ( book_id ) REFERENCES recipe_book.book( id ) ON DELETE CASCADE;
+
+ALTER TABLE recipe_book.book_account ADD CONSTRAINT fk_book_account_account_id FOREIGN KEY ( account_id ) REFERENCES recipe.account( id ) ON DELETE CASCADE;
+
+ALTER TABLE recipe_book.book_recipe ADD CONSTRAINT fk_book_recipe_recipe_id FOREIGN KEY ( recipe_id ) REFERENCES recipe.recipe( id ) ON DELETE CASCADE;
+
+ALTER TABLE recipe_book.book_recipe ADD CONSTRAINT fk_book_recipe_book_id FOREIGN KEY ( book_id ) REFERENCES recipe_book.book( id ) ON DELETE CASCADE;
+
sql/recipe-book.txt
+ COLOUR_SCHEME, BLUEBERRY, Blueberry, \header{\color{blue}}
+ COLOUR_SCHEME, RASPBERRY, Raspberry, \header{\color{red}}
+ COLOUR_SCHEME, PEACH, Peach, \header{\color{...}}
+ LIST, ENUMERATED, Use Numbered instructions, \enumerate_instructions{true} \paragraph_instructions{false}
+ LIST, PARAGRAPH, Use Paragraph instructions, \enumerate_instructions{false} \paragraph_instructions{true}
+ LIST_LIST_BACKGROUND, SQUARE, Square bullets, \list_background{...}
+ LIST_LIST_BACKGROUND, CIRCLE, Circular bullets, \list_background{...}
+ LIST_LIST_BACKGROUND, TRIANGLE, Triangular bullets, \list_background{...}
+ LIST_LIST_BACKGROUND, RAINDROP, Raindrop bullets, \list_background{...}
+ HEADER_BACKGROUND, SQUARE, Square header background line, \header{\background{...}}
+ HEADER_BACKGROUND, NONE, No header background
+ LAYOUT, ONE_SIDED, One-sided, ...
+ LAYOUT, TWO_SIDED, Two-sided, ...
+ PICTURE, TILT, Tilt Picture, \picture_tilt{ true }
+ PICTURE, DROP_SHADOW, Drop Shadow, \picture_shadow{ true }
+ PICTURE, FADED_SHADOW, Faded Shadow, \picture_faded_shadow{ true }
+ PICTURE, BORDER_THICKNESS, Border Thickness, \picture_border_thickness{ 0 }
+ PICTURE, BORDER_COLOUR, Border Colour, \picture_border_colour{ \primarycolour }
+
+Then, the ModernSquare would be stored in the database as:
+
+ THEME, MODERN_SQUARE, COLOUR_SCHEME, PEACH
+ THEME, MODERN_SQUARE, LIST, ENUMERATED
+ THEME, MODERN_SQUARE, LIST_BACKGROUND, SQUARE
+ THEME, MODERN_SQUARE, HEADER_BACKGROUND, SQUARE
+ THEME, MODERN_SQUARE, LAYOUT, ONE_SIDED