mirror of
https://github.com/torrentpier/torrentpier
synced 2025-08-22 22:33:55 -07:00
Improvements in code and work cache (#101)
* Add hash prefix to key of the cache Change file cache adapter * Change in code style and fix in phpdoc * Add code sniffer Add copy-paste detected Fix version dev library Add script checker * Fix code style * Some improvements in configure the application. Code style. Start SettingsService and VisitorService.
This commit is contained in:
parent
7c77d29afb
commit
a523102e47
40 changed files with 941 additions and 168 deletions
24
app.php
Normal file
24
app.php
Normal file
|
@ -0,0 +1,24 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
require_once __DIR__ . '/bootstrap.php';
|
||||||
|
|
||||||
|
/** @var \TorrentPier\View $view */
|
||||||
|
$view = $di->view;
|
||||||
|
/** @var \TorrentPier\Db\Adapter $db */
|
||||||
|
$db = $di->db;
|
||||||
|
|
||||||
|
|
||||||
|
$view->addGlobal('title', 'Title Page Simple');
|
||||||
|
|
||||||
|
|
||||||
|
$categories = $db->select('bb_categories', function (\Zend\Db\Sql\Select $query) {
|
||||||
|
$query->join('bb_forums', 'bb_categories.cat_id = bb_forums.cat_id');
|
||||||
|
})->all();
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
echo $view->make('app', [
|
||||||
|
'data' => 'Hello world',
|
||||||
|
'categories' => $categories
|
||||||
|
]);
|
30
bootstrap.php
Normal file
30
bootstrap.php
Normal file
|
@ -0,0 +1,30 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
require_once __DIR__ . '/vendor/autoload.php';
|
||||||
|
|
||||||
|
use TorrentPier\Di,
|
||||||
|
TorrentPier\ServiceProviders;
|
||||||
|
|
||||||
|
$di = new Di();
|
||||||
|
|
||||||
|
$di->register(new ServiceProviders\ConfigServiceProvider, [
|
||||||
|
'file.system.main' => __DIR__ . '/configs/main.php',
|
||||||
|
'file.local.main' => __DIR__ . '/configs/local.php',
|
||||||
|
]);
|
||||||
|
|
||||||
|
//// Application
|
||||||
|
$di->register(new ServiceProviders\LogServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\CacheServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\DbServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\SettingsServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\VisitorServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\RequestServiceProvider());
|
||||||
|
|
||||||
|
// Services
|
||||||
|
//$di->register(new \TorrentPier\ServiceProviders\SphinxServiceProvider());
|
||||||
|
|
||||||
|
// View and Templates
|
||||||
|
$di->register(new ServiceProviders\TranslationServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\CaptchaServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\TwigServiceProvider());
|
||||||
|
$di->register(new ServiceProviders\ViewServiceProvider());
|
53
common.php
53
common.php
|
@ -38,44 +38,19 @@ $di['settings.locale'] = function($di) {
|
||||||
};
|
};
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\ConfigServiceProvider, [
|
$di->register(new \TorrentPier\ServiceProviders\ConfigServiceProvider, [
|
||||||
'config.file.system.main' => __DIR__ . '/library/config.php',
|
'file.system.main' => __DIR__ . '/library/config.php',
|
||||||
'config.file.local.main' => __DIR__ . '/library/config.local.php',
|
'file.local.main' => __DIR__ . '/library/config.local.php',
|
||||||
]);
|
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\LogServiceProvider(), [
|
|
||||||
'config.log.handlers' => $di->config->log->handlers
|
|
||||||
]);
|
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\CacheServiceProvider(), [
|
|
||||||
'config.services.cache' => $di->config->services->cache->toArray()
|
|
||||||
]);
|
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\DbServiceProvider, [
|
|
||||||
'config.db' => $di->config->db->toArray()
|
|
||||||
]);
|
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\SphinxServiceProvider, [
|
|
||||||
'config.sphinx' => $di->config->sphinx->toArray()
|
|
||||||
]);
|
]);
|
||||||
|
|
||||||
|
$di->register(new \TorrentPier\ServiceProviders\LogServiceProvider());
|
||||||
|
$di->register(new \TorrentPier\ServiceProviders\CacheServiceProvider());
|
||||||
|
$di->register(new \TorrentPier\ServiceProviders\DbServiceProvider());
|
||||||
|
$di->register(new \TorrentPier\ServiceProviders\SphinxServiceProvider());
|
||||||
$di->register(new \TorrentPier\ServiceProviders\RequestServiceProvider());
|
$di->register(new \TorrentPier\ServiceProviders\RequestServiceProvider());
|
||||||
$di->register(new \TorrentPier\ServiceProviders\ViewServiceProvider());
|
$di->register(new \TorrentPier\ServiceProviders\ViewServiceProvider());
|
||||||
|
$di->register(new \TorrentPier\ServiceProviders\TranslationServiceProvider());
|
||||||
$di->register(new \TorrentPier\ServiceProviders\TranslationServiceProvider(), [
|
$di->register(new \TorrentPier\ServiceProviders\TwigServiceProvider());
|
||||||
'config.debug' => $di->config->debug,
|
$di->register(new \TorrentPier\ServiceProviders\CaptchaServiceProvider());
|
||||||
'config.translator.dir_cache' => $di->config->translator->dir_cache,
|
|
||||||
'config.translator.resources' => $di->config->translator->resources->toArray()
|
|
||||||
]);
|
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\TwigServiceProvider, [
|
|
||||||
'config.debug' => $di->config->debug,
|
|
||||||
'config.twig.dir_templates' => $di->config->twig->dir_templates,
|
|
||||||
'config.twig.dir_cache' => $di->config->twig->dir_cache
|
|
||||||
]);
|
|
||||||
|
|
||||||
$di->register(new \TorrentPier\ServiceProviders\CaptchaServiceProvider, [
|
|
||||||
'config.captcha.secret_key' => $di->config->captcha->secret_key
|
|
||||||
]);
|
|
||||||
|
|
||||||
$bb_cfg = $di->config->toArray();
|
$bb_cfg = $di->config->toArray();
|
||||||
$page_cfg = $di->config->page->toArray();
|
$page_cfg = $di->config->page->toArray();
|
||||||
|
@ -132,11 +107,11 @@ require(CORE_DIR . 'dbs.php');
|
||||||
$DBS = new DBS([
|
$DBS = new DBS([
|
||||||
'db' => [
|
'db' => [
|
||||||
'db' => [
|
'db' => [
|
||||||
$di->config->db->hostname,
|
$di->config->services->db->hostname,
|
||||||
$di->config->db->database,
|
$di->config->services->db->database,
|
||||||
$di->config->db->username,
|
$di->config->services->db->username,
|
||||||
$di->config->db->password,
|
$di->config->services->db->password,
|
||||||
$di->config->db->charset,
|
$di->config->services->db->charset,
|
||||||
false
|
false
|
||||||
]
|
]
|
||||||
],
|
],
|
||||||
|
|
|
@ -46,7 +46,9 @@
|
||||||
"doctrine/cache": "^1.6"
|
"doctrine/cache": "^1.6"
|
||||||
},
|
},
|
||||||
"require-dev": {
|
"require-dev": {
|
||||||
"phpunit/phpunit": "^4.8"
|
"phpunit/phpunit": "4.8.*",
|
||||||
|
"squizlabs/php_codesniffer": "2.5.*",
|
||||||
|
"sebastian/phpcpd": "2.0.*"
|
||||||
},
|
},
|
||||||
"autoload": {
|
"autoload": {
|
||||||
"psr-4": {
|
"psr-4": {
|
||||||
|
@ -54,5 +56,24 @@
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
"minimum-stability": "stable",
|
"minimum-stability": "stable",
|
||||||
"prefer-stable": true
|
"prefer-stable": true,
|
||||||
|
"scripts": {
|
||||||
|
"test": [
|
||||||
|
"composer test:lint",
|
||||||
|
"composer test:unit",
|
||||||
|
"composer test:cpd"
|
||||||
|
],
|
||||||
|
"test:lint": [
|
||||||
|
"vendor/bin/phpcs --colors --report-full --standard=PSR2 src tests"
|
||||||
|
],
|
||||||
|
"test:unit": [
|
||||||
|
"vendor/bin/phpunit --configuration phpunit.xml --coverage-text"
|
||||||
|
],
|
||||||
|
"test:unit:html": [
|
||||||
|
"vendor/bin/phpunit --configuration phpunit.xml --coverage-html=internal_data/report"
|
||||||
|
],
|
||||||
|
"test:cpd": [
|
||||||
|
"vendor/bin/phpcpd --exclude=vendor --exclude=internal_data ."
|
||||||
|
]
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
79
configs/main.php
Normal file
79
configs/main.php
Normal file
|
@ -0,0 +1,79 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
return [
|
||||||
|
'debug' => false,
|
||||||
|
|
||||||
|
'services' => [
|
||||||
|
// Database
|
||||||
|
'db' => [
|
||||||
|
'debug' => '{self.debug}',
|
||||||
|
'driver' => 'Pdo_Mysql',
|
||||||
|
'hostname' => '127.0.0.1',
|
||||||
|
'database' => 'tp_220',
|
||||||
|
'username' => 'user',
|
||||||
|
'password' => 'pass',
|
||||||
|
'charset' => 'utf8'
|
||||||
|
],
|
||||||
|
|
||||||
|
// Cache
|
||||||
|
'cache' => [
|
||||||
|
'adapter' => \TorrentPier\Cache\FileAdapter::class,
|
||||||
|
'options' => [
|
||||||
|
'directory' => __DIR__ . '/../internal_data/cache',
|
||||||
|
],
|
||||||
|
],
|
||||||
|
|
||||||
|
// Translation
|
||||||
|
'translator' => [
|
||||||
|
'dir_cache' => __DIR__ . '/../internal_data/cache',
|
||||||
|
'resources' => [
|
||||||
|
[
|
||||||
|
'resource' => __DIR__ . '/../messages/ru.php',
|
||||||
|
'locale' => 'ru',
|
||||||
|
],
|
||||||
|
[
|
||||||
|
'resource' => __DIR__ . '/../messages/en.php',
|
||||||
|
'locale' => 'en',
|
||||||
|
]
|
||||||
|
]
|
||||||
|
],
|
||||||
|
|
||||||
|
// Twig
|
||||||
|
'twig' => [
|
||||||
|
'dir_templates' => __DIR__ . '/../templates/default',
|
||||||
|
'dir_cache' => __DIR__ . '/../internal_data/cache',
|
||||||
|
],
|
||||||
|
|
||||||
|
// Sphinx
|
||||||
|
'sphinx' => [
|
||||||
|
'debug' => '{self.debug}',
|
||||||
|
'driver' => '{self.db.driver}',
|
||||||
|
'hostname' => '{self.db.hostname}',
|
||||||
|
'username' => 'user',
|
||||||
|
'password' => 'pass',
|
||||||
|
'port' => 9306,
|
||||||
|
'charset' => 'utf8'
|
||||||
|
],
|
||||||
|
|
||||||
|
// Logger
|
||||||
|
'log' => [
|
||||||
|
'handlers' => [
|
||||||
|
function () {
|
||||||
|
return new \Monolog\Handler\StreamHandler(
|
||||||
|
__DIR__.'/../internal_data/log/app.log',
|
||||||
|
\Monolog\Logger::DEBUG
|
||||||
|
);
|
||||||
|
}
|
||||||
|
]
|
||||||
|
],
|
||||||
|
|
||||||
|
// Captcha
|
||||||
|
// Get a Google reCAPTCHA API Key: https://www.google.com/recaptcha/admin
|
||||||
|
'captcha' => [
|
||||||
|
'disabled' => false,
|
||||||
|
'public_key' => '', // your public key
|
||||||
|
'secret_key' => '', // your secret key
|
||||||
|
'theme' => 'light', // light or dark
|
||||||
|
],
|
||||||
|
]
|
||||||
|
];
|
|
@ -24,6 +24,7 @@ $config = [
|
||||||
'adapter' => \TorrentPier\Cache\FileAdapter::class,
|
'adapter' => \TorrentPier\Cache\FileAdapter::class,
|
||||||
'options' => [
|
'options' => [
|
||||||
'directory' => __DIR__ . '/../internal_data/cache',
|
'directory' => __DIR__ . '/../internal_data/cache',
|
||||||
|
'prefix' => 'hash string'
|
||||||
],
|
],
|
||||||
],
|
],
|
||||||
/*'cache' => [
|
/*'cache' => [
|
||||||
|
@ -36,62 +37,62 @@ $config = [
|
||||||
],
|
],
|
||||||
],
|
],
|
||||||
],*/
|
],*/
|
||||||
],
|
|
||||||
|
|
||||||
// Database
|
// Database
|
||||||
'db' => [
|
'db' => [
|
||||||
'debug' => '{self.debug}',
|
'debug' => '{self.debug}',
|
||||||
'driver' => 'Pdo_Mysql',
|
'driver' => 'Pdo_Mysql',
|
||||||
'hostname' => '127.0.0.1',
|
'hostname' => '127.0.0.1',
|
||||||
'database' => 'tp_220',
|
'database' => 'tp_220',
|
||||||
'username' => 'user',
|
'username' => 'user',
|
||||||
'password' => 'pass',
|
'password' => 'pass',
|
||||||
'charset' => 'utf8'
|
'charset' => 'utf8'
|
||||||
],
|
],
|
||||||
|
|
||||||
// Sphinx
|
// Sphinx
|
||||||
'sphinx' => [
|
'sphinx' => [
|
||||||
'debug' => '{self.debug}',
|
'debug' => '{self.debug}',
|
||||||
'driver' => '{self.db.driver}',
|
'driver' => '{self.db.driver}',
|
||||||
'hostname' => '{self.db.hostname}',
|
'hostname' => '{self.db.hostname}',
|
||||||
'username' => 'user',
|
'username' => 'user',
|
||||||
'password' => 'pass',
|
'password' => 'pass',
|
||||||
'port' => 9306,
|
'port' => 9306,
|
||||||
'charset' => 'utf8'
|
'charset' => 'utf8'
|
||||||
],
|
],
|
||||||
|
|
||||||
// Twig
|
// Twig
|
||||||
'twig' => [
|
'twig' => [
|
||||||
'dir_templates' => __DIR__ . '/../templates/default',
|
'dir_templates' => __DIR__ . '/../templates/default',
|
||||||
'dir_cache' => __DIR__ . '/../internal_data/cache',
|
'dir_cache' => __DIR__ . '/../internal_data/cache',
|
||||||
],
|
],
|
||||||
|
|
||||||
// Translation
|
// Translation
|
||||||
'translator' => [
|
'translator' => [
|
||||||
'dir_cache' => __DIR__ . '/../internal_data/cache',
|
'dir_cache' => __DIR__ . '/../internal_data/cache',
|
||||||
'resources' => [
|
'resources' => [
|
||||||
[
|
[
|
||||||
'resource' => __DIR__ . '/../messages/ru.php',
|
'resource' => __DIR__ . '/../messages/ru.php',
|
||||||
'locale' => 'ru',
|
'locale' => 'ru',
|
||||||
],
|
],
|
||||||
[
|
[
|
||||||
'resource' => __DIR__ . '/../messages/en.php',
|
'resource' => __DIR__ . '/../messages/en.php',
|
||||||
'locale' => 'en',
|
'locale' => 'en',
|
||||||
|
]
|
||||||
]
|
]
|
||||||
]
|
],
|
||||||
],
|
|
||||||
|
|
||||||
// Log
|
// Log
|
||||||
'log' => [
|
'log' => [
|
||||||
'handlers' => [
|
'handlers' => [
|
||||||
function () {
|
function () {
|
||||||
return new \Monolog\Handler\StreamHandler(
|
return new \Monolog\Handler\StreamHandler(
|
||||||
__DIR__.'/../internal_data/log/app.log',
|
__DIR__.'/../internal_data/log/app.log',
|
||||||
\Monolog\Logger::DEBUG
|
\Monolog\Logger::DEBUG
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
]
|
]
|
||||||
],
|
],
|
||||||
|
],
|
||||||
|
|
||||||
// Aliases
|
// Aliases
|
||||||
// TODO: удалить
|
// TODO: удалить
|
||||||
|
|
16
phpcs.xml
Normal file
16
phpcs.xml
Normal file
|
@ -0,0 +1,16 @@
|
||||||
|
<?xml version="1.0"?>
|
||||||
|
<ruleset name="TorrentPier">
|
||||||
|
|
||||||
|
<description>Codestyle ruleset for TorrentPier</description>
|
||||||
|
|
||||||
|
<rule ref="PSR2"/>
|
||||||
|
|
||||||
|
<file>src</file>
|
||||||
|
|
||||||
|
<arg name="encoding" value="UTF-8"/>
|
||||||
|
<arg name="extensions" value="php"/>
|
||||||
|
|
||||||
|
<exclude-pattern>tests/*</exclude-pattern>
|
||||||
|
<exclude-pattern>vendor/*</exclude-pattern>
|
||||||
|
|
||||||
|
</ruleset>
|
|
@ -17,6 +17,11 @@ abstract class Adapter
|
||||||
*/
|
*/
|
||||||
protected $provider;
|
protected $provider;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var string
|
||||||
|
*/
|
||||||
|
protected $prefix = '';
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set options for setting cache provider.
|
* Set options for setting cache provider.
|
||||||
*
|
*
|
||||||
|
@ -48,6 +53,18 @@ abstract class Adapter
|
||||||
*/
|
*/
|
||||||
abstract protected function getType();
|
abstract protected function getType();
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Add prefix to the namespace for security of key.
|
||||||
|
*
|
||||||
|
* @param string $prefix
|
||||||
|
* @return $this
|
||||||
|
*/
|
||||||
|
protected function setPrefix($prefix)
|
||||||
|
{
|
||||||
|
$this->prefix = $prefix;
|
||||||
|
return $this;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Prepare key.
|
* Prepare key.
|
||||||
*
|
*
|
||||||
|
@ -68,7 +85,7 @@ abstract class Adapter
|
||||||
list($namespace, $id) = $result;
|
list($namespace, $id) = $result;
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->getProvider()->setNamespace($namespace);
|
$this->getProvider()->setNamespace($this->prefix . $namespace);
|
||||||
|
|
||||||
return $id;
|
return $id;
|
||||||
}
|
}
|
||||||
|
@ -89,7 +106,7 @@ abstract class Adapter
|
||||||
* Fetches an entry from the cache.
|
* Fetches an entry from the cache.
|
||||||
*
|
*
|
||||||
* @param string $key
|
* @param string $key
|
||||||
* @param mixed|null $defaultValue
|
* @param mixed|\Closure|null $defaultValue
|
||||||
* @return mixed|null
|
* @return mixed|null
|
||||||
*/
|
*/
|
||||||
public function get($key, $defaultValue = null)
|
public function get($key, $defaultValue = null)
|
||||||
|
@ -98,6 +115,10 @@ abstract class Adapter
|
||||||
$result = $this->getProvider()->fetch($id);
|
$result = $this->getProvider()->fetch($id);
|
||||||
|
|
||||||
if ($result === false) {
|
if ($result === false) {
|
||||||
|
if ($defaultValue instanceof \Closure) {
|
||||||
|
return call_user_func($defaultValue, $this, $key);
|
||||||
|
}
|
||||||
|
|
||||||
return $defaultValue;
|
return $defaultValue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -108,12 +129,13 @@ abstract class Adapter
|
||||||
* Returns an associative array of values for keys is found in cache.
|
* Returns an associative array of values for keys is found in cache.
|
||||||
*
|
*
|
||||||
* @param array $keys
|
* @param array $keys
|
||||||
|
* @param string $namespace
|
||||||
* @return array|\string[]
|
* @return array|\string[]
|
||||||
*/
|
*/
|
||||||
public function gets(array $keys)
|
public function gets(array $keys, $namespace = self::DEFAULT_NAMESPACE)
|
||||||
{
|
{
|
||||||
$keys = array_map([$this, 'prepareKey'], $keys);
|
$this->getProvider()->setNamespace($this->prefix . $namespace);
|
||||||
return $this->getProvider()->fetchMultiple([$keys]);
|
return $this->getProvider()->fetchMultiple($keys);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -134,16 +156,13 @@ abstract class Adapter
|
||||||
* Returns a boolean value indicating if the operation succeeded.
|
* Returns a boolean value indicating if the operation succeeded.
|
||||||
*
|
*
|
||||||
* @param array $keysAndValues
|
* @param array $keysAndValues
|
||||||
|
* @param string $namespace
|
||||||
* @param int $timeLeft
|
* @param int $timeLeft
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
public function sets(array $keysAndValues, $timeLeft)
|
public function sets(array $keysAndValues, $namespace = self::DEFAULT_NAMESPACE, $timeLeft = 0)
|
||||||
{
|
{
|
||||||
foreach ($keysAndValues as $key => $value) {
|
$this->getProvider()->setNamespace($this->prefix . $namespace);
|
||||||
$id = $this->prepareKey($key);
|
|
||||||
$keysAndValues[$id] = $value;
|
|
||||||
unset($keysAndValues[$key]);
|
|
||||||
}
|
|
||||||
return $this->getProvider()->saveMultiple($keysAndValues, $timeLeft);
|
return $this->getProvider()->saveMultiple($keysAndValues, $timeLeft);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -167,7 +186,7 @@ abstract class Adapter
|
||||||
*/
|
*/
|
||||||
public function deleteAll($namespace = '')
|
public function deleteAll($namespace = '')
|
||||||
{
|
{
|
||||||
$this->getProvider()->setNamespace($namespace);
|
$this->getProvider()->setNamespace($this->prefix . $namespace);
|
||||||
return $this->getProvider()->deleteAll();
|
return $this->getProvider()->deleteAll();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
namespace TorrentPier\Cache;
|
namespace TorrentPier\Cache;
|
||||||
|
|
||||||
use Doctrine\Common\Cache\PhpFileCache;
|
use Doctrine\Common\Cache\FilesystemCache;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class FileAdapter
|
* Class FileAdapter
|
||||||
|
@ -18,7 +18,7 @@ class FileAdapter extends Adapter
|
||||||
/**
|
/**
|
||||||
* @var string The cache file extension.
|
* @var string The cache file extension.
|
||||||
*/
|
*/
|
||||||
protected $extension = PhpFileCache::EXTENSION;
|
protected $extension = FilesystemCache::EXTENSION;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var int The cache file umask.
|
* @var int The cache file umask.
|
||||||
|
@ -31,7 +31,7 @@ class FileAdapter extends Adapter
|
||||||
public function getProvider()
|
public function getProvider()
|
||||||
{
|
{
|
||||||
if (!$this->provider) {
|
if (!$this->provider) {
|
||||||
$this->provider = new PhpFileCache($this->directory, $this->extension, $this->umask);
|
$this->provider = new FilesystemCache($this->directory, $this->extension, $this->umask);
|
||||||
}
|
}
|
||||||
|
|
||||||
return $this->provider;
|
return $this->provider;
|
||||||
|
@ -42,7 +42,7 @@ class FileAdapter extends Adapter
|
||||||
*/
|
*/
|
||||||
protected function getType()
|
protected function getType()
|
||||||
{
|
{
|
||||||
return 'Cache in php file';
|
return 'Filesystem Cache';
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -98,6 +98,6 @@ class MemoryAdapter extends Adapter
|
||||||
*/
|
*/
|
||||||
protected function getType()
|
protected function getType()
|
||||||
{
|
{
|
||||||
return $this->isMemcached ? 'Cache in memcached' : 'Cache in memcache';
|
return sprintf('Memory Cache (Driver: %s)', $this->isMemcached ? 'memcached' : 'memcache');
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -19,7 +19,7 @@ class Config extends ZendConfig
|
||||||
* @param bool $allowModifications
|
* @param bool $allowModifications
|
||||||
* @param Config|null $root
|
* @param Config|null $root
|
||||||
*/
|
*/
|
||||||
public function __construct(array $array, $allowModifications = false, Config $root = null)
|
public function __construct(array $array, $allowModifications = false, Config &$root = null)
|
||||||
{
|
{
|
||||||
$this->allowModifications = (bool) $allowModifications;
|
$this->allowModifications = (bool) $allowModifications;
|
||||||
|
|
||||||
|
|
|
@ -31,8 +31,12 @@ class Adapter extends \Zend\Db\Adapter\Adapter
|
||||||
/**
|
/**
|
||||||
* {@inheritdoc}
|
* {@inheritdoc}
|
||||||
*/
|
*/
|
||||||
public function __construct($driver, PlatformInterface $platform = null, ResultSetInterface $queryResultPrototype = null, ProfilerInterface $profiler = null)
|
public function __construct(
|
||||||
{
|
$driver,
|
||||||
|
PlatformInterface $platform = null,
|
||||||
|
ResultSetInterface $queryResultPrototype = null,
|
||||||
|
ProfilerInterface $profiler = null
|
||||||
|
) {
|
||||||
if ($driver instanceof Config) {
|
if ($driver instanceof Config) {
|
||||||
$driver = $driver->toArray();
|
$driver = $driver->toArray();
|
||||||
}
|
}
|
||||||
|
@ -85,7 +89,6 @@ class Adapter extends \Zend\Db\Adapter\Adapter
|
||||||
$table = $this->prepareTable($table);
|
$table = $this->prepareTable($table);
|
||||||
$sql = $this->getSql();
|
$sql = $this->getSql();
|
||||||
|
|
||||||
|
|
||||||
/** @var Insert $sqlInsert */
|
/** @var Insert $sqlInsert */
|
||||||
$sqlInsert = $sql->insert($table);
|
$sqlInsert = $sql->insert($table);
|
||||||
$sqlInsert->values($values);
|
$sqlInsert->values($values);
|
||||||
|
|
39
src/Di.php
39
src/Di.php
|
@ -10,14 +10,27 @@ use Pimple\Container;
|
||||||
*/
|
*/
|
||||||
class Di extends Container
|
class Di extends Container
|
||||||
{
|
{
|
||||||
|
const DELIMITER = '.';
|
||||||
|
|
||||||
private static $instance;
|
private static $instance;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Di constructor.
|
||||||
|
*
|
||||||
|
* @param array $values
|
||||||
|
*/
|
||||||
public function __construct(array $values = [])
|
public function __construct(array $values = [])
|
||||||
{
|
{
|
||||||
parent::__construct($values);
|
parent::__construct($values);
|
||||||
static::$instance = $this;
|
static::$instance = $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get instance dependency injection container.
|
||||||
|
*
|
||||||
|
* @return self
|
||||||
|
* @throws \RuntimeException
|
||||||
|
*/
|
||||||
public static function getInstance()
|
public static function getInstance()
|
||||||
{
|
{
|
||||||
if (static::$instance instanceof Container) {
|
if (static::$instance instanceof Container) {
|
||||||
|
@ -27,12 +40,28 @@ class Di extends Container
|
||||||
throw new \RuntimeException('The container has not been initialized');
|
throw new \RuntimeException('The container has not been initialized');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function offsetGet($id)
|
||||||
|
{
|
||||||
|
try {
|
||||||
|
return parent::offsetGet($id);
|
||||||
|
} catch (\InvalidArgumentException $e) {
|
||||||
|
if (strpos($id, self::DELIMITER)) {
|
||||||
|
list($service, $key) = explode(self::DELIMITER, $id, 2);
|
||||||
|
|
||||||
|
if ($this->offsetExists($service)) {
|
||||||
|
return parent::offsetGet($service)->get($key);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
throw new \InvalidArgumentException($e->getMessage(), $e->getCode(), $e->getPrevious());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public function __get($id)
|
public function __get($id)
|
||||||
{
|
{
|
||||||
if ($this->offsetExists($id)) {
|
return $this->offsetGet($id);
|
||||||
return $this->offsetGet($id);
|
|
||||||
}
|
|
||||||
|
|
||||||
throw new \RuntimeException("Service '{$id}' is not registered in the container");
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,7 +21,7 @@ class CacheServiceProvider implements ServiceProviderInterface
|
||||||
$setting = $container['config.services.cache'];
|
$setting = $container['config.services.cache'];
|
||||||
/** @var Adapter $adapter */
|
/** @var Adapter $adapter */
|
||||||
$adapter = new $setting['adapter']();
|
$adapter = new $setting['adapter']();
|
||||||
$adapter->setOptions($setting['options']);
|
$adapter->setOptions($setting['options']->toArray());
|
||||||
return $adapter;
|
return $adapter;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -18,7 +18,7 @@ class CaptchaServiceProvider implements ServiceProviderInterface
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
{
|
{
|
||||||
$container['captcha'] = function (Container $container) {
|
$container['captcha'] = function (Container $container) {
|
||||||
$captcha = new ReCaptcha($container['config.captcha.secret_key']);
|
$captcha = new ReCaptcha($container['config.services.captcha.secret_key']);
|
||||||
return $captcha;
|
return $captcha;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -7,6 +7,10 @@ use Pimple\ServiceProviderInterface;
|
||||||
use TorrentPier\Config;
|
use TorrentPier\Config;
|
||||||
use Zend\Config\Factory;
|
use Zend\Config\Factory;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class ConfigServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class ConfigServiceProvider implements ServiceProviderInterface
|
class ConfigServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
@ -15,10 +19,10 @@ class ConfigServiceProvider implements ServiceProviderInterface
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
{
|
{
|
||||||
$container['config'] = function ($container) {
|
$container['config'] = function ($container) {
|
||||||
$config = new Config(Factory::fromFile($container['config.file.system.main']));
|
$config = new Config(Factory::fromFile($container['file.system.main']));
|
||||||
|
|
||||||
if (isset($container['config.file.local.main']) && file_exists($container['config.file.local.main'])) {
|
if (isset($container['file.local.main']) && file_exists($container['file.local.main'])) {
|
||||||
$config->merge(new Config(Factory::fromFile($container['config.file.local.main'])));
|
$config->merge(new Config(Factory::fromFile($container['file.local.main'])));
|
||||||
}
|
}
|
||||||
|
|
||||||
return $config;
|
return $config;
|
||||||
|
|
|
@ -7,6 +7,10 @@ use Pimple\ServiceProviderInterface;
|
||||||
use TorrentPier\Db\Adapter;
|
use TorrentPier\Db\Adapter;
|
||||||
use TorrentPier\Db\Connection;
|
use TorrentPier\Db\Connection;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class DbServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class DbServiceProvider implements ServiceProviderInterface
|
class DbServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
@ -15,8 +19,8 @@ class DbServiceProvider implements ServiceProviderInterface
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
{
|
{
|
||||||
$container['db'] = function ($container) {
|
$container['db'] = function ($container) {
|
||||||
$adapter = new Adapter($container['config.db']);
|
$adapter = new Adapter($container['config.services.db']);
|
||||||
unset($container['config.db']);
|
unset($container['config.services.db']);
|
||||||
return $adapter;
|
return $adapter;
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,7 +26,7 @@ class LogServiceProvider implements ServiceProviderInterface
|
||||||
$container['log'] = function ($container) {
|
$container['log'] = function ($container) {
|
||||||
/** @var Logger $logger */
|
/** @var Logger $logger */
|
||||||
$logger = $container['logger']('app');
|
$logger = $container['logger']('app');
|
||||||
foreach ($container['config.log.handlers'] as $logHandler) {
|
foreach ($container['config.services.log.handlers'] as $logHandler) {
|
||||||
$logger->pushHandler(call_user_func($logHandler));
|
$logger->pushHandler(call_user_func($logHandler));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -6,6 +6,10 @@ use Pimple\Container;
|
||||||
use Pimple\ServiceProviderInterface;
|
use Pimple\ServiceProviderInterface;
|
||||||
use Symfony\Component\HttpFoundation\Request;
|
use Symfony\Component\HttpFoundation\Request;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class RequestServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class RequestServiceProvider implements ServiceProviderInterface
|
class RequestServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
|
|
17
src/ServiceProviders/SettingsServiceProvider.php
Normal file
17
src/ServiceProviders/SettingsServiceProvider.php
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier\ServiceProviders;
|
||||||
|
|
||||||
|
use Pimple\Container;
|
||||||
|
use Pimple\ServiceProviderInterface;
|
||||||
|
use TorrentPier\Settings;
|
||||||
|
|
||||||
|
class SettingsServiceProvider implements ServiceProviderInterface
|
||||||
|
{
|
||||||
|
public function register(Container $container)
|
||||||
|
{
|
||||||
|
$container['settings'] = function (Container $container) {
|
||||||
|
return new Settings($container['db'], $container['cache']);
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
|
@ -11,6 +11,10 @@ use Zend\Db\Adapter\Adapter;
|
||||||
use Zend\Db\Adapter\Driver\Mysqli\Mysqli;
|
use Zend\Db\Adapter\Driver\Mysqli\Mysqli;
|
||||||
use Zend\Db\Adapter\Driver\Pdo\Pdo;
|
use Zend\Db\Adapter\Driver\Pdo\Pdo;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class SphinxServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class SphinxServiceProvider implements ServiceProviderInterface
|
class SphinxServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
|
@ -20,7 +24,7 @@ class SphinxServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
$container['sphinx'] = function ($container) {
|
$container['sphinx'] = function ($container) {
|
||||||
$platform = new SphinxQL();
|
$platform = new SphinxQL();
|
||||||
$adapter = new Adapter($container['config.sphinx']);
|
$adapter = new Adapter($container['config.services.sphinx']);
|
||||||
|
|
||||||
$driver = $adapter->getDriver();
|
$driver = $adapter->getDriver();
|
||||||
// Check driver
|
// Check driver
|
||||||
|
@ -34,7 +38,7 @@ class SphinxServiceProvider implements ServiceProviderInterface
|
||||||
}
|
}
|
||||||
|
|
||||||
$platform->setDriver($adapter->getDriver());
|
$platform->setDriver($adapter->getDriver());
|
||||||
unset($container['config.sphinx']);
|
unset($container['config.services.sphinx']);
|
||||||
|
|
||||||
return $adapter;
|
return $adapter;
|
||||||
};
|
};
|
||||||
|
|
|
@ -7,21 +7,29 @@ use Pimple\ServiceProviderInterface;
|
||||||
use Symfony\Component\Translation\Loader\PhpFileLoader;
|
use Symfony\Component\Translation\Loader\PhpFileLoader;
|
||||||
use Symfony\Component\Translation\Translator;
|
use Symfony\Component\Translation\Translator;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class TranslationServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class TranslationServiceProvider implements ServiceProviderInterface
|
class TranslationServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
{
|
{
|
||||||
$container['translator'] = function (Container $container) {
|
$container['translator'] = function (Container $container) {
|
||||||
$translator = new Translator(
|
$translator = new Translator(
|
||||||
$container['settings.locale'],
|
$container['visitor.settings.base.locale'] ?: $container['settings.base.locale'],
|
||||||
null,
|
null,
|
||||||
null, // $container['config.translator.dir_cache'],
|
null, // $container['config.services.translator.dir_cache'],
|
||||||
$container['config.debug']
|
$container['config.debug']
|
||||||
);
|
);
|
||||||
|
|
||||||
$translator->addLoader('php', new PhpFileLoader());
|
$translator->addLoader('php', new PhpFileLoader());
|
||||||
|
|
||||||
foreach ($container['config.translator.resources'] as $item) {
|
$resources = $container['config.services.translator.resources']->toArray();
|
||||||
|
foreach ($resources as $item) {
|
||||||
$translator->addResource('php', $item['resource'], $item['locale']);
|
$translator->addResource('php', $item['resource'], $item['locale']);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,24 +5,28 @@ namespace TorrentPier\ServiceProviders;
|
||||||
use Pimple\Container;
|
use Pimple\Container;
|
||||||
use Pimple\ServiceProviderInterface;
|
use Pimple\ServiceProviderInterface;
|
||||||
use Symfony\Bridge\Twig\Extension\TranslationExtension;
|
use Symfony\Bridge\Twig\Extension\TranslationExtension;
|
||||||
|
use TorrentPier\Twig\Loader\Filesystem;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class TwigServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class TwigServiceProvider implements ServiceProviderInterface
|
class TwigServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
{
|
{
|
||||||
$container['twig'] = function (Container $container) {
|
$container['twig'] = function (Container $container) {
|
||||||
$loader = new \Twig_Loader_Filesystem($container['config.twig.dir_templates']);
|
$loader = new Filesystem($container['config.services.twig.dir_templates']);
|
||||||
$twig = new \Twig_Environment($loader, [
|
$twig = new \Twig_Environment($loader, [
|
||||||
'debug' => $container['config.debug'],
|
'debug' => $container['config.debug'],
|
||||||
'cache' => $container['config.twig.dir_cache'],
|
'cache' => $container['config.services.twig.dir_cache'],
|
||||||
]);
|
]);
|
||||||
|
|
||||||
$twig->addExtension(new \Twig_Extension_Core());
|
|
||||||
$twig->addExtension(new \Twig_Extension_Escaper());
|
|
||||||
$twig->addExtension(new \Twig_Extension_Optimizer());
|
|
||||||
$twig->addExtension(new \Twig_Extension_Debug());
|
|
||||||
|
|
||||||
$twig->addExtension(new TranslationExtension($container['translator']));
|
$twig->addExtension(new TranslationExtension($container['translator']));
|
||||||
|
$twig->addExtension(new \Twig_Extension_Debug());
|
||||||
|
|
||||||
return $twig;
|
return $twig;
|
||||||
};
|
};
|
||||||
|
|
|
@ -6,6 +6,10 @@ use Pimple\Container;
|
||||||
use Pimple\ServiceProviderInterface;
|
use Pimple\ServiceProviderInterface;
|
||||||
use TorrentPier\View;
|
use TorrentPier\View;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class ViewServiceProvider
|
||||||
|
* @package TorrentPier\ServiceProviders
|
||||||
|
*/
|
||||||
class ViewServiceProvider implements ServiceProviderInterface
|
class ViewServiceProvider implements ServiceProviderInterface
|
||||||
{
|
{
|
||||||
public function register(Container $container)
|
public function register(Container $container)
|
||||||
|
|
17
src/ServiceProviders/VisitorServiceProvider.php
Normal file
17
src/ServiceProviders/VisitorServiceProvider.php
Normal file
|
@ -0,0 +1,17 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier\ServiceProviders;
|
||||||
|
|
||||||
|
use Pimple\Container;
|
||||||
|
use Pimple\ServiceProviderInterface;
|
||||||
|
use TorrentPier\Visitor;
|
||||||
|
|
||||||
|
class VisitorServiceProvider implements ServiceProviderInterface
|
||||||
|
{
|
||||||
|
public function register(Container $container)
|
||||||
|
{
|
||||||
|
$container['visitor'] = function (Container $container) {
|
||||||
|
return new Visitor();
|
||||||
|
};
|
||||||
|
}
|
||||||
|
}
|
26
src/Settings.php
Normal file
26
src/Settings.php
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier;
|
||||||
|
|
||||||
|
use TorrentPier\Db\Adapter as DbAdapter;
|
||||||
|
use TorrentPier\Cache\Adapter as CacheAdapter;
|
||||||
|
|
||||||
|
class Settings
|
||||||
|
{
|
||||||
|
/** @var DbAdapter */
|
||||||
|
protected $db;
|
||||||
|
|
||||||
|
/** @var CacheAdapter */
|
||||||
|
protected $cache;
|
||||||
|
|
||||||
|
public function __construct(DbAdapter $db, CacheAdapter $cache)
|
||||||
|
{
|
||||||
|
$this->db = $db;
|
||||||
|
$this->cache = $cache;
|
||||||
|
}
|
||||||
|
|
||||||
|
public function get($key)
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
20
src/Twig/Loader/Filesystem.php
Normal file
20
src/Twig/Loader/Filesystem.php
Normal file
|
@ -0,0 +1,20 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier\Twig\Loader;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Class Filesystem
|
||||||
|
* @package TorrentPier\Twig\Loader
|
||||||
|
*/
|
||||||
|
class Filesystem extends \Twig_Loader_Filesystem
|
||||||
|
{
|
||||||
|
const FILE_EXTENSION = '.twig';
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
protected function normalizeName($name)
|
||||||
|
{
|
||||||
|
return parent::normalizeName($name) . self::FILE_EXTENSION;
|
||||||
|
}
|
||||||
|
}
|
13
src/View.php
13
src/View.php
|
@ -9,19 +9,28 @@ class View
|
||||||
*/
|
*/
|
||||||
protected $twig;
|
protected $twig;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* View constructor.
|
||||||
|
*
|
||||||
|
* @param \Twig_Environment $twig
|
||||||
|
*/
|
||||||
public function __construct(\Twig_Environment $twig)
|
public function __construct(\Twig_Environment $twig)
|
||||||
{
|
{
|
||||||
$this->twig = $twig;
|
$this->twig = $twig;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public function addGlobal($name, $value)
|
||||||
|
{
|
||||||
|
$this->twig->addGlobal($name, $value);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param $template
|
* @param $template
|
||||||
* @param array $params
|
* @param array $params
|
||||||
*
|
|
||||||
* @return string
|
* @return string
|
||||||
*/
|
*/
|
||||||
public function make($template, $params = [])
|
public function make($template, $params = [])
|
||||||
{
|
{
|
||||||
return $this->twig->render($template.'.twig', $params);
|
return $this->twig->render($template, $params);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
11
src/Visitor.php
Normal file
11
src/Visitor.php
Normal file
|
@ -0,0 +1,11 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier;
|
||||||
|
|
||||||
|
class Visitor
|
||||||
|
{
|
||||||
|
public function get()
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
}
|
26
templates/default/app.twig
Normal file
26
templates/default/app.twig
Normal file
|
@ -0,0 +1,26 @@
|
||||||
|
{% extends "layouts/main" %}
|
||||||
|
|
||||||
|
{% block content %}
|
||||||
|
<h1>{{ data }}</h1>
|
||||||
|
|
||||||
|
<ul>
|
||||||
|
{% for category in categories %}
|
||||||
|
<li>
|
||||||
|
<h3>{{ category.forum_name|e }} - {{ category.cat_title|e }}</h3>
|
||||||
|
<p>{{ category.forum_desc }}</p>
|
||||||
|
</li>
|
||||||
|
{% endfor %}
|
||||||
|
</ul>
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
{% endblock %}
|
||||||
|
|
||||||
|
|
||||||
|
|
33
templates/default/blocks/menu.twig
Normal file
33
templates/default/blocks/menu.twig
Normal file
|
@ -0,0 +1,33 @@
|
||||||
|
<!-- Fixed navbar -->
|
||||||
|
<nav class="navbar navbar-inverse navbar-fixed-top">
|
||||||
|
<div class="container">
|
||||||
|
<div class="navbar-header">
|
||||||
|
<button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#navbar" aria-expanded="false" aria-controls="navbar">
|
||||||
|
<span class="sr-only">Toggle navigation</span>
|
||||||
|
<span class="icon-bar"></span>
|
||||||
|
<span class="icon-bar"></span>
|
||||||
|
<span class="icon-bar"></span>
|
||||||
|
</button>
|
||||||
|
<a class="navbar-brand" href="#">Bootstrap theme</a>
|
||||||
|
</div>
|
||||||
|
<div id="navbar" class="navbar-collapse collapse">
|
||||||
|
<ul class="nav navbar-nav">
|
||||||
|
<li class="active"><a href="#">Home</a></li>
|
||||||
|
<li><a href="#about">About</a></li>
|
||||||
|
<li><a href="#contact">Contact</a></li>
|
||||||
|
<li class="dropdown">
|
||||||
|
<a href="#" class="dropdown-toggle" data-toggle="dropdown" role="button" aria-haspopup="true" aria-expanded="false">Dropdown <span class="caret"></span></a>
|
||||||
|
<ul class="dropdown-menu">
|
||||||
|
<li><a href="#">Action</a></li>
|
||||||
|
<li><a href="#">Another action</a></li>
|
||||||
|
<li><a href="#">Something else here</a></li>
|
||||||
|
<li role="separator" class="divider"></li>
|
||||||
|
<li class="dropdown-header">Nav header</li>
|
||||||
|
<li><a href="#">Separated link</a></li>
|
||||||
|
<li><a href="#">One more separated link</a></li>
|
||||||
|
</ul>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
</div><!--/.nav-collapse -->
|
||||||
|
</div>
|
||||||
|
</nav>
|
41
templates/default/layouts/main.twig
Normal file
41
templates/default/layouts/main.twig
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
<!doctype html>
|
||||||
|
<html lang="ru">
|
||||||
|
<head>
|
||||||
|
<meta charset="UTF-8">
|
||||||
|
<meta name="viewport"
|
||||||
|
content="width=device-width, user-scalable=no, initial-scale=1.0, maximum-scale=1.0, minimum-scale=1.0">
|
||||||
|
<meta http-equiv="X-UA-Compatible" content="ie=edge">
|
||||||
|
<title>{{ title }}</title>
|
||||||
|
|
||||||
|
<!-- Latest compiled and minified CSS -->
|
||||||
|
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap.min.css" integrity="sha384-1q8mTJOASx8j1Au+a5WDVnPi2lkFfwwEAa8hDDdjZlpLegxhjVME1fgjWPGmkzs7" crossorigin="anonymous">
|
||||||
|
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/font-awesome/4.6.3/css/font-awesome.min.css" integrity="sha384-T8Gy5hrqNKT+hzMclPo118YTQO6cYprQmhrYwIiQ/3axmI1hQomh7Ud2hPOy8SP1" crossorigin="anonymous">
|
||||||
|
|
||||||
|
<!-- Optional theme -->
|
||||||
|
<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/css/bootstrap-theme.min.css" integrity="sha384-fLW2N01lMqjakBkx3l/M9EahuwpSfeNvV63J5ezn3uZzapT0u7EYsXMjQV+0En5r" crossorigin="anonymous">
|
||||||
|
{#<link rel="stylesheet" href="https://maxcdn.bootstrapcdn.com/bootswatch/3.3.6/slate/bootstrap.min.css" integrity="sha384-X9JiR5BtXUXiV6R3XuMyVGefFyy+18PHpBwaMfteb/vd2RrK6Gt4KPenkQyWLxCC" crossorigin="anonymous">#}
|
||||||
|
<style>
|
||||||
|
body{padding-top:40px;padding-bottom:40px;background-color:#eee}.form-signin{max-width:330px;padding:15px;margin:0 auto}.form-signin .form-signin-heading,.form-signin .checkbox{margin-bottom:10px}.form-signin .checkbox{font-weight:normal}.form-signin .form-control{position:relative;height:auto;-webkit-box-sizing:border-box;-moz-box-sizing:border-box;box-sizing:border-box;padding:10px;font-size:16px}.form-signin .form-control:focus{z-index:2}.form-signin input[type="email"]{margin-bottom:-1px;border-bottom-right-radius:0;border-bottom-left-radius:0}.form-signin input[type="password"]{margin-bottom:10px;border-top-left-radius:0;border-top-right-radius:0}
|
||||||
|
body{padding-top:70px;padding-bottom:30px}.theme-dropdown .dropdown-menu{position:static;display:block;margin-bottom:20px}.theme-showcase>p>.btn{margin:5px 0}.theme-showcase .navbar .container{width:auto}
|
||||||
|
</style>
|
||||||
|
|
||||||
|
</head>
|
||||||
|
<body>
|
||||||
|
|
||||||
|
{% include 'blocks/menu' %}
|
||||||
|
|
||||||
|
<div class="container theme-showcase" role="main">
|
||||||
|
|
||||||
|
{% block content %}
|
||||||
|
Content of the page...
|
||||||
|
{% endblock %}
|
||||||
|
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<!-- Latest compiled and minified JavaScript -->
|
||||||
|
<script src="https://code.jquery.com/jquery-2.2.4.min.js" integrity="sha256-BbhdlvQf/xTY9gja0Dq3HiwQF8LaCRTXxZKRutelT44=" crossorigin="anonymous"></script>
|
||||||
|
<script src="https://maxcdn.bootstrapcdn.com/bootstrap/3.3.6/js/bootstrap.min.js" integrity="sha384-0mSbJDEHialfmuBBQP6A4Qrprq5OVfW37PRR3j5ELqxss1yVqOtnepnHVP9aJ7xS" crossorigin="anonymous"></script>
|
||||||
|
|
||||||
|
|
||||||
|
</body>
|
||||||
|
</html>
|
154
tests/src/Cache/AdapterTest.php
Normal file
154
tests/src/Cache/AdapterTest.php
Normal file
|
@ -0,0 +1,154 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier\Cache;
|
||||||
|
|
||||||
|
use Doctrine\Common\Cache\CacheProvider;
|
||||||
|
|
||||||
|
class AdapterTest extends \PHPUnit_Framework_TestCase
|
||||||
|
{
|
||||||
|
/** @var Adapter|\PHPUnit_Framework_MockObject_MockObject */
|
||||||
|
private $adapter;
|
||||||
|
|
||||||
|
/** @var CacheProvider|\PHPUnit_Framework_MockObject_MockObject */
|
||||||
|
private $cacheProvider;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function setUp()
|
||||||
|
{
|
||||||
|
$this->cacheProvider = $this->getMock(CacheProvider::class,
|
||||||
|
['doFetch', 'doContains', 'doSave', 'doDelete', 'doFlush', 'doGetStats']);
|
||||||
|
|
||||||
|
$this->adapter = $this->getMock(Adapter::class, ['getProvider', 'getType']);
|
||||||
|
$this->adapter->method('getProvider')->willReturn($this->cacheProvider);
|
||||||
|
$this->adapter->method('getType')->willReturn('Void Cache for tests');
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::has
|
||||||
|
*/
|
||||||
|
public function testHas()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::once())->method('doContains')
|
||||||
|
->with('namespaceTest[keyTest][1]')->willReturn(false);
|
||||||
|
|
||||||
|
self::assertEquals(false, $this->adapter->has('namespaceTest::keyTest'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::get
|
||||||
|
*/
|
||||||
|
public function testGet()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doFetch')
|
||||||
|
->with('namespaceTest[keyTest][1]')->willReturn(false);
|
||||||
|
|
||||||
|
self::assertEquals(false, $this->adapter->get('namespaceTest::keyTest'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::get
|
||||||
|
*/
|
||||||
|
public function testGetCallback()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doFetch')
|
||||||
|
->with('namespaceTest[keyTest][1]')->willReturn(false);
|
||||||
|
|
||||||
|
$callback = function ($cache, $key) {
|
||||||
|
return [$cache instanceof Adapter, $key];
|
||||||
|
};
|
||||||
|
|
||||||
|
self::assertEquals([true, 'namespaceTest::keyTest'], $this->adapter->get('namespaceTest::keyTest', $callback));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::set
|
||||||
|
*/
|
||||||
|
public function testSet()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doSave')
|
||||||
|
->with('namespaceTest[keyTest][1]', [1,2,3,4], 10)->willReturn(true);
|
||||||
|
|
||||||
|
self::assertEquals(true, $this->adapter->set('namespaceTest::keyTest', [1,2,3,4], 10));
|
||||||
|
}
|
||||||
|
|
||||||
|
public function testGets()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doFetch')
|
||||||
|
->with('namespaceTest[keyTest][1]')->willReturn('testValue');
|
||||||
|
|
||||||
|
self::assertEquals(['keyTest' => 'testValue'], $this->adapter->gets(['keyTest'], 'namespaceTest'));
|
||||||
|
}
|
||||||
|
|
||||||
|
public function testSets()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doSave')
|
||||||
|
->with('namespaceTest[keyTest][1]', [1,2,3,4], 10)->willReturn(true);
|
||||||
|
|
||||||
|
self::assertEquals(true, $this->adapter->sets(['keyTest' => [1,2,3,4]], 'namespaceTest', 10));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::delete
|
||||||
|
*/
|
||||||
|
public function testDelete()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doDelete')
|
||||||
|
->with('namespaceTest[keyTest][1]')->willReturn(true);
|
||||||
|
|
||||||
|
self::assertEquals(true, $this->adapter->delete('namespaceTest::keyTest'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::deleteAll
|
||||||
|
*/
|
||||||
|
public function testDeleteAll()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFetch')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]')->willReturn(false);
|
||||||
|
|
||||||
|
$this->cacheProvider->expects(self::at(1))->method('doSave')
|
||||||
|
->with('DoctrineNamespaceCacheKey[namespaceTest]', 2)->willReturn(true);
|
||||||
|
|
||||||
|
self::assertEquals(true, $this->adapter->deleteAll('namespaceTest'));
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::flush
|
||||||
|
*/
|
||||||
|
public function testFlush()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doFlush')->willReturn(true);
|
||||||
|
|
||||||
|
self::assertEquals(true, $this->adapter->flush());
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @covers TorrentPier\Cache\Adapter::stats
|
||||||
|
*/
|
||||||
|
public function testStats()
|
||||||
|
{
|
||||||
|
$this->cacheProvider->expects(self::at(0))->method('doGetStats')->willReturn(null);
|
||||||
|
|
||||||
|
self::assertEquals(['type' => 'Void Cache for tests'], $this->adapter->stats());
|
||||||
|
}
|
||||||
|
}
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
namespace TorrentPier\Cache;
|
namespace TorrentPier\Cache;
|
||||||
|
|
||||||
use Doctrine\Common\Cache\PhpFileCache;
|
use Doctrine\Common\Cache\FilesystemCache;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Class FileAdapterTest
|
* Class FileAdapterTest
|
||||||
|
@ -31,7 +31,7 @@ class FileAdapterTest extends \PHPUnit_Framework_TestCase
|
||||||
*/
|
*/
|
||||||
public function testAdapterCache()
|
public function testAdapterCache()
|
||||||
{
|
{
|
||||||
self::assertInstanceOf(PhpFileCache::class, $this->adapter->getProvider());
|
self::assertInstanceOf(FilesystemCache::class, $this->adapter->getProvider());
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -39,7 +39,7 @@ class FileAdapterTest extends \PHPUnit_Framework_TestCase
|
||||||
*/
|
*/
|
||||||
public function testStatsType()
|
public function testStatsType()
|
||||||
{
|
{
|
||||||
self::assertEquals('Cache in php file', $this->adapter->stats()['type']);
|
self::assertEquals('Filesystem Cache', $this->adapter->stats()['type']);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -31,7 +31,7 @@ class ConfigTest extends \PHPUnit_Framework_TestCase
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get value from array by key
|
* Get value from array by key.
|
||||||
*
|
*
|
||||||
* @see \TorrentPier\Config::get
|
* @see \TorrentPier\Config::get
|
||||||
*/
|
*/
|
||||||
|
|
209
tests/src/Db/AdapterTest.php
Normal file
209
tests/src/Db/AdapterTest.php
Normal file
|
@ -0,0 +1,209 @@
|
||||||
|
<?php
|
||||||
|
|
||||||
|
namespace TorrentPier\Db;
|
||||||
|
|
||||||
|
use Zend\Db\Adapter\Driver\Pdo\Result;
|
||||||
|
use Zend\Db\Adapter\Driver\Pdo\Statement;
|
||||||
|
use Zend\Db\Adapter\Driver\Pdo\Connection;
|
||||||
|
use Zend\Db\Adapter\Driver\Pdo\Pdo;
|
||||||
|
use Zend\Db\Adapter\Platform\AbstractPlatform;
|
||||||
|
use Zend\Db\Sql\Delete;
|
||||||
|
use Zend\Db\Sql\Insert;
|
||||||
|
use Zend\Db\Sql\Sql;
|
||||||
|
use Zend\Db\Sql\Update;
|
||||||
|
|
||||||
|
class AdapterTest extends \PHPUnit_Framework_TestCase
|
||||||
|
{
|
||||||
|
const AFFECTED_ROWS = 2;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var \PHPUnit_Framework_MockObject_MockObject|Adapter
|
||||||
|
*/
|
||||||
|
protected $adapterMock;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var \PHPUnit_Framework_MockObject_MockObject|Sql
|
||||||
|
*/
|
||||||
|
protected $sqlMock;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @var \PHPUnit_Framework_MockObject_MockObject|Statement
|
||||||
|
*/
|
||||||
|
protected $statementMock;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* {@inheritdoc}
|
||||||
|
*/
|
||||||
|
public function setUp()
|
||||||
|
{
|
||||||
|
$resultMock = $this->getMock(Result::class, ['getGeneratedValue', 'getAffectedRows']);
|
||||||
|
$resultMock->method('getGeneratedValue')->willReturn(self::AFFECTED_ROWS);
|
||||||
|
$resultMock->method('getAffectedRows')->willReturn(self::AFFECTED_ROWS);
|
||||||
|
|
||||||
|
$this->statementMock = $this->getMock(Statement::class, ['execute']);
|
||||||
|
$this->statementMock->method('execute')->willReturn($resultMock);
|
||||||
|
|
||||||
|
$this->adapterMock = $this->getMockBuilder(Adapter::class)
|
||||||
|
->setMethods(['getSql', 'getPlatform', 'getDriver'])
|
||||||
|
->disableOriginalConstructor()
|
||||||
|
->getMock();
|
||||||
|
|
||||||
|
$platformMock = $this->getMock(AbstractPlatform::class, ['getName', 'quoteIdentifier', 'quoteValue']);
|
||||||
|
$platformMock->method('quoteIdentifier')->willReturnCallback(function ($v) { return '`' . $v . '`'; });
|
||||||
|
$platformMock->method('quoteValue')->willReturnCallback(function ($v) {
|
||||||
|
if (is_int($v)) {
|
||||||
|
return $v;
|
||||||
|
} elseif ($v instanceof \DateTime) {
|
||||||
|
$v = $v->format('Y-m-d H:i:s');
|
||||||
|
}
|
||||||
|
|
||||||
|
return '\'' . $v . '\'';
|
||||||
|
});
|
||||||
|
$platformMock->method('getName')->willReturn('platform name');
|
||||||
|
$this->adapterMock->method('getPlatform')->willReturn($platformMock);
|
||||||
|
|
||||||
|
$connectionMock = $this->getMock(Connection::class);
|
||||||
|
|
||||||
|
$driverMock = $this->getMock(Pdo::class, [], [
|
||||||
|
$connectionMock,
|
||||||
|
$this->statementMock,
|
||||||
|
$resultMock,
|
||||||
|
]);
|
||||||
|
$this->adapterMock->method('getDriver')->willReturn($driverMock);
|
||||||
|
|
||||||
|
$this->sqlMock = $this->getMockBuilder(Sql::class)
|
||||||
|
->setMethods(['prepareStatementForSqlObject'])
|
||||||
|
->setConstructorArgs([$this->adapterMock])
|
||||||
|
->getMock();
|
||||||
|
$this->adapterMock->method('getSql')->willReturn($this->sqlMock);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create sql insert query.
|
||||||
|
* @covers \TorrentPier\Db\Adapter::insert
|
||||||
|
*/
|
||||||
|
public function testInsert()
|
||||||
|
{
|
||||||
|
$date = new \DateTime('now', new \DateTimeZone('UTC'));
|
||||||
|
|
||||||
|
$this->sqlMock->expects(static::once())
|
||||||
|
->method('prepareStatementForSqlObject')
|
||||||
|
->willReturnCallback(function (Insert $sqlObject) use ($date) {
|
||||||
|
static::assertEquals(
|
||||||
|
join(' ', [
|
||||||
|
"INSERT INTO",
|
||||||
|
"`tableName` (`field_int`, `field_str`, `field_date`)",
|
||||||
|
"VALUES (123, 'string', '{$date->format('Y-m-d H:i:s')}')",
|
||||||
|
]),
|
||||||
|
$this->sqlMock->buildSqlString($sqlObject)
|
||||||
|
);
|
||||||
|
return $this->statementMock;
|
||||||
|
});
|
||||||
|
|
||||||
|
$actual = $this->adapterMock->insert('tableName', [
|
||||||
|
'field_int' => 123,
|
||||||
|
'field_str' => 'string',
|
||||||
|
'field_date' => $date,
|
||||||
|
]);
|
||||||
|
|
||||||
|
static::assertEquals(self::AFFECTED_ROWS, $actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create sql update query.
|
||||||
|
* @covers \TorrentPier\Db\Adapter::update
|
||||||
|
*/
|
||||||
|
public function testUpdate()
|
||||||
|
{
|
||||||
|
$date = new \DateTime('now', new \DateTimeZone('UTC'));
|
||||||
|
|
||||||
|
$this->sqlMock->expects(static::once())
|
||||||
|
->method('prepareStatementForSqlObject')
|
||||||
|
->willReturnCallback(function (Update $sqlObject) use ($date) {
|
||||||
|
static::assertEquals(
|
||||||
|
join(' ', [
|
||||||
|
"UPDATE `tableName` SET",
|
||||||
|
"`field_int` = 123, `field_str` = 'string', `field_date` = '{$date->format('Y-m-d H:i:s')}'",
|
||||||
|
"WHERE \"field_id\" = 1"
|
||||||
|
]),
|
||||||
|
$this->sqlMock->buildSqlString($sqlObject)
|
||||||
|
);
|
||||||
|
return $this->statementMock;
|
||||||
|
});
|
||||||
|
|
||||||
|
$actual = $this->adapterMock->update('tableName', [
|
||||||
|
'field_int' => 123,
|
||||||
|
'field_str' => 'string',
|
||||||
|
'field_date' => $date,
|
||||||
|
], [
|
||||||
|
'field_id' => 1
|
||||||
|
]);
|
||||||
|
|
||||||
|
static::assertEquals(self::AFFECTED_ROWS, $actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create sql delete query.
|
||||||
|
* @covers \TorrentPier\Db\Adapter::delete
|
||||||
|
*/
|
||||||
|
public function testDelete()
|
||||||
|
{
|
||||||
|
$this->sqlMock->expects(static::once())
|
||||||
|
->method('prepareStatementForSqlObject')
|
||||||
|
->willReturnCallback(function (Delete $sqlObject) {
|
||||||
|
static::assertEquals(
|
||||||
|
"DELETE FROM `tableName` WHERE \"field_id\" = 1",
|
||||||
|
$this->sqlMock->buildSqlString($sqlObject)
|
||||||
|
);
|
||||||
|
return $this->statementMock;
|
||||||
|
});
|
||||||
|
|
||||||
|
$actual = $this->adapterMock->delete('tableName', [
|
||||||
|
'field_id' => 1
|
||||||
|
]);
|
||||||
|
|
||||||
|
static::assertEquals(self::AFFECTED_ROWS, $actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create sql increment query.
|
||||||
|
* @covers \TorrentPier\Db\Adapter::increment
|
||||||
|
*/
|
||||||
|
public function testIncrement()
|
||||||
|
{
|
||||||
|
$this->sqlMock->expects(static::once())
|
||||||
|
->method('prepareStatementForSqlObject')
|
||||||
|
->willReturnCallback(function (Update $sqlObject) {
|
||||||
|
static::assertEquals(
|
||||||
|
"UPDATE `tableName` SET `inc` = \"inc\" + 1 WHERE \"field_id\" = 1",
|
||||||
|
$this->sqlMock->buildSqlString($sqlObject)
|
||||||
|
);
|
||||||
|
return $this->statementMock;
|
||||||
|
});
|
||||||
|
|
||||||
|
$actual = $this->adapterMock->increment('tableName', 'inc', ['field_id' => 1]);
|
||||||
|
|
||||||
|
static::assertEquals(self::AFFECTED_ROWS, $actual);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Create sql decrement query.
|
||||||
|
* @covers \TorrentPier\Db\Adapter::decrement
|
||||||
|
*/
|
||||||
|
public function testDecrement()
|
||||||
|
{
|
||||||
|
$this->sqlMock->expects(static::once())
|
||||||
|
->method('prepareStatementForSqlObject')
|
||||||
|
->willReturnCallback(function (Update $sqlObject) {
|
||||||
|
static::assertEquals(
|
||||||
|
"UPDATE `tableName` SET `inc` = \"inc\" - 1 WHERE \"field_id\" = 1",
|
||||||
|
$this->sqlMock->buildSqlString($sqlObject)
|
||||||
|
);
|
||||||
|
return $this->statementMock;
|
||||||
|
});
|
||||||
|
|
||||||
|
$actual = $this->adapterMock->decrement('tableName', 'inc', ['field_id' => 1]);
|
||||||
|
|
||||||
|
static::assertEquals(self::AFFECTED_ROWS, $actual);
|
||||||
|
}
|
||||||
|
}
|
|
@ -1,20 +0,0 @@
|
||||||
<?php
|
|
||||||
|
|
||||||
namespace TorrentPier\Db;
|
|
||||||
|
|
||||||
class EntityTest extends \PHPUnit_Framework_TestCase
|
|
||||||
{
|
|
||||||
/**
|
|
||||||
* @covers TorrentPier\Db\Entity::table
|
|
||||||
*/
|
|
||||||
public function testGetTableName()
|
|
||||||
{
|
|
||||||
$model = new Model();
|
|
||||||
static::assertEquals('table name', $model->table());
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
class Model extends Entity
|
|
||||||
{
|
|
||||||
protected $table = 'table name';
|
|
||||||
}
|
|
|
@ -29,8 +29,8 @@ class DiTest extends \PHPUnit_Framework_TestCase
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @depends testGetInstanceIsNotInitialized
|
* @depends testGetInstanceIsNotInitialized
|
||||||
* @expectedException \RuntimeException
|
* @expectedException \InvalidArgumentException
|
||||||
* @expectedExceptionMessage Service 'test' is not registered in the container
|
* @expectedExceptionMessage Identifier "test" is not defined.
|
||||||
*/
|
*/
|
||||||
public function testGetByPropertyIsNotExists()
|
public function testGetByPropertyIsNotExists()
|
||||||
{
|
{
|
||||||
|
|
|
@ -14,7 +14,7 @@ class CaptchaServiceProviderTest extends \PHPUnit_Framework_TestCase
|
||||||
{
|
{
|
||||||
$di = new Di();
|
$di = new Di();
|
||||||
$di->register(new CaptchaServiceProvider, [
|
$di->register(new CaptchaServiceProvider, [
|
||||||
'config.captcha.secret_key' => 'secret key'
|
'config.services.captcha.secret_key' => 'secret key'
|
||||||
]);
|
]);
|
||||||
|
|
||||||
static::assertInstanceOf(ReCaptcha::class, $di->captcha);
|
static::assertInstanceOf(ReCaptcha::class, $di->captcha);
|
||||||
|
|
|
@ -9,13 +9,14 @@ namespace TorrentPier;
|
||||||
class ViewTest extends \PHPUnit_Framework_TestCase
|
class ViewTest extends \PHPUnit_Framework_TestCase
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
* @see \TorrentPier\View::make
|
* @covers \TorrentPier\View::make
|
||||||
*/
|
*/
|
||||||
public function testMake()
|
public function testMake()
|
||||||
{
|
{
|
||||||
$templateFileName = 'template';
|
$templateFileName = 'template';
|
||||||
$templateParam = ['key' => 'value'];
|
$templateParam = ['key' => 'value'];
|
||||||
|
|
||||||
|
/** @var \Twig_Environment|\PHPUnit_Framework_MockObject_MockObject $mockTwig */
|
||||||
$mockTwig = $this
|
$mockTwig = $this
|
||||||
->getMockBuilder(\Twig_Environment::class)
|
->getMockBuilder(\Twig_Environment::class)
|
||||||
->setMethods(['render'])
|
->setMethods(['render'])
|
||||||
|
@ -24,7 +25,7 @@ class ViewTest extends \PHPUnit_Framework_TestCase
|
||||||
$mockTwig
|
$mockTwig
|
||||||
->expects(static::once())
|
->expects(static::once())
|
||||||
->method('render')
|
->method('render')
|
||||||
->with(static::equalTo($templateFileName . '.twig'), static::equalTo($templateParam))
|
->with(static::equalTo($templateFileName), static::equalTo($templateParam))
|
||||||
->willReturnCallback(function () {
|
->willReturnCallback(function () {
|
||||||
return 'test render';
|
return 'test render';
|
||||||
});
|
});
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue