├── .gitignore
├── _config.yml
├── src
└── Magma
│ ├── Router
│ ├── Exception
│ │ └── .gitkeep
│ ├── RouterInterface.php
│ ├── RouterFactory.php
│ └── Router.php
│ ├── Session
│ ├── Exception
│ │ └── .gitkeep
│ ├── Storage
│ │ ├── ArraySessionStorage.php
│ │ ├── NativeSessionStorage.php
│ │ ├── SessionStorageInterface.php
│ │ └── AbstractSessionStorage.php
│ ├── SessionManager.php
│ ├── SessionFactory.php
│ ├── SessionInterface.php
│ └── Session.php
│ ├── LiquidOrm
│ ├── DataMapper
│ │ ├── Exception
│ │ │ └── .gitkeep
│ │ ├── DataMapperInterface.php
│ │ ├── DataMapperFactory.php
│ │ ├── DataMapperEnvironmentConfiguration.php
│ │ └── DataMapper.php
│ ├── DataRepository
│ │ ├── Exception
│ │ │ └── .gitkeep
│ │ ├── DataRepositoryFactory.php
│ │ ├── DataRepositoryInterface.php
│ │ └── DataRepository.php
│ ├── EntityManager
│ │ ├── Exception
│ │ │ └── .gitkeep
│ │ ├── EntityManagerInterface.php
│ │ ├── EntityManager.php
│ │ ├── EntityManagerFactory.php
│ │ ├── CrudInterface.php
│ │ └── Crud.php
│ ├── QueryBuilder
│ │ ├── Exception
│ │ │ └── .gitkeep
│ │ ├── QueryBuilderInterface.php
│ │ ├── QueryBuilderFactory.php
│ │ ├── AbstractQueryBuilder.php
│ │ └── QueryBuilder.php
│ └── LiquidOrmManager.php
│ ├── Datatable
│ ├── DatatableColumnInterface.php
│ ├── AbstractDatatableColumn.php
│ ├── DatatableInterface.php
│ ├── AbstractDatatable.php
│ └── Datatable.php
│ ├── Application
│ ├── Config.php
│ └── Application.php
│ ├── GlobalManager
│ ├── Exception
│ │ ├── GlobalManagerException.php
│ │ └── GlobalManagerInvalidArgumentException.php
│ ├── GlobalManagerInterface.php
│ └── GlobalManager.php
│ ├── Flash
│ ├── FlashTypes.php
│ ├── FlashInterface.php
│ └── Flash.php
│ ├── Twig
│ └── TwigExtension.php
│ ├── Abstracts
│ └── AbstractBaseModel.php
│ ├── DatabaseConnection
│ ├── DatabaseConnectionInterface.php
│ ├── Exception
│ │ └── DatabaseConnectionException.php
│ └── DatabaseConnection.php
│ ├── Http
│ ├── ResponseHandler.php
│ └── RequestHandler.php
│ ├── Base
│ ├── Exception
│ │ ├── BaseLengthException.php
│ │ ├── BaseNoValueException.php
│ │ ├── BaseException.php
│ │ ├── BaseRuntimeException.php
│ │ ├── BaseOverFlowException.php
│ │ ├── BaseOutOfRangeException.php
│ │ ├── BaseInvalidArgumentException.php
│ │ ├── BaseLogicException.php
│ │ ├── BaseOutOfBoundsException.php
│ │ ├── BaseUnderFlowException.php
│ │ ├── BaseBadFunctionCallException.php
│ │ ├── BaseBadMethodCallException.php
│ │ └── BaseUnexpectedValueException.php
│ ├── BaseEntity.php
│ ├── BaseModel.php
│ ├── BaseView.php
│ └── BaseController.php
│ ├── Traits
│ └── SystemTrait.php
│ ├── Utility
│ ├── Token.php
│ ├── Paginator.php
│ ├── Sortable.php
│ └── Sanitizer.php
│ ├── Yaml
│ └── YamlConfig.php
│ └── ErrorHandling
│ └── ErrorHandling.php
├── Config
├── app.yaml
├── controller.yaml
├── routes.yaml
├── database.yaml
├── twig.yaml
└── session.yaml
├── App
├── Templates
│ └── client
│ │ └── home
│ │ └── index.html.twig
├── Controller
│ ├── SecurityController.php
│ ├── Admin
│ │ └── UserController.php
│ └── HomeController.php
├── Entity
│ └── UserEntity.php
├── Model
│ └── UserModel.php
└── DataColumns
│ └── UserColumns.php
├── README.md
├── dataFlow
├── MVC_process_GET.pdf
├── Presentation (2).pdf
└── CopyOfMVCProcessPOST.pdf
├── index.php
├── composer.json
├── .htaccess
└── composer.lock
/.gitignore:
--------------------------------------------------------------------------------
1 | /vendor/
2 |
--------------------------------------------------------------------------------
/_config.yml:
--------------------------------------------------------------------------------
1 | theme: jekyll-theme-tactile
--------------------------------------------------------------------------------
/src/Magma/Router/Exception/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/src/Magma/Session/Exception/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataMapper/Exception/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataRepository/Exception/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/EntityManager/Exception/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/QueryBuilder/Exception/.gitkeep:
--------------------------------------------------------------------------------
1 |
--------------------------------------------------------------------------------
/Config/app.yaml:
--------------------------------------------------------------------------------
1 | pdo_driver: mysql
2 | seccret_key: 8541wedfef511
--------------------------------------------------------------------------------
/App/Templates/client/home/index.html.twig:
--------------------------------------------------------------------------------
1 | {{ table }}
2 | {{ pagination }}
--------------------------------------------------------------------------------
/README.md:
--------------------------------------------------------------------------------
1 | # MagmaCore
2 | # Project Abondon Please see MagmaSkeleton
3 |
--------------------------------------------------------------------------------
/dataFlow/MVC_process_GET.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/TheCodingWorkshop/MagmaCore/HEAD/dataFlow/MVC_process_GET.pdf
--------------------------------------------------------------------------------
/dataFlow/Presentation (2).pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/TheCodingWorkshop/MagmaCore/HEAD/dataFlow/Presentation (2).pdf
--------------------------------------------------------------------------------
/dataFlow/CopyOfMVCProcessPOST.pdf:
--------------------------------------------------------------------------------
https://raw.githubusercontent.com/TheCodingWorkshop/MagmaCore/HEAD/dataFlow/CopyOfMVCProcessPOST.pdf
--------------------------------------------------------------------------------
/src/Magma/Session/Storage/ArraySessionStorage.php:
--------------------------------------------------------------------------------
1 | message = $message;
23 | $this->code = $code;
24 | }
25 |
26 | }
--------------------------------------------------------------------------------
/src/Magma/Base/Exception/BaseInvalidArgumentException.php:
--------------------------------------------------------------------------------
1 | createFromGlobals();
23 | if ($create) {
24 | return $create;
25 | }
26 | }
27 | }
28 | return false;
29 | }
30 |
31 | }
--------------------------------------------------------------------------------
/src/Magma/Base/Exception/BaseLogicException.php:
--------------------------------------------------------------------------------
1 | crud = $crud;
25 | }
26 |
27 | /**
28 | * @inheritDoc
29 | */
30 | public function getCrud() : Object
31 | {
32 | return $this->crud;
33 | }
34 |
35 | }
--------------------------------------------------------------------------------
/src/Magma/Session/SessionManager.php:
--------------------------------------------------------------------------------
1 | create('magmacore', \Magma\Session\Storage\NativeSessionStorage::class, YamlConfig::file('session'));
24 | }
25 |
26 | }
--------------------------------------------------------------------------------
/src/Magma/Base/Exception/BaseOutOfBoundsException.php:
--------------------------------------------------------------------------------
1 | routeParams['action'];
23 | }
24 |
25 | protected function editAction()
26 | {
27 | $user = new UserModel();
28 | echo $this->routeParams['namespace'] . '/' . $this->routeParams['controller'] . '/' . $this->routeParams['id'] . '/' . $this->routeParams['action'];
29 | }
30 |
31 | }
--------------------------------------------------------------------------------
/index.php:
--------------------------------------------------------------------------------
1 | run()
22 | ->setSession()
23 | ->setRouteHandler();
24 |
--------------------------------------------------------------------------------
/src/Magma/Flash/Flash.php:
--------------------------------------------------------------------------------
1 | has(self::FLASH_KEY)) {
20 | $session->set(self::FLASH_KEY, []);
21 | }
22 | $session->setArray(self::FLASH_KEY, ['message' => $message, 'type' => $type]);
23 | }
24 |
25 | public static function get()
26 | {
27 | $session = GlobalManager::get('global_session');
28 | $session->flush(self::FLASH_KEY);
29 | }
30 |
31 | }
--------------------------------------------------------------------------------
/src/Magma/Base/Exception/BaseUnexpectedValueException.php:
--------------------------------------------------------------------------------
1 | token = $tokenValue;
26 | } else {
27 | $this->token = bin2hex(random_bytes($bytes));
28 | }
29 | }
30 |
31 | /**
32 | * Get the token value
33 | *
34 | * @return string the token value
35 | * @throws Exception
36 | */
37 | public function getValue() : string
38 | {
39 | return $this->token;
40 | }
41 |
42 | /**
43 | * Get the hashed token value
44 | *
45 | * @return string The hashed value
46 | * @throws Exception
47 | */
48 | public function getHash() : string
49 | {
50 | return hash_hmac('sha256', $this->value, YamlConfig::file('app')['secret_key']);
51 | }
52 |
53 | }
--------------------------------------------------------------------------------
/App/Controller/HomeController.php:
--------------------------------------------------------------------------------
1 | getRepo()->findWithSearchAndPaging((new RequestHandler())->handler(), $args);
28 |
29 | $tableData = (new Datatable())->create(UserColumns::class, $repository, $args)->setAttr(['table_id' => 'sexytable', 'table_class' => ['youtube-datatable']])->table();
30 |
31 | $this->render('client/home/index.html.twig', [
32 | 'table' => $tableData,
33 | 'pagination' => (new Datatable())->create(UserColumns::class, $repository, $args)->pagination()
34 | ]);
35 | }
36 |
37 | protected function before()
38 | {}
39 |
40 | protected function after()
41 | {}
42 |
43 |
44 | }
--------------------------------------------------------------------------------
/src/Magma/Base/BaseEntity.php:
--------------------------------------------------------------------------------
1 | cleanData($dirtyData) as $key => $value) {
28 | $this->$key = $value;
29 | }
30 | }
31 | }
32 |
33 | /**
34 | * Return the sanitize post data back to the main constructor
35 | *
36 | * @param array $dirtyData
37 | * @return array
38 | * @throws BaseInvalidArgumentException
39 | */
40 | private function cleanData(array $dirtyData) : array
41 | {
42 | $cleanData = Sanitizer::clean($dirtyData);
43 | if ($cleanData) {
44 | return $cleanData;
45 | }
46 | }
47 |
48 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/QueryBuilder/QueryBuilderInterface.php:
--------------------------------------------------------------------------------
1 | repository = $factory->create(DataRepository::class);
38 | }
39 |
40 | /**
41 | * Get the data repository object based on the context model
42 | * which the repository is being executed from.
43 | *
44 | * @return DataRepository
45 | */
46 | public function getRepo() : DataRepository
47 | {
48 | return $this->repository;
49 | }
50 |
51 |
52 | }
--------------------------------------------------------------------------------
/src/Magma/Yaml/YamlConfig.php:
--------------------------------------------------------------------------------
1 | isFileExists($file);
39 | $parts = parse_url($file);
40 | $path = $parts['path'];
41 | if (strpos($path, $yamlFile) !== false) {
42 | return Yaml::parseFile($file);
43 | }
44 | }
45 | }
46 |
47 | /**
48 | * Load a yaml configuration into the yaml parser
49 | *
50 | * @param string $yamlFile
51 | * @return void
52 | */
53 | public static function file(string $yamlFile) : array
54 | {
55 | return (array)(new YamlConfig)->getYaml($yamlFile);
56 | }
57 |
58 | }
--------------------------------------------------------------------------------
/Config/twig.yaml:
--------------------------------------------------------------------------------
1 | # When set to true, the generated templates have a __toString() method that you can use to display the generated nodes (default to false).
2 | debug: false
3 | # The charset used by the templates.
4 | charset: utf-8
5 | # An absolute path where to store the compiled templates, or false to disable caching (which is the default).
6 | cache: ''
7 | # When developing with Twig, it’s useful to recompile the template whenever the source code changes. If you don’t provide a value for the auto_reload option, it will be determined automatically based on the debug value.
8 | auto_reload: true
9 | # If set to false, Twig will silently ignore invalid variables (variables and or attributes/methods that do not exist) and replace them with a null value. When set to true, Twig throws an exception instead (default to false).
10 | strict_variables: false
11 | # Sets the default auto-escaping strategy (name, html, js, css, url, html_attr, or a PHP callback that takes the template “filename” and returns the escaping strategy to use – the callback cannot be a function name to avoid collision with built-in escaping strategies); set it to false to disable auto-escaping. The name escaping strategy determines the escaping strategy to use for a template based on the template filename extension (this strategy does not incur any overhead at runtime as auto-escaping is done at compilation time.)
12 | autoescape: false
13 | # A flag that indicates which optimizations to apply (default to -1 – all optimizations are enabled; set it to 0 to disable).
14 | optimizations : -1
15 | # set a default extension to use with our view template files. This is not part of the twig configurations
16 | template_ext:
17 | - .html
18 | - .twig
19 | - .html.twig
--------------------------------------------------------------------------------
/Config/session.yaml:
--------------------------------------------------------------------------------
1 | session_name: 'magmaCore__' #The unqiue session name
2 | lifetime: '0' #The lifetime of the cookie in seconds.
3 | path: '/' #The path where the information is stored.
4 | domain: '' #The domain the cookie belongs to.
5 | secure: false #The cookie should only be sent over secure connections
6 | httponly: true #The cookie can only be access through HTTP protocol.
7 | samesite: lax #Controls the cross-domain sending of the cookie.
8 | # - supports 'lax', 'strict', 'none', null
9 |
10 | #specifies the number of seconds after which data will be seen as
11 | #'garbage' and potentially cleaned up.
12 | gc_maxlifetime: '1800'
13 | #in conjunction with session.gc_divisor is used to manage probability
14 | #that the gc (garbage collection) routine is started.
15 | gc_probability: '1000'
16 | #coupled with session.gc_probability defines the probability that the gc (garbage collection) process is started on every session initialization. The probability is calculated by using gc_probability/gc_divisor, e.g. 1/100 means there is a 1% chance that the GC process starts on each request. session.gc_divisor defaults to 100.
17 | gc_divisor: '100'
18 | #specifies whether the module will use cookies to store the session id on the client side. Defaults to 1 (enabled).
19 | use_cookies: '1'
20 |
21 | #driver:
22 | #file:
23 | #class: \Magma\Session\Storage\NativeSessionStorage
24 | #alias: native_storage
25 | #default: true
26 | #database:
27 | #class: \Magma\Session\Storage\PDOSessionStorage
28 | #alias: pdo_database
29 | #default: false
30 | #array:
31 | #class: \Magma\Session\Storage\ArraySessionStorage
32 | #alias: array_storage
33 | #default: false
34 |
--------------------------------------------------------------------------------
/src/Magma/DatabaseConnection/DatabaseConnection.php:
--------------------------------------------------------------------------------
1 | credentials = $credentials;
32 | }
33 |
34 | /**
35 | * @inheritDoc
36 | *
37 | * @return PDO
38 | */
39 | public function open() : PDO
40 | {
41 | try {
42 | $params = [
43 | PDO::ATTR_EMULATE_PREPARES => false,
44 | PDO::ATTR_PERSISTENT => true,
45 | PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION,
46 | PDO::ATTR_DEFAULT_FETCH_MODE => PDO::FETCH_ASSOC
47 | ];
48 | $this->dbh = new PDO(
49 | $this->credentials['dsn'],
50 | $this->credentials['username'],
51 | $this->credentials['password'],
52 | $params
53 | );
54 | } catch(PDOException $expection) {
55 | throw new DatabaseConnectionException($expection->getMessage(), (int)$expection->getCode());
56 | }
57 |
58 | return $this->dbh;
59 | }
60 |
61 | /**
62 | * @inheritDoc
63 | *
64 | * @return void
65 | */
66 | public function close() : void
67 | {
68 | $this->dbh = null;
69 | }
70 |
71 |
72 | }
--------------------------------------------------------------------------------
/src/Magma/GlobalManager/GlobalManager.php:
--------------------------------------------------------------------------------
1 | addExtension(new DebugExtension());
39 | $twig->addExtension(new TwigExtension());
40 | }
41 | return $twig->render($template, $context);
42 | }
43 |
44 | /**
45 | * echo the contents of a view template using Twig
46 | *
47 | * @param string $template The template file
48 | * @param array $context Associative array of data to display in the view (optional)
49 | *
50 | * @return string
51 | * @throws LoaderError
52 | * @throws RuntimeError
53 | * @throws SyntaxError
54 | * @throws Exception
55 | */
56 | public function twigRender(string $template, array $context = [])
57 | {
58 | echo $this->getTemplate($template, $context);
59 | }
60 |
61 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/EntityManager/EntityManagerFactory.php:
--------------------------------------------------------------------------------
1 | dataMapper = $dataMapper;
30 | $this->queryBuilder = $queryBuilder;
31 | }
32 |
33 | /**
34 | * Create the entityManager obejct and inject the dependency which is the crud object
35 | *
36 | * @param string $crudString
37 | * @param string $tableSchema
38 | * @param string $tableSchemaID
39 | * @param array $options
40 | * @return EntityManagerInterface
41 | * @throws BaseUnexpectedValueException
42 | */
43 | public function create(string $crudString, string $tableSchema, string $tableSchemaID, array $options = []) : EntityManagerInterface
44 | {
45 | $crudObject = new $crudString($this->dataMapper, $this->queryBuilder, $tableSchema, $tableSchemaID, $options);
46 | if (!$crudObject instanceof CrudInterface) {
47 | throw new BaseUnexpectedValueException($crudString . ' is not a valid crud object.');
48 | }
49 | return new EntityManager($crudObject);
50 | }
51 |
52 | }
--------------------------------------------------------------------------------
/src/Magma/Utility/Paginator.php:
--------------------------------------------------------------------------------
1 | totalPages = ceil($totalRecords / $recordsPerPage);
32 | $data = [
33 | 'options' => [
34 | 'default' => 1,
35 | 'min_range' => 1,
36 | 'max_range' => $this->totalPages
37 | ]
38 | ];
39 | $this->page = filter_var($page, FILTER_VALIDATE_INT, $data);
40 | // Calculate the starting record based on the page and number of records per page
41 | $this->offset = $recordsPerPage * ($this->page - 1);
42 | }
43 |
44 | /**
45 | * Get the starting record within the SQL Query
46 | *
47 | * @return int
48 | */
49 | public function getOffset() : int
50 | {
51 | return (int)$this->offset;
52 | }
53 |
54 | /**
55 | * Gte the current page
56 | *
57 | * @return void
58 | */
59 | public function getPage() : int
60 | {
61 | return (int)$this->page;
62 | }
63 |
64 | /**
65 | * Get the total number of pages
66 | *
67 | * @return int
68 | */
69 | public function getTotalPages() : int
70 | {
71 | return (int)$this->totalPages;
72 | }
73 |
74 |
75 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataMapper/DataMapperInterface.php:
--------------------------------------------------------------------------------
1 | columns = $columns;
36 | }
37 |
38 | public function getColumn() : string
39 | {
40 | if (is_array($this->columns)) {
41 | $this->column = isset($_GET['column']) && in_array($_GET['column'], $this->columns) ? $_GET['column'] : $this->columns[0];
42 | if ($this->column) {
43 | return $this->column;
44 | }
45 | }
46 | }
47 |
48 | public function getDirection() : string
49 | {
50 | $this->order = isset($_GET['order']) && strtolower($_GET['order']) == 'desc' ? 'DESC' : 'ASC';
51 | if ($this->order) {
52 | return $this->order;
53 | }
54 | }
55 |
56 | public function sortDirection() : string
57 | {
58 | $this->direction = str_replace(array('ASC', 'DESC'), array('up', 'down'), $this->getDirection());
59 | if ($this->direction) {
60 | return $this->direction;
61 | }
62 | }
63 |
64 | public function sortDescAsc()
65 | {
66 | if ($this->getDirection()) {
67 | return $this->getDirection() == 'ASC' ? 'desc' : 'asc';
68 | }
69 | }
70 |
71 | public function getClass() : string
72 | {
73 | return $this->class;
74 | }
75 |
76 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataRepository/DataRepositoryFactory.php:
--------------------------------------------------------------------------------
1 | crudIdentifier = $crudIdentifier;
34 | $this->tableSchema = $tableSchema;
35 | $this->tableSchemaID = $tableSchemaID;
36 | }
37 |
38 | /**
39 | * Create the DataRepository Object
40 | *
41 | * @param string $dataRepositoryString
42 | * @return void
43 | * @throws BaseUnexpectedValueException
44 | */
45 | public function create(string $dataRepositoryString) : DataRepositoryInterface
46 | {
47 | $entityManager = $this->initializeLiquidOrmManager();
48 | $dataRepositoryObject = new $dataRepositoryString($entityManager);
49 | if (!$dataRepositoryObject instanceof DataRepositoryInterface) {
50 | throw new BaseUnexpectedValueException($dataRepositoryString . ' is not a valid repository object');
51 | }
52 | return $dataRepositoryObject;
53 | }
54 |
55 | public function initializeLiquidOrmManager()
56 | {
57 | $environmentConfiguration = new DataMapperEnvironmentConfiguration(YamlConfig::file('database'));
58 | $ormManager = new LiquidOrmManager($environmentConfiguration, $this->tableSchema, $this->tableSchemaID);
59 | return $ormManager->initialize();
60 | }
61 |
62 | }
--------------------------------------------------------------------------------
/src/Magma/ErrorHandling/ErrorHandling.php:
--------------------------------------------------------------------------------
1 | getCode();
37 | if ($code !=404) {
38 | $code = 500;
39 | }
40 | http_response_code($code);
41 |
42 | $error = true;
43 | if ($error) {
44 | //echo "
";
45 | echo "
Fatal Error
";
46 | echo "
Uncaught exception: " . get_class($exception) . "
";
47 | echo "
Message: " . $exception->getMessage() . "
";
48 | echo "
Stack trace: " . $exception->getTraceAsString() . "
";
49 | echo "
Thrown in " . $exception->getFile() . " on line " . $exception->getLine() . "
";
50 | //echo "
";
51 | } else {
52 | $errorLog = LOG_DIR . "/" . date("Y-m-d H:is") . ".txt";
53 | ini_set('error_log', $errorLog);
54 | $message = "Uncaught exception: " . get_class($exception);
55 | $message .= "with message " . $exception->getMessage();
56 | $message .= "\nStack trace: " . $exception->getTraceAsString();
57 | $message .= "\nThrown in " . $exception->getFile() . " on line " . $exception->getLine();
58 |
59 | error_log($message);
60 |
61 | echo (new BaseView)->getTemplate("error/{$code}.html.twig", ["error_message" => $message]);
62 | }
63 | }
64 |
65 |
66 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataMapper/DataMapperFactory.php:
--------------------------------------------------------------------------------
1 | getDatabaseCredentials('mysql');
25 | $databaseConnectionObject = new $databaseConnectionString($credentials);
26 | if (!$databaseConnectionObject instanceof DatabaseConnectionInterface) {
27 | throw new DataMapperException($databaseConnectionString . ' is not a valid database connection object');
28 | }
29 | return new DataMapper($databaseConnectionObject);
30 | }*/
31 |
32 | /**
33 | * Creates the data mapper object and inject the dependency for this object. We are also
34 | * creating the DatabaseConnection Object
35 | * $dataMapperEnvironmentConfiguration get instantiated in the DataRepositoryFactory
36 | *
37 | * @param string $databaseConnectionString
38 | * @param Object $dataMapperEnvironmentConfiguration
39 | * @return DataMapperInterface
40 | * @throws BaseUnexpectedValueException
41 | */
42 | public function create(string $databaseConnectionString, Object $dataMapperEnvironmentConfiguration) : DataMapperInterface
43 | {
44 | // Create databaseConnection Object and pass the database credentials in
45 | $credentials = $dataMapperEnvironmentConfiguration->getDatabaseCredentials(YamlConfig::file('app')['pdo_driver']);
46 | $databaseConnectionObject = new $databaseConnectionString($credentials);
47 | if (!$databaseConnectionObject instanceof DatabaseConnectionInterface) {
48 | throw new BaseUnexpectedValueException($databaseConnectionString . ' is not a valid database connection object');
49 | }
50 | return new DataMapper($databaseConnectionObject);
51 | }
52 |
53 |
54 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/QueryBuilder/AbstractQueryBuilder.php:
--------------------------------------------------------------------------------
1 | [],
19 | 'selectors' => [],
20 | 'replace' => false,
21 | 'distinct' => false,
22 | 'from' => [],
23 | 'where' => null,
24 | 'and' => [],
25 | 'or' => [],
26 | 'orderby' => [],
27 | 'fields' => [],
28 | 'primary_key' => '',
29 | 'table' => '',
30 | 'type' => '',
31 | 'raw' => '',
32 |
33 | 'table_join' => '',
34 | 'join_key' => '',
35 | 'join' => []
36 | ];
37 |
38 | /** @var array */
39 | protected const QUERY_TYPES = ['insert', 'select', 'update', 'delete', 'raw', 'search', 'join'];
40 |
41 | /**
42 | * Main class constructor
43 | *
44 | * @return void
45 | */
46 | public function __construct()
47 | {}
48 |
49 | protected function orderByQuery()
50 | {
51 | // Append the orderby statement if set
52 | if (isset($this->key["extras"]["orderby"]) && $this->key["extras"]["orderby"] != "") {
53 | $this->sqlQuery .= " ORDER BY " . $this->key["extras"]["orderby"] . " ";
54 | }
55 | }
56 |
57 | protected function queryOffset()
58 | {
59 | // Append the limit and offset statement for adding pagination to the query
60 | if (isset($this->key["params"]["limit"]) && $this->key["params"]["offset"] != -1) {
61 | $this->sqlQuery .= " LIMIT :offset, :limit";
62 | }
63 |
64 | }
65 |
66 | protected function isQueryTypeValid(string $type) : bool
67 | {
68 | if (in_array($type, self::QUERY_TYPES)) {
69 | return true;
70 | }
71 | return false;
72 | }
73 |
74 | /**
75 | * Checks whether a key is set. returns true or false if not set
76 | *
77 | * @param string $key
78 | * @return bool
79 | */
80 | protected function has(string $key): bool
81 | {
82 | return isset($this->key[$key]);
83 | }
84 |
85 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/LiquidOrmManager.php:
--------------------------------------------------------------------------------
1 | environmentConfiguration = $environmentConfiguration;
40 | $this->tableSchema = $tableSchema;
41 | $this->tableSchemaID = $tableSchemaID;
42 | $this->options = $options;
43 | }
44 |
45 | /**
46 | * initialize method which glues all the components together and inject the necessary dependency within the
47 | * respective object
48 | *
49 | * @return Object
50 | */
51 | public function initialize() : Object
52 | {
53 | $dataMapperFactory = new DataMapperFactory();
54 | $dataMapper = $dataMapperFactory->create(DatabaseConnection::class, $this->environmentConfiguration);
55 | if ($dataMapper) {
56 | $queryBuilderFactory = new QueryBuilderFactory();
57 | $queryBuilder = $queryBuilderFactory->create(QueryBuilder::class);
58 | if ($queryBuilder) {
59 | $entityManagerFactory = new EntityManagerFactory($dataMapper, $queryBuilder);
60 | return $entityManagerFactory->create(Crud::class, $this->tableSchema, $this->tableSchemaID, $this->options);
61 | }
62 | }
63 | }
64 |
65 | }
--------------------------------------------------------------------------------
/src/Magma/Utility/Sanitizer.php:
--------------------------------------------------------------------------------
1 | 0) {
27 | foreach ($dirtyData as $key => $value) {
28 | if (!isset($key)) {
29 | throw new BaseInvalidArgumentException('Invalid key');
30 | }
31 | if (!is_array($value)) {
32 | $value = trim(stripslashes($value));
33 | }
34 |
35 | switch ($value) {
36 | case is_int($value) :
37 | $input[$key] = isset($value) ? filter_var($value, FILTER_SANITIZE_NUMBER_INT) : '';
38 | break;
39 | case is_string($value) :
40 | $input[$key] = isset($value) ? filter_var($value, FILTER_SANITIZE_STRING) : '';
41 | break;
42 | case is_array($value) :
43 | if (count($value) > 0) {
44 | foreach ($value as $arrKey => $arrValue) {
45 | if (isset($arrKey) && $arrKey !='') {
46 | if (is_int($arrValue)) {
47 | $input[$arrKey] = isset($arrValue) ? filter_var($arrValue, FILTER_SANITIZE_NUMBER_INT) : '';
48 | } else {
49 | $input[$arrKey] = isset($arrValue) ? filter_var($value, FILTER_SANITIZE_STRING) : '';
50 | }
51 | }
52 | }
53 | }
54 | break;
55 | }
56 | }
57 | if (isset($input) && $input !='') {
58 | return $input;
59 | }
60 | }
61 | }
62 |
63 | }
--------------------------------------------------------------------------------
/src/Magma/Router/RouterFactory.php:
--------------------------------------------------------------------------------
1 | routes.yaml has your defined routes and your passing the correct $_SERVER variable ie "QUERY_STRING".');
33 | }
34 | $this->dispatcedUrl = $dispatcedUrl;
35 | $this->routes = $routes;
36 | }
37 |
38 | /**
39 | * Instantiate the router object and checks whether the object
40 | * implements the correct interface else throw an exception.
41 | *
42 | * @param string $routerString
43 | * @return self
44 | */
45 | public function create(string $routerString) : self
46 | {
47 | $this->router = new $routerString();
48 | if (!$this->router instanceof RouterInterface) {
49 | throw new BaseUnexpectedValueException($routerString . ' is not a valid Router object');
50 | }
51 | return $this;
52 |
53 | }
54 |
55 | /**
56 | * Undocumented function
57 | *
58 | * @return void
59 | */
60 | public function buildRoutes()
61 | {
62 | if (is_array($this->routes) && !empty($this->routes)) {
63 | $args = [];
64 | foreach ($this->routes as $key => $route) {
65 | if (isset($route['namespace']) && $route['namespace'] !='') {
66 | $args = ['namespace' => $route['namespace']];
67 | } elseif(isset($route['controller']) && $route['controller'] !='') {
68 | $args = ['controller' => $route['controller'], 'action' => $route['action']];
69 | }
70 | if (isset($key)) {
71 | $this->router->add($key, $args);
72 | }
73 | }
74 | $this->router->dispatch($this->dispatcedUrl);
75 | }
76 | return false;
77 |
78 | }
79 |
80 | }
--------------------------------------------------------------------------------
/src/Magma/Session/SessionInterface.php:
--------------------------------------------------------------------------------
1 | hasSession($key)) {
54 | return $_SESSION[$key];
55 | }
56 | return $default;
57 | }
58 |
59 | /**
60 | * @inheritdoc
61 | *
62 | * @param string $key
63 | * @return void
64 | */
65 | public function deleteSession(string $key) : void
66 | {
67 | if ($this->hasSession($key)) {
68 | unset($_SESSION[$key]);
69 | }
70 | }
71 |
72 | /**
73 | * @inheritdoc
74 | *
75 | * @return void
76 | */
77 | public function invalidate() : void
78 | {
79 | $_SESSION = array();
80 | if (ini_get('session.use_cookies')) {
81 | $params = session_get_cookie_params();
82 | setCookie($this->getSessionName(), '', time() - $params['lifetime'], $params['path'], $params['domain'], $params['secure'], $params['httponly']);
83 | }
84 | session_unset();
85 | session_destroy();
86 | }
87 |
88 | /**
89 | * @inheritdoc
90 | *
91 | * @param string $key
92 | * @param [type] $default
93 | * @return void
94 | */
95 | public function flush(string $key, $default = null)
96 | {
97 | if ($this->hasSession($key)) {
98 | $value = $_SESSION[$key];
99 | $this->deleteSession($key);
100 | return $value;
101 | }
102 | return $default;
103 |
104 | }
105 |
106 | /**
107 | * @inheritdoc
108 | *
109 | * @param string $key
110 | * @return boolean
111 | */
112 | public function hasSession(string $key) : bool
113 | {
114 | return isset($_SESSION[$key]);
115 | }
116 |
117 |
118 | }
--------------------------------------------------------------------------------
/App/DataColumns/UserColumns.php:
--------------------------------------------------------------------------------
1 | 'id',
17 | 'dt_row' => 'ID',
18 | 'class' => 'id-class',
19 | 'show_column' => true,
20 | 'sortable' => false,
21 | 'formatter' => ''
22 | ],
23 | [
24 | 'db_row' => 'firstname',
25 | 'dt_row' => 'Firstname',
26 | 'class' => '',
27 | 'show_column' => true,
28 | 'sortable' => true,
29 | 'formatter' => ''
30 | ],
31 | [
32 | 'db_row' => 'lastname',
33 | 'dt_row' => 'Lastname',
34 | 'class' => '',
35 | 'show_column' => true,
36 | 'sortable' => false,
37 | 'formatter' => ''
38 | ],
39 | [
40 | 'db_row' => 'email',
41 | 'dt_row' => 'Email Address',
42 | 'class' => '',
43 | 'show_column' => true,
44 | 'sortable' => true,
45 | 'formatter' => ''
46 | ],
47 | [
48 | 'db_row' => 'status',
49 | 'dt_row' => 'Status',
50 | 'class' => '',
51 | 'show_column' => true,
52 | 'sortable' => false,
53 | 'formatter' => ''
54 | ],
55 | [
56 | 'db_row' => 'created_at',
57 | 'dt_row' => 'Published',
58 | 'class' => '',
59 | 'show_column' => true,
60 | 'sortable' => false,
61 | 'formatter' => ''
62 | ],
63 | [
64 | 'db_row' => 'modified_at',
65 | 'dt_row' => 'Modified',
66 | 'class' => '',
67 | 'show_column' => true,
68 | 'sortable' => false,
69 | 'formatter' => ''
70 | ],
71 | [
72 | 'db_row' => 'gravatar',
73 | 'dt_row' => 'Thumbnail',
74 | 'class' => '',
75 | 'show_column' => false,
76 | 'sortable' => false,
77 | 'formatter' => ''
78 | ],
79 | [
80 | 'db_row' => 'ip',
81 | 'dt_row' => 'IP Address',
82 | 'class' => '',
83 | 'show_column' => false,
84 | 'sortable' => false,
85 | 'formatter' => ''
86 | ],
87 | [
88 | 'db_row' => '',
89 | 'dt_row' => 'Action',
90 | 'class' => '',
91 | 'show_column' => true,
92 | 'sortable' => false,
93 | 'formatter' => ''
94 | ],
95 |
96 | ];
97 | }
98 |
99 | }
--------------------------------------------------------------------------------
/src/Magma/Datatable/AbstractDatatable.php:
--------------------------------------------------------------------------------
1 | '',
15 | 'orderby' => '',
16 | 'table_class' => ['uk-table'],
17 | 'table_id' => 'datatable',
18 | 'show_table_thead' => true,
19 | 'show_table_tfoot' => false,
20 | 'before' => '',
21 | 'after' => '
'
22 | ];
23 |
24 | protected const COLUMNS_PARTS = [
25 | 'db_row' => '',
26 | 'dt_row' => '',
27 | 'class' => '',
28 | 'show_column' => true,
29 | 'sortable' => false,
30 | 'formatter' => ''
31 | ];
32 |
33 | protected array $attr = [];
34 |
35 | public function __construct()
36 | {
37 | $this->attr = self::TABLE_PROPERTIES;
38 | foreach ($this->attr as $key => $value) {
39 | if (!$this->validAttributes($key, $value)) {
40 | $this->validAttributes($key, $value);
41 | }
42 | }
43 | }
44 |
45 | public function setAttr($attributes = []) : self
46 | {
47 | if (is_array($attributes) && count($attributes) > 0) {
48 | $propKeys = array_keys(self::TABLE_PROPERTIES);
49 | foreach ($attributes as $key => $value) {
50 | if (!in_array($key, $propKeys)) {
51 | throw new BaseInvalidArgumentException('Invalid property key set.');
52 | }
53 | $this->validAttributes($key, $value);
54 | $this->attr[$key] = $value;
55 | }
56 | }
57 | return $this;
58 | }
59 |
60 | protected function validAttributes(string $key, $value) : void
61 | {
62 | if (empty($key)) {
63 | throw new BaseInvalidArgumentException('Inavlid or empty attribute key. Ensure the key is present and of the correct data type ' . $value);
64 | }
65 | switch ($key) {
66 | case 'status' :
67 | case 'orderby' :
68 | case 'table_id' :
69 | case 'before' :
70 | case 'after' :
71 | if (!is_string($value)) {
72 | throw new BaseInvalidArgumentException('Invalid argument type ' . $value . ' should be a string');
73 | }
74 | break;
75 | case 'show_table_thead' :
76 | case 'show_table_tfoot' :
77 | if (!is_bool($value)) {
78 | throw new BaseInvalidArgumentException('Invalid argument type ' . $value . ' should be a boolean');
79 | }
80 | break;
81 | case 'table_class' :
82 | if (!is_array($value)) {
83 | throw new BaseInvalidArgumentException('Invalid argument type ' . $value . ' should be a array');
84 | }
85 | break;
86 | }
87 | $this->attr[$key] = $value;
88 | }
89 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataMapper/DataMapperEnvironmentConfiguration.php:
--------------------------------------------------------------------------------
1 | credentials = $credentials;
27 | }
28 |
29 | /*private function __isCredentialsValid(string $driver) : void
30 | {
31 | if (empty($driver) && !is_string($driver)) {
32 | throw new DataMapperInvalidArgumentException('Invalid argument. This is either missing or off the invalid data type.');
33 | }
34 | if (!is_array($this->credentials)) {
35 | throw new DataMapperInvalidArgumentException('Invalid credentials');
36 | }
37 | if (!in_array($driver, array_keys($this->credentials[$driver]))) {
38 | throw new DataMapperInvalidArgumentException('Invalid or unsupport database driver.');
39 | }
40 | }*/
41 |
42 | /**
43 | * Checks credentials for validity
44 | *
45 | * @param string $driver
46 | * @return void
47 | */
48 | private function isCredentialsValid(string $driver) : void
49 | {
50 | if (empty($driver) || !is_array($this->credentials)) {
51 | throw new BaseInvalidArgumentException('Core Error: You have either not specify the default database driver or the database.yaml is returning null or empty.');
52 | }
53 | }
54 |
55 |
56 | /*public function __getDatabaseCredentials(string $driver) : array
57 | {
58 | $connectionArray = [];
59 | $this->isCredentialsValid($driver);
60 | foreach ($this->credentials as $credential) {
61 | if (array_key_exists($driver, $credential)) {
62 | $connectionArray = $credential[$driver];
63 | }
64 | }
65 | return $connectionArray;
66 | }*/
67 | /**
68 | * Get the user defined database connection array
69 | *
70 | * @param string $driver
71 | * @return array
72 | * @throws BaseInvalidArgumentException
73 | */
74 | public function getDatabaseCredentials(string $driver) : array
75 | {
76 | $connectionArray = [];
77 | $this->isCredentialsValid($driver);
78 | foreach ($this->credentials as $credential) {
79 | if (!array_key_exists($driver, $credential)) {
80 | throw new BaseInvalidArgumentException('Core Error: Your selected database driver is not supported. Please see the database.yaml file for all support driver. Or specify a supported driver from your app.yaml configuration file');
81 | } else {
82 | $connectionArray = $credential[$driver];
83 | }
84 | }
85 | return $connectionArray;
86 | }
87 |
88 | }
--------------------------------------------------------------------------------
/src/Magma/Application/Application.php:
--------------------------------------------------------------------------------
1 | appRoot = $appRoot;
28 | }
29 |
30 | /**
31 | * Execute at application level
32 | *
33 | * @return self
34 | */
35 | public function run() : self
36 | {
37 | $this->constants();
38 | if (version_compare($phpVersion = PHP_VERSION, $coreVersion = Config::MAGMA_MIN_VERSION, '<')) {
39 | die(sprintf('You are runninig PHP %s, but the core framework requires at least PHP %s', $phpVersion, $coreVersion));
40 | }
41 | $this->environment();
42 | $this->errorHandler();
43 | return $this;
44 | }
45 |
46 | /**
47 | * Define framework and application directory constants
48 | *
49 | * @return void
50 | */
51 | private function constants() : void
52 | {
53 | defined('DS') or define('DS', '/');
54 | defined('APP_ROOT') or define('APP_ROOT', $this->appRoot);
55 | defined('CONFIG_PATH') or define('CONFIG_PATH', APP_ROOT . DS . 'Config');
56 | defined('TEMPLATE_PATH') or define('TEMPLATE_PATH', APP_ROOT . DS . 'App/');
57 | defined('LOG_DIR') or define('LOG_DIR', APP_ROOT . DS . 'tmp/log');
58 |
59 | }
60 |
61 | /**
62 | * Set default framework and application settings
63 | *
64 | * @return void
65 | */
66 | private function environment()
67 | {
68 | ini_set('default_charset', 'UTF-8');
69 | }
70 |
71 | /**
72 | * Convert PHP errors to exception and set a custom exception
73 | * handler. Which allows us to take control or error handling
74 | * so we can display errors in a customizable way
75 | *
76 | * @return void
77 | */
78 | private function errorHandler() : void
79 | {
80 | error_reporting(E_ALL | E_STRICT);
81 | set_error_handler('Magma\ErrorHandling\ErrorHandling::errorHandler');
82 | set_exception_handler('Magma\ErrorHandling\ErrorHandling::exceptionHandler');
83 | }
84 |
85 | public function setSession()
86 | {
87 | SystemTrait::sessionInit(true);
88 | return $this;
89 | }
90 |
91 | /**
92 | * Undocumented function
93 | *
94 | * @param string $url
95 | * @param array $routes
96 | * @return self
97 | */
98 | public function setRouteHandler(string $url = null, array $routes = []) : self
99 | {
100 | $url = ($url) ? $url : $_SERVER['QUERY_STRING'];
101 | $routes = ($routes) ? $routes : YamlConfig::file('routes');
102 |
103 | $factory = new RouterFactory($url, $routes);
104 | $factory->create(\Magma\Router\Router::class)->buildRoutes();
105 | return $this;
106 | }
107 |
108 | }
--------------------------------------------------------------------------------
/.htaccess:
--------------------------------------------------------------------------------
1 | # Determine the RewriteBase automatically and set it as environment variable.
2 | # If you are using Apache aliases to do mass virtual hosting or installed the
3 | # project in a subdirectory, the base path will be prepended to allow proper
4 | # resolution of the index.php file and to redirect to the correct URI. It will
5 | # work in environments without path prefix as well, providing a safe, one-size
6 | # fits all solution. But as you do not need it in this case, you can comment
7 | # the following 2 lines to eliminate the overhead.
8 |
9 | # By default, Apache does not evaluate symbolic links if you did not enable this
10 | # feature in your server configuration. Uncomment the following line if you
11 | # install assets as symlinks or if you experience problems related to symlinks
12 | # when compiling LESS/Sass/CoffeScript assets.
13 | # Options FollowSymlinks
14 |
15 | # Disabling MultiViews prevents unwanted negotiation, e.g. "/index" should not resolve
16 | # to the front controller "/index.php" but be rewritten to "/index.php/index".
17 | # Remove the question mark from the request but maintain the query string
18 | RewriteEngine On
19 | RewriteBase /
20 |
21 | ## Begin - X-Forwarded-Proto
22 | # In some hosted or load balanced environments, SSL negotiation happens upstream.
23 | # In order for Lava-Studio to recognize the connection as secure, you need to uncomment
24 | # the following lines.
25 | #
26 | # RewriteCond %{HTTP:X-Forwarded-Proto} https
27 | # RewriteRule .* - [E=HTTPS:on]
28 | #
29 | ## End - X-Forwarded-Proto
30 |
31 | ## Begin - Index
32 | # If the requested filename exists, simply serve it.
33 | # We only want to let Apache serve files and not directories.
34 | # Rewrite all other queries to the front controller.
35 | # If the requested path and file is not /index.php and the request
36 | # has not already been internally rewritten to the index.php script
37 | # RewriteCond %{REQUEST_URI} !^/index\.php
38 | RewriteCond %{REQUEST_FILENAME} !-f
39 | RewriteCond %{REQUEST_FILENAME} !-d
40 | RewriteCond %{REQUEST_FILENAME} !-l
41 | RewriteRule ^(.*)$ index.php?$1 [L,QSA]
42 | ## End - Index
43 |
44 | ## Begin - Security
45 | # Block all direct access for these folders
46 | RewriteRule ^(\.git|bin|tmp|storage|webserver-configs|tests)/(.*) error [F]
47 | # Block access to specific file types for these system folders
48 | RewriteRule ^(core|vendor)/(.*)\.(txt|xml|md|html|yaml|yml|php|pl|py|cgi|twig|sh|bat)$ error [F]
49 | # Block access to specific file types for these user folders
50 | RewriteRule ^(public)/(.*)\.(txt|md|yaml|yml|php|pl|py|cgi|twig|sh|bat)$ error [F]
51 | # Block all direct access to .md files:
52 | RewriteRule \.md$ error [F]
53 | # Block all direct access to files and folders beginning with a dot
54 | RewriteRule (^|/)\.(?!well-known) - [F]
55 | # Block access to specific files in the root folder
56 | RewriteRule ^(LICENSE\.txt|composer\.lock|composer\.json|\.htaccess)$ error [F]
57 | ## End - Security
58 |
59 |
60 |
61 | # Begin - Prevent Browsing and Set Default Resources
62 | Options -Indexes
63 | DirectoryIndex index.php index.html index.htm
64 | # End - Prevent Browsing and Set Default Resources
65 |
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/EntityManager/CrudInterface.php:
--------------------------------------------------------------------------------
1 | options = $options;
26 |
27 | $this->iniSet();
28 | // Destroy any existing sessions started with session.auto_start
29 | if ($this->isSessionStarted()) {
30 | session_unset();
31 | session_destroy();
32 | }
33 | $this->start();
34 | }
35 |
36 | /**
37 | * Set the name of the session
38 | *
39 | * @param string $sessionName
40 | * @return void
41 | */
42 | public function setSessionName(string $sessionName) : void
43 | {
44 | session_name($sessionName);
45 | }
46 |
47 | /**
48 | * Return the current session name
49 | *
50 | * @return string
51 | */
52 | public function getSessionName() : string
53 | {
54 | return session_name();
55 | }
56 |
57 | /**
58 | * Set the name of the session ID
59 | *
60 | * @param $sessionID
61 | * @return void
62 | */
63 | public function setSessionID(string $sessionID) : void
64 | {
65 | session_id($sessionID);
66 | }
67 |
68 | /**
69 | * Return the current session ID
70 | *
71 | * @return string
72 | */
73 | public function getSessionID()
74 | {
75 | return session_id();
76 | }
77 |
78 | public function iniSet()
79 | {
80 | ini_set('session.gc_maxlifetime', $this->options['gc_maxlifetime']);
81 | ini_set('session.gc_divisor', $this->options['gc_divisor']);
82 | ini_set('session.gc_probability', $this->options['gc_probability']);
83 | ini_set('session.lifetime', $this->options['lifetime']);
84 | ini_set('session.use_cookies', $this->options['use_cookies']);
85 | }
86 |
87 | /**
88 | * Prevent session within the cli. Even though we can't run sessions within
89 | * the command line. also we checking we have a session id and its not empty
90 | * else return false
91 | *
92 | * @return bool
93 | */
94 | public function isSessionStarted()
95 | {
96 | return php_sapi_name() !== 'cli' ? $this->getSessionID() !=='' : false;
97 | }
98 |
99 | /**
100 | * Start our session if we haven't already have a php session
101 | *
102 | * @return void
103 | */
104 | public function startSession()
105 | {
106 | if (session_status() == PHP_SESSION_NONE)
107 | session_start();
108 | }
109 |
110 | /**
111 | * Define our session_set_cookie_params method via the $this->options parameters which
112 | * will be define within our core config directory
113 | *
114 | * @return void
115 | */
116 | public function start() : void
117 | {
118 | $this->setSessionName($this->options['session_name']);
119 | $domain = (isset($this->options['domain']) ? $this->options['domain'] : isset($_SERVER['SERVER_NAME']));
120 | $secure = (isset($this->options['secure']) ? $this->options['secure'] : isset($_SERVER['HTTPS']));
121 |
122 | session_set_cookie_params($this->options['lifetime'], $this->options['path'], $domain, $secure, $this->options['httponly']);
123 |
124 | $this->startSession();
125 | }
126 |
127 |
128 | }
--------------------------------------------------------------------------------
/src/Magma/Base/BaseController.php:
--------------------------------------------------------------------------------
1 | routeParams = $routeParams;
31 | $this->twig = new BaseView();
32 | }
33 |
34 | /**
35 | * Renders a view template from sub controller classes
36 | *
37 | * @param string $template
38 | * @param array $context
39 | * @return Response
40 | */
41 | public function render(string $template, array $context = [])
42 | {
43 | if ($this->twig === null) {
44 | throw new BaseLogicException('You cannot use the render method if the twig bundle is not available.');
45 | }
46 | return $this->twig->twigRender($template, $context);
47 | }
48 |
49 | /**
50 | * Magic method called when a non-existent or inaccessible method is
51 | * called on an object of this class. Used to execute before and after
52 | * filter methods on action methods. Action methods need to be named
53 | * with an "Action" suffix, e.g. indexAction, showAction etc.
54 | *
55 | * @param $name
56 | * @param $arguments
57 | * @throws BaseBadMethodCallException
58 | * @return void
59 | */
60 | public function __call($name, $arguments) : void
61 | {
62 | $method = $name . 'Action';
63 | if (method_exists($this, $method)) {
64 | if ($this->before() !== false) {
65 | call_user_func_array([$this, $method], $arguments);
66 | $this->after();
67 | }
68 | } else {
69 | throw new BaseBadMethodCallException('Method ' . $method . ' does not exist in ' . get_class($this));
70 | }
71 | }
72 |
73 | /**
74 | * Before method which is called before a controller method
75 | *
76 | * @return void
77 | */
78 | protected function before()
79 | {}
80 |
81 | /**
82 | * After method which is called after a controller method
83 | *
84 | * @return void
85 | */
86 | protected function after()
87 | {}
88 |
89 | /**
90 | * Method for allowing child controller class to dependency inject other objects
91 | * @param array $args
92 | * @return Object
93 | * @throws BaseInvalidArgumentException
94 | * @throws ReflectionException
95 | */
96 | public function create(array $args)
97 | {
98 | if (!is_array($args)) {
99 | throw new BaseInvalidArgumentException('Invalid argument');
100 | }
101 | $args = func_get_args();
102 | if ($args) {
103 | $output = '';
104 | foreach ($args as $arg) {
105 | foreach ($arg as $key => $class) {
106 | if (strpos($class, $arg[$key]) !== false) {
107 | if ($class) {
108 | $output = ($key === 'dataColumns' || $key === 'column') ? $this->$key = $class : $this->$key = $this->getReflection($class);
109 | }
110 | }
111 | }
112 | }
113 | return $output;
114 | }
115 | }
116 |
117 | /**
118 | * simple Dependency injection
119 | * @param $className
120 | * @return object
121 | * @throws ReflectionException
122 | */
123 | public function getReflection($className)
124 | {
125 | try{
126 | $reflector = new \ReflectionClass($className);
127 | $constructor = $reflector->getConstructor();
128 | if (!$constructor) return $reflector->newInstance();
129 |
130 | $dependencies = [];
131 | $params = $constructor->getParameters();
132 | foreach ($params as $param) {
133 | $paramType = $param->getClass();
134 | if ($paramType) {
135 | $dependencies[] = $this->getReflection($paramType->name);
136 | }
137 | }
138 | return $reflector->newInstanceArgs($dependencies);
139 | } catch (\ReflectionException $e) {
140 | throw $e;
141 | }
142 | }
143 |
144 | }
--------------------------------------------------------------------------------
/src/Magma/Router/Router.php:
--------------------------------------------------------------------------------
1 | [a-z-]+)', $route);
43 |
44 | // Convert variables with custom regular expressions e.g. {id:\d+}
45 | $route = preg_replace('/\{([a-z]+):([^\}]+)\}/', '(?P<\1>\2)', $route);
46 |
47 | // Add start and end delimiters, and case insensitive flag
48 | $route = '/^' . $route . '$/i';
49 |
50 | $this->routes[$route] = $params;
51 | }
52 |
53 | /**
54 | * @inheritDoc
55 | */
56 | public function dispatch(string $url) : void
57 | {
58 | $url = $this->formatQueryString($url);
59 | if ($this->match($url)) {
60 | $controllerString = $this->params['controller'] . $this->controllerSuffix;
61 | $controllerString = $this->transformUpperCamelCase($controllerString);
62 | $controllerString = $this->getNamespace($controllerString) . $controllerString;
63 |
64 | if (class_exists($controllerString)) {
65 | $controllerObject = new $controllerString($this->params);
66 | $action = $this->params['action'];
67 | $action = $this->transformCamelCase($action);
68 |
69 | if (\is_callable([$controllerObject, $action])) {
70 | $controllerObject->$action();
71 | } else {
72 | throw new BaseBadMethodCallException('Invalid method');
73 | }
74 | } else {
75 | throw new BaseBadFunctionCallException('Controller class does not exist');
76 | }
77 | } else {
78 | throw new BaseInvalidArgumentException('404 ERROR no page found');
79 | }
80 | }
81 |
82 | public function transformUpperCamelCase(string $string) : string
83 | {
84 | return str_replace(' ', '', ucwords(str_replace('-', ' ', $string)));
85 | }
86 |
87 | public function transformCamelCase(string $string) : string
88 | {
89 | return \lcfirst($this->transformUpperCamelCase($string));
90 | }
91 |
92 | /**
93 | * Match the route to the routes in the routing table, setting the $this->params property
94 | * if a route is found
95 | *
96 | * @param string $url
97 | * @return bool
98 | */
99 | private function match(string $url) : bool
100 | {
101 | foreach ($this->routes as $route => $params) {
102 | if (preg_match($route, $url, $matches)) {
103 | foreach ($matches as $key => $param) {
104 | if (is_string($key)) {
105 | $params[$key] = $param;
106 | }
107 | }
108 | $this->params = $params;
109 | return true;
110 | }
111 | }
112 | return false;
113 | }
114 |
115 | /**
116 | * Get the namespace for the controller class. the namespace difined within the route parameters
117 | * only if it was added.
118 | *
119 | * @param string $string
120 | * @return string
121 | */
122 | public function getNamespace(string $string) : string
123 | {
124 | $namespace = 'App\Controller\\';
125 | if (array_key_exists('namespace', $this->params)) {
126 | $namespace .= $this->params['namespace'] . '\\';
127 | }
128 | return $namespace;
129 | }
130 |
131 | /**
132 | */
133 | protected function formatQueryString($url)
134 | {
135 | if ($url != '') {
136 | $parts = explode('&', $url, 2);
137 |
138 | if (strpos($parts[0], '=') === false) {
139 | $url = $parts[0];
140 | } else {
141 | $url = '';
142 | }
143 | }
144 |
145 | return rtrim($url, '/');
146 | }
147 |
148 | public function getRoutes()
149 | {
150 | return $this->routes;
151 | }
152 |
153 |
154 | }
--------------------------------------------------------------------------------
/src/Magma/Session/Session.php:
--------------------------------------------------------------------------------
1 | isSessionKeyValid($sessionName) === false) {
35 | throw new BaseInvalidArgumentException($sessionName . ' is not a valid session name');
36 | }
37 |
38 | $this->sessionName = $sessionName;
39 | $this->storage = $storage;
40 | }
41 |
42 | /**
43 | * @inheritdoc
44 | *
45 | * @param string $key
46 | * @param mixed $value
47 | * @return void
48 | * @throws BaseException
49 | */
50 | public function set(string $key, $value) : void
51 | {
52 | $this->ensureSessionKeyIsValid($key);
53 | try{
54 | $this->storage->SetSession($key, $value);
55 | } catch(Throwable $throwable) {
56 | throw new BaseException('An exception was thrown in retrieving the key from the session storage. ' . $throwable);
57 | }
58 |
59 | }
60 |
61 | /**
62 | * @inheritdoc
63 | *
64 | * @param string $key
65 | * @param mixed $value
66 | * @return void
67 | * @throws BaseException
68 | */
69 | public function setArray(string $key, $value) : void
70 | {
71 | $this->ensureSessionKeyIsValid($key);
72 | try{
73 | $this->storage->setArraySession($key, $value);
74 | }catch(Throwable $throwable) {
75 | throw new BaseException('An exception was thrown in retrieving the key from the session storage. ' . $throwable);
76 | }
77 |
78 | }
79 |
80 | /**
81 | * @inheritdoc
82 | *
83 | * @param string $key
84 | * @param mixed $default
85 | * @return void
86 | * @throws BaseException
87 | */
88 | public function get(string $key, $default = null)
89 | {
90 | try{
91 | return $this->storage->getSession($key, $default);
92 | } catch(Throwable $throwable) {
93 | throw $throwable;
94 | }
95 | }
96 |
97 | /**
98 | * @inheritdoc
99 | *
100 | * @param string $key
101 | * @return boolean
102 | * @throws BaseException
103 | */
104 | public function delete(string $key) : bool
105 | {
106 | $this->ensureSessionKeyIsValid($key);
107 | try{
108 | $this->storage->deleteSession($key);
109 | }catch(Throwable $throwable) {
110 | throw $throwable;
111 | }
112 | return true;
113 | }
114 |
115 | /**
116 | * @inheritdoc
117 | *
118 | * @return void
119 | */
120 | public function invalidate() : void
121 | {
122 | $this->storage->invalidate();
123 | }
124 |
125 | /**
126 | * @inheritdoc
127 | *
128 | * @param string $key
129 | * @param [type] $value
130 | * @return void
131 | * @throws BaseException
132 | */
133 | public function flush(string $key, $value = null)
134 | {
135 | $this->ensureSessionKeyIsValid($key);
136 | try{
137 | $this->storage->flush($key, $value);
138 | }catch(Throwable $throwable) {
139 | throw $throwable;
140 | }
141 | }
142 |
143 | /**
144 | * @inheritdoc
145 | *
146 | * @param string $key
147 | * @return boolean
148 | * @throws SessiopnInvalidArgumentException
149 | */
150 | public function has(string $key) : bool
151 | {
152 | $this->ensureSessionKeyIsValid($key);
153 | return $this->storage->hasSession($key);
154 | }
155 |
156 | /**
157 | * Checks whether our session key is valid according the defined regular expression
158 | *
159 | * @param string $key
160 | * @return boolean
161 | */
162 | protected function isSessionKeyValid(string $key) : bool
163 | {
164 | return (preg_match(self::SESSION_PATTERN, $key) === 1);
165 | }
166 |
167 | /**
168 | * Checks whether we have session key
169 | *
170 | * @param string $key
171 | * @return void
172 | */
173 | protected function ensureSessionKeyIsvalid(string $key) : void
174 | {
175 | if ($this->isSessionKeyValid($key) === false) {
176 | throw new BaseInvalidArgumentException($key . ' is not a valid session key');
177 | }
178 | }
179 |
180 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/QueryBuilder/QueryBuilder.php:
--------------------------------------------------------------------------------
1 | key = $arg;
30 | return $this;
31 | }
32 |
33 | public function insertQuery() : string
34 | {
35 | if ($this->isQueryTypeValid('insert')) {
36 | if (is_array($this->key['fields']) && count($this->key['fields']) > 0) {
37 | $index = array_keys($this->key['fields']);
38 | $value = array(implode(', ', $index), ":" . implode(', :', $index));
39 | $this->sqlQuery = "INSERT INTO {$this->key['table']} ({$value[0]}) VALUES({$value[1]})";
40 | return $this->sqlQuery;
41 | }
42 | }
43 | return false;
44 | }
45 |
46 | public function selectQuery() : string
47 | {
48 | if ($this->isQueryTypeValid('select')) {
49 | $selectors = (!empty($this->key['selectors'])) ? implode(", ", $this->key['selectors']) : '*';
50 | if (isset($this->key['aggregate']) && $this->key['aggregate']) {
51 | $this->sqlQuery = "SELECT {$this->key['aggregate']}({$this->key['aggregate_field']}) FROM {$this->key['table']}";
52 | } else {
53 | $this->sqlQuery = "SELECT {$selectors} FROM {$this->key['table']}";
54 | }
55 | $this->sqlQuery = $this->hasConditions();
56 | return $this->sqlQuery;
57 |
58 | }
59 | return false;
60 | }
61 |
62 | public function updateQuery() : string
63 | {
64 | if ($this->isQueryTypeValid('update')) {
65 | if (is_array($this->key['fields']) && count($this->key['fields']) > 0) {
66 | $values = '';
67 | foreach ($this->key['fields'] as $field) {
68 | if ($field !== $this->key['primary_key']) {
69 | $values .= $field . " = :" . $field . ", ";
70 | }
71 | }
72 | $values = substr_replace($values, '', -2);
73 | if (count($this->key['fields']) > 0) {
74 | $this->sqlQuery = "UPDATE {$this->key['table']} SET {$values} WHERE {$this->key['primary_key']} = :{$this->key['primary_key']} LIMIT 1";
75 | if (isset($this->key['primary_key']) && $this->key['primary_key'] === '0') {
76 | unset($this->key['primary_key']);
77 | $this->sqlQuery = "UPDATE {$this->key['table']} SET {$values}";
78 | }
79 | }
80 | return $this->sqlQuery;
81 | }
82 | }
83 | return false;
84 | }
85 |
86 | public function deleteQuery() : string
87 | {
88 | if ($this->isQueryTypeValid('delete')) {
89 | $index = array_keys($this->key['conditions']);
90 | $this->sqlQuery = "DELETE FROM {$this->key['table']} WHERE {$index[0]} = :{$index[0]} LIMIT 1";
91 | $bulkDelete = array_values($this->key['fields']);
92 | if (is_array($bulkDelete) && count($bulkDelete) > 1) {
93 | for ($i = 0; $i < count($bulkDelete); $i++) {
94 | $this->sqlQuery = "DELETE FROM {$this->key['table']} WHERE {$index[0]} = :{$index[0]}";
95 | }
96 | }
97 |
98 | return $this->sqlQuery;
99 | }
100 | return false;
101 | }
102 |
103 | public function searchQuery() : string
104 | {
105 | if ($this->isQueryTypeValid('search ')) {
106 | if (is_array($this->key['selectors']) && $this->key['selectors'] != '') {
107 | $this->sqlQuery = "SELECT * FROM {$this->key['table']} WHERE ";
108 | if ($this->has('selectors')) {
109 | $values = [];
110 | foreach ($this->key['selectors'] as $selector) {
111 | $values[] = $selector . " LIKE " . "{$selector}";
112 | }
113 | if (count($this->key['selectors']) >= 1) {
114 | $this->sqlQuery .= implode(" OR ", $values);
115 | }
116 | }
117 | //$this->sqlQuery .= $this->orderByQuery();
118 | //$this->sqlQuery .= $this->queryOffset();
119 | }
120 | return $this->sqlQuery;
121 | }
122 | return false;
123 | }
124 |
125 | public function rawQuery(): string
126 | {
127 | if ($this->isQueryTypeValid('raw')) {
128 | $this->sqlQuery = $this->key['raw'];
129 |
130 | return $this->sqlQuery;
131 | }
132 | return false;
133 | }
134 |
135 | private function hasConditions()
136 | {
137 | if (isset($this->key['conditions']) && $this->key['conditions'] !='') {
138 | if (is_array($this->key['conditions'])) {
139 | $sort = [];
140 | foreach (array_keys($this->key['conditions']) as $where) {
141 | if (isset($where) && $where !='') {
142 | $sort[] = $where . " = :" . $where;
143 | }
144 | }
145 | if (count($this->key['conditions']) > 0) {
146 | $this->sqlQuery .= " WHERE " . implode(" AND ", $sort);
147 | }
148 | }
149 | } else if (empty($this->key['conditions'])) {
150 | $this->sqlQuery = " WHERE 1";
151 | }
152 | $this->sqlQuery .= $this->orderByQuery();
153 | $this->sqlQuery .= $this->queryOffset();
154 |
155 | return $this->sqlQuery;
156 | }
157 |
158 |
159 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataMapper/DataMapper.php:
--------------------------------------------------------------------------------
1 | dbh = $dbh;
35 | }
36 |
37 | /**
38 | * Check the incoming $valis isn't empty else throw an exception
39 | *
40 | * @param mixed $value
41 | * @param string|null $errorMessage
42 | * @return void
43 | * @throws DataMapperException
44 | */
45 | private function isEmpty($value, string $errorMessage = null)
46 | {
47 | if (empty($value)) {
48 | throw new BaseNoValueException($errorMessage);
49 | }
50 | }
51 |
52 | /**
53 | * Check the incoming argument $value is an array else throw an exception
54 | *
55 | * @param array $value
56 | * @return void
57 | * @throws BaseInvalidArgumentException
58 | */
59 | private function isArray(array $value)
60 | {
61 | if (!is_array($value)) {
62 | throw new BaseInvalidArgumentException('Your argument needs to be an array');
63 | }
64 | }
65 |
66 | /**
67 | * @inheritDoc
68 | */
69 | public function prepare(string $sqlQuery) : self
70 | {
71 | $this->isEmpty($sqlQuery);
72 | $this->statement = $this->dbh->open()->prepare($sqlQuery);
73 | return $this;
74 | }
75 |
76 | /**
77 | * @inheritDoc
78 | *
79 | * @param [type] $value
80 | * @return void
81 | */
82 | public function bind($value)
83 | {
84 | try {
85 | switch($value) {
86 | case is_bool($value) :
87 | case intval($value) :
88 | $dataType = PDO::PARAM_INT;
89 | break;
90 | case is_null($value) :
91 | $dataType = PDO::PARAM_NULL;
92 | break;
93 | default :
94 | $dataType = PDO::PARAM_STR;
95 | break;
96 | }
97 | return $dataType;
98 | } catch(BaseException $exception) {
99 | throw $exception;
100 | }
101 | }
102 |
103 | /**
104 | * @inheritDoc
105 | *
106 | * @param array $fields
107 | * @param boolean $isSearch
108 | * @return self
109 | */
110 | public function bindParameters(array $fields, bool $isSearch = false) : self
111 | {
112 | $this->isArray($fields);
113 | if (is_array($fields)) {
114 | $type = ($isSearch === false) ? $this->bindValues($fields) : $this->bindSearchValues($fields);
115 | if ($type) {
116 | return $this;
117 | }
118 | }
119 | return false;
120 | }
121 |
122 | /**
123 | * Binds a value to a corresponding name or question mark placeholder in the SQL
124 | * statement that was used to prepare the statement
125 | *
126 | * @param array $fields
127 | * @return PDOStatement
128 | * @throws BaseInvalidArgumentException
129 | */
130 | protected function bindValues(array $fields) : PDOStatement
131 | {
132 | $this->isArray($fields); // don't need
133 | foreach ($fields as $key => $value) {
134 | $this->statement->bindValue(':' . $key, $value, $this->bind($value));
135 | }
136 | return $this->statement;
137 | }
138 |
139 | /**
140 | * Binds a value to a corresponding name or question mark placeholder
141 | * in the SQL statement that was used to prepare the statement. Similar to
142 | * above but optimised for search queries
143 | *
144 | * @param array $fields
145 | * @return mixed
146 | * @throws BaseInvalidArgumentException
147 | */
148 | protected function bindSearchValues(array $fields) : PDOStatement
149 | {
150 | $this->isArray($fields); // don't need
151 | foreach ($fields as $key => $value) {
152 | $this->statement->bindValue(':' . $key, '%' . $value . '%', $this->bind($value));
153 | }
154 | return $this->statement;
155 | }
156 |
157 | /**
158 | * @inheritDoc
159 | *
160 | * @return void
161 | */
162 | public function execute()
163 | {
164 | if ($this->statement)
165 | return $this->statement->execute();
166 | }
167 | /**
168 | * @inheritDoc
169 | *
170 | * @return integer
171 | */
172 | public function numRows() : int
173 | {
174 | if ($this->statement) return $this->statement->rowCount();
175 | }
176 | /**
177 | * @inheritDoc
178 | *
179 | * @return Object
180 | */
181 | public function result() : Object
182 | {
183 | if ($this->statement) return $this->statement->fetch(PDO::FETCH_OBJ);
184 | }
185 | /**
186 | * @inheritDoc
187 | *
188 | * @return array
189 | */
190 | public function results() : array
191 | {
192 | if ($this->statement) return $this->statement->fetchAll();
193 | }
194 |
195 | /**
196 | * @inheritDoc
197 | */
198 | public function column()
199 | {
200 | if ($this->statement) return $this->statement->fetchColumn();
201 | }
202 |
203 | /**
204 | * @inheritDoc
205 | *
206 | * @return integer
207 | */
208 | public function getLastId() : int
209 | {
210 | try {
211 | if ($this->dbh->open()) {
212 | $lastID = $this->dbh->open()->lastInsertId();
213 | if (!empty($lastID)) {
214 | return intval($lastID);
215 | }
216 | }
217 | }catch(Throwable $throwable) {
218 | throw $throwable;
219 | }
220 | }
221 |
222 | /**
223 | * Returns the query condition merged with the query parameters
224 | *
225 | * @param array $conditions
226 | * @param array $parameters
227 | * @return array
228 | */
229 | public function buildQueryParameters(array $conditions = [], array $parameters = []) : array
230 | {
231 | return (!empty($parameters) || (!empty($conditions)) ? array_merge($conditions, $parameters) : $parameters);
232 | }
233 |
234 | /**
235 | * Persist queries to database
236 | *
237 | * @param string $query
238 | * @param array $parameters
239 | * @return mixed
240 | * @throws Throwable
241 | */
242 | public function persist(string $sqlQuery, array $parameters)
243 | {
244 | try {
245 | return $this->prepare($sqlQuery)->bindParameters($parameters)->execute();
246 | } catch(Throwable $throwable){
247 | throw $throwable;
248 | }
249 | }
250 | }
--------------------------------------------------------------------------------
/src/Magma/Datatable/Datatable.php:
--------------------------------------------------------------------------------
1 | dataColumnObject = new $dataColumnString();
29 | if (!$this->dataColumnObject instanceof DatatableColumnInterface) {
30 | throw new BaseUnexpectedValueException($dataColumnString . ' is not a valid data column object.');
31 | }
32 | $this->dataColumns = $this->dataColumnObject->columns();
33 | $this->sortController = $sortController;
34 | $this->getRepositoryParts($dataRepository);
35 | return $this;
36 |
37 | }
38 |
39 | private function getRepositoryParts(array $dataRepository) : void
40 | {
41 | list($this->dataOptions, $this->currentPage, $this->totalPages, $this->totalRecords, $this->direction, $this->sortDirection, $this->tdClass, $this->tableColumn, $this->tableOrder) = $dataRepository;
42 | }
43 |
44 | public function table() : ?string
45 | {
46 | extract($this->attr, EXTR_SKIP);
47 | $this->element .= $before;
48 | if (is_array($this->dataColumns) && count($this->dataColumns) > 0) {
49 | if (is_array($this->dataOptions) && $this->dataOptions !=null) {
50 | $this->element .= '' . "\n";
51 | $this->element .= ($show_table_thead) ? $this->tableGridElements($status) : false;
52 | $this->element .= '' . "\n";
53 | foreach ($this->dataOptions as $row) {
54 | $this->element .= '' . "\n";
55 | foreach ($this->dataColumns as $column) {
56 | if (isset($column['show_column']) && $column['show_column'] != false) {
57 | $this->element .= '| ';
58 | if (is_callable($column['formatter'])) {
59 | $this->element .= call_user_func_array($column['formatter'], [$row]);
60 | } else {
61 | $this->element .= (isset($row[$column['db_row']]) ? $row[$column['db_row']] : '');
62 | }
63 | $this->element .= ' | ' . "\n";
64 | }
65 | }
66 | $this->element .= '
' . "\n";
67 | }
68 | $this->element .= '' . "\n";
69 | //$this->element .= ($show_table_tfoot) ? $this->tableGridElements($status, true) : '';
70 | $this->element .= '
' . "\n";
71 | }
72 | }
73 | $this->element .= $after;
74 |
75 | return $this->element;
76 |
77 | }
78 |
79 | protected function tableGridElements(string $status, bool $inFoot = false) : string
80 | {
81 | $element = sprintf('<%s>', ($inFoot) ? 'tfoot' : 'thead');
82 | $element .= '';
83 | foreach ($this->dataColumns as $column) {
84 | if (isset($column['show_column']) && $column['show_column'] != false) {
85 | $element .= '| ';
86 | $element .= $this->tableSorting($column, $status);
87 | $element .= ' | ';
88 | }
89 | }
90 | $element .= '
';
91 | $element .= sprintf('%s>', ($inFoot) ? 'tfoot' : 'thead');
92 |
93 | return $element;
94 | }
95 |
96 | private function tableSorting(array $column, string $status) : string
97 | {
98 | $element = '';
99 | if (isset($column['sortable']) && $column['sortable'] != false) {
100 | $element .= '';
101 | $element .= $column['dt_row'];
102 | $element .= '';
103 | $element .= '';
104 | } else {
105 | $element .= $column['dt_row'];
106 | }
107 | return $element;
108 | }
109 |
110 | public function pagination() : string
111 | {
112 | extract($this->attr, EXTR_SKIP);
113 |
114 | $element = '';
115 | $element .= '';
193 | $element .= '';
194 |
195 | return $element;
196 | }
197 |
198 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/EntityManager/Crud.php:
--------------------------------------------------------------------------------
1 | dataMapper = $dataMapper;
43 | $this->queryBuilder = $queryBuilder;
44 | $this->tableSchema = $tableSchema;
45 | $this->tableSchemaID = $tableSchemaID;
46 | $this->options = $options;
47 | }
48 |
49 | /**
50 | * @inheritdoc
51 | *
52 | * @return string
53 | */
54 | public function getSchema() : string
55 | {
56 | return (string)$this->tableSchema;
57 | }
58 |
59 | /**
60 | * @inheritdoc
61 | *
62 | * @return string
63 | */
64 | public function getSchemaID() : string
65 | {
66 | return (string)$this->tableSchemaID;
67 | }
68 |
69 | /**
70 | * @inheritdoc
71 | *
72 | * @return integer
73 | */
74 | public function lastID() : int
75 | {
76 | return $this->dataMapper->getLastId();
77 | }
78 |
79 | /**
80 | * @inheritdoc
81 | *
82 | * @param array $fields
83 | * @return boolean
84 | */
85 | public function create(array $fields = []) : bool
86 | {
87 | try {
88 | $args = ['table' => $this->getSchema(), 'type' => 'insert', 'fields' => $fields];
89 | $query = $this->queryBuilder->buildQuery($args)->insertQuery();
90 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($fields));
91 | if ($this->dataMapper->numRows() ==1) {
92 | return true;
93 | }
94 | } catch(Throwable $throwable) {
95 | throw $throwable;
96 | }
97 | }
98 |
99 | /**
100 | * @inheritdoc
101 | *
102 | * @param array $selectors
103 | * @param array $conditions
104 | * @param array $parameters
105 | * @param array $optional
106 | * @return array
107 | */
108 | public function read(array $selectors = [], array $conditions = [], array $parameters = [], array $optional = []) : array
109 | {
110 | //try{
111 | $args = ['table' => $this->getSchema(), 'type' => 'select', 'selectors' => $selectors, 'conditions' => $conditions, 'params' => $parameters, 'extras' => $optional];
112 | $query = $this->queryBuilder->buildQuery($args)->selectQuery();
113 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($conditions, $parameters));
114 | if ($this->dataMapper->numRows() >= 0) {
115 | return $this->dataMapper->results();
116 | }
117 | //} catch(Throwable $throwable) {
118 | //throw $throwable;
119 | //}
120 | }
121 |
122 | /**
123 | * @inheritdoc
124 | *
125 | * @param array $fields
126 | * @param string $primaryKey
127 | * @return boolean
128 | */
129 | public function update(array $fields = [], string $primaryKey) : bool
130 | {
131 | try {
132 | $args = ['table' => $this->getSchema(), 'type' => 'update', 'fields' => $fields, 'primary_key' => $primaryKey];
133 | $query = $this->queryBuilder->buildQuery($args)->updateQuery();
134 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($fields));
135 | if ($this->dataMapper->numRows() == 1) {
136 | return true;
137 | }
138 | }catch(Throwable $throwable) {
139 | throw $throwable;
140 | }
141 | }
142 |
143 | /**
144 | * @inheritdoc
145 | *
146 | * @param array $conditions
147 | * @return boolean
148 | */
149 | public function delete(array $conditions = []) : bool
150 | {
151 | try {
152 | $args = ['table' => $this->getSchema(), 'type' => 'delete', 'conditions' => $conditions];
153 | $query = $this->queryBuilder->buildQuery($args)->deleteQuery();
154 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($conditions));
155 | if ($this->dataMapper->numRows() == 1) {
156 | return true;
157 | }
158 | }catch(Throwable $throwable) {
159 | throw $throwable;
160 | }
161 | }
162 |
163 | /**
164 | * @inheritdoc
165 | *
166 | * @param array $selectors
167 | * @param array $conditions
168 | * @return array
169 | */
170 | public function search(array $selectors = [], array $conditions = []) : array
171 | {
172 | try {
173 | $args = ['table' => $this->getSchema(), 'type' => 'search', 'selectors' => $selectors, 'conditions' => $conditions];
174 | $query = $this->queryBuilder->buildQuery($args)->searchQuery();
175 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($conditions));
176 | if ($this->dataMapper->numRows() >= 0) {
177 | return $this->dataMapper->results();
178 | }
179 | }catch(Throwable $throwable) {
180 | throw $throwable;
181 | }
182 | }
183 |
184 | /**
185 | * @inheritDoc
186 | *
187 | * @param array $selectors
188 | * @param array $conditions
189 | * @return Object|null
190 | */
191 | public function get(array $selectors = [], array $conditions = []) : ?Object
192 | {
193 | $args = ['table' => $this->getSchema(), 'type' => 'select', 'selectors' => $selectors, 'conditions' => $conditions];
194 | $query = $this->queryBuilder->buildQuery($args)->selectQuery();
195 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($conditions));
196 | if ($this->dataMapper->numRows() >= 0) {
197 | return $this->dataMapper->result();
198 | }
199 | }
200 |
201 | /**
202 | * @inheritDoc
203 | * @throws Throwable
204 | */
205 | public function aggregate(string $type, ?string $field = 'id', array $conditions = [])
206 | {
207 | $args = ['table' => $this->getSchema(), 'primary_key'=>$this->getSchemaID(),
208 | 'type' => 'select', 'aggregate' => $type, 'aggregate_field' => $field,
209 | 'conditions' => $conditions];
210 |
211 | $query = $this->queryBuilder->buildQuery($args)->selectQuery();
212 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($conditions));
213 | if ($this->dataMapper->numRows() > 0)
214 | return $this->dataMapper->column();
215 | }
216 |
217 | /**
218 | * @inheritDoc
219 | * @throws Throwable
220 | */
221 | public function countRecords(array $conditions = [], ?string $field = 'id') : int
222 | {
223 | if ($this->getSchemaID() !='') {
224 | return empty($conditions) ? $this->aggregate('count', $this->getSchemaID()) : $this->aggregate('count', $this->getSchemaID(), $conditions);
225 | }
226 | }
227 |
228 | /**
229 | * @inheritDoc
230 | *
231 | * @param string $sqlQuery
232 | * @param array|null $conditions
233 | * @param string $resultType
234 | * @return void
235 | */
236 | public function rawQuery(string $sqlQuery, ?array $conditions = [], string $resultType = 'column')
237 | {
238 | /*$args = ['table' => $this->getSchema(), 'type' => 'raw', 'conditions' => $conditions, 'raw' => $sqlQuery];
239 | $query = $this->queryBuilder->buildQuery($args)->rawQuery();
240 | $this->dataMapper->persist($query, $this->dataMapper->buildQueryParameters($conditions));
241 | if ($this->dataMapper->numRows()) {
242 | if (!in_array($resultType, ['fetch', 'fetch_all', 'column'])) {
243 | throw new BaseInvalidArgumentException('Invalid 3rd argument. Your options are "fetch, fetch_all or column"');
244 | }
245 | switch ($resultType) {
246 | case 'column' :
247 | //$data = $this->dataMapper->column(); not implemented yet!
248 | break;
249 | case 'fetch' :
250 | $data = $this->dataMapper->result();
251 | break;
252 | case 'fetch_all' :
253 | $data = $this->dataMapper->results();
254 | break;
255 | default :
256 | throw new BaseUnexpectedValueException('Please choose a return type for this method ie. "fetch, fetch_all or column."');
257 | break;
258 | }
259 | if ($data) {
260 | return $data;
261 | }
262 | }*/
263 |
264 | }
265 |
266 |
267 | }
--------------------------------------------------------------------------------
/src/Magma/LiquidOrm/DataRepository/DataRepository.php:
--------------------------------------------------------------------------------
1 | em = $em;
22 | }
23 |
24 | /**
25 | * Checks whether the arguement is of the array type else throw an exception
26 | *
27 | * @param array $conditions
28 | * @return void
29 | */
30 | private function isArray(array $conditions) : void
31 | {
32 | if (!is_array($conditions))
33 | throw new BaseInvalidArgumentException('The argument supplied is not an array');
34 | }
35 |
36 | /**
37 | * Checks whether the argument is set else throw an exception
38 | *
39 | * @param integer $id
40 | * @return void
41 | */
42 | private function isEmpty(int $id) : void
43 | {
44 | if (empty($id))
45 | throw new BaseInvalidArgumentException('Argument should not be empty');
46 | }
47 |
48 | /**
49 | * @inheritDoc
50 | *
51 | * @param integer $id
52 | * @return array
53 | * @throws BaseInvalidArgumentException
54 | */
55 | public function find(int $id) : array
56 | {
57 | $this->isEmpty($id);
58 | try{
59 | return $this->findOneBy(['id' => $id]);
60 | }catch(Throwable $throwable) {
61 | throw $throwable;
62 | }
63 | }
64 |
65 | /**
66 | * @inheritDoc
67 | *
68 | * @return array
69 | */
70 | public function findAll() : array
71 | {
72 | try{
73 | return $this->findBy();
74 | }catch(Throwable $throwable) {
75 | throw $throwable;
76 | }
77 | }
78 |
79 | /**
80 | * @inheritDoc
81 | *
82 | * @param array $selectors
83 | * @param array $conditions
84 | * @param array $parameters
85 | * @param array $optional
86 | * @return array
87 | */
88 | public function findBy(array $selectors = [], array $conditions = [], array $parameters = [], array $optional = []) : array
89 | {
90 | try{
91 | return $this->em->getCrud()->read($selectors, $conditions, $parameters, $optional);
92 | }catch(Throwable $throwable) {
93 | throw $throwable;
94 | }
95 | }
96 |
97 | /**
98 | * @inheritDoc
99 | *
100 | * @param array $conditions
101 | * @return array
102 | * @throws BaseInvalidArgumentException
103 | */
104 | public function findOneBy(array $conditions) : array
105 | {
106 | $this->isArray($conditions);
107 | try{
108 | return $this->em->getCrud()->read([], $conditions);
109 | }catch(Throwable $throwable) {
110 | throw $throwable;
111 | }
112 | }
113 |
114 | /**
115 | * @inheritDoc
116 | *
117 | * @param array $conditions
118 | * @param array $selectors
119 | * @return Object
120 | */
121 | public function findObjectBy(array $conditions = [], array $selectors = []) : Object
122 | {
123 | $this->isArray($conditions);
124 | try{
125 | return $this->em->getCrud()->get($selectors, $conditions);
126 | } catch(Throwable $throwable) {
127 | throw $throwable;
128 | }
129 | }
130 |
131 | /**
132 | * @inheritDoc
133 | *
134 | * @param array $selectors
135 | * @param array $conditions
136 | * @param array $parameters
137 | * @param array $optional
138 | * @return array
139 | * @throws BaseInvalidArgumentException
140 | */
141 | public function findBySearch(array $selectors = [], array $conditions = [], array $parameters = [], array $optional = []) : array
142 | {
143 | $this->isArray($conditions);
144 | try{
145 | return $this->em->getCrud()->search($selectors, $conditions, $parameters, $optional);
146 | }catch(Throwable $throwable) {
147 | throw $throwable;
148 | }
149 | }
150 |
151 | /**
152 | * @inheritDoc
153 | *
154 | * @param array $conditions
155 | * @return boolean
156 | * @throws BaseInvalidArgumentException
157 | */
158 | public function findByIdAndDelete(array $conditions) : bool
159 | {
160 | $this->isArray($conditions);
161 | try{
162 | $result = $this->findOneBy($conditions);
163 | if ($result !=null && count($result) > 0) {
164 | $delete = $this->em->getCrud()->delete($conditions);
165 | if ($delete) {
166 | return true;
167 | }
168 | }
169 | }catch(Throwable $throwable) {
170 | throw $throwable;
171 | }
172 | }
173 |
174 | /**
175 | * @inheritDoc
176 | *
177 | * @param array $fields
178 | * @param integer $id
179 | * @return boolean
180 | * @throws BaseInvalidArgumentException
181 | */
182 | public function findByIdAndUpdate(array $fields = [], int $id) : bool
183 | {
184 | $this->isArray($fields);
185 | try{
186 | $result = $this->findOneBy([$this->em->getCrud()->getSchemaID() => $id]);
187 | if ($result !=null && count($result) > 0) {
188 | $params = (!empty($fields)) ? array_merge([$this->em->getCrud()->getSchemaID() => $id], $fields) : $fields;
189 | $update = $this->em->getCrud()->update($params, $this->em->getCrud()->getSchemaID());
190 | if ($update) {
191 | return true;
192 | }
193 | }
194 | }catch(Throwable $throwable) {
195 | throw $throwable;
196 | }
197 | }
198 |
199 | /**
200 | * @inheritDoc
201 | *
202 | * @param array $args
203 | * @param Object $request
204 | * @return array
205 | */
206 | public function findWithSearchAndPaging(Object $request, array $args = []) : array
207 | {
208 | list($conditions, $totalRecords) = $this->getCurrentQueryStatus($request, $args);
209 | $sorting = new Sortable($args['sort_columns']);
210 | $paging = new Paginator($totalRecords, $args['records_per_page'], $request->query->getInt('page', 1));
211 |
212 | $parameters = ['limit' => $args['records_per_page'], 'offset' => $paging->getOffset()];
213 | $optional = ['orderby' => $sorting->getColumn() . ' ' . $sorting->getDirection()];
214 |
215 | if ($request->query->getAlnum($args['filter_alias'])) {
216 | $searchRequest = $request->query->getAlnum($args['filter_alias']);
217 | if (is_array($args['filter_by'])) {
218 | for ($i=0; $i < count($args['filter_by']); $i++) {
219 | $searchConditions = [$args['filter_by'][$i] => $searchRequest];
220 | }
221 | }
222 | $results = $this->findBySearch($args['filter_by'], $searchConditions);
223 | } else {
224 | $queryConditions = array_merge($args['additional_conditions'], $conditions);
225 | $results = $this->findBy($args['selectors'], $queryConditions, $parameters, $optional);
226 | }
227 | return [
228 | $results,
229 | $paging->getPage(),
230 | $paging->getTotalPages(),
231 | $totalRecords,
232 | $sorting->sortDirection(),
233 | $sorting->sortDescAsc(),
234 | $sorting->getClass(),
235 | $sorting->getColumn(),
236 | $sorting->getDirection()
237 | ];
238 | }
239 |
240 | private function getCurrentQueryStatus(Object $request, array $args)
241 | {
242 | $totalRecords = 0;
243 | $req = $request->query;
244 | $status = $req->getAlnum($args['query']);
245 | $searchResults = $req->getAlnum($args['filter_alias']);
246 | if ($searchResults) {
247 | for ($i=0; $i < count($args['filter_by']); $i++) {
248 | $conditions = [$args['filter_by'][$i] => $searchResults];
249 | $totalRecords = $this->em->getCrud()->countRecords($conditions, $args['filter_by'][$i]);
250 | }
251 | } else if ($status) {
252 | $conditions = [$args['query'] => $status];
253 | $totalRecords = $this->em->getCrud()->countRecords($conditions);
254 | } else {
255 | $conditions = [];
256 | $totalRecords = $this->em->getCrud()->countRecords($conditions);
257 | }
258 | return [
259 | $conditions,
260 | $totalRecords
261 | ];
262 | }
263 |
264 |
265 | /**
266 | * @inheritDoc
267 | *
268 | * @param integer $id
269 | * @param array $selectors
270 | * @return self
271 | */
272 | public function findAndReturn(int $id, array $selectors = []) : self
273 | {
274 | if (empty($id) || $id === 0) {
275 | throw new BaseInvalidArgumentException('Please add a valid argument');
276 | }
277 | try {
278 | $this->findAndReturn = $this->findObjectBy($selectors, ['id' => $id]);
279 | return $this;
280 | }catch(Throwable $throwable) {
281 | throw $throwable;
282 | }
283 | }
284 |
285 | /**
286 | * @inheritDoc
287 | *
288 | * @return Object|null
289 | * @throws LoaderError
290 | * @throws RuntimeError
291 | * @throws SyntaxError
292 | */
293 | public function or404()
294 | {
295 | if ($this->findAndReturn !=null) {
296 | return $this->findAndReturn;
297 | } else {
298 | header('HTTP/1.1 404 not found');
299 | $twig = new \Magma\Base\BaseView();
300 | $twig->twigRender('error/404.html.twig');
301 | exit;
302 | }
303 | }
304 |
305 |
306 | }
--------------------------------------------------------------------------------
/composer.lock:
--------------------------------------------------------------------------------
1 | {
2 | "_readme": [
3 | "This file locks the dependencies of your project to a known state",
4 | "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#installing-dependencies",
5 | "This file is @generated automatically"
6 | ],
7 | "content-hash": "817ebe3920444c7b37b87cb98af0fb31",
8 | "packages": [
9 | {
10 | "name": "symfony/deprecation-contracts",
11 | "version": "v2.2.0",
12 | "source": {
13 | "type": "git",
14 | "url": "https://github.com/symfony/deprecation-contracts.git",
15 | "reference": "5fa56b4074d1ae755beb55617ddafe6f5d78f665"
16 | },
17 | "dist": {
18 | "type": "zip",
19 | "url": "https://api.github.com/repos/symfony/deprecation-contracts/zipball/5fa56b4074d1ae755beb55617ddafe6f5d78f665",
20 | "reference": "5fa56b4074d1ae755beb55617ddafe6f5d78f665",
21 | "shasum": ""
22 | },
23 | "require": {
24 | "php": ">=7.1"
25 | },
26 | "type": "library",
27 | "extra": {
28 | "branch-alias": {
29 | "dev-master": "2.2-dev"
30 | },
31 | "thanks": {
32 | "name": "symfony/contracts",
33 | "url": "https://github.com/symfony/contracts"
34 | }
35 | },
36 | "autoload": {
37 | "files": [
38 | "function.php"
39 | ]
40 | },
41 | "notification-url": "https://packagist.org/downloads/",
42 | "license": [
43 | "MIT"
44 | ],
45 | "authors": [
46 | {
47 | "name": "Nicolas Grekas",
48 | "email": "p@tchwork.com"
49 | },
50 | {
51 | "name": "Symfony Community",
52 | "homepage": "https://symfony.com/contributors"
53 | }
54 | ],
55 | "description": "A generic function and convention to trigger deprecation notices",
56 | "homepage": "https://symfony.com",
57 | "support": {
58 | "source": "https://github.com/symfony/deprecation-contracts/tree/master"
59 | },
60 | "funding": [
61 | {
62 | "url": "https://symfony.com/sponsor",
63 | "type": "custom"
64 | },
65 | {
66 | "url": "https://github.com/fabpot",
67 | "type": "github"
68 | },
69 | {
70 | "url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
71 | "type": "tidelift"
72 | }
73 | ],
74 | "time": "2020-09-07T11:33:47+00:00"
75 | },
76 | {
77 | "name": "symfony/http-foundation",
78 | "version": "v5.2.0-RC2",
79 | "source": {
80 | "type": "git",
81 | "url": "https://github.com/symfony/http-foundation.git",
82 | "reference": "ba0aeb1f49a2e687446fb82b828e957dfd999fe1"
83 | },
84 | "dist": {
85 | "type": "zip",
86 | "url": "https://api.github.com/repos/symfony/http-foundation/zipball/ba0aeb1f49a2e687446fb82b828e957dfd999fe1",
87 | "reference": "ba0aeb1f49a2e687446fb82b828e957dfd999fe1",
88 | "shasum": ""
89 | },
90 | "require": {
91 | "php": ">=7.2.5",
92 | "symfony/deprecation-contracts": "^2.1",
93 | "symfony/polyfill-mbstring": "~1.1",
94 | "symfony/polyfill-php80": "^1.15"
95 | },
96 | "require-dev": {
97 | "predis/predis": "~1.0",
98 | "symfony/cache": "^4.4|^5.0",
99 | "symfony/expression-language": "^4.4|^5.0",
100 | "symfony/mime": "^4.4|^5.0"
101 | },
102 | "suggest": {
103 | "symfony/mime": "To use the file extension guesser"
104 | },
105 | "type": "library",
106 | "autoload": {
107 | "psr-4": {
108 | "Symfony\\Component\\HttpFoundation\\": ""
109 | },
110 | "exclude-from-classmap": [
111 | "/Tests/"
112 | ]
113 | },
114 | "notification-url": "https://packagist.org/downloads/",
115 | "license": [
116 | "MIT"
117 | ],
118 | "authors": [
119 | {
120 | "name": "Fabien Potencier",
121 | "email": "fabien@symfony.com"
122 | },
123 | {
124 | "name": "Symfony Community",
125 | "homepage": "https://symfony.com/contributors"
126 | }
127 | ],
128 | "description": "Symfony HttpFoundation Component",
129 | "homepage": "https://symfony.com",
130 | "support": {
131 | "source": "https://github.com/symfony/http-foundation/tree/v5.2.0-RC2"
132 | },
133 | "funding": [
134 | {
135 | "url": "https://symfony.com/sponsor",
136 | "type": "custom"
137 | },
138 | {
139 | "url": "https://github.com/fabpot",
140 | "type": "github"
141 | },
142 | {
143 | "url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
144 | "type": "tidelift"
145 | }
146 | ],
147 | "time": "2020-11-20T17:25:36+00:00"
148 | },
149 | {
150 | "name": "symfony/polyfill-ctype",
151 | "version": "v1.20.0",
152 | "source": {
153 | "type": "git",
154 | "url": "https://github.com/symfony/polyfill-ctype.git",
155 | "reference": "f4ba089a5b6366e453971d3aad5fe8e897b37f41"
156 | },
157 | "dist": {
158 | "type": "zip",
159 | "url": "https://api.github.com/repos/symfony/polyfill-ctype/zipball/f4ba089a5b6366e453971d3aad5fe8e897b37f41",
160 | "reference": "f4ba089a5b6366e453971d3aad5fe8e897b37f41",
161 | "shasum": ""
162 | },
163 | "require": {
164 | "php": ">=7.1"
165 | },
166 | "suggest": {
167 | "ext-ctype": "For best performance"
168 | },
169 | "type": "library",
170 | "extra": {
171 | "branch-alias": {
172 | "dev-main": "1.20-dev"
173 | },
174 | "thanks": {
175 | "name": "symfony/polyfill",
176 | "url": "https://github.com/symfony/polyfill"
177 | }
178 | },
179 | "autoload": {
180 | "psr-4": {
181 | "Symfony\\Polyfill\\Ctype\\": ""
182 | },
183 | "files": [
184 | "bootstrap.php"
185 | ]
186 | },
187 | "notification-url": "https://packagist.org/downloads/",
188 | "license": [
189 | "MIT"
190 | ],
191 | "authors": [
192 | {
193 | "name": "Gert de Pagter",
194 | "email": "BackEndTea@gmail.com"
195 | },
196 | {
197 | "name": "Symfony Community",
198 | "homepage": "https://symfony.com/contributors"
199 | }
200 | ],
201 | "description": "Symfony polyfill for ctype functions",
202 | "homepage": "https://symfony.com",
203 | "keywords": [
204 | "compatibility",
205 | "ctype",
206 | "polyfill",
207 | "portable"
208 | ],
209 | "support": {
210 | "source": "https://github.com/symfony/polyfill-ctype/tree/v1.20.0"
211 | },
212 | "funding": [
213 | {
214 | "url": "https://symfony.com/sponsor",
215 | "type": "custom"
216 | },
217 | {
218 | "url": "https://github.com/fabpot",
219 | "type": "github"
220 | },
221 | {
222 | "url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
223 | "type": "tidelift"
224 | }
225 | ],
226 | "time": "2020-10-23T14:02:19+00:00"
227 | },
228 | {
229 | "name": "symfony/polyfill-mbstring",
230 | "version": "v1.20.0",
231 | "source": {
232 | "type": "git",
233 | "url": "https://github.com/symfony/polyfill-mbstring.git",
234 | "reference": "39d483bdf39be819deabf04ec872eb0b2410b531"
235 | },
236 | "dist": {
237 | "type": "zip",
238 | "url": "https://api.github.com/repos/symfony/polyfill-mbstring/zipball/39d483bdf39be819deabf04ec872eb0b2410b531",
239 | "reference": "39d483bdf39be819deabf04ec872eb0b2410b531",
240 | "shasum": ""
241 | },
242 | "require": {
243 | "php": ">=7.1"
244 | },
245 | "suggest": {
246 | "ext-mbstring": "For best performance"
247 | },
248 | "type": "library",
249 | "extra": {
250 | "branch-alias": {
251 | "dev-main": "1.20-dev"
252 | },
253 | "thanks": {
254 | "name": "symfony/polyfill",
255 | "url": "https://github.com/symfony/polyfill"
256 | }
257 | },
258 | "autoload": {
259 | "psr-4": {
260 | "Symfony\\Polyfill\\Mbstring\\": ""
261 | },
262 | "files": [
263 | "bootstrap.php"
264 | ]
265 | },
266 | "notification-url": "https://packagist.org/downloads/",
267 | "license": [
268 | "MIT"
269 | ],
270 | "authors": [
271 | {
272 | "name": "Nicolas Grekas",
273 | "email": "p@tchwork.com"
274 | },
275 | {
276 | "name": "Symfony Community",
277 | "homepage": "https://symfony.com/contributors"
278 | }
279 | ],
280 | "description": "Symfony polyfill for the Mbstring extension",
281 | "homepage": "https://symfony.com",
282 | "keywords": [
283 | "compatibility",
284 | "mbstring",
285 | "polyfill",
286 | "portable",
287 | "shim"
288 | ],
289 | "support": {
290 | "source": "https://github.com/symfony/polyfill-mbstring/tree/v1.20.0"
291 | },
292 | "funding": [
293 | {
294 | "url": "https://symfony.com/sponsor",
295 | "type": "custom"
296 | },
297 | {
298 | "url": "https://github.com/fabpot",
299 | "type": "github"
300 | },
301 | {
302 | "url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
303 | "type": "tidelift"
304 | }
305 | ],
306 | "time": "2020-10-23T14:02:19+00:00"
307 | },
308 | {
309 | "name": "symfony/polyfill-php80",
310 | "version": "v1.20.0",
311 | "source": {
312 | "type": "git",
313 | "url": "https://github.com/symfony/polyfill-php80.git",
314 | "reference": "e70aa8b064c5b72d3df2abd5ab1e90464ad009de"
315 | },
316 | "dist": {
317 | "type": "zip",
318 | "url": "https://api.github.com/repos/symfony/polyfill-php80/zipball/e70aa8b064c5b72d3df2abd5ab1e90464ad009de",
319 | "reference": "e70aa8b064c5b72d3df2abd5ab1e90464ad009de",
320 | "shasum": ""
321 | },
322 | "require": {
323 | "php": ">=7.1"
324 | },
325 | "type": "library",
326 | "extra": {
327 | "branch-alias": {
328 | "dev-main": "1.20-dev"
329 | },
330 | "thanks": {
331 | "name": "symfony/polyfill",
332 | "url": "https://github.com/symfony/polyfill"
333 | }
334 | },
335 | "autoload": {
336 | "psr-4": {
337 | "Symfony\\Polyfill\\Php80\\": ""
338 | },
339 | "files": [
340 | "bootstrap.php"
341 | ],
342 | "classmap": [
343 | "Resources/stubs"
344 | ]
345 | },
346 | "notification-url": "https://packagist.org/downloads/",
347 | "license": [
348 | "MIT"
349 | ],
350 | "authors": [
351 | {
352 | "name": "Ion Bazan",
353 | "email": "ion.bazan@gmail.com"
354 | },
355 | {
356 | "name": "Nicolas Grekas",
357 | "email": "p@tchwork.com"
358 | },
359 | {
360 | "name": "Symfony Community",
361 | "homepage": "https://symfony.com/contributors"
362 | }
363 | ],
364 | "description": "Symfony polyfill backporting some PHP 8.0+ features to lower PHP versions",
365 | "homepage": "https://symfony.com",
366 | "keywords": [
367 | "compatibility",
368 | "polyfill",
369 | "portable",
370 | "shim"
371 | ],
372 | "support": {
373 | "source": "https://github.com/symfony/polyfill-php80/tree/v1.20.0"
374 | },
375 | "funding": [
376 | {
377 | "url": "https://symfony.com/sponsor",
378 | "type": "custom"
379 | },
380 | {
381 | "url": "https://github.com/fabpot",
382 | "type": "github"
383 | },
384 | {
385 | "url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
386 | "type": "tidelift"
387 | }
388 | ],
389 | "time": "2020-10-23T14:02:19+00:00"
390 | },
391 | {
392 | "name": "symfony/yaml",
393 | "version": "v5.2.0-RC2",
394 | "source": {
395 | "type": "git",
396 | "url": "https://github.com/symfony/yaml.git",
397 | "reference": "34b513f1bfb3677fc40aac34f8e4397eba4066ed"
398 | },
399 | "dist": {
400 | "type": "zip",
401 | "url": "https://api.github.com/repos/symfony/yaml/zipball/34b513f1bfb3677fc40aac34f8e4397eba4066ed",
402 | "reference": "34b513f1bfb3677fc40aac34f8e4397eba4066ed",
403 | "shasum": ""
404 | },
405 | "require": {
406 | "php": ">=7.2.5",
407 | "symfony/deprecation-contracts": "^2.1",
408 | "symfony/polyfill-ctype": "~1.8"
409 | },
410 | "conflict": {
411 | "symfony/console": "<4.4"
412 | },
413 | "require-dev": {
414 | "symfony/console": "^4.4|^5.0"
415 | },
416 | "suggest": {
417 | "symfony/console": "For validating YAML files using the lint command"
418 | },
419 | "bin": [
420 | "Resources/bin/yaml-lint"
421 | ],
422 | "type": "library",
423 | "autoload": {
424 | "psr-4": {
425 | "Symfony\\Component\\Yaml\\": ""
426 | },
427 | "exclude-from-classmap": [
428 | "/Tests/"
429 | ]
430 | },
431 | "notification-url": "https://packagist.org/downloads/",
432 | "license": [
433 | "MIT"
434 | ],
435 | "authors": [
436 | {
437 | "name": "Fabien Potencier",
438 | "email": "fabien@symfony.com"
439 | },
440 | {
441 | "name": "Symfony Community",
442 | "homepage": "https://symfony.com/contributors"
443 | }
444 | ],
445 | "description": "Symfony Yaml Component",
446 | "homepage": "https://symfony.com",
447 | "support": {
448 | "source": "https://github.com/symfony/yaml/tree/v5.2.0-RC2"
449 | },
450 | "funding": [
451 | {
452 | "url": "https://symfony.com/sponsor",
453 | "type": "custom"
454 | },
455 | {
456 | "url": "https://github.com/fabpot",
457 | "type": "github"
458 | },
459 | {
460 | "url": "https://tidelift.com/funding/github/packagist/symfony/symfony",
461 | "type": "tidelift"
462 | }
463 | ],
464 | "time": "2020-11-15T22:55:04+00:00"
465 | },
466 | {
467 | "name": "twig/twig",
468 | "version": "v3.1.1",
469 | "source": {
470 | "type": "git",
471 | "url": "https://github.com/twigphp/Twig.git",
472 | "reference": "b02fa41f3783a2616eccef7b92fbc2343ffed737"
473 | },
474 | "dist": {
475 | "type": "zip",
476 | "url": "https://api.github.com/repos/twigphp/Twig/zipball/b02fa41f3783a2616eccef7b92fbc2343ffed737",
477 | "reference": "b02fa41f3783a2616eccef7b92fbc2343ffed737",
478 | "shasum": ""
479 | },
480 | "require": {
481 | "php": ">=7.2.5",
482 | "symfony/polyfill-ctype": "^1.8",
483 | "symfony/polyfill-mbstring": "^1.3"
484 | },
485 | "require-dev": {
486 | "psr/container": "^1.0",
487 | "symfony/phpunit-bridge": "^4.4.9|^5.0.9"
488 | },
489 | "type": "library",
490 | "extra": {
491 | "branch-alias": {
492 | "dev-master": "3.1-dev"
493 | }
494 | },
495 | "autoload": {
496 | "psr-4": {
497 | "Twig\\": "src/"
498 | }
499 | },
500 | "notification-url": "https://packagist.org/downloads/",
501 | "license": [
502 | "BSD-3-Clause"
503 | ],
504 | "authors": [
505 | {
506 | "name": "Fabien Potencier",
507 | "email": "fabien@symfony.com",
508 | "homepage": "http://fabien.potencier.org",
509 | "role": "Lead Developer"
510 | },
511 | {
512 | "name": "Twig Team",
513 | "role": "Contributors"
514 | },
515 | {
516 | "name": "Armin Ronacher",
517 | "email": "armin.ronacher@active-4.com",
518 | "role": "Project Founder"
519 | }
520 | ],
521 | "description": "Twig, the flexible, fast, and secure template language for PHP",
522 | "homepage": "https://twig.symfony.com",
523 | "keywords": [
524 | "templating"
525 | ],
526 | "support": {
527 | "issues": "https://github.com/twigphp/Twig/issues",
528 | "source": "https://github.com/twigphp/Twig/tree/v3.1.1"
529 | },
530 | "funding": [
531 | {
532 | "url": "https://github.com/fabpot",
533 | "type": "github"
534 | },
535 | {
536 | "url": "https://tidelift.com/funding/github/packagist/twig/twig",
537 | "type": "tidelift"
538 | }
539 | ],
540 | "time": "2020-10-27T19:28:23+00:00"
541 | }
542 | ],
543 | "packages-dev": [],
544 | "aliases": [],
545 | "minimum-stability": "alpha",
546 | "stability-flags": {
547 | "symfony/http-foundation": 5,
548 | "symfony/yaml": 5
549 | },
550 | "prefer-stable": false,
551 | "prefer-lowest": false,
552 | "platform": {
553 | "php": "7.4.12|^8.0",
554 | "ext-mbstring": "*",
555 | "ext-iconv": "*",
556 | "ext-pdo": "*",
557 | "ext-json": "*",
558 | "ext-curl": "*",
559 | "ext-simplexml": "*"
560 | },
561 | "platform-dev": [],
562 | "plugin-api-version": "2.0.0"
563 | }
564 |
--------------------------------------------------------------------------------