This commit is contained in:
parent
ab530652bb
commit
19407e41a5
@ -1,166 +0,0 @@
|
|||||||
+++ Introduction
|
|
||||||
|
|
||||||
{{Doctrine_Db}} is a wrapper for PDO database object. Why should you consider using {{Doctrine_Db}} instead of PDO?
|
|
||||||
|
|
||||||
# It provides efficient eventlistener architecture, hence its easy to add new aspects to existing methods like on-demand-caching
|
|
||||||
# {{Doctrine_Db}} lazy-connects database. Creating an instance of {{Doctrine_Db}} doesn't directly connect database, hence {{Doctrine_Db}} fits perfectly for application using for example page caching.
|
|
||||||
# It has many short cuts for commonly used fetching methods like {{Doctrine_Db::fetchOne()}}.
|
|
||||||
# Supports PEAR-like data source names as well as PDO data source names.
|
|
||||||
|
|
||||||
|
|
||||||
+++ Connecting to a database
|
|
||||||
|
|
||||||
|
|
||||||
{{Doctrine_Db}} allows both PEAR-like DSN (data source name) as well as PDO like DSN as constructor parameters.
|
|
||||||
|
|
||||||
Getting an instance of {{Doctrine_Db}} using PEAR-like DSN:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// using PEAR like dsn for connecting pgsql database
|
|
||||||
|
|
||||||
$dbh = new Doctrine_Db('pgsql://root:password@localhost/mydb');
|
|
||||||
|
|
||||||
// using PEAR like dsn for connecting mysql database
|
|
||||||
|
|
||||||
$dbh = new Doctrine_Db('mysql://root:password@localhost/test');
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Getting an instance of {{Doctrine_Db}} using PDO-like DSN (PDO mysql driver):
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$dbh = new Doctrine_Db('mysql:host=localhost;dbname=test',
|
|
||||||
$user, $pass);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Getting an instance of {{Doctrine_Db}} using PDO-like DSN (PDO sqlite with memory tables):
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$dbh = new Doctrine_Db('sqlite::memory:');
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Handling connection errors:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
try {
|
|
||||||
$dbh = new Doctrine_Db('mysql:host=localhost;dbname=test',
|
|
||||||
$user, $pass);
|
|
||||||
foreach ($dbh->query('SELECT * FROM foo') as $row) {
|
|
||||||
print_r($row);
|
|
||||||
}
|
|
||||||
$dbh = null;
|
|
||||||
} catch (PDOException $e) {
|
|
||||||
print 'Error!: ' . $e->getMessage() . '
|
|
||||||
';
|
|
||||||
die();
|
|
||||||
}
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Using event listeners
|
|
||||||
|
|
||||||
{{Doctrine_Db}} has a pluggable event listener architecture. It provides before and after listeners for all relevant methods. Every listener method takes one parameter: a {{Doctrine_Db_Event}} object, which holds info about the occurred event.
|
|
||||||
|
|
||||||
Every listener object must either implement the {{Doctrine_Db_EventListener_Interface}} or {{Doctrine_Overloadable}} interface. Using {{Doctrine_Overloadable}} interface only requires you to implement {{__call()}} which is then used for listening all the events.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
class OutputLogger extends Doctrine_Overloadable {
|
|
||||||
public function __call($m, $a) {
|
|
||||||
print $m . ' called!';
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</code>
|
|
||||||
|
|
||||||
For convience you may want to make your listener class extend {{Doctrine_Db_EventListener}} which has empty listener methods, hence allowing you not to define all the listener methods by hand. The following listener, 'MyLogger', is used for listening only {{onPreQuery}} and {{onQuery}} methods.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
class MyLogger extends Doctrine_Db_EventListener {
|
|
||||||
public function onPreQuery(Doctrine_Db_Event $event) {
|
|
||||||
print 'database is going to be queried!';
|
|
||||||
}
|
|
||||||
public function onQuery(Doctrine_Db_Event $event) {
|
|
||||||
print 'executed: ' . $event->getQuery();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Now the next thing we need to do is bind the eventlistener objects to our database handler.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// using PDO dsn for connecting sqlite memory table
|
|
||||||
|
|
||||||
$dbh = Doctrine_Db::getConnection('sqlite::memory:');
|
|
||||||
|
|
||||||
class MyLogger extends Doctrine_Db_EventListener {
|
|
||||||
public function onPreQuery(Doctrine_Db_Event $event) {
|
|
||||||
print "database is going to be queried!";
|
|
||||||
}
|
|
||||||
public function onQuery(Doctrine_Db_Event $event) {
|
|
||||||
print "executed: " . $event->getQuery();
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$dbh->setListener(new MyLogger());
|
|
||||||
|
|
||||||
$dbh->query("SELECT * FROM foo");
|
|
||||||
// prints:
|
|
||||||
// database is going to be queried
|
|
||||||
// executed: SELECT * FROM foo
|
|
||||||
|
|
||||||
|
|
||||||
class MyLogger2 extends Doctrine_Overloadable {
|
|
||||||
public function __call($m, $a) {
|
|
||||||
print $m." called!";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
$dbh->setListener(new MyLogger2());
|
|
||||||
|
|
||||||
$dbh->exec("DELETE FROM foo");
|
|
||||||
// prints:
|
|
||||||
// onPreExec called!
|
|
||||||
// onExec called!
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Chaining listeners
|
|
||||||
|
|
||||||
{{Doctrine_Db}} supports event listener chaining. It means multiple listeners can be attached for
|
|
||||||
listening the events of a single instance of {{Doctrine_Db}}.
|
|
||||||
|
|
||||||
For example you might want to add different aspects to your {{Doctrine_Db}} instance on-demand. These aspects may include caching, query profiling etc.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
|
|
||||||
// using PDO dsn for connecting sqlite memory table
|
|
||||||
|
|
||||||
$dbh = Doctrine_Db::getConnection('sqlite::memory:');
|
|
||||||
|
|
||||||
class Counter extends Doctrine_Db_EventListener {
|
|
||||||
private $queries = 0;
|
|
||||||
|
|
||||||
public function onQuery(Doctrine_Db_Event $event) {
|
|
||||||
$this->queries++;
|
|
||||||
}
|
|
||||||
public function count() {
|
|
||||||
return count($this->queries);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
class OutputLogger extends Doctrine_Overloadable {
|
|
||||||
public function __call($m, $a) {
|
|
||||||
print $m." called!";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
$counter = new Counter();
|
|
||||||
|
|
||||||
$dbh->addListener($counter);
|
|
||||||
$dbh->addListener(new OutputLogger());
|
|
||||||
|
|
||||||
$dbh->query("SELECT * FROM foo");
|
|
||||||
// prints:
|
|
||||||
// onPreQuery called!
|
|
||||||
// onQuery called!
|
|
||||||
|
|
||||||
print $counter->count(); // 1
|
|
||||||
|
|
||||||
</code>
|
|
||||||
|
|
@ -1,9 +0,0 @@
|
|||||||
+++ Introduction
|
|
||||||
|
|
||||||
{{Doctrine_Db_Profiler}} is an eventlistener for {{Doctrine_Db}}. It provides flexible query profiling. Besides the SQL strings the query profiles include elapsed time to run the queries. This allows inspection of the queries that have been performed without the need for adding extra debugging code to model classes.
|
|
||||||
|
|
||||||
{{Doctrine_Db_Profiler}} can be enabled by adding it as an eventlistener for {{Doctrine_Db}}.
|
|
||||||
|
|
||||||
|
|
||||||
+++ Basic usage
|
|
||||||
+++ Advanced usage
|
|
@ -1,14 +0,0 @@
|
|||||||
+++ Overview
|
|
||||||
|
|
||||||
+++ List of exceptions
|
|
||||||
|
|
||||||
: {{InvalidKeyException}} :
|
|
||||||
: {{Doctrine_Exception}} :
|
|
||||||
: {{DQLException}} :
|
|
||||||
: {{Doctrine_PrimaryKey_Exception}} : thrown when {{Doctrine_Record}} is loaded and there is no primary key field
|
|
||||||
: {{Doctrine_Refresh_Exception}} : thrown when {{Doctrine_Record}} is refreshed and the refreshed primary key doens't match the old one
|
|
||||||
: {{Doctrine_Find_Exception}} : thrown when user tries to find a {{Doctrine_Record}} for given primary key and that object is not found
|
|
||||||
: {{Doctrine_Naming_Exception}} : thrown when user defined {{Doctrine_Table}} is badly named
|
|
||||||
: {{Doctrine_Connection_Exception}} : thrown when user tries to get the current connection and there are no open connections
|
|
||||||
: {{Doctrine_Table_Exception}} : thrown when user tries to initialize a new instance of {{Doctrine_Table}}, while there already exists an instance of that factory
|
|
||||||
: {{Doctrine_Mapping_Exception}} : thrown when user tries to get a foreign key object but the mapping is not done right
|
|
@ -1,178 +0,0 @@
|
|||||||
+++ Introduction
|
|
||||||
|
|
||||||
DQL (Doctrine Query Language) is a object query language which allows you to find objects. DQL understands things like object relationships, polymorphism and inheritance (including column aggregation inheritance). For more info about DQL see the actual DQL chapter.
|
|
||||||
|
|
||||||
{{Doctrine_Query}} along with {{Doctrine_Expression}} provide an easy-to-use wrapper for writing DQL queries. Creating a new query object can be done by either using the new operator or by calling create method. The create method exists for allowing easy method call chaining.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// initalizing a new Doctrine_Query (using the current connection)
|
|
||||||
$q = new Doctrine_Query();
|
|
||||||
|
|
||||||
// initalizing a new Doctrine_Query (using custom connection parameter)
|
|
||||||
// here $conn is an instance of Doctrine_Connection
|
|
||||||
$q = new Doctrine_Query($conn);
|
|
||||||
|
|
||||||
// an example using the create method
|
|
||||||
// here we simple fetch all users
|
|
||||||
$users = new Doctrine_Query::create()->from('User')->execute();
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Selecting tables
|
|
||||||
|
|
||||||
The {{FROM}} clause indicates the component or components from which to retrieve records. If you name more than one component, you are performing a join. For each table specified, you can optionally specify an alias. {{Doctrine_Query}} offers easy to use methods such as {{from()}}, {{addFrom()}}, {{leftJoin()}} and {{innerJoin()}} for managing the {{FROM}} part of your DQL query.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// find all users
|
|
||||||
$q = new Doctrine_Query();
|
|
||||||
|
|
||||||
$coll = $q->from('User')->execute();
|
|
||||||
|
|
||||||
// find all users with only their names (and primary keys) fetched
|
|
||||||
|
|
||||||
$coll = $q->select('u.name')->('User u');
|
|
||||||
</code>
|
|
||||||
|
|
||||||
The following example shows how to use leftJoin and innerJoin methods:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// find all groups
|
|
||||||
|
|
||||||
$coll = $q->from("FROM Group");
|
|
||||||
|
|
||||||
// find all users and user emails
|
|
||||||
|
|
||||||
$coll = $q->from("FROM User u LEFT JOIN u.Email e");
|
|
||||||
|
|
||||||
// find all users and user emails with only user name and
|
|
||||||
// age + email address loaded
|
|
||||||
|
|
||||||
$coll = $q->select('u.name, u.age, e.address')
|
|
||||||
->from('FROM User u')
|
|
||||||
->leftJoin('u.Email e')
|
|
||||||
->execute();
|
|
||||||
|
|
||||||
// find all users, user email and user phonenumbers
|
|
||||||
|
|
||||||
$coll = $q->from('FROM User u')
|
|
||||||
->innerJoin('u.Email e')
|
|
||||||
->innerJoin('u.Phonenumber p')
|
|
||||||
->execute();
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Limiting the query results
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// find the first ten users and associated emails
|
|
||||||
|
|
||||||
$q = new Doctrine_Query();
|
|
||||||
|
|
||||||
$coll = $q->from('User u LEFT JOIN u.Email e')->limit(10);
|
|
||||||
|
|
||||||
// find the first ten users starting from the user number 5
|
|
||||||
|
|
||||||
$coll = $q->from('User u')->limit(10)->offset(5);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Setting query conditions
|
|
||||||
|
|
||||||
The {{WHERE}} clause, if given, indicates the condition or conditions that the records must satisfy to be selected.
|
|
||||||
|
|
||||||
{{Doctrine_Query}} provides easy to use {{WHERE}} -part management methods {{where}} and {{addWhere}}. The {{where}} methods always overrides the query {{WHERE}} -part whereas {{addWhere}} adds new condition to the {{WHERE}} -part stack.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// find all groups where the group primary key is bigger than 10
|
|
||||||
|
|
||||||
$coll = $q->from('Group')->where('Group.id > 10');
|
|
||||||
|
|
||||||
// the same query using Doctrine_Expression component
|
|
||||||
$e = $q->expr;
|
|
||||||
$coll = $q->from('Group')->where($e->gt('Group.id', 10));
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Using regular expression operator:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// find all users where users where user name matches
|
|
||||||
// a regular expression, regular expressions must be
|
|
||||||
// supported by the underlying database
|
|
||||||
|
|
||||||
$coll = $conn->query("FROM User WHERE User.name REGEXP '[ad]'");
|
|
||||||
</code>
|
|
||||||
|
|
||||||
DQL has support for portable {{LIKE}} operator:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// find all users and their associated emails
|
|
||||||
// where SOME of the users phonenumbers
|
|
||||||
// (the association between user and phonenumber
|
|
||||||
// tables is One-To-Many) starts with 123
|
|
||||||
|
|
||||||
$coll = $q->select('u.*, e.*')
|
|
||||||
->from('User u LEFT JOIN u.Email e LEFT JOIN u.Phonenumber p')
|
|
||||||
->where(\"p.phonenumber LIKE '123%'");
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Using multiple conditions and condition nesting are also possible:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// multiple conditions
|
|
||||||
|
|
||||||
$coll = $q->select('u.*')
|
|
||||||
->from('User u LEFT JOIN u.Email e')
|
|
||||||
->where(\"u.name LIKE '%Jack%' AND e.address LIKE '%@drinkmore.info'\");
|
|
||||||
|
|
||||||
// nesting conditions
|
|
||||||
|
|
||||||
$coll = $q->select('u.*')
|
|
||||||
->from('User u LEFT JOIN u.Email e')
|
|
||||||
->where(\"u.name LIKE '%Jack%' OR u.name LIKE '%John%') AND e.address LIKE '%@drinkmore.info'");
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ HAVING conditions
|
|
||||||
|
|
||||||
{{Doctrine_Query}} provides {{having()}} method for adding {{HAVING}} conditions to the DQL query. This method is identical in function to the {{Doctrine_Query::where()}} method.
|
|
||||||
|
|
||||||
If you call {{having()}} multiple times, the conditions are ANDed together; if you want to OR a condition, use {{orHaving()}}.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$q = new Doctrine_Query();
|
|
||||||
|
|
||||||
$users = $q->select('u.name')
|
|
||||||
->from('User u')
|
|
||||||
->leftJoin('u.Phonenumber p');
|
|
||||||
->having('COUNT(p.id) > 3');
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Sorting query results
|
|
||||||
|
|
||||||
{{ORDER BY}} - part works in much same way as SQL {{ORDER BY}}.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$q = new Doctrine_Query();
|
|
||||||
|
|
||||||
// find all users, sort by name descending
|
|
||||||
|
|
||||||
$users = $q->from('User u')->orderby('u.name DESC');
|
|
||||||
|
|
||||||
// find all users sort by name ascending
|
|
||||||
|
|
||||||
$users = $q->from('User u')->orderby('u.name ASC');
|
|
||||||
|
|
||||||
// find all users and their emails, sort by email address in ascending order
|
|
||||||
|
|
||||||
$users = $q->from('User u')->leftJoin('u.Email e')->orderby('e.address');
|
|
||||||
|
|
||||||
// find all users and their emails, sort by user name and email address
|
|
||||||
|
|
||||||
$users = $q->from('User u')->leftJoin('u.Email e')
|
|
||||||
->addOrderby('u.name')->addOrderby('e.address');
|
|
||||||
|
|
||||||
// grab randomly 10 users
|
|
||||||
$users = $q->select('u.*, RAND() rand')->from('User u')->limit(10)->orderby('rand DESC');
|
|
||||||
</code>
|
|
||||||
|
|
@ -1,61 +0,0 @@
|
|||||||
+++ Introduction
|
|
||||||
|
|
||||||
In Doctrine you may express your queries in the native SQL dialect of your database. This is useful if you want to use the full power of your database vendor's features (like query hints or the CONNECT keyword in Oracle).
|
|
||||||
|
|
||||||
It should be noted that not all the sql is portable. So when you make database portable applications you might want to use the DQL API instead.
|
|
||||||
|
|
||||||
|
|
||||||
+++ Using SQL
|
|
||||||
|
|
||||||
The {{rawSql}} component works in much same way as {{Zend_Db_Select}}. You may use method overloading like {{$q->from()->where()}} or just use {{$q->parseQuery()}}. There are some differences though:
|
|
||||||
|
|
||||||
# In {{Doctrine_RawSql}} component you need to specify all the mapped table columns in curly brackets {} this is used for smart column aliasing.
|
|
||||||
# When joining multiple tables you need to specify the component paths with {{addComponent()}} method
|
|
||||||
|
|
||||||
The following example represents a very simple case where no {{addComponent()}} calls are needed.
|
|
||||||
Here we select all entities from table entity with all the columns loaded in the records.
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$query = new Doctrine_RawSql($conn);
|
|
||||||
|
|
||||||
$query->parseQuery("SELECT {entity.name} FROM entity");
|
|
||||||
|
|
||||||
$entities = $query->execute();
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Adding components
|
|
||||||
|
|
||||||
The following example represents a bit harder case where we select all entities and their associated phonenumbers using a left join. Again we wrap all the columns in curly brackets but we also specify what tables associate to which components.
|
|
||||||
|
|
||||||
First we specify that table entity maps to record class {{Entity}}.
|
|
||||||
|
|
||||||
Then we specify that table phonenumber maps to {{Entity.Phonenumber}} (meaning phonenumber associated with an entity).
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$query = new Doctrine_RawSql($conn);
|
|
||||||
|
|
||||||
$query->parseQuery("SELECT {entity.*}, {phonenumber.*}
|
|
||||||
FROM entity
|
|
||||||
LEFT JOIN phonenumber
|
|
||||||
ON phonenumber.entity_id = entity.id");
|
|
||||||
|
|
||||||
$query->addComponent("entity", "Entity");
|
|
||||||
$query->addComponent("phonenumber", "Entity.Phonenumber");
|
|
||||||
|
|
||||||
$entities = $query->execute();
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Method overloading
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$query = new Doctrine_RawSql($conn);
|
|
||||||
|
|
||||||
$query->select('{entity.name}')
|
|
||||||
->from('entity');
|
|
||||||
|
|
||||||
$query->addComponent("entity", "User");
|
|
||||||
|
|
||||||
$coll = $query->execute();
|
|
||||||
</code>
|
|
@ -1,3 +1,139 @@
|
|||||||
++ Introduction
|
++ Introduction
|
||||||
++ Levels of configuration
|
++ Levels of configuration
|
||||||
++ Setting attributes
|
++ General attributes
|
||||||
|
+++ Portability
|
||||||
|
|
||||||
|
Each database management system (DBMS) has it's own behaviors. For example, some databases capitalize field names in their output, some lowercase them, while others leave them alone. These quirks make it difficult to port your scripts over to another server type. PEAR Doctrine:: strives to overcome these differences so your program can switch between DBMS's without any changes.
|
||||||
|
|
||||||
|
You control which portability modes are enabled by using the portability configuration option. Configuration options are set via {{factory()}} and {{setOption()}}.
|
||||||
|
|
||||||
|
The portability modes are bitwised, so they can be combined using {{|}} and removed using {{^}}. See the examples section below on how to do this.
|
||||||
|
|
||||||
|
|
||||||
|
++++ Portability Mode Constants
|
||||||
|
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_ALL}} (default) : turn on all portability features. this is the default setting.
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_DELETE_COUNT}} : Force reporting the number of rows deleted. Some DBMS's don't count the number of rows deleted when performing simple {{DELETE FROM}} tablename queries. This mode tricks such DBMS's into telling the count by adding {{WHERE 1=1}} to the end of {{DELETE}} queries.
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_EMPTY_TO_NULL}} : Convert empty strings values to null in data in and output. Needed because Oracle considers empty strings to be null, while most other DBMS's know the difference between empty and null.
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_ERRORS}} : Makes certain error messages in certain drivers compatible with those from other DBMS's
|
||||||
|
|
||||||
|
Error Code Re-mappings:
|
||||||
|
|
||||||
|
||~ Driver ||~ Description ||~ Old Constant ||~ New Constant ||
|
||||||
|
|| mysql, mysqli || unique and primary key constraints || {{Doctrine::ERROR_ALREADY_EXISTS}} || {{Doctrine::ERROR_CONSTRAINT}} ||
|
||||||
|
|| mysql, mysqli || not-null constraints || {{Doctrine::ERROR_CONSTRAINT}} || {{Doctrine::ERROR_CONSTRAINT_NOT_NULL}} ||
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_FIX_ASSOC_FIELD_NAMES}} : This removes any qualifiers from keys in associative fetches. some RDBMS , like for example SQLite, will be default use the fully qualified name for a column in assoc fetches if it is qualified in a query.
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_FIX_CASE}} : Convert names of tables and fields to lower or upper case in all methods. The case depends on the {{field_case}} option that may be set to either {{CASE_LOWER}} (default) or {{CASE_UPPER}}
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_NONE}} : Turn off all portability features
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_NUMROWS}} : Enable hack that makes {{numRows()}} work in Oracle
|
||||||
|
|
||||||
|
: {{Doctrine::PORTABILITY_RTRIM}} : Right trim the data output for all data fetches. This does not applied in drivers for RDBMS that automatically right trim values of fixed length character values, even if they do not right trim value of variable length character values.
|
||||||
|
|
||||||
|
|
||||||
|
++++ Examples
|
||||||
|
|
||||||
|
Using {{setAttribute()}} to enable portability for lowercasing and trimming
|
||||||
|
|
||||||
|
<code type="php">
|
||||||
|
$conn->setAttribute('portability',
|
||||||
|
Doctrine::PORTABILITY_FIX_CASE | Doctrine::PORTABILITY_RTRIM);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
Using {{setAttribute()}} to enable all portability options except trimming
|
||||||
|
|
||||||
|
<code type="php">
|
||||||
|
$conn->setAttribute('portability',
|
||||||
|
Doctrine::PORTABILITY_ALL ^ Doctrine::PORTABILITY_RTRIM);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
|
||||||
|
+++ Identifier quoting
|
||||||
|
|
||||||
|
You can quote the db identifiers (table and field names) with {{quoteIdentifier()}}. The delimiting style depends on which database driver is being used.
|
||||||
|
|
||||||
|
NOTE: just because you CAN use delimited identifiers, it doesn't mean you SHOULD use them. In general, they end up causing way more problems than they solve. Anyway, it may be necessary when you have a reserved word as a field name (in this case, we suggest you to change it, if you can).
|
||||||
|
|
||||||
|
Some of the internal Doctrine methods generate queries. Enabling the {{quote_identifier}} attribute of Doctrine you can tell Doctrine to quote the identifiers in these generated queries. For all user supplied queries this option is irrelevant.
|
||||||
|
|
||||||
|
Portability is broken by using the following characters inside delimited identifiers:
|
||||||
|
|
||||||
|
* backtick (`) -- due to MySQL
|
||||||
|
* double quote (") -- due to Oracle
|
||||||
|
* brackets ([ or ]) -- due to Access
|
||||||
|
|
||||||
|
Delimited identifiers are known to generally work correctly under the following drivers:
|
||||||
|
|
||||||
|
* Mssql
|
||||||
|
* Mysql
|
||||||
|
* Oracle
|
||||||
|
* Pgsql
|
||||||
|
* Sqlite
|
||||||
|
* Firebird
|
||||||
|
|
||||||
|
When using the {{quote_identifiers}} option, all of the field identifiers will be automatically quoted in the resulting SQL statements:
|
||||||
|
|
||||||
|
<code type="php">
|
||||||
|
$conn->setAttribute('quote_identifiers', true);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
will result in a SQL statement that all the field names are quoted with the backtick '`' operator (in MySQL).
|
||||||
|
|
||||||
|
<code type="sql">
|
||||||
|
SELECT * FROM `sometable` WHERE `id` = '123'
|
||||||
|
</code>
|
||||||
|
|
||||||
|
as opposed to:
|
||||||
|
|
||||||
|
<code type="sql">
|
||||||
|
SELECT * FROM sometable WHERE id='123'
|
||||||
|
</code>
|
||||||
|
|
||||||
|
|
||||||
|
+++ Exporting
|
||||||
|
|
||||||
|
<code type="php">
|
||||||
|
$manager->setAttribute(Doctrine::ATTR_EXPORT, Doctrine::EXPORT_NONE);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
|
||||||
|
+++ Fetching strategy
|
||||||
|
|
||||||
|
<code type="php">
|
||||||
|
// sets the default collection type (fetching strategy)
|
||||||
|
$manager->setAttribute(Doctrine::ATTR_FETCHMODE, Doctrine::FETCH_LAZY);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
+++ Event listener
|
||||||
|
|
||||||
|
<code type="php">
|
||||||
|
// setting default event listener
|
||||||
|
$manager->setAttribute(Doctrine::ATTR_LISTENER, new MyListener());
|
||||||
|
</code>
|
||||||
|
++ Naming convention attributes
|
||||||
|
|
||||||
|
+++ Index name format
|
||||||
|
|
||||||
|
+++ Sequence name format
|
||||||
|
|
||||||
|
+++ Table name format
|
||||||
|
|
||||||
|
+++ Database name format
|
||||||
|
|
||||||
|
++ Validation attributes
|
||||||
|
|
||||||
|
+++ Validation
|
||||||
|
<code type="php">
|
||||||
|
// turns transactional validation on
|
||||||
|
$manager->setAttribute(Doctrine::ATTR_VLD, true);
|
||||||
|
</code>
|
||||||
|
+++ Automatic length validation
|
||||||
|
|
||||||
|
+++ Automatic type validation
|
||||||
|
@ -4,19 +4,26 @@ Doctrine has a three-level configuration structure. You can set configuration at
|
|||||||
: **Connection level** : The attributes set in connection level will take effect on each table in that connection.
|
: **Connection level** : The attributes set in connection level will take effect on each table in that connection.
|
||||||
: **Table level** : The attributes set in table level will take effect only on that table.
|
: **Table level** : The attributes set in table level will take effect only on that table.
|
||||||
|
|
||||||
|
In the following example we set an attribute at the global level:
|
||||||
<code type="php">
|
<code type="php">
|
||||||
// setting a global level attribute
|
// setting a global level attribute
|
||||||
$manager = Doctrine_Manager::getInstance();
|
$manager = Doctrine_Manager::getInstance();
|
||||||
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_VLD, false);
|
$manager->setAttribute(Doctrine::ATTR_VLD, false);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
In the next example above we override the global attribute on given connection.
|
||||||
|
<code type="php">
|
||||||
// setting a connection level attribute
|
// setting a connection level attribute
|
||||||
// (overrides the global level attribute on this connection)
|
// (overrides the global level attribute on this connection)
|
||||||
|
|
||||||
$conn = $manager->openConnection(new PDO('dsn', 'username', 'pw'));
|
$conn = $manager->openConnection(new PDO('dsn', 'username', 'pw'));
|
||||||
|
|
||||||
$conn->setAttribute(Doctrine::ATTR_VLD, true);
|
$conn->setAttribute(Doctrine::ATTR_VLD, true);
|
||||||
|
</code>
|
||||||
|
|
||||||
|
In the last example we override once again the connection level attribute in the table level.
|
||||||
|
<code type="php">
|
||||||
// setting a table level attribute
|
// setting a table level attribute
|
||||||
// (overrides the connection/global level attribute on this table)
|
// (overrides the connection/global level attribute on this table)
|
||||||
|
|
||||||
|
@ -1,151 +1,2 @@
|
|||||||
+++ Portability
|
|
||||||
|
|
||||||
Each database management system (DBMS) has it's own behaviors. For example, some databases capitalize field names in their output, some lowercase them, while others leave them alone. These quirks make it difficult to port your scripts over to another server type. PEAR Doctrine:: strives to overcome these differences so your program can switch between DBMS's without any changes.
|
|
||||||
|
|
||||||
You control which portability modes are enabled by using the portability configuration option. Configuration options are set via {{factory()}} and {{setOption()}}.
|
|
||||||
|
|
||||||
The portability modes are bitwised, so they can be combined using {{|}} and removed using {{^}}. See the examples section below on how to do this.
|
|
||||||
|
|
||||||
|
|
||||||
++++ Portability Mode Constants
|
|
||||||
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_ALL}} (default) : turn on all portability features. this is the default setting.
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_DELETE_COUNT}} : Force reporting the number of rows deleted. Some DBMS's don't count the number of rows deleted when performing simple {{DELETE FROM}} tablename queries. This mode tricks such DBMS's into telling the count by adding {{WHERE 1=1}} to the end of {{DELETE}} queries.
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_EMPTY_TO_NULL}} : Convert empty strings values to null in data in and output. Needed because Oracle considers empty strings to be null, while most other DBMS's know the difference between empty and null.
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_ERRORS}} : Makes certain error messages in certain drivers compatible with those from other DBMS's
|
|
||||||
|
|
||||||
Error Code Re-mappings:
|
|
||||||
|
|
||||||
||~ Driver ||~ Description ||~ Old Constant ||~ New Constant ||
|
|
||||||
|| mysql, mysqli || unique and primary key constraints || {{Doctrine::ERROR_ALREADY_EXISTS}} || {{Doctrine::ERROR_CONSTRAINT}} ||
|
|
||||||
|| mysql, mysqli || not-null constraints || {{Doctrine::ERROR_CONSTRAINT}} || {{Doctrine::ERROR_CONSTRAINT_NOT_NULL}} ||
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_FIX_ASSOC_FIELD_NAMES}} : This removes any qualifiers from keys in associative fetches. some RDBMS , like for example SQLite, will be default use the fully qualified name for a column in assoc fetches if it is qualified in a query.
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_FIX_CASE}} : Convert names of tables and fields to lower or upper case in all methods. The case depends on the {{field_case}} option that may be set to either {{CASE_LOWER}} (default) or {{CASE_UPPER}}
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_NONE}} : Turn off all portability features
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_NUMROWS}} : Enable hack that makes {{numRows()}} work in Oracle
|
|
||||||
|
|
||||||
: {{Doctrine::PORTABILITY_RTRIM}} : Right trim the data output for all data fetches. This does not applied in drivers for RDBMS that automatically right trim values of fixed length character values, even if they do not right trim value of variable length character values.
|
|
||||||
|
|
||||||
|
|
||||||
++++ Examples
|
|
||||||
|
|
||||||
Using {{setAttribute()}} to enable portability for lowercasing and trimming
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$conn->setAttribute('portability',
|
|
||||||
Doctrine::PORTABILITY_FIX_CASE | Doctrine::PORTABILITY_RTRIM);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
Using {{setAttribute()}} to enable all portability options except trimming
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$conn->setAttribute('portability',
|
|
||||||
Doctrine::PORTABILITY_ALL ^ Doctrine::PORTABILITY_RTRIM);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Identifier quoting
|
|
||||||
|
|
||||||
You can quote the db identifiers (table and field names) with {{quoteIdentifier()}}. The delimiting style depends on which database driver is being used.
|
|
||||||
|
|
||||||
NOTE: just because you CAN use delimited identifiers, it doesn't mean you SHOULD use them. In general, they end up causing way more problems than they solve. Anyway, it may be necessary when you have a reserved word as a field name (in this case, we suggest you to change it, if you can).
|
|
||||||
|
|
||||||
Some of the internal Doctrine methods generate queries. Enabling the {{quote_identifier}} attribute of Doctrine you can tell Doctrine to quote the identifiers in these generated queries. For all user supplied queries this option is irrelevant.
|
|
||||||
|
|
||||||
Portability is broken by using the following characters inside delimited identifiers:
|
|
||||||
|
|
||||||
* backtick (`) -- due to MySQL
|
|
||||||
* double quote (") -- due to Oracle
|
|
||||||
* brackets ([ or ]) -- due to Access
|
|
||||||
|
|
||||||
Delimited identifiers are known to generally work correctly under the following drivers:
|
|
||||||
|
|
||||||
* Mssql
|
|
||||||
* Mysql
|
|
||||||
* Oracle
|
|
||||||
* Pgsql
|
|
||||||
* Sqlite
|
|
||||||
* Firebird
|
|
||||||
|
|
||||||
When using the {{quote_identifiers}} option, all of the field identifiers will be automatically quoted in the resulting SQL statements:
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
$conn->setAttribute('quote_identifiers', true);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
will result in a SQL statement that all the field names are quoted with the backtick '`' operator (in MySQL).
|
|
||||||
|
|
||||||
<code type="sql">
|
|
||||||
SELECT * FROM `sometable` WHERE `id` = '123'
|
|
||||||
</code>
|
|
||||||
|
|
||||||
as opposed to:
|
|
||||||
|
|
||||||
<code type="sql">
|
|
||||||
SELECT * FROM sometable WHERE id='123'
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Table creation
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// turns automatic table creation off
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_CREATE_TABLES, false);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Fetching strategy
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// sets the default collection type (fetching strategy)
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_FETCHMODE, Doctrine::FETCH_LAZY);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Batch size
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// setting default batch size for batch collections
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_BATCH_SIZE, 7);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Session lockmode
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// setting default lockmode
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_LOCKMODE, Doctrine::LOCK_PESSIMISTIC);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Event listener
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// setting default event listener
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_LISTENER, new MyListener());
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Validation
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// turns transactional validation on
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_VLD, true);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
|
||||||
+++ Offset collection limit
|
|
||||||
|
|
||||||
<code type="php">
|
|
||||||
// sets the default offset collection limit
|
|
||||||
$manager->setAttribute(Doctrine::ATTR_COLL_LIMIT, 10);
|
|
||||||
</code>
|
|
||||||
|
|
||||||
|
@ -4,12 +4,13 @@
|
|||||||
+ Mapping relations
|
+ Mapping relations
|
||||||
+ Working with objects
|
+ Working with objects
|
||||||
+ Configuration
|
+ Configuration
|
||||||
+ Advanced components
|
|
||||||
+ DQL (Doctrine Query Language)
|
+ DQL (Doctrine Query Language)
|
||||||
+ Native SQL
|
+ Native SQL
|
||||||
+ Transactions
|
+ Transactions
|
||||||
+ Caching
|
+ Caching
|
||||||
|
+ Plugins
|
||||||
+ Database abstraction
|
+ Database abstraction
|
||||||
+ Technology
|
+ Technology
|
||||||
|
+ Exceptions and warnings
|
||||||
+ Real world examples
|
+ Real world examples
|
||||||
+ Coding standards
|
+ Coding standards
|
||||||
|
Loading…
x
Reference in New Issue
Block a user