Skip to content

Commit

Permalink
Fixed Phalcon\Mvc\Model\Metadata::initialize behaviour [#16393]
Browse files Browse the repository at this point in the history
  • Loading branch information
rudiservo committed Aug 9, 2023
1 parent 837dcd6 commit 1192ed1
Show file tree
Hide file tree
Showing 3 changed files with 107 additions and 97 deletions.
5 changes: 5 additions & 0 deletions CHANGELOG-5.0.md
Original file line number Diff line number Diff line change
Expand Up @@ -5,9 +5,14 @@
### Added
- Added `Phalcon\Mvc\Model::appendMessagedFrom` for code consistency and to add messages from another another model. [#16391](https://github.com/phalcon/cphalcon/issues/16391)
- Added `Phalcon\Autoload\Loader::isRegistered` for debugging purposes [#16391](https://github.com/phalcon/cphalcon/issues/16391)
- Added `Phalcon\Mvc\Model\Metadata::initializeMetadata` [#16393] (https://github.com/phalcon/cphalcon/issues/16393)
- Added `Phalcon\Mvc\Model\Metadata::initializeMetadata` [#16393] (https://github.com/phalcon/cphalcon/issues/16393)
- Added `Phalcon\Mvc\Model\Metadata::getMetaDataUniqueKey` [#16393] (https://github.com/phalcon/cphalcon/issues/16393)
- Added `Phalcon\Mvc\Model\Metadata::getColumnMapUniqueKey` [#16393] (https://github.com/phalcon/cphalcon/issues/16393)

### Changed
- Refactored `Phalcon\Mvc\Model::doLowUpdate` and `Phalcon\Mvc\Model::postSaveRelatedRecords` for better code logic and a clearer seperation of behaviour although it lead to partially repeated code.[#16391](https://github.com/phalcon/cphalcon/issues/16391)
- Cleaned `Phalcon\Mvc\Model\Metadata::initialize` [#16393] (https://github.com/phalcon/cphalcon/issues/16393)

### Fixed

Expand Down
190 changes: 96 additions & 94 deletions phalcon/Mvc/Model/MetaData.zep
Original file line number Diff line number Diff line change
Expand Up @@ -484,10 +484,10 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
let columnMap = this->getReverseColumnMap(model);

if typeof columnMap == "array" {
return isset columnMap[attribute];
return isset(columnMap[attribute]);
}

return isset this->readMetaData(model)[self::MODELS_DATA_TYPES][attribute];
return isset(this->readMetaData(model)[self::MODELS_DATA_TYPES][attribute]);
}

/**
Expand Down Expand Up @@ -525,21 +525,16 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
*/
final public function readColumnMap(<ModelInterface> model) -> array | null
{
var keyName, data;
var keyName;

if !globals_get("orm.column_renaming") {
return null;
}

let keyName = get_class_lower(model);

if !fetch data, this->columnMap[keyName] {
this->initialize(model, null, null, null);

let data = this->columnMap[keyName];
let keyName = this->getColumnMapUniqueKey(model);
if keyName !== null {
return this->columnMap[keyName];
}

return data;
return null;
}

/**
Expand All @@ -556,23 +551,16 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
*/
final public function readColumnMapIndex(<ModelInterface> model, int index)
{
var keyName, columnMapModel, map;
var keyName;

if !globals_get("orm.column_renaming") {
return null;
}

let keyName = get_class_lower(model);

if !fetch columnMapModel, this->columnMap[keyName] {
this->initialize(model, null, null, null);

let columnMapModel = this->columnMap[keyName];
let keyName = this->getColumnMapUniqueKey(model);
if keyName !== null {
return this->columnMap[keyName][index];
}

fetch map, columnMapModel[index];

return map;
return null;
}

/**
Expand All @@ -586,24 +574,14 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
* );
*```
*/
final public function readMetaData(<ModelInterface> model) -> array
final public function readMetaData(<ModelInterface> model) -> array | null
{
var source, schema;
string key;

let source = model->getSource(),
schema = model->getSchema();

/*
* Unique key for meta-data is created using class-name-schema-source
*/
let key = get_class_lower(model) . "-" . schema . source;

if !isset this->metaData[key] {
this->initialize(model, key, source, schema);
var key;
let key = this->getMetaDataUniqueKey(model);
if key !== null {
return this->metaData[key];
}

return this->metaData[key];
return null;
}

/**
Expand All @@ -618,24 +596,14 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
* );
*```
*/
final public function readMetaDataIndex(<ModelInterface> model, int index)
final public function readMetaDataIndex(<ModelInterface> model, int index) -> array | null
{
var source, schema;
string key;

let source = model->getSource(),
schema = model->getSchema();

/*
* Unique key for meta-data is created using class-name-schema-source
*/
let key = get_class_lower(model) . "-" . schema . source;

if !isset this->metaData[key][index] {
this->initialize(model, key, source, schema);
var key;
let key = this->getMetaDataUniqueKey(model);
if key !== null {
return this->metaData[key][index];
}

return this->metaData[key][index];
return null;
}

/**
Expand Down Expand Up @@ -766,44 +734,36 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
*/
final public function writeMetaDataIndex(<ModelInterface> model, int index, var data) -> void
{
var source, schema;
string key;

if unlikely (typeof data != "array" && typeof data != "string" && typeof data != "boolean") {
throw new Exception("Invalid data for index");
}

let source = model->getSource(),
schema = model->getSchema();

/*
* Unique key for meta-data is created using class-name-schema-table
*/
let key = get_class_lower(model) . "-" . schema . source;

if !isset this->metaData[key] {
this->initialize(model, key, source, schema);
var key;
let key = this->getMetaDataUniqueKey(model);
if key !== null {
let this->metaData[key][index] = data;
}
}

let this->metaData[key][index] = data;
/**
* Initialize old behaviour for compatability
*/
final protected function initialize(<ModelInterface> model, var key, var table, var schema)
{
this->initializeMetaData(model, key);
this->initializeColumnMap(model, key);
}

/**
* Initialize the metadata for certain table
*/
final protected function initialize(<ModelInterface> model, var key, var table, var schema)
final protected function initializeMetaData(<ModelInterface> model, var key) -> bool
{
var strategy, className, metaData, data, modelMetadata, modelColumnMap,
container, keyName;
var strategy, metaData, data, modelMetadata, container;
string prefixKey;

let strategy = null,
className = get_class(model);
let strategy = null;

if key !== null {
let metaData = this->metaData;

if !isset metaData[key] {
if false === isset(metaData[key]) {
/**
* The meta-data is read from the adapter always if not available in metaData property
*/
Expand All @@ -821,7 +781,7 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface

if unlikely typeof modelMetadata != "array" {
throw new Exception(
"Invalid meta-data for model " . className
"Invalid meta-data for model " . get_class(model)
);
}
} else {
Expand All @@ -847,53 +807,61 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface
this->{"write"}(prefixKey, modelMetadata);
}
}
return true;
}
return false;
}

/**
* Initialize ColumnMap for a certain table
*/
final protected function initializeColumnMap(<ModelInterface> model, key) -> bool
{
var strategy, data, modelColumnMap, container;
string prefixKey;
/**
* Check for a column map, store in columnMap in order and reversed order
*/
if !globals_get("orm.column_renaming") {
return null;
return false;
}

let keyName = strtolower(className);

if isset this->columnMap[keyName] {
return null;
if true === isset(this->columnMap[key]) {
return false;
}

/**
* Create the map key name
* Check if the meta-data is already in the adapter
*/
let prefixKey = "map-" . keyName,
let prefixKey = "map-" . key,
data = this->{"read"}(prefixKey);

if data !== null {
let this->columnMap[keyName] = data;
let this->columnMap[key] = data;

return null;
return false;
}

/**
* Get the meta-data extraction strategy
*/
if typeof strategy != "object" {
let container = this->getDI(),
strategy = this->getStrategy();
}

let container = this->getDI(),
strategy = this->getStrategy();

/**
* Get the meta-data
* Update the column map locally
*/
let modelColumnMap = strategy->getColumnMaps(model, container),
this->columnMap[keyName] = modelColumnMap;
this->columnMap[key] = modelColumnMap;

/**
* Write the data to the adapter
*/
this->{"write"}(prefixKey, modelColumnMap);
return true;
}

/**
Expand Down Expand Up @@ -928,4 +896,38 @@ abstract class MetaData implements InjectionAwareInterface, MetaDataInterface

return value;
}

/**
* Returns a MetaData Unique key for meta-data is created using className
*
* @return string
*/
public final function getMetaDataUniqueKey(<ModelInterface> model) -> string | null
{
string key;
let key = get_class_lower(model);
if false === isset(this->metaData[key]) {
if false === this->initializeMetaData(model, key) {
return null;
}
}
return key;
}

/**
* Returns a ColumnMap Unique key for meta-data is created using className
*
* @return string
*/
public final function getColumnMapUniqueKey(<ModelInterface> model) -> string | null
{
string key;
let key = get_class_lower(model);
if false === isset(this->columnMap[key]) {
if false === this->initializeColumnMap(model, key) {
return null;
}
}
return key;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -87,6 +87,7 @@ public function mvcModelMetadataGetAttributesRedis(
'photo_id',
];
$actual = $metadata->getAttributes($model);
$columnMap = $metadata->getColumnMap($model);
$I->assertEquals($expected, $actual);

$model = new AlbumPhoto();
Expand All @@ -97,6 +98,7 @@ public function mvcModelMetadataGetAttributesRedis(
'position',
];
$actual = $metadata->getAttributes($model);
$columnMap = $metadata->getColumnMap($model);
$I->assertEquals($expected, $actual);

$model = new Photo();
Expand All @@ -120,6 +122,7 @@ public function mvcModelMetadataGetAttributesRedis(
'wins',
];
$actual = $metadata->getAttributes($model);
$columnMap = $metadata->getColumnMap($model);
$I->assertEquals($expected, $actual);

$service = $adapter->getAdapter();
Expand Down Expand Up @@ -165,7 +168,7 @@ private function getExamples(): array
private function getKeyData(): array
{
return [
'meta-phalcon\tests\fixtures\models\albumphoto-album_photo' => [
'meta-phalcon\tests\fixtures\models\albumphoto' => [
0 => [
'id',
'photo_id',
Expand Down Expand Up @@ -220,7 +223,7 @@ private function getKeyData(): array
0 => null,
1 => null,
],
'meta-phalcon\tests\fixtures\models\photo-photo' => [
'meta-phalcon\tests\fixtures\models\photo' => [
0 => [
'id',
'date_uploaded',
Expand Down Expand Up @@ -345,7 +348,7 @@ private function getKeyData(): array
0 => null,
1 => null,
],
'meta-phalcon\tests\fixtures\models\album-album' => [
'meta-phalcon\tests\fixtures\models\album' => [
0 => [
'id',
'name',
Expand Down

0 comments on commit 1192ed1

Please sign in to comment.