diff --git a/src/Adapter/AdapterInterface.php b/src/Adapter/AdapterInterface.php index 6d3ee2c..61567a2 100644 --- a/src/Adapter/AdapterInterface.php +++ b/src/Adapter/AdapterInterface.php @@ -15,20 +15,7 @@ interface AdapterInterface { public function connect() : object /* | PdoObject|mixed */; public function buildDataSourceName() : string; public function setup(array $configuration) : void; - public function escapeIdentifier(string $segment, int $type) : string; - public function defaultEngine() : ? string; - public function writableValue(/* mixed */ $value); /*: mixed*/ - - - /* public function databaseName() : string; - public function mapFieldType(FieldDefinition $field) : string; - public function schemaTable(string $databaseName, string $tableName) /*: object|EntityCollection -*/ public function repositoryClass() : string; public function queryBuilderClass() : string; - public function tableSyntax() : array; - public function whitelistAttributes(array &$parameters) : void; - public function generateAlterColumn(FieldDefinition $definition, array $field) : string|\Stringable; - public function splitAlterQuery() : bool; } diff --git a/src/Adapter/MsSQL.php b/src/Adapter/MsSQL.php index ed7fc6a..ae6ccaa 100644 --- a/src/Adapter/MsSQL.php +++ b/src/Adapter/MsSQL.php @@ -9,10 +9,10 @@ use Ulmus\Exception\AdapterConfigurationException; use Ulmus\Ulmus; use Ulmus\Migration\FieldDefinition; -use Ulmus\{Entity\InformationSchema\Table, Repository, QueryBuilder}; +use Ulmus\{Entity\InformationSchema\Table, Migration\MigrateInterface, Repository, QueryBuilder}; -class MsSQL implements AdapterInterface { - use DefaultAdapterTrait; +class MsSQL implements AdapterInterface, MigrateInterface, SqlAdapterInterface { + use SqlAdapterTrait; const ALLOWED_ATTRIBUTES = [ 'default', 'primary_key', 'auto_increment', diff --git a/src/Adapter/MySQL.php b/src/Adapter/MySQL.php index 93bd9e8..b50de69 100644 --- a/src/Adapter/MySQL.php +++ b/src/Adapter/MySQL.php @@ -3,6 +3,7 @@ namespace Ulmus\Adapter; use Ulmus\Entity\InformationSchema\Table; +use Ulmus\Migration\MigrateInterface; use Ulmus\QueryBuilder; use Ulmus\Repository; use Ulmus\Common\PdoObject; @@ -11,8 +12,8 @@ use Ulmus\Exception\AdapterConfigurationException; use Ulmus\Ulmus; use Ulmus\Migration\FieldDefinition; -class MySQL implements AdapterInterface { - use DefaultAdapterTrait; +class MySQL implements AdapterInterface, MigrateInterface, SqlAdapterInterface { + use SqlAdapterTrait; const ALLOWED_ATTRIBUTES = [ 'default', 'primary_key', 'auto_increment', 'update', @@ -21,13 +22,13 @@ class MySQL implements AdapterInterface { const DSN_PREFIX = "mysql"; public string $hostname; - + public string $database; - - public string $username; - - public string $password; - + + protected string $username; + + protected string $password; + public string $charset = "utf8mb4"; public ? string $socket; diff --git a/src/Adapter/SQLite.php b/src/Adapter/SQLite.php index 5a90d55..3cae7fb 100644 --- a/src/Adapter/SQLite.php +++ b/src/Adapter/SQLite.php @@ -8,10 +8,11 @@ use Ulmus\ConnectionAdapter; use Ulmus\Entity\Sqlite\Table; use Ulmus\Exception\AdapterConfigurationException; use Ulmus\Migration\FieldDefinition; -use Ulmus\{Repository, QueryBuilder, Ulmus}; +use Ulmus\{Migration\MigrateInterface, Repository, QueryBuilder, Ulmus}; + +class SQLite implements AdapterInterface, MigrateInterface, SqlAdapterInterface { + use SqlAdapterTrait; -class SQLite implements AdapterInterface { - use DefaultAdapterTrait; const ALLOWED_ATTRIBUTES = [ 'default', 'primary_key', 'auto_increment' ]; diff --git a/src/Adapter/SqlAdapterInterface.php b/src/Adapter/SqlAdapterInterface.php new file mode 100644 index 0000000..3a5bfea --- /dev/null +++ b/src/Adapter/SqlAdapterInterface.php @@ -0,0 +1,9 @@ +adapter ?: false; + } } diff --git a/src/Common/EntityResolver.php b/src/Common/EntityResolver.php index 3f4d00f..7c792b5 100644 --- a/src/Common/EntityResolver.php +++ b/src/Common/EntityResolver.php @@ -61,16 +61,7 @@ class EntityResolver { public function searchField($name) : null|array { - try{ - return $this->field($name, self::KEY_ENTITY_NAME, false) ?: $this->field($name, self::KEY_COLUMN_NAME, false); - } - catch(\Throwable $e) { - if ( $throwException) { - throw new \InvalidArgumentException("Can't find entity field's column named `$name` from entity {$this->entityClass}"); - } - } - - return null; + return $this->field($name, self::KEY_ENTITY_NAME, false) ?: $this->field($name, self::KEY_COLUMN_NAME, false); } public function fieldList($fieldKey = self::KEY_ENTITY_NAME, bool $skipVirtual = false) : array @@ -173,7 +164,7 @@ class EntityResolver { return $table->name ?? ""; } - public function tableAnnotation($required = false) : Table|Attribute\Obj\Table + public function tableAnnotation($required = false) : null|Table|Attribute\Obj\Table { if ( null === $table = $this->getTableAttribute() ) { if ($required) { @@ -191,10 +182,10 @@ class EntityResolver { public function sqlAdapter() : \Ulmus\ConnectionAdapter { - if ( null !== $table = $this->getTableAttribute() ) { - if ( $table->adapter ?? null ) { - if ( null === ( $adapter = \Ulmus\Ulmus::$registeredAdapters[$table->adapter] ?? null ) ) { - throw new \Exception("Requested database adapter `{$table->adapter}` is not registered."); + if ( $adapterObj = $this->getAdapterInterfaceAttribute()) { + if ( false !== $adapterName = $adapterObj->adapter() ) { + if ( null === ( $adapter = \Ulmus\Ulmus::$registeredAdapters[$adapterName] ?? null ) ) { + throw new \Exception("Requested database adapter `$adapterName` is not registered."); } else { return $adapter; @@ -250,6 +241,11 @@ class EntityResolver { return null; } + protected function getAdapterInterfaceAttribute() : null|object + { + return $this->getAttributeImplementing(Attribute\Obj\AdapterAttributeInterface::class); + } + protected function getTableAttribute() { return $this->getAnnotationFromClassname(Attribute\Obj\Table::class, false) ?: $this->getAnnotationFromClassname( Table::class, false ); @@ -294,6 +290,17 @@ class EntityResolver { return null; } + public function getAttributeImplementing(string $interface) : ? object + { + foreach (array_reverse($this->class['tags']) as $item) { + if ($item['object'] instanceof $interface) { + return $item['object']; + } + } + + return null; + } + public function instanciateAnnotationObject(array|\ReflectionAttribute $tagDefinition) : object { if ($tagDefinition instanceof \ReflectionAttribute) { diff --git a/src/ConnectionAdapter.php b/src/ConnectionAdapter.php index 162bad3..dd29d44 100644 --- a/src/ConnectionAdapter.php +++ b/src/ConnectionAdapter.php @@ -53,7 +53,7 @@ class ConnectionAdapter public function connect() : self { $this->pdo = $this->adapter->connect(); - + return $this; } diff --git a/src/EntityTrait.php b/src/EntityTrait.php index 1879dea..26a8723 100644 --- a/src/EntityTrait.php +++ b/src/EntityTrait.php @@ -27,7 +27,7 @@ trait EntityTrait { public array $entityLoadedDataset = []; #[Ignore] - public function __construct() { + public function __construct(array $dataset = null) { $this->resetVirtualProperties(); } diff --git a/src/Migration/MigrateInterface.php b/src/Migration/MigrateInterface.php new file mode 100644 index 0000000..b8d1d4c --- /dev/null +++ b/src/Migration/MigrateInterface.php @@ -0,0 +1,15 @@ +loadOneFromField($primaryKey, $value) : $this->wherePrimaryKey($value)->loadOne(); } - public function loadAll() : EntityCollection + public function loadAll () : EntityCollection { return $this->selectSqlQuery()->collectionFromQuery(); } @@ -590,7 +590,7 @@ class Repository $pkField = key($primaryKeyField); - return $this->where($primaryKeyField[$pkField]->name ?? $pkField, $value); + return $this->where($this->entityClass::field($primaryKeyField[$pkField]->name ?? $pkField), $value); } public function withJoin(string|array $fields, array $options = []) : self diff --git a/src/Repository/RelationBuilder.php b/src/Repository/RelationBuilder.php index 992c513..a9cdc39 100644 --- a/src/Repository/RelationBuilder.php +++ b/src/Repository/RelationBuilder.php @@ -187,7 +187,7 @@ class RelationBuilder return $relation->bridgeField ?? false ? $relation->bridge::entityCollection() : $relationRelation->entity::entityCollection(); } - return new $class(); + throw new \InvalidArgumentException("Unknown or no relation was provided as relation type."); } protected function fetchFromDataset($name, ? array $data = null) : object|bool @@ -227,6 +227,9 @@ class RelationBuilder elseif ( substr($key, 0, $len ) === sprintf(static::JOIN_FIELD_SEPARATOR, strtolower($name)) ) { $vars[substr($key, $len)] = $value; } + else { + # load here for API objects ! + } } if ($vars) {