init
This commit is contained in:
parent
f020707f5c
commit
44e77d8a18
|
@ -0,0 +1,2 @@
|
|||
# phpstorm project files
|
||||
.idea
|
|
@ -0,0 +1,80 @@
|
|||
<?php
|
||||
|
||||
namespace bethrezen\arangodb;
|
||||
|
||||
use Yii;
|
||||
use Closure;
|
||||
use yii\helpers\Html;
|
||||
use yii\helpers\Url;
|
||||
|
||||
use kartik\icons\Icon;
|
||||
|
||||
class ActionColumn extends \yii\grid\Column
|
||||
{
|
||||
public $buttons = [
|
||||
[
|
||||
'url' => 'edit',
|
||||
'icon' => 'pencil',
|
||||
'class' => 'btn-primary',
|
||||
'label' => 'Edit',
|
||||
],
|
||||
[
|
||||
'url' => 'delete',
|
||||
'icon' => 'trash-o',
|
||||
'class' => 'btn-danger',
|
||||
'label' => 'Delete',
|
||||
],
|
||||
];
|
||||
/**
|
||||
* @var string the ID of the controller that should handle the actions specified here.
|
||||
* If not set, it will use the currently active controller. This property is mainly used by
|
||||
* [[urlCreator]] to create URLs for different actions. The value of this property will be prefixed
|
||||
* to each action name to form the route of the action.
|
||||
*/
|
||||
public $controller;
|
||||
/**
|
||||
* @var callable a callback that creates a button URL using the specified model information.
|
||||
* The signature of the callback should be the same as that of [[createUrl()]].
|
||||
* If this property is not set, button URLs will be created using [[createUrl()]].
|
||||
*/
|
||||
public $urlCreator;
|
||||
|
||||
/**
|
||||
* Creates a URL for the given action and model.
|
||||
* This method is called for each button and each row.
|
||||
* @param string $action the button name (or action ID)
|
||||
* @param \yii\db\ActiveRecord $model the data model
|
||||
* @param mixed $key the key associated with the data model
|
||||
* @param integer $index the current row index
|
||||
* @return string the created URL
|
||||
*/
|
||||
public function createUrl($action, $model, $key, $index)
|
||||
{
|
||||
if ($this->urlCreator instanceof Closure) {
|
||||
return call_user_func($this->urlCreator, $action, $model, $key, $index);
|
||||
} else {
|
||||
$params = is_array($key) ? $key : ['id' => (string) $key];
|
||||
$params[0] = $this->controller ? $this->controller . '/' . $action : $action;
|
||||
|
||||
return Url::toRoute($params);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
protected function renderDataCellContent($model, $key, $index)
|
||||
{
|
||||
$data = '';
|
||||
foreach ($this->buttons as $button) {
|
||||
$data .= Html::a(
|
||||
Icon::show($button['icon']).' '.$button['label'],
|
||||
$url = $this->createUrl($button['url'], $model, $key, $index),
|
||||
[
|
||||
'data-pjax' => 0,
|
||||
'class' => 'btn btn-xs '.$button['class']
|
||||
]
|
||||
) . ' ';
|
||||
}
|
||||
|
||||
return $data;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,76 @@
|
|||
<?php
|
||||
|
||||
namespace bethrezen\arangodb;
|
||||
|
||||
use yii\helpers\ArrayHelper;
|
||||
use yii\base\Object;
|
||||
|
||||
// set up some aliases for less typing later
|
||||
use triagens\ArangoDb\Connection as ArangoConnection;
|
||||
use triagens\ArangoDb\ConnectionOptions as ArangoConnectionOptions;
|
||||
use triagens\ArangoDb\DocumentHandler as ArangoDocumentHandler;
|
||||
|
||||
use triagens\ArangoDb\Document as ArangoDocument;
|
||||
use triagens\ArangoDb\Exception as ArangoException;
|
||||
use triagens\ArangoDb\ConnectException as ArangoConnectException;
|
||||
use triagens\ArangoDb\ClientException as ArangoClientException;
|
||||
use triagens\ArangoDb\ServerException as ArangoServerException;
|
||||
use triagens\ArangoDb\UpdatePolicy as ArangoUpdatePolicy;
|
||||
use triagens\ArangoDb\Statement as Statement;
|
||||
|
||||
class ArangoDbConnection extends Object {
|
||||
private $_connection = null;
|
||||
public $connectionOptions = [
|
||||
// server endpoint to connect to
|
||||
ArangoConnectionOptions::OPTION_ENDPOINT => 'tcp://127.0.0.1:8529',
|
||||
// authorization type to use (currently supported: 'Basic')
|
||||
ArangoConnectionOptions::OPTION_AUTH_TYPE => 'Basic',
|
||||
// user for basic authorization
|
||||
ArangoConnectionOptions::OPTION_AUTH_USER => 'root',
|
||||
// password for basic authorization
|
||||
ArangoConnectionOptions::OPTION_AUTH_PASSWD => '',
|
||||
// connection persistence on server. can use either 'Close' (one-time connections) or 'Keep-Alive' (re-used connections)
|
||||
ArangoConnectionOptions::OPTION_CONNECTION => 'Close',
|
||||
// connect timeout in seconds
|
||||
ArangoConnectionOptions::OPTION_TIMEOUT => 3,
|
||||
// whether or not to reconnect when a keep-alive connection has timed out on server
|
||||
ArangoConnectionOptions::OPTION_RECONNECT => true,
|
||||
// optionally create new collections when inserting documents
|
||||
ArangoConnectionOptions::OPTION_CREATE => true,
|
||||
// optionally create new collections when inserting documents
|
||||
ArangoConnectionOptions::OPTION_UPDATE_POLICY => ArangoUpdatePolicy::LAST,
|
||||
];
|
||||
|
||||
private $_collectionHandler = null;
|
||||
private $_documentHandler = null;
|
||||
|
||||
public function __construct($config=[])
|
||||
{
|
||||
parent::__construct($config);
|
||||
}
|
||||
|
||||
public function init()
|
||||
{
|
||||
parent::init();
|
||||
|
||||
$this->_connection = new ArangoConnection($this->connectionOptions);
|
||||
$this->_collectionHandler = new \triagens\ArangoDb\CollectionHandler($this->_connection);
|
||||
$this->_documentHandler = new \triagens\ArangoDb\DocumentHandler($this->_connection);
|
||||
}
|
||||
|
||||
public function getDocument($collection, $id) {
|
||||
return $this->documentHandler()->get($collection, $id);
|
||||
}
|
||||
|
||||
public function documentHandler() {
|
||||
return $this->_documentHandler;
|
||||
}
|
||||
|
||||
public function statement($options=[]) {
|
||||
return new Statement($this->_connection, $options);
|
||||
}
|
||||
|
||||
public function collectionHandler() {
|
||||
return $this->_collectionHandler;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,100 @@
|
|||
<?php
|
||||
|
||||
namespace bethrezen\arangodb;
|
||||
|
||||
use yii;
|
||||
|
||||
|
||||
use triagens\ArangoDb\Document;
|
||||
|
||||
class ArangoModel extends \yii\base\model {
|
||||
|
||||
private $_isNewRecord = true;
|
||||
|
||||
private $_doc = null;
|
||||
|
||||
|
||||
public static function findById($id)
|
||||
{
|
||||
$parts = explode("\\", $id);
|
||||
if (count($parts)==2) {
|
||||
$id = $parts[1]; // для формата "Collection\1237643123"
|
||||
} else {
|
||||
$parts = explode("/", $id); // для формата "Collection/123123321"
|
||||
if (count($parts)==2) {
|
||||
$id = $parts[1];
|
||||
}
|
||||
}
|
||||
$model = new static;
|
||||
$model
|
||||
->setDocument(Yii::$app->arango->getDocument(static::class_to_collection(get_called_class()), $id))
|
||||
->setIsNewRecord(false);
|
||||
|
||||
return $model;
|
||||
}
|
||||
|
||||
/**
|
||||
* @todo функция должна возвращать true/false в зависимости от результата
|
||||
* Но аранга возвращает различный тип данных. Надо написать код
|
||||
*
|
||||
*/
|
||||
public function save()
|
||||
{
|
||||
if ($this->_isNewRecord) {
|
||||
// добавляем запись
|
||||
$this->_doc = Document::createFromArray($this->getAttributes());
|
||||
|
||||
return intval(Yii::$app->arango->documentHandler()->add(static::class_to_collection(get_called_class()), $this->_doc)) > 0;
|
||||
} else {
|
||||
// патчим!
|
||||
$doc_attributes = array_keys($this->_doc->getAll());
|
||||
|
||||
$attributes = $this->getAttributes();
|
||||
foreach ($attributes as $k=>$v) {
|
||||
$this->_doc->set($k, $v);
|
||||
unset($doc_attributes[$k]);
|
||||
}
|
||||
foreach ($doc_attributes as $key) {
|
||||
if ($key != '_key')
|
||||
unset($this->_doc->$key);
|
||||
}
|
||||
return Yii::$app->arango->documentHandler()->update($this->_doc);
|
||||
}
|
||||
}
|
||||
|
||||
private static function class_to_collection($class)
|
||||
{
|
||||
$parts = explode("\\", $class);
|
||||
return end($parts);
|
||||
}
|
||||
private static function id_to_int($class)
|
||||
{
|
||||
$parts = explode("/", $class);
|
||||
return end($parts);
|
||||
}
|
||||
|
||||
public function setIsNewRecord($state)
|
||||
{
|
||||
$this->_isNewRecord = $state;
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function setDocument($doc)
|
||||
{
|
||||
$this->_doc = $doc;
|
||||
$all = $this->_doc->getAll();
|
||||
$this->_id = $this->_doc->getInternalId();
|
||||
$this->setAttributes($all, false);
|
||||
|
||||
return $this;
|
||||
}
|
||||
|
||||
public function delete()
|
||||
{
|
||||
|
||||
Yii::$app->arango->documentHandler()->deleteById(
|
||||
static::class_to_collection(get_called_class()),
|
||||
static::id_to_int($this->_doc->getInternalId())
|
||||
);
|
||||
}
|
||||
}
|
|
@ -0,0 +1,133 @@
|
|||
<?php
|
||||
|
||||
namespace bethrezen\arangodb;
|
||||
|
||||
use yii;
|
||||
use yii\di\Instance;
|
||||
|
||||
use triagens\ArangoDb\Document;
|
||||
|
||||
use app;
|
||||
|
||||
class ArangoProvider extends yii\data\ActiveDataProvider
|
||||
{
|
||||
public $arango = 'arango';
|
||||
|
||||
public $collection;
|
||||
|
||||
/**
|
||||
* @var array parameters for example
|
||||
*/
|
||||
public $params = [];
|
||||
|
||||
public function init()
|
||||
{
|
||||
parent::init();
|
||||
$this->arango = Instance::ensure($this->arango, app\components\ArangoDbConnection::className());
|
||||
if ($this->collection === null) {
|
||||
throw new InvalidConfigException('The "collection" property must be set.');
|
||||
}
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected function prepareKeys($models)
|
||||
{
|
||||
|
||||
return array_keys($models);
|
||||
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected function prepareModels()
|
||||
{
|
||||
// $sql = $this->sql;
|
||||
// $qb = $this->db->getQueryBuilder();
|
||||
// if (($sort = $this->getSort()) !== false) {
|
||||
// $orderBy = $qb->buildOrderBy($sort->getOrders());
|
||||
// if (!empty($orderBy)) {
|
||||
// $orderBy = substr($orderBy, 9);
|
||||
// if (preg_match('/\s+order\s+by\s+[\w\s,\.]+$/i', $sql)) {
|
||||
// $sql .= ', ' . $orderBy;
|
||||
// } else {
|
||||
// $sql .= ' ORDER BY ' . $orderBy;
|
||||
// }
|
||||
// }
|
||||
// }
|
||||
|
||||
// if (($pagination = $this->getPagination()) !== false) {
|
||||
// $pagination->totalCount = $this->getTotalCount();
|
||||
// $sql .= ' ' . $qb->buildLimit($pagination->getLimit(), $pagination->getOffset());
|
||||
// }
|
||||
|
||||
// return $this->db->createCommand($sql, $this->params)->queryAll();
|
||||
$statement = $this->getBaseStatement();
|
||||
|
||||
if (($pagination = $this->getPagination()) !== false) {
|
||||
$pagination->totalCount = $this->getTotalCount();
|
||||
$statement->setQuery($statement->getQuery() . "\n LIMIT " . $pagination->getOffset() . ", " . $pagination->getLimit());
|
||||
}
|
||||
|
||||
|
||||
$statement->setQuery($statement->getQuery()."\n RETURN a");
|
||||
$cursor = $statement->execute();
|
||||
$data = $cursor->getAll();
|
||||
$result = [];
|
||||
foreach ($data as $doc) {
|
||||
$item = $doc->getAll();
|
||||
foreach ($item as $k=>$v) {
|
||||
if (is_array($item[$k]) || is_object($item[$k])) {
|
||||
$item[$k] = json_encode($v, true);
|
||||
}
|
||||
}
|
||||
$result[$item['_key']] = $item;
|
||||
}
|
||||
$pagination->totalCount = $cursor->getFullCount();
|
||||
|
||||
return $result;
|
||||
}
|
||||
|
||||
public function getTotalCount() {
|
||||
$statement = $this->getBaseStatement();
|
||||
$statement->setQuery($statement->getQuery(). "\n LIMIT 1 \n RETURN a");
|
||||
|
||||
|
||||
$cursor = $statement->execute();
|
||||
return $cursor->getFullCount();
|
||||
}
|
||||
|
||||
private function getBaseStatement() {
|
||||
$query = "FOR a in @@collection\n";
|
||||
|
||||
$filter = [];
|
||||
$bindings = ['@collection' => $this->collection];
|
||||
$counter = 0;
|
||||
foreach ($this->params as $k => $v) {
|
||||
$filter[] = " a.@filter_field_$counter == @filter_value_$counter ";
|
||||
$bindings["filter_field_$counter"] = $k;
|
||||
$bindings["filter_value_$counter"] = $v;
|
||||
$counter++;
|
||||
}
|
||||
if (count($filter)>0){
|
||||
$query .= "\nFILTER ".implode(" && ", $filter)."\n";
|
||||
}
|
||||
$statement = $this->arango->statement([
|
||||
'query' => $query,
|
||||
'count' => true,
|
||||
'bindVars' => $bindings,
|
||||
'fullCount' => true,
|
||||
]);
|
||||
return $statement;
|
||||
}
|
||||
|
||||
/**
|
||||
* @inheritdoc
|
||||
*/
|
||||
protected function prepareTotalCount()
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,22 @@
|
|||
{
|
||||
"name": "bethrezen/yii2-arangodb",
|
||||
"description": "Yii2 arangodb components",
|
||||
"type": "yii2-extension",
|
||||
"keywords": ["yii2","arangodb"],
|
||||
"license": "GPL-3.0+",
|
||||
"authors": [
|
||||
{
|
||||
"name": "Alexander Kozhevnikov",
|
||||
"email": "b37hr3z3n@gmail.com"
|
||||
}
|
||||
],
|
||||
"require": {
|
||||
"yiisoft/yii2": "*",
|
||||
"triagens/arangodb": "*"
|
||||
},
|
||||
"autoload": {
|
||||
"psr-4": {
|
||||
"bethrezen\\arangodb\\": ""
|
||||
}
|
||||
}
|
||||
}
|
Loading…
Reference in New Issue