[DC-845] One of our Foreign Keys is not being inserted/passed Created: 27/Aug/10 Updated: 27/Aug/10 |
|
| Status: | Open |
| Project: | Doctrine 1 |
| Component/s: | Record, Relations, Transactions |
| Affects Version/s: | 1.2.0, 1.2.1, 1.2.2, 1.2.3 |
| Fix Version/s: | None |
| Type: | Bug | Priority: | Major |
| Reporter: | charles wisniewski | Assignee: | Jonathan H. Wage |
| Resolution: | Unresolved | Votes: | 0 |
| Labels: | None | ||
| Environment: |
Linux ubuntu 2.6.31-22-generic #63-Ubuntu SMP Thu Aug 19 00:23:50 UTC 2010 x86_64 GNU/Linux |
||
| Description |
|
We are working on a symfony/doctrine project and have come to a near halt on development. We feel that now, it may be a bug/feature in doctrine, regarding foreign keys Part of our model includes a join table that references three different table. Below is a diagram of what the model looks like, and the relevant portion of our schema.yml is at the bottom. Image of our schema: http://imgur.com/dfFYI.png We have a form that contains a set of embedded forms that attempt to create a new Person entry and add rows to the join table, adding items to the PersonName table as needed. The form attempts to do this by creating and saving PersonName objects with NameType parameters, but are running into the problem of Doctrine not including that column when trying to do an insert into the join table. Part of the problem seems to be caused by the Doctrine_Connection_UnitOfWork::saveAssociations method: foreach ($v->getInsertDiff() as $r) { $assocRecord = $assocTable->create(); $assocRecord->set($assocTable->getFieldName($rel->getForeign()), $r); $assocRecord->set($assocTable->getFieldName($rel->getLocal()), $record); $this->saveGraph($assocRecord); }Are we correct in understanding that this means that Doctrine 1.2 does not support tables with multiple foreign keys in this scenario? Here is the relevant portion of schema.yml: agPerson: As a caveat: we've noticed that sfdoctrineguard group table, has such a relationship: mysql> describe sf_guard_user_group;
-----------
----------- i.e. IT has two foreign keys taken into account |
[DC-984] Pessimistic locking locks entire table rather than record Created: 16/Mar/11 Updated: 13/Dec/12 |
|
| Status: | Open |
| Project: | Doctrine 1 |
| Component/s: | Transactions |
| Affects Version/s: | 1.2.4 |
| Fix Version/s: | None |
| Type: | Bug | Priority: | Major |
| Reporter: | Barry O'Donovan | Assignee: | Jonathan H. Wage |
| Resolution: | Unresolved | Votes: | 1 |
| Labels: | None | ||
| Environment: |
Standard LAMP stack using current SVN from http://svn.doctrine-project.org/branches/1.2/lib/Doctrine/Locking/Manager |
||
| Attachments: |
|
| Description |
|
When using pessimistic locking as described in: the locking manager locks the entire table rather than the specific object. This should be clear from the attached patch which corrects the issue (assuming I have correctly interpreted the intention of pessimistic locking!). The current behavior will have worked as expected for users but it will have locked far more than was intended and may thus have affected performance. NB: I can confirm this works for non-composite keys but please review and test for composite keys as I have no such tables to hand. |
| Comments |
| Comment by Barry O'Donovan [ 18/Oct/11 ] |
|
Folks - just wondering if anyone had a chance to look at this as, while not critical, it does appear to be a genuinely major performance issue. |
| Comment by Grégoire Paris [ 13/Dec/12 ] |
|
Duplicate with more information : http://www.doctrine-project.org/jira/browse/DC-185 |
[DC-526] Savepoint-rollback ignored in nested transaction context. Created: 26/Feb/10 Updated: 06/Aug/10 |
|
| Status: | Open |
| Project: | Doctrine 1 |
| Component/s: | Transactions |
| Affects Version/s: | 1.2.1 |
| Fix Version/s: | None |
| Type: | Bug | Priority: | Major |
| Reporter: | Michael Nielsen | Assignee: | Jonathan H. Wage |
| Resolution: | Unresolved | Votes: | 0 |
| Labels: | None | ||
| Description |
|
The example from the documentation on savepoints: try { $conn->beginTransaction(); // do some operations here // creates a new savepoint called mysavepoint $conn->beginTransaction('mysavepoint'); try { // do some operations here $conn->commit('mysavepoint'); } catch(Exception $e) { $conn->rollback('mysavepoint'); # (a) } $conn->commit(); } catch(Exception $e) { $conn->rollback(); } What seems to be a bug to me: (a) doesn't actually do a savepoint-rollback if reached, but rather returns false as soon as the nesting level is seen to be > 1. |
| Comments |
| Comment by Jonathan H. Wage [ 15/Mar/10 ] |
|
What rdbms are you using? Does it support this feature? |
| Comment by Michael Nielsen [ 15/Mar/10 ] |
|
I use MySQL 5.0.51/InnoDB. It is supported and the doctrine-example does indeed work, if I hack the rollback-method a bit. 316 public function rollback($savepoint = null) 317 { 318 if ($this->_nestingLevel == 0) { 319 throw new Doctrine_Transaction_Exception("Rollback failed. There is no active transaction."); 320 } 321 322 $this->conn->connect(); 323 324 if ($this->_internalNestingLevel >= 1 && $this->_nestingLevel > 1) { 325 $this->_internalNestingLevel--; 326 $this->_nestingLevel--; 327 return false; 328 } else if ($this->_nestingLevel > 1) { 329 $this->_nestingLevel--; 330 return false; 331 } 332 333 $listener = $this->conn->getAttribute(Doctrine_Core::ATTR_LISTENER); 334 335 if ( ! is_null($savepoint)) { [...] The problem is that in a nested context, the rollback-method never does anything but a nesting-level decrement and a false-return, regardless of savepoints. So in the doctrine-example, (a) just ends up at the false-return at line 327 or 330, rather than reaching the savepoint-rollback-block starting at line 335. And so the command is never sent to MySQL. |
| Comment by Jonathan H. Wage [ 15/Mar/10 ] |
|
Do you have a patch/diff that fixes the issue for you? |
| Comment by Michael Nielsen [ 15/Mar/10 ] |
|
I just skipped the nestingLevel-section in case of a savepoint. I have not spent any time reviewing how (un)healthy that might be for the level counters and the method in general, but it fixes my current application of it. @@ -321,14 +321,16 @@
$this->conn->connect();
- if ($this->_internalNestingLevel >= 1 && $this->_nestingLevel > 1) {
- $this->_internalNestingLevel--;
- $this->_nestingLevel--;
- return false;
- } else if ($this->_nestingLevel > 1) {
- $this->_nestingLevel--;
- return false;
- }
+ if (is_null($savepoint)) {
+ if ($this->_internalNestingLevel >= 1 && $this->_nestingLevel > 1) {
+ $this->_internalNestingLevel--;
+ $this->_nestingLevel--;
+ return false;
+ } else if ($this->_nestingLevel > 1) {
+ $this->_nestingLevel--;
+ return false;
+ }
+ }
$listener = $this->conn->getAttribute(Doctrine_Core::ATTR_LISTENER);
|
| Comment by Jonathan H. Wage [ 08/Jun/10 ] |
|
The change unfortunately breaks the tests. |
| Comment by Hendri Kurniawan [ 06/Aug/10 ] |
|
Hi Jonathan, I can also replicate and confirm the issue. I found a workaround that will fix this issue. The patch is for Doctrine/Transaction.php @@ -214,9 +214,9 @@
}
$listener->postTransactionBegin($event);
}
- }
$level = ++$this->_nestingLevel;
+ }
return $level;
}
@@ -244,7 +244,7 @@
$listener = $this->conn->getAttribute(Doctrine_Core::ATTR_LISTENER);
if ( ! is_null($savepoint)) {
- $this->_nestingLevel -= $this->removeSavePoints($savepoint);
+ $this->removeSavePoints($savepoint);
$event = new Doctrine_Event($this, Doctrine_Event::SAVEPOINT_COMMIT);
@@ -333,7 +333,7 @@
$listener = $this->conn->getAttribute(Doctrine_Core::ATTR_LISTENER);
if ( ! is_null($savepoint)) {
- $this->_nestingLevel -= $this->removeSavePoints($savepoint);
+ $this->removeSavePoints($savepoint);
$event = new Doctrine_Event($this, Doctrine_Event::SAVEPOINT_ROLLBACK);
@@ -507,7 +507,10 @@
*/
public function beginInternalTransaction($savepoint = null)
{
+ if (is_null($savepoint)) {
$this->_internalNestingLevel++;
+ }
+
return $this->beginTransaction($savepoint);
}
Thanks |