From 4aac226eabecc4121e0d024bcbd11573ccb61acc Mon Sep 17 00:00:00 2001 From: Julio Montoya Date: Mon, 25 Mar 2013 19:50:26 +0100 Subject: [PATCH] Adding chash vendor --- vendor/autoload.php | 2 +- vendor/chamilo/chash/.travis.yml | 6 + vendor/chamilo/chash/README.md | 88 +++ vendor/chamilo/chash/chash.phar | Bin 0 -> 499380 bytes vendor/chamilo/chash/chash.php | 160 ++++ vendor/chamilo/chash/composer.json | 14 + vendor/chamilo/chash/composer.lock | 110 +++ vendor/chamilo/chash/createPhar.php | 21 + vendor/chamilo/chash/license.html | 708 ++++++++++++++++++ .../Database/CommonChamiloDatabaseCommand.php | 31 + .../Command/Database/DropDatabaseCommand.php | 65 ++ .../Chash/Command/Database/DumpCommand.php | 39 + .../Command/Database/FullBackupCommand.php | 106 +++ .../Chash/Command/Database/RestoreCommand.php | 49 ++ .../Chash/Command/Database/RunSQLCommand.php | 63 ++ .../Command/Database/SQLCountCommand.php | 51 ++ .../Chash/Command/Files/CleanConfigFiles.php | 65 ++ .../Command/Files/CleanTempFolderCommand.php | 67 ++ .../Translation/ExportLanguageCommand.php | 107 +++ .../Translation/ImportLanguageCommand.php | 135 ++++ .../src/Chash/Helpers/ConfigurationHelper.php | 182 +++++ vendor/composer/autoload_namespaces.php | 1 + vendor/composer/autoload_real.php | 6 +- vendor/composer/installed.json | 62 +- vendor/doctrine/dbal/.travis.yml | 2 +- vendor/doctrine/dbal/composer.json | 4 +- .../DBAL/Platforms/Keywords/MySQLKeywords.php | 1 + .../Platforms/Keywords/OracleKeywords.php | 1 + .../DBAL/Platforms/SQLServerPlatform.php | 4 +- .../dbal/lib/Doctrine/DBAL/SQLParserUtils.php | 53 +- .../DBAL/Schema/AbstractSchemaManager.php | 6 +- .../DBAL/Schema/SQLServerSchemaManager.php | 1 + .../dbal/lib/Doctrine/DBAL/Version.php | 2 +- .../DBAL/Platforms/SQLServerPlatformTest.php | 2 +- .../Tests/DBAL/SQLParserUtilsTest.php | 8 + .../dbal/tests/Doctrine/Tests/TestInit.php | 21 +- vendor/doctrine/orm/composer.json | 2 +- .../lib/Doctrine/ORM/Id/IdentityGenerator.php | 14 +- .../Hydration/SimpleObjectHydrator.php | 5 +- .../ORM/Mapping/ClassMetadataFactory.php | 30 +- .../ORM/Mapping/ClassMetadataInfo.php | 4 + .../Doctrine/ORM/Mapping/Driver/XmlDriver.php | 3 +- .../ORM/Mapping/Driver/YamlDriver.php | 1 + .../lib/Doctrine/ORM/PersistentCollection.php | 20 +- .../Query/Exec/MultiTableUpdateExecutor.php | 31 +- .../orm/lib/Doctrine/ORM/Query/Expr/Base.php | 2 +- .../orm/lib/Doctrine/ORM/Query/SqlWalker.php | 14 +- .../Tools/Pagination/CountOutputWalker.php | 4 + .../orm/lib/Doctrine/ORM/UnitOfWork.php | 57 +- .../doctrine/orm/lib/Doctrine/ORM/Version.php | 2 +- .../OneToManyBidirectionalAssociationTest.php | 26 +- .../ORM/Functional/Ticket/DDC117Test.php | 18 + .../Hydration/SimpleObjectHydratorTest.php | 24 + .../ORM/Mapping/AbstractMappingDriverTest.php | 24 +- ....DDC1476EntityWithDefaultFieldType.dcm.yml | 2 +- ...ne.Tests.ORM.Mapping.DDC2069Entity.dcm.yml | 4 +- .../Doctrine/Tests/ORM/Query/ExprTest.php | 14 + .../Pagination/CountOutputWalkerTest.php | 17 + 58 files changed, 2409 insertions(+), 152 deletions(-) create mode 100644 vendor/chamilo/chash/.travis.yml create mode 100644 vendor/chamilo/chash/README.md create mode 100755 vendor/chamilo/chash/chash.phar create mode 100755 vendor/chamilo/chash/chash.php create mode 100644 vendor/chamilo/chash/composer.json create mode 100644 vendor/chamilo/chash/composer.lock create mode 100644 vendor/chamilo/chash/createPhar.php create mode 100644 vendor/chamilo/chash/license.html create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/CommonChamiloDatabaseCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/DropDatabaseCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/DumpCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/FullBackupCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/RestoreCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/RunSQLCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Database/SQLCountCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Files/CleanConfigFiles.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Files/CleanTempFolderCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Translation/ExportLanguageCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Command/Translation/ImportLanguageCommand.php create mode 100644 vendor/chamilo/chash/src/Chash/Helpers/ConfigurationHelper.php diff --git a/vendor/autoload.php b/vendor/autoload.php index f58bd8e5c6..1044960bb8 100644 --- a/vendor/autoload.php +++ b/vendor/autoload.php @@ -4,4 +4,4 @@ require_once __DIR__ . '/composer' . '/autoload_real.php'; -return ComposerAutoloaderInitf1ee82f2567fa86f78d258bf9f6cac97::getLoader(); +return ComposerAutoloaderInitccfd96f09fad4b03f395700cf22111c8::getLoader(); diff --git a/vendor/chamilo/chash/.travis.yml b/vendor/chamilo/chash/.travis.yml new file mode 100644 index 0000000000..99f111908f --- /dev/null +++ b/vendor/chamilo/chash/.travis.yml @@ -0,0 +1,6 @@ +language: php + +php: + - 5.3 + - 5.4 + - 5.5 \ No newline at end of file diff --git a/vendor/chamilo/chash/README.md b/vendor/chamilo/chash/README.md new file mode 100644 index 0000000000..d7d2a44b89 --- /dev/null +++ b/vendor/chamilo/chash/README.md @@ -0,0 +1,88 @@ +Chamilo Shell script +==================== + +The Chamilo Shell (or "Chash") is a command-line PHP tool meant to speed up the +management of (multiple) Chamilo portals under Linux. + +To get the most out of Chash, you should move the chash.phar file to your +/usr/local/bin directory. You can do this getting inside the directory where +you put chash.phar and doing: + + chmod +x chash.phar + mv chash.phar /usr/local/bin/chash + +Then you can launch chash by moving into any Chamilo installation directory and +typing + + chash + +It will give you the details of what command you can use to run it properly. + +The most useful command to us until now has been the "chash database:sql" command, +which puts you directly into a MySQL client session. + +Building the chash.phar file +==================== + +In order to generate the executable chash.phar file. You have to set first this php setting (in your cli php configuration file) + + phar.readonly = Off + +Then you can call the php createPhar.php file. A new chash.phar file will be created. + +Remember to add execution permissions to the phar file. + + Example: + + cd chash + php -d phar.readonly=0 createPhar.php + chmod +x chash.phar + sudo mv chash.phar /usr/local/bin/chash + Then you can call the chash.phar file in your Chamilo installation + + cd /var/www/chamilo + chash + +Available commands: +==================== + + db + db:drop_databases Drops all databases from the current Chamilo install + db:dump Outputs a dump of the database + db:full_backup Generates a .tgz from the Chamilo files and database + db:restore Allows you to restore an SQL dump right into the active database of a given Chamilo installation (which will also erase all previous data in that database) + db:sql_cli Enters to the SQL command line + db:sql_count Count the number of rows in a specific table + + files + files:clean_archives Cleans the archives directory + + translation + translation:export_language Exports a Chamilo language package + translation:import_language Import a Chamilo language package + +Usage +==================== + +Inside a chamilo folder execute db:sql_cli in order to enter to the SQL client of the Chamilo database: + + chash.phar db:sql_cli + + +Licensing +========= + +This program is free software: you can redistribute it and/or modify +it under the terms of the GNU General Public License as published by +the Free Software Foundation, either version 3 of the License, or +(at your option) any later version. + +This program is distributed in the hope that it will be useful, +but WITHOUT ANY WARRANTY; without even the implied warranty of +MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +GNU General Public License for more details. + +You should have received a copy of the GNU General Public License +along with this program. If not, see . + +Mail: info@chamilo.org \ No newline at end of file diff --git a/vendor/chamilo/chash/chash.phar b/vendor/chamilo/chash/chash.phar new file mode 100755 index 0000000000000000000000000000000000000000..6d17c0b0be04be482b619f723af50cf298786642 GIT binary patch literal 499380 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�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 literal 0 HcmV?d00001 diff --git a/vendor/chamilo/chash/chash.php b/vendor/chamilo/chash/chash.php new file mode 100755 index 0000000000..8dfc4ebe23 --- /dev/null +++ b/vendor/chamilo/chash/chash.php @@ -0,0 +1,160 @@ + + * @author Julio Montoya + * @version 2.0 + * @license This script is provided under the terms of the GNU/GPLv3+ license + */ + +/** + * Security check: do not allow any other calling method than command-line + */ + +if (PHP_SAPI != 'cli') { + die("Chash cannot be called by any other method than the command line."); +} + +require __DIR__.'/vendor/autoload.php'; + +use Symfony\Component\Console\Application; + +$helpers = array( + 'configuration' => new Chash\Helpers\ConfigurationHelper() +); + +$application = new Application('Chamilo Command Line Interface', '1.0'); + +$helperSet = $application->getHelperSet(); +foreach ($helpers as $name => $helper) { + $helperSet->set($helper, $name); +} + +$application->addCommands(array( + new Chash\Command\Database\RunSQLCommand(), + new Chash\Command\Database\DumpCommand(), + new Chash\Command\Database\RestoreCommand(), + new Chash\Command\Database\SQLCountCommand(), + new Chash\Command\Database\FullBackupCommand(), + new Chash\Command\Database\DropDatabaseCommand(), + new Chash\Command\Files\CleanTempFolderCommand(), + new Chash\Command\Files\CleanConfigFiles(), + new Chash\Command\Translation\ExportLanguageCommand(), + new Chash\Command\Translation\ImportLanguageCommand() +)); + +$application->run(); + +//Interactive shell +//$shell = new Console\Shell($application); +//$shell->run(); + +/** + * Initialization: find the local Chamilo configuration file or thow error + */ +if (!$config_file = _chash_find_config_file()) { + die(_t( + "Couldn't find config file. Please either give the path to the Chamilo installation you want to act on, through the -c option, or 'cd' into a valid Chamilo installation directory" + )); +} + +/** + * Helper functions + */ +/** + * Shows the usage documentation (all possible commands and the general syntax + */ +function _chash_usage() +{ + echo "\n"; + echo _t( + "ChaSh goes for \"Chamilo Shell\".\nIt allows you to execute common administrative operations on a Chamilo LMS installation (1.9 or higher) from the command line." + )."\n"; + echo _t( + "ChaSh is developed by BeezNest, the Chamilo specialist corporation. See http://www.beeznest.com/ for contact details." + )."\n"; + echo _t( + 'You can call chash.php with a series of commands. Each command has its own parameters. To run chash.php, you can either call it from inside a Chamilo directory (it will then find its way on its own) or from any other directory giving the path to the configuration file with --conf=/path/to/configuration.php' + )."\n\n"; + echo _t(' Usage: php5 chash.php [command] [options]')."\n\n"; + // -- Commands explanation -- + echo _t('Available commands:')."\n"; + echo _t(" sql_cli\t\tEnters to the SQL command line")."\n"; + echo _t(" sql_dump\t\tOutputs a dump of the database")."\n"; + echo _t(" sql_restore\t\tInserts a database dump into the active database")."\n"; + echo _t(" sql_count\t\tOutputs a report about the number of rows in a table")."\n"; + echo _t(" full_backup\t\tGenerates a .tgz from the Chamilo files and database")."\n"; + echo _t(" clean_archives\tCleans the archives directory")."\n"; + echo _t(" drop_databases\tDrops all databases from the current Chamilo install")."\n"; + echo _t(" export_language_package\tGenerates a .tgz file with all the translations for a wanted language")."\n"; + echo _t(" import_language_package\tImports .tgz file previously created")."\n"; + echo "\n"; + echo _t("Available options:")."\n"; + echo _t(" --conf=\tIndicates to chash where to find the configuration file of Chamilo.")."\n"; + echo "\n"; +} + + +/** + * Find the complete path to the Chamilo configuration file + * @return string Path to the configuration file + */ +function _chash_find_config_file() +{ + global $argc, $argv; + $found = false; + if ($argc > 1) { + $find = '--conf='; + foreach ($argv as $arg) { + if (substr($arg, 0, 7) == $find) { + if (is_file(substr($arg, 7))) { + $found = substr($arg, 7); + break; + } + if (substr($arg, -1, 1) == '/') { + $arg = substr($arg, 0, -1); + } + if (is_file(substr($arg, 7).'/configuration.php')) { + $found = substr($arg, 7).'/configuration.php'; + break; + } + if (is_file(substr($arg, 7).'/main/inc/conf/configuration.php')) { + $found = substr($arg, 7).'/main/inc/conf/configuration.php'; + break; + } + } + } + } + if (!$found) { + $dir = getcwd(); + for ($i = 0; $i < 10; $i++) { + $dir = realpath($dir); + if (is_file($dir.'/configuration.php')) { + $found = $dir.'/configuration.php'; + break; + } elseif (is_file($dir.'/conf/configuration.php')) { + $found = $dir.'/conf/configuration.php'; + break; + } elseif (is_file($dir.'/inc/conf/configuration.php')) { + $found = $dir.'/inc/conf/configuration.php'; + break; + } elseif (is_file($dir.'/main/inc/conf/configuration.php')) { + $found = $dir.'/main/inc/conf/configuration.php'; + break; + } else { + $dir = $dir.'/../'; + } + } + } + return $found; +} + +function _t($var) +{ + return $var; +} \ No newline at end of file diff --git a/vendor/chamilo/chash/composer.json b/vendor/chamilo/chash/composer.json new file mode 100644 index 0000000000..b3c798be97 --- /dev/null +++ b/vendor/chamilo/chash/composer.json @@ -0,0 +1,14 @@ +{ + "name": "chamilo/chash", + "autoload": { + "psr-0": { + "Chash": "src/" + } + }, + "require": { + "php": ">=5.3.2", + "symfony/console": "2.3.*@dev", + "symfony/yaml" : "2.1.*" + }, + "minimum-stability": "dev" +} \ No newline at end of file diff --git a/vendor/chamilo/chash/composer.lock b/vendor/chamilo/chash/composer.lock new file mode 100644 index 0000000000..3e490f680c --- /dev/null +++ b/vendor/chamilo/chash/composer.lock @@ -0,0 +1,110 @@ +{ + "hash": "1bea5cc52d392819dc48a5b9caa6a96b", + "packages": [ + { + "name": "symfony/console", + "version": "dev-master", + "target-dir": "Symfony/Component/Console", + "source": { + "type": "git", + "url": "https://github.com/symfony/Console.git", + "reference": "ce8d34ee8b1abc7c0f3d0923fdb32a85e7decb98" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/Console/zipball/ce8d34ee8b1abc7c0f3d0923fdb32a85e7decb98", + "reference": "ce8d34ee8b1abc7c0f3d0923fdb32a85e7decb98", + "shasum": "" + }, + "require": { + "php": ">=5.3.3" + }, + "type": "library", + "extra": { + "branch-alias": { + "dev-master": "2.3-dev" + } + }, + "autoload": { + "psr-0": { + "Symfony\\Component\\Console\\": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "http://symfony.com/contributors" + } + ], + "description": "Symfony Console Component", + "homepage": "http://symfony.com", + "time": "2013-03-23 07:15:46" + }, + { + "name": "symfony/yaml", + "version": "2.1.x-dev", + "target-dir": "Symfony/Component/Yaml", + "source": { + "type": "git", + "url": "https://github.com/symfony/Yaml.git", + "reference": "1238ede850fb8c6946a6c44963d38bbf9cad6dd1" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/symfony/Yaml/zipball/1238ede850fb8c6946a6c44963d38bbf9cad6dd1", + "reference": "1238ede850fb8c6946a6c44963d38bbf9cad6dd1", + "shasum": "" + }, + "require": { + "php": ">=5.3.3" + }, + "type": "library", + "autoload": { + "psr-0": { + "Symfony\\Component\\Yaml": "" + } + }, + "notification-url": "https://packagist.org/downloads/", + "license": [ + "MIT" + ], + "authors": [ + { + "name": "Fabien Potencier", + "email": "fabien@symfony.com" + }, + { + "name": "Symfony Community", + "homepage": "http://symfony.com/contributors" + } + ], + "description": "Symfony Yaml Component", + "homepage": "http://symfony.com", + "time": "2013-03-23 01:54:33" + } + ], + "packages-dev": [ + + ], + "aliases": [ + + ], + "minimum-stability": "dev", + "stability-flags": { + "symfony/console": 20 + }, + "platform": { + "php": ">=5.3.2" + }, + "platform-dev": [ + + ] +} diff --git a/vendor/chamilo/chash/createPhar.php b/vendor/chamilo/chash/createPhar.php new file mode 100644 index 0000000000..dea8353775 --- /dev/null +++ b/vendor/chamilo/chash/createPhar.php @@ -0,0 +1,21 @@ +setSignatureAlgorithm(\Phar::SHA1); +$phar->startBuffering(); + +$phar->buildFromDirectory(__DIR__, '/\.php$/'); + +$defaultStub = $phar->createDefaultStub('chash.php'); + +// Create a custom stub to add the shebang +$stub = "#!/usr/bin/env php \n".$defaultStub; + +// Add the stub +$phar->setStub($stub); + +$phar->stopBuffering(); \ No newline at end of file diff --git a/vendor/chamilo/chash/license.html b/vendor/chamilo/chash/license.html new file mode 100644 index 0000000000..6978d0c0ea --- /dev/null +++ b/vendor/chamilo/chash/license.html @@ -0,0 +1,708 @@ + + + + Chamilo License + + +
+ +

GNU GENERAL PUBLIC LICENSE

+

Version 3, 29 June 2007

+ +

Copyright © 2007 Free Software Foundation, Inc. + <http://fsf.org/>

+ Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed.

+ +

Preamble

+ +

The GNU General Public License is a free, copyleft license for +software and other kinds of works.

+ +

The licenses for most software and other practical works are designed +to take away your freedom to share and change the works. By contrast, +the GNU General Public License is intended to guarantee your freedom to +share and change all versions of a program--to make sure it remains free +software for all its users. We, the Free Software Foundation, use the +GNU General Public License for most of our software; it applies also to +any other work released this way by its authors. You can apply it to +your programs, too.

+ +

When we speak of free software, we are referring to freedom, not +price. Our General Public Licenses are designed to make sure that you +have the freedom to distribute copies of free software (and charge for +them if you wish), that you receive source code or can get it if you +want it, that you can change the software or use pieces of it in new +free programs, and that you know you can do these things.

+ +

To protect your rights, we need to prevent others from denying you +these rights or asking you to surrender the rights. Therefore, you have +certain responsibilities if you distribute copies of the software, or if +you modify it: responsibilities to respect the freedom of others.

+ +

For example, if you distribute copies of such a program, whether +gratis or for a fee, you must pass on to the recipients the same +freedoms that you received. You must make sure that they, too, receive +or can get the source code. And you must show them these terms so they +know their rights.

+ +

Developers that use the GNU GPL protect your rights with two steps: +(1) assert copyright on the software, and (2) offer you this License +giving you legal permission to copy, distribute and/or modify it.

+ +

For the developers' and authors' protection, the GPL clearly explains +that there is no warranty for this free software. For both users' and +authors' sake, the GPL requires that modified versions be marked as +changed, so that their problems will not be attributed erroneously to +authors of previous versions.

+ +

Some devices are designed to deny users access to install or run +modified versions of the software inside them, although the manufacturer +can do so. This is fundamentally incompatible with the aim of +protecting users' freedom to change the software. The systematic +pattern of such abuse occurs in the area of products for individuals to +use, which is precisely where it is most unacceptable. Therefore, we +have designed this version of the GPL to prohibit the practice for those +products. If such problems arise substantially in other domains, we +stand ready to extend this provision to those domains in future versions +of the GPL, as needed to protect the freedom of users.

+ +

Finally, every program is threatened constantly by software patents. +States should not allow patents to restrict development and use of +software on general-purpose computers, but in those that do, we wish to +avoid the special danger that patents applied to a free program could +make it effectively proprietary. To prevent this, the GPL assures that +patents cannot be used to render the program non-free.

+ +

The precise terms and conditions for copying, distribution and +modification follow.

+ +

TERMS AND CONDITIONS

+ +

0. Definitions.

+ +

“This License” refers to version 3 of the GNU General Public License.

+ +

“Copyright” also means copyright-like laws that apply to other kinds of +works, such as semiconductor masks.

+ +

“The Program” refers to any copyrightable work licensed under this +License. Each licensee is addressed as “you”. “Licensees” and + +“recipients” may be individuals or organizations.

+ +

To “modify” a work means to copy from or adapt all or part of the work +in a fashion requiring copyright permission, other than the making of an +exact copy. The resulting work is called a “modified version” of the +earlier work or a work “based on” the earlier work.

+ +

A “covered work” means either the unmodified Program or a work based +on the Program.

+ +

To “propagate” a work means to do anything with it that, without +permission, would make you directly or secondarily liable for +infringement under applicable copyright law, except executing it on a +computer or modifying a private copy. Propagation includes copying, +distribution (with or without modification), making available to the +public, and in some countries other activities as well.

+ +

To “convey” a work means any kind of propagation that enables other +parties to make or receive copies. Mere interaction with a user through +a computer network, with no transfer of a copy, is not conveying.

+ +

An interactive user interface displays “Appropriate Legal Notices” +to the extent that it includes a convenient and prominently visible +feature that (1) displays an appropriate copyright notice, and (2) +tells the user that there is no warranty for the work (except to the +extent that warranties are provided), that licensees may convey the +work under this License, and how to view a copy of this License. If +the interface presents a list of user commands or options, such as a +menu, a prominent item in the list meets this criterion.

+ +

1. Source Code.

+ +

The “source code” for a work means the preferred form of the work +for making modifications to it. “Object code” means any non-source +form of a work.

+ +

A “Standard Interface” means an interface that either is an official +standard defined by a recognized standards body, or, in the case of +interfaces specified for a particular programming language, one that +is widely used among developers working in that language.

+ +

The “System Libraries” of an executable work include anything, other +than the work as a whole, that (a) is included in the normal form of +packaging a Major Component, but which is not part of that Major +Component, and (b) serves only to enable use of the work with that +Major Component, or to implement a Standard Interface for which an +implementation is available to the public in source code form. A +“Major Component”, in this context, means a major essential component +(kernel, window system, and so on) of the specific operating system +(if any) on which the executable work runs, or a compiler used to +produce the work, or an object code interpreter used to run it.

+ +

The “Corresponding Source” for a work in object code form means all +the source code needed to generate, install, and (for an executable +work) run the object code and to modify the work, including scripts to +control those activities. However, it does not include the work's +System Libraries, or general-purpose tools or generally available free +programs which are used unmodified in performing those activities but +which are not part of the work. For example, Corresponding Source +includes interface definition files associated with source files for +the work, and the source code for shared libraries and dynamically +linked subprograms that the work is specifically designed to require, +such as by intimate data communication or control flow between those +subprograms and other parts of the work.

+ +

The Corresponding Source need not include anything that users +can regenerate automatically from other parts of the Corresponding +Source.

+ +

The Corresponding Source for a work in source code form is that +same work.

+ +

2. Basic Permissions.

+ +

All rights granted under this License are granted for the term of +copyright on the Program, and are irrevocable provided the stated +conditions are met. This License explicitly affirms your unlimited +permission to run the unmodified Program. The output from running a +covered work is covered by this License only if the output, given its +content, constitutes a covered work. This License acknowledges your +rights of fair use or other equivalent, as provided by copyright law.

+ +

You may make, run and propagate covered works that you do not +convey, without conditions so long as your license otherwise remains +in force. You may convey covered works to others for the sole purpose +of having them make modifications exclusively for you, or provide you +with facilities for running those works, provided that you comply with +the terms of this License in conveying all material for which you do +not control copyright. Those thus making or running the covered works +for you must do so exclusively on your behalf, under your direction +and control, on terms that prohibit them from making any copies of +your copyrighted material outside their relationship with you.

+ +

Conveying under any other circumstances is permitted solely under +the conditions stated below. Sublicensing is not allowed; section 10 +makes it unnecessary.

+ +

3. Protecting Users' Legal Rights From Anti-Circumvention Law.

+ +

No covered work shall be deemed part of an effective technological +measure under any applicable law fulfilling obligations under article +11 of the WIPO copyright treaty adopted on 20 December 1996, or +similar laws prohibiting or restricting circumvention of such +measures.

+ +

When you convey a covered work, you waive any legal power to forbid +circumvention of technological measures to the extent such circumvention +is effected by exercising rights under this License with respect to +the covered work, and you disclaim any intention to limit operation or +modification of the work as a means of enforcing, against the work's +users, your or third parties' legal rights to forbid circumvention of +technological measures.

+ +

4. Conveying Verbatim Copies.

+ +

You may convey verbatim copies of the Program's source code as you +receive it, in any medium, provided that you conspicuously and +appropriately publish on each copy an appropriate copyright notice; +keep intact all notices stating that this License and any +non-permissive terms added in accord with section 7 apply to the code; +keep intact all notices of the absence of any warranty; and give all +recipients a copy of this License along with the Program.

+ +

You may charge any price or no price for each copy that you convey, +and you may offer support or warranty protection for a fee.

+ +

5. Conveying Modified Source Versions.

+ +

You may convey a work based on the Program, or the modifications to +produce it from the Program, in the form of source code under the +terms of section 4, provided that you also meet all of these conditions:

+ +
    +
  • a) The work must carry prominent notices stating that you modified + it, and giving a relevant date.
  • + +
  • b) The work must carry prominent notices stating that it is + released under this License and any conditions added under section + 7. This requirement modifies the requirement in section 4 to + “keep intact all notices”.
  • + +
  • c) You must license the entire work, as a whole, under this + License to anyone who comes into possession of a copy. This + License will therefore apply, along with any applicable section 7 + additional terms, to the whole of the work, and all its parts, + regardless of how they are packaged. This License gives no + permission to license the work in any other way, but it does not + invalidate such permission if you have separately received it.
  • + +
  • d) If the work has interactive user interfaces, each must display + Appropriate Legal Notices; however, if the Program has interactive + interfaces that do not display Appropriate Legal Notices, your + work need not make them do so.
  • +
+ +

A compilation of a covered work with other separate and independent +works, which are not by their nature extensions of the covered work, +and which are not combined with it such as to form a larger program, +in or on a volume of a storage or distribution medium, is called an +“aggregate” if the compilation and its resulting copyright are not +used to limit the access or legal rights of the compilation's users +beyond what the individual works permit. Inclusion of a covered work +in an aggregate does not cause this License to apply to the other +parts of the aggregate.

+ +

6. Conveying Non-Source Forms.

+ +

You may convey a covered work in object code form under the terms +of sections 4 and 5, provided that you also convey the +machine-readable Corresponding Source under the terms of this License, +in one of these ways:

+ +
    +
  • a) Convey the object code in, or embodied in, a physical product + (including a physical distribution medium), accompanied by the + Corresponding Source fixed on a durable physical medium + customarily used for software interchange.
  • + +
  • b) Convey the object code in, or embodied in, a physical product + (including a physical distribution medium), accompanied by a + written offer, valid for at least three years and valid for as + long as you offer spare parts or customer support for that product + model, to give anyone who possesses the object code either (1) a + copy of the Corresponding Source for all the software in the + product that is covered by this License, on a durable physical + medium customarily used for software interchange, for a price no + more than your reasonable cost of physically performing this + conveying of source, or (2) access to copy the + Corresponding Source from a network server at no charge.
  • + +
  • c) Convey individual copies of the object code with a copy of the + written offer to provide the Corresponding Source. This + alternative is allowed only occasionally and noncommercially, and + only if you received the object code with such an offer, in accord + with subsection 6b.
  • + +
  • d) Convey the object code by offering access from a designated + place (gratis or for a charge), and offer equivalent access to the + Corresponding Source in the same way through the same place at no + further charge. You need not require recipients to copy the + Corresponding Source along with the object code. If the place to + copy the object code is a network server, the Corresponding Source + may be on a different server (operated by you or a third party) + that supports equivalent copying facilities, provided you maintain + clear directions next to the object code saying where to find the + Corresponding Source. Regardless of what server hosts the + Corresponding Source, you remain obligated to ensure that it is + available for as long as needed to satisfy these requirements.
  • + +
  • e) Convey the object code using peer-to-peer transmission, provided + you inform other peers where the object code and Corresponding + Source of the work are being offered to the general public at no + charge under subsection 6d.
  • +
+ +

A separable portion of the object code, whose source code is excluded +from the Corresponding Source as a System Library, need not be +included in conveying the object code work.

+ +

A “User Product” is either (1) a “consumer product”, which means any +tangible personal property which is normally used for personal, family, +or household purposes, or (2) anything designed or sold for incorporation +into a dwelling. In determining whether a product is a consumer product, +doubtful cases shall be resolved in favor of coverage. For a particular +product received by a particular user, “normally used” refers to a +typical or common use of that class of product, regardless of the status +of the particular user or of the way in which the particular user +actually uses, or expects or is expected to use, the product. A product +is a consumer product regardless of whether the product has substantial +commercial, industrial or non-consumer uses, unless such uses represent +the only significant mode of use of the product.

+ +

“Installation Information” for a User Product means any methods, +procedures, authorization keys, or other information required to install +and execute modified versions of a covered work in that User Product from +a modified version of its Corresponding Source. The information must +suffice to ensure that the continued functioning of the modified object +code is in no case prevented or interfered with solely because +modification has been made.

+ +

If you convey an object code work under this section in, or with, or +specifically for use in, a User Product, and the conveying occurs as +part of a transaction in which the right of possession and use of the +User Product is transferred to the recipient in perpetuity or for a +fixed term (regardless of how the transaction is characterized), the +Corresponding Source conveyed under this section must be accompanied +by the Installation Information. But this requirement does not apply +if neither you nor any third party retains the ability to install +modified object code on the User Product (for example, the work has +been installed in ROM).

+ +

The requirement to provide Installation Information does not include a +requirement to continue to provide support service, warranty, or updates +for a work that has been modified or installed by the recipient, or for +the User Product in which it has been modified or installed. Access to a +network may be denied when the modification itself materially and +adversely affects the operation of the network or violates the rules and +protocols for communication across the network.

+ +

Corresponding Source conveyed, and Installation Information provided, +in accord with this section must be in a format that is publicly +documented (and with an implementation available to the public in +source code form), and must require no special password or key for +unpacking, reading or copying.

+ +

7. Additional Terms.

+ +

“Additional permissions” are terms that supplement the terms of this +License by making exceptions from one or more of its conditions. +Additional permissions that are applicable to the entire Program shall +be treated as though they were included in this License, to the extent +that they are valid under applicable law. If additional permissions +apply only to part of the Program, that part may be used separately +under those permissions, but the entire Program remains governed by +this License without regard to the additional permissions.

+ +

When you convey a copy of a covered work, you may at your option +remove any additional permissions from that copy, or from any part of +it. (Additional permissions may be written to require their own +removal in certain cases when you modify the work.) You may place +additional permissions on material, added by you to a covered work, +for which you have or can give appropriate copyright permission.

+ +

Notwithstanding any other provision of this License, for material you +add to a covered work, you may (if authorized by the copyright holders of +that material) supplement the terms of this License with terms:

+ +
    +
  • a) Disclaiming warranty or limiting liability differently from the + terms of sections 15 and 16 of this License; or
  • + +
  • b) Requiring preservation of specified reasonable legal notices or + author attributions in that material or in the Appropriate Legal + Notices displayed by works containing it; or
  • + +
  • c) Prohibiting misrepresentation of the origin of that material, or + requiring that modified versions of such material be marked in + reasonable ways as different from the original version; or
  • + +
  • d) Limiting the use for publicity purposes of names of licensors or + authors of the material; or
  • + +
  • e) Declining to grant rights under trademark law for use of some + trade names, trademarks, or service marks; or
  • + +
  • f) Requiring indemnification of licensors and authors of that + material by anyone who conveys the material (or modified versions of + it) with contractual assumptions of liability to the recipient, for + any liability that these contractual assumptions directly impose on + those licensors and authors.
  • +
+ +

All other non-permissive additional terms are considered “further +restrictions” within the meaning of section 10. If the Program as you +received it, or any part of it, contains a notice stating that it is +governed by this License along with a term that is a further +restriction, you may remove that term. If a license document contains +a further restriction but permits relicensing or conveying under this +License, you may add to a covered work material governed by the terms +of that license document, provided that the further restriction does +not survive such relicensing or conveying.

+ +

If you add terms to a covered work in accord with this section, you +must place, in the relevant source files, a statement of the +additional terms that apply to those files, or a notice indicating +where to find the applicable terms.

+ +

Additional terms, permissive or non-permissive, may be stated in the +form of a separately written license, or stated as exceptions; +the above requirements apply either way.

+ +

8. Termination.

+ +

You may not propagate or modify a covered work except as expressly +provided under this License. Any attempt otherwise to propagate or +modify it is void, and will automatically terminate your rights under +this License (including any patent licenses granted under the third +paragraph of section 11).

+ +

However, if you cease all violation of this License, then your +license from a particular copyright holder is reinstated (a) +provisionally, unless and until the copyright holder explicitly and +finally terminates your license, and (b) permanently, if the copyright +holder fails to notify you of the violation by some reasonable means +prior to 60 days after the cessation.

+ +

Moreover, your license from a particular copyright holder is +reinstated permanently if the copyright holder notifies you of the +violation by some reasonable means, this is the first time you have +received notice of violation of this License (for any work) from that +copyright holder, and you cure the violation prior to 30 days after +your receipt of the notice.

+ +

Termination of your rights under this section does not terminate the +licenses of parties who have received copies or rights from you under +this License. If your rights have been terminated and not permanently +reinstated, you do not qualify to receive new licenses for the same +material under section 10.

+ +

9. Acceptance Not Required for Having Copies.

+ +

You are not required to accept this License in order to receive or +run a copy of the Program. Ancillary propagation of a covered work +occurring solely as a consequence of using peer-to-peer transmission +to receive a copy likewise does not require acceptance. However, +nothing other than this License grants you permission to propagate or +modify any covered work. These actions infringe copyright if you do +not accept this License. Therefore, by modifying or propagating a +covered work, you indicate your acceptance of this License to do so.

+ +

10. Automatic Licensing of Downstream Recipients.

+ +

Each time you convey a covered work, the recipient automatically +receives a license from the original licensors, to run, modify and +propagate that work, subject to this License. You are not responsible +for enforcing compliance by third parties with this License.

+ +

An “entity transaction” is a transaction transferring control of an +organization, or substantially all assets of one, or subdividing an +organization, or merging organizations. If propagation of a covered +work results from an entity transaction, each party to that +transaction who receives a copy of the work also receives whatever +licenses to the work the party's predecessor in interest had or could +give under the previous paragraph, plus a right to possession of the +Corresponding Source of the work from the predecessor in interest, if +the predecessor has it or can get it with reasonable efforts.

+ +

You may not impose any further restrictions on the exercise of the +rights granted or affirmed under this License. For example, you may +not impose a license fee, royalty, or other charge for exercise of +rights granted under this License, and you may not initiate litigation +(including a cross-claim or counterclaim in a lawsuit) alleging that +any patent claim is infringed by making, using, selling, offering for +sale, or importing the Program or any portion of it.

+ +

11. Patents.

+ +

A “contributor” is a copyright holder who authorizes use under this +License of the Program or a work on which the Program is based. The +work thus licensed is called the contributor's “contributor version”.

+ +

A contributor's “essential patent claims” are all patent claims +owned or controlled by the contributor, whether already acquired or +hereafter acquired, that would be infringed by some manner, permitted +by this License, of making, using, or selling its contributor version, +but do not include claims that would be infringed only as a +consequence of further modification of the contributor version. For +purposes of this definition, “control” includes the right to grant +patent sublicenses in a manner consistent with the requirements of +this License.

+ +

Each contributor grants you a non-exclusive, worldwide, royalty-free +patent license under the contributor's essential patent claims, to +make, use, sell, offer for sale, import and otherwise run, modify and +propagate the contents of its contributor version.

+ +

In the following three paragraphs, a “patent license” is any express +agreement or commitment, however denominated, not to enforce a patent +(such as an express permission to practice a patent or covenant not to +sue for patent infringement). To “grant” such a patent license to a +party means to make such an agreement or commitment not to enforce a +patent against the party.

+ +

If you convey a covered work, knowingly relying on a patent license, +and the Corresponding Source of the work is not available for anyone +to copy, free of charge and under the terms of this License, through a +publicly available network server or other readily accessible means, +then you must either (1) cause the Corresponding Source to be so +available, or (2) arrange to deprive yourself of the benefit of the +patent license for this particular work, or (3) arrange, in a manner +consistent with the requirements of this License, to extend the patent +license to downstream recipients. “Knowingly relying” means you have +actual knowledge that, but for the patent license, your conveying the +covered work in a country, or your recipient's use of the covered work +in a country, would infringe one or more identifiable patents in that +country that you have reason to believe are valid.

+ + +

If, pursuant to or in connection with a single transaction or +arrangement, you convey, or propagate by procuring conveyance of, a +covered work, and grant a patent license to some of the parties +receiving the covered work authorizing them to use, propagate, modify +or convey a specific copy of the covered work, then the patent license +you grant is automatically extended to all recipients of the covered +work and works based on it.

+ +

A patent license is “discriminatory” if it does not include within +the scope of its coverage, prohibits the exercise of, or is +conditioned on the non-exercise of one or more of the rights that are +specifically granted under this License. You may not convey a covered +work if you are a party to an arrangement with a third party that is +in the business of distributing software, under which you make payment +to the third party based on the extent of your activity of conveying +the work, and under which the third party grants, to any of the +parties who would receive the covered work from you, a discriminatory +patent license (a) in connection with copies of the covered work +conveyed by you (or copies made from those copies), or (b) primarily +for and in connection with specific products or compilations that +contain the covered work, unless you entered into that arrangement, +or that patent license was granted, prior to 28 March 2007.

+ +

Nothing in this License shall be construed as excluding or limiting +any implied license or other defenses to infringement that may +otherwise be available to you under applicable patent law.

+ +

12. No Surrender of Others' Freedom.

+ +

If conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot convey a +covered work so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you may +not convey it at all. For example, if you agree to terms that obligate you +to collect a royalty for further conveying from those to whom you convey +the Program, the only way you could satisfy both those terms and this +License would be to refrain entirely from conveying the Program.

+ +

13. Use with the GNU Affero General Public License.

+ +

Notwithstanding any other provision of this License, you have +permission to link or combine any covered work with a work licensed +under version 3 of the GNU Affero General Public License into a single +combined work, and to convey the resulting work. The terms of this +License will continue to apply to the part which is the covered work, +but the special requirements of the GNU Affero General Public License, +section 13, concerning interaction through a network will apply to the +combination as such.

+ +

14. Revised Versions of this License.

+ +

The Free Software Foundation may publish revised and/or new versions of +the GNU General Public License from time to time. Such new versions will +be similar in spirit to the present version, but may differ in detail to +address new problems or concerns.

+ +

Each version is given a distinguishing version number. If the +Program specifies that a certain numbered version of the GNU General +Public License “or any later version” applies to it, you have the +option of following the terms and conditions either of that numbered +version or of any later version published by the Free Software +Foundation. If the Program does not specify a version number of the +GNU General Public License, you may choose any version ever published +by the Free Software Foundation.

+ +

If the Program specifies that a proxy can decide which future +versions of the GNU General Public License can be used, that proxy's +public statement of acceptance of a version permanently authorizes you +to choose that version for the Program.

+ +

Later license versions may give you additional or different +permissions. However, no additional obligations are imposed on any +author or copyright holder as a result of your choosing to follow a +later version.

+ +

15. Disclaimer of Warranty.

+ +

THERE IS NO WARRANTY FOR THE PROGRAM, TO THE EXTENT PERMITTED BY +APPLICABLE LAW. EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT +HOLDERS AND/OR OTHER PARTIES PROVIDE THE PROGRAM “AS IS” WITHOUT WARRANTY +OF ANY KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, +THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE PROGRAM +IS WITH YOU. SHOULD THE PROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF +ALL NECESSARY SERVICING, REPAIR OR CORRECTION.

+ +

16. Limitation of Liability.

+ +

IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING +WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MODIFIES AND/OR CONVEYS +THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES, INCLUDING ANY +GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING OUT OF THE +USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED TO LOSS OF +DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD +PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER PROGRAMS), +EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF +SUCH DAMAGES.

+ +

17. Interpretation of Sections 15 and 16.

+ +

If the disclaimer of warranty and limitation of liability provided +above cannot be given local legal effect according to their terms, +reviewing courts shall apply local law that most closely approximates +an absolute waiver of all civil liability in connection with the +Program, unless a warranty or assumption of liability accompanies a +copy of the Program in return for a fee.

+ +

END OF TERMS AND CONDITIONS

+ +

How to Apply These Terms to Your New Programs

+ +

If you develop a new program, and you want it to be of the greatest +possible use to the public, the best way to achieve this is to make it +free software which everyone can redistribute and change under these terms.

+ +

To do so, attach the following notices to the program. It is safest +to attach them to the start of each source file to most effectively +state the exclusion of warranty; and each file should have at least +the “copyright” line and a pointer to where the full notice is found.

+ +
    <one line to give the program's name and a brief idea of what it does.>
+    Copyright (C) <year>  <name of author>
+
+    This program is free software: you can redistribute it and/or modify
+    it under the terms of the GNU General Public License as published by
+    the Free Software Foundation, either version 3 of the License, or
+    (at your option) any later version.
+
+    This program is distributed in the hope that it will be useful,
+    but WITHOUT ANY WARRANTY; without even the implied warranty of
+    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
+    GNU General Public License for more details.
+
+    You should have received a copy of the GNU General Public License
+    along with this program.  If not, see <http://www.gnu.org/licenses/>.
+
+ +

Also add information on how to contact you by electronic and paper mail.

+ +

If the program does terminal interaction, make it output a short +notice like this when it starts in an interactive mode:

+ +
    <program>  Copyright (C) <year>  <name of author>
+
+    This program comes with ABSOLUTELY NO WARRANTY; for details type `show w'.
+    This is free software, and you are welcome to redistribute it
+    under certain conditions; type `show c' for details.
+
+ +

The hypothetical commands `show w' and `show c' should show the appropriate +parts of the General Public License. Of course, your program's commands +might be different; for a GUI interface, you would use an “about box”.

+ +

You should also get your employer (if you work as a programmer) or school, +if any, to sign a “copyright disclaimer” for the program, if necessary. +For more information on this, and how to apply and follow the GNU GPL, see +<http://www.gnu.org/licenses/>.

+ +

The GNU General Public License does not permit incorporating your program +into proprietary programs. If your program is a subroutine library, you +may consider it more useful to permit linking proprietary applications with +the library. If this is what you want to do, use the GNU Lesser General +Public License instead of this License. But first, please read +<http://www.gnu.org/philosophy/why-not-lgpl.html>.

+ + +
+ + Valid XHTML 1.0 Transitional + + Valid CSS + + + diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/CommonChamiloDatabaseCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/CommonChamiloDatabaseCommand.php new file mode 100644 index 0000000000..779c718785 --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/CommonChamiloDatabaseCommand.php @@ -0,0 +1,31 @@ +addOption( + 'conf', + null, + InputOption::VALUE_NONE, + 'Set a configuration file' + ); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + $configuration = $input->getOption('conf'); + $this->getHelper('configuration')->readConfigurationFile($configuration); + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/DropDatabaseCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/DropDatabaseCommand.php new file mode 100644 index 0000000000..8d6153f232 --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/DropDatabaseCommand.php @@ -0,0 +1,65 @@ +setName('db:drop_databases') + ->setDescription('Drops all databases from the current Chamilo install'); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + + $dialog = $this->getHelperSet()->get('dialog'); + + if (!$dialog->askConfirmation( + $output, + 'Are you sure you want to drop all database in this portal? (y/N)', + false + ) + ) { + return; + } + + if (!$dialog->askConfirmation( + $output, + 'Really sure? (y/N)', + false + ) + ) { + return; + } + + $_configuration = $this->getHelper('configuration')->getConfiguration(); + $connection = $this->getHelper('configuration')->getConnection(); + + if ($connection) { + $cmd = 'mysql -h '.$_configuration['db_host'].' -u '.$_configuration['db_user'].' -p'.$_configuration['db_password'].' -e "DROP DATABASE %s"'; + $list = $_configuration = $this->getHelper('configuration')->getAllDatabases(); + if (is_array($list)) { + $output->writeln('Starting Chamilo process'); + foreach ($list as $db) { + $c = sprintf($cmd, $db); + $output->writeln("Dropping DB: $db"); + $err = @system($c); + } + $output->writeln('End Chamilo process'); + } + } else { + $output->writeln("Can't stablished connection with the database"); + } + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/DumpCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/DumpCommand.php new file mode 100644 index 0000000000..6f7a9492e0 --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/DumpCommand.php @@ -0,0 +1,39 @@ +setName('db:dump') + ->setDescription('Outputs a dump of the database'); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + $_configuration = $this->getHelper('configuration')->getConfiguration(); + $dump = 'mysqldump -h '.$_configuration['db_host'].' -u '.$_configuration['db_user'].' -p'.$_configuration['db_password'].' '.$_configuration['main_database']; + system($dump); + return null; + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/FullBackupCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/FullBackupCommand.php new file mode 100644 index 0000000000..922a300276 --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/FullBackupCommand.php @@ -0,0 +1,106 @@ +setHelp( + 'The full_backup command allows you to do a full backup of the files and database of a given Chamilo installation' + ); + + $this + ->setName('db:full_backup') + ->setDescription('Generates a .tgz from the Chamilo files and database') + ->addArgument( + 'result', + InputArgument::REQUIRED, + 'Allows you to specify a destination file, e.g. database:full_backup /home/user/backup.tgz or backup.tgz' + ) + ->addOption( + 'tmp', + null, + InputOption::VALUE_OPTIONAL, + 'Allows you to specify in which temporary directory the backup files should be placed (optional, defaults to /tmp)' + ) + ->addOption( + 'del-archive', + null, + InputOption::VALUE_NONE, + 'Deletes the contents of the archive/ directory before the backup is executed' + ); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + + $_configuration = $this->getHelper('configuration')->getConfiguration(); + $resultPath = $input->getArgument('result'); + $tmpFolder = $input->getOption('tmp'); + + if (empty($tmpFolder)) { + $output->writeln( + 'No temporary directory defined. Assuming /tmp/. Please make sure you have *enough space* left on that device' + ); + $tmpFolder = '/tmp'; + } + + $deleteTemp = $input->getOption('del-archive'); + + if ($deleteTemp) { + //Calling command + $command = $this->getApplication()->find('files:clean_archives'); + + $arguments = array( + 'command' => 'files:clean_archives' + ); + $input = new ArrayInput($arguments); + $command->run($input, $output); + } else { + $output->writeln('Temp archives are not removed'); + } + + $cha_dir = realpath($_configuration['root_sys']); + + $output->writeln('Starting full backup'); + + $f = $_configuration['db_user']; + //backup the files (this requires root permissions) + $bkp_dir = $tmpFolder.'/'.$f.'-'.date('Ymdhis'); + $err = @mkdir($bkp_dir); + $tgz = $bkp_dir.'/'.$f.'.tgz'; + $sql = $bkp_dir.'/'.$f.'-db.sql'; + $err = @system('tar zcf '.$tgz.' '.$cha_dir); + + $output->writeln('Generating mysqldump'); + + $err = @system( + 'mysqldump -h '.$_configuration['db_host'].' -u '.$_configuration['db_user'].' -p'.$_configuration['db_password'].' '.$_configuration['main_database'].' --result-file='.$sql + ); + + $output->writeln('Generating tarball '); + + $err = @system('tar zcf '.$resultPath.' '.$bkp_dir); + $err = @system('rm -rf '.$bkp_dir); + + $output->writeln( + 'End Chamilo backup. File can be found here: '.realpath($resultPath).' ' + ); + + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/RestoreCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/RestoreCommand.php new file mode 100644 index 0000000000..ac7dc5554a --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/RestoreCommand.php @@ -0,0 +1,49 @@ +setName('db:restore') + ->setDescription( + 'Allows you to restore an SQL dump right into the active database of a given Chamilo installation (which will also erase all previous data in that database)' + ) + ->addArgument( + 'file', + InputArgument::REQUIRED, + 'Specify the dump\'s full path, e.g. database:restore /tmp/dump.sql' + ); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + $dumpPath = $input->getArgument('file'); + if (!is_dir($dumpPath) && file_exists($dumpPath)) { + $_configuration = $this->getHelper('configuration')->getConfiguration(); + + $output->writeln('Starting restoring database'); + $action = 'mysql -h '.$_configuration['db_host'].' -u '.$_configuration['db_user'].' -p'.$_configuration['db_password'].' '.$_configuration['main_database'].' < '.$dumpPath; + system($action); + $output->writeln('Process ended succesfully'); + } else { + $output->writeln('File is not a valid SQL file: '.$dumpPath.' '); + } + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/RunSQLCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/RunSQLCommand.php new file mode 100644 index 0000000000..af0c09e5a2 --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/RunSQLCommand.php @@ -0,0 +1,63 @@ +setName('db:sql_cli') + ->setDescription('Enters to the SQL command line'); + $this->setHelp('Prompts a SQL cli'); + + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + $output->writeln('Starting Chamilo SQL cli'); + + $_configuration = $this->getHelper('configuration')->getConfiguration(); + + $cmd = 'mysql -h '.$_configuration['db_host'].' -u '.$_configuration['db_user'].' -p'.$_configuration['db_password'].' '.$_configuration['main_database']; + $process = proc_open($cmd, array(0 => STDIN, 1 => STDOUT, 2 => STDERR), $pipes); + $proc_status = proc_get_status($process); + $exit_code = proc_close($process); + return ($proc_status["running"] ? $exit_code : $proc_status["exitcode"]); + + /*$output->writeln('Starting Chamilo process'); + $output->writeln('Chamilo process ended succesfully'); + */ + /* + $progress = $this->getHelperSet()->get('progress'); + + $progress->start($output, 50); + $i = 0; + while ($i++ < 50) { + // ... do some work + + // advance the progress bar 1 unit + $progress->advance(); + } + $progress->finish();*/ + + // Inside execute function + //$output->getFormatter()->setStyle('fcbarcelona', new OutputFormatterStyle('red', 'blue', array('blink', 'bold', 'underscore'))); + //$output->writeln('Messi for the win'); + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Database/SQLCountCommand.php b/vendor/chamilo/chash/src/Chash/Command/Database/SQLCountCommand.php new file mode 100644 index 0000000000..57f23c7ce5 --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Database/SQLCountCommand.php @@ -0,0 +1,51 @@ +setName('db:sql_count') + ->setDescription('Count the number of rows in a specific table') + ->addArgument( + 'table', + InputArgument::REQUIRED, + 'Name of the table' + ); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + $table = $input->getArgument('table'); + $_configuration = $this->getHelper('configuration')->getConfiguration(); + $connection = $this->getHelper('configuration')->getConnection(); + + $t = mysql_real_escape_string($table); + $q = mysql_query('SELECT COUNT(*) FROM '.$t); + if ($q !== false) { + $r = mysql_fetch_row($q); + $n = $r[0]; + $output->writeln( + 'Database/table/number of rows: '.$_configuration['main_database'].'/'.$t.'/'.$n.'' + ); + } else { + $output->writeln( + "Table '$table' does not exists in the database: ".$_configuration['main_database'] + ); + } + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Files/CleanConfigFiles.php b/vendor/chamilo/chash/src/Chash/Command/Files/CleanConfigFiles.php new file mode 100644 index 0000000000..6c8d78fb1f --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Files/CleanConfigFiles.php @@ -0,0 +1,65 @@ +setName('files:clean_config_files') + ->setDescription('Cleans the archives directory'); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + + $output->writeln('Starting cleaning your Chamilo installation'); + + $dialog = $this->getHelperSet()->get('dialog'); + + if (!$dialog->askConfirmation( + $output, + 'Are you sure you want to clean your config files? (y/N)', + false + ) + ) { + return; + } + + $filesToDelete = $this->getHelper('configuration')->getConfigFiles(); + + if (!empty($filesToDelete)) { + foreach ($filesToDelete as $file) { + if (isset($file) && file_exists($file) && is_file($file)) { + if (!$dialog->askConfirmation( + $output, + "Are you sure you want to delete: $file (y/N)", + false + ) + ) { + return; + } + unlink($file); + $output->writeln("File deleted: $file"); + } + } + } else { + $output->writeln("Nothing to delete"); + } + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Files/CleanTempFolderCommand.php b/vendor/chamilo/chash/src/Chash/Command/Files/CleanTempFolderCommand.php new file mode 100644 index 0000000000..bf41e03e3a --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Files/CleanTempFolderCommand.php @@ -0,0 +1,67 @@ +setName('files:clean_archives') + ->setDescription('Cleans the archives directory'); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + $output->writeln('Starting Clean temp folders '); + + $dialog = $this->getHelperSet()->get('dialog'); + + if (!$dialog->askConfirmation( + $output, + 'Are you sure you want to clean the Chamilo temp files? (y/N)', + false + ) + ) { + return; + } + + $_configuration = $this->getHelper('configuration')->getConfiguration(); + + if (empty($_configuration['root_sys'])) { + $output->writeln( + '$_configuration[\'root_sys\'] is empty. In these conditions, it is too dangerous to proceed with the deletion. Please ensure this variable is defined in main/inc/conf/configuration.php' + ); + return false; + } + + $dir = $_configuration['root_sys'].'archive'; + $files = scandir($dir); + foreach ($files as $file) { + if (substr($file, 0, 1) == '.') { + //ignore + } elseif ($file == 'twig') { + $err = @system('rm -rf '.$dir.'/twig/*'); + } elseif ($file == 'Serializer') { + $err = @system('rm -rf '.$dir.'/Serializer/*'); + } else { + $err = @system('rm -rf '.$dir.'/'.$file); + } + } + $output->writeln('Files were cleaned'); + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Translation/ExportLanguageCommand.php b/vendor/chamilo/chash/src/Chash/Command/Translation/ExportLanguageCommand.php new file mode 100644 index 0000000000..857ce16c9f --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Translation/ExportLanguageCommand.php @@ -0,0 +1,107 @@ +setName('translation:export_language') + ->setDescription('Exports a Chamilo language package') + ->addArgument( + 'language', + InputArgument::REQUIRED, + 'Which language you want to export' + ) + ->addOption( + 'tmp', + null, + InputOption::VALUE_OPTIONAL, + 'Allows you to specify in which temporary directory the backup files should be placed (optional, defaults to /tmp)' + ); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + + $language = $input->getArgument('language'); + $tmpFolder = $input->getOption('tmp'); + + $_configuration = $this->getHelper('configuration')->getConfiguration(); + + $connection = $this->getHelper('configuration')->getConnection(); + + if ($connection) { + $lang = isset($language) ? $language : null; + + $lang = mysql_real_escape_string($lang); + + $q = mysql_query("SELECT * FROM language WHERE english_name = '$lang' "); + $langInfo = mysql_fetch_array($q, MYSQL_ASSOC); + + if (!$langInfo) { + + $output->writeln("Language '$lang' is not registered in the Chamilo Database"); + + $q = mysql_query("SELECT * FROM language WHERE parent_id IS NULL or parent_id = 0"); + $output->writeln("Available languages are: "); + while ($langRow = mysql_fetch_array($q, MYSQL_ASSOC)) { + $output->write($langRow['english_name'].", "); + } + $output->writeln(' '); + + $q = mysql_query("SELECT * FROM language WHERE parent_id <> 0"); + $output->writeln("Available sub languages are: "); + while ($langRow = mysql_fetch_array($q, MYSQL_ASSOC)) { + $output->write($langRow['english_name'].", "); + } + $output->writeln(' '); + exit; + } else { + $output->writeln( + "Language '$lang' is registered in the Chamilo installation with iso code: {$langInfo['isocode']} " + ); + } + + $langFolder = $_configuration['root_sys'].'main/lang/'.$lang; + + if (!is_dir($langFolder)) { + $output->writeln("Language '$lang' does not exist in the path: $langFolder"); + } + + if (empty($tmpFolder)) { + $tmpFolder = '/tmp/'; + $output->writeln( + "No temporary directory defined. Assuming /tmp/. Please make sure you have *enough space* left on that device" + ); + } + + if (!is_dir($tmpFolder)) { + $output->writeln( + "Temporary directory: $tmpFolder is not a valid dir path, using /tmp/ " + ); + $tmpFolder = '/tmp/'; + } + + if ($langInfo) { + $output->writeln("Creating translation package"); + $fileName = $tmpFolder.$langInfo['english_name'].'.tar'; + $phar = new \PharData($fileName); + $phar->buildFromDirectory($langFolder); + + $phar->setMetadata($langInfo); + $output->writeln("File created: {$fileName}"); + } + } + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Command/Translation/ImportLanguageCommand.php b/vendor/chamilo/chash/src/Chash/Command/Translation/ImportLanguageCommand.php new file mode 100644 index 0000000000..ba5a52bcce --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Command/Translation/ImportLanguageCommand.php @@ -0,0 +1,135 @@ +setName('translation:import_language') + ->setDescription('Import a Chamilo language package') + ->addArgument( + 'file', + InputArgument::REQUIRED, + 'Path of the language package' + ); + } + + protected function execute(InputInterface $input, OutputInterface $output) + { + parent::execute($input, $output); + + $dialog = $this->getHelperSet()->get('dialog'); + + $_configuration = $this->getHelper('configuration')->getConfiguration(); + + $file = $input->getArgument('file'); + + $connection = $this->getHelper('configuration')->getConnection(); + + if (is_file($file) && is_readable($file)) { + $phar = new \PharData($file); + if ($phar->hasMetadata()) { + $langInfo = $phar->getMetadata(); + + $connection = $this->getHelper('configuration')->getConnection(); + if ($connection) { + $q = mysql_query( + "SELECT * FROM language WHERE dokeos_folder = '{$langInfo['dokeos_folder']}' " + ); + $langInfoFromDB = mysql_fetch_array($q, MYSQL_ASSOC); + $langFolderPath = $_configuration['root_sys'].'main/lang/'.$langInfoFromDB['dokeos_folder']; + if ($langInfoFromDB && $langFolderPath) { + //Overwrite lang files + if (!$dialog->askConfirmation( + $output, + 'The '.$langInfo['original_name'].' language already exists in Chamilo. Did you want to overwrite the contents? (y/N)', + false + ) + ) { + return; + } + if (is_writable($langFolderPath)) { + $output->writeln("Trying to save files here: $langFolderPath"); + $phar->extractTo($langFolderPath, null, true); // extract all files + $output->writeln("Files were copied."); + } else { + $output->writeln( + "Make sure that this folder $langFolderPath has writable permissions or execute the script with sudo " + ); + } + } else { + //Check if parent_id exists + $parentId = ''; + if (!empty($langInfo['parent_id'])) { + $sql = "select selected_value from settings_current where variable = 'allow_use_sub_language'"; + $result = mysql_query($sql); + $subLanguageSetting = mysql_fetch_array($result, MYSQL_ASSOC); + $subLanguageSetting = $subLanguageSetting['selected_value']; + if ($subLanguageSetting == 'true') { + + $q = mysql_query( + "SELECT * FROM language WHERE id = '{$langInfo['parent_id']}' " + ); + $parentLangInfoFromDB = mysql_fetch_array($q, MYSQL_ASSOC); + if ($parentLangInfoFromDB) { + $output->writeln( + "Setting parent language: ".$parentLangInfoFromDB['original_name'] + ); + $parentId = $langInfo['parent_id']; + } else { + $output->writeln( + "The lang parent_id = {$langInfo['parent_id']} does not exist in Chamilo. Try to import first the parent language." + ); + exit; + } + } else { + $output->writeln( + "Please turn ON the sublanguage feature in this portal" + ); + exit; + } + } else { + $output->writeln("Parent language was not provided"); + } + + $q = mysql_query( + "INSERT INTO language (original_name, english_name, isocode, dokeos_folder, available, parent_id) VALUES ( + '".$langInfo['original_name']."', + '".$langInfo['english_name']."', + '".$langInfo['isocode']."', + '".$langInfo['dokeos_folder']."', + '1', + '".$parentId."')" + ); + + if ($q) { + $output->writeln("Language inserted in the DB"); + $langFolderPath = $_configuration['root_sys'].'main/lang/'.$langInfo['dokeos_folder']; + $phar->extractTo($langFolderPath, null, true); // extract all files + $output->writeln("Files were copied here $langFolderPath "); + } else { + $output->writeln("An error ocurred while tring to create the language"); + } + + } + } + + } else { + $output->writeln("The file is not a valid Chamilo language package"); + } + } else { + $output->writeln("The file located in '$file' is not accessible"); + } + + } +} \ No newline at end of file diff --git a/vendor/chamilo/chash/src/Chash/Helpers/ConfigurationHelper.php b/vendor/chamilo/chash/src/Chash/Helpers/ConfigurationHelper.php new file mode 100644 index 0000000000..3e0e1265bf --- /dev/null +++ b/vendor/chamilo/chash/src/Chash/Helpers/ConfigurationHelper.php @@ -0,0 +1,182 @@ +getConfigurationPath($path); + + + if (!empty($confPath)) { + $confFile = $confPath.'configuration.php'; + if (file_exists($confFile)) { + require $confFile; + $this->setConfiguration($_configuration); + + return $_configuration; + } + + $confYML = $confPath.'configuration.yml'; + if (file_exists($confYML)) { + $yaml = new Parser(); + $_configuration = $yaml->parse(file_get_contents($confYML)); + + return $_configuration; + } + } + + return false; + } + + public function setConfiguration($configuration) + { + $this->configuration = $configuration; + } + + public function getConfigFiles() + { + $configFiles = array(); + + $_configuration = $this->getConfiguration(); + + $sysPath = isset($_configuration['sys_path']) ? $_configuration['sys_path'] : null; + + if (file_exists($sysPath.'main/inc/conf/configuration.php')) { + $configFiles[] = $sysPath.'main/inc/conf/configuration.php'; + } + + if (file_exists($sysPath.'main/inc/conf/configuration.yml')) { + $configFiles[] = $sysPath.'main/inc/conf/configuration.yml'; + } + + return $configFiles; + } + + /** + * Connect to the database + * @return object Database handler + */ + public function getConnection() + { + $conf = $this->getConfiguration(); + + $dbh = false; + + if (isset($conf['db_host']) && isset($conf['db_host']) && isset($conf['db_password'])) { + $dbh = mysql_connect($conf['db_host'], $conf['db_user'], $conf['db_password']); + + if (!$dbh) { + + return false; + //die('Could not connect to server: '.mysql_error()); + } + $db = mysql_select_db($conf['main_database'], $dbh); + if (!$db) { + + return false; + //die('Could not connect to database: '.mysql_error()); + } + } + return $dbh; + } + + /** + * Gets an array with all the databases (particularly useful for Chamilo <1.9) + * @return mixed Array of databases + */ + function getAllDatabases() + { + $_configuration = $this->getConfiguration(); + $dbs = array(); + + $dbs[] = $_configuration['main_database']; + + if (isset($_configuration['statistics_database']) && !in_array( + $_configuration['statistics_database'], + $dbs + ) && !empty($_configuration['statistics_database']) + ) { + $dbs[] = $_configuration['statistics_database']; + } + + if (isset($_configuration['scorm_database']) && !in_array( + $_configuration['scorm_database'], + $dbs + ) && !empty($_configuration['scorm_database']) + ) { + $dbs[] = $_configuration['scorm_database']; + } + + if (isset($_configuration['user_personal_database']) && !in_array( + $_configuration['user_personal_database'], + $dbs + ) && !empty($_configuration['user_personal_database']) + ) { + $dbs[] = $_configuration['user_personal_database']; + } + + $t = $_configuration['main_database'].'.course'; + $sql = 'SELECT db_name from '.$t; + $res = mysql_query($sql); + if (mysql_num_rows($res) > 0) { + while ($row = mysql_fetch_array($res)) { + if (!empty($row['db_name'])) { + $dbs[] = $row['db_name']; + } + } + } + return $dbs; + } + + public function getConfiguration() + { + if (empty($this->configuration)) { + $this->configuration = $this->readConfigurationFile(); + } + return $this->configuration; + } + + public function getName() + { + return 'configuration'; + } +} diff --git a/vendor/composer/autoload_namespaces.php b/vendor/composer/autoload_namespaces.php index 27b1775047..02e699a72f 100644 --- a/vendor/composer/autoload_namespaces.php +++ b/vendor/composer/autoload_namespaces.php @@ -44,5 +44,6 @@ return array( 'Dflydev\\Silex\\Provider\\DoctrineOrm' => $vendorDir . '/dflydev/doctrine-orm-service-provider/src', 'Dflydev\\Pimple\\Provider\\DoctrineOrm' => $vendorDir . '/dflydev/doctrine-orm-service-provider/src', 'Dflydev\\Cilex\\Provider\\DoctrineOrm' => $vendorDir . '/dflydev/doctrine-orm-service-provider/src', + 'Chash' => $vendorDir . '/chamilo/chash/src/', 'ChamiloLMS' => $baseDir . '/src/', ); diff --git a/vendor/composer/autoload_real.php b/vendor/composer/autoload_real.php index 1969839fef..2974e12dba 100644 --- a/vendor/composer/autoload_real.php +++ b/vendor/composer/autoload_real.php @@ -2,7 +2,7 @@ // autoload_real.php generated by Composer -class ComposerAutoloaderInitf1ee82f2567fa86f78d258bf9f6cac97 +class ComposerAutoloaderInitccfd96f09fad4b03f395700cf22111c8 { private static $loader; @@ -19,9 +19,9 @@ class ComposerAutoloaderInitf1ee82f2567fa86f78d258bf9f6cac97 return self::$loader; } - spl_autoload_register(array('ComposerAutoloaderInitf1ee82f2567fa86f78d258bf9f6cac97', 'loadClassLoader'), true, true); + spl_autoload_register(array('ComposerAutoloaderInitccfd96f09fad4b03f395700cf22111c8', 'loadClassLoader'), true, true); self::$loader = $loader = new \Composer\Autoload\ClassLoader(); - spl_autoload_unregister(array('ComposerAutoloaderInitf1ee82f2567fa86f78d258bf9f6cac97', 'loadClassLoader')); + spl_autoload_unregister(array('ComposerAutoloaderInitccfd96f09fad4b03f395700cf22111c8', 'loadClassLoader')); $vendorDir = dirname(__DIR__); $baseDir = dirname($vendorDir); diff --git a/vendor/composer/installed.json b/vendor/composer/installed.json index cda94fe5b2..81db2a21aa 100644 --- a/vendor/composer/installed.json +++ b/vendor/composer/installed.json @@ -1998,24 +1998,24 @@ }, { "name": "doctrine/dbal", - "version": "2.3.2", - "version_normalized": "2.3.2.0", + "version": "2.3.3", + "version_normalized": "2.3.3.0", "source": { "type": "git", - "url": "https://github.com/doctrine/dbal", - "reference": "2.3.2" + "url": "https://github.com/doctrine/dbal.git", + "reference": "2.3.3" }, "dist": { "type": "zip", - "url": "https://github.com/doctrine/dbal/archive/2.3.2.zip", - "reference": "2.3.2", + "url": "https://api.github.com/repos/doctrine/dbal/zipball/2.3.3", + "reference": "2.3.3", "shasum": "" }, "require": { - "doctrine/common": "2.3.*", + "doctrine/common": ">=2.3.0,<2.5-dev", "php": ">=5.3.2" }, - "time": "2013-01-07 20:03:43", + "time": "2013-03-24 19:16:29", "type": "library", "extra": { "branch-alias": { @@ -2034,7 +2034,7 @@ ], "authors": [ { - "name": "Jonathan H. Wage", + "name": "Jonathan Wage", "email": "jonwage@gmail.com", "homepage": "http://www.jwage.com/" }, @@ -2063,17 +2063,17 @@ }, { "name": "doctrine/orm", - "version": "2.3.2", - "version_normalized": "2.3.2.0", + "version": "2.3.3", + "version_normalized": "2.3.3.0", "source": { "type": "git", - "url": "git://github.com/doctrine/doctrine2.git", - "reference": "2.3.2" + "url": "https://github.com/doctrine/doctrine2.git", + "reference": "2.3.3" }, "dist": { "type": "zip", - "url": "https://github.com/doctrine/doctrine2/archive/2.3.2.zip", - "reference": "2.3.2", + "url": "https://api.github.com/repos/doctrine/doctrine2/zipball/2.3.3", + "reference": "2.3.3", "shasum": "" }, "require": { @@ -2085,7 +2085,7 @@ "suggest": { "symfony/yaml": "If you want to use YAML Metadata Mapping Driver" }, - "time": "2013-01-07 20:05:04", + "time": "2013-03-24 20:43:58", "bin": [ "bin/doctrine", "bin/doctrine.php" @@ -2132,5 +2132,35 @@ "database", "orm" ] + }, + { + "name": "chamilo/chash", + "version": "dev-master", + "version_normalized": "9999999-dev", + "source": { + "type": "git", + "url": "https://github.com/chamilo/chash.git", + "reference": "87def53dfe80a1e15ed9bceb76f7a8f01b31990e" + }, + "dist": { + "type": "zip", + "url": "https://api.github.com/repos/chamilo/chash/zipball/87def53dfe80a1e15ed9bceb76f7a8f01b31990e", + "reference": "87def53dfe80a1e15ed9bceb76f7a8f01b31990e", + "shasum": "" + }, + "require": { + "php": ">=5.3.2", + "symfony/console": "2.3.*@dev", + "symfony/yaml": "2.1.*" + }, + "time": "2013-03-25 18:35:52", + "type": "library", + "installation-source": "source", + "autoload": { + "psr-0": { + "Chash": "src/" + } + }, + "notification-url": "https://packagist.org/downloads/" } ] diff --git a/vendor/doctrine/dbal/.travis.yml b/vendor/doctrine/dbal/.travis.yml index da89c600c2..1a438ca27f 100644 --- a/vendor/doctrine/dbal/.travis.yml +++ b/vendor/doctrine/dbal/.travis.yml @@ -10,13 +10,13 @@ env: - DB=mysqli before_script: + - composer update --dev --prefer-source - sh -c "if [ '$DB' = 'pgsql' ]; then psql -c 'DROP DATABASE IF EXISTS doctrine_tests;' -U postgres; fi" - sh -c "if [ '$DB' = 'pgsql' ]; then psql -c 'DROP DATABASE IF EXISTS doctrine_tests_tmp;' -U postgres; fi" - sh -c "if [ '$DB' = 'pgsql' ]; then psql -c 'create database doctrine_tests;' -U postgres; fi" - sh -c "if [ '$DB' = 'pgsql' ]; then psql -c 'create database doctrine_tests_tmp;' -U postgres; fi" - sh -c "if [ '$DB' = 'mysql' ]; then mysql -e 'create database IF NOT EXISTS doctrine_tests_tmp;create database IF NOT EXISTS doctrine_tests;'; fi" - sh -c "if [ '$DB' = 'mysqli' ]; then mysql -e 'create database IF NOT EXISTS doctrine_tests_tmp;create database IF NOT EXISTS doctrine_tests;'; fi" - - git submodule update --init script: phpunit --configuration tests/travis/$DB.travis.xml diff --git a/vendor/doctrine/dbal/composer.json b/vendor/doctrine/dbal/composer.json index b24c254ddc..00ae9da52e 100644 --- a/vendor/doctrine/dbal/composer.json +++ b/vendor/doctrine/dbal/composer.json @@ -1,6 +1,6 @@ { "name": "doctrine/dbal", - "type": "library","version":"2.3.2", + "type": "library","version":"2.3.3", "description": "Database Abstraction Layer", "keywords": ["dbal", "database", "persistence", "queryobject"], "homepage": "http://www.doctrine-project.org", @@ -13,7 +13,7 @@ ], "require": { "php": ">=5.3.2", - "doctrine/common": "2.3.*" + "doctrine/common": ">=2.3.0,<2.5-dev" }, "autoload": { "psr-0": { "Doctrine\\DBAL": "lib/" } diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/MySQLKeywords.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/MySQLKeywords.php index 71704f6be4..c4ad5d684f 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/MySQLKeywords.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/MySQLKeywords.php @@ -190,6 +190,7 @@ class MySQLKeywords extends KeywordList 'PROCEDURE', 'PURGE', 'RAID0', + 'RANGE', 'READ', 'READS', 'REAL', diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/OracleKeywords.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/OracleKeywords.php index 525286e833..9f34ba64a7 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/OracleKeywords.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/Keywords/OracleKeywords.php @@ -151,6 +151,7 @@ class OracleKeywords extends KeywordList 'MODE', 'ROWS', 'WITH', + 'RANGE', ); } } diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/SQLServerPlatform.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/SQLServerPlatform.php index acac55bac5..c0b31c76bf 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/SQLServerPlatform.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Platforms/SQLServerPlatform.php @@ -687,12 +687,12 @@ class SQLServerPlatform extends AbstractPlatform // Remove ORDER BY clause from $query $query = preg_replace('/\s+ORDER BY(.*)/', '', $query); - $query = preg_replace('/^SELECT\s/', '', $query); + $query = preg_replace('/\sFROM/i', ", ROW_NUMBER() OVER ($over) AS doctrine_rownum FROM", $query); $start = $offset + 1; $end = $offset + $limit; - $query = "SELECT * FROM (SELECT ROW_NUMBER() OVER ($over) AS doctrine_rownum, $query) AS doctrine_tbl WHERE doctrine_rownum BETWEEN $start AND $end"; + $query = "SELECT * FROM ($query) AS doctrine_tbl WHERE doctrine_rownum BETWEEN $start AND $end"; } } diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/SQLParserUtils.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/SQLParserUtils.php index 8e3827fbea..502c0fc341 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/SQLParserUtils.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/SQLParserUtils.php @@ -32,6 +32,13 @@ use Doctrine\DBAL\Connection; */ class SQLParserUtils { + const POSITIONAL_TOKEN = '\?'; + const NAMED_TOKEN = ':[a-zA-Z_][a-zA-Z0-9_]*'; + + // Quote characters within string literals can be preceded by a backslash. + const ESCAPED_SINGLE_QUOTED_TEXT = "'(?:[^'\\\\]|\\\\'|\\\\\\\\)*'"; + const ESCAPED_DOUBLE_QUOTED_TEXT = '"(?:[^"\\\\]|\\\\"|\\\\\\\\)*"'; + /** * Get an array of the placeholders in an sql statements as keys and their positions in the query string. * @@ -49,27 +56,18 @@ class SQLParserUtils return array(); } - $count = 0; - $inLiteral = false; // a valid query never starts with quotes - $stmtLen = strlen($statement); + $token = ($isPositional) ? self::POSITIONAL_TOKEN : self::NAMED_TOKEN; $paramMap = array(); - for ($i = 0; $i < $stmtLen; $i++) { - if ($statement[$i] == $match && !$inLiteral && ($isPositional || $statement[$i+1] != '=')) { - // real positional parameter detected + + foreach (self::getUnquotedStatementFragments($statement) as $fragment) { + preg_match_all("/$token/", $fragment[0], $matches, PREG_OFFSET_CAPTURE); + foreach ($matches[0] as $placeholder) { if ($isPositional) { - $paramMap[$count] = $i; + $paramMap[] = $placeholder[1] + $fragment[1]; } else { - $name = ""; - // TODO: Something faster/better to match this than regex? - for ($j = $i + 1; ($j < $stmtLen && preg_match('(([a-zA-Z0-9_]{1}))', $statement[$j])); $j++) { - $name .= $statement[$j]; - } - $paramMap[$i] = $name; // named parameters can be duplicated! - $i = $j; + $pos = $placeholder[1] + $fragment[1]; + $paramMap[$pos] = substr($placeholder[0], 1, strlen($placeholder[0])); } - ++$count; - } else if ($statement[$i] == "'" || $statement[$i] == '"') { - $inLiteral = ! $inLiteral; // switch state! } } @@ -180,4 +178,23 @@ class SQLParserUtils return array($query, $paramsOrd, $typesOrd); } -} + + /** + * Slice the SQL statement around pairs of quotes and + * return string fragments of SQL outside of quoted literals. + * Each fragment is captured as a 2-element array: + * + * 0 => matched fragment string, + * 1 => offset of fragment in $statement + * + * @param string $statement + * @return array + */ + static private function getUnquotedStatementFragments($statement) + { + $literal = self::ESCAPED_SINGLE_QUOTED_TEXT . '|' . self::ESCAPED_DOUBLE_QUOTED_TEXT; + preg_match_all("/([^'\"]+)(?:$literal)?/s", $statement, $fragments, PREG_OFFSET_CAPTURE); + + return $fragments[1]; + } +} \ No newline at end of file diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/AbstractSchemaManager.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/AbstractSchemaManager.php index 425426e0fa..068d6b5dc6 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/AbstractSchemaManager.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/AbstractSchemaManager.php @@ -59,10 +59,10 @@ abstract class AbstractSchemaManager * * @param \Doctrine\DBAL\Connection $conn */ - public function __construct(\Doctrine\DBAL\Connection $conn) + public function __construct(\Doctrine\DBAL\Connection $conn, AbstractPlatform $platform = null) { - $this->_conn = $conn; - $this->_platform = $this->_conn->getDatabasePlatform(); + $this->_conn = $conn; + $this->_platform = $platform ?: $this->_conn->getDatabasePlatform(); } /** diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/SQLServerSchemaManager.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/SQLServerSchemaManager.php index 174dc11f9b..660e9f0b31 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/SQLServerSchemaManager.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Schema/SQLServerSchemaManager.php @@ -40,6 +40,7 @@ class SQLServerSchemaManager extends AbstractSchemaManager protected function _getPortableTableColumnDefinition($tableColumn) { $dbType = strtolower($tableColumn['TYPE_NAME']); + $dbType = strtok($dbType, '(), '); $autoincrement = false; if (stripos($dbType, 'identity')) { diff --git a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Version.php b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Version.php index 207c20ffc6..e611a83665 100644 --- a/vendor/doctrine/dbal/lib/Doctrine/DBAL/Version.php +++ b/vendor/doctrine/dbal/lib/Doctrine/DBAL/Version.php @@ -36,7 +36,7 @@ class Version /** * Current Doctrine Version */ - const VERSION = '2.3.2'; + const VERSION = '2.3.3'; /** * Compares a Doctrine version with the current one. diff --git a/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/Platforms/SQLServerPlatformTest.php b/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/Platforms/SQLServerPlatformTest.php index 397e4cfc0c..21c42ad550 100644 --- a/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/Platforms/SQLServerPlatformTest.php +++ b/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/Platforms/SQLServerPlatformTest.php @@ -154,7 +154,7 @@ class SQLServerPlatformTest extends AbstractPlatformTestCase public function testModifyLimitQueryWithOffset() { $sql = $this->_platform->modifyLimitQuery('SELECT * FROM user ORDER BY username DESC', 10, 5); - $this->assertEquals('SELECT * FROM (SELECT ROW_NUMBER() OVER (ORDER BY username DESC) AS doctrine_rownum, * FROM user) AS doctrine_tbl WHERE doctrine_rownum BETWEEN 6 AND 15', $sql); + $this->assertEquals('SELECT * FROM (SELECT *, ROW_NUMBER() OVER (ORDER BY username DESC) AS doctrine_rownum FROM user) AS doctrine_tbl WHERE doctrine_rownum BETWEEN 6 AND 15', $sql); } public function testModifyLimitQueryWithAscOrderBy() diff --git a/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/SQLParserUtilsTest.php b/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/SQLParserUtilsTest.php index ce2e7ba709..ea341b1451 100644 --- a/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/SQLParserUtilsTest.php +++ b/vendor/doctrine/dbal/tests/Doctrine/Tests/DBAL/SQLParserUtilsTest.php @@ -28,6 +28,13 @@ class SQLParserUtilsTest extends \Doctrine\Tests\DbalTestCase array("SELECT '?' FROM foo", true, array()), array('SELECT "?" FROM foo WHERE bar = ?', true, array(32)), array("SELECT '?' FROM foo WHERE bar = ?", true, array(32)), + array( +<<<'SQLDATA' +SELECT * FROM foo WHERE bar = 'it\'s a trap? \\' OR bar = ? +AND baz = "\"quote\" me on it? \\" OR baz = ? +SQLDATA + , true, array(58, 104) + ), // named array('SELECT :foo FROM :bar', false, array(7 => 'foo', 17 => 'bar')), @@ -37,6 +44,7 @@ class SQLParserUtilsTest extends \Doctrine\Tests\DbalTestCase array('SELECT :foo_id', false, array(7 => 'foo_id')), // Ticket DBAL-231 array('SELECT @rank := 1', false, array()), // Ticket DBAL-398 array('SELECT @rank := 1 AS rank, :foo AS foo FROM :bar', false, array(27 => 'foo', 44 => 'bar')), // Ticket DBAL-398 + array('SELECT * FROM Foo WHERE bar > :start_date AND baz > :start_date', false, array(30 => 'start_date', 52 => 'start_date')) // Ticket GH-113 ); } diff --git a/vendor/doctrine/dbal/tests/Doctrine/Tests/TestInit.php b/vendor/doctrine/dbal/tests/Doctrine/Tests/TestInit.php index 65803431ef..cb4cc2786a 100644 --- a/vendor/doctrine/dbal/tests/Doctrine/Tests/TestInit.php +++ b/vendor/doctrine/dbal/tests/Doctrine/Tests/TestInit.php @@ -6,17 +6,12 @@ namespace Doctrine\Tests; error_reporting(E_ALL | E_STRICT); -require_once __DIR__ . '/../../../lib/vendor/doctrine-common/lib/Doctrine/Common/ClassLoader.php'; - -$classLoader = new \Doctrine\Common\ClassLoader('Doctrine\Common', __DIR__ . '/../../../lib/vendor/doctrine-common/lib'); -$classLoader->register(); - -$classLoader = new \Doctrine\Common\ClassLoader('Doctrine\DBAL', __DIR__ . '/../../../lib'); -$classLoader->register(); - -$classLoader = new \Doctrine\Common\ClassLoader('Doctrine\Tests', __DIR__ . '/../../'); -$classLoader->register(); - -$classLoader = new \Doctrine\Common\ClassLoader('Symfony', __DIR__ . "/../../../lib/vendor"); -$classLoader->register(); +if (file_exists(__DIR__ . '/../../../vendor/autoload.php')) { + $loader = require_once __DIR__ . '/../../../vendor/autoload.php'; +} elseif (file_exists(__DIR__ . '/../../../../../autoload.php')) { + $loader = require __DIR__ . '/../../../vendor/autoload.php'; +} else { + throw new \RuntimeException('Could not locate composer autoloader'); +} +$loader->add('Doctrine\Tests', __DIR__ . '/../../'); diff --git a/vendor/doctrine/orm/composer.json b/vendor/doctrine/orm/composer.json index 64d415af04..a8cf0314dc 100644 --- a/vendor/doctrine/orm/composer.json +++ b/vendor/doctrine/orm/composer.json @@ -1,6 +1,6 @@ { "name": "doctrine/orm", - "type": "library","version":"2.3.2", + "type": "library","version":"2.3.3", "description": "Object-Relational-Mapper for PHP", "keywords": ["orm", "database"], "homepage": "http://www.doctrine-project.org", diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Id/IdentityGenerator.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Id/IdentityGenerator.php index ff2cd01b1b..ad6131280c 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Id/IdentityGenerator.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Id/IdentityGenerator.php @@ -28,17 +28,21 @@ use Doctrine\ORM\EntityManager; */ class IdentityGenerator extends AbstractIdGenerator { - /** @var string The name of the sequence to pass to lastInsertId(), if any. */ - private $_seqName; + /** + * The name of the sequence to pass to lastInsertId(), if any. + * + * @var string + */ + private $sequenceName; /** * @param string $seqName The name of the sequence to pass to lastInsertId() * to obtain the last generated identifier within the current * database session/connection, if any. */ - public function __construct($seqName = null) + public function __construct($sequenceName = null) { - $this->_seqName = $seqName; + $this->sequenceName = $sequenceName; } /** @@ -46,7 +50,7 @@ class IdentityGenerator extends AbstractIdGenerator */ public function generate(EntityManager $em, $entity) { - return (int)$em->getConnection()->lastInsertId($this->_seqName); + return (int)$em->getConnection()->lastInsertId($this->sequenceName); } /** diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Internal/Hydration/SimpleObjectHydrator.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Internal/Hydration/SimpleObjectHydrator.php index 8f8ed4b9a9..613f94cf0e 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Internal/Hydration/SimpleObjectHydrator.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Internal/Hydration/SimpleObjectHydrator.php @@ -178,10 +178,13 @@ class SimpleObjectHydrator extends AbstractHydrator // One solution is to load the association, but it might require extra efforts. return array('name' => $column); - default: + case (isset($this->_rsm->metaMappings[$column])): return array( 'name' => $this->_rsm->metaMappings[$column] ); + + default: + return null; } } } diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataFactory.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataFactory.php index f79eda8b9d..bf449a4506 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataFactory.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataFactory.php @@ -19,16 +19,17 @@ namespace Doctrine\ORM\Mapping; -use ReflectionException, - Doctrine\ORM\ORMException, - Doctrine\ORM\EntityManager, - Doctrine\DBAL\Platforms, - Doctrine\ORM\Events, - Doctrine\Common\Persistence\Mapping\ReflectionService, - Doctrine\Common\Persistence\Mapping\ClassMetadata as ClassMetadataInterface, - Doctrine\Common\Persistence\Mapping\AbstractClassMetadataFactory, - Doctrine\ORM\Id\IdentityGenerator, - Doctrine\ORM\Event\LoadClassMetadataEventArgs; +use ReflectionException; +use Doctrine\ORM\ORMException; +use Doctrine\ORM\EntityManager; +use Doctrine\DBAL\Platforms; +use Doctrine\ORM\Events; +use Doctrine\Common\Persistence\Mapping\ReflectionService; +use Doctrine\Common\Persistence\Mapping\ClassMetadata as ClassMetadataInterface; +use Doctrine\Common\Persistence\Mapping\AbstractClassMetadataFactory; +use Doctrine\ORM\Id\IdentityGenerator; +use Doctrine\ORM\Id\BigIntegerIdentityGenerator; +use Doctrine\ORM\Event\LoadClassMetadataEventArgs; /** * The ClassMetadataFactory is used to create ClassMetadata objects that contain all the @@ -418,9 +419,9 @@ class ClassMetadataFactory extends AbstractClassMetadataFactory // __seq in PostgreSQL for SERIAL columns. // Not pretty but necessary and the simplest solution that currently works. $sequenceName = null; + $fieldName = $class->identifier ? $class->getSingleIdentifierFieldName() : null; if ($this->targetPlatform instanceof Platforms\PostgreSQLPlatform) { - $fieldName = $class->getSingleIdentifierFieldName(); $columnName = $class->getSingleIdentifierColumnName(); $quoted = isset($class->fieldMappings[$fieldName]['quoted']) || isset($class->table['quoted']); $sequenceName = $class->getTableName() . '_' . $columnName . '_seq'; @@ -435,7 +436,12 @@ class ClassMetadataFactory extends AbstractClassMetadataFactory $sequenceName = $this->em->getConfiguration()->getQuoteStrategy()->getSequenceName($definition, $class, $this->targetPlatform); } - $class->setIdGenerator(new \Doctrine\ORM\Id\IdentityGenerator($sequenceName)); + $generator = ($fieldName && $class->fieldMappings[$fieldName]['type'] === "bigint") + ? new BigIntegerIdentityGenerator($sequenceName) + : new IdentityGenerator($sequenceName); + + $class->setIdGenerator($generator); + break; case ClassMetadata::GENERATOR_TYPE_SEQUENCE: diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataInfo.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataInfo.php index e0c6f2f17f..cba525a0c6 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataInfo.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/ClassMetadataInfo.php @@ -1421,6 +1421,10 @@ class ClassMetadataInfo implements ClassMetadata $mapping['orphanRemoval'] = isset($mapping['orphanRemoval']) ? (bool) $mapping['orphanRemoval'] : false; $mapping['isCascadeRemove'] = $mapping['orphanRemoval'] ? true : $mapping['isCascadeRemove']; + if ($mapping['orphanRemoval']) { + unset($mapping['unique']); + } + if (isset($mapping['id']) && $mapping['id'] === true && !$mapping['isOwningSide']) { throw MappingException::illegalInverseIdentifierAssocation($this->name, $mapping['fieldName']); } diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/XmlDriver.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/XmlDriver.php index bc0e79e709..0be7c36bca 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/XmlDriver.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/XmlDriver.php @@ -233,6 +233,7 @@ class XmlDriver extends FileDriver if (isset($mapping['version'])) { $metadata->setVersionMapping($mapping); + unset($mapping['version']); } $metadata->mapField($mapping); @@ -662,7 +663,7 @@ class XmlDriver extends FileDriver } if (isset($fieldMapping['version']) && $fieldMapping['version']) { - $mapping['version'] = $fieldMapping['version']; + $mapping['version'] = $this->evaluateBoolean($fieldMapping['version']); } if (isset($fieldMapping['column-definition'])) { diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/YamlDriver.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/YamlDriver.php index 35631e7a1e..f339045afe 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/YamlDriver.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Mapping/Driver/YamlDriver.php @@ -299,6 +299,7 @@ class YamlDriver extends FileDriver if (isset($mapping['version'])) { $metadata->setVersionMapping($mapping); + unset($mapping['version']); } $metadata->mapField($mapping); diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/PersistentCollection.php b/vendor/doctrine/orm/lib/Doctrine/ORM/PersistentCollection.php index 8c306f4ab4..ed5d7dfb7b 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/PersistentCollection.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/PersistentCollection.php @@ -805,6 +805,10 @@ final class PersistentCollection implements Collection, Selectable */ public function matching(Criteria $criteria) { + if ($this->isDirty) { + $this->initialize(); + } + if ($this->initialized) { return $this->coll->matching($criteria); } @@ -813,16 +817,10 @@ final class PersistentCollection implements Collection, Selectable throw new \RuntimeException("Matching Criteria on PersistentCollection only works on OneToMany assocations at the moment."); } - // If there are NEW objects we have to check if any of them matches the criteria - $newObjects = array(); - - if ($this->isDirty) { - $newObjects = $this->coll->matching($criteria)->toArray(); - } - - $targetClass = $this->em->getClassMetadata(get_class($this->owner)); - - $id = $targetClass->getSingleIdReflectionProperty()->getValue($this->owner); + $id = $this->em + ->getClassMetadata(get_class($this->owner)) + ->getSingleIdReflectionProperty() + ->getValue($this->owner); $builder = Criteria::expr(); $ownerExpression = $builder->eq($this->backRefFieldName, $id); $expression = $criteria->getWhereExpression(); @@ -832,7 +830,7 @@ final class PersistentCollection implements Collection, Selectable $persister = $this->em->getUnitOfWork()->getEntityPersister($this->association['targetEntity']); - return new ArrayCollection(array_merge($persister->loadCriteria($criteria), $newObjects)); + return new ArrayCollection($persister->loadCriteria($criteria)); } } diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Exec/MultiTableUpdateExecutor.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Exec/MultiTableUpdateExecutor.php index 7dc3fed821..60951eef21 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Exec/MultiTableUpdateExecutor.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Exec/MultiTableUpdateExecutor.php @@ -104,19 +104,8 @@ class MultiTableUpdateExecutor extends AbstractSqlExecutor $updateSql .= $sqlWalker->walkUpdateItem($updateItem); - //FIXME: parameters can be more deeply nested. traverse the tree. - //FIXME (URGENT): With query cache the parameter is out of date. Move to execute() stage. if ($newValue instanceof AST\InputParameter) { - $parameterName = $newValue->name; - $parameter = $sqlWalker->getQuery()->getParameter($parameterName); - - $value = $sqlWalker->getQuery()->processParameterValue($parameter->getValue()); - $type = ($parameter->getValue() === $value) - ? $parameter->getType() - : ParameterTypeInferer::inferType($value); - - $this->_sqlParameters[$i]['parameters'][] = $value; - $this->_sqlParameters[$i]['types'][] = $type; + $this->_sqlParameters[$i][] = $newValue->name; ++$this->_numParametersInUpdateClause; } @@ -168,16 +157,18 @@ class MultiTableUpdateExecutor extends AbstractSqlExecutor ); // Execute UPDATE statements - for ($i=0, $count=count($this->_sqlStatements); $i<$count; ++$i) { - $parameters = array(); - $types = array(); - - if (isset($this->_sqlParameters[$i])) { - $parameters = isset($this->_sqlParameters[$i]['parameters']) ? $this->_sqlParameters[$i]['parameters'] : array(); - $types = isset($this->_sqlParameters[$i]['types']) ? $this->_sqlParameters[$i]['types'] : array(); + foreach ($this->_sqlStatements as $key => $statement) { + $paramValues = array(); + $paramTypes = array(); + + if (isset($this->_sqlParameters[$key])) { + foreach ($this->_sqlParameters[$key] as $parameterKey => $parameterName) { + $paramValues[] = $params[$parameterKey]; + $paramTypes[] = isset($types[$parameterKey]) ? $types[$parameterKey] : ParameterTypeInferer::inferType($params[$parameterKey]); + } } - $conn->executeUpdate($this->_sqlStatements[$i], $parameters, $types); + $conn->executeUpdate($statement, $paramValues, $paramTypes); } } catch (\Exception $exception) { // FAILURE! Drop temporary table to avoid possible collisions diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Expr/Base.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Expr/Base.php index a2bc98cc7d..0fee7b2d50 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Expr/Base.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Query/Expr/Base.php @@ -83,7 +83,7 @@ abstract class Base */ public function add($arg) { - if ( $arg !== null || ($arg instanceof self && $arg->count() > 0) ) { + if ( $arg !== null && (!$arg instanceof self || $arg->count() > 0) ) { // If we decide to keep Expr\Base instances, we can use this check if ( ! is_string($arg)) { $class = get_class($arg); diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Query/SqlWalker.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Query/SqlWalker.php index fd40874dd6..6fb3abb03f 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Query/SqlWalker.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Query/SqlWalker.php @@ -750,7 +750,10 @@ class SqlWalker implements TreeWalker $sqlParts = array(); foreach ($identificationVarDecls as $identificationVariableDecl) { - $sql = $this->walkRangeVariableDeclaration($identificationVariableDecl->rangeVariableDeclaration); + $sql = $this->platform->appendLockHint( + $this->walkRangeVariableDeclaration($identificationVariableDecl->rangeVariableDeclaration), + $this->query->getHint(Query::HINT_LOCK_MODE) + ); foreach ($identificationVariableDecl->joins as $join) { $sql .= $this->walkJoin($join); @@ -770,7 +773,7 @@ class SqlWalker implements TreeWalker } } - $sqlParts[] = $this->platform->appendLockHint($sql, $this->query->getHint(Query::HINT_LOCK_MODE)); + $sqlParts[] = $sql; } return ' FROM ' . implode(', ', $sqlParts); @@ -1367,13 +1370,16 @@ class SqlWalker implements TreeWalker $sqlParts = array (); foreach ($identificationVarDecls as $subselectIdVarDecl) { - $sql = $this->walkRangeVariableDeclaration($subselectIdVarDecl->rangeVariableDeclaration); + $sql = $this->platform->appendLockHint( + $this->walkRangeVariableDeclaration($subselectIdVarDecl->rangeVariableDeclaration), + $this->query->getHint(Query::HINT_LOCK_MODE) + ); foreach ($subselectIdVarDecl->joins as $join) { $sql .= $this->walkJoin($join); } - $sqlParts[] = $this->platform->appendLockHint($sql, $this->query->getHint(Query::HINT_LOCK_MODE)); + $sqlParts[] = $sql; } return ' FROM ' . implode(', ', $sqlParts); diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Tools/Pagination/CountOutputWalker.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Tools/Pagination/CountOutputWalker.php index 098934e302..43e8f22396 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Tools/Pagination/CountOutputWalker.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Tools/Pagination/CountOutputWalker.php @@ -74,6 +74,10 @@ class CountOutputWalker extends SqlWalker */ public function walkSelectStatement(SelectStatement $AST) { + if ($this->platform->getName() === "mssql") { + $AST->orderByClause = null; + } + $sql = parent::walkSelectStatement($AST); // Find out the SQL alias of the identifier column of the root entity diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php b/vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php index 05b8e3b0ab..1d56af300a 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/UnitOfWork.php @@ -1376,6 +1376,10 @@ class UnitOfWork implements PropertyChangedListener return self::STATE_NEW; } + if ($class->containsForeignIdentifier) { + $id = $this->flattenIdentifier($class, $id); + } + switch (true) { case ($class->isIdentifierNatural()); // Check for a version field, if available, to avoid a db lookup. @@ -1688,6 +1692,29 @@ class UnitOfWork implements PropertyChangedListener return $this->doMerge($entity, $visited); } + /** + * convert foreign identifiers into scalar foreign key values to avoid object to string conversion failures. + * + * @param ClassMetadata $class + * @param array $id + * @return array + */ + private function flattenIdentifier($class, $id) + { + $flatId = array(); + + foreach ($id as $idField => $idValue) { + if (isset($class->associationMappings[$idField])) { + $targetClassMetadata = $this->em->getClassMetadata($class->associationMappings[$idField]['targetEntity']); + $associatedId = $this->getEntityIdentifier($idValue); + + $flatId[$idField] = $associatedId[$targetClassMetadata->identifier[0]]; + } + } + + return $flatId; + } + /** * Executes a merge operation on an entity. * @@ -1735,19 +1762,9 @@ class UnitOfWork implements PropertyChangedListener $this->persistNew($class, $managedCopy); } else { - $flatId = $id; - if ($class->containsForeignIdentifier) { - // convert foreign identifiers into scalar foreign key - // values to avoid object to string conversion failures. - foreach ($id as $idField => $idValue) { - if (isset($class->associationMappings[$idField])) { - $targetClassMetadata = $this->em->getClassMetadata($class->associationMappings[$idField]['targetEntity']); - $associatedId = $this->getEntityIdentifier($idValue); - - $flatId[$idField] = $associatedId[$targetClassMetadata->identifier[0]]; - } - } - } + $flatId = ($class->containsForeignIdentifier) + ? $this->flattenIdentifier($class, $id) + : $id; $managedCopy = $this->tryGetById($flatId, $class->rootEntityName); @@ -2415,17 +2432,23 @@ class UnitOfWork implements PropertyChangedListener if ($entity instanceof NotifyPropertyChanged) { $entity->addPropertyChangedListener($this); } + + // inject ObjectManager into just loaded proxies. + if ($overrideLocalValues && $entity instanceof ObjectManagerAware) { + $entity->injectObjectManager($this->em, $class); + } + } else { $overrideLocalValues = isset($hints[Query::HINT_REFRESH]); // If only a specific entity is set to refresh, check that it's the one if(isset($hints[Query::HINT_REFRESH_ENTITY])) { $overrideLocalValues = $hints[Query::HINT_REFRESH_ENTITY] === $entity; + } - // inject ObjectManager into just loaded proxies. - if ($overrideLocalValues && $entity instanceof ObjectManagerAware) { - $entity->injectObjectManager($this->em, $class); - } + // inject ObjectManager upon refresh. + if ($overrideLocalValues && $entity instanceof ObjectManagerAware) { + $entity->injectObjectManager($this->em, $class); } } diff --git a/vendor/doctrine/orm/lib/Doctrine/ORM/Version.php b/vendor/doctrine/orm/lib/Doctrine/ORM/Version.php index 3484195e1d..9f32726dfa 100644 --- a/vendor/doctrine/orm/lib/Doctrine/ORM/Version.php +++ b/vendor/doctrine/orm/lib/Doctrine/ORM/Version.php @@ -36,7 +36,7 @@ class Version /** * Current Doctrine Version */ - const VERSION = '2.3.2'; + const VERSION = '2.3.3'; /** * Compares a Doctrine version with the current one. diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/OneToManyBidirectionalAssociationTest.php b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/OneToManyBidirectionalAssociationTest.php index 75d9d2abe6..f513395d7b 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/OneToManyBidirectionalAssociationTest.php +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/OneToManyBidirectionalAssociationTest.php @@ -173,14 +173,36 @@ class OneToManyBidirectionalAssociationTest extends \Doctrine\Tests\OrmFunctiona $this->assertInstanceOf('Doctrine\Common\Collections\Collection', $results); $this->assertEquals(2, count($results)); } - + + /** + * @group DDC-2340 + */ + public function testMatchingOnDirtyCollection() + { + $this->_createFixture(); + + $product = $this->_em->find('Doctrine\Tests\Models\ECommerce\ECommerceProduct', $this->product->getId()); + + $thirdFeature = new ECommerceFeature(); + $thirdFeature->setDescription('Model writing tutorial'); + + $features = $product->getFeatures(); + $features->add($thirdFeature); + + $results = $features->matching(new Criteria( + Criteria::expr()->eq('description', 'Model writing tutorial') + )); + + $this->assertEquals(2, count($results)); + } + public function testMatchingBis() { $this->_createFixture(); $product = $this->_em->find('Doctrine\Tests\Models\ECommerce\ECommerceProduct', $this->product->getId()); $features = $product->getFeatures(); - + $thirdFeature = new ECommerceFeature(); $thirdFeature->setDescription('Third feature'); $product->addFeature($thirdFeature); diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/Ticket/DDC117Test.php b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/Ticket/DDC117Test.php index 6ae4595dce..bf2ef0b274 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/Ticket/DDC117Test.php +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Functional/Ticket/DDC117Test.php @@ -461,4 +461,22 @@ class DDC117Test extends \Doctrine\Tests\OrmFunctionalTestCase $this->assertEquals($before + 3, count($data)); } + + /** + * @group DDC-2246 + */ + public function testGetEntityState() + { + $this->article1 = $this->_em->find("Doctrine\Tests\Models\DDC117\DDC117Article", $this->article1->id()); + $this->article2 = $this->_em->find("Doctrine\Tests\Models\DDC117\DDC117Article", $this->article2->id()); + + $this->reference = new DDC117Reference($this->article2, $this->article1, "Test-Description"); + + $this->assertEquals(\Doctrine\ORM\UnitOfWork::STATE_NEW, $this->_em->getUnitOfWork()->getEntityState($this->reference)); + + $idCriteria = array('source' => $this->article1->id(), 'target' => $this->article2->id()); + $reference = $this->_em->find("Doctrine\Tests\Models\DDC117\DDC117Reference", $idCriteria); + + $this->assertEquals(\Doctrine\ORM\UnitOfWork::STATE_MANAGED, $this->_em->getUnitOfWork()->getEntityState($reference)); + } } diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Hydration/SimpleObjectHydratorTest.php b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Hydration/SimpleObjectHydratorTest.php index 80f90e7ff4..400b5829f7 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Hydration/SimpleObjectHydratorTest.php +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Hydration/SimpleObjectHydratorTest.php @@ -34,4 +34,28 @@ class SimpleObjectHydratorTest extends HydrationTestCase $hydrator = new \Doctrine\ORM\Internal\Hydration\SimpleObjectHydrator($this->_em); $hydrator->hydrateAll($stmt, $rsm); } + + public function testExtraFieldInResultSetShouldBeIgnore() + { + $rsm = new ResultSetMapping; + $rsm->addEntityResult('Doctrine\Tests\Models\CMS\CmsAddress', 'a'); + $rsm->addFieldResult('a', 'a__id', 'id'); + $rsm->addFieldResult('a', 'a__city', 'city'); + $resultSet = array( + array( + 'a__id' => '1', + 'a__city' => 'Cracow', + 'doctrine_rownum' => '1' + ), + ); + + $expectedEntity = new \Doctrine\Tests\Models\CMS\CmsAddress(); + $expectedEntity->id = 1; + $expectedEntity->city = 'Cracow'; + + $stmt = new HydratorMockStatement($resultSet); + $hydrator = new \Doctrine\ORM\Internal\Hydration\SimpleObjectHydrator($this->_em); + $result = $hydrator->hydrateAll($stmt, $rsm); + $this->assertEquals($result[0], $expectedEntity); + } } diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/AbstractMappingDriverTest.php b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/AbstractMappingDriverTest.php index b994d4863d..7300a3ad40 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/AbstractMappingDriverTest.php +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/AbstractMappingDriverTest.php @@ -156,6 +156,8 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase { $this->assertTrue($class->isVersioned); $this->assertEquals("version", $class->versionField); + + $this->assertFalse(isset($class->fieldMappings['version']['version'])); } /** @@ -475,24 +477,22 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase /** * @group DDC-889 - * @expectedException Doctrine\ORM\Mapping\MappingException - * @expectedExceptionMessage Class "Doctrine\Tests\Models\DDC889\DDC889Class" sub class of "Doctrine\Tests\Models\DDC889\DDC889SuperClass" is not a valid entity or mapped super class. */ public function testInvalidEntityOrMappedSuperClassShouldMentionParentClasses() { + $this->setExpectedException('Doctrine\ORM\Mapping\MappingException', 'Class "Doctrine\Tests\Models\DDC889\DDC889Class" sub class of "Doctrine\Tests\Models\DDC889\DDC889SuperClass" is not a valid entity or mapped super class.'); + $this->createClassMetadata('Doctrine\Tests\Models\DDC889\DDC889Class'); } /** * @group DDC-889 - * @expectedException Doctrine\ORM\Mapping\MappingException - * @expectedExceptionMessage No identifier/primary key specified for Entity "Doctrine\Tests\Models\DDC889\DDC889Entity" sub class of "Doctrine\Tests\Models\DDC889\DDC889SuperClass". Every Entity must have an identifier/primary key. */ public function testIdentifierRequiredShouldMentionParentClasses() { - $factory = $this->createClassMetadataFactory(); - + + $this->setExpectedException('Doctrine\ORM\Mapping\MappingException', 'No identifier/primary key specified for Entity "Doctrine\Tests\Models\DDC889\DDC889Entity" sub class of "Doctrine\Tests\Models\DDC889\DDC889SuperClass". Every Entity must have an identifier/primary key.'); $factory->getMetadataFor('Doctrine\Tests\Models\DDC889\DDC889Entity'); } @@ -509,7 +509,7 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase */ public function testNamedNativeQuery() { - + $class = $this->createClassMetadata('Doctrine\Tests\Models\CMS\CmsAddress'); //named native query @@ -538,7 +538,7 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase $this->assertArrayHasKey('mapping-count', $class->sqlResultSetMappings); $this->assertArrayHasKey('mapping-find-all', $class->sqlResultSetMappings); $this->assertArrayHasKey('mapping-without-fields', $class->sqlResultSetMappings); - + $findAllMapping = $class->getSqlResultSetMapping('mapping-find-all'); $this->assertEquals('mapping-find-all', $findAllMapping['name']); $this->assertEquals('Doctrine\Tests\Models\CMS\CmsAddress', $findAllMapping['entities'][0]['entityClass']); @@ -550,7 +550,7 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase $this->assertEquals('mapping-without-fields', $withoutFieldsMapping['name']); $this->assertEquals('Doctrine\Tests\Models\CMS\CmsAddress', $withoutFieldsMapping['entities'][0]['entityClass']); $this->assertEquals(array(), $withoutFieldsMapping['entities'][0]['fields']); - + $countMapping = $class->getSqlResultSetMapping('mapping-count'); $this->assertEquals('mapping-count', $countMapping['name']); $this->assertEquals(array('name'=>'count'), $countMapping['columns'][0]); @@ -638,7 +638,7 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase $adminMetadata = $factory->getMetadataFor('Doctrine\Tests\Models\DDC964\DDC964Admin'); $guestMetadata = $factory->getMetadataFor('Doctrine\Tests\Models\DDC964\DDC964Guest'); - + // assert groups association mappings $this->assertArrayHasKey('groups', $guestMetadata->associationMappings); $this->assertArrayHasKey('groups', $adminMetadata->associationMappings); @@ -697,7 +697,7 @@ abstract class AbstractMappingDriverTest extends \Doctrine\Tests\OrmTestCase $this->assertEquals($guestAddress['isCascadeRefresh'], $adminAddress['isCascadeRefresh']); $this->assertEquals($guestAddress['isCascadeMerge'], $adminAddress['isCascadeMerge']); $this->assertEquals($guestAddress['isCascadeDetach'], $adminAddress['isCascadeDetach']); - + // assert override $this->assertEquals('address_id', $guestAddress['joinColumns'][0]['name']); $this->assertEquals(array('address_id'=>'id'), $guestAddress['sourceToTargetKeyColumns']); @@ -1071,7 +1071,7 @@ class DDC807Entity * @GeneratedValue(strategy="NONE") **/ public $id; - + public static function loadMetadata(ClassMetadataInfo $metadata) { $metadata->mapField(array( diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.Models.DDC1476.DDC1476EntityWithDefaultFieldType.dcm.yml b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.Models.DDC1476.DDC1476EntityWithDefaultFieldType.dcm.yml index 3437a9b378..674328cd52 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.Models.DDC1476.DDC1476EntityWithDefaultFieldType.dcm.yml +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.Models.DDC1476.DDC1476EntityWithDefaultFieldType.dcm.yml @@ -5,4 +5,4 @@ Doctrine\Tests\Models\DDC1476\DDC1476EntityWithDefaultFieldType: generator: strategy: NONE fields: - name: \ No newline at end of file + name: ~ diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.ORM.Mapping.DDC2069Entity.dcm.yml b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.ORM.Mapping.DDC2069Entity.dcm.yml index 88ab2da207..5b16c12bc9 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.ORM.Mapping.DDC2069Entity.dcm.yml +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Mapping/yaml/Doctrine.Tests.ORM.Mapping.DDC2069Entity.dcm.yml @@ -1,7 +1,7 @@ Doctrine\Tests\ORM\Mapping\DDC2069Entity: type: entity id: - id: + id: ~ fields: name: type: string ( 255 ) @@ -12,4 +12,4 @@ Doctrine\Tests\ORM\Mapping\DDC2069Entity: columns: name, value indexes: 0: - columns: value, name \ No newline at end of file + columns: value, name diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Query/ExprTest.php b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Query/ExprTest.php index 122b98f037..f35b5d4073 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Query/ExprTest.php +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Query/ExprTest.php @@ -409,4 +409,18 @@ class ExprTest extends \Doctrine\Tests\OrmTestCase $select = new Expr\Select(array('foo', 'bar')); $this->assertEquals(array('foo', 'bar'), $select->getParts()); } + + public function testAddEmpty() { + $andExpr = $this->_expr->andx(); + $andExpr->add($this->_expr->andx()); + + $this->assertEquals(0, $andExpr->count()); + } + + public function testAddNull() { + $andExpr = $this->_expr->andx(); + $andExpr->add(null); + + $this->assertEquals(0, $andExpr->count()); + } } diff --git a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Tools/Pagination/CountOutputWalkerTest.php b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Tools/Pagination/CountOutputWalkerTest.php index 688f101b0f..f3c2e1b50a 100644 --- a/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Tools/Pagination/CountOutputWalkerTest.php +++ b/vendor/doctrine/orm/tests/Doctrine/Tests/ORM/Tools/Pagination/CountOutputWalkerTest.php @@ -41,5 +41,22 @@ class CountOutputWalkerTest extends PaginationTestCase "SELECT COUNT(*) AS dctrn_count FROM (SELECT DISTINCT id1 FROM (SELECT count(u0_.id) AS sclr0, g1_.id AS id1, u0_.id AS id2 FROM groups g1_ LEFT JOIN user_group u2_ ON g1_.id = u2_.group_id LEFT JOIN User u0_ ON u0_.id = u2_.user_id GROUP BY g1_.id HAVING sclr0 > 0) dctrn_result) dctrn_table", $query->getSql() ); } + + public function testCountQueryOrderBySqlServer() + { + if ($this->entityManager->getConnection()->getDatabasePlatform()->getName() !== "mssql") { + $this->markTestSkipped('SQLServer only test.'); + } + + $query = $this->entityManager->createQuery( + 'SELECT p FROM Doctrine\Tests\ORM\Tools\Pagination\BlogPost p ORDER BY p.id'); + $query->setHint(Query::HINT_CUSTOM_OUTPUT_WALKER, 'Doctrine\ORM\Tools\Pagination\CountOutputWalker'); + $query->setFirstResult(null)->setMaxResults(null); + + $this->assertEquals( + "SELECT COUNT(*) AS dctrn_count FROM (SELECT DISTINCT id0 FROM (SELECT b0_.id AS id0, b0_.author_id AS author_id1, b0_.category_id AS category_id2 FROM BlogPost b0_) dctrn_result) dctrn_table", + $query->getSql() + ); + } }