diff --git a/js/src/normalization.js b/js/src/normalization.js index c800ff634d..3fc98a9f93 100644 --- a/js/src/normalization.js +++ b/js/src/normalization.js @@ -18,13 +18,12 @@ var dataParsed = null; function appendHtmlColumnsList () { $.post( - 'index.php?route=/normalization', + 'index.php?route=/normalization/get-columns', { 'ajax_request': true, 'db': window.CommonParams.get('db'), 'table': window.CommonParams.get('table'), 'server': window.CommonParams.get('server'), - 'getColumns': true }, function (data) { if (data.success === true) { @@ -220,11 +219,11 @@ function goTo2NFFinish (pd) { 'table': window.CommonParams.get('table'), 'server': window.CommonParams.get('server'), 'pd': JSON.stringify(pd), - 'newTablesName':JSON.stringify(tables), - 'createNewTables2NF':1 }; + 'newTablesName': JSON.stringify(tables), + }; $.ajax({ type: 'POST', - url: 'index.php?route=/normalization', + url: 'index.php?route=/normalization/2nf/create-new-tables', data: datastring, async:false, success: function (data) { @@ -265,11 +264,11 @@ function goTo3NFFinish (newTables) { 'ajax_request': true, 'db': window.CommonParams.get('db'), 'server': window.CommonParams.get('server'), - 'newTables':JSON.stringify(newTables), - 'createNewTables3NF':1 }; + 'newTables': JSON.stringify(newTables), + }; $.ajax({ type: 'POST', - url: 'index.php?route=/normalization', + url: 'index.php?route=/normalization/3nf/create-new-tables', data: datastring, async:false, success: function (data) { @@ -366,10 +365,10 @@ function goTo3NFStep2 (pd, tablesTds) { 'tables': JSON.stringify(tablesTds), 'server': window.CommonParams.get('server'), 'pd': JSON.stringify(pd), - 'getNewTables3NF':1 }; + }; $.ajax({ type: 'POST', - url: 'index.php?route=/normalization', + url: 'index.php?route=/normalization/3nf/new-tables', data: datastring, async:false, success: function (data) { @@ -465,7 +464,7 @@ function moveRepeatingGroup (repeatingCols) { }; $.ajax({ type: 'POST', - url: 'index.php?route=/normalization', + url: 'index.php?route=/normalization/move-repeating-group', data: datastring, async:false, success: function (data) { @@ -511,13 +510,12 @@ window.AJAX.registerOnload('normalization.js', function () { } var numField = $('#numField').val(); $.post( - 'index.php?route=/normalization', + 'index.php?route=/normalization/create-new-column', { 'ajax_request': true, 'db': window.CommonParams.get('db'), 'table': window.CommonParams.get('table'), 'server': window.CommonParams.get('server'), - 'splitColumn': true, 'numFields': numField }, function (data) { @@ -594,13 +592,12 @@ window.AJAX.registerOnload('normalization.js', function () { $('#extra').on('click', '#addNewPrimary', function () { $.post( - 'index.php?route=/normalization', + 'index.php?route=/normalization/add-new-primary', { 'ajax_request': true, 'db': window.CommonParams.get('db'), 'table': window.CommonParams.get('table'), 'server': window.CommonParams.get('server'), - 'addNewPrimary': true }, function (data) { if (data.success === true) { @@ -758,13 +755,12 @@ window.AJAX.registerOnload('normalization.js', function () { $('#newCols').insertAfter('#mainContent h4'); $('#newCols').html('
' + window.Messages.strLoading + '
' + window.Messages.strWaitForPd + '
'); $.post( - 'index.php?route=/normalization', + 'index.php?route=/normalization/partial-dependencies', { 'ajax_request': true, 'db': window.CommonParams.get('db'), 'table': window.CommonParams.get('table'), 'server': window.CommonParams.get('server'), - 'findPdl': true }, function (data) { $('#showPossiblePd').html('- ' + window.Messages.strHidePd); $('#showPossiblePd').addClass('hideList'); diff --git a/libraries/classes/Controllers/Normalization/AddNewPrimaryController.php b/libraries/classes/Controllers/Normalization/AddNewPrimaryController.php new file mode 100644 index 0000000000..bbbdd9976c --- /dev/null +++ b/libraries/classes/Controllers/Normalization/AddNewPrimaryController.php @@ -0,0 +1,41 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $num_fields = 1; + $columnMeta = [ + 'Field' => $GLOBALS['table'] . '_id', + 'Extra' => 'auto_increment', + ]; + $html = $this->normalization->getHtmlForCreateNewColumn( + $num_fields, + $GLOBALS['db'], + $GLOBALS['table'], + $columnMeta + ); + $html .= Url::getHiddenInputs($GLOBALS['db'], $GLOBALS['table']); + $this->response->addHTML($html); + } +} diff --git a/libraries/classes/Controllers/Normalization/CreateNewColumnController.php b/libraries/classes/Controllers/Normalization/CreateNewColumnController.php new file mode 100644 index 0000000000..ae03dc1d00 --- /dev/null +++ b/libraries/classes/Controllers/Normalization/CreateNewColumnController.php @@ -0,0 +1,35 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $num_fields = min(4096, intval($_POST['numFields'])); + $html = $this->normalization->getHtmlForCreateNewColumn($num_fields, $GLOBALS['db'], $GLOBALS['table']); + $html .= Url::getHiddenInputs($GLOBALS['db'], $GLOBALS['table']); + $this->response->addHTML($html); + } +} diff --git a/libraries/classes/Controllers/Normalization/GetColumnsController.php b/libraries/classes/Controllers/Normalization/GetColumnsController.php new file mode 100644 index 0000000000..f9d6e333b6 --- /dev/null +++ b/libraries/classes/Controllers/Normalization/GetColumnsController.php @@ -0,0 +1,39 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $html = '' + . ''; + //get column whose datatype falls under string category + $html .= $this->normalization->getHtmlForColumnsList( + $GLOBALS['db'], + $GLOBALS['table'], + _pgettext('string types', 'String') + ); + $this->response->addHTML($html); + } +} diff --git a/libraries/classes/Controllers/Normalization/MainController.php b/libraries/classes/Controllers/Normalization/MainController.php new file mode 100644 index 0000000000..91bde1300b --- /dev/null +++ b/libraries/classes/Controllers/Normalization/MainController.php @@ -0,0 +1,23 @@ +addScriptFiles(['normalization.js', 'vendor/jquery/jquery.uitablefilter.js']); + $this->render('table/normalization/normalization', [ + 'db' => $GLOBALS['db'], + 'table' => $GLOBALS['table'], + ]); + } +} diff --git a/libraries/classes/Controllers/Normalization/MoveRepeatingGroup.php b/libraries/classes/Controllers/Normalization/MoveRepeatingGroup.php new file mode 100644 index 0000000000..f308d9a1e0 --- /dev/null +++ b/libraries/classes/Controllers/Normalization/MoveRepeatingGroup.php @@ -0,0 +1,40 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $repeatingColumns = $_POST['repeatingColumns']; + $newTable = $_POST['newTable']; + $newColumn = $_POST['newColumn']; + $primary_columns = $_POST['primary_columns']; + $res = $this->normalization->moveRepeatingGroup( + $repeatingColumns, + $primary_columns, + $newTable, + $newColumn, + $GLOBALS['table'], + $GLOBALS['db'] + ); + $this->response->addJSON($res); + } +} diff --git a/libraries/classes/Controllers/Normalization/PartialDependenciesController.php b/libraries/classes/Controllers/Normalization/PartialDependenciesController.php new file mode 100644 index 0000000000..a847ef6832 --- /dev/null +++ b/libraries/classes/Controllers/Normalization/PartialDependenciesController.php @@ -0,0 +1,29 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $html = $this->normalization->findPartialDependencies($GLOBALS['table'], $GLOBALS['db']); + $this->response->addHTML($html); + } +} diff --git a/libraries/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesController.php b/libraries/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesController.php new file mode 100644 index 0000000000..2be037c58d --- /dev/null +++ b/libraries/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesController.php @@ -0,0 +1,38 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $partialDependencies = json_decode($_POST['pd'], true); + $tablesName = json_decode($_POST['newTablesName']); + $res = $this->normalization->createNewTablesFor2NF( + $partialDependencies, + $tablesName, + $GLOBALS['table'], + $GLOBALS['db'] + ); + $this->response->addJSON($res); + } +} diff --git a/libraries/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesController.php b/libraries/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesController.php new file mode 100644 index 0000000000..bd3e0b2c4a --- /dev/null +++ b/libraries/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesController.php @@ -0,0 +1,32 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $newtables = json_decode($_POST['newTables'], true); + $res = $this->normalization->createNewTablesFor3NF($newtables, $GLOBALS['db']); + $this->response->addJSON($res); + } +} diff --git a/libraries/classes/Controllers/Normalization/ThirdNormalForm/NewTablesController.php b/libraries/classes/Controllers/Normalization/ThirdNormalForm/NewTablesController.php new file mode 100644 index 0000000000..1717a29f39 --- /dev/null +++ b/libraries/classes/Controllers/Normalization/ThirdNormalForm/NewTablesController.php @@ -0,0 +1,33 @@ +normalization = $normalization; + } + + public function __invoke(ServerRequest $request): void + { + $dependencies = json_decode($_POST['pd']); + $tables = json_decode($_POST['tables'], true); + $newTables = $this->normalization->getHtmlForNewTables3NF($dependencies, $tables, $GLOBALS['db']); + $this->response->addJSON($newTables); + } +} diff --git a/libraries/classes/Controllers/NormalizationController.php b/libraries/classes/Controllers/NormalizationController.php deleted file mode 100644 index 1dbf6586bd..0000000000 --- a/libraries/classes/Controllers/NormalizationController.php +++ /dev/null @@ -1,143 +0,0 @@ -normalization = $normalization; - } - - public function __invoke(ServerRequest $request): void - { - if (isset($_POST['getColumns'])) { - $html = '' - . ''; - //get column whose datatype falls under string category - $html .= $this->normalization->getHtmlForColumnsList( - $GLOBALS['db'], - $GLOBALS['table'], - _pgettext('string types', 'String') - ); - echo $html; - - return; - } - - if (isset($_POST['splitColumn'])) { - $num_fields = min(4096, intval($_POST['numFields'])); - $html = $this->normalization->getHtmlForCreateNewColumn($num_fields, $GLOBALS['db'], $GLOBALS['table']); - $html .= Url::getHiddenInputs($GLOBALS['db'], $GLOBALS['table']); - echo $html; - - return; - } - - if (isset($_POST['addNewPrimary'])) { - $num_fields = 1; - $columnMeta = [ - 'Field' => $GLOBALS['table'] . '_id', - 'Extra' => 'auto_increment', - ]; - $html = $this->normalization->getHtmlForCreateNewColumn( - $num_fields, - $GLOBALS['db'], - $GLOBALS['table'], - $columnMeta - ); - $html .= Url::getHiddenInputs($GLOBALS['db'], $GLOBALS['table']); - echo $html; - - return; - } - - if (isset($_POST['findPdl'])) { - $html = $this->normalization->findPartialDependencies($GLOBALS['table'], $GLOBALS['db']); - echo $html; - - return; - } - - if (isset($_POST['getNewTables3NF'])) { - $dependencies = json_decode($_POST['pd']); - $tables = json_decode($_POST['tables'], true); - $newTables = $this->normalization->getHtmlForNewTables3NF($dependencies, $tables, $GLOBALS['db']); - $this->response->disable(); - Core::headerJSON(); - echo json_encode($newTables); - - return; - } - - $this->addScriptFiles(['normalization.js', 'vendor/jquery/jquery.uitablefilter.js']); - - if (isset($_POST['createNewTables2NF'])) { - $partialDependencies = json_decode($_POST['pd'], true); - $tablesName = json_decode($_POST['newTablesName']); - $res = $this->normalization->createNewTablesFor2NF( - $partialDependencies, - $tablesName, - $GLOBALS['table'], - $GLOBALS['db'] - ); - $this->response->addJSON($res); - - return; - } - - if (isset($_POST['createNewTables3NF'])) { - $newtables = json_decode($_POST['newTables'], true); - $res = $this->normalization->createNewTablesFor3NF($newtables, $GLOBALS['db']); - $this->response->addJSON($res); - - return; - } - - if (isset($_POST['repeatingColumns'])) { - $repeatingColumns = $_POST['repeatingColumns']; - $newTable = $_POST['newTable']; - $newColumn = $_POST['newColumn']; - $primary_columns = $_POST['primary_columns']; - $res = $this->normalization->moveRepeatingGroup( - $repeatingColumns, - $primary_columns, - $newTable, - $newColumn, - $GLOBALS['table'], - $GLOBALS['db'] - ); - $this->response->addJSON($res); - - return; - } - - $this->render('table/normalization/normalization', [ - 'db' => $GLOBALS['db'], - 'table' => $GLOBALS['table'], - ]); - } -} diff --git a/libraries/routes.php b/libraries/routes.php index 7f17bbf603..44f1062780 100644 --- a/libraries/routes.php +++ b/libraries/routes.php @@ -22,7 +22,6 @@ use PhpMyAdmin\Controllers\LintController; use PhpMyAdmin\Controllers\LogoutController; use PhpMyAdmin\Controllers\NavigationController; use PhpMyAdmin\Controllers\Normalization; -use PhpMyAdmin\Controllers\NormalizationController; use PhpMyAdmin\Controllers\PhpInfoController; use PhpMyAdmin\Controllers\Preferences; use PhpMyAdmin\Controllers\RecentTablesListController; @@ -131,14 +130,22 @@ return static function (RouteCollector $routes): void { $routes->addRoute(['GET', 'POST'], '/logout', LogoutController::class); $routes->addRoute(['GET', 'POST'], '/navigation', NavigationController::class); $routes->addGroup('/normalization', static function (RouteCollector $routes): void { - $routes->addRoute(['GET', 'POST'], '', NormalizationController::class); + $routes->addRoute(['GET', 'POST'], '', Normalization\MainController::class); $routes->post('/1nf/step1', Normalization\FirstNormalForm\FirstStepController::class); $routes->post('/1nf/step2', Normalization\FirstNormalForm\SecondStepController::class); $routes->post('/1nf/step3', Normalization\FirstNormalForm\ThirdStepController::class); $routes->post('/1nf/step4', Normalization\FirstNormalForm\FourthStepController::class); + $routes->post('/2nf/create-new-tables', Normalization\SecondNormalForm\CreateNewTablesController::class); $routes->post('/2nf/new-tables', Normalization\SecondNormalForm\NewTablesController::class); $routes->post('/2nf/step1', Normalization\SecondNormalForm\FirstStepController::class); + $routes->post('/3nf/create-new-tables', Normalization\ThirdNormalForm\CreateNewTablesController::class); + $routes->post('/3nf/new-tables', Normalization\ThirdNormalForm\NewTablesController::class); $routes->post('/3nf/step1', Normalization\ThirdNormalForm\FirstStepController::class); + $routes->post('/add-new-primary', Normalization\AddNewPrimaryController::class); + $routes->post('/get-columns', Normalization\GetColumnsController::class); + $routes->post('/create-new-column', Normalization\CreateNewColumnController::class); + $routes->post('/move-repeating-group', Normalization\MoveRepeatingGroup::class); + $routes->post('/partial-dependencies', Normalization\PartialDependenciesController::class); }); $routes->get('/phpinfo', PhpInfoController::class); $routes->addGroup('/preferences', static function (RouteCollector $routes): void { diff --git a/libraries/services_controllers.php b/libraries/services_controllers.php index 3d9eb312ea..02725969a4 100644 --- a/libraries/services_controllers.php +++ b/libraries/services_controllers.php @@ -22,7 +22,6 @@ use PhpMyAdmin\Controllers\LintController; use PhpMyAdmin\Controllers\LogoutController; use PhpMyAdmin\Controllers\NavigationController; use PhpMyAdmin\Controllers\Normalization; -use PhpMyAdmin\Controllers\NormalizationController; use PhpMyAdmin\Controllers\PhpInfoController; use PhpMyAdmin\Controllers\Preferences; use PhpMyAdmin\Controllers\RecentTablesListController; @@ -617,6 +616,14 @@ return [ '$normalization' => '@normalization', ], ], + Normalization\SecondNormalForm\CreateNewTablesController::class => [ + 'class' => Normalization\SecondNormalForm\CreateNewTablesController::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], Normalization\SecondNormalForm\FirstStepController::class => [ 'class' => Normalization\SecondNormalForm\FirstStepController::class, 'arguments' => [ @@ -633,6 +640,14 @@ return [ '$normalization' => '@normalization', ], ], + Normalization\ThirdNormalForm\CreateNewTablesController::class => [ + 'class' => Normalization\ThirdNormalForm\CreateNewTablesController::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], Normalization\ThirdNormalForm\FirstStepController::class => [ 'class' => Normalization\ThirdNormalForm\FirstStepController::class, 'arguments' => [ @@ -641,8 +656,52 @@ return [ '$normalization' => '@normalization', ], ], - NormalizationController::class => [ - 'class' => NormalizationController::class, + Normalization\ThirdNormalForm\NewTablesController::class => [ + 'class' => Normalization\ThirdNormalForm\NewTablesController::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], + Normalization\AddNewPrimaryController::class => [ + 'class' => Normalization\AddNewPrimaryController::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], + Normalization\CreateNewColumnController::class => [ + 'class' => Normalization\CreateNewColumnController::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], + Normalization\GetColumnsController::class => [ + 'class' => Normalization\GetColumnsController::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], + Normalization\MainController::class => [ + 'class' => Normalization\MainController::class, + 'arguments' => ['$response' => '@response', '$template' => '@template'], + ], + Normalization\MoveRepeatingGroup::class => [ + 'class' => Normalization\MoveRepeatingGroup::class, + 'arguments' => [ + '$response' => '@response', + '$template' => '@template', + '$normalization' => '@normalization', + ], + ], + Normalization\PartialDependenciesController::class => [ + 'class' => Normalization\PartialDependenciesController::class, 'arguments' => [ '$response' => '@response', '$template' => '@template', diff --git a/phpstan-baseline.neon b/phpstan-baseline.neon index b223fbc395..371bfa983e 100644 --- a/phpstan-baseline.neon +++ b/phpstan-baseline.neon @@ -1220,35 +1220,35 @@ parameters: count: 1 path: libraries/classes/Controllers/HomeController.php + - + message: "#^Parameter \\#1 \\$partialDependencies of method PhpMyAdmin\\\\Normalization\\:\\:createNewTablesFor2NF\\(\\) expects array, mixed given\\.$#" + count: 1 + path: libraries/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesController.php + + - + message: "#^Parameter \\#2 \\$tablesName of method PhpMyAdmin\\\\Normalization\\:\\:createNewTablesFor2NF\\(\\) expects object, mixed given\\.$#" + count: 1 + path: libraries/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesController.php + - message: "#^Parameter \\#1 \\$partialDependencies of method PhpMyAdmin\\\\Normalization\\:\\:getHtmlForNewTables2NF\\(\\) expects array, mixed given\\.$#" count: 1 path: libraries/classes/Controllers/Normalization/SecondNormalForm/NewTablesController.php - - - message: "#^Parameter \\#1 \\$dependencies of method PhpMyAdmin\\\\Normalization\\:\\:getHtmlForNewTables3NF\\(\\) expects object, mixed given\\.$#" - count: 1 - path: libraries/classes/Controllers/NormalizationController.php - - message: "#^Parameter \\#1 \\$newTables of method PhpMyAdmin\\\\Normalization\\:\\:createNewTablesFor3NF\\(\\) expects array, mixed given\\.$#" count: 1 - path: libraries/classes/Controllers/NormalizationController.php + path: libraries/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesController.php - - message: "#^Parameter \\#1 \\$partialDependencies of method PhpMyAdmin\\\\Normalization\\:\\:createNewTablesFor2NF\\(\\) expects array, mixed given\\.$#" + message: "#^Parameter \\#1 \\$dependencies of method PhpMyAdmin\\\\Normalization\\:\\:getHtmlForNewTables3NF\\(\\) expects object, mixed given\\.$#" count: 1 - path: libraries/classes/Controllers/NormalizationController.php + path: libraries/classes/Controllers/Normalization/ThirdNormalForm/NewTablesController.php - message: "#^Parameter \\#2 \\$tables of method PhpMyAdmin\\\\Normalization\\:\\:getHtmlForNewTables3NF\\(\\) expects array, mixed given\\.$#" count: 1 - path: libraries/classes/Controllers/NormalizationController.php - - - - message: "#^Parameter \\#2 \\$tablesName of method PhpMyAdmin\\\\Normalization\\:\\:createNewTablesFor2NF\\(\\) expects object, mixed given\\.$#" - count: 1 - path: libraries/classes/Controllers/NormalizationController.php + path: libraries/classes/Controllers/Normalization/ThirdNormalForm/NewTablesController.php - message: "#^Property PhpMyAdmin\\\\Controllers\\\\Server\\\\BinlogController\\:\\:\\$binaryLogs type has no value type specified in iterable type array\\.$#" diff --git a/psalm-baseline.xml b/psalm-baseline.xml index 98672f2a3c..c6df54e6e3 100644 --- a/psalm-baseline.xml +++ b/psalm-baseline.xml @@ -2407,6 +2407,32 @@ $normalForm + + + $newColumn + $newTable + $primary_columns + $repeatingColumns + + + $newColumn + $newTable + $primary_columns + $repeatingColumns + + + + + $_POST['newTablesName'] + $_POST['pd'] + $partialDependencies + $tablesName + + + $partialDependencies + $tablesName + + $_POST['pd'] @@ -2416,6 +2442,15 @@ $partialDependencies + + + $_POST['newTables'] + $newtables + + + $newtables + + $tables @@ -2424,33 +2459,16 @@ $tables - - - $_POST['newTables'] - $_POST['newTablesName'] - $_POST['pd'] + + $_POST['pd'] $_POST['tables'] $dependencies - $newColumn - $newTable - $newtables - $partialDependencies - $primary_columns - $repeatingColumns $tables - $tablesName - + $dependencies - $newColumn - $newTable - $newtables - $partialDependencies - $primary_columns - $repeatingColumns $tables - $tablesName diff --git a/test/classes/Controllers/Normalization/AddNewPrimaryControllerTest.php b/test/classes/Controllers/Normalization/AddNewPrimaryControllerTest.php new file mode 100644 index 0000000000..d55100fc08 --- /dev/null +++ b/test/classes/Controllers/Normalization/AddNewPrimaryControllerTest.php @@ -0,0 +1,44 @@ +createDbiDummy(); + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new AddNewPrimaryController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + $this->assertStringContainsString('getHTMLResult()); + } +} diff --git a/test/classes/Controllers/Normalization/CreateNewColumnControllerTest.php b/test/classes/Controllers/Normalization/CreateNewColumnControllerTest.php new file mode 100644 index 0000000000..2a18d763bb --- /dev/null +++ b/test/classes/Controllers/Normalization/CreateNewColumnControllerTest.php @@ -0,0 +1,45 @@ +createDbiDummy(); + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new CreateNewColumnController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + $this->assertStringContainsString('
getHTMLResult()); + } +} diff --git a/test/classes/Controllers/Normalization/GetColumnsControllerTest.php b/test/classes/Controllers/Normalization/GetColumnsControllerTest.php new file mode 100644 index 0000000000..d9bc364973 --- /dev/null +++ b/test/classes/Controllers/Normalization/GetColumnsControllerTest.php @@ -0,0 +1,48 @@ +createDbiDummy(); + $dbiDummy->addSelectDb('test_db'); + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new GetColumnsController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + // phpcs:disable Generic.Files.LineLength.TooLong + $this->assertSame( + '', + $response->getHTMLResult() + ); + // phpcs:enable + } +} diff --git a/test/classes/Controllers/Normalization/MainControllerTest.php b/test/classes/Controllers/Normalization/MainControllerTest.php new file mode 100644 index 0000000000..803967e84c --- /dev/null +++ b/test/classes/Controllers/Normalization/MainControllerTest.php @@ -0,0 +1,77 @@ +dummyDbi = $this->createDbiDummy(); + $this->dbi = $this->createDatabaseInterface($this->dummyDbi); + $GLOBALS['dbi'] = $this->dbi; + parent::loadContainerBuilder(); + parent::loadDbiIntoContainerBuilder(); + $GLOBALS['server'] = 1; + $GLOBALS['PMA_PHP_SELF'] = 'index.php'; + parent::loadResponseIntoContainerBuilder(); + $GLOBALS['db'] = 'my_db'; + $GLOBALS['table'] = 'test_tbl'; + } + + public function testNormalization(): void + { + $GLOBALS['db'] = 'test_db'; + $GLOBALS['table'] = 'test_table'; + $response = new ResponseRenderer(); + + $controller = new MainController($response, new Template()); + $controller($this->createStub(ServerRequest::class)); + + $files = $response->getHeader()->getScripts()->getFiles(); + $this->assertTrue( + in_array(['name' => 'normalization.js', 'fire' => 1], $files, true), + 'normalization.js script was not included in the response.' + ); + $this->assertTrue( + in_array(['name' => 'vendor/jquery/jquery.uitablefilter.js', 'fire' => 0], $files, true), + 'vendor/jquery/jquery.uitablefilter.js script was not included in the response.' + ); + + $output = $response->getHTMLResult(); + $this->assertStringContainsString( + 'assertStringContainsString('', $output); + $this->assertStringContainsString('', $output); + $this->assertStringContainsString('type="radio" name="normalizeTo"', $output); + $this->assertStringContainsString('id="normalizeToRadio1" value="1nf" checked>', $output); + $this->assertStringContainsString('id="normalizeToRadio2" value="2nf">', $output); + $this->assertStringContainsString('id="normalizeToRadio3" value="3nf">', $output); + } +} diff --git a/test/classes/Controllers/Normalization/MoveRepeatingGroupTest.php b/test/classes/Controllers/Normalization/MoveRepeatingGroupTest.php new file mode 100644 index 0000000000..b7ff21a73a --- /dev/null +++ b/test/classes/Controllers/Normalization/MoveRepeatingGroupTest.php @@ -0,0 +1,53 @@ +createDbiDummy(); + $dbiDummy->addSelectDb('test_db'); + $dbiDummy->addResult('CREATE TABLE `new_table` SELECT `id`,`col1`,`col1` as `new_column` FROM `test_table` UNION SELECT `id`,`col1`,`col2` as `new_column` FROM `test_table`', []); + $dbiDummy->addResult('ALTER TABLE `test_table` DROP `col1`, DROP `col2`', []); + // phpcs:enable + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new MoveRepeatingGroup( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + $message = Message::success('Selected repeating group has been moved to the table \'test_table\''); + $this->assertSame(['queryError' => false, 'message' => $message->getDisplay()], $response->getJSONResult()); + } +} diff --git a/test/classes/Controllers/Normalization/PartialDependenciesControllerTest.php b/test/classes/Controllers/Normalization/PartialDependenciesControllerTest.php new file mode 100644 index 0000000000..2d01962001 --- /dev/null +++ b/test/classes/Controllers/Normalization/PartialDependenciesControllerTest.php @@ -0,0 +1,56 @@ +createDbiDummy(); + $dbiDummy->addSelectDb('test_db'); + $dbiDummy->addResult('SELECT COUNT(*) FROM (SELECT * FROM `test_table` LIMIT 500) as dt;', [['0']], ['dt']); + $dbiDummy->addResult( + 'SELECT COUNT(DISTINCT `id`) as \'`id`_cnt\', COUNT(DISTINCT `name`) as \'`name`_cnt\', COUNT(DISTINCT `datetimefield`) as \'`datetimefield`_cnt\' FROM (SELECT * FROM `test_table` LIMIT 500) as dt;', + [], + ['`id`_cnt', '`name`_cnt', '`datetimefield`_cnt', '`datetimefield`_cnt', 'dt'] + ); + // phpcs:enable + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new PartialDependenciesController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + // phpcs:disable Generic.Files.LineLength.TooLong + $this->assertSame( + 'This list is based on a subset of the table\'s data and is not necessarily accurate.

No partial dependencies found!

', + $response->getHTMLResult() + ); + // phpcs:enable + } +} diff --git a/test/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesControllerTest.php b/test/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesControllerTest.php new file mode 100644 index 0000000000..e9feec843c --- /dev/null +++ b/test/classes/Controllers/Normalization/SecondNormalForm/CreateNewTablesControllerTest.php @@ -0,0 +1,55 @@ + [], 'task' => ['timestamp']]); + $_POST['newTablesName'] = json_encode(['ID, task' => 'batch_log2', 'task' => 'table2']); + + $dbiDummy = $this->createDbiDummy(); + $dbiDummy->addSelectDb('test_db'); + $dbiDummy->addResult('CREATE TABLE `batch_log2` SELECT DISTINCT `ID`, `task` FROM `test_table`;', []); + $dbiDummy->addResult('CREATE TABLE `table2` SELECT DISTINCT `task`, `timestamp` FROM `test_table`;', []); + $dbiDummy->addResult('DROP TABLE `test_table`', []); + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new CreateNewTablesController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + $this->assertSame([ + 'legendText' => 'End of step', + 'headText' => '

The second step of normalization is complete for table \'test_table\'.

', + 'queryError' => false, + 'extra' => '', + ], $response->getJSONResult()); + } +} diff --git a/test/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesControllerTest.php b/test/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesControllerTest.php new file mode 100644 index 0000000000..a6980ce7ee --- /dev/null +++ b/test/classes/Controllers/Normalization/ThirdNormalForm/CreateNewTablesControllerTest.php @@ -0,0 +1,64 @@ + [ + 'event' => [ + 'pk' => 'eventID', + 'nonpk' => 'Start_time, DateOfEvent, NumberOfGuests, NameOfVenue, LocationOfVenue', + ], + 'table2' => ['pk' => 'Start_time', 'nonpk' => 'TypeOfEvent, period'], + ], + ]); + + // phpcs:disable Generic.Files.LineLength.TooLong + $dbiDummy = $this->createDbiDummy(); + $dbiDummy->addSelectDb('test_db'); + $dbiDummy->addResult('CREATE TABLE `event` SELECT DISTINCT `eventID`, `Start_time`, `DateOfEvent`, `NumberOfGuests`, `NameOfVenue`, `LocationOfVenue` FROM `test_table`;', []); + $dbiDummy->addResult('CREATE TABLE `table2` SELECT DISTINCT `Start_time`, `TypeOfEvent`, `period` FROM `test_table`;', []); + $dbiDummy->addResult('DROP TABLE `test_table`', []); + // phpcs:enable + + $dbi = $this->createDatabaseInterface($dbiDummy); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new CreateNewTablesController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + $this->assertSame([ + 'legendText' => 'End of step', + 'headText' => '

The third step of normalization is complete.

', + 'queryError' => false, + 'extra' => '', + ], $response->getJSONResult()); + } +} diff --git a/test/classes/Controllers/Normalization/ThirdNormalForm/NewTablesControllerTest.php b/test/classes/Controllers/Normalization/ThirdNormalForm/NewTablesControllerTest.php new file mode 100644 index 0000000000..88d14fc7c0 --- /dev/null +++ b/test/classes/Controllers/Normalization/ThirdNormalForm/NewTablesControllerTest.php @@ -0,0 +1,82 @@ + [ + 'event', + 'event', + 'event', + 'event', + 'NameOfVenue', + 'event', + 'period', + 'event', + 'event', + ], + ]); + $_POST['pd'] = json_encode([ + '' => [], + 'event' => [ + 'TypeOfEvent', + 'period', + 'Start_time', + 'NameOfVenue', + 'LocationOfVenue', + ], + 'NameOfVenue' => ['DateOfEvent'], + 'period' => ['NumberOfGuests'], + ]); + + $dbi = $this->createDatabaseInterface(); + $GLOBALS['dbi'] = $dbi; + $response = new ResponseRenderer(); + $template = new Template(); + + $controller = new NewTablesController( + $response, + $template, + new Normalization($dbi, new Relation($dbi), new Transformations(), $template) + ); + $controller($this->createStub(ServerRequest::class)); + + // phpcs:disable Generic.Files.LineLength.TooLong + $this->assertSame([ + 'html' => '

In order to put the original table \'test_table\' into Third normal form we need to create the following tables:

( event, TypeOfEvent, period, Start_time, NameOfVenue, LocationOfVenue )

( NameOfVenue, DateOfEvent )

( period, NumberOfGuests )', + 'newTables' => [ + 'test_table' => [ + 'test_table' => [ + 'pk' => 'event', + 'nonpk' => 'TypeOfEvent, period, Start_time, NameOfVenue, LocationOfVenue', + ], + 'table2' => ['pk' => 'NameOfVenue', 'nonpk' => 'DateOfEvent'], + 'table3' => ['pk' => 'period', 'nonpk' => 'NumberOfGuests'], + ], + ], + 'success' => true, + ], $response->getJSONResult()); + // phpcs:enable + } +} diff --git a/test/classes/Controllers/NormalizationControllerTest.php b/test/classes/Controllers/NormalizationControllerTest.php deleted file mode 100644 index 6e8ca6e76d..0000000000 --- a/test/classes/Controllers/NormalizationControllerTest.php +++ /dev/null @@ -1,230 +0,0 @@ -dummyDbi = $this->createDbiDummy(); - $this->dbi = $this->createDatabaseInterface($this->dummyDbi); - $GLOBALS['dbi'] = $this->dbi; - parent::loadContainerBuilder(); - parent::loadDbiIntoContainerBuilder(); - $GLOBALS['server'] = 1; - $GLOBALS['PMA_PHP_SELF'] = 'index.php'; - parent::loadResponseIntoContainerBuilder(); - $GLOBALS['db'] = 'my_db'; - $GLOBALS['table'] = 'test_tbl'; - } - - public function testGetNewTables3NF(): void - { - $_POST['getNewTables3NF'] = 1; - $_POST['tables'] = json_encode([ - 'test_tbl' => [ - 'event', - 'event', - 'event', - 'event', - 'NameOfVenue', - 'event', - 'period', - 'event', - 'event', - ], - ]); - $_POST['pd'] = json_encode([ - '' => [], - 'event' => [ - 'TypeOfEvent', - 'period', - 'Start_time', - 'NameOfVenue', - 'LocationOfVenue', - ], - 'NameOfVenue' => ['DateOfEvent'], - 'period' => ['NumberOfGuests'], - ]); - - $GLOBALS['goto'] = 'index.php?route=/sql'; - $GLOBALS['containerBuilder']->setParameter('db', $GLOBALS['db']); - $GLOBALS['containerBuilder']->setParameter('table', $GLOBALS['table']); - /** @var NormalizationController $normalizationController */ - $normalizationController = $GLOBALS['containerBuilder']->get(NormalizationController::class); - $normalizationController($this->createStub(ServerRequest::class)); - - $this->assertResponseWasSuccessfull(); - - $this->getResponseJsonResult();// Will echo the contents - - $data = (string) json_encode( - [ - 'html' => '

In order to put the original table \'test_tbl\' into ' - . 'Third normal form we need to create the following tables:' - . '

' - . '( event, TypeOfEvent, period, Start_time, NameOfVenue, LocationOfVenue )' - . '

' - . '( NameOfVenue, DateOfEvent )

' - . '( period, NumberOfGuests )', - 'newTables' => [ - 'test_tbl' => [ - 'test_tbl' => [ - 'pk' => 'event', - 'nonpk' => 'TypeOfEvent, period, Start_time, NameOfVenue, LocationOfVenue', - ], - 'table2' => [ - 'pk' => 'NameOfVenue', - 'nonpk' => 'DateOfEvent', - ], - 'table3' => [ - 'pk' => 'period', - 'nonpk' => 'NumberOfGuests', - ], - ], - ], - 'success' => true, - ] - ); - $this->expectOutputString($data); - } - - public function testCreateNewTables2NF(): void - { - $_POST['createNewTables2NF'] = 1; - $_POST['pd'] = json_encode([ - 'ID, task' => [], - 'task' => ['timestamp'], - ]); - $_POST['newTablesName'] = json_encode([ - 'ID, task' => 'batch_log2', - 'task' => 'table2', - ]); - - $GLOBALS['goto'] = 'index.php?route=/sql'; - $GLOBALS['containerBuilder']->setParameter('db', $GLOBALS['db']); - $GLOBALS['containerBuilder']->setParameter('table', $GLOBALS['table']); - /** @var NormalizationController $normalizationController */ - $normalizationController = $GLOBALS['containerBuilder']->get(NormalizationController::class); - $this->dummyDbi->addSelectDb('my_db'); - $normalizationController($this->createStub(ServerRequest::class)); - $this->dummyDbi->assertAllSelectsConsumed(); - - $this->assertResponseWasSuccessfull(); - - $this->assertSame( - [ - 'legendText' => 'End of step', - 'headText' => '

The second step of normalization is complete for table \'test_tbl\'.

', - 'queryError' => false, - 'extra' => '', - ], - $this->getResponseJsonResult() - ); - } - - public function testCreateNewTables3NF(): void - { - $_POST['createNewTables3NF'] = 1; - $_POST['newTables'] = json_encode([ - 'test_tbl' => [ - 'event' => [ - 'pk' => 'eventID', - 'nonpk' => 'Start_time, DateOfEvent, NumberOfGuests, NameOfVenue, LocationOfVenue', - ], - 'table2' => [ - 'pk' => 'Start_time', - 'nonpk' => 'TypeOfEvent, period', - ], - ], - ]); - - $GLOBALS['goto'] = 'index.php?route=/sql'; - $GLOBALS['containerBuilder']->setParameter('db', $GLOBALS['db']); - $GLOBALS['containerBuilder']->setParameter('table', $GLOBALS['table']); - /** @var NormalizationController $normalizationController */ - $normalizationController = $GLOBALS['containerBuilder']->get(NormalizationController::class); - $this->dummyDbi->addSelectDb('my_db'); - $normalizationController($this->createStub(ServerRequest::class)); - $this->dummyDbi->assertAllSelectsConsumed(); - - $this->assertResponseWasSuccessfull(); - - $this->assertSame( - [ - 'legendText' => 'End of step', - 'headText' => '

The third step of normalization is complete.

', - 'queryError' => false, - 'extra' => '', - ], - $this->getResponseJsonResult() - ); - } - - public function testNormalization(): void - { - $GLOBALS['db'] = 'test_db'; - $GLOBALS['table'] = 'test_table'; - $dbi = $this->createDatabaseInterface(); - $response = new ResponseRenderer(); - $template = new Template(); - - $controller = new NormalizationController( - $response, - $template, - new Normalization($dbi, new Relation($dbi), new Transformations(), $template) - ); - $controller($this->createStub(ServerRequest::class)); - - $files = $response->getHeader()->getScripts()->getFiles(); - $this->assertTrue( - in_array(['name' => 'normalization.js', 'fire' => 1], $files, true), - 'normalization.js script was not included in the response.' - ); - $this->assertTrue( - in_array(['name' => 'vendor/jquery/jquery.uitablefilter.js', 'fire' => 0], $files, true), - 'vendor/jquery/jquery.uitablefilter.js script was not included in the response.' - ); - - $output = $response->getHTMLResult(); - $this->assertStringContainsString( - 'assertStringContainsString('', $output); - $this->assertStringContainsString('', $output); - $this->assertStringContainsString('type="radio" name="normalizeTo"', $output); - $this->assertStringContainsString('id="normalizeToRadio1" value="1nf" checked>', $output); - $this->assertStringContainsString('id="normalizeToRadio2" value="2nf">', $output); - $this->assertStringContainsString('id="normalizeToRadio3" value="3nf">', $output); - } -}