blueweather/api/blueweather.php

308 lines
9.3 KiB
PHP
Raw Normal View History

2019-07-15 20:29:19 +02:00
<?php
/**
* BlueWeather
*
* PHP version 7.2
*
* @category Tools
* @package BlueWeather
* @author Dorian Zedler <dorian@itsblue.de>
* @license GPLV3 gpl.com
* @link itsblue.de
*/
class BlueWeather
{
private $_config;
private $_con;
/**
* Constructor
*
* @param mixed $_config config array containing some stuff
*
* @return void
*/
public function __construct($_config)
{
$this->_config = $_config;
$this->_con = mysqli_connect(
$_config['dbhost'],
$_config['dbuser'],
$_config['dbpassword'],
$_config['dbname']
);
if (!$this->_con) {
echo "Error connecting to database: " . mysqli_connect_error();
http_response_code(500);
die();
}
}
2019-07-16 17:42:33 +02:00
// -------------------
// - user management -
// -------------------
2019-07-15 20:29:19 +02:00
/**
* Function to login users
*
* @param string $username username
* @param string $password passowrd
*
* @return string '' or session token
*/
public function loginUser($username, $password)
{
$sql = "SELECT * FROM `users`
WHERE`username`=\"".$this->_con->real_escape_string($username)."\"";
$result = $this->_con->query($sql);
// only one row will be returned
$data = $result->fetch_assoc();
if (!password_verify($password, $data['password'])) {
return "";
}
//generate random token
$length = 10;
$str = "";
$characters = array_merge(range('A', 'Z'), range('a', 'z'), range('0', '9'));
$max = count($characters) - 1;
for ($i = 0; $i < $length; $i++) {
$rand = mt_rand(0, $max);
$str .= $characters[$rand];
}
$token_hash = password_hash($str, PASSWORD_DEFAULT);
$sql = 'INSERT INTO `sessions` (userId, session)
VALUES ("'. $data['id'] .'", "'. $token_hash .'")';
if (!$this->_con->query($sql)) {
return "";
}
return $token_hash;
}
2019-07-16 17:42:33 +02:00
/**
* Function to check if a session token exists and get the corresponding user
*
* @param string $session session token
*
* @return int (-1: does not exist; x>0: userId)
*/
public function checkSession($session)
{
$sql = "SELECT * FROM `sessions`
WHERE`session`=\"".$this->_con->real_escape_string($session)."\"";
$result = $this->_con->query($sql);
if (!$result->num_rows > 0) {
return -1;
}
// only one row will be returned
$data = $result->fetch_assoc();
return($data['userId']);
}
2019-07-15 20:29:19 +02:00
// --------------------
// - getter functions -
// --------------------
/**
* Function to get all locations from the database
*
* @return mixed (array with all locations)
*/
public function getAllLocations()
{
// get all locations
$sql = "SELECT * FROM `locations`";
$result = $this->_con->query($sql);
//loop through the returned data
while ($row = $result->fetch_assoc()) {
$locations[] = $row;
}
return $locations;
}
/**
* Function to get the data of a specific location
*
* @param int $locId id of the location to return data of
* @param mixed $range contains 'from' and 'to' as unix timestamps
* @param int $maxVals maximum measvals to be transmitted; if more are
* present in the timespan, the avarage will be calculated
*
* @return mixed object with all information about the location (see docs)
*/
function getLocationData($locId, $range, $maxVals)
{
2019-07-15 20:42:06 +02:00
$locId = $this->_con->real_escape_string($locId);
$range["from"] = $this->_con->real_escape_string($range["from"]);
$range["to"] = $this->_con->real_escape_string($range["to"]);
$maxVals = $this->_con->real_escape_string($maxVals);
2019-07-15 20:29:19 +02:00
$sql = "SELECT * FROM `locations`
WHERE`id`=$locId";
$result = $this->_con->query($sql);
// only one row will be returned
$data = $result->fetch_assoc();
if (!isset($range['from']) || $range['from'] === "") {
$range['from'] = time() - 24 * 60 * 60;
}
if (!isset($range['to']) || $range['to'] === "") {
$range['to'] = time();
}
// get all measvalues of given location
$sql = "SELECT M.measvalue,M.sensorid,M.timestamp FROM measvalues M
JOIN sensors S ON M.sensorid = S.id
JOIN locations L ON S.locationid=L.id
WHERE L.id=$locId AND M.timestamp > " . $range['from'] .
2019-07-15 21:00:30 +02:00
" AND M.timestamp < " . $range['to'] .
" ORDER BY timestamp ASC";
2019-07-15 20:29:19 +02:00
$result = $this->_con->query($sql);
while ($row = $result->fetch_assoc()) {
$measvalues[] = $row;
}
// get all sensors of given location
$sql = "SELECT * FROM `sensors`
WHERE `locationid` = $locId";
$result = $this->_con->query($sql);
//loop through the returned data
while ($row = $result->fetch_assoc()) {
unset($row['locationid']); // remove locId as it is redundant
$sensors[] = $row;
}
// get all value types
$sql = "SELECT * FROM `valuetypes`";
$result = $this->_con->query($sql);
//loop through the returned data
while ($row = $result->fetch_assoc()) {
foreach ($sensors as $sensor) {
if ($sensor['valuetypeid'] == $row['id']) {
$valuetypes[] = $row;
break;
}
}
}
2019-07-16 17:42:33 +02:00
if (isset($maxVals) && $maxVals > 0) {
2019-07-15 20:29:19 +02:00
// build the new measvalues array with respect to maxVals for each sensor
$finalMeasvals = array();
foreach ($sensors as $sensor) {
// get all measvalues of the current sensor
$rawMeasvalsOfThisSensor = array();
$finalMeasvalsOfThisSensor = array();
foreach ($measvalues as $measvalue) {
if ($measvalue["sensorid"] === $sensor["id"]) {
array_push($rawMeasvalsOfThisSensor, $measvalue);
}
}
2019-07-16 17:42:33 +02:00
if (count($rawMeasvalsOfThisSensor) <= $maxVals) {
2019-07-16 17:44:04 +02:00
$finalMeasvals = array_merge(
$finalMeasvals, $rawMeasvalsOfThisSensor
);
2019-07-16 17:42:33 +02:00
continue;
}
2019-07-15 20:29:19 +02:00
// always sum up the same amount of values to get a new array
// which doesn't have more than $maxVals values
$countOfValuesForAvarage = intval(
round(count($rawMeasvalsOfThisSensor) / $maxVals, 0)
);
$takenValuesForNextSum = 0;
$tmpMeasvalueSum = 0;
$tmpTimestampSum = 0;
for ($i = 0; $i < count($rawMeasvalsOfThisSensor); $i++) {
// loop through all measvals of the sensor
$measvalue = $rawMeasvalsOfThisSensor[$i];
if ($measvalue["sensorid"] === $sensor["id"]) {
$tmpMeasvalueSum += $measvalue["measvalue"];
$tmpTimestampSum += $measvalue["timestamp"];
$takenValuesForNextSum += 1;
}
if ($takenValuesForNextSum === $countOfValuesForAvarage || $i === count($rawMeasvalsOfThisSensor) - 1) {
array_push(
$finalMeasvalsOfThisSensor,
array(
"measvalue" => round(
$tmpMeasvalueSum / $takenValuesForNextSum, 2
),
"timestamp" => round(
$tmpTimestampSum / $takenValuesForNextSum, 0
),
"sensorid" => $sensor["id"]
)
);
$takenValuesForNextSum = 0;
$tmpMeasvalueSum = 0;
$tmpTimestampSum = 0;
}
}
// insert the new vals of this sensor into the global new vals
$finalMeasvals = array_merge(
$finalMeasvals, $finalMeasvalsOfThisSensor
);
}
$measvalues = $finalMeasvals;
}
// find actual range
$min = null;
$max = null;
foreach ($measvalues as $value) {
if ($value['timestamp'] < $min || !isset($min)) {
$min = $value['timestamp'];
} else if ($value['timestamp'] > $max || !isset($max)) {
$max = $value['timestamp'];
}
}
// add sensors and value types to data object
$data['measvalues'] = $measvalues;
$data['sensors'] = $sensors;
$data['valuetypes'] = $valuetypes;
$data['range'] = array('from' => $min, 'to' => $max);
return $data;
}
}
?>