diff options
author | friendica <info@friendica.com> | 2013-12-05 15:40:50 -0800 |
---|---|---|
committer | friendica <info@friendica.com> | 2013-12-05 15:40:50 -0800 |
commit | d66d8ff524203ccc0fae894b483178b2f706b711 (patch) | |
tree | 97597dd54adfa7f9ad1f657589d20457bfdc561c | |
parent | cc1e906825dd30f74d0a30190a7dd2a26d6b1642 (diff) | |
download | volse-hubzilla-d66d8ff524203ccc0fae894b483178b2f706b711.tar.gz volse-hubzilla-d66d8ff524203ccc0fae894b483178b2f706b711.tar.bz2 volse-hubzilla-d66d8ff524203ccc0fae894b483178b2f706b711.zip |
mod_authtest --- magic-auth diagnostic for those that are too freaking important to read logs or code and expect others to be able to debug complex authentication transactions with no information beyond "it didn't work". This will provide a transaction report including both sides of the exchange that you can paste into a bug report and that a developer can actually figure out where in the transaction that things went wrong and maybe even be able to then figure out why.
-rw-r--r-- | mod/authtest.php | 43 | ||||
-rw-r--r-- | mod/magic.php | 48 | ||||
-rw-r--r-- | mod/post.php | 64 | ||||
-rw-r--r-- | version.inc | 2 |
4 files changed, 147 insertions, 10 deletions
diff --git a/mod/authtest.php b/mod/authtest.php new file mode 100644 index 000000000..ec32fe171 --- /dev/null +++ b/mod/authtest.php @@ -0,0 +1,43 @@ +<?php + +require_once('include/zot.php'); +require_once('mod/magic.php'); + +function authtest_content(&$a) { + + + + $o .= '<h3>Magic-Auth Diagnostic</h3>'; + + if(! local_user()) { + notice( t('Permission denied.') . EOL); + return $o; + } + + $o .= '<form action="authtest" method="get">'; + $o .= 'Target URL: <input type="text" style="width: 250px;" name="dest" value="' . $_GET['dest'] .'" />'; + $o .= '<input type="submit" name="submit" value="Submit" /></form>'; + + $o .= '<br /><br />'; + + if(x($_GET,'dest')) { + $_REQUEST['test'] = 1; + $x = magic_init($a); + $o .= 'Local Setup returns: ' . print_r($x,true); + + + + if($x['url']) { + $z = z_fetch_url($x['url'] . '&test=1'); + if($z['success']) { + $j = json_decode($z['body'],true); + $o .= 'Remote site responded: ' . print_r($j,true); + } + else { + $o .= 'fetch url failure.' . print_r($z,true); + } + } + } + + return str_replace("\n",'<br />',$o); +} diff --git a/mod/magic.php b/mod/magic.php index a268f1ecb..03d09e70d 100644 --- a/mod/magic.php +++ b/mod/magic.php @@ -4,6 +4,7 @@ function magic_init(&$a) { + $ret = array('success' => false, 'url' => '', 'message' => ''); logger('mod_magic: invoked', LOGGER_DEBUG); logger('mod_magic: args: ' . print_r($_REQUEST,true),LOGGER_DATA); @@ -11,12 +12,18 @@ function magic_init(&$a) { $addr = ((x($_REQUEST,'addr')) ? $_REQUEST['addr'] : ''); $hash = ((x($_REQUEST,'hash')) ? $_REQUEST['hash'] : ''); $dest = ((x($_REQUEST,'dest')) ? $_REQUEST['dest'] : ''); - $rev = ((x($_REQUEST,'rev')) ? intval($_REQUEST['rev']) : 0); + $test = ((x($_REQUEST,'test')) ? intval($_REQUEST['test']) : 0); + $rev = ((x($_REQUEST,'rev')) ? intval($_REQUEST['rev']) : 0); $parsed = parse_url($dest); - if(! $parsed) + if(! $parsed) { + if($test) { + $ret['message'] .= 'could not parse ' . $dest . EOL; + return($ret); + } goaway($dest); + } $basepath = $parsed['scheme'] . '://' . $parsed['host'] . (($parsed['port']) ? ':' . $parsed['port'] : ''); @@ -49,6 +56,10 @@ function magic_init(&$a) { goaway($dest); else { logger('mod_magic: no channels found for requested hub.' . print_r($_REQUEST,true)); + if($test) { + $ret['message'] .= 'This site has no previous connections with ' . $basepath . EOL; + return $ret; + } notice( t('Hub not found.') . EOL); return; } @@ -66,12 +77,22 @@ function magic_init(&$a) { call_hooks('magic_auth',$arr); $dest = $arr['destination']; - if(! $arr['proceed']) + if(! $arr['proceed']) { + if($test) { + $ret['message'] .= 'cancelled by plugin.' . EOL; + return $ret; + } goaway($dest); + } if((get_observer_hash()) && ($x[0]['hubloc_url'] === z_root())) { // We are already authenticated on this site and a registered observer. // Just redirect. + if($test) { + $ret['success'] = true; + $ret['message'] .= 'Local site - you are already authenticated.' . EOL; + return $ret; + } goaway($dest); } @@ -92,12 +113,25 @@ function magic_init(&$a) { dbesc(datetime_convert()) ); - $target_url = $x[0]['hubloc_callback']; + $target_url = $x[0]['hubloc_callback'] . '/?f=&auth=' . urlencode($channel['channel_address'] . '@' . $a->get_hostname()) + . '&sec=' . $token . '&dest=' . urlencode($dest) . '&version=' . ZOT_REVISION; + logger('mod_magic: redirecting to: ' . $target_url, LOGGER_DEBUG); - goaway($target_url - . '/?f=&auth=' . urlencode($channel['channel_address'] . '@' . $a->get_hostname()) - . '&sec=' . $token . '&dest=' . urlencode($dest) . '&version=' . ZOT_REVISION); + if($test) { + $ret['success'] = true; + $ret['url'] = $target_url; + $ret['message'] = 'token ' . $token . ' created for channel ' . $channel['channel_id'] . ' for url ' . $x[0]['hubloc_url'] . EOL; + return $ret; + } + + goaway($target_url); + + } + + if($test) { + $ret['message'] = 'Not authenticated or invalid arguments to mod_magic' . EOL; + return $ret; } goaway($dest); diff --git a/mod/post.php b/mod/post.php index e589378dc..31f17a873 100644 --- a/mod/post.php +++ b/mod/post.php @@ -83,12 +83,15 @@ function post_init(&$a) { */ if(array_key_exists('auth',$_REQUEST)) { + + $ret = array('success' => false, 'message' => ''); + logger('mod_zot: auth request received.'); $address = $_REQUEST['auth']; $desturl = $_REQUEST['dest']; $sec = $_REQUEST['sec']; $version = $_REQUEST['version']; - + $test = ((x($_REQUEST,'test')) ? intval($_REQUEST['test']) : 0); // They are authenticating ultimately to the site and not to a particular channel. // Any channel will do, providing it's currently active. We just need to have an @@ -100,8 +103,12 @@ function post_init(&$a) { if(! $c) { // nobody here - logger('mod_zot: auth: unable to find a response channel'); + if($test) { + $ret['message'] .= 'no local channels found.' . EOL; + json_return_and_die($ret); + } + goaway($desturl); } @@ -124,6 +131,12 @@ function post_init(&$a) { } if(! $x) { logger('mod_zot: auth: unable to finger ' . $address); + + if($test) { + $ret['message'] .= 'no hubloc found for ' . $address . ' and probing failed.' . EOL; + json_return_and_die($ret); + } + goaway($desturl); } @@ -143,6 +156,8 @@ function post_init(&$a) { $already_authed = ((($remote) && ($x[0]['hubloc_hash'] == $remote) && ($x[0]['hubloc_url'] === $_SESSION['remote_hub'])) ? true : false); + $j = array(); + if(! $already_authed) { // Auth packets MUST use ultra top-secret hush-hush mode - e.g. the entire packet is encrypted using the site private key @@ -150,9 +165,21 @@ function post_init(&$a) { // which can be verified $p = zot_build_packet($c[0],$type = 'auth_check', array(array('guid' => $x[0]['hubloc_guid'],'guid_sig' => $x[0]['hubloc_guid_sig'])), $x[0]['hubloc_sitekey'], $sec); + if($test) { + $ret['message'] .= 'auth check packet created using sitekey ' . $x[0]['hubloc_sitekey'] . EOL; + $ret['message'] .= 'packet contents: ' . $p . EOL; + } + $result = zot_zot($x[0]['hubloc_callback'],$p); + + $ret['message'] .= 'auth check request to your site returned .' . print_r($result, true) . EOL; + if(! $result['success']) { logger('mod_zot: auth_check callback failed.'); + if($test) { + json_return_and_die($ret); + } + goaway($desturl); } $j = json_decode($result['body'],true); @@ -163,6 +190,11 @@ function post_init(&$a) { // legit response, but we do need to check that this wasn't answered by a man-in-middle if(! rsa_verify($sec . $x[0]['xchan_hash'],base64url_decode($j['confirm']),$x[0]['xchan_pubkey'])) { logger('mod_zot: auth: final confirmation failed.'); + if($test) { + $ret['message'] .= 'final confirmation failed. ' . $sec . print_r($j,true) . print_r($x[0],true); + json_return_and_die($ret); + } + goaway($desturl); } if(array_key_exists('service_class',$j)) @@ -177,11 +209,23 @@ function post_init(&$a) { if($a->channel['channel_hash'] != $x[0]['xchan_hash']) { logger('mod_zot: auth: already authenticated locally as somebody else.'); notice( t('Remote authentication blocked. You are logged into this site locally. Please logout and retry.') . EOL); + if($test) { + $ret['message'] .= 'already logged in locally with a conflicting identity.' . EOL; + json_return_and_die($ret); + } + } goaway($desturl); } // log them in + if($test) { + $ret['success'] = true; + $ret['message'] .= 'Success' . EOL; + json_return_and_die($ret); + } + + $_SESSION['authenticated'] = 1; $_SESSION['visitor_id'] = $x[0]['xchan_hash']; $_SESSION['my_address'] = $address; @@ -197,6 +241,11 @@ function post_init(&$a) { logger('mod_zot: auth success from ' . $x[0]['xchan_addr']); } else { + if($test) { + $ret['message'] .= 'auth failure. ' . print_r($_REQUEST,true) . print_r($j,true) . EOL; + json_return_and_dir($ret); + } + logger('mod_zot: magic-auth failure - not authenticated: ' . $x[0]['xchan_addr']); q("update hubloc set hubloc_status = (hubloc_status | %d ) where hubloc_id = %d ", intval(HUBLOC_RECEIVE_ERROR), @@ -208,6 +257,11 @@ function post_init(&$a) { // This does however prevent a recursion if you visit rmagic directly, as it would otherwise send you back here again. // But z_root() probably isn't where you really want to go. + if($test) { + $ret['message'] .= 'auth failure fallthrough ' . print_r($_REQUEST,true) . print_r($j,true) . EOL; + json_return_and_dir($ret); + } + if(strstr($desturl,z_root() . '/rmagic')) goaway(z_root()); @@ -608,6 +662,7 @@ function post_post(&$a) { if(! $encrypted_packet) { logger('mod_zot: auth_check packet was not encrypted.'); + $ret['message'] .= 'no packet encryption' . EOL; json_return_and_die($ret); } @@ -628,11 +683,14 @@ function post_post(&$a) { if((! $y) || (! rsa_verify($data['secret'],base64url_decode($data['secret_sig']),$y[0]['xchan_pubkey']))) { logger('mod_zot: auth_check: sender not found or secret_sig invalid.'); + $ret['message'] .= 'sender not found or sig invalid ' . print_r($y,true) . EOL; json_return_and_die($ret); } // There should be exactly one recipient, the original auth requestor + $ret['message'] .= 'recipients ' . print_r($recipients,true) . EOL; + if($data['recipients']) { $arr = $data['recipients'][0]; @@ -642,6 +700,7 @@ function post_post(&$a) { ); if(! $c) { logger('mod_zot: auth_check: recipient channel not found.'); + $ret['message'] .= 'recipient not found.' . EOL; json_return_and_die($ret); } @@ -657,6 +716,7 @@ function post_post(&$a) { ); if(! $z) { logger('mod_zot: auth_check: verification key not found.'); + $ret['message'] .= 'verification key not found' . EOL; json_return_and_die($ret); } $r = q("delete from verify where id = %d limit 1", diff --git a/version.inc b/version.inc index 8e4f4a4dc..b1d3ec938 100644 --- a/version.inc +++ b/version.inc @@ -1 +1 @@ -2013-12-04.517 +2013-12-05.518 |