From e5bad9e959b6e0d29dfbc7d5dc7533f633c5bd97 Mon Sep 17 00:00:00 2001 From: Bartek Fabiszewski Date: Fri, 7 Apr 2017 16:04:59 +0200 Subject: [PATCH] Refactor tracks, positions handling to use helper classes --- auth.php | 1 - changepass.php | 1 + client/index.php | 47 ++++------- download.php | 190 ++++++++++++++++++++----------------------- getpositions.php | 81 +++++++----------- gettracks.php | 27 +++--- helpers/position.php | 182 +++++++++++++++++++++++++++++++++++++++++ helpers/track.php | 94 +++++++++++++++++++++ helpers/user.php | 26 ++++-- index.php | 37 +++++---- 10 files changed, 464 insertions(+), 222 deletions(-) create mode 100644 helpers/position.php create mode 100644 helpers/track.php diff --git a/auth.php b/auth.php index 1b374a7..afea5ef 100755 --- a/auth.php +++ b/auth.php @@ -100,7 +100,6 @@ if (!$user->isValid && ($config::$require_authentication || defined('headless')) $user->storeInSession(); $url = str_replace("//", "/", $_SERVER['HTTP_HOST'].dirname($_SERVER['SCRIPT_NAME'])."/index.php"); header("Location: $ssl://$url"); - exit(); } else { // unsuccessful $error = "?auth_error=1"; diff --git a/changepass.php b/changepass.php index 2bdae62..9702dfc 100644 --- a/changepass.php +++ b/changepass.php @@ -41,6 +41,7 @@ $xml->endElement(); $xml->endDocument(); $xml->flush(); + $mysqli->close(); exit; } diff --git a/client/index.php b/client/index.php index e7a3018..af43810 100644 --- a/client/index.php +++ b/client/index.php @@ -24,7 +24,6 @@ function setError(&$response, $message) { define("headless", true); require_once("../auth.php"); // sets $mysqli, $user -$userid = $user->id; $action = isset($_REQUEST['action']) ? $_REQUEST['action'] : null; $response = [ 'error' => false ]; @@ -54,23 +53,20 @@ switch ($action) { // action: addtrack case "addtrack": - $trackname = isset($_REQUEST['track']) ? $_REQUEST['track'] : NULL; - if (empty($trackname)) { + $trackName = isset($_REQUEST['track']) ? $_REQUEST['track'] : NULL; + if (empty($trackName)) { setError($response, "missing required parameter"); break; } - $sql = "INSERT INTO tracks (user_id, name) VALUES (?, ?)"; - $query = $mysqli->prepare($sql); - $query->bind_param('is', $userid, $trackname); - $query->execute(); - $trackid = $mysqli->insert_id; - $query->close(); - if ($mysqli->errno) { - setError($response, $mysqli->error); + require_once("../helpers/track.php"); + $track = new uTrack(); + $trackId = $track->add($user->id, $trackName); + if ($trackId === false) { + setError($response, "Server error"); break; } // return track id - $response['trackid'] = $trackid; + $response['trackid'] = $trackId; break; // action: addposition @@ -84,30 +80,23 @@ switch ($action) { $accuracy = isset($_REQUEST["accuracy"]) ? $_REQUEST["accuracy"] : NULL; $provider = isset($_REQUEST["provider"]) ? $_REQUEST["provider"] : NULL; $comment = isset($_REQUEST["comment"]) ? $_REQUEST["comment"] : NULL; - $imageid = isset($_REQUEST["imageid"]) ? $_REQUEST["imageid"] : NULL; - $trackid = isset($_REQUEST["trackid"]) ? $_REQUEST["trackid"] : NULL; + $imageId = isset($_REQUEST["imageid"]) ? $_REQUEST["imageid"] : NULL; + $trackId = isset($_REQUEST["trackid"]) ? $_REQUEST["trackid"] : NULL; - if (is_null($lat) || is_null($lon) || is_null($time) || is_null($trackid)) { + if (is_null($lat) || is_null($lon) || is_null($time) || is_null($trackId)) { setError($response, "missing required parameter"); break; } - $sql = "INSERT INTO positions " - ."(user_id, track_id," - ."time, latitude, longitude, altitude, speed, bearing, accuracy, provider, comment, image_id)" - ."VALUES (?,?,FROM_UNIXTIME(?),?,?,?,?,?,?,?,?,?)"; - - $query = $mysqli->prepare($sql); - $query->bind_param('iisddddddssi', - $userid, $trackid, - $time, $lat, $lon, $altitude, $speed, $bearing, $accuracy, $provider, $comment, $imageid); - $query->execute(); - $query->close(); - if ($mysqli->errno) { - setError($response, $mysqli->error); + require_once("../helpers/position.php"); + $position = new uPosition(); + $positionId = $position->add($user->id, $trackId, + $time, $lat, $lon, $altitude, $speed, $bearing, $accuracy, $provider, $comment, $imageId); + + if ($positionId === false) { + setError($response, "Server error"); } break; - } $mysqli->close(); diff --git a/download.php b/download.php index 49b005a..fa533df 100755 --- a/download.php +++ b/download.php @@ -17,39 +17,10 @@ * along with this program; if not, see . */ -require_once("auth.php"); -$type = (isset($_REQUEST["type"]) ? $_REQUEST["type"] : "kml"); -$userid = ((isset($_REQUEST["userid"]) && is_numeric($_REQUEST["userid"])) ? $_REQUEST["userid"] : 0); -$trackid = ((isset($_REQUEST["trackid"]) && is_numeric($_REQUEST["trackid"])) ? $_REQUEST["trackid"] : 0); +require_once("auth.php"); // sets $mysqli, $user +require_once("helpers/position.php"); -if ($config::$units=="imperial") { - $factor_kmh = 0.62; //to mph - $unit_kmh = "mph"; - $factor_m = 3.28; // to feet - $unit_m = "ft"; - $factor_km = 0.62; // to miles - $unit_km = "mi"; -} -else { - $factor_kmh = 1; - $unit_kmh = "km/h"; - $factor_m = 1; - $unit_m = "m"; - $factor_km = 1; - $unit_km = "km"; -} - -function haversine_distance($lat1, $lon1, $lat2, $lon2) { - $lat1 = deg2rad($lat1); - $lon1 = deg2rad($lon1); - $lat2 = deg2rad($lat2); - $lon2 = deg2rad($lon2); - $latD = $lat2 - $lat1; - $lonD = $lon2 - $lon1; - $bearing = 2*asin(sqrt(pow(sin($latD/2),2)+cos($lat1)*cos($lat2)*pow(sin($lonD/2),2))); - return $bearing * 6371000; -} -function addStyle($xml,$name,$url) { +function addStyle($xml, $name, $url) { $xml->startElement("Style"); $xml->writeAttribute("id", $name."Style"); $xml->startElement("IconStyle"); @@ -60,93 +31,108 @@ function addStyle($xml,$name,$url) { $xml->endElement(); $xml->endElement(); } + function toHMS($s) { - $d = floor($s/86400); - $h = floor(($s%86400)/3600); - $m = floor((($s%86400)%3600)/60); - $s = (($s%86400)%3600)%60; - return (($d>0)?($d." d "):"").(substr("00".$h,-2)).":".(substr("00".$m,-2)).":".(substr("00".$s,-2)); + $d = floor($s / 86400); + $h = floor(($s % 86400) / 3600); + $m = floor((($s % 86400) % 3600) / 60); + $s = (($s % 86400) % 3600) % 60; + return (($d > 0) ? ($d." d ") : "").(substr("00".$h, -2)).":".(substr("00".$m, -2)).":".(substr("00".$s, -2)); } -if ($trackid>0 && $userid>0) { - $query = $mysqli->prepare("SELECT p.id, p.latitude, p.longitude, p.altitude, p.speed, p.bearing, p.time, u.login, t.name - FROM positions p - LEFT JOIN users u ON (p.user_id=u.id) - LEFT JOIN tracks t ON (p.track_id=t.id) - WHERE p.user_id=? AND p.track_id=? - ORDER BY p.time"); - $query->bind_param("ii", $userid, $trackid); - $query->execute(); - $query->store_result(); - $query->bind_result($positionid,$latitude,$longitude,$altitude,$speed,$bearing,$dateoccured,$username,$trackname); - $query->fetch(); // take just one row to get trackname etc - $query->data_seek(0); // and reset result set +$type = isset($_REQUEST["type"]) ? $_REQUEST["type"] : "kml"; +$userId = (isset($_REQUEST["userid"]) && is_numeric($_REQUEST["userid"])) ? $_REQUEST["userid"] : NULL; +$trackId = (isset($_REQUEST["trackid"]) && is_numeric($_REQUEST["trackid"])) ? $_REQUEST["trackid"] : NULL; + +if ($config::$units == "imperial") { + $factor_kmh = 0.62; //to mph + $unit_kmh = "mph"; + $factor_m = 3.28; // to feet + $unit_m = "ft"; + $factor_km = 0.62; // to miles + $unit_km = "mi"; +} else { + $factor_kmh = 1; + $unit_kmh = "km/h"; + $factor_m = 1; + $unit_m = "m"; + $factor_km = 1; + $unit_km = "km"; +} + +if ($trackId && $userId) { + $position = new uPosition(); + $positionsArr = []; + $positionsArr = $position->getAll($userId, $trackId); + if (empty($positionsArr)) { + $mysqli->close(); + exit(); + } + switch ($type) { case "kml": default: header("Content-type: application/vnd.google-earth.kml+xml"); - header("Content-Disposition: attachment; filename=\"track$trackid.kml\""); + header("Content-Disposition: attachment; filename=\"track" . $positionsArr[0]->trackId . ".kml\""); $xml = new XMLWriter(); $xml->openURI("php://output"); - $xml->startDocument("1.0"); + $xml->setIndent(true); + $xml->startDocument("1.0", "utf-8"); $xml->startElement("kml"); $xml->writeAttribute("xmlns", "http://earth.google.com/kml/2.1"); - $xml->setIndent(true); $xml->startElement("Document"); - $xml->writeElement("name", $trackname); + $xml->writeElement("name", $positionsArr[0]->trackName); // line style $xml->startElement("Style"); $xml->writeAttribute("id", "lineStyle"); $xml->startElement("LineStyle"); - $xml->writeElement("color","7f0000ff"); - $xml->writeElement("width","4"); + $xml->writeElement("color", "7f0000ff"); + $xml->writeElement("width", "4"); $xml->endElement(); $xml->endElement(); // marker styles - addStyle($xml,"red","http://maps.google.com/mapfiles/markerA.png"); - addStyle($xml,"green","http://maps.google.com/mapfiles/marker_greenB.png"); - addStyle($xml,"gray","http://maps.gstatic.com/mapfiles/ridefinder-images/mm_20_gray.png"); + addStyle($xml, "red", "http://maps.google.com/mapfiles/markerA.png"); + addStyle($xml, "green", "http://maps.google.com/mapfiles/marker_greenB.png"); + addStyle($xml, "gray", "http://maps.gstatic.com/mapfiles/ridefinder-images/mm_20_gray.png"); $style = "#redStyle"; // for first element $i = 0; $totalMeters = 0; $totalSeconds = 0; - while ($query->fetch()) { - $distance = (isset($prev_latitude))?haversine_distance($prev_latitude,$prev_longitude,$latitude,$longitude):0; - $prev_latitude = $latitude; - $prev_longitude = $longitude; - $seconds = (isset($prev_dateoccured))?(strtotime($dateoccured)-strtotime($prev_dateoccured)):0; - $prev_dateoccured = $dateoccured; + foreach ($positionsArr as $position) { + $distance = isset($prevPosition) ? $position->distanceTo($prevPosition) : 0; + $seconds = isset($prevPosition) ? $position->secondsTo($prevPosition) : 0; + $prevPosition = $position; $totalMeters += $distance; $totalSeconds += $seconds; - if(++$i == $query->num_rows) { $style = "#greenStyle"; } // last element + if(++$i == count($positionsArr)) { $style = "#greenStyle"; } // last element $xml->startElement("Placemark"); - $xml->writeAttribute("id", $positionid); - //$xml->writeElement("name", $i); + $xml->writeAttribute("id", $position->id); $description = - "
".$lang_user.": ".strtoupper($username)."
".$lang_track.": ".strtoupper($trackname). + "
". + $lang_user.": ".strtoupper($position->userLogin)."
".$lang_track.": ".strtoupper($position->trackName). "
". "
". - "
".$lang_time.": ".$dateoccured."
". - (($speed)?"".$lang_speed.": ".round($speed*3.6,2*$factor_kmh)." ".$unit_kmh."
":""). - (($altitude != null)?"".$lang_altitude.": ".round($altitude*$factor_m)." ".$unit_m."
":""). + "
".$lang_time.": ".$position->time."
". + (!is_null($position->speed) ? "".$lang_speed.": ".round($position->speed * 3.6 * $factor_kmh, 2)." ".$unit_kmh."
" : ""). + (!is_null($position->altitude) ? "".$lang_altitude.": ".round($position->altitude * $factor_m)." ".$unit_m."
" : ""). "".$lang_ttime.": ".toHMS($totalSeconds)."
". - "".$lang_aspeed.": ".(($totalSeconds!=0)?round($totalMeters/$totalSeconds*3.6*$factor_kmh,2):0)." ".$unit_kmh."
". - "".$lang_tdistance.": ".round($totalMeters/1000*$factor_km,2)." ".$unit_km."
"."
". - "
".$lang_point." ".$i." ".$lang_of." ".($query->num_rows-1)."
". + "".$lang_aspeed.": ".(($totalSeconds != 0) ? round($totalMeters / $totalSeconds * 3.6 * $factor_kmh, 2) : 0)." ".$unit_kmh."
". + "".$lang_tdistance.": ".round($totalMeters / 1000 * $factor_km, 2)." ".$unit_km."
"."
". + "
".$lang_point." ".$i." ".$lang_of." ".count($positionsArr)."
". "
"; $xml->startElement("description"); $xml->writeCData($description); $xml->endElement(); $xml->writeElement("styleUrl", $style); $xml->startElement("Point"); - $coordinate[$i] = $longitude.",".$latitude.(($altitude) ? ",".$altitude : ""); + $coordinate[$i] = $position->longitude.",".$position->latitude.(!is_null($position->altitude) ? ",".$position->altitude : ""); $xml->writeElement("coordinates", $coordinate[$i]); $xml->endElement(); $xml->endElement(); $style = "#grayStyle"; // other elements } - $coordinates = implode("\n",$coordinate); + $coordinates = implode("\n", $coordinate); $xml->startElement("Placemark"); $xml->writeElement("styleUrl", "#lineStyle"); $xml->startElement("LineString"); @@ -154,7 +140,6 @@ if ($trackid>0 && $userid>0) { $xml->endElement(); $xml->endElement(); - $xml->endElement(); $xml->endElement(); $xml->endDocument(); @@ -164,49 +149,49 @@ if ($trackid>0 && $userid>0) { case "gpx": header("Content-type: application/application/gpx+xm"); - header("Content-Disposition: attachment; filename=\"track$trackid.gpx\""); + header("Content-Disposition: attachment; filename=\"track" . $positionsArr[0]->trackId . ".gpx\""); $xml = new XMLWriter(); $xml->openURI("php://output"); - $xml->startDocument("1.0"); + $xml->setIndent(true); + $xml->startDocument("1.0", "utf-8"); $xml->startElement("gpx"); + $xml->writeAttributeNs('xsi', 'schemaLocation', NULL, "http://www.topografix.com/GPX/1/1 http://www.topografix.com/GPX/1/1/gpx.xsd"); + $xml->writeAttributeNs('xmlns', 'xsi', NULL, 'http://www.w3.org/2001/XMLSchema-instance'); $xml->writeAttribute("xmlns", "http://www.topografix.com/GPX/1/1"); - $xml->writeAttribute("xmlns:gpxdata", "http://www.cluetrust.com/XML/GPXDATA/1/0"); $xml->writeAttribute("creator", "μlogger"); $xml->writeAttribute("version", "1.1"); $xml->startElement("metadata"); - $xml->writeElement("name", $trackname); - $xml->writeElement("time", str_replace(" ","T",$dateoccured)); + $xml->writeElement("name", $positionsArr[0]->trackName); + $xml->writeElement("time", str_replace(" ", "T", $positionsArr[0]->time)); $xml->endElement(); $xml->startElement("trk"); - $xml->writeElement("name", $trackname); + $xml->writeElement("name", $positionsArr[0]->trackName); $xml->startElement("trkseg"); $i = 0; $totalMeters = 0; $totalSeconds = 0; - while ($query->fetch()) { - $distance = (isset($prev_latitude))?haversine_distance($prev_latitude,$prev_longitude,$latitude,$longitude):0; - $prev_latitude = $latitude; - $prev_longitude = $longitude; - $seconds = (isset($prev_dateoccured))?(strtotime($dateoccured)-strtotime($prev_dateoccured)):0; - $prev_dateoccured = $dateoccured; + foreach ($positionsArr as $position) { + $distance = isset($prevPosition) ? $position->distanceTo($prevPosition) : 0; + $seconds = isset($prevPosition) ? $position->secondsTo($prevPosition) : 0; + $prevPosition = $position; $totalMeters += $distance; $totalSeconds += $seconds; $xml->startElement("trkpt"); - $xml->writeAttribute("lat", $latitude); - $xml->writeAttribute("lon", $longitude); - if($altitude) { $xml->writeElement("ele", $altitude); } - $xml->writeElement("time", str_replace(" ","T",$dateoccured)); + $xml->writeAttribute("lat", $position->latitude); + $xml->writeAttribute("lon", $position->longitude); + if (!is_null($position->altitude)) { $xml->writeElement("ele", $position->altitude); } + $xml->writeElement("time", str_replace(" ", "T", $position->time)); $xml->writeElement("name", ++$i); $xml->startElement("desc"); $description = - $lang_user.": ".strtoupper($username)." ".$lang_track.": ".strtoupper($trackname). - " ".$lang_time.": ".$dateoccured. - (($speed)?" ".$lang_speed.": ".round($speed*3.6,2*$factor_kmh)." ".$unit_kmh:""). - (($altitude != null)?" ".$lang_altitude.": ".round($altitude*$factor_m)." ".$unit_m:""). + $lang_user.": ".strtoupper($position->userLogin)." ".$lang_track.": ".strtoupper($position->trackName). + " ".$lang_time.": ".$position->time. + (!is_null($position->speed) ? " ".$lang_speed.": ".round($position->speed * 3.6 * $factor_kmh, 2)." ".$unit_kmh : ""). + (!is_null($position->altitude) ? " ".$lang_altitude.": ".round($position->altitude * $factor_m)." ".$unit_m : ""). " ".$lang_ttime.": ".toHMS($totalSeconds)."". - " ".$lang_aspeed.": ".(($totalSeconds!=0)?round($totalMeters/$totalSeconds*3.6*$factor_kmh,2):0)." ".$unit_kmh. - " ".$lang_tdistance.": ".round($totalMeters/1000*$factor_km,2)." ".$unit_km. - " ".$lang_point." ".$i." ".$lang_of." ".($query->num_rows-1); + " ".$lang_aspeed.": ".(($totalSeconds != 0) ? round($totalMeters / $totalSeconds * 3.6 * $factor_kmh, 2) : 0)." ".$unit_kmh. + " ".$lang_tdistance.": ".round($totalMeters / 1000 * $factor_km, 2)." ".$unit_km. + " ".$lang_point." ".$i." ".$lang_of." ".count($positionsArr); $xml->writeCData($description); $xml->endElement(); $xml->endElement(); @@ -219,8 +204,7 @@ if ($trackid>0 && $userid>0) { break; } - $query->free_result(); - $query->close(); + } $mysqli->close(); ?> diff --git a/getpositions.php b/getpositions.php index 9eeae29..e4d3cdd 100755 --- a/getpositions.php +++ b/getpositions.php @@ -17,45 +17,24 @@ * along with this program; if not, see . */ -require_once("auth.php"); +require_once("auth.php"); // sets $mysqli, $user +require_once("helpers/position.php"); -$userid = ((isset($_REQUEST["userid"]) && is_numeric($_REQUEST["userid"])) ? $_REQUEST["userid"] : 0); -$trackid = ((isset($_REQUEST["trackid"]) && is_numeric($_REQUEST["trackid"])) ? $_REQUEST["trackid"] : 0); +$userId = (isset($_REQUEST["userid"]) && is_numeric($_REQUEST["userid"])) ? $_REQUEST["userid"] : NULL; +$trackId = (isset($_REQUEST["trackid"]) && is_numeric($_REQUEST["trackid"])) ? $_REQUEST["trackid"] : NULL; -function haversine_distance($lat1, $lon1, $lat2, $lon2) { - $lat1 = deg2rad($lat1); - $lon1 = deg2rad($lon1); - $lat2 = deg2rad($lat2); - $lon2 = deg2rad($lon2); - $latD = $lat2 - $lat1; - $lonD = $lon2 - $lon1; - $bearing = 2*asin(sqrt(pow(sin($latD/2),2)+cos($lat1)*cos($lat2)*pow(sin($lonD/2),2))); - return $bearing * 6371000; -} - -if ($userid) { - if ($trackid) { +if ($userId) { + $position = new uPosition(); + $positionsArr = []; + if ($trackId) { // get all track data - $query = $mysqli->prepare("SELECT p.id, p.latitude, p.longitude, p.altitude, p.speed, p.bearing, p.time, p.accuracy, p.comment, u.login, t.name, t.id - FROM positions p - LEFT JOIN users u ON (p.user_id=u.id) - LEFT JOIN tracks t ON (p.track_id=t.id) - WHERE p.user_id=? AND p.track_id=? - ORDER BY p.time"); - $query->bind_param('ii', $userid, $trackid); + $positionsArr = $position->getAll($userId, $trackId); } else { // get data only for latest point - $query = $mysqli->prepare("SELECT p.id, p.latitude, p.longitude, p.altitude, p.speed, p.bearing, p.time, p.accuracy, p.comment, u.login, t.name, t.id - FROM positions p - LEFT JOIN users u ON (p.user_id=u.id) - LEFT JOIN tracks t ON (p.track_id=t.id) - WHERE p.user_id=? - ORDER BY p.time DESC LIMIT 1"); - $query->bind_param('i', $userid); + $position->getLast($userId); + $positionsArr[] = $position; } - $query->execute(); - $query->bind_result($positionid,$latitude,$longitude,$altitude,$speed,$bearing,$dateoccured,$accuracy,$comments,$username,$trackname,$trackid); - + header("Content-type: text/xml"); $xml = new XMLWriter(); $xml->openURI("php://output"); @@ -63,35 +42,31 @@ if ($userid) { $xml->setIndent(true); $xml->startElement('root'); - while ($query->fetch()) { + foreach ($positionsArr as $position) { $xml->startElement("position"); - $xml->writeAttribute("id", $positionid); - $xml->writeElement("latitude", $latitude); - $xml->writeElement("longitude", $longitude); - $xml->writeElement("altitude", ($altitude)?round($altitude):$altitude); - $xml->writeElement("speed", $speed); - $xml->writeElement("bearing", $bearing); - $xml->writeElement("dateoccured", $dateoccured); - $xml->writeElement("accuracy", $accuracy); - $xml->writeElement("comments", $comments); - $xml->writeElement("username", $username); - $xml->writeElement("trackid", $trackid); - $xml->writeElement("trackname", $trackname); - $distance = (isset($prev_latitude))?haversine_distance($prev_latitude,$prev_longitude,$latitude,$longitude):0; - $prev_latitude = $latitude; - $prev_longitude = $longitude; + $xml->writeAttribute("id", $position->id); + $xml->writeElement("latitude", $position->latitude); + $xml->writeElement("longitude", $position->longitude); + $xml->writeElement("altitude", ($position->altitude) ? round($position->altitude) : $position->altitude); + $xml->writeElement("speed", $position->speed); + $xml->writeElement("bearing", $position->bearing); + $xml->writeElement("dateoccured", $position->time); + $xml->writeElement("accuracy", $position->accuracy); + $xml->writeElement("comments", $position->comment); + $xml->writeElement("username", $position->userLogin); + $xml->writeElement("trackid", $position->trackId); + $xml->writeElement("trackname", $position->trackName); + $distance = isset($prevPosition) ? $position->distanceTo($prevPosition) : 0; $xml->writeElement("distance", round($distance)); - $seconds = (isset($prev_dateoccured))?(strtotime($dateoccured)-strtotime($prev_dateoccured)):0; - $prev_dateoccured = $dateoccured; + $seconds = isset($prevPosition) ? $position->secondsTo($prevPosition) : 0; $xml->writeElement("seconds", $seconds); $xml->endElement(); + $prevPosition = $position; } $xml->endElement(); $xml->endDocument(); $xml->flush(); - - $query->free_result(); } $mysqli->close(); diff --git a/gettracks.php b/gettracks.php index 663389a..fdbc7bc 100755 --- a/gettracks.php +++ b/gettracks.php @@ -17,15 +17,14 @@ * along with this program; if not, see . */ -require_once("auth.php"); +require_once("auth.php"); // sets $mysqli, $user +require_once("helpers/track.php"); -$userid = ((isset($_REQUEST["userid"]) && is_numeric($_REQUEST["userid"])) ? $_REQUEST["userid"] : 0); +$userId = ((isset($_REQUEST["userid"]) && is_numeric($_REQUEST["userid"])) ? $_REQUEST["userid"] : 0); -if ($userid) { - $query = $mysqli->prepare("SELECT id, name FROM tracks WHERE user_id=? ORDER BY id DESC"); - $query->bind_param('i', $userid); - $query->execute(); - $query->bind_result($trackid, $trackname); +if ($userId) { + $track = new uTrack(); + $tracksArr = $track->getAll($userId); header("Content-type: text/xml"); $xml = new XMLWriter(); @@ -34,18 +33,18 @@ if ($userid) { $xml->setIndent(true); $xml->startElement('root'); - while ($query->fetch()) { - $xml->startElement("track"); - $xml->writeElement("trackid", $trackid); - $xml->writeElement("trackname", $trackname); - $xml->endElement(); + if (!empty($tracksArr)) { + foreach ($tracksArr as $aTrack) { + $xml->startElement("track"); + $xml->writeElement("trackid", $aTrack->id); + $xml->writeElement("trackname", $aTrack->name); + $xml->endElement(); + } } $xml->endElement(); $xml->endDocument(); $xml->flush(); - - $query->free_result(); } $mysqli->close(); diff --git a/helpers/position.php b/helpers/position.php new file mode 100644 index 0000000..1a03a41 --- /dev/null +++ b/helpers/position.php @@ -0,0 +1,182 @@ +. + */ + +require_once(__DIR__ . "/db.php"); + +class uPosition { + public $id; + public $time; + public $userId; + public $userLogin; + public $trackId; + public $trackName; + public $latitude; + public $longitude; + public $altitude; + public $speed; + public $bearing; + public $accuracy; + public $provider; + public $comment; // not used yet + public $imageId; // not used yet + + public $isValid = false; + + private static $db; + + public function __construct($positionId = NULL) { + + self::$db = uDB::getInstance(); + + if (!empty($positionId)) { + $query = "SELECT p.id, p.time, p.user_id, p.track_id, + p.latitude, p.longitude, p.altitude, p.speed, p.bearing, p.accuracy, p.provider, + p.comment, p.image_id, u.login, t.name + FROM positions p + LEFT JOIN users u ON (p.user_id = u.id) + LEFT JOIN tracks t ON (p.track_id = t.id) + WHERE id = ? LIMIT 1"; + $params = [ 'i', $positionId ]; + $this->loadWithQuery($query, $params); + } + } + + public function add($userId, $trackId, $time, $lat, $lon, $altitude, $speed, $bearing, $accuracy, $provider, $comment, $imageId) { + $positionId = false; + if (!is_null($lat) && !is_null($lon) && !is_null($time) && !empty($userId) && !empty($trackId)) { + $query = "INSERT INTO positions + (user_id, track_id, + time, latitude, longitude, altitude, speed, bearing, accuracy, provider, comment, image_id) + VALUES (?, ?, FROM_UNIXTIME(?), ?, ?, ?, ?, ?, ?, ?, ?, ?)"; + $stmt = self::$db->prepare($query); + $stmt->bind_param('iisddddddssi', + $userId, $trackId, + $time, $lat, $lon, $altitude, $speed, $bearing, $accuracy, $provider, $comment, $imageId); + $stmt->execute(); + if (!self::$db->error && !$stmt->errno) { + $positionId = self::$db->insert_id; + } + $stmt->close(); + } + return $positionId; + } + + public function getLast() { + $query = "SELECT p.id, p.time, p.user_id, p.track_id, + p.latitude, p.longitude, p.altitude, p.speed, p.bearing, p.accuracy, p.provider, + p.comment, p.image_id, u.login, t.name + FROM positions p + LEFT JOIN users u ON (p.user_id = u.id) + LEFT JOIN tracks t ON (p.track_id = t.id) + ORDER BY p.time DESC LIMIT 1"; + $this->loadWithQuery($query); + } + + public function getAll($userId = NULL, $trackId = NULL) { + $rules = []; + if (!empty($userId)) { + $rule[] = "p.user_id='" . self::$db->real_escape_string($userId) ."'"; + } + if (!empty($trackId)) { + $rule[] = "p.track_id='" . self::$db->real_escape_string($trackId) ."'"; + } + if (!empty($rules)) { + $where = "WHERE " . implode(" AND ", $rules); + } else { + $where = ""; + } + $query = "SELECT p.id, p.time, p.user_id, p.track_id, + p.latitude, p.longitude, p.altitude, p.speed, p.bearing, p.accuracy, p.provider, + p.comment, p.image_id, u.login, t.name + FROM positions p + LEFT JOIN users u ON (p.user_id = u.id) + LEFT JOIN tracks t ON (p.track_id = t.id) + $where + ORDER BY p.time"; + $result = self::$db->query($query); + if ($result === false) { + return false; + } + $positionsArr = []; + while ($row = $result->fetch_assoc()) { + $positionsArr[] = $this->rowToObject($row); + } + $result->close(); + return $positionsArr; + } + + // haversine distance to target point + public function distanceTo($target) { + $lat1 = deg2rad($this->latitude); + $lon1 = deg2rad($this->longitude); + $lat2 = deg2rad($target->latitude); + $lon2 = deg2rad($target->longitude); + $latD = $lat2 - $lat1; + $lonD = $lon2 - $lon1; + $bearing = 2 * asin(sqrt(pow(sin($latD / 2), 2) + cos($lat1) * cos($lat2) * pow(sin($lonD / 2), 2))); + return $bearing * 6371000; + } + + public function secondsTo($target) { + return strtotime($this->time) - strtotime($target->time); + } + + private function rowToObject($row) { + $position = new uPosition(); + $position->id = $row['id']; + $position->time = $row['time']; + $position->userId = $row['user_id']; + $position->userLogin = $row['login']; + $position->trackId = $row['track_id']; + $position->trackName = $row['name']; + $position->latitude = $row['latitude']; + $position->longitude = $row['longitude']; + $position->altitude = $row['altitude']; + $position->speed = $row['speed']; + $position->bearing = $row['bearing']; + $position->accuracy = $row['accuracy']; + $position->provider = $row['provider']; + $position->comment = $row['comment']; + $position->imageId = $row['image_id']; + $position->isValid = true; + return $position; + } + + private function loadWithQuery($query, $bindParams = NULL) { + $stmt = self::$db->prepare($query); + if (is_array($bindParams) && ($types = array_shift($bindParams))) { + call_user_func_array( + [ $stmt, 'bind_param' ], + array_merge([ $types ], array_map(function(&$param) { return $param; }, $bindParams)) + ); + } + if ($stmt->execute()) { + $stmt->bind_result($this->id, $this->time, $this->userId, $this->trackId, + $this->latitude, $this->longitude, $this->altitude, $this->speed, + $this->bearing, $this->accuracy, $this->provider, + $this->comment, $this->imageId, $this->userLogin, $this->trackName); + if ($stmt->fetch()) { + $this->isValid = true; + } + } + $stmt->close(); + } +} + +?> \ No newline at end of file diff --git a/helpers/track.php b/helpers/track.php new file mode 100644 index 0000000..1bddb44 --- /dev/null +++ b/helpers/track.php @@ -0,0 +1,94 @@ +. + */ + +require_once(__DIR__ . "/db.php"); + +class uTrack { + public $id; + public $userId; + public $name; + public $comment; + + public $isValid = false; + + private static $db; + + public function __construct($trackId = NULL) { + + self::$db = uDB::getInstance(); + + if (!empty($trackId)) { + $stmt = self::$db->prepare("SELECT id, user_id, name, comment FROM tracks WHERE id = ? LIMIT 1"); + $stmt->bind_param('i', $trackId); + $stmt->execute(); + $stmt->bind_result($this->id, $this->userId, $this->name, $this->comment); + if ($stmt->fetch()) { + $this->isValid = true; + } + $stmt->close(); + + } + } + + public function add($userId, $name, $comment = NULL) { + $trackId = false; + if (!empty($userId) && !empty($name)) { + $query = "INSERT INTO tracks (user_id, name, comment) VALUES (?, ?, ?)"; + $stmt = self::$db->prepare($query); + $stmt->bind_param('iss', $userId, $name, $comment); + $stmt->execute(); + if (!self::$db->error && !$stmt->errno) { + $trackId = self::$db->insert_id; + } + $stmt->close(); + } + return $trackId; + } + + public function getAll($userId = NULL) { + if (!empty($userId)) { + $where = "WHERE user_id='" . self::$db->real_escape_string($userId) ."'"; + } else { + $where = ""; + } + $query = "SELECT id, user_id, name, comment FROM tracks $where ORDER BY id DESC"; + $result = self::$db->query($query); + if ($result === false) { + return false; + } + $trackArr = []; + while ($row = $result->fetch_assoc()) { + $trackArr[] = $this->rowToObject($row); + } + $result->close(); + return $trackArr; + } + + private function rowToObject($row) { + $track = new uTrack(); + $track->id = $row['id']; + $track->userId = $row['user_id']; + $track->name = $row['name']; + $track->comment = $row['comment']; + $track->isValid = true; + return $track; + } +} + +?> \ No newline at end of file diff --git a/helpers/user.php b/helpers/user.php index fd82ab3..0d2cbb3 100644 --- a/helpers/user.php +++ b/helpers/user.php @@ -40,10 +40,7 @@ class uUser { $this->isValid = true; } $stmt->close(); - $config = new uConfig(); - if (!empty($config::$admin_user) && $config::$admin_user == $this->login) { - $this->isAdmin = true; - } + $this->isAdmin = $this->isAdmin($this->login); } } @@ -94,19 +91,34 @@ class uUser { } } - public function listAll() { - $query = "SELECT id, login FROM users ORDER BY login"; + public function getAll() { + $query = "SELECT id, login, password FROM users ORDER BY login"; $result = self::$db->query($query); if ($result === false) { return false; } $userArr = []; while ($row = $result->fetch_assoc()) { - $userArr[$row['id']] = $row['login']; + $userArr[] = $this->rowToObject($row); } $result->close(); return $userArr; } + + private function rowToObject($row) { + $user = new uUser(); + $user->id = $row['id']; + $user->login = $row['login']; + $user->hash = $row['password']; + $user->isAdmin = $this->isAdmin($row['login']); + $user->isValid = true; + return $user; + } + + private function isAdmin($login) { + $config = new uConfig(); + return (!empty($config::$admin_user) && $config::$admin_user == $login); + } } ?> \ No newline at end of file diff --git a/index.php b/index.php index 07f302c..efee265 100755 --- a/index.php +++ b/index.php @@ -17,7 +17,10 @@ * along with this program; if not, see . */ -require_once ("auth.php"); +require_once("auth.php"); +require_once("helpers/position.php"); +require_once("helpers/track.php"); + if ($user->isValid) { $itemPass = '' . $lang_changepass . ''; $itemLogout = '' . $lang_logout . ''; @@ -44,16 +47,16 @@ if ($user->isAdmin || $config::$public_tracks) { @@ -241,5 +247,6 @@ print '
'; + $mysqli->close(); ?>