From aa2b4c40fca515108aac72b7a88762bfcfbcef7e Mon Sep 17 00:00:00 2001 From: Alex Solomaha Date: Fri, 19 Aug 2016 17:48:27 +0300 Subject: [PATCH] Some work --- components/ApiHelper.php | 51 ++++++++++------ components/ApiHelperInterface.php | 11 ++++ config/params.php | 6 +- models/Item.php | 3 + servers/Panel.php | 98 +++++++++++++------------------ 5 files changed, 92 insertions(+), 77 deletions(-) create mode 100644 components/ApiHelperInterface.php diff --git a/components/ApiHelper.php b/components/ApiHelper.php index 9155ffc..d81d424 100644 --- a/components/ApiHelper.php +++ b/components/ApiHelper.php @@ -5,17 +5,36 @@ namespace app\components; use app\models\Item; use linslin\yii2\curl\Curl; use Yii; +use yii\base\Component; use yii\helpers\Json; -class ApiHelper +class ApiHelper extends Component implements ApiHelperInterface { + /** + * @var Item + */ + public $item; + + /** + * ApiHelper constructor. + * @param Item $item + */ + public function __construct(Item $item) + { + parent::__construct(); + + $this->item = $item; + + return $this; + } + /** * Get CURL instance * * @param int $timeout * @return Curl */ - public static function getCurl($timeout = 2) + public function getCurl($timeout = 2) { $curl = new Curl(); $curl->setOption(CURLOPT_TIMEOUT, $timeout); @@ -26,9 +45,9 @@ class ApiHelper /** * @return string */ - public static function getBaseUrl($item) + public function getBaseUrl() { - return Yii::$app->params['apiBaseUrl']; + return $this->item->board->baseUrl; } /** @@ -37,21 +56,19 @@ class ApiHelper * @param $url * @return array */ - public static function makeRequest($url) + public function makeRequestToApi($url) { - $curl = self::getCurl(); - $response = $curl->get(self::getBaseUrl() . $url); + $response = $this->getCurl()->get($this->getBaseUrl() . $url); return Json::decode($response); } /** - * @param Item $item * @return mixed */ - public static function getItemValue($item) + public function getValue() { - $data = self::makeRequest($item->url); + $data = $this->makeRequestToApi($this->item->url); return $data['value']; } @@ -59,22 +76,20 @@ class ApiHelper /** * Turn item on and return current state * - * @param Item $item - * @return boolean + * @return array */ - public static function itemTurnOn($item) + public function turnOn() { - return self::makeRequest($item->url . '/1'); + return $this->makeRequestToApi($this->item->url . '/1'); } /** * Turn item off and return current state * - * @param Item $item - * @return boolean + * @return array */ - public static function itemTurnOff($item) + public function turnOff() { - return self::makeRequest($item->url . '/0'); + return $this->makeRequestToApi($this->item->url . '/0'); } } diff --git a/components/ApiHelperInterface.php b/components/ApiHelperInterface.php new file mode 100644 index 0000000..2719071 --- /dev/null +++ b/components/ApiHelperInterface.php @@ -0,0 +1,11 @@ + 'admin@example.com', - 'apiBaseUrl' => 'http://176.36.54.229', + 'auth' => [ + 'tokenExpireSec' => 2, + ], ]; -return ArrayHelper::merge($params, require 'params-local.php'); \ No newline at end of file +return ArrayHelper::merge($params, require 'params-local.php'); diff --git a/models/Item.php b/models/Item.php index da927c3..70e2030 100644 --- a/models/Item.php +++ b/models/Item.php @@ -33,6 +33,9 @@ class Item extends ActiveRecord const TYPE_VARIABLE_BOOLEAN = 25; const TYPE_VARIABLE_BOOLEAN_DOOR = 26; + const VALUE_ON = 1; + const VALUE_OFF = 0; + /** * @inheritdoc */ diff --git a/servers/Panel.php b/servers/Panel.php index eadb74e..3e1b353 100644 --- a/servers/Panel.php +++ b/servers/Panel.php @@ -8,6 +8,7 @@ use app\models\Item; use app\models\User; use Ratchet\ConnectionInterface; use Ratchet\MessageComponentInterface; +use Ratchet\WebSocket\Version\RFC6455\Connection; use React\EventLoop\LoopInterface; use Yii; use yii\helpers\Json; @@ -65,7 +66,7 @@ class Panel implements MessageComponentInterface $this->items[$item->id] = $item; if ($item->save_history_interval > 0) { - $this->loop->addPeriodicTimer($item->save_history_interval, function () { + $this->loop->addPeriodicTimer($item->save_history_interval, function () use ($item) { $this->saveHistory($item); }); } @@ -80,8 +81,36 @@ class Panel implements MessageComponentInterface // Get query $query = $conn->WebSocket->request->getQuery(); - // Welcome user - return $this->auth($conn, $query); + $id = $query->get('id'); + $time = $query->get('time'); + $token = $query->get('token'); + + if ((time() - $time) >= Yii::$app->params['auth']['tokenExpireSec']) { + return $this->log("Auth failed (Token expired). ID: $id; Token: $token; IP: {$conn->remoteAddress}; Timestamp: $time"); + } + + // Find user by auth info + /** @var User $user */ + $user = User::findOne([ + 'id' => $id, + 'auth_key' => $token, + ]); + + // Security checks + if (!$user) { + return $this->log("Auth failed. ID: $id; Token: $token; IP: {$conn->remoteAddress}; Timestamp: $time"); + } + + // Close previous connection + if (isset($this->clients[$user->id])) { + $this->clients[$user->id]->close(); + } + + // Attach to online users + $conn->User = $user; + $this->clients[$user->id] = $conn; + + return $this->log("Connected new user [$id] {$user->username}"); } public function onMessage(ConnectionInterface $from, $msg) @@ -95,7 +124,7 @@ class Panel implements MessageComponentInterface /** @var User $user */ $user = $from->User; - $data = json_decode($msg, true); + $data = Json::decode($msg); if ($data['type'] === 'switch') { return $this->handleSwitch($from, $user, $data); @@ -118,57 +147,12 @@ class Panel implements MessageComponentInterface public function onError(ConnectionInterface $conn, \Exception $e) { // Logging - echo "An error has occurred: {$e->getMessage()} in file {$e->getFile()} at line {$e->getLine()}" . PHP_EOL; + echo "Error: {$e->getMessage()} in file {$e->getFile()} at line {$e->getLine()}" . PHP_EOL; // Close connection $conn->close(); } - /** - * Authenticate connected user - * - * @param ConnectionInterface $conn - * @param $query - * @return bool - */ - protected function auth(ConnectionInterface $conn, $query) - { - $id = $query->get('id'); - $time = $query->get('time'); - $token = $query->get('token'); - - if ((time() - $time) >= Yii::$app->params['auth']['tokenExpireSec']) { - echo 'Token expired' . PHP_EOL; - - return false; - } - - // Find user by auth info - /** @var User $user */ - $user = User::findOne([ - 'id' => $id, - 'auth_key' => $token, - ]); - - // Security checks - if (!$user) { - echo 'Wrong token or id: steamID: "' . $id . '", token: "' . $token . '", IP: ' . $conn->remoteAddress . ', time: ' . $time . PHP_EOL; - - return false; - } - - // Close previous connection - if (isset($this->clients[$user->id])) { - $this->clients[$user->id]->close(); - } - - // Attach to online users - $conn->User = $user; - $this->clients[$user->id] = $conn; - - return true; - } - /** * @param ConnectionInterface $from * @param User $user @@ -195,9 +179,10 @@ class Panel implements MessageComponentInterface ]); } - ApiHelper::itemTurnOn($item); + $api = new ApiHelper($item); + $api->turnOn(); - return $this->saveHistory($item, 1); + return $this->saveHistory($item, Item::VALUE_ON); } /** @@ -219,7 +204,7 @@ class Panel implements MessageComponentInterface * * @param integer $user_id * @param array $data - * @return bool + * @return bool|mixed */ private function sendTo($user_id, $data) { @@ -227,9 +212,7 @@ class Panel implements MessageComponentInterface /** @var ConnectionInterface $client */ $client = $this->clients[$user_id]; - $client->send(Json::encode($data)); - - return true; + return $client->send(Json::encode($data)); } return false; @@ -254,7 +237,8 @@ class Panel implements MessageComponentInterface { if ($value === null) { try { - $value = ApiHelper::getItemValue($item); + $api = new ApiHelper($item); + $value = $api->getValue(); } catch (\Exception $e) { return false; }