diff options
Diffstat (limited to 'app/frontend/db')
-rw-r--r-- | app/frontend/db/ActiveRecord.php | 69 | ||||
-rw-r--r-- | app/frontend/db/DBConnection.php | 28 | ||||
-rw-r--r-- | app/frontend/db/DBModule.php | 40 | ||||
-rw-r--r-- | app/frontend/db/DBTransaction.php | 53 | ||||
l--------- | app/frontend/db/config.json | 1 | ||||
-rw-r--r-- | app/frontend/db/config.xml | 10 |
6 files changed, 201 insertions, 0 deletions
diff --git a/app/frontend/db/ActiveRecord.php b/app/frontend/db/ActiveRecord.php new file mode 100644 index 0000000..1176767 --- /dev/null +++ b/app/frontend/db/ActiveRecord.php @@ -0,0 +1,69 @@ +<?php + +class ActiveRecord extends TActiveRecord { + + private function _getMappedPropertyName($name) { + if (isset(static::$COLUMN_MAPPING[$name])) { + return static::$COLUMN_MAPPING[$name]; + } + return $name; + } + + const DYNAMIC_METHODS = [ + 'findby', + 'findallby', + 'deleteby', + 'deleteallby' + ]; + + private function _getMappedMethodName($method) { + if (static::$COLUMN_MAPPING) { + $methodParts = []; + if (preg_match('/^(' . implode('|', self::DYNAMIC_METHODS) . ')(.*)$/i', $method, $methodParts)) { + $methodParameters = []; + $columnString = implode( + '|', + array_merge( + array_keys(static::$COLUMN_MAPPING), + array_values(static::$COLUMN_MAPPING) + ) + ); + $parameterRegex = '/(' . $columnString . ')(and|_and_|or|_or_)?/i'; + $method = $methodParts[1]; + if (preg_match_all($parameterRegex, $methodParts[2], $methodParameters, PREG_SET_ORDER)) { + foreach ($methodParameters as $parameter) { + $mappedColumn = array_search($parameter[1], static::$COLUMN_MAPPING); + $method .= ($mappedColumn !== FALSE) ? $mappedColumn : $parameter[1]; + if (count($parameter) > 2) { + $method .= $parameter[2]; + } + } + } + } + } + return $method; + } + + public function __get($name) { + $name = $this->_getMappedPropertyName($name); + if (property_exists($this, $name)) { + return $this->$name; + } + return parent::__get($name); + } + + public function __set($name, $value) { + $name = $this->_getMappedPropertyName($name); + if (property_exists($this, $name)) { + return $this->$name = $value; + } + return parent::__set($name, $value); + } + + public function __call($method, $args) { + return parent::__call($this->_getMappedMethodName($method), $args); + } + +} + +?> diff --git a/app/frontend/db/DBConnection.php b/app/frontend/db/DBConnection.php new file mode 100644 index 0000000..92ab0fb --- /dev/null +++ b/app/frontend/db/DBConnection.php @@ -0,0 +1,28 @@ +<?php + +Prado::using('Application.db.DBTransaction'); +Prado::using('System.Data.TDbConnection'); + +class DBConnection extends TDbConnection { + + private $_transaction = NULL; + public function getCurrentTransaction() { + if (!$this->_transaction->getActive()) { + $this->_transaction = NULL; + } + return $this->_transaction; + } + + public function beginTransaction() { + if ($this->_transaction && $this->_transaction->getActive()) { + $this->_transaction->beginNestedTransaction(); + } + else { + $this->_transaction = parent::beginTransaction(); + } + return $this->_transaction; + } + +} + +?> diff --git a/app/frontend/db/DBModule.php b/app/frontend/db/DBModule.php new file mode 100644 index 0000000..462b6f6 --- /dev/null +++ b/app/frontend/db/DBModule.php @@ -0,0 +1,40 @@ +<?php + +Prado::using('System.Data.TDataSourceConfig'); + +class DBModule extends TDataSourceConfig { + + private $_config; + + public function init($xml) { + $newXML = new TXmlElement('module'); + foreach ($xml->getAttributes() as $attr => $val) { + $newXML->setAttribute($attr, $val); + } + $dbXML = new TXmlElement('database'); + $config = json_decode(file_get_contents( + Prado::getPathOfNamespace($this->_config, '.json') + )); + if (isset($config->cset)) { + $dbXML->setAttribute('Charset', $config->cset); + } + $dbXML->setAttribute('Username', $config->user); + $dbXML->setAttribute('Password', $config->pass); + $dbXML->setAttribute( + 'ConnectionString', + sprintf( + '%s:host=%s;dbname=%s', + $config->type, $config->host, $config->name + ) + ); + $newXML->Elements[] = $dbXML; + parent::init($newXML); + } + + public function setConfig($config) { + $this->_config = TPropertyValue::ensureString($config); + } + +} + +?> diff --git a/app/frontend/db/DBTransaction.php b/app/frontend/db/DBTransaction.php new file mode 100644 index 0000000..b176453 --- /dev/null +++ b/app/frontend/db/DBTransaction.php @@ -0,0 +1,53 @@ +<?php + +Prado::using('Application.db.DBConnection'); +Prado::using('System.Data.TDbTransaction'); + +class DBTransaction extends TDbTransaction { + + private $_nestedCount = 0; + private $_rolledBack = FALSE; + + public function beginNestedTransaction() { + if ($this->getActive()) { + $this->_nestedCount++; + } + } + + public function commit() { + if ($this->_rolledBack) { + $childTransaction = (bool)($this->_nestedCount); + $this->rollback(); + if (!$childTransaction) { + throw new TDbException('Nested transaction was rolled back, unable to commit.'); + } + } + else { + if ($this->_nestedCount) { + $this->_nestedCount--; + } + else { + parent::commit(); + } + } + } + + public function rollback() { + if (!$this->getActive()) { + $this->_nestedCount = 0; + return; + } + if ($this->_nestedCount) { + $this->_rolledBack = TRUE; + $this->_nestedCount--; + } + else { + parent::rollback(); + $this->_nestedCount = 0; + $this->_rolledBack = FALSE; + } + } + +} + +?> diff --git a/app/frontend/db/config.json b/app/frontend/db/config.json new file mode 120000 index 0000000..89a492f --- /dev/null +++ b/app/frontend/db/config.json @@ -0,0 +1 @@ +../../../config/db.json
\ No newline at end of file diff --git a/app/frontend/db/config.xml b/app/frontend/db/config.xml new file mode 100644 index 0000000..3210593 --- /dev/null +++ b/app/frontend/db/config.xml @@ -0,0 +1,10 @@ +<?xml version="1.0" encoding="utf-8"?> +<configuration> + <modules> + <module id="db" + class="Application.db.DBModule" + config="Application.db.config" + ConnectionClass="Application.db.DBConnection" + DbConnection.TransactionClass="Application.db.DBTransaction" /> + </modules> +</configuration> |