From fb389109a92a507bbacddcca71043f9a922cd973 Mon Sep 17 00:00:00 2001 From: Nikolaos Dimopoulos Date: Sat, 7 Sep 2019 10:53:27 -0400 Subject: [PATCH] [#13697] - Removed collection classes for mongo --- phalcon/Mvc/Collection.zep | 1726 ----------------- phalcon/Mvc/Collection/Behavior.zep | 74 - .../Mvc/Collection/Behavior/SoftDelete.zep | 90 - .../Mvc/Collection/Behavior/Timestampable.zep | 90 - phalcon/Mvc/Collection/BehaviorInterface.zep | 31 - phalcon/Mvc/Collection/Document.zep | 100 - phalcon/Mvc/Collection/Exception.zep | 22 - phalcon/Mvc/Collection/Manager.zep | 378 ---- phalcon/Mvc/Collection/ManagerInterface.zep | 96 - phalcon/Mvc/CollectionInterface.zep | 132 -- 10 files changed, 2739 deletions(-) delete mode 100644 phalcon/Mvc/Collection.zep delete mode 100644 phalcon/Mvc/Collection/Behavior.zep delete mode 100644 phalcon/Mvc/Collection/Behavior/SoftDelete.zep delete mode 100644 phalcon/Mvc/Collection/Behavior/Timestampable.zep delete mode 100644 phalcon/Mvc/Collection/BehaviorInterface.zep delete mode 100644 phalcon/Mvc/Collection/Document.zep delete mode 100644 phalcon/Mvc/Collection/Exception.zep delete mode 100644 phalcon/Mvc/Collection/Manager.zep delete mode 100644 phalcon/Mvc/Collection/ManagerInterface.zep delete mode 100644 phalcon/Mvc/CollectionInterface.zep diff --git a/phalcon/Mvc/Collection.zep b/phalcon/Mvc/Collection.zep deleted file mode 100644 index 42d0213a4ae..00000000000 --- a/phalcon/Mvc/Collection.zep +++ /dev/null @@ -1,1726 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc; - -use Mongo; -use MongoCollection; -use MongoId; -use Phalcon\Di; -use Phalcon\Di\DiInterface; -use Phalcon\Di\InjectionAwareInterface; -use Phalcon\Messages\MessageInterface; -use Phalcon\Mvc\Collection\BehaviorInterface; -use Phalcon\Mvc\Collection\Document; -use Phalcon\Mvc\Collection\Exception; -use Phalcon\Mvc\Collection\ManagerInterface; -use Phalcon\Messages\Message as Message; -use Phalcon\Validation\ValidationInterface; -use Phalcon\Storage\Serializer\SerializerInterface; -use Serializable; - -/** - * Phalcon\Mvc\Collection - * - * This component implements a high level abstraction for NoSQL databases which - * works with documents - */ -abstract class Collection implements EntityInterface, CollectionInterface, InjectionAwareInterface, Serializable -{ - const DIRTY_STATE_DETACHED = 2; - const DIRTY_STATE_PERSISTENT = 0; - const DIRTY_STATE_TRANSIENT = 1; - const OP_CREATE = 1; - const OP_DELETE = 3; - const OP_NONE = 0; - const OP_UPDATE = 2; - - public _id; - - protected connection; - - protected container; - - protected dirtyState = 1; - - protected static disableEvents; - - protected errorMessages = []; - - protected modelsManager; - - protected operationMade = 0; - - protected static reserved; - - protected skipped = false; - - protected source; - - /** - * Phalcon\Mvc\Collection constructor - */ - final public function __construct( container = null, modelsManager = null) - { - /** - * We use a default DI if the user doesn't define one - */ - if typeof container != "object" { - let container = Di::getDefault(); - } - - if unlikely typeof container != "object" { - throw new Exception( - Exception::containerServiceNotFound( - "the services related to the ODM" - ) - ); - } - - let this->container = container; - - /** - * Inject the manager service from the DI - */ - if typeof modelsManager != "object" { - let modelsManager = container->getShared("collectionManager"); - if unlikely typeof modelsManager != "object" { - throw new Exception( - "The injected service 'modelsManager' is not valid" - ); - } - } - - /** - * Update the models-manager - */ - let this->modelsManager = modelsManager; - - /** - * The manager always initializes the object - */ - modelsManager->initialize(this); - - /** - * This allows the developer to execute initialization stuff every time - * an instance is created - */ - if method_exists(this, "onConstruct") { - this->{"onConstruct"}(); - } - } - - /** - * Sets up a behavior in a collection - */ - protected function addBehavior( behavior) -> void - { - ( this->modelsManager)->addBehavior(this, behavior); - } - - /** - * Perform an aggregation using the Mongo aggregation framework - */ - public static function aggregate(array parameters = null, array options = null) -> array - { - var className, model, connection, source; - - let className = get_called_class(); - - let model = new {className}(); - - let connection = model->getConnection(); - - let source = model->getSource(); - if unlikely empty source { - throw new Exception("Method getSource() returns empty string"); - } - - return connection->selectCollection(source)->aggregate( - parameters, - options - ); - } - - /** - * Appends a customized message on the validation process - * - *```php - * use \Phalcon\Messages\Message as Message; - * - * class Robots extends \Phalcon\Mvc\Model - * { - * public function beforeSave() - * { - * if ($this->name === "Peter") { - * $message = new Message( - * "Sorry, but a robot cannot be named Peter" - * ); - * - * $this->appendMessage(message); - * } - * } - * } - *``` - */ - public function appendMessage( message) - { - let this->errorMessages[] = message; - } - - /** - * Returns a cloned collection - */ - public static function cloneResult( collection, array! document) -> - { - var clonedCollection, key, value; - - let clonedCollection = clone collection; - for key, value in document { - clonedCollection->writeAttribute(key, value); - } - - if method_exists(clonedCollection, "afterFetch") { - clonedCollection->{"afterFetch"}(); - } - - return clonedCollection; - } - - /** - * Creates a collection based on the values in the attributes - */ - public function create() -> bool - { - var data, success, status, id, ok, collection; - bool exists; - - let collection = this->prepareCU(); - - /** - * Check the dirty state of the current operation to update the current - * operation - */ - let exists = false; - let this->operationMade = self::OP_CREATE; - - /** - * The messages added to the validator are reset here - */ - let this->errorMessages = []; - - /** - * Execute the preSave hook - */ - if this->preSave(this->container, self::disableEvents, exists) === false { - return false; - } - - let data = this->toArray(); - - let success = false; - - /** - * We always use safe stores to get the success state - * Save the document - */ - let status = collection->insert( - data, - [ - "w": true - ] - ); - - if fetch ok, status["ok"] && ok { - let success = true; - - if fetch id, data["_id"] { - let this->_id = id; - } - - let this->dirtyState = self::DIRTY_STATE_PERSISTENT; - } - - /** - * Call the postSave hooks - */ - return this->postSave( - self::disableEvents, - success, - exists - ); - } - - /** - * Creates a document based on the values in the attributes, if not found by - * criteria. Preferred way to avoid duplication is to create index o - * attribute - * - * ```php - * $robot = new Robot(); - * - * $robot->name = "MyRobot"; - * $robot->type = "Droid"; - * - * // Create only if robot with same name and type does not exist - * $robot->createIfNotExist( - * [ - * "name", - * "type", - * ] - * ); - * ``` - */ - public function createIfNotExist(array! criteria) -> bool - { - var exists, data, keys, query, success, status, doc, collection; - - if unlikely empty criteria { - throw new Exception( - "Criteria parameter must be array with one or more attributes of the model" - ); - } - - /** - * Choose a collection according to the collection name - */ - let collection = this->prepareCU(); - - /** - * Assume non-existence to fire beforeCreate events - no update does - * occur anyway - */ - let exists = false; - - /** - * Reset current operation - */ - - let this->operationMade = self::OP_NONE; - - /** - * The messages added to the validator are reset here - */ - let this->errorMessages = []; - - /** - * Execute the preSave hook - */ - if this->preSave(this->container, self::disableEvents, exists) === false { - return false; - } - - let keys = array_flip(criteria); - let data = this->toArray(); - - if unlikely array_diff_key(keys, data) { - throw new Exception( - "Criteria parameter must be array with one or more attributes of the model" - ); - } - - let query = array_intersect_key(data, keys); - - let success = false; - - /** - * $setOnInsert in conjunction with upsert ensures creating a new document - * "new": false returns null if new document created, otherwise new or old document could be returned - */ - let status = collection->findAndModify( - query, - [ - "$setOnInsert": data - ], - null, - [ - "new": false, - "upsert": true - ] - ); - - if status == null { - let doc = collection->findOne(query); - - if typeof doc == "array" { - let success = true; - let this->operationMade = self::OP_CREATE; - let this->_id = doc["_id"]; - } - } else { - this->appendMessage( - new Message("Document already exists") - ); - } - - /** - * Call the postSave hooks - */ - return this->postSave( - self::disableEvents, - success, - exists - ); - } - - /** - * Perform a count over a collection - * - *```php - * echo "There are ", Robots::count(), " robots"; - *``` - */ - public static function count(array parameters = null) -> int - { - var className, collection, connection; - - let className = get_called_class(); - - let collection = new {className}(); - - let connection = collection->getConnection(); - - return self::getGroupResultset(parameters, collection, connection); - } - - /** - * Deletes a model instance. Returning true on success or false otherwise. - * - * ```php - * $robot = Robots::findFirst(); - * - * $robot->delete(); - * - * $robots = Robots::find(); - * - * foreach ($robots as $robot) { - * $robot->delete(); - * } - * ``` - */ - public function delete() -> bool - { - var disableEvents, status, id, connection, source, collection, mongoId, - success, ok; - - if unlikely !fetch id, this->_id { - throw new Exception( - "The document cannot be deleted because it doesn't exist" - ); - } - - let disableEvents = self::disableEvents; - - if !disableEvents { - if this->fireEventCancel("beforeDelete") === false { - return false; - } - } - - if this->skipped === true { - return true; - } - - let connection = this->getConnection(); - - let source = this->getSource(); - if unlikely empty source { - throw new Exception("Method getSource() returns empty string"); - } - - /** - * Get the MongoCollection - */ - let collection = connection->selectCollection(source); - - if typeof id == "object" { - let mongoId = id; - } else { - /** - * Is the collection using implicit object Ids? - */ - if this->modelsManager->isUsingImplicitObjectIds(this) { - let mongoId = new MongoId(id); - } else { - let mongoId = id; - } - } - - let success = false; - - /** - * Remove the instance - */ - let status = collection->remove( - [ - "_id": mongoId - ], - [ - "w": true - ] - ); - - if typeof status != "array" { - return false; - } - - /** - * Check the operation status - */ - if fetch ok, status["ok"] { - if ok { - let success = true; - - if !disableEvents { - this->fireEvent("afterDelete"); - } - - let this->dirtyState = self::DIRTY_STATE_DETACHED; - } - } else { - let success = false; - } - - return success; - } - - /** - * Allows to query a set of records that match the specified conditions - * - * ```php - * // How many robots are there? - * $robots = Robots::find(); - * - * echo "There are ", count($robots), "\n"; - * - * // How many mechanical robots are there? - * $robots = Robots::find( - * [ - * [ - * "type" => "mechanical", - * ] - * ] - * ); - * - * echo "There are ", count(robots), "\n"; - * - * // Get and print virtual robots ordered by name - * $robots = Robots::findFirst( - * [ - * [ - * "type" => "virtual" - * ], - * "order" => [ - * "name" => 1, - * ] - * ] - * ); - * - * foreach ($robots as $robot) { - * echo $robot->name, "\n"; - * } - * - * // Get first 100 virtual robots ordered by name - * $robots = Robots::find( - * [ - * [ - * "type" => "virtual", - * ], - * "order" => [ - * "name" => 1, - * ], - * "limit" => 100, - * ] - * ); - * - * foreach ($robots as $robot) { - * echo $robot->name, "\n"; - * } - * ``` - */ - public static function find(array parameters = null) -> array - { - var className, collection; - - let className = get_called_class(); - let collection = new {className}(); - - return self::getResultset( - parameters, - collection, - collection->getConnection(), - false - ); - } - - /** - * Find a document by its id (_id) - * - * ```php - * // Find user by using \MongoId object - * $user = Users::findById( - * new \MongoId("545eb081631d16153a293a66") - * ); - * - * // Find user by using id as sting - * $user = Users::findById("45cbc4a0e4123f6920000002"); - * - * // Validate input - * if ($user = Users::findById($_POST["id"])) { - * // ... - * } - * ``` - */ - public static function findById(var id) -> | null - { - var className, collection, mongoId; - - if typeof id != "object" { - if !preg_match("/^[a-f\d]{24}$/i", id) { - return null; - } - - let className = get_called_class(); - - let collection = new {className}(); - - /** - * Check if the model use implicit ids - */ - if collection->getCollectionManager()->isUsingImplicitObjectIds(collection) { - let mongoId = new MongoId(id); - } else { - let mongoId = id; - } - } else { - let mongoId = id; - } - - return self::findFirst( - [ - [ - "_id": mongoId - ] - ] - ); - } - - /** - * Allows to query the first record that match the specified conditions - * - * ```php - * // What's the first robot in the robots table? - * $robot = Robots::findFirst(); - * - * echo "The robot name is ", $robot->name, "\n"; - * - * // What's the first mechanical robot in robots table? - * $robot = Robots::findFirst( - * [ - * [ - * "type" => "mechanical", - * ] - * ] - * ); - * - * echo "The first mechanical robot name is ", $robot->name, "\n"; - * - * // Get first virtual robot ordered by name - * $robot = Robots::findFirst( - * [ - * [ - * "type" => "mechanical", - * ], - * "order" => [ - * "name" => 1, - * ], - * ] - * ); - * - * echo "The first virtual robot name is ", $robot->name, "\n"; - * - * // Get first robot by id (_id) - * $robot = Robots::findFirst( - * [ - * [ - * "_id" => new \MongoId("45cbc4a0e4123f6920000002"), - * ] - * ] - * ); - * - * echo "The robot id is ", $robot->_id, "\n"; - * ``` - */ - public static function findFirst(array parameters = null) -> array - { - var className, collection, connection; - - let className = get_called_class(); - - let collection = new {className}(); - - let connection = collection->getConnection(); - - return self::getResultset(parameters, collection, connection, true); - } - - /** - * Fires an internal event - */ - public function fireEvent(string! eventName) -> bool - { - /** - * Check if there is a method with the same name of the event - */ - if method_exists(this, eventName) { - this->{eventName}(); - } - - /** - * Send a notification to the events manager - */ - return this->modelsManager->notifyEvent(eventName, this); - } - - /** - * Fires an internal event that cancels the operation - */ - public function fireEventCancel(string! eventName) -> bool - { - /** - * Check if there is a method with the same name of the event - */ - if method_exists(this, eventName) { - if this->{eventName}() === false { - return false; - } - } - - /** - * Send a notification to the events manager - */ - if this->modelsManager->notifyEvent(eventName, this) === false { - return false; - } - - return true; - } - - /** - * Returns the models manager related to the entity instance - */ - public function getCollectionManager() -> - { - return this->modelsManager; - } - - /** - * Retrieves a database connection - * - * @return \MongoDb - */ - public function getConnection() - { - if typeof this->connection != "object" { - let this->connection = this->modelsManager->getConnection(this); - } - - return this->connection; - } - - /** - * Returns DependencyInjection connection service - */ - public function getConnectionService() -> string - { - return this->modelsManager->getConnectionService(this); - } - - /** - * Returns the dependency injection container - */ - public function getDI() -> - { - return this->container; - } - - /** - * Returns one of the DIRTY_STATE_* constants telling if the document exists - * in the collection or not - */ - public function getDirtyState() -> int - { - return this->dirtyState; - } - - /** - * Returns the custom events manager - */ - protected function getEventsManager() -> - { - return this->modelsManager->getCustomEventsManager(this); - } - - /** - * Returns the value of the _id property - * - * @return \MongoId - */ - public function getId() - { - return this->_id; - } - - /** - * Returns all the validation messages - * - * ```php - * $robot = new Robots(); - * - * $robot->type = "mechanical"; - * $robot->name = "Astro Boy"; - * $robot->year = 1952; - * - * if ($robot->save() === false) { - * echo "Umh, We can't store robots right now "; - * - * $messages = $robot->getMessages(); - * - * foreach ($messages as $message) { - * echo $message; - * } - * } else { - * echo "Great, a new robot was saved successfully!"; - * } - * ``` - */ - public function getMessages() -> - { - return this->errorMessages; - } - - /** - * Returns an array with reserved properties that cannot be part of the - * insert/update - */ - public function getReservedAttributes() -> array - { - if typeof self::reserved != "array" { - let self::reserved = [ - "_connection" : true, - "container" : true, - "source" : true, - "operationMade" : true, - "errorMessages" : true, - "dirtyState" : true, - "modelsManager" : true, - "skipped" : true - ]; - } - - return self::reserved; - } - - /** - * Returns collection name mapped in the model - */ - public function getSource() -> string - { - var collection; - - if !this->source { - let collection = this; - let this->source = uncamelize(get_class_ns(collection)); - } - - return this->source; - } - - /** - * Reads an attribute value by its name - * - *```php - * echo $robot->readAttribute("name"); - *``` - */ - public function readAttribute(string! attribute) -> var | null - { - if !isset this->{attribute} { - return null; - } - - return this->{attribute}; - } - - /** - * Creates/Updates a collection based on the values in the attributes - */ - public function save() -> bool - { - var exists, data, success, status, id, ok, collection; - - let collection = this->prepareCU(); - - /** - * Check the dirty state of the current operation to update the current - * operation - */ - let exists = this->exists(collection); - - if exists === false { - let this->operationMade = self::OP_CREATE; - } else { - let this->operationMade = self::OP_UPDATE; - } - - /** - * The messages added to the validator are reset here - */ - let this->errorMessages = []; - - /** - * Execute the preSave hook - */ - if this->preSave(this->container, self::disableEvents, exists) === false { - return false; - } - - let data = this->toArray(); - - let success = false; - - /** - * We always use safe stores to get the success state - * Save the document - */ - let status = collection->save( - data, - [ - "w": true - ] - ); - - if fetch ok, status["ok"] && ok { - let success = true; - - if exists === false { - if fetch id, data["_id"] { - let this->_id = id; - } - - let this->dirtyState = self::DIRTY_STATE_PERSISTENT; - } - } - - /** - * Call the postSave hooks - */ - return this->postSave( - self::disableEvents, - success, - exists - ); - } - - /** - * Serializes the object ignoring connections or protected properties - */ - public function serialize() -> string - { - var container, serializer; - - /** - * Obtain the default DI - */ - let container = Di::getDefault(); - if unlikely typeof container != "object" { - throw new Exception( - "The dependency injector container is not valid" - ); - } - - if container->has("serializer") { - let serializer = this->container->getShared("serializer"); - - serializer->setData( - this->toArray() - ); - - return serializer->serialize(); - } - - /** - * Use the standard serialize function to serialize the array data - */ - return serialize( - this->toArray() - ); - } - - /** - * Sets the DependencyInjection connection service name - */ - public function setConnectionService(string! connectionService) -> - { - this->modelsManager->setConnectionService(this, connectionService); - - return this; - } - - /** - * Sets the dependency injection container - */ - public function setDI( container) -> void - { - let this->container = container; - } - - /** - * Sets the dirty state of the object using one of the DIRTY_STATE_* - * constants - */ - public function setDirtyState(int dirtyState) -> - { - let this->dirtyState = dirtyState; - - return this; - } - - /** - * Sets a custom events manager - */ - protected function setEventsManager( eventsManager) -> void - { - this->modelsManager->setCustomEventsManager(this, eventsManager); - } - - /** - * Sets a value for the _id property, creates a MongoId object if needed - * - * @param mixed id - */ - public function setId(id) - { - var mongoId; - - if typeof id != "object" { - /** - * Check if the model use implicit ids - */ - if this->modelsManager->isUsingImplicitObjectIds(this) { - let mongoId = new MongoId(id); - } else { - let mongoId = id; - } - } else { - let mongoId = id; - } - - let this->_id = mongoId; - } - - /** - * Sets collection name which model should be mapped - */ - protected function setSource(string! source) -> - { - let this->source = source; - - return this; - } - - /** - * Skips the current operation forcing a success state - */ - public function skipOperation(bool skip) - { - let this->skipped = skip; - } - - /** - * Allows to perform a summatory group for a column in the collection - */ - public static function summatory(string! field, conditions = null, finalize = null) -> array - { - var className, model, connection, source, collection, initial, - reduce, group, retval, firstRetval; - - let className = get_called_class(); - - let model = new {className}(); - - let connection = model->getConnection(); - - let source = model->getSource(); - if unlikely empty source { - throw new Exception("Method getSource() returns empty string"); - } - - let collection = connection->selectCollection(source); - - /** - * Uses a javascript hash to group the results - */ - let initial = [ - "summatory": [] - ]; - - /** - * Uses a javascript hash to group the results, however this is slow - * with larger datasets - */ - let reduce = "function (curr, result) { if (typeof result.summatory[curr." . field . "] === \"undefined\") { result.summatory[curr." . field . "] = 1; } else { result.summatory[curr." . field . "]++; } }"; - - let group = collection->group([], initial, reduce); - - if !fetch retval, group["retval"] { - return []; - } - - if fetch firstRetval, retval[0] { - if isset firstRetval["summatory"] { - return firstRetval["summatory"]; - } - - return firstRetval; - } - - return retval; - } - - /** - * Returns the instance as an array representation - * - *```php - * print_r( - * $robot->toArray() - * ); - *``` - */ - public function toArray() -> array - { - var reserved, key, value; - array data; - - let reserved = this->getReservedAttributes(); - - /** - * Get an array with the values of the object - * We only assign values to the public properties - */ - let data = []; - - for key, value in get_object_vars(this) { - if key == "_id" { - if value { - let data[key] = value; - } - } elseif !isset reserved[key] { - let data[key] = value; - } - } - - return data; - } - - /** - * Unserializes the object from a serialized string - */ - public function unserialize(var data) - { - var attributes, container, manager, key, value, serializer; - - /** - * Obtain the default DI - */ - let container = Di::getDefault(); - if unlikely typeof container != "object" { - throw new Exception( - Exception::containerServiceNotFound( - "the services related to the ODM" - ) - ); - } - - /** - * Update the dependency injector - */ - let this->container = container; - - if container->has("serializer") { - let serializer = container->getShared("serializer"); - let attributes = serializer->unserialize(data); - } else { - let attributes = unserialize(data); - } - - if typeof attributes == "array" { - /** - * Gets the default modelsManager service - */ - let manager = container->getShared("collectionManager"); - - if unlikely typeof manager != "object" { - throw new Exception( - "The injected service 'collectionManager' is not valid" - ); - } - - /** - * Update the models manager - */ - let this->modelsManager = manager; - - /** - * Update the objects attributes - */ - for key, value in attributes { - let this->{key} = value; - } - } - } - - /** - * Creates/Updates a collection based on the values in the attributes - */ - public function update() -> bool - { - var exists, data, success, status, ok, collection; - - let collection = this->prepareCU(); - - /** - * Check the dirty state of the current operation to update the current - * operation - */ - let exists = this->exists(collection); - - if unlikely !exists { - throw new Exception( - "The document cannot be updated because it doesn't exist" - ); - } - - let this->operationMade = self::OP_UPDATE; - - /** - * The messages added to the validator are reset here - */ - let this->errorMessages = []; - - /** - * Execute the preSave hook - */ - if this->preSave(this->container, self::disableEvents, exists) === false { - return false; - } - - let data = this->toArray(); - - /** - * We always use safe stores to get the success state - * Save the document - */ - let status = collection->update( - [ - "_id": this->_id - ], - data, - [ - "w": true - ] - ); - - if fetch ok, status["ok"] && ok { - let success = true; - } else { - let success = false; - } - - /** - * Call the postSave hooks - */ - return this->postSave( - self::disableEvents, - success, - exists - ); - } - - /** - * Executes validators on every validation call - * - *```php - * use Phalcon\Mvc\Collection; - * use Phalcon\Validation; - * use Phalcon\Validation\Validator\ExclusionIn; - * - * class Subscriptors extends Collection - * { - * public function validation() - * { - * $validator = new Validation(); - * - * $validator->add( - * "status", - * new ExclusionIn( - * [ - * "domain" => [ - * "A", - * "I", - * ], - * ] - * ) - * ); - * - * return $this->validate($validator); - * } - * } - *``` - */ - protected function validate( validator) -> bool - { - var messages, message; - - let messages = validator->validate(null, this); - - // Call the validation, if it returns not the bool - // we append the messages to the current object - if typeof messages == "boolean" { - return messages; - } - - for message in iterator(messages) { - this->appendMessage( - new Message( - message->getMessage(), - message->getField(), - message->getType(), - null, - message->getCode() - ) - ); - } - - // If there is a message, it returns false otherwise true - return !count(messages); - } - - /** - * Sets if a model must use implicit objects ids - */ - protected function useImplicitObjectIds(bool useImplicitObjectIds) - { - this->modelsManager->useImplicitObjectIds(this, useImplicitObjectIds); - } - - /** - * Writes an attribute value by its name - * - *```php - * $robot->writeAttribute("name", "Rosey"); - *``` - */ - public function writeAttribute(string attribute, var value) - { - let this->{attribute} = value; - } - - /** - * Cancel the current operation - */ - protected function cancelOperation(bool disableEvents) -> bool - { - var eventName; - - if disableEvents { - return false; - } - - if this->operationMade == self::OP_DELETE { - let eventName = "notDeleted"; - } else { - let eventName = "notSaved"; - } - - this->fireEvent(eventName); - - return true; - } - - /** - * Checks if the document exists in the collection - * - * @param MongoCollection collection - */ - protected function exists(collection) -> bool - { - var id, mongoId, exists; - - if !fetch id, this->_id { - return false; - } - - if typeof id == "object" { - let mongoId = id; - } else { - /** - * Check if the model use implicit ids - */ - if this->modelsManager->isUsingImplicitObjectIds(this) { - let mongoId = new MongoId(id); - let this->_id = mongoId; - } else { - let mongoId = id; - } - } - - /** - * If we already know if the document exists we don't check it - */ - if !this->dirtyState { - return true; - } - - /** - * Perform the count using the function provided by the driver - */ - let exists = collection->count(["_id": mongoId]) > 0; - - if exists { - let this->dirtyState = self::DIRTY_STATE_PERSISTENT; - } else { - let this->dirtyState = self::DIRTY_STATE_TRANSIENT; - } - - return exists; - } - - /** - * Perform a count over a resultset - * - * @param array params - * @param \MongoDb connection - */ - protected static function getGroupResultset(params, collection, connection) -> int - { - var source, mongoCollection, conditions, limit, sort, documentsCursor; - - let source = collection->getSource(); - if unlikely empty source { - throw new Exception("Method getSource() returns empty string"); - } - - let mongoCollection = connection->selectCollection(source); - - /** - * Convert the string to an array - */ - if !fetch conditions, params[0] { - if !fetch conditions, params["conditions"] { - let conditions = []; - } - } - - if isset params["limit"] || isset params["sort"] || isset params["skip"] { - /** - * Perform the find - */ - let documentsCursor = mongoCollection->find(conditions); - - /** - * Check if a "limit" clause was defined - */ - if fetch limit, params["limit"] { - documentsCursor->limit(limit); - } - - /** - * Check if a "sort" clause was defined - */ - if fetch sort, params["sort"] { - documentsCursor->sort(sort); - } - - /** - * Check if a "skip" clause was defined - */ - if fetch sort, params["skip"] { - documentsCursor->skip(sort); - } - - /** - * Only "count" is supported - */ - return count(documentsCursor); - } - - return mongoCollection->count(conditions); - } - - /** - * Returns a collection resultset - * - * @param array params - * @param \MongoDb connection - * @return array - */ - protected static function getResultset(var params, collection, connection, bool unique) - { - var source, mongoCollection, conditions, base, documentsCursor, - fields, skip, limit, sort, document, collections, className; - - /** - * Check if "class" clause was defined - */ - if fetch className, params["class"] { - let base = new {className}(); - - if unlikely !(base instanceof CollectionInterface || base instanceof Collection\Document) { - throw new Exception( - "Object of class '" . className . "' must be an implementation of Phalcon\\Mvc\\CollectionInterface or an instance of Phalcon\\Mvc\\Collection\\Document" - ); - } - } else { - let base = collection; - } - - if base instanceof Collection { - base->setDirtyState( - self::DIRTY_STATE_PERSISTENT - ); - } - - let source = collection->getSource(); - if unlikely empty source { - throw new Exception("Method getSource() returns empty string"); - } - - let mongoCollection = connection->selectCollection(source); - - if unlikely typeof mongoCollection != "object" { - throw new Exception("Couldn't select mongo collection"); - } - - /** - * Convert the string to an array - */ - if !fetch conditions, params[0] { - if !fetch conditions, params["conditions"] { - let conditions = []; - } - } - - if unlikely typeof conditions != "array" { - throw new Exception("Find parameters must be an array"); - } - - /** - * Perform the find - */ - if fetch fields, params["fields"] { - let documentsCursor = mongoCollection->find(conditions, fields); - } else { - let documentsCursor = mongoCollection->find(conditions); - } - - /** - * Check if a "limit" clause was defined - */ - if fetch limit, params["limit"] { - documentsCursor->limit(limit); - } - - /** - * Check if a "sort" clause was defined - */ - if fetch sort, params["sort"] { - documentsCursor->sort(sort); - } - - /** - * Check if a "skip" clause was defined - */ - if fetch skip, params["skip"] { - documentsCursor->skip(skip); - } - - if unique { - /** - * Requesting a single result - */ - documentsCursor->rewind(); - - let document = documentsCursor->current(); - - if typeof document != "array" { - return false; - } - - /** - * Assign the values to the base object - */ - return self::cloneResult(base, document); - } - - /** - * Requesting a complete resultset - */ - let collections = []; - for document in iterator_to_array(documentsCursor, false) { - /** - * Assign the values to the base object - */ - let collections[] = self::cloneResult(base, document); - } - - return collections; - } - - /** - * Executes internal hooks before save a document - */ - final protected function preSave( container, bool disableEvents, bool exists) -> bool - { - var eventName; - - /** - * Run Validation Callbacks Before - */ - if !disableEvents { - if this->fireEventCancel("beforeValidation") === false { - return false; - } - - if !exists { - let eventName = "beforeValidationOnCreate"; - } else { - let eventName = "beforeValidationOnUpdate"; - } - - if this->fireEventCancel(eventName) === false { - return false; - } - } - - /** - * Run validation - */ - if this->fireEventCancel("validation") === false { - if !disableEvents { - this->fireEvent("onValidationFails"); - } - - return false; - } - - if !disableEvents { - /** - * Run Validation Callbacks After - */ - if !exists { - let eventName = "afterValidationOnCreate"; - } else { - let eventName = "afterValidationOnUpdate"; - } - - if this->fireEventCancel(eventName) === false { - return false; - } - - if this->fireEventCancel("afterValidation") === false { - return false; - } - - /** - * Run Before Callbacks - */ - if this->fireEventCancel("beforeSave") === false { - return false; - } - - if exists { - let eventName = "beforeUpdate"; - } else { - let eventName = "beforeCreate"; - } - - if this->fireEventCancel(eventName) === false { - return false; - } - } - - return true; - } - - /** - * Executes internal events after save a document - */ - final protected function postSave(bool disableEvents, bool success, bool exists) -> bool - { - var eventName; - - if !success { - if !disableEvents { - this->fireEvent("notSaved"); - } - - this->cancelOperation(disableEvents); - - return false; - } - - if !disableEvents { - if exists { - let eventName = "afterUpdate"; - } else { - let eventName = "afterCreate"; - } - - this->fireEvent(eventName); - - this->fireEvent("afterSave"); - } - - return success; - } - - /** - * Shared Code for CU Operations - * Prepares Collection - */ - protected function prepareCU() - { - var container, connection, source, collection; - - let container = this->container; - if unlikely typeof container != "object" { - throw new Exception( - Exception::containerServiceNotFound( - "the services related to the ODM" - ) - ); - } - - let source = this->getSource(); - if unlikely empty source { - throw new Exception("Method getSource() returns empty string"); - } - - let connection = this->getConnection(); - - /** - * Choose a collection according to the collection name - */ - let collection = connection->selectCollection(source); - - return collection; - } -} diff --git a/phalcon/Mvc/Collection/Behavior.zep b/phalcon/Mvc/Collection/Behavior.zep deleted file mode 100644 index 1b5c7614b23..00000000000 --- a/phalcon/Mvc/Collection/Behavior.zep +++ /dev/null @@ -1,74 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection; - -use Phalcon\Mvc\CollectionInterface; - -/** - * Phalcon\Mvc\Collection\Behavior - * - * This is an optional base class for ORM behaviors - */ -abstract class Behavior implements BehaviorInterface -{ - protected options; - - /** - * Phalcon\Mvc\Collection\Behavior - */ - public function __construct(array options = []) - { - let this->options = options; - } - - /** - * Returns the behavior options related to an event - * - * @return array - */ - protected function getOptions(string! eventName = null) - { - var options, eventOptions; - - let options = this->options; - if eventName !== null { - if fetch eventOptions, options[eventName] { - return eventOptions; - } - return null; - } - return options; - } - - /** - * Acts as fallbacks when a missing method is called on the collection - */ - public function missingMethod( model, string method, array arguments = []) - { - return null; - } - - /** - * Checks whether the behavior must take action on certain event - */ - protected function mustTakeAction(string! eventName) -> bool - { - return isset this->options[eventName]; - } - - /** - * This method receives the notifications from the EventsManager - */ - public function notify(string type, model) - { - return null; - } -} diff --git a/phalcon/Mvc/Collection/Behavior/SoftDelete.zep b/phalcon/Mvc/Collection/Behavior/SoftDelete.zep deleted file mode 100644 index f1e250dab44..00000000000 --- a/phalcon/Mvc/Collection/Behavior/SoftDelete.zep +++ /dev/null @@ -1,90 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection\Behavior; - -use Phalcon\Mvc\CollectionInterface; -use Phalcon\Mvc\Collection\Behavior; -use Phalcon\Mvc\Collection\Exception; - -/** - * Phalcon\Mvc\Collection\Behavior\SoftDelete - * - * Instead of permanently delete a record it marks the record as - * deleted changing the value of a flag column - */ -class SoftDelete extends Behavior -{ - /** - * Listens for notifications from the models manager - */ - public function notify(string! type, model) - { - var options, value, field, updateModel, message; - - if type !== "beforeDelete" { - return; - } - - let options = this->getOptions(); - - /** - * 'value' is the value to be updated instead of delete the record - */ - if unlikely !fetch value, options["value"] { - throw new Exception("The option 'value' is required"); - } - - /** - * 'field' is the attribute to be updated instead of delete the record - */ - if unlikely !fetch field, options["field"] { - throw new Exception("The option 'field' is required"); - } - - /** - * Skip the current operation - */ - model->skipOperation(true); - - /** - * If the record is already flagged as 'deleted' we don't delete it again - */ - if model->readAttribute(field) == value { - return; - } - - /** - * Clone the current model to make a clean new operation - */ - let updateModel = clone model; - - updateModel->writeAttribute(field, value); - - /** - * Update the cloned model - */ - if !updateModel->save() { - /** - * Transfer the messages from the cloned model to the original model - */ - for message in updateModel->getMessages() { - model->appendMessage(message); - } - - return false; - } - - /** - * Update the original model too - */ - model->writeAttribute(field, value); - } -} diff --git a/phalcon/Mvc/Collection/Behavior/Timestampable.zep b/phalcon/Mvc/Collection/Behavior/Timestampable.zep deleted file mode 100644 index ba762339172..00000000000 --- a/phalcon/Mvc/Collection/Behavior/Timestampable.zep +++ /dev/null @@ -1,90 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection\Behavior; - -use Closure; -use Phalcon\Mvc\CollectionInterface; -use Phalcon\Mvc\Collection\Behavior; -use Phalcon\Mvc\Collection\Exception; - -/** - * Phalcon\Mvc\Collection\Behavior\Timestampable - * - * Allows to automatically update a model’s attribute saving the - * datetime when a record is created or updated - */ -class Timestampable extends Behavior -{ - /** - * Listens for notifications from the models manager - */ - public function notify(string! type, model) - { - var options, timestamp, singleField, field, generator, format; - - /** - * Check if the developer decided to take action here - */ - if this->mustTakeAction(type) !== true { - return null; - } - - let options = this->getOptions(type); - if typeof options == "array" { - - /** - * The field name is required in this behavior - */ - if unlikely !fetch field, options["field"] { - throw new Exception("The option 'field' is required"); - } - - let timestamp = null; - - if fetch format, options["format"] { - /** - * Format is a format for date() - */ - let timestamp = date(format); - } else { - if fetch generator, options["generator"] { - - /** - * A generator is a closure that produce the correct timestamp value - */ - if typeof generator == "object" { - if generator instanceof Closure { - let timestamp = call_user_func(generator); - } - } - } - } - - /** - * Last resort call time() - */ - if timestamp === null { - let timestamp = time(); - } - - /** - * Assign the value to the field, use writeattribute if the property is protected - */ - if typeof field == "array" { - for singleField in field { - model->writeAttribute(singleField, timestamp); - } - } else { - model->writeAttribute(field, timestamp); - } - } - } -} diff --git a/phalcon/Mvc/Collection/BehaviorInterface.zep b/phalcon/Mvc/Collection/BehaviorInterface.zep deleted file mode 100644 index ffa3bb458fa..00000000000 --- a/phalcon/Mvc/Collection/BehaviorInterface.zep +++ /dev/null @@ -1,31 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection; - -use Phalcon\Mvc\CollectionInterface; - -/** - * Phalcon\Mvc\Collection\BehaviorInterface - * - * Interface for Phalcon\Mvc\Collection\Behavior - */ -interface BehaviorInterface -{ - /** - * Calls a method when it's missing in the collection - */ - public function missingMethod( collection, string !method, array arguments = []); - - /** - * This method receives the notifications from the EventsManager - */ - public function notify(string! type, collection); -} diff --git a/phalcon/Mvc/Collection/Document.zep b/phalcon/Mvc/Collection/Document.zep deleted file mode 100644 index f3d63118d7d..00000000000 --- a/phalcon/Mvc/Collection/Document.zep +++ /dev/null @@ -1,100 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection; - -use ArrayAccess; -use Phalcon\Mvc\EntityInterface; -use Phalcon\Mvc\Collection\Exception; - -/** - * Phalcon\Mvc\Collection\Document - * - * This component allows Phalcon\Mvc\Collection to return rows without an associated entity. - * This objects implements the ArrayAccess interface to allow access the object as object->x or array[x]. - */ -class Document implements EntityInterface, ArrayAccess -{ - /** - * Returns the value of a field using the ArrayAccess interfase - */ - public function offsetGet(var index) -> var - { - var value; - - if unlikely !fetch value, this->{index} { - throw new Exception("The index does not exist in the row"); - } - - return value; - } - - /** - * Checks whether an offset exists in the document - */ - public function offsetExists(var index) -> bool - { - return isset this->{index}; - } - - /** - * Change a value using the ArrayAccess interface - */ - public function offsetSet(var index, value) -> void - { - let this->{index} = value; - } - - /** - * Rows cannot be changed. It has only been implemented to meet the definition of the ArrayAccess interface - */ - public function offsetUnset(var index) -> void - { - throw new Exception("The index does not exist in the row"); - } - - /** - * Reads an attribute value by its name - * - *```php - * echo $robot->readAttribute("name"); - *``` - */ - public function readAttribute(string! attribute) -> var | null - { - var value; - - if !fetch value, this->{attribute} { - return null; - } - - return value; - } - - /** - * Returns the instance as an array representation - */ - public function toArray() -> array - { - return get_object_vars(this); - } - - /** - * Writes an attribute value by its name - * - *```php - * $robot->writeAttribute("name", "Rosey"); - *``` - */ - public function writeAttribute(string! attribute, var value) -> void - { - let this->{attribute} = value; - } -} diff --git a/phalcon/Mvc/Collection/Exception.zep b/phalcon/Mvc/Collection/Exception.zep deleted file mode 100644 index e3a3e5109c3..00000000000 --- a/phalcon/Mvc/Collection/Exception.zep +++ /dev/null @@ -1,22 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection; - -/** - * Phalcon\Mvc\Collection\Exception - * - * Exceptions thrown in Phalcon\Mvc\Collection\* classes will use this class - * - */ -class Exception extends \Phalcon\Exception -{ - -} diff --git a/phalcon/Mvc/Collection/Manager.zep b/phalcon/Mvc/Collection/Manager.zep deleted file mode 100644 index be75a26c86f..00000000000 --- a/phalcon/Mvc/Collection/Manager.zep +++ /dev/null @@ -1,378 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection; - -use Phalcon\Di\DiInterface; -use Phalcon\Di\InjectionAwareInterface; -use Phalcon\Events\EventsAwareInterface; -use Phalcon\Events\ManagerInterface; -use Phalcon\Mvc\CollectionInterface; -use Phalcon\Mvc\Collection\BehaviorInterface; - -/** - * Phalcon\Mvc\Collection\Manager - * - * This components controls the initialization of models, keeping record of relations - * between the different models of the application. - * - * A CollectionManager is injected to a model via a Dependency Injector Container such as Phalcon\Di. - * - * ```php - * $di = new \Phalcon\Di(); - * - * $di->set( - * "collectionManager", - * function () { - * return new \Phalcon\Mvc\Collection\Manager(); - * } - * ); - * - * $robot = new Robots($di); - * ``` - */ -class Manager implements InjectionAwareInterface, EventsAwareInterface -{ - protected behaviors; - - protected connectionServices; - - protected container; - - protected customEventsManager; - - protected eventsManager; - - protected implicitObjectsIds; - - protected initialized; - - protected lastInitialized; - - protected serviceName = "mongo" { get, set }; - - /** - * Binds a behavior to a model - */ - public function addBehavior( model, behavior) - { - var entityName, modelsBehaviors; - - let entityName = get_class_lower(model); - - /** - * Get the current behaviors - */ - if !fetch modelsBehaviors, this->behaviors[entityName] { - let modelsBehaviors = []; - } - - /** - * Append the behavior to the list of behaviors - */ - let modelsBehaviors[] = behavior; - - /** - * Update the behaviors list - */ - let this->behaviors[entityName] = modelsBehaviors; - } - - /** - * Returns a custom events manager related to a model - */ - public function getCustomEventsManager( model) -> var | null - { - var customEventsManager, className; - - let customEventsManager = this->customEventsManager; - if typeof customEventsManager == "array" { - let className = get_class_lower(model); - if isset customEventsManager[className] { - return customEventsManager[className]; - } - } - - return null; - } - - /** - * Returns the connection related to a model - * - * @return \Mongo - */ - public function getConnection( model) - { - var service, connectionService, connection, container, entityName; - - let service = this->serviceName; - let connectionService = this->connectionServices; - if typeof connectionService == "array" { - let entityName = get_class(model); - - /** - * Check if the model has a custom connection service - */ - if isset connectionService[entityName] { - let service = connectionService[entityName]; - } - } - - let container = this->container; - if unlikely typeof container != "object" { - throw new Exception( - Exception::containerServiceNotFound( - "the services related to the ORM" - ) - ); - } - - /** - * Request the connection service from the DI - */ - let connection = container->getShared(service); - if unlikely typeof connection != "object" { - throw new Exception("Invalid injected connection service"); - } - - return connection; - } - - /** - * Gets a connection service for a specific model - */ - public function getConnectionService( model) -> string - { - var service, entityName; - - let service = this->serviceName; - let entityName = get_class(model); - if isset this->connectionServices[entityName] { - let service = this->connectionServices[entityName]; - } - - return service; - } - - /** - * Returns the DependencyInjector container - */ - public function getDI() -> - { - return this->container; - } - - /** - * Returns the internal event manager - */ - public function getEventsManager() -> - { - return this->eventsManager; - } - - /** - * Get the latest initialized model - */ - public function getLastInitialized() -> - { - return this->lastInitialized; - } - - /** - * Checks if a model is using implicit object ids - */ - public function isUsingImplicitObjectIds( model) -> bool - { - var implicit; - - /** - * All collections use by default are using implicit object ids - */ - if fetch implicit, this->implicitObjectsIds[get_class(model)] { - return implicit; - } - - return true; - } - - /** - * Check whether a model is already initialized - */ - public function isInitialized(string! className) -> bool - { - return isset this->initialized[strtolower(className)]; - } - - /** - * Initializes a model in the models manager - */ - public function initialize( model) -> void - { - var className, initialized, eventsManager; - - let className = get_class_lower(model); - let initialized = this->initialized; - - /** - * Models are just initialized once per request - */ - if !isset initialized[className] { - /** - * Call the 'initialize' method if it's implemented - */ - if method_exists(model, "initialize") { - model->{"initialize"}(); - } - - /** - * If an EventsManager is available we pass to it every initialized model - */ - let eventsManager = this->eventsManager; - if typeof eventsManager == "object" { - eventsManager->fire("collectionManager:afterInitialize", model); - } - - let this->initialized[className] = model; - let this->lastInitialized = model; - } - } - - /** - * Dispatch an event to the listeners and behaviors - * This method expects that the endpoint listeners/behaviors returns true - * meaning that at least one was implemented - */ - public function missingMethod( model, string! eventName, var data) -> bool - { - var behaviors, modelsBehaviors, result, eventsManager, behavior; - - /** - * Dispatch events to the global events manager - */ - let behaviors = this->behaviors; - if typeof behaviors == "array" { - - if fetch modelsBehaviors, behaviors[get_class_lower(model)] { - - /** - * Notify all the events on the behavior - */ - for behavior in modelsBehaviors { - let result = behavior->missingMethod(model, eventName, data); - if result !== null { - return result; - } - } - } - } - - /** - * Dispatch events to the global events manager - */ - let eventsManager = this->eventsManager; - if typeof eventsManager == "object" { - return eventsManager->fire("model:" . eventName, model, data); - } - - return false; - } - - /** - * Receives events generated in the models and dispatches them to an events-manager if available - * Notify the behaviors that are listening in the model - */ - public function notifyEvent(string! eventName, model) - { - var behavior, behaviors, modelsBehaviors, eventsManager, status = null, - customEventsManager; - - let behaviors = this->behaviors; - if typeof behaviors == "array" { - if fetch modelsBehaviors, behaviors[get_class_lower(model)] { - - /** - * Notify all the events on the behavior - */ - for behavior in modelsBehaviors { - let status = behavior->notify(eventName, model); - if status === false { - return false; - } - } - } - } - - /** - * Dispatch events to the global events manager - */ - let eventsManager = this->eventsManager; - if typeof eventsManager == "object" { - let status = eventsManager->fire( "collection:". eventName, model); - if !status { - return status; - } - } - - /** - * A model can has a specific events manager for it - */ - let customEventsManager = this->customEventsManager; - if typeof customEventsManager == "array" { - if isset customEventsManager[get_class_lower(model)] { - let status = customEventsManager->fire("collection:" . eventName, model); - if !status { - return status; - } - } - } - - return status; - } - - /** - * Sets a custom events manager for a specific model - */ - public function setCustomEventsManager( model, eventsManager) -> void - { - let this->customEventsManager[get_class(model)] = eventsManager; - } - - /** - * Sets a connection service for a specific model - */ - public function setConnectionService( model, string! connectionService) -> void - { - let this->connectionServices[get_class(model)] = connectionService; - } - - /** - * Sets the DependencyInjector container - */ - public function setDI( container) -> void - { - let this->container = container; - } - - /** - * Sets the event manager - */ - public function setEventsManager( eventsManager) -> void - { - let this->eventsManager = eventsManager; - } - - /** - * Sets whether a model must use implicit objects ids - */ - public function useImplicitObjectIds( model, bool useImplicitObjectIds) -> void - { - let this->implicitObjectsIds[get_class(model)] = useImplicitObjectIds; - } -} diff --git a/phalcon/Mvc/Collection/ManagerInterface.zep b/phalcon/Mvc/Collection/ManagerInterface.zep deleted file mode 100644 index 7f9ffb5156e..00000000000 --- a/phalcon/Mvc/Collection/ManagerInterface.zep +++ /dev/null @@ -1,96 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc\Collection; - -use Phalcon\Db\Adapter\AdapterInterface; -use Phalcon\Mvc\CollectionInterface; -use Phalcon\Mvc\Collection\BehaviorInterface; -use Phalcon\Events\ManagerInterface as EventsManagerInterface; - -/** - * Phalcon\Mvc\Collection\Manager - * - * This components controls the initialization of models, keeping record of relations - * between the different models of the application. - * - * A CollectionManager is injected to a model via a Dependency Injector Container such as Phalcon\Di. - * - * ```php - * $di = new \Phalcon\Di(); - * - * $di->set( - * "collectionManager", - * function() { - * return new \Phalcon\Mvc\Collection\Manager(); - * } - * ); - * - * $robot = new Robots(di); - * ``` - */ -interface ManagerInterface -{ - /** - * Binds a behavior to a collection - */ - public function addBehavior( model, behavior); - - /** - * Returns the connection related to a model - */ - public function getConnection( model) -> ; - - /** - * Returns a custom events manager related to a model - */ - public function getCustomEventsManager( model) -> ; - - /** - * Get the latest initialized model - */ - public function getLastInitialized() -> ; - - /** - * Initializes a model in the models manager - */ - public function initialize( model); - - /** - * Check whether a model is already initialized - */ - public function isInitialized(string! className) -> bool; - - /** - * Checks if a model is using implicit object ids - */ - public function isUsingImplicitObjectIds( model) -> bool; - - /** - * Receives events generated in the models and dispatches them to an events-manager if available - * Notify the behaviors that are listening in the model - */ - public function notifyEvent(string! eventName, model); - - /** - * Sets a custom events manager for a specific model - */ - public function setCustomEventsManager( model, eventsManager); - - /** - * Sets a connection service for a specific model - */ - public function setConnectionService( model, string! connectionService); - - /** - * Sets if a model must use implicit objects ids - */ - public function useImplicitObjectIds( model, bool useImplicitObjectIds); -} diff --git a/phalcon/Mvc/CollectionInterface.zep b/phalcon/Mvc/CollectionInterface.zep deleted file mode 100644 index e671923cf39..00000000000 --- a/phalcon/Mvc/CollectionInterface.zep +++ /dev/null @@ -1,132 +0,0 @@ - -/** - * This file is part of the Phalcon Framework. - * - * (c) Phalcon Team - * - * For the full copyright and license information, please view the LICENSE.txt - * file that was distributed with this source code. - */ - -namespace Phalcon\Mvc; - -use Phalcon\Messages\MessageInterface; - -/** - * Interface for Phalcon\Mvc\Collection - */ -interface CollectionInterface -{ - /** - * Appends a customized message on the validation process - */ - public function appendMessage( message); - - /** - * Returns a cloned collection - */ - public static function cloneResult( collection, array! document) -> ; - - /** - * Perform a count over a collection - */ - public static function count(array parameters = null) -> int; - - /** - * Deletes a model instance. Returning true on success or false otherwise - */ - public function delete() -> bool; - - /** - * Allows to query a set of records that match the specified conditions - */ - public static function find(array parameters = null) -> array; - - /** - * Find a document by its id - * - * @param string id - */ - public static function findById(var id) -> | null; - - /** - * Allows to query the first record that match the specified conditions - */ - public static function findFirst(array parameters = null) -> array; - - /** - * Fires an event, implicitly calls behaviors and listeners in the events - * manager are notified - */ - public function fireEvent(string! eventName) -> bool; - - /** - * Fires an event, implicitly listeners in the events manager are notified - * This method stops if one of the callbacks/listeners returns bool false - */ - public function fireEventCancel(string! eventName) -> bool; - - /** - * Retrieves a database connection - * - * @return MongoDb - */ - public function getConnection(); - - /** - * Returns one of the DIRTY_STATE_* constants telling if the record exists - * in the database or not - */ - public function getDirtyState() -> int; - - /** - * Returns the value of the _id property - * - * @return MongoId - */ - public function getId(); - - /** - * Returns all the validation messages - */ - public function getMessages() -> ; - - /** - * Returns an array with reserved properties that cannot be part of the - * insert/update - */ - public function getReservedAttributes() -> array; - - /** - * Returns collection name mapped in the model - */ - public function getSource() -> string; - - /** - * Creates/Updates a collection based on the values in the attributes - */ - public function save() -> bool; - - /** - * Sets a service in the services container that returns the Mongo database - */ - public function setConnectionService(string! connectionService); - - /** - * Sets the dirty state of the object using one of the DIRTY_STATE_* - * constants - */ - public function setDirtyState(int dirtyState) -> ; - - /** - * Sets a value for the _id property, creates a MongoId object if needed - * - * @param mixed id - */ - public function setId(id); - - /** - * Check whether validation process has generated any messages - */ - public function validationHasFailed() -> bool; -}