diff options
Diffstat (limited to 'Zotlabs/Web')
-rw-r--r-- | Zotlabs/Web/HTTPSig.php | 46 | ||||
-rw-r--r-- | Zotlabs/Web/HttpMeta.php | 13 | ||||
-rw-r--r-- | Zotlabs/Web/Router.php | 91 | ||||
-rw-r--r-- | Zotlabs/Web/Session.php | 2 | ||||
-rw-r--r-- | Zotlabs/Web/WebServer.php | 92 |
5 files changed, 136 insertions, 108 deletions
diff --git a/Zotlabs/Web/HTTPSig.php b/Zotlabs/Web/HTTPSig.php index 7c289ff5f..ce56ae46b 100644 --- a/Zotlabs/Web/HTTPSig.php +++ b/Zotlabs/Web/HTTPSig.php @@ -2,6 +2,7 @@ namespace Zotlabs\Web; +use App; use DateTime; use DateTimeZone; use Zotlabs\Lib\Activity; @@ -11,6 +12,7 @@ use Zotlabs\Lib\Keyutils; use Zotlabs\Lib\Webfinger; use Zotlabs\Lib\Zotfinger; use Zotlabs\Lib\Libzot; +use HttpSignature\HttpMessageSigner; /** * @brief Implements HTTP Signatures per draft-cavage-http-signatures-10. @@ -88,7 +90,7 @@ class HTTPSig { // See draft-cavage-http-signatures-10 - static function verify($data, $key = '', $keytype = '') { + public static function verify($data, $key = '', $keytype = '') { $body = $data; $headers = null; @@ -102,11 +104,49 @@ class HTTPSig { 'content_valid' => false ]; - $headers = self::find_headers($data, $body); - if (!$headers) + if (!$headers) { return $result; + } + + if (array_key_exists('signature-input', $headers) && array_key_exists('signature', $headers)) { + $found = preg_match('/keyid="(.*?)"/', $headers['signature-input'], $matches); + $keyId = ($found) ? $matches[1] : ''; + + if (!$keyId) { + return $result; + } + + $found = preg_match('/alg="(.*?)"/', $headers['signature-input'], $matches); + $alg = ($found) ? $matches[1] : null; + + $keyInfo = self::get_key($key, $keytype, $keyId); + $publicKey = $keyInfo['public_key']; + + $messageSigner = new HttpMessageSigner(); + + $messageSigner->setPublicKey($publicKey); + $messageSigner->setAlgorithm($alg); + $messageSigner->setKeyId($keyId); + + $messageSigner->setNonce(preg_match('/nonce="(.*?)"/', $headers['signature-input'], $matches) ? $matches[1] : ''); + $messageSigner->setTag(preg_match('/tag="(.*?)"/', $headers['signature-input'], $matches) ? $matches[1] : ''); + $messageSigner->setCreated(preg_match('/created=([0-9]+)/', $headers['signature-input'], $matches) ? $matches[1] : ''); + $messageSigner->setExpires(preg_match('/expires=([0-9]+)/', $headers['signature-input'], $matches) ? $matches[1] : ''); + + $verified = $messageSigner->verifyRequest(App::$request); + logger('verified (RFC9421): ' . (($verified) ? 'true' : 'false'), LOGGER_DEBUG); + + return [ + 'signer' => $keyId, + 'portable_id' => $keyInfo['portable_id'] ?? '', + 'header_signed' => true, + 'header_valid' => $verified, + 'content_signed' => array_key_exists('content-digest', $headers), + 'content_valid' => $verified + ]; + } if (is_array($body)) { btlogger('body is array:' . print_r($body, true)); diff --git a/Zotlabs/Web/HttpMeta.php b/Zotlabs/Web/HttpMeta.php index 7cf93dda9..d12037a51 100644 --- a/Zotlabs/Web/HttpMeta.php +++ b/Zotlabs/Web/HttpMeta.php @@ -5,16 +5,9 @@ namespace Zotlabs\Web; class HttpMeta { - private $vars = null; - private $og = null; - - function __construct() { - - $this->vars = []; - $this->og = []; - $this->ogproperties = []; - - } + private $vars = []; + private $og = []; + private $ogproperties = []; //Set Meta Value // Mode: diff --git a/Zotlabs/Web/Router.php b/Zotlabs/Web/Router.php index 122e7ff73..9f4cb4b4a 100644 --- a/Zotlabs/Web/Router.php +++ b/Zotlabs/Web/Router.php @@ -4,6 +4,7 @@ namespace Zotlabs\Web; use App; use Zotlabs\Extend\Route; +use Zotlabs\Render\Theme; use Zotlabs\Lib\Config; use Exception; @@ -33,6 +34,7 @@ use Exception; * so within the module init and/or post functions and then invoke killme() to terminate * further processing. */ + class Router { private $modname = ''; @@ -49,7 +51,7 @@ class Router { $module = App::$module; $modname = "Zotlabs\\Module\\" . ucfirst($module); - if(strlen($module)) { + if(!empty($module)) { /* * We will always have a module name. @@ -57,11 +59,11 @@ class Router { */ $routes = Route::get(); - if($routes) { + if ($routes) { foreach($routes as $route) { - if(is_array($route) && file_exists($route[0]) && strtolower($route[1]) === $module) { + if (is_array($route) && file_exists($route[0]) && strtolower($route[1]) === $module) { include_once($route[0]); - if(class_exists($modname)) { + if (class_exists($modname)) { $this->controller = new $modname; $this->module_loaded = true; } @@ -71,14 +73,14 @@ class Router { // legacy plugins - this can be removed when they have all been converted - if(! ($this->module_loaded)) { - if(is_array(App::$plugins) && in_array($module, App::$plugins) && file_exists("addon/{$module}/{$module}.php")) { + if (!$this->module_loaded) { + if (is_array(App::$plugins) && in_array($module, App::$plugins) && file_exists("addon/{$module}/{$module}.php")) { include_once("addon/{$module}/{$module}.php"); - if(class_exists($modname)) { + if (class_exists($modname)) { $this->controller = new $modname; $this->module_loaded = true; } - elseif(function_exists($module . '_module')) { + elseif (function_exists($module . '_module')) { $this->module_loaded = true; } } @@ -89,7 +91,7 @@ class Router { * Otherwise, look for the standard program module */ - if(! ($this->module_loaded)) { + if (!$this->module_loaded) { try { $filename = 'Zotlabs/SiteModule/'. ucfirst($module). '.php'; if(file_exists($filename)) { @@ -105,15 +107,16 @@ class Router { $this->module_loaded = true; } } - if(! $this->module_loaded) + if (!$this->module_loaded) { throw new Exception('Module not found'); + } } - catch(Exception $e) { - if(file_exists("mod/site/{$module}.php")) { + catch (Exception $e) { + if (file_exists("mod/site/{$module}.php")) { include_once("mod/site/{$module}.php"); $this->module_loaded = true; } - elseif(file_exists("mod/{$module}.php")) { + elseif (file_exists("mod/{$module}.php")) { include_once("mod/{$module}.php"); $this->module_loaded = true; } @@ -125,6 +128,7 @@ class Router { 'installed' => $this->module_loaded, 'controller' => $this->controller ]; + /** * @hooks module_loaded * Called when a module has been successfully locate to server a URL request. @@ -138,7 +142,8 @@ class Router { * * \e mixed \b controller - The initialized module object */ call_hooks('module_loaded', $x); - if($x['installed']) { + + if ($x['installed']) { $this->module_loaded = true; $this->controller = $x['controller']; } @@ -147,7 +152,7 @@ class Router { * The URL provided does not resolve to a valid module. */ - if(! ($this->module_loaded)) { + if (!$this->module_loaded) { // undo the setting of a letsencrypt acme-challenge rewrite rule // which blocks access to our .well-known routes. @@ -155,8 +160,8 @@ class Router { // for a custom .htaccess in the .well-known directory; but they should // make the file read-only so letsencrypt doesn't modify it - if(strpos($_SERVER['REQUEST_URI'],'/.well-known/') === 0) { - if(file_exists('.well-known/.htaccess') && Config::Get('system','fix_apache_acme',true)) { + if (strpos($_SERVER['REQUEST_URI'],'/.well-known/') === 0) { + if (file_exists('.well-known/.htaccess') && Config::Get('system','fix_apache_acme',true)) { rename('.well-known/.htaccess','.well-known/.htaccess.old'); } } @@ -166,16 +171,17 @@ class Router { 'installed' => $this->module_loaded, 'controller' => $this->controller ]; + call_hooks('page_not_found',$x); // Stupid browser tried to pre-fetch our Javascript img template. // Don't log the event or return anything - just quietly exit. - if((x($_SERVER, 'QUERY_STRING')) && preg_match('/{[0-9]}/', $_SERVER['QUERY_STRING']) !== 0) { + if (!empty($_SERVER['QUERY_STRING']) && preg_match('/{[0-9]}/', $_SERVER['QUERY_STRING']) !== 0) { killme(); } - if(Config::Get('system','log_404',true)) { + if (Config::Get('system','log_404',true)) { logger("Module {$module} not found.", LOGGER_DEBUG, LOG_WARNING); logger('index.php: page not found: ' . $_SERVER['REQUEST_URI'] . ' ADDRESS: ' . $_SERVER['REMOTE_ADDR'] . ' QUERY: ' @@ -206,7 +212,7 @@ class Router { * Call module functions */ - if($this->module_loaded) { + if ($this->module_loaded) { App::$page['page_title'] = App::$module; $placeholder = ''; @@ -218,13 +224,18 @@ class Router { * to over-ride them. */ - $arr = array('init' => true, 'replace' => false); + $arr = [ + 'init' => true, + 'replace' => false + ]; + call_hooks(App::$module . '_mod_init', $arr); - if(! $arr['replace']) { - if($this->controller && method_exists($this->controller,'init')) { + + if (!$arr['replace']) { + if ($this->controller && method_exists($this->controller,'init')) { $this->controller->init(); } - elseif(function_exists(App::$module . '_init')) { + elseif (function_exists(App::$module . '_init')) { $func = App::$module . '_init'; $func(); } @@ -250,52 +261,58 @@ class Router { * load current theme info */ - $current_theme = \Zotlabs\Render\Theme::current(); + $current_theme = Theme::current(); $theme_info_file = 'view/theme/' . $current_theme[0] . '/php/theme.php'; if (file_exists($theme_info_file)){ require_once($theme_info_file); } - if(function_exists(str_replace('-', '_', $current_theme[0]) . '_init')) { + if (function_exists(str_replace('-', '_', $current_theme[0]) . '_init')) { $func = str_replace('-', '_', $current_theme[0]) . '_init'; $func(); } - elseif (x(App::$theme_info, 'extends') && file_exists('view/theme/' . App::$theme_info['extends'] . '/php/theme.php')) { + elseif (!empty(App::$theme_info['extends']) && file_exists('view/theme/' . App::$theme_info['extends'] . '/php/theme.php')) { require_once('view/theme/' . App::$theme_info['extends'] . '/php/theme.php'); - if(function_exists(str_replace('-', '_', App::$theme_info['extends']) . '_init')) { + if (function_exists(str_replace('-', '_', App::$theme_info['extends']) . '_init')) { $func = str_replace('-', '_', App::$theme_info['extends']) . '_init'; $func(); } } - if(($_SERVER['REQUEST_METHOD'] === 'POST') && (! App::$error) && (! x($_POST, 'auth-params'))) { + if ($_SERVER['REQUEST_METHOD'] === 'POST' && !App::$error && empty($_POST['auth-params'])) { call_hooks(App::$module . '_mod_post', $_POST); - if($this->controller && method_exists($this->controller,'post')) { + if ($this->controller && method_exists($this->controller, 'post')) { $this->controller->post(); } - elseif(function_exists(App::$module . '_post')) { + elseif (function_exists(App::$module . '_post')) { $func = App::$module . '_post'; $func(); } } - if(! App::$error) { - $arr = array('content' => App::$page['content'], 'replace' => false); + if (!App::$error) { + $arr = [ + 'content' => App::$page['content'], + 'replace' => false + ]; + call_hooks(App::$module . '_mod_content', $arr); - if(! $arr['replace']) { - if($this->controller && method_exists($this->controller,'get')) { + if (!$arr['replace']) { + if ($this->controller && method_exists($this->controller, 'get')) { $arr = array('content' => $this->controller->get()); } - elseif(function_exists(App::$module . '_content')) { + elseif (function_exists(App::$module . '_content')) { $func = App::$module . '_content'; $arr = array('content' => $func()); } } + call_hooks(App::$module . '_mod_aftercontent', $arr); - App::$page['content'] = ((isset($arr['replace'])) ? $arr['content'] : App::$page['content'] . $arr['content']); + + App::$page['content'] = ((empty($arr['replace'])) ? App::$page['content'] . $arr['content'] : $arr['content']); } } } diff --git a/Zotlabs/Web/Session.php b/Zotlabs/Web/Session.php index ec26e6b0d..1762d3832 100644 --- a/Zotlabs/Web/Session.php +++ b/Zotlabs/Web/Session.php @@ -132,7 +132,7 @@ class Session { else logger('no session handler'); - if (x($_COOKIE, 'jsdisabled')) { + if (!empty($_COOKIE['jsdisabled'])) { setcookie( 'jsdisabled', $_COOKIE['jsdisabled'], diff --git a/Zotlabs/Web/WebServer.php b/Zotlabs/Web/WebServer.php index 6f8a4b956..89ef755d9 100644 --- a/Zotlabs/Web/WebServer.php +++ b/Zotlabs/Web/WebServer.php @@ -2,6 +2,10 @@ namespace Zotlabs\Web; +use App; +use Zotlabs\Lib\Text; +use GuzzleHttp\Psr7\ServerRequest; + class WebServer { public function run() { @@ -15,9 +19,10 @@ class WebServer { $installed = sys_boot(); + App::$request = ServerRequest::fromGlobals(); - \App::$language = get_best_language(); - load_translation_table(\App::$language, !$installed); + App::$language = get_best_language(); + load_translation_table(App::$language, !$installed); /** @@ -31,8 +36,8 @@ class WebServer { * */ - if(\App::$session) { - \App::$session->start(); + if(App::$session) { + App::$session->start(); } else { session_start(); @@ -51,16 +56,16 @@ class WebServer { unset($_SESSION['language']); } - if ((x($_SESSION, 'language')) && ($_SESSION['language'] !== \App::$language)) { - \App::$language = $_SESSION['language']; + if ((!empty($_SESSION['language'])) && ($_SESSION['language'] !== App::$language)) { + App::$language = $_SESSION['language']; load_translation_table(\App::$language); } - if (x($_GET,'zid') && $installed) { - \App::$query_string = strip_zids(\App::$query_string); + if (!empty($_GET['zid']) && $installed) { + App::$query_string = strip_zids(App::$query_string); if(! local_channel()) { - if (!isset($_SESSION['my_address']) || $_SESSION['my_address'] != $_GET['zid']) { - $_SESSION['my_address'] = $_GET['zid']; + if (!isset($_SESSION['my_address'])) { + $_SESSION['my_address'] = Text::escape_tags($_GET['zid']); $_SESSION['authenticated'] = 0; } if(!$_SESSION['authenticated']) { @@ -69,26 +74,28 @@ class WebServer { } } - if (x($_GET,'zat') && $installed) { - \App::$query_string = strip_zats(\App::$query_string); + if (!empty($_GET['zat']) && $installed) { + App::$query_string = strip_zats(App::$query_string); if(! local_channel()) { zat_init(); } } - if (x($_REQUEST,'owt') && $installed) { + if (!empty($_REQUEST['owt']) && $installed) { $token = $_REQUEST['owt']; - \App::$query_string = strip_query_param(\App::$query_string,'owt'); + App::$query_string = strip_query_param(App::$query_string,'owt'); owt_init($token); } - if((x($_SESSION, 'authenticated')) || (x($_POST, 'auth-params')) || (\App::$module === 'login')) + if(!empty($_SESSION['authenticated']) || !empty($_POST['auth-params']) || App::$module === 'login') { require('include/auth.php'); + } if (!$installed) { /* Allow an exception for the view module so that pcss will be interpreted during installation */ - if(\App::$module != 'view') - \App::$module = 'setup'; + if(App::$module != 'view') { + App::$module = 'setup'; + } } else { @@ -109,17 +116,7 @@ class WebServer { $Router->Dispatch(); - // TODO: this is not used for anything atm and messes up comanche templates by adding some javascript - //$this->set_homebase(); - - // now that we've been through the module content, see if the page reported - // a permission problem and if so, a 403 response would seem to be in order. - - if(isset($_SESSION['sysmsg']) && is_array($_SESSION['sysmsg']) && stristr(implode("", $_SESSION['sysmsg']), t('Permission denied'))) { - header($_SERVER['SERVER_PROTOCOL'] . ' 403 ' . t('Permission denied.')); - } - - call_hooks('page_end', \App::$page['content']); + call_hooks('page_end', App::$page['content']); construct_page(); @@ -131,10 +128,11 @@ class WebServer { /* initialise content region */ - if(! x(\App::$page, 'content')) - \App::$page['content'] = ''; + if(empty(App::$page['content'])) { + App::$page['content'] = ''; + } - call_hooks('page_content_top', \App::$page['content']); + call_hooks('page_content_top', App::$page['content']); } @@ -146,44 +144,24 @@ class WebServer { * to all protocol drivers; thus doing it here avoids duplication. */ - if (( \App::$module === 'channel' ) && argc() > 1) { - \App::$channel_links = [ + if (App::$module === 'channel' && argc() > 1) { + App::$channel_links = [ [ 'rel' => 'lrdd', 'type' => 'application/xrd+xml', - 'url' => z_root() . '/xrd?f=&uri=acct%3A' . argv(1) . '%40' . \App::get_hostname() + 'url' => z_root() . '/xrd?f=&uri=acct%3A' . argv(1) . '%40' . App::get_hostname() ], [ 'rel' => 'jrd', 'type' => 'application/jrd+json', - 'url' => z_root() . '/.well-known/webfinger?f=&resource=acct%3A' . argv(1) . '%40' . \App::get_hostname() + 'url' => z_root() . '/.well-known/webfinger?f=&resource=acct%3A' . argv(1) . '%40' . App::get_hostname() ], ]; - $x = [ 'channel_address' => argv(1), 'channel_links' => \App::$channel_links ]; + $x = [ 'channel_address' => argv(1), 'channel_links' => App::$channel_links ]; call_hooks('channel_links', $x ); - \App::$channel_links = $x['channel_links']; + App::$channel_links = $x['channel_links']; header('Link: ' . \App::get_channel_links()); } } - - private function set_homebase() { - - // If you're just visiting, let javascript take you home - - if(x($_SESSION, 'visitor_home')) { - $homebase = $_SESSION['visitor_home']; - } - elseif(local_channel()) { - $homebase = z_root() . '/channel/' . \App::$channel['channel_address']; - } - - if(isset($homebase)) { - \App::$page['content'] .= '<script>var homebase = "' . $homebase . '";</script>'; - } - - } - - - } |