199 lines
5.8 KiB
PHP
199 lines
5.8 KiB
PHP
<?php
|
|
|
|
class YandexIoT
|
|
{
|
|
private string $clientId;
|
|
private string $clientSecret;
|
|
private ?string $accessToken = null;
|
|
private ?string $refreshToken = null;
|
|
|
|
public function __construct(
|
|
string $clientId,
|
|
string $clientSecret,
|
|
?string $accessToken = null,
|
|
?string $refreshToken = null
|
|
) {
|
|
$this->clientId = $clientId;
|
|
$this->clientSecret = $clientSecret;
|
|
$this->accessToken = $accessToken;
|
|
$this->refreshToken = $refreshToken;
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function initFromFile(string $file): self
|
|
{
|
|
if (!file_exists($file)) {
|
|
throw new RuntimeException('Файл для инициализации не найден');
|
|
}
|
|
$data = json_decode(file_get_contents($file), true, 512, JSON_THROW_ON_ERROR);
|
|
$this->accessToken = $data['access_token'] ?? null;
|
|
$this->refreshToken = $data['access_token'] ?? null;
|
|
return $this;
|
|
}
|
|
|
|
/**
|
|
* Отправка запроса
|
|
*
|
|
* @param string $url
|
|
* @param array $headers
|
|
* @param array|null $data
|
|
* @param string|null $method
|
|
* @return array
|
|
* @throws JsonException
|
|
*/
|
|
public static function sendRequest(string $url, array $headers = [], ?array $data = null, ?string $method = null): array
|
|
{
|
|
$ch = curl_init();
|
|
curl_setopt($ch, CURLOPT_URL, $url);
|
|
|
|
if (!empty($method)) {
|
|
curl_setopt($ch, CURLOPT_CUSTOMREQUEST, $method);
|
|
}
|
|
|
|
if (!empty($data)) {
|
|
curl_setopt($ch, CURLOPT_POST, 1);
|
|
curl_setopt($ch, CURLOPT_POSTFIELDS, http_build_query($data));
|
|
}
|
|
|
|
curl_setopt($ch, CURLOPT_FAILONERROR, 0);
|
|
curl_setopt($ch, CURLOPT_FOLLOWLOCATION, 0);
|
|
curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1);
|
|
curl_setopt($ch, CURLOPT_VERBOSE, 0);
|
|
curl_setopt($ch, CURLOPT_TIMEOUT, 5);
|
|
curl_setopt($ch, CURLOPT_HTTPHEADER, $headers);
|
|
$result = curl_exec($ch);
|
|
$result = json_decode($result, true, 512, JSON_THROW_ON_ERROR);
|
|
curl_close($ch);
|
|
return $result;
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function sendYandexRequest(
|
|
string $function,
|
|
array $additionalHeaders = [],
|
|
?array $data = null,
|
|
?string $method = null
|
|
): array {
|
|
$apiUrl = 'https://api.iot.yandex.net';
|
|
$url = $apiUrl . $function;
|
|
$headers = array_merge(['Authorization: Bearer ' . $this->getAccessToken()], $additionalHeaders);
|
|
return (self::sendRequest($url, $headers, $data, $method));
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function getPowerState(string $deviceId): bool
|
|
{
|
|
$function = '/v1.0/devices/' . $deviceId;
|
|
$result = $this->sendYandexRequest($function);
|
|
if (isset($result['capabilities'])) {
|
|
foreach ($result['capabilities'] as $capability) {
|
|
if ($capability['type'] === 'devices.capabilities.on_off') {
|
|
return (int)$capability['state']['value'] === 1;
|
|
}
|
|
}
|
|
}
|
|
return false;
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function getProps(string $deviceId): array
|
|
{
|
|
$res = [];
|
|
$function = '/v1.0/devices/' . $deviceId;
|
|
$result = $this->sendYandexRequest($function);
|
|
|
|
// состояние по умолчанию
|
|
$res['state'] = false;
|
|
|
|
if (isset($result['capabilities'])) {
|
|
foreach ($result['capabilities'] as $capability) {
|
|
if ($capability['type'] === 'devices.capabilities.on_off' && (int)$capability['state']['value'] === 1) {
|
|
$res['state'] = true;
|
|
break;
|
|
}
|
|
}
|
|
}
|
|
|
|
if (isset($result['properties'])) {
|
|
foreach ($result['properties'] as $prop) {
|
|
$res[$prop['state']['instance']] = $prop['state']['value'];
|
|
}
|
|
}
|
|
return $res;
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function getInfo(): array
|
|
{
|
|
$function = '/v1.0/user/info';
|
|
return $this->sendYandexRequest($function);
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function setPowerState(string $deviceId, bool $state): bool
|
|
{
|
|
$function = '/v1.0/devices/actions';
|
|
$headers = ['Content-Type: application/json'];
|
|
$data = [
|
|
'devices' => [
|
|
'actions' => [
|
|
'state' => [
|
|
'instance' => 'on',
|
|
'value' => $state ? 'true' : 'false',
|
|
],
|
|
'type' => 'devices.capabilities.on_off',
|
|
],
|
|
'id' => $deviceId,
|
|
],
|
|
];
|
|
$result = $this->sendYandexRequest($function, $headers, $data);
|
|
return isset($result['status']) && $result['status'] === 'ok';
|
|
}
|
|
|
|
public function getAccessToken(): ?string
|
|
{
|
|
return $this->accessToken;
|
|
}
|
|
|
|
public function getRefreshToken(): ?string
|
|
{
|
|
return $this->refreshToken;
|
|
}
|
|
|
|
/**
|
|
* @throws JsonException
|
|
*/
|
|
public function updateToken(): bool
|
|
{
|
|
$url = 'https://oauth.yandex.ru/token';
|
|
$auth = base64_encode($this->clientId . ':' . $this->clientSecret);
|
|
$headers = [
|
|
'Authorization: Basic ' . $auth,
|
|
'application/x-www-form-urlencoded'
|
|
];
|
|
$data = [
|
|
'grant_type' => 'refresh_token',
|
|
'refresh_token' => $this->getRefreshToken(),
|
|
];
|
|
$response = self::sendRequest($url, $headers, $data);
|
|
if (isset($response['access_token'])) {
|
|
$this->accessToken = '';
|
|
$this->refreshToken = '';
|
|
return true;
|
|
}
|
|
|
|
return false;
|
|
}
|
|
} |