users@jpa-spec.java.net

[jpa-spec users] [jsr338-experts] Re: schema generation proposed changes

From: Linda DeMichiel <linda.demichiel_at_oracle.com>
Date: Thu, 30 Aug 2012 20:41:00 -0700

Great, thanks!

So, should we specify all 4 pieces of information?


On 8/30/2012 8:09 PM, Steve Ebersole wrote:
> Another is PostgreSQL adds "if exists" as an option for dropping tables in 8.2 (major=8, minor=2) which did not exist in
> 8.1 or earlier
>
>
> On Thu 30 Aug 2012 10:04:35 PM CDT, Steve Ebersole wrote:
>> Well a real simple example is that Derby supports sequences after
>> 10.6, but not before. So there
>> DatabaseMetaData#getDatabaseMajorVersion=10 and
>> DatabaseMetaData#getDatabaseMinorVersion=6. Even if the Derby driver
>> were to report the DatabaseMetaData#getDatabaseProductVersion="10.6"
>> or somesuch, relying on being able to parse that into ints to be able
>> to do range checks make me nervous, especially when JDBC already
>> offers means to know the major/minor.
>>
>> And thats just one example that came to me immediately.
>>
>> On Thu 30 Aug 2012 07:24:45 PM CDT, Linda DeMichiel wrote:
>>> Hi Steve,
>>>
>>> I'd like to understand this better, as the info I have from our team
>>> here
>>> indicates that database produce name together with version (in the
>>> worst case)
>>> would be sufficient. Do we need all four properties to accommodate
>>> the range
>>> of drivers/databases?
>>>
>>> thanks,
>>>
>>> -Linda
>>>
>>>
>>> On 8/29/2012 7:30 AM, Steve Ebersole wrote:
>>>> As far as:
>>>>
>>>> javax.persistence.database-product-name,
>>>> javax.persistence.database-product-version,
>>>>
>>>> I'd really rather see major/minor version used:
>>>>
>>>> (int) java.sql.DatabaseMetaData#getDatabaseMajorVersion
>>>> (int) java.sql.DatabaseMetaData#getDatabaseMinorVersion
>>>>
>>>> as opposed to the proposed:
>>>>
>>>> (String) java.sql.DatabaseMetaData#getDatabaseProductVersion
>>>>
>>>> For one Hibernate already uses those 2 ;) For another its more
>>>> indicative of what is/isn't available consistently across
>>>> databases.
>>>>
>>>>
>>>> On 07/23/2012 06:55 PM, Linda DeMichiel wrote:
>>>>> Here's an updated version of my earlier schema generation proposal,
>>>>> broken out as to proposed spec changes. You should hopefully find
>>>>> this considerably more flexible and detailed than the earlier draft.
>>>>>
>>>>> -Linda
>>>>>
>>>>> ----------------------------
>>>>>
>>>>> Proposed spec changes:
>>>>>
>>>>>
>>>>> New Section: Schema Generation [to follow section 9.3]
>>>>>
>>>>> Schema generation may either happen prior to application deployment or
>>>>> when the entity manager factory is created as part of the application
>>>>> deployment and initialization process.
>>>>>
>>>>> * In Java EE environments, the container may call the
>>>>> PersistenceProvider generateSchema method separately from and/or
>>>>> prior to the creation of the entity manager factory for the
>>>>> persistence unit, or the container may pass additional
>>>>> information to the createContainerEntityManagerFactory call to
>>>>> cause schema generation to happen as part of the entity manager
>>>>> factory creation and application initialization process. The
>>>>> information passed to these methods determines whether the
>>>>> generation of schemas and/or tables occurs directly in the target
>>>>> database, or whether DDL scripts for schema generation are
>>>>> created, or both.
>>>>>
>>>>> * In Java SE environments, the application may call the Persistence
>>>>> generateSchema method separately from and/or prior to the creation
>>>>> of the entity manager factory or may pass information to the
>>>>> createEntityManagerFactory method to cause schema generation to
>>>>> occur as part of the entity manager factory creation.
>>>>>
>>>>>
>>>>> The application may provide DDL scripts to be used for schema
>>>>> generation, and package these scripts as part of the persistence unit
>>>>> or specify URLs corresponding to the location of such scripts. In
>>>>> Java EE environments, such scripts may be executed by the container,
>>>>> or the container may direct the persistence provider to execute the
>>>>> scripts; in Java SE environments, the execution of the scripts is the
>>>>> responsibility of the persistence provider. In the absence of the
>>>>> specification of scripts, schema generation, if requested, will be
>>>>> determined by the object/relational metadata of the persistence unit.
>>>>>
>>>>>
>>>>> The following standard properties are defined for use in schema
>>>>> generation. In Java EE environments these properties are passed by
>>>>> the container in the Map argument to the PersistenceProvider
>>>>> generateSchema method or createContainerEntityManagerFactory method.
>>>>> In Java SE environments, they are passed in the Map argument to the
>>>>> Persistence generateSchema or createEntityManagerFactory method.
>>>>>
>>>>>
>>>>> javax.persistence.schema-generation-target:
>>>>>
>>>>> The schema-generation-target property specifies whether the schema
>>>>> is to be created in the database, whether scripts are to be
>>>>> generated, or both.
>>>>>
>>>>> values for this property: DATABASE, SCRIPTS, DATABASE_AND_SCRIPTS
>>>>> [Open Issue: introduce for these enum or use strings? Better names??]
>>>>>
>>>>>
>>>>> javax.persistence.schema-generation-action:
>>>>>
>>>>> The schema-generation-action property is used to specify the action
>>>>> to be taken by the persistence provider. If the
>>>>> schema-generation-target property is not specified, no action must
>>>>> be taken.
>>>>>
>>>>> values for this property: NONE, CREATE, DROP_AND_CREATE, DROP
>>>>> [Open Issue: enum strings ("none", "create", "drop-and-create",...)
>>>>>
>>>>>
>>>>> javax.persistence.create-database-schemas
>>>>>
>>>>> In Java EE environments, it is anticipated that the Java EE
>>>>> platform provider may wish to control the creation of database
>>>>> schemas rather than delegate this task to the persistence provider.
>>>>> The create-database-schemas property specifies whether the
>>>>> persistence provider is to create the database schema(s) in
>>>>> addition to creating database objects such as tables, sequences,
>>>>> constraints, etc. The value of this boolean property should be set
>>>>> to true if the persistence provider is to create schemas in the
>>>>> database or to generate DDL which is to contain "CREATE SCHEMA"
>>>>> commands. If this property is not supplied, the provider should
>>>>> not attempt to create database schemas. This property may be
>>>>> specified in Java SE environments as well.
>>>>>
>>>>>
>>>>> javax.persistence.ddl-create-script-target,
>>>>> javax.persistence.ddl-drop-script-target:
>>>>>
>>>>> If scripts are to be generated, the target locations for the
>>>>> writing of these scripts must be specified. These targets may take
>>>>> the form of either Writers or strings designating URLs. The
>>>>> persistence provider must produce both create and drop scripts if
>>>>> the corresponding DDL targets are specified. This is independent
>>>>> of whether a drop action is included in the value passed for the
>>>>> schema-generation-action property. If the schema-generation-target
>>>>> property specifies scripts and script targets are not specified,
>>>>> the IllegalArgumentException should be thrown by the provider.
>>>>>
>>>>> ddl-create-script-target: a Writer configured for the persistence
>>>>> provider for output of the DDL script or a string specifying
>>>>> the URL for the DDL script. This property should only be
>>>>> specified if scripts are to be generated.
>>>>>
>>>>> ddl-drop-script-target: a Writer configured for the persistence
>>>>> provider for output of the DDL script or a string specifying the
>>>>> URL for the DDL script. This property should only be specified
>>>>> if scripts are to be generated.
>>>>> [Suggestions for better names ??]
>>>>>
>>>>>
>>>>> javax.persistence.database-product-name,
>>>>> javax.persistence.database-product-version,
>>>>>
>>>>> If scripts are to be generated by the persistence provider and a
>>>>> connection to the target database is not supplied, the
>>>>> javax.persistence.database-product-name property must be
>>>>> specified. The value of this property should be the value
>>>>> returned for the target database by the JDBC DatabaseMetaData
>>>>> method getDatabaseProductName. If sufficient database version
>>>>> information is not included in the result of this method, the
>>>>> database-product-version property should also be specified, and
>>>>> should contain the value returned by the JDBC
>>>>> getDatabaseProductVersion method.
>>>>>
>>>>>
>>>>>
>>>>> javax.persistence.ddl-create-script-source,
>>>>> javax.persistence.ddl-drop-script-source:
>>>>>
>>>>> The ddl-create-script-source and ddl-drop-script-source properties
>>>>> are used for script execution. In Java EE container environments,
>>>>> it is generally expected that the container will be responsible
>>>>> for executing DDL scripts, although the container is permitted to
>>>>> delegate this task to the persistence provider. If DDL scripts
>>>>> are to be used in Java SE environments or if the Java EE container
>>>>> delegates the execution of scripts to the persistence provider,
>>>>> these properties must be specified. The script sources may take
>>>>> the form of either Readers or strings designating URLs.
>>>>>
>>>>> ddl-create-script-source: a Reader configured for reading of the
>>>>> DDL script or a string specifying the URL for the DDL script.
>>>>>
>>>>> ddl-drop-script-source: a Reader configured for reading of the DDL
>>>>> script or a string specifying the URL for the DDL script.
>>>>> [Suggestions for better names ??]
>>>>>
>>>>>
>>>>>
>>>>> javax.persistence.sql-load-script-source:
>>>>>
>>>>> A data load script may be supplied as part of the persistence
>>>>> unit. In Java EE container environments, it is generally expected
>>>>> that the container will be responsible for executing data load
>>>>> scripts, although the container is permitted to delegate this task
>>>>> to the persistence provider. If a load script is to be used in
>>>>> Java SE environments or if the Java EE container delegates the
>>>>> execution of the load script to the persistence provider, this
>>>>> property must be specified. The script source may take the form
>>>>> of either a Reader or a string designating a URL.
>>>>>
>>>>> sql-load-script-source: a Reader configured for reading of the SQL
>>>>> load script for database initialization or a string specifying
>>>>> the URL for the script.
>>>>>
>>>>>
>>>>>
>>>>> javax.persistence.schema-generation-connection:
>>>>>
>>>>> JDBC connection to be used for schema generation. This is intended
>>>>> for use in Java EE environments, where the platform provider may
>>>>> want to control the database privileges that are available to the
>>>>> persistence provider. This connection is provided by the container,
>>>>> and should be closed by the container when the schema generation
>>>>> request or entity manager factory creation completes. The
>>>>> connection provided must have credentials sufficient for the
>>>>> persistence provider to carry out the requested actions. If this
>>>>> property is not specified, the persistence provider should use the
>>>>> DataSource that has otherwise been provided.
>>>>>
>>>>>
>>>>>
>>>>> 9.4.1 PersistenceProvider Interface:
>>>>>
>>>>> New method:
>>>>>
>>>>> /**
>>>>> * Create database schemas and/or tables and/or create DDL
>>>>> * scripts as determined by the supplied properties
>>>>> *
>>>>> * @param info metadata for use by the persistence provider
>>>>> * @param map properties for schema generation; these
>>>>> * may also contain provider-specific properties
>>>>> * @throws PersistenceException if insufficient or inconsistent
>>>>> * configuration information is provided or if schema
>>>>> * generation otherwise fails.
>>>>> */
>>>>> public void generateSchema(PersistenceUnitInfo info, Map map)
>>>>>
>>>>>
>>>>> 9.6 Persistence Class
>>>>>
>>>>> New method:
>>>>>
>>>>> /**
>>>>> * Create database schemas and/or tables and/or create DDL
>>>>> * scripts as determined by the supplied properties
>>>>> *
>>>>> * @param persistenceUnitName the name of the persistence unit
>>>>> * @param map properties for schema generation; these may also
>>>>> * contain provider-specific properties. The values of
>>>>> * these properties override any values that may have been
>>>>> * configured elsewhere.
>>>>> * @throws PersistenceException if insufficient or inconsistent
>>>>> * configuration information is provided or if schema
>>>>> * generation otherwise fails.
>>>>> */
>>>>> public void generateSchema(String persistenceUnitName, Map properties)
>>>>>
>>>>>
>>>>> -----------------------
>>>>>
>>>>> Section 8.2.1 persistence.xml file
>>>>>
>>>>> To be added to section 8.2.1:
>>>>>
>>>>> Scripts for use in schema generation and bulk loading of data may be
>>>>> packaged as part of the persistence unit.
>>>>>
>>>>>
>>>>> To be added to Section 8.2.1.9 (properties):
>>>>>
>>>>> Scripts for use in schema generation are specified using the
>>>>> ddl-create-script and ddl-drop-script elements. A script to specify
>>>>> SQL for the bulk loading of data may be specified by the
>>>>> sql-load-script element. These scripts may be packaged as part of the
>>>>> persistence unit or designated by URL strings.
>>>>>
>>>>> <xsd:element name="database-scripts" type="database-scripts-type"
>>>>> minOccurs="0"/>
>>>>>
>>>>> <xsd:complexType name="database-scripts-type">
>>>>> <xsd:sequence>
>>>>> <xsd:element name="ddl-create-script" type="xsd:string"/>
>>>>> <xsd:element name="ddl-drop-script" type="xsd:string" minOccurs="0"/>
>>>>> <xsd:element name="sql-load-script" type="xsd:string" minOccurs="0"/>
>>>>> </xsd:sequence>
>>>>> </xsd:complexType>
>>>>>
>>>>> [Open Issue: do we want to require a drop-script if a create-script
>>>>> has been provided?]
>>>>>
>>>>> -----------
>>>>>
>>>>> Chapter 11:
>>>>>
>>>>> New annotations for use in schema generation:
>>>>>
>>>>> @Target({}) @Retention(RUNTIME)
>>>>> public @interface Index {
>>>>> String name() default "";
>>>>> String columnList();
>>>>> boolean unique() default false; // should this be here or just use
>>>>> UniqueConstraints?
>>>>> }
>>>>>
>>>>> columnList syntax follows that of the OrderBy annotation:
>>>>>
>>>>> columnList::= indexColumn [, indexColumn]*
>>>>> indexColumn::= columnName [ASC | DESC]
>>>>>
>>>>> If ASC or DESC is not specified, ASC is assumed
>>>>>
>>>>> Index[] indexes() default {};
>>>>> is to be added to Table, SecondaryTable, CollectionTable, JoinTable,
>>>>> and
>>>>> TableGenerator
>>>>>
>>>>>
>>>>>
>>>>> /**
>>>>> * Provides for defining a foreign key constraint or for overriding
>>>>> * or disabling the persistence provider's default foreign key
>>>>> * definition.
>>>>> */
>>>>> @Target({}) @Retention(RUNTIME)
>>>>> public @interface ForeignKey {
>>>>> String name() default "";
>>>>> String foreignKeyDefinition() default "";
>>>>> boolean disableForeignKey() default false;
>>>>> }
>>>>>
>>>>>
>>>>> The syntax used in the foreignKeyDefinition element should follow the
>>>>> SQL syntax used by the target database for foreign key constraints.
>>>>> E.g., this would likely be similar to the following:
>>>>>
>>>>> FOREIGN KEY ( <COLUMN expression> {, <COLUMN expression>}... )
>>>>> REFERENCES <TABLE identifier> [ ( <COLUMN expression> {, <COLUMN
>>>>> expression>}... ) ]
>>>>> [ ON UPDATE <referential action> ]
>>>>> [ ON DELETE <referential action> ]
>>>>>
>>>>> If disableForeignKey is specified as true, the provider must not
>>>>> generate
>>>>> a foreign key constraint.
>>>>>
>>>>>
>>>>> The following is to be added to JoinColumn, JoinColumns,
>>>>> MapKeyJoinColumn,
>>>>> MapKeyJoinColumns, PrimaryKeyJoinColumn and PrimaryKeyJoinColumns:
>>>>>
>>>>> ForeignKey foreignKey() default @ForeignKey();
>>>>>
>>>>>