diff --git a/cp/app/Controllers/SystemController.php b/cp/app/Controllers/SystemController.php index 331f54d..a035761 100644 --- a/cp/app/Controllers/SystemController.php +++ b/cp/app/Controllers/SystemController.php @@ -5,6 +5,7 @@ namespace App\Controllers; use Psr\Http\Message\ResponseInterface as Response; use Psr\Http\Message\ServerRequestInterface as Request; use Psr\Container\ContainerInterface; +use Respect\Validation\Validator as v; class SystemController extends Controller { @@ -47,6 +48,235 @@ class SystemController extends Controller return $response->withHeader('Location', '/dashboard')->withStatus(302); } + if ($request->getMethod() === 'POST') { + // Retrieve POST data + $data = $request->getParsedBody(); + $db = $this->container->get('db'); + + if (isset($data['extension'])) { + $extension = $data['extension']; + + // Remove any leading and trailing dots + $extension = trim($extension, '.'); + + // Add a dot at the beginning if it's missing + if ($extension !== '' && $extension[0] !== '.') { + $extension = '.' . $extension; + } + + // Store the modified 'extension' value back in $data + $data['extension'] = $extension; + } + + $validators = [ + 'extension' => v::stringType()->notEmpty()->length(3, 64), + 'tldType' => v::stringType()->notEmpty(), + 'script' => v::stringType()->notEmpty(), + 'createm0' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm12' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm24' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm36' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm48' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm60' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm72' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm84' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm96' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm108' => v::numericVal()->between(0.00, 9999999.99, true), + 'createm120' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm0' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm12' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm24' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm36' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm48' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm60' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm72' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm84' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm96' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm108' => v::numericVal()->between(0.00, 9999999.99, true), + 'renewm120' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm0' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm12' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm24' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm36' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm48' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm60' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm72' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm84' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm96' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm108' => v::numericVal()->between(0.00, 9999999.99, true), + 'transferm120' => v::numericVal()->between(0.00, 9999999.99, true), + 'restorePrice' => v::numericVal()->between(0.00, 9999999.99, true), + 'premiumNamesFile' => v::optional(v::file()->mimetype('text/csv')->size(5 * 1024 * 1024)), + 'categoryPrice1' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice2' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice3' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice4' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice5' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice6' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice7' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice8' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice9' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryPrice10' => v::optional(v::numericVal()->between(0.00, 9999999.99, true)), + 'categoryName1' => v::optional(v::stringType()->length(1, 50)), + 'categoryName2' => v::optional(v::stringType()->length(1, 50)), + 'categoryName3' => v::optional(v::stringType()->length(1, 50)), + 'categoryName4' => v::optional(v::stringType()->length(1, 50)), + 'categoryName5' => v::optional(v::stringType()->length(1, 50)), + 'categoryName6' => v::optional(v::stringType()->length(1, 50)), + 'categoryName7' => v::optional(v::stringType()->length(1, 50)), + 'categoryName8' => v::optional(v::stringType()->length(1, 50)), + 'categoryName9' => v::optional(v::stringType()->length(1, 50)), + 'categoryName10' => v::optional(v::stringType()->length(1, 50)) + ]; + + $errors = []; + foreach ($validators as $field => $validator) { + // If the field is not set and it's optional, skip validation + if (!isset($data[$field]) && strpos($field, 'category') === 0) { + continue; + } + + try { + $validator->assert(isset($data[$field]) ? $data[$field] : []); + } catch (\Respect\Validation\Exceptions\NestedValidationException $e) { + $errors[$field] = $e->getMessages(); + } + } + + if (!empty($errors)) { + // Handle errors + $errorText = ''; + + foreach ($errors as $field => $messages) { + $errorText .= ucfirst($field) . ' errors: ' . implode(', ', $messages) . '; '; + } + + // Trim the final semicolon and space + $errorText = rtrim($errorText, '; '); + + $this->container->get('flash')->addMessage('error', $errorText); + return $response->withHeader('Location', '/registry/tld/create')->withStatus(302); + } + + $result = $db->select( + 'SELECT id FROM domain_tld WHERE tld = ?', + [ $data['extension'] ] + ); + + if (!empty($result)) { + $this->container->get('flash')->addMessage('error', 'The TLD you are trying to add already exists'); + return $response->withHeader('Location', '/registry/tld/create')->withStatus(302); + } + + switch ($data['extension']) { + case 'ascii': + $idntable = '/^(?!-)(?!.*--)[A-Z0-9-]{1,63}(?beginTransaction(); + + $currentDateTime = new \DateTime(); + $crdate = $currentDateTime->format('Y-m-d H:i:s.v'); // Current timestamp + + $db->insert('domain_tld', [ + 'tld' => $data['extension'], + 'idn_table' => $idntable, + 'secure' => 0, + ]); + $tld_id = $db->getlastInsertId(); + + $db->insert( + 'domain_price', + [ + 'tldid' => $tld_id, + 'command' => 'create', + 'm0' => $data['createm0'], + 'm12' => $data['createm12'], + 'm24' => $data['createm24'], + 'm36' => $data['createm36'], + 'm48' => $data['createm48'], + 'm60' => $data['createm60'], + 'm72' => $data['createm72'], + 'm84' => $data['createm84'], + 'm96' => $data['createm96'], + 'm108' => $data['createm108'], + 'm120' => $data['createm120'] + ] + ); + + $db->insert( + 'domain_price', + [ + 'tldid' => $tld_id, + 'command' => 'renew', + 'm0' => $data['renewm0'], + 'm12' => $data['renewm12'], + 'm24' => $data['renewm24'], + 'm36' => $data['renewm36'], + 'm48' => $data['renewm48'], + 'm60' => $data['renewm60'], + 'm72' => $data['renewm72'], + 'm84' => $data['renewm84'], + 'm96' => $data['renewm96'], + 'm108' => $data['renewm108'], + 'm120' => $data['renewm120'] + ] + ); + + $db->insert( + 'domain_price', + [ + 'tldid' => $tld_id, + 'command' => 'transfer', + 'm0' => $data['transferm0'], + 'm12' => $data['transferm12'], + 'm24' => $data['transferm24'], + 'm36' => $data['transferm36'], + 'm48' => $data['transferm48'], + 'm60' => $data['transferm60'], + 'm72' => $data['transferm72'], + 'm84' => $data['transferm84'], + 'm96' => $data['transferm96'], + 'm108' => $data['transferm108'], + 'm120' => $data['transferm120'] + ] + ); + + $db->insert( + 'domain_restore_price', + [ + 'tldid' => $tld_id, + 'price' => $data['restorePrice'] + ] + ); + + //todo: add premium domains and price categories + + $db->commit(); + } catch (Exception $e) { + $db->rollBack(); + $this->container->get('flash')->addMessage('error', 'Database failure: ' . $e->getMessage()); + return $response->withHeader('Location', '/registry/tld/create')->withStatus(302); + } + + $this->container->get('flash')->addMessage('success', 'TLD ' . $data['extension'] . ' has been created successfully'); + return $response->withHeader('Location', '/registry/tlds')->withStatus(302); + } + $db = $this->container->get('db'); return view($response,'admin/system/createTld.twig'); diff --git a/cp/resources/views/admin/system/createTld.twig b/cp/resources/views/admin/system/createTld.twig index 771a118..1399a59 100644 --- a/cp/resources/views/admin/system/createTld.twig +++ b/cp/resources/views/admin/system/createTld.twig @@ -1,6 +1,6 @@ {% extends "layouts/app.twig" %} -{% block title %}{{ __('Create TLD') }}{% endblock %} +{% block title %}{{ __('Create New TLD') }}{% endblock %} {% block content %}
@@ -14,7 +14,7 @@ {{ __('Overview') }}

- {{ __('Create TLD') }} + {{ __('Create New TLD') }}

@@ -24,147 +24,169 @@
-
+ {% include 'partials/flash.twig' %} + {{ csrf.field | raw }} -
-
-
New TLD Registration
+
+
General Details
+
+
+
+ + + Enter the desired top-level domain (TLD) name, like '.test' or '.example'.
-
- - -
- - - Enter the desired top-level domain (TLD) name, like '.test' or '.example'. -
- - -
- - DNSSEC is currently activated manually. This option is for display purposes only. -
- - -
- - - Select the type of TLD: ccTLD (Country Code Top-Level Domain) or gTLD (Generic Top-Level Domain). -
- - -
- - - Choose the script type that the TLD will support. Options include ASCII, Cyrillic, Japanese, and Korean. -
+
+ + DNSSEC is currently activated manually. This option is for display purposes only.
+
+ + + Select the type of TLD: ccTLD (Country Code Top-Level Domain) or gTLD (Generic Top-Level Domain). +
+
+ + + Choose the script type that the TLD will support. Options include ASCII, Cyrillic, Japanese, and Korean. +
+
-
-
TLD Pricing
+
+
Pricing
+
+
+
+ + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + +
CommandSetup Fee1 Year *2 Years *3 Years *4 Years *5 Years *6 Years *7 Years *8 Years *9 Years *10 Years *
Create
Renew
Transfer
+ When you type a price for 1 Year above, it will automatically get multiplied for subsequent years.
-
- -
- - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - - -
Command / DurationSetup Fee1 Year2 Years3 Year4 Years5 Year6 Years7 Year8 Years9 Years10 Years
Create
Renew
Transfer
-
- -
- - - Enter the price for restoring a TLD. -
+
+ + + Enter the price for restoring the TLD.
- +
+ +
+
+
Premium Names
+
+
+
+ + + + Upload a CSV file with premium names. Each row should contain a name and its pricing category, separated by a comma. + +
+ +
+ +
Set Premium Name Price Categories
+ + + + + + + + + + + + + + + +
Category NamePriceAction
+
+ +
-
@@ -180,61 +202,68 @@
{% endblock %} \ No newline at end of file diff --git a/cp/resources/views/admin/system/manageTlds.twig b/cp/resources/views/admin/system/manageTlds.twig index bc798d3..d1b75b9 100644 --- a/cp/resources/views/admin/system/manageTlds.twig +++ b/cp/resources/views/admin/system/manageTlds.twig @@ -41,19 +41,7 @@
- {% if subject is defined %} - - {% endif %} + {% include 'partials/flash.twig' %}