Adds gitignore for upload files and updates everything to the latest state

This commit is contained in:
Nils Otterpohl 2023-09-01 10:01:49 +02:00
parent e9b3a8d313
commit 82a0d9d6ce
13 changed files with 236 additions and 140 deletions

4
.gitignore vendored Normal file
View File

@ -0,0 +1,4 @@
upl/
qr/
conf/*.php
var/*.php

View File

@ -10,14 +10,14 @@ foreach ($files["ext"] as $val) {
//Include libraries (excl. hidden [.file])
$files["lib"] = scandir("lib");
foreach ($files["lib"] as $val) {
if (substr($val,0,1)!= "." && $val!="99_manager_new.php") {
if (substr($val,0,1)!= ".") {
include "lib/".$val;
} }
//Import configuration files (excl. hidden [.file])
$files["var"] = scandir("var");
foreach ($files["var"] as $val) {
if (substr($val,0,1)!= ".") {
if (substr($val,0,1)!= "." && ".php"==substr($val,strlen($val)-4,4)) {
include "var/".$val;
} }

View File

@ -17,6 +17,6 @@ foreach ($files["lib"] as $val) {
//Import configuration files (excl. hidden [.file])
$files["conf"] = scandir("conf");
foreach ($files["conf"] as $val) {
if (substr($val,0,1)!= ".") {
if (substr($val,0,1)!= "." && ".php"==substr($val,strlen($val)-4,4)) {
include "conf/".$val;
} }

View File

@ -6,7 +6,7 @@ define(
"JWT_KEY",
"v9upLZkm7uVGH9zqEGnp4sZAqeJX33vygYBTKEGdVqtsKeEKaSGp2KBnZmcVNPDb"
."3BkXGwdp9GMDwjaqp6BqfVNRYQf9X5PC8BP74UZPKGPujCeAsayMRpLv2GPBUgXz"
."TVY36KcpYy77SPUmZ7zY2q7ZTFEvM73jMBufdUV8fcEDp4eTQDqMpvp8dhkDxZPj"
."ZVY36KcpYy77SPUmZ7zY2q7ZTFEvM73jMBufdUV8fcEDp4eTQDqMpvp8dhkDxZPj"
."wVYtkHxLtkTHVa9DMm2pWmXqhsjJckgPMxdRsgngCSv8H8BBjXFkG2dn7ndJeApF"
);
define("JWT_VALID_TIME", 7 * 24 * 60 * 60);

View File

@ -7,9 +7,14 @@ namespace Routes;
/**************************************************/
abstract class Route {
public function __construct() {}
protected $resourceClass;
public function __construct() {
$this->resourceClass = ("\\Resources\\".(get_called_class()::$resource));
}
public function Answer() {
try {
$subroute = \Request::Subroute();
if (is_null($subroute)) {
switch (\Request::Method()) {
@ -21,7 +26,7 @@ abstract class Route {
case "GET":
$id = \Request::ID();
if (is_null($id)) {
return $this->restrictFilter() && $this->head() && $this->getAll();
return $this->restrictFilter() && $this->getAll() && $this->head();
} else {
$json = [];
return $this->head($id) && $this->getOne($id, $json) && $this->checkOutput($id, $json);
@ -42,39 +47,42 @@ abstract class Route {
}
} else {
$id = \Request::ID();
return $this->answerSub($subroute, $id) && $this->head($id) && $this->get($id) && $this->checkOutput($id, );
$json = [];
return $this->answerSub($subroute, $id) && $this->getOne($id, $json) && $this->head($id) && $this->checkOutput($id, $json);
} }
catch (ResponseException $e) {
\Response::Get()->HandleException($e);
return;
}
\Response::Get()->Good();
}
abstract public static function Rights();
protected function info() {
$class = get_called_class();
\Response::Get()->Good()->Json("rights", $class::Rights()->Export());
\Response::Get()->Good()->Json("rights", get_called_class()::Rights());
return true;
}
protected function answerSub($subroute, $id) {
$class = "\\Resources\\".$this->resource;
$answerFnc = "answer_".$class::Get()->Table()."_".$subroute;
$answerFnc = "answer_".$this->resourceClass::Get()->Table()."_".$subroute;
if (method_exists($this, $answerFnc)) {
$subid = \Request::SubID();
return $this->$answerFnc($id, $subid);
} else if (method_exists($this, "answer_Files") && $class::Get()->HasFile($subroute)) {
return $this->answer_Files($this->resource, $id, $subroute);
} else if (method_exists($this, "answer_Files") && $this->resourceClass::Get()->HasFile($subroute)) {
return $this->answer_Files(get_called_class()::$resource, $id, $subroute);
}
\Response::Get()->SubRouteNotExisting($subroute);
return false;
}
protected function head($id = null) {
$class = "\\Resources\\".$this->resource;
\Response::Get()->Good()->Etag($class::Get()->Checksum($id));
\Response::Get()->Good()->Etag($this->resourceClass::Get()->Checksum($id));
return true; // Needed for &&-chain-call
}
protected function getOne($id, &$json) {
$class = "\\Resources\\".$this->resource;
$resource = $class::Get()->Ref($id);
$resource = $this->resourceClass::Get()->Ref($id);
if ($resource->Load()) {
$json = $resource->Json();
return true;
@ -85,8 +93,7 @@ abstract class Route {
}
protected function getAll() {
$class = "\\Resources\\".$this->resource;
$list = $class::Get()->RefAll();
$list = $this->resourceClass::Get()->RefAll();
$json = [];
foreach ($list as $resource) {
$json[] = $resource->Json();
@ -98,38 +105,35 @@ abstract class Route {
}
protected function insert($json) {
$class = "\\Resources\\".$this->resource;
$newid = null;
if ($class::Get()->Insert($json, $newid)) {
\Response::Get()->Inserted($this->resource)->Content($class::Get()->Ref($newid)->Json());
if ($this->resourceClass::Get()->Insert($json, $newid)) {
\Response::Get()->Inserted(get_called_class()::$resource)->Content($this->resourceClass::Get()->Ref($newid)->Json());
return true;
}
return false;
}
protected function update($id, $json) {
$class = "\\Resources\\".$this->resource;
$resource = $class::Get()->Ref($id);
$resource = $this->resourceClass::Get()->Ref($id);
if ($resource->Load()) {
$resource->Patch($json);
if ($resource->Store()) {
\Response::Get()->Updated($this->resource)->Content($resource->Json());
\Response::Get()->Updated(get_called_class()::$resource)->Content($resource->Json());
return true;
} }
return false;
}
protected function remove($id) {
$class = "\\Resources\\".$this->resource;
if ($class::Get()->Remove($id)) {
\Response::Get()->Deleted($this->resource);
if ($this->resourceClass::Get()->Remove($id)) {
\Response::Get()->Deleted(get_called_class()::$resource);
return true;
}
return false;
}
protected function restrictFilter() {
if (get_called_class()::Rights()->RestrictFilter()) {
if ($this->resourceClass::Rights()->RestrictFilter()) {
return true;
}
\Response::Get()->IllegalQuery();
@ -137,7 +141,7 @@ abstract class Route {
}
protected function checkOutput($id, $json) {
if (get_called_class()::Rights()->CheckInput("get", $id, $json)) {
if (($this->resourceClass)::Rights()->CheckInput("get", $id, $json)) {
\Response::Get()->Good()->Content($json);
return true;
}
@ -152,7 +156,7 @@ abstract class Route {
} else if ((is_null($json) || empty($json)) && in_array($action, ["insert", "update"])) {
\Response::Get()->MissingContent();
return false;
} else if (!get_called_class()::Rights()->CheckInput($action, $id, $json)) {
} else if (!($this->resourceClass)::Rights()->CheckInput($action, $id, $json)) {
\Response::Get()->IllegalInput();
return false;
}

View File

@ -1,8 +1,6 @@
<?php #lib/20_routes.php
<?php
/**************************************************/
/********************* Route **********************/
/**************************************************/
namespace Rights;
class Condition
{
@ -99,9 +97,9 @@ class Restriction
protected $condition = null;
protected $limits = [];
public function AddCondition(\Condition $condition) {
public function AddCondition(Condition $condition) {
if (is_null($this->condition)) {
$this->condition = \Condition::Make("or");
$this->condition = Condition::Make("or");
}
$this->condition->Sub($condition);
return $this;
@ -142,7 +140,7 @@ class Restriction
}
}
class Right
abstract class Right
{
protected $requiredRight = null;
protected $restriction = null;
@ -160,10 +158,49 @@ class Right
return sizeof($this->allow)==6 && is_null($this->restriction);
}
public function Require(Condition $condition) {
if (is_null($this->restriction)) {
$this->restriction = new Restriction();
}
$this->restriction->AddCondition($condition);
return $this;
}
public function Limit($fields) {
if (is_null($this->restriction)) {
$this->restriction = new Restriction();
}
$this->restriction->AddLimits($fields);
return $this;
}
public function GetAllowed() {
return $this->allow;
}
public function GetRestriction() {
return $this->restriction;
}
public static function Make($requiredRight = null) {
$class = get_called_class();
return (new $class($requiredRight));
}
}
class Main extends Right
{
public static function AdminAllow() {
return ["get", "update", "insert", "remove", "upload", "erase"];
}
public function Allow($allow = "readonly") {
if (is_array($allow)) {
$this->allow = array_intersect($allow, self::AdminAllow());
} else {
switch ($allow) {
case "admin":
$this->allow = ["get", "update", "insert", "remove", "upload", "erase"];
$this->allow = self::AdminAllow();
break;
case "nodelete":
$this->allow = ["get", "update", "insert", "upload"];
@ -179,62 +216,46 @@ class Right
break;
default:
$this->allow = [];
}
} }
return $this;
}
public function Require(\Condition $condition) {
if (is_null($this->restriction)) {
$this->restriction = new \Restriction();
}
$this->restriction->AddCondition($condition);
class Link extends Right
{
public static function AdminAllow() {
return ["set", "update", "unset"];
}
public function Allow($allow = "readonly") {
if (is_array($allow)) {
$this->allow = array_intersect($allow, self::AdminAllow());
} else {
switch ($allow) {
case "admin":
$this->allow = self::AdminAllow();
break;
case "nodelete":
$this->allow = ["set", "update"];
break;
case "justadd":
$this->allow = ["set"];
break;
case "update":
$this->allow = ["update"];
break;
default:
$this->allow = [];
} }
return $this;
}
public function Limit($fields) {
if (is_null($this->restriction)) {
$this->restriction = new \Restriction();
}
$this->restriction->AddLimits($fields);
return $this;
}
public function GetAllowed() {
return $this->allow;
abstract class Rights {
protected function __construct($adminAllow) {
$this->actions = array_fill_keys($adminAllow, false);
}
public function GetRestriction() {
return $this->restriction;
}
public static function Make($requiredRight = null) {
return (new self($requiredRight));
}
public static function AllowSelf() {
return self::Make()->Allow("readonly")->Require(\Condition::Make()->Add("ID", \Login::ID()));
}
public static function AllowUpdateSelf() {
return self::Make()->Allow("update")->Require(\Condition::Make()->Add("ID", \Login::ID()));
}
}
class Rights {
// false == not allowed
// array with refs to restrictions [a ... n] == restrictions apply
// true == allowed without restrictions
protected $actions = [
"get" => false,
"update" => false,
"insert" => false,
"remove" => false,
"upload" => false,
"erase" => false
];
public function __construct() {}
public function Add($right) {
// If user already has admin rights or does not posess this right, skip
if ($right->IsApplicable()) {
@ -296,8 +317,31 @@ class Rights {
} }
return $ret;
}
}
class MainRights extends Rights
{
// false == not allowed
// array with refs to restrictions [a ... n] == restrictions apply
// true == allowed without restrictions
protected $actions = [];
public static function Make() {
return (new self())->Add(\Right::Make("ADMIN")->Allow("admin"));
return (new self(Main::AdminAllow()))->Add(Main::Make("ADMIN")->Allow("admin"));
}
}
class LinkRights extends Rights
{
// false == not allowed
// array with refs to restrictions [a ... n] == restrictions apply
// true == allowed without restrictions
protected $actions = [];
public static function Make() {
return (new self(Link::AdminAllow()))->Add(Link::Make("ADMIN")->Allow("admin"));
}
}

View File

@ -34,8 +34,8 @@ class Manager
} else {
// Include routes. Needed also for /-Request
foreach (self::$routes as $route => $filename) {
$file = "routes/".str_replace(["ä", "ö", "ü", "ß"], ["ae", "oe", "ue", "ss"], $filename).".php";
foreach (self::$routes as $route) {
$file = "routes/".str_replace(["ä", "ö", "ü", "ß"], ["ae", "oe", "ue", "ss"], $route).".php";
if (file_exists($file)) {
include $file;
} }
@ -43,7 +43,7 @@ class Manager
if (Request::IsRoot()) {
// POST (Login) or GET/OPTIONS... i dont care, all will result in the same
$access = [];
foreach (self::$routes as $route => $filename) {
foreach (self::$routes as $route) {
$class = "\\Routes\\".$route;
$access[$route] = $class::Rights();
}

View File

@ -14,4 +14,15 @@ class Fahrzeuge_Einweisungen extends \Links\Link
"fields" => [],
"keys" => []
];
protected static $rights = null;
public static function Rights() {
if (is_null(self::$rights)) {
self::$rights = \Rights\LinkRights::Make()
->Add(\Rights\Link::Make("DARF_PERSONAL_VERWALTEN")->Allow("admin"))
->Add(\Rights\Link::Make("DARF_FAHRZEUGEINWEISUNGEN_VERWALTEN")->Allow("admin"));
}
return self::$rights;
}
}

View File

@ -20,4 +20,15 @@ class Fahrzeug extends \Resources\Handler
"Einweisungen" => ["linkClass" => "Fahrzeuge_Einweisungen"],
]
];
protected static $rights = null;
public static function Rights() {
if (is_null(self::$rights)) {
self::$rights = \Rights\MainRights::Make()
->Add(\Rights\Main::Make()->Allow("readonly")) // Jeder darf alle Fahrzeuge SEHEN
->Add(\Rights\Main::Make("DARF_FAHRZEUGE_VERWALTEN")->Allow("admin"));
}
return self::$rights;
}
}

View File

@ -40,4 +40,27 @@ class Personal extends \Resources\Handler
"Bildadresse" => "Nopic.svg",
]
];
protected static $rights = null;
public static function Rights() {
if (is_null(self::$rights)) {
self::$rights = \Rights\MainRights::Make()
->Add(\Rights\Main::Make("DARF_PERSONAL_VERWALTEN")->Allow("admin"))
// Jeder darf sich selbst sehen
->Add(\Rights\Main::Make()->Allow("readonly")->Require(\Rights\Condition::Make()->Add("ID", \Login::ID())))
// Jeder darf seine Telefonnummer und E-Mail-Adresse ändern
->Add(\Rights\Main::Make()
->Allow(["update"])
->Require(\Rights\Condition::Make()->Add("ID", \Login::ID()))
->Limit(["Telefon", "EMail"]))
->Add(\Rights\Main::Make("DARF_KRAFTFAHRER_SEHEN")
->Allow("readonly")
->Require(\Rights\Condition::Make()->Add("Lehrgänge", 5, \Links\Personal_Lehrgänge::Get()->Short())))
->Add(\Rights\Main::Make("DARF_AGTS_SEHEN")
->Allow("readonly")
->Require(\Rights\Condition::Make()->Add("Lehrgänge", 2, \Links\Personal_Lehrgänge::Get()->Short())));
}
return self::$rights;
}
}

View File

@ -65,6 +65,9 @@ Konzeption Feuerwehr-App
https://github.com/nimiq/qr-scanner
- Client 2 / Server 3
- Framework für Mobile- und Webintegration (Flutter?)
- Entkopplung von Templates und Pages
- Golang statt PHP
- Objektifizierung des Backends
- Client 3 / Server 4
- Framework für Mobile- und Webintegration (Flutter?)
- Golang/Rust/C++ statt PHP

View File

@ -3,7 +3,6 @@
namespace Routes;
require_once("resources/Personal/Personal.php");
require_once("links/Personal_Lehrgaenge.php");
require_once("subroutes/Fahrzeuge_Personal.php");
require_once("subroutes/Personal_Abteilungen.php");
require_once("subroutes/Personal_Gruppen.php");
@ -20,19 +19,16 @@ class Personal extends Route
use \Subroutes\Personal_Verwalter;
use \subroutes\Files;
protected $resource = "Personal\\Personal";
protected static $rights = null;
protected static $resource = "Personal\\Personal";
public static function Rights() {
if (is_null(self::$rights)) {
self::$rights = \Rights::Make()
->Add(\Right::Make("DARF_PERSONAL_VERWALTEN")->Allow("admin"))
->Add(\Right::AllowSelf())
->Add(\Right::AllowUpdateSelf()->Limit(["Telefon", "EMail"]))
->Add(\Right::Make("DARF_KRAFTFAHRER_SEHEN")->Allow("readonly")->Require(\Condition::Make()->Add("Lehrgänge", 5, \Links\Personal_Lehrgänge::Get()->Short())))
->Add(\Right::Make("DARF_AGTS_SEHEN")->Allow("readonly")->Require(\Condition::Make()->Add("Lehrgänge", 2, \Links\Personal_Lehrgänge::Get()->Short())));
}
return self::$rights;
return [
"" => ("\\Resources\\".self::$resource)::Rights()->Export(),
"Fahrzeuge" => \Links\Fahrzeuge_Einweisungen::Rights()->Export(),
// "Abteilungen" => \Links\Personal_Abteilungen::Rights()->Export(),
// "Gruppen" => \Links\Personal_Gruppen::Rights()->Export(),
// "Lehrgänge" => \Links\Personal_Lehrgänge::Rights()->Export(),
// "Verwalter" => \Links\Personal_Verwalter::Rights()->Export()
];
}
}

View File

@ -10,7 +10,7 @@ define(
"JWT_KEY",
"v9upLZkm7uVGH9zqEGnp4sZAqeJX33vygYBTKEGdVqtsKeEKaSGp2KBnZmcVNPDb"
."3BkXGwdp9GMDwjaqp6BqfVNRYQf9X5PC8BP74UZPKGPujCeAsayMRpLv2GPBUgXz"
."TVY36KcpYy77SPUmZ7zY2q7ZTFEvM73jMBufdUV8fcEDp4eTQDqMpvp8dhkDxZPj"
."ZVY36KcpYy77SPUmZ7zY2q7ZTFEvM73jMBufdUV8fcEDp4eTQDqMpvp8dhkDxZPj"
."wVYtkHxLtkTHVa9DMm2pWmXqhsjJckgPMxdRsgngCSv8H8BBjXFkG2dn7ndJeApF"
);
define("JWT_VALID_TIME", 7 * 24 * 60 * 60);