diff options
author | marijus <mario@mariovavti.com> | 2014-08-22 09:14:19 +0200 |
---|---|---|
committer | marijus <mario@mariovavti.com> | 2014-08-22 09:14:19 +0200 |
commit | c5f4e5bac76de93b30c00fa9fb3dc8a559d7b070 (patch) | |
tree | fcb7c92735bbcbae9359d3fcf91a185226698426 | |
parent | 85ef5c10333ce4ce9d7e2d4b17caa4b1e7c871ef (diff) | |
parent | 1abd2a2917504d102a6e4c6a9c34fa4a5fba4937 (diff) | |
download | volse-hubzilla-c5f4e5bac76de93b30c00fa9fb3dc8a559d7b070.tar.gz volse-hubzilla-c5f4e5bac76de93b30c00fa9fb3dc8a559d7b070.tar.bz2 volse-hubzilla-c5f4e5bac76de93b30c00fa9fb3dc8a559d7b070.zip |
Merge branch 'master' of https://github.com/friendica/red into upstream
-rwxr-xr-x | boot.php | 5 | ||||
-rw-r--r-- | doc/de/main.bb | 1 | ||||
-rw-r--r-- | include/chat.php | 23 | ||||
-rw-r--r-- | include/crypto.php | 5 | ||||
-rwxr-xr-x | include/diaspora.php | 237 | ||||
-rw-r--r-- | include/externals.php | 2 | ||||
-rw-r--r-- | include/identity.php | 24 | ||||
-rwxr-xr-x | include/items.php | 585 | ||||
-rw-r--r-- | include/network.php | 166 | ||||
-rwxr-xr-x | include/text.php | 8 | ||||
-rw-r--r-- | include/zot.php | 16 | ||||
-rw-r--r-- | mod/admin.php | 50 | ||||
-rw-r--r-- | mod/dirsearch.php | 4 | ||||
-rw-r--r-- | mod/frphotos.php | 87 | ||||
-rw-r--r-- | mod/item.php | 1 | ||||
-rw-r--r-- | mod/profiles.php | 19 | ||||
-rw-r--r-- | mod/receive.php | 9 | ||||
-rw-r--r-- | mod/xrd.php | 21 | ||||
-rw-r--r-- | util/frphotohelper.php | 75 | ||||
-rw-r--r-- | version.inc | 2 | ||||
-rwxr-xr-x | view/tpl/admin_site.tpl | 1 | ||||
-rw-r--r-- | view/tpl/diaspora_vcard.tpl | 57 | ||||
-rwxr-xr-x | view/tpl/field_acheckbox.tpl | 2 | ||||
-rw-r--r-- | view/tpl/frphotos.tpl | 13 | ||||
-rwxr-xr-x | view/tpl/profile_edit.tpl | 9 | ||||
-rwxr-xr-x | view/tpl/profile_vcard.tpl | 3 | ||||
-rw-r--r-- | view/tpl/xrd_diaspora.tpl | 8 | ||||
-rwxr-xr-x | view/tpl/xrd_person.tpl | 10 |
28 files changed, 663 insertions, 780 deletions
@@ -358,11 +358,6 @@ define ( 'MAX_LIKERS', 10); define ( 'ZCURL_TIMEOUT' , (-1)); -/** - * Hours before chat lines are deleted - */ - -define ( 'MAX_CHATROOM_HOURS' , 36); /** * email notification options diff --git a/doc/de/main.bb b/doc/de/main.bb index 1c8031c3e..7a4c8ebe2 100644 --- a/doc/de/main.bb +++ b/doc/de/main.bb @@ -58,6 +58,7 @@ Zot ist das großartige neue Kommunikationsprotokoll, das extra für die Red-Mat [zrl=[baseurl]/help/developers]Entwickler[/zrl] [zrl=[baseurl]/help/intro_for_developers]Einführung für Entwickler[/zrl] [zrl=[baseurl]/help/api_functions]API-Funktionen[/zrl] +[zrl=[baseurl]/help/api_posting]Mit der API einen Beitrag erstellen[/zrl] [zrl=[baseurl]/help/developer_function_primer]Übersicht der wichtigsten Red-Funktionen[/zrl] [zrl=[baseurl]/doc/html/]Code-Referenz (mit doxygen generiert - setzt Cookies)[/zrl] [zrl=[baseurl]/help/to_do_doco]To-Do-Liste für das Projekt Red-Dokumentation[/zrl] diff --git a/include/chat.php b/include/chat.php index 5f69853e7..b8fb185df 100644 --- a/include/chat.php +++ b/include/chat.php @@ -128,8 +128,10 @@ function chatroom_enter($observer_xchan,$room_id,$status,$client) { } } - if(intval($x[0]['cr_expire'])) - $r = q("delete from chat where created < UTC_TIMESTAMP() - INTERVAL " . intval($x[0]['cr_expire']) . " MINUTE and chat_room = " . intval($x[0]['cr_id'])); + if(intval($x[0]['cr_expire'])) { + $sql = "delete from chat where created < UTC_TIMESTAMP() - INTERVAL " . intval($x[0]['cr_expire']) . " MINUTE and chat_room = " . intval($x[0]['cr_id']); + $r = q($sql); + } $r = q("select * from chatpresence where cp_xchan = '%s' and cp_room = %d limit 1", dbesc($observer_xchan), @@ -153,7 +155,6 @@ function chatroom_enter($observer_xchan,$room_id,$status,$client) { dbesc($client) ); - chatroom_flush($room_id,$xchan); return $r; } @@ -226,21 +227,5 @@ function chat_message($uid,$room_id,$xchan,$text) { ); $ret['success'] = true; - chatroom_flush($room_id,$xchan); return $ret; } - -/** - * Reduces the number of lines shown in chat by removing those older than MAX_CHATROOM_HOURS - */ - -function chatroom_flush($room_id,$xchan) { - - - $date_limit = date('Y-m-d H:i:s', time() - 3600 * MAX_CHATROOM_HOURS); - $d = q("delete from chat where chat_room = %d and chat_xchan = '%s' and created < '%s'", - intval($room_id), - dbesc($xchan), - datetime_convert('','', $date_limit)); - return true; -} diff --git a/include/crypto.php b/include/crypto.php index c053dfae2..07655e24f 100644 --- a/include/crypto.php +++ b/include/crypto.php @@ -1,5 +1,8 @@ <?php /** @file */ +require_once('library/ASNValue.class.php'); +require_once('library/asn1.php'); + function rsa_sign($data,$key,$alg = 'sha256') { if(! $key) return 'no key'; @@ -241,7 +244,6 @@ function metopem($m,$e) { function pubrsatome($key,&$m,&$e) { require_once('library/asn1.php'); - require_once('include/salmon.php'); $lines = explode("\n",$key); unset($lines[0]); @@ -266,7 +268,6 @@ function pemtorsa($key) { } function pemtome($key,&$m,&$e) { - require_once('include/salmon.php'); $lines = explode("\n",$key); unset($lines[0]); unset($lines[count($lines)]); diff --git a/include/diaspora.php b/include/diaspora.php index dda552536..982e40f2f 100755 --- a/include/diaspora.php +++ b/include/diaspora.php @@ -106,29 +106,49 @@ function diaspora_dispatch($importer,$msg,$attempt=1) { return $ret; } -function diaspora_handle_from_contact($contact_id) { - $handle = false; - logger("diaspora_handle_from_contact: contact id is " . $contact_id, LOGGER_DEBUG); +function diaspora_is_blacklisted($s) { - $r = q("SELECT * from abook left join xchan on abook_xchan = xchan_hash where abook_id = %d", - intval($contact_id) + $bl1 = get_config('system','blacklisted_sites'); + if(is_array($bl1) && $bl1) { + foreach($bl1 as $bl) { + if($bl && strpos($s,$bl) !== false) { + logger('diaspora_is_blacklisted: blacklisted ' . $s); + return true; + } + } + } + return false; +} + + + + + + +function diaspora_handle_from_contact($contact_hash) { + + logger("diaspora_handle_from_contact: contact id is " . $contact_hash, LOGGER_DEBUG); + + $r = q("SELECT * from abook left join xchan on abook_xchan = xchan_hash where abook_xchan = '%s' limit 1", + intval($contact_hash) ); if($r) { - $contact = $r[0]; + return $r[0]['xchan_addr']; } - $handle = $contact['xchan_addr']; - return $handle; + return false; } function diaspora_get_contact_by_handle($uid,$handle) { + + if(diaspora_is_blacklisted($handle)) + return false; + $r = q("SELECT * FROM abook left join xchan on xchan_hash = abook_xchan where xchan_addr = '%s' and abook_channel = %d limit 1", dbesc($handle), intval($uid) ); - if($r) - return $r[0]; - return false; + return (($r) ? $r[0] : false); } function find_diaspora_person_by_handle($handle) { @@ -140,6 +160,8 @@ function find_diaspora_person_by_handle($handle) { $endlessloop = 0; $maxloops = 10; + if(diaspora_is_blacklisted($handle)) + return false; $r = q("select * from xchan where xchan_addr = '%s' limit 1", dbesc($handle) @@ -162,6 +184,7 @@ function find_diaspora_person_by_handle($handle) { $result = discover_by_webbie($handle); + } @@ -169,13 +192,10 @@ function find_diaspora_person_by_handle($handle) { } -function get_diaspora_key($uri) { - logger('Fetching diaspora key for: ' . $uri); - - $r = find_diaspora_person_by_handle($uri); - if($r) - return $r['pubkey']; - return ''; +function get_diaspora_key($handle) { + logger('Fetching diaspora key for: ' . $handle, LOGGER_DEBUG); + $r = find_diaspora_person_by_handle($handle); + return(($r) ? $r['xchan_pubkey'] : ''); } @@ -350,7 +370,7 @@ function diaspora_decode($importer,$xml) { $ciphertext = base64_decode($encrypted_header->ciphertext); $outer_key_bundle = ''; - openssl_private_decrypt($encrypted_aes_key_bundle,$outer_key_bundle,$importer['prvkey']); + openssl_private_decrypt($encrypted_aes_key_bundle,$outer_key_bundle,$importer['channel_prvkey']); $j_outer_key_bundle = json_decode($outer_key_bundle); @@ -428,7 +448,6 @@ function diaspora_decode($importer,$xml) { $encoding = $base->encoding; $alg = $base->alg; - $signed_data = $data . '.' . base64url_encode($type) . '.' . base64url_encode($encoding) . '.' . base64url_encode($alg); @@ -580,15 +599,14 @@ function diaspora_request($importer,$xml) { return; } -//FIXME -// $g = q("select def_gid from user where uid = %d limit 1", -// intval($importer['channel_id']) -// ); -// if($g && intval($g[0]['def_gid'])) { -// require_once('include/group.php'); -// group_add_member($importer['channel_id'],'',$contact_record['id'],$g[0]['def_gid']); -// } + /** If there is a default group for this channel, add this member to it */ + if($importer['channel_default_group']) { + require_once('include/group.php'); + $g = group_rec_byhash($importer['channel_id'],$importer['channel_default_group']); + if($g) + group_add_member($importer['channel_id'],'',$contact_record['xchan_hash'],$g['id']); + } return; } @@ -680,9 +698,6 @@ function diaspora_post($importer,$xml,$msg) { $datarray['uid'] = $importer['channel_id']; // FIXME - $datarray['contact-id'] = $contact['id']; - $datarray['wall'] = 0; - $datarray['network'] = NETWORK_DIASPORA; $datarray['verb'] = ACTIVITY_POST; @@ -691,7 +706,6 @@ function diaspora_post($importer,$xml,$msg) { $datarray['changed'] = $datarray['created'] = $datarray['edited'] = datetime_convert('UTC','UTC',$created); $datarray['item_private'] = $private; - $datarray['plink'] = $plink; $datarray['author_xchan'] = $contact['xchan_hash']; @@ -2029,8 +2043,8 @@ function diaspora_profile($importer,$xml,$msg) { function diaspora_share($me,$contact) { $a = get_app(); - $myaddr = $me['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); - $theiraddr = $contact['addr']; + $myaddr = $me['channel_address'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); + $theiraddr = $contact['xchan_addr']; $tpl = get_markup_template('diaspora_share.tpl'); $msg = replace_macros($tpl, array( @@ -2067,8 +2081,8 @@ function diaspora_unshare($me,$contact) { function diaspora_send_status($item,$owner,$contact,$public_batch = false) { $a = get_app(); - $myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); - $theiraddr = $contact['addr']; + $myaddr = $owner['channel_address'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); + $theiraddr = $contact['xchan_addr']; $images = array(); @@ -2120,44 +2134,44 @@ function diaspora_send_status($item,$owner,$contact,$public_batch = false) { } - $public = (($item['private']) ? 'false' : 'true'); + $public = (($item['item_private']) ? 'false' : 'true'); require_once('include/datetime.php'); $created = datetime_convert('UTC','UTC',$item['created'],'Y-m-d H:i:s \U\T\C'); // Detect a share element and do a reshare // see: https://github.com/Raven24/diaspora-federation/blob/master/lib/diaspora-federation/entities/reshare.rb - if (!$item['private'] AND ($ret = diaspora_is_reshare($item["body"]))) { + if (!$item['item_private'] AND ($ret = diaspora_is_reshare($item["body"]))) { $tpl = get_markup_template('diaspora_reshare.tpl'); $msg = replace_macros($tpl, array( '$root_handle' => xmlify($ret['root_handle']), '$root_guid' => $ret['root_guid'], - '$guid' => $item['guid'], + '$guid' => $item['mid'], '$handle' => xmlify($myaddr), '$public' => $public, '$created' => $created, - '$provider' => $item["app"] + '$provider' => $item['app'] )); } else { $tpl = get_markup_template('diaspora_post.tpl'); $msg = replace_macros($tpl, array( '$body' => $body, - '$guid' => $item['guid'], + '$guid' => $item['mid'], '$handle' => xmlify($myaddr), '$public' => $public, '$created' => $created, - '$provider' => $item["app"] + '$provider' => $item['app'] )); } - logger('diaspora_send_status: '.$owner['username'].' -> '.$contact['name'].' base message: '.$msg, LOGGER_DATA); + logger('diaspora_send_status: '.$owner['channel_name'].' -> '.$contact['xchan_name'].' base message: '.$msg, LOGGER_DATA); - $slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch))); + $slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['channel_prvkey'],$contact['xchan_pubkey'],$public_batch))); //$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)); $return_code = diaspora_transmit($owner,$contact,$slap,$public_batch); - logger('diaspora_send_status: guid: '.$item['guid'].' result '.$return_code, LOGGER_DEBUG); + logger('diaspora_send_status: guid: '.$item['mid'].' result '.$return_code, LOGGER_DEBUG); if(count($images)) { diaspora_send_images($item,$owner,$contact,$images,$public_batch); @@ -2167,51 +2181,52 @@ function diaspora_send_status($item,$owner,$contact,$public_batch = false) { } function diaspora_is_reshare($body) { + $body = trim($body); - // Skip if it isn't a pure repeated messages - // Does it start with a share? - if (strpos($body, "[share") > 0) - return(false); + // Skip if it isn't a pure repeated messages + // Does it start with a share? + if(strpos($body, "[share") > 0) + return(false); - // Does it end with a share? - if (strlen($body) > (strrpos($body, "[/share]") + 8)) - return(false); + // Does it end with a share? + if(strlen($body) > (strrpos($body, "[/share]") + 8)) + return(false); - $attributes = preg_replace("/\[share(.*?)\]\s?(.*?)\s?\[\/share\]\s?/ism","$1",$body); - // Skip if there is no shared message in there - if ($body == $attributes) - return(false); + $attributes = preg_replace("/\[share(.*?)\]\s?(.*?)\s?\[\/share\]\s?/ism","$1",$body); + // Skip if there is no shared message in there + if ($body == $attributes) + return(false); - $profile = ""; - preg_match("/profile='(.*?)'/ism", $attributes, $matches); - if ($matches[1] != "") - $profile = $matches[1]; + $profile = ""; + preg_match("/profile='(.*?)'/ism", $attributes, $matches); + if ($matches[1] != "") + $profile = $matches[1]; - preg_match('/profile="(.*?)"/ism', $attributes, $matches); - if ($matches[1] != "") - $profile = $matches[1]; + preg_match('/profile="(.*?)"/ism', $attributes, $matches); + if ($matches[1] != "") + $profile = $matches[1]; - $ret= array(); + $ret= array(); - $ret["root_handle"] = preg_replace("=https?://(.*)/u/(.*)=ism", "$2@$1", $profile); - if (($ret["root_handle"] == $profile) OR ($ret["root_handle"] == "")) - return(false); + $ret["root_handle"] = preg_replace("=https?://(.*)/u/(.*)=ism", "$2@$1", $profile); + if (($ret["root_handle"] == $profile) OR ($ret["root_handle"] == "")) + return(false); - $link = ""; - preg_match("/link='(.*?)'/ism", $attributes, $matches); - if ($matches[1] != "") - $link = $matches[1]; + $link = ""; + preg_match("/link='(.*?)'/ism", $attributes, $matches); + if ($matches[1] != "") + $link = $matches[1]; - preg_match('/link="(.*?)"/ism', $attributes, $matches); - if ($matches[1] != "") - $link = $matches[1]; + preg_match('/link="(.*?)"/ism', $attributes, $matches); + if ($matches[1] != "") + $link = $matches[1]; - $ret["root_guid"] = preg_replace("=https?://(.*)/posts/(.*)=ism", "$2", $link); - if (($ret["root_guid"] == $link) OR ($ret["root_guid"] == "")) - return(false); + $ret["root_guid"] = preg_replace("=https?://(.*)/posts/(.*)=ism", "$2", $link); + if (($ret["root_guid"] == $link) OR ($ret["root_guid"] == "")) + return(false); - return($ret); + return($ret); } function diaspora_send_images($item,$owner,$contact,$images,$public_batch = false) { @@ -2227,18 +2242,18 @@ function diaspora_send_images($item,$owner,$contact,$images,$public_batch = fals $resource = str_replace('.jpg','',$image['file']); $resource = substr($resource,0,strpos($resource,'-')); - $r = q("select * from photo where `resource-id` = '%s' and `uid` = %d limit 1", + $r = q("select * from photo where `resource_id` = '%s' and `uid` = %d limit 1", dbesc($resource), intval($owner['uid']) ); - if(! count($r)) + if(! $r) continue; $public = (($r[0]['allow_cid'] || $r[0]['allow_gid'] || $r[0]['deny_cid'] || $r[0]['deny_gid']) ? 'false' : 'true' ); $msg = replace_macros($tpl,array( '$path' => xmlify($image['path']), '$filename' => xmlify($image['file']), '$msg_guid' => xmlify($image['guid']), - '$guid' => xmlify($r[0]['guid']), + '$guid' => xmlify($r[0]['resource_id']), '$handle' => xmlify($image['handle']), '$public' => xmlify($public), '$created_at' => xmlify(datetime_convert('UTC','UTC',$r[0]['created'],'Y-m-d H:i:s \U\T\C')) @@ -2246,7 +2261,7 @@ function diaspora_send_images($item,$owner,$contact,$images,$public_batch = fals logger('diaspora_send_photo: base message: ' . $msg, LOGGER_DATA); - $slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch))); + $slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['channel_prvkey'],$contact['xchan_pubkey'],$public_batch))); //$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)); diaspora_transmit($owner,$contact,$slap,$public_batch); @@ -2257,27 +2272,27 @@ function diaspora_send_images($item,$owner,$contact,$images,$public_batch = fals function diaspora_send_followup($item,$owner,$contact,$public_batch = false) { $a = get_app(); - $myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); -// $theiraddr = $contact['addr']; + $myaddr = $owner['channel_address'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); + $theiraddr = $contact['xchan_addr']; // Diaspora doesn't support threaded comments, but some // versions of Diaspora (i.e. Diaspora-pistos) support // likes on comments - if($item['verb'] === ACTIVITY_LIKE && $item['thr-parent']) { - $p = q("select guid, type, uri, `parent-uri` from item where uri = '%s' limit 1", - dbesc($item['thr-parent']) - ); + if($item['verb'] === ACTIVITY_LIKE && $item['thr_parent']) { + $p = q("select mid, parent_mid from item where mid = '%s' limit 1", + dbesc($item['thr_parent']) + ); } else { // The first item in the `item` table with the parent id is the parent. However, MySQL doesn't always // return the items ordered by `item`.`id`, in which case the wrong item is chosen as the parent. // The only item with `parent` and `id` as the parent id is the parent item. - $p = q("select guid, type, uri, `parent-uri` from item where parent = %d and id = %d limit 1", + $p = q("select * from item where parent = %d and id = %d limit 1", intval($item['parent']), intval($item['parent']) ); } - if(count($p)) + if($p) $parent = $p[0]; else return; @@ -2285,12 +2300,10 @@ function diaspora_send_followup($item,$owner,$contact,$public_batch = false) { if($item['verb'] === ACTIVITY_LIKE) { $tpl = get_markup_template('diaspora_like.tpl'); $like = true; - $target_type = ( $parent['uri'] === $parent['parent-uri'] ? 'Post' : 'Comment'); -// $target_type = (strpos($parent['type'], 'comment') ? 'Comment' : 'Post'); -// $positive = (($item['deleted']) ? 'false' : 'true'); + $target_type = ( $parent['mid'] === $parent['parent_mid'] ? 'Post' : 'Comment'); $positive = 'true'; - if(($item['deleted'])) + if(($item_['item_restrict'] & ITEM_DELETED)) logger('diaspora_send_followup: received deleted "like". Those should go to diaspora_send_retraction'); } else { @@ -2303,15 +2316,15 @@ function diaspora_send_followup($item,$owner,$contact,$public_batch = false) { // sign it if($like) - $signed_text = $item['guid'] . ';' . $target_type . ';' . $parent['guid'] . ';' . $positive . ';' . $myaddr; + $signed_text = $item['mid'] . ';' . $target_type . ';' . $parent['mid'] . ';' . $positive . ';' . $myaddr; else - $signed_text = $item['guid'] . ';' . $parent['guid'] . ';' . $text . ';' . $myaddr; + $signed_text = $item['mid'] . ';' . $parent['mid'] . ';' . $text . ';' . $myaddr; - $authorsig = base64_encode(rsa_sign($signed_text,$owner['uprvkey'],'sha256')); + $authorsig = base64_encode(rsa_sign($signed_text,$owner['channel_prvkey'],'sha256')); $msg = replace_macros($tpl,array( - '$guid' => xmlify($item['guid']), - '$parent_guid' => xmlify($parent['guid']), + '$guid' => xmlify($item['mid']), + '$parent_guid' => xmlify($parent['mid']), '$target_type' =>xmlify($target_type), '$authorsig' => xmlify($authorsig), '$body' => xmlify($text), @@ -2321,8 +2334,8 @@ function diaspora_send_followup($item,$owner,$contact,$public_batch = false) { logger('diaspora_followup: base message: ' . $msg, LOGGER_DATA); - $slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch))); - //$slap = 'xml=' . urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['uprvkey'],$contact['pubkey'],$public_batch)); + $slap = 'xml=' . urlencode(urlencode(diaspora_msg_build($msg,$owner,$contact,$owner['channel_prvkey'],$contact['xchan_pubkey'],$public_batch))); + return(diaspora_transmit($owner,$contact,$slap,$public_batch)); } @@ -2332,7 +2345,7 @@ function diaspora_send_relay($item,$owner,$contact,$public_batch = false) { $a = get_app(); - $myaddr = $owner['nickname'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); + $myaddr = $owner['channel_address'] . '@' . substr($a->get_baseurl(), strpos($a->get_baseurl(),'://') + 3); // $theiraddr = $contact['addr']; $body = $item['body']; @@ -2341,21 +2354,21 @@ function diaspora_send_relay($item,$owner,$contact,$public_batch = false) { // Diaspora doesn't support threaded comments, but some // versions of Diaspora (i.e. Diaspora-pistos) support // likes on comments - if($item['verb'] === ACTIVITY_LIKE && $item['thr-parent']) { - $p = q("select guid, type, uri, `parent-uri` from item where uri = '%s' limit 1", - dbesc($item['thr-parent']) - ); + if($item['verb'] === ACTIVITY_LIKE && $item['thr_parent']) { + $p = q("select * from item where mid = '%s' limit 1", + dbesc($item['thr_parent']) + ); } else { // The first item in the `item` table with the parent id is the parent. However, MySQL doesn't always // return the items ordered by `item`.`id`, in which case the wrong item is chosen as the parent. // The only item with `parent` and `id` as the parent id is the parent item. - $p = q("select guid, type, uri, `parent-uri` from item where parent = %d and id = %d limit 1", + $p = q("select * from item where parent = %d and id = %d limit 1", intval($item['parent']), intval($item['parent']) ); } - if(count($p)) + if($p) $parent = $p[0]; else return; @@ -2363,7 +2376,7 @@ function diaspora_send_relay($item,$owner,$contact,$public_batch = false) { $like = false; $relay_retract = false; $sql_sign_id = 'iid'; - if( $item['deleted']) { + if( $item['item_restrict'] & ITEM_DELETED) { $relay_retract = true; $target_type = ( ($item['verb'] === ACTIVITY_LIKE) ? 'Like' : 'Comment'); @@ -2374,8 +2387,8 @@ function diaspora_send_relay($item,$owner,$contact,$public_batch = false) { elseif($item['verb'] === ACTIVITY_LIKE) { $like = true; - $target_type = ( $parent['uri'] === $parent['parent-uri'] ? 'Post' : 'Comment'); -// $positive = (($item['deleted']) ? 'false' : 'true'); + $target_type = ( $parent['mid'] === $parent['parent_mid'] ? 'Post' : 'Comment'); +// $positive = (($item['item_restrict'] & ITEM_DELETED) ? 'false' : 'true'); $positive = 'true'; $tpl = get_markup_template('diaspora_like_relay.tpl'); @@ -2419,7 +2432,7 @@ function diaspora_send_relay($item,$owner,$contact,$public_batch = false) { * been done yet */ - $handle = diaspora_handle_from_contact($item['contact-id']); + $handle = diaspora_handle_from_contact($item['author_xchan']); if(! $handle) return; diff --git a/include/externals.php b/include/externals.php index a96bf7c97..8944524b7 100644 --- a/include/externals.php +++ b/include/externals.php @@ -41,7 +41,7 @@ function externals_run($argv, $argc){ $bl1 = get_config('system','blacklisted_sites'); if(is_array($bl1) && $bl1) { foreach($bl1 as $bl) { - if(strpos($url,$bl) !== false) { + if($bl && strpos($url,$bl) !== false) { $blacklisted = true; break; } diff --git a/include/identity.php b/include/identity.php index 9335673a0..8b742f53e 100644 --- a/include/identity.php +++ b/include/identity.php @@ -770,9 +770,26 @@ logger('online: ' . $profile['online']); $location = $pdesc = $gender = $marital = $homepage = $online = False; } - $firstname = ((strpos($profile['name'],' ')) - ? trim(substr($profile['name'],0,strpos($profile['name'],' '))) : $profile['name']); - $lastname = (($firstname === $profile['name']) ? '' : trim(substr($profile['name'],strlen($firstname)))); + $firstname = ((strpos($profile['channel_name'],' ')) + ? trim(substr($profile['channel_name'],0,strpos($profile['channel_name'],' '))) : $profile['channel_name']); + $lastname = (($firstname === $profile['channel_name']) ? '' : trim(substr($profile['channel_name'],strlen($firstname)))); + + if(get_config('system','diaspora_enabled')) { + $diaspora = array( + 'podloc' => z_root(), + 'searchable' => (($block) ? 'false' : 'true'), + 'nickname' => $profile['channel_address'], + 'fullname' => $profile['channel_name'], + 'firstname' => $firstname, + 'lastname' => $lastname, + 'photo300' => z_root() . '/photo/profile/300/' . $profile['uid'] . '.jpg', + 'photo100' => z_root() . '/photo/profile/100/' . $profile['uid'] . '.jpg', + 'photo50' => z_root() . '/photo/profile/50/' . $profile['uid'] . '.jpg', + ); + } + else + $diaspora = null; + $contact_block = contact_block(); @@ -802,6 +819,7 @@ logger('online: ' . $profile['online']); '$marital' => $marital, '$homepage' => $homepage, '$chanmenu' => $channel_menu, + '$diaspora' => $diaspora, '$contact_block' => $contact_block, )); diff --git a/include/items.php b/include/items.php index 30a685ed3..783c67752 100755 --- a/include/items.php +++ b/include/items.php @@ -1224,21 +1224,21 @@ function get_profile_elements($x) { -function get_atom_elements($feed,$item) { +function get_atom_elements($feed,$item,&$author) { $best_photo = array(); $res = array(); - $author = $item->get_author(); - if($author) { - $res['author_name'] = unxmlify($author->get_name()); - $res['author_link'] = unxmlify($author->get_link()); + $found_author = $item->get_author(); + if($found_author) { + $author['author_name'] = unxmlify($found_author->get_name()); + $author['author_link'] = unxmlify($found_author->get_link()); } else { - $res['author_name'] = unxmlify($feed->get_title()); - $res['author_link'] = unxmlify($feed->get_permalink()); + $author['author_name'] = unxmlify($feed->get_title()); + $author['author_link'] = unxmlify($feed->get_permalink()); } $res['mid'] = unxmlify($item->get_id()); @@ -1265,9 +1265,9 @@ function get_atom_elements($feed,$item) { if($rawauthor && $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']) { $base = $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']; foreach($base as $link) { - if(!x($res, 'author_photo') || !$res['author_photo']) { + if(!x($author, 'author_photo') || ! $author['author_photo']) { if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') - $res['author_photo'] = unxmlify($link['attribs']['']['href']); + $author['author_photo'] = unxmlify($link['attribs']['']['href']); } } } @@ -1279,10 +1279,10 @@ function get_atom_elements($feed,$item) { if($base && count($base)) { foreach($base as $link) { if($link['attribs']['']['rel'] === 'alternate' && (! $res['author_link'])) - $res['author_link'] = unxmlify($link['attribs']['']['href']); - if(!x($res, 'author_photo') || !$res['author_photo']) { + $author['author_link'] = unxmlify($link['attribs']['']['href']); + if(!x($author, 'author_photo') || ! $author['author_photo']) { if($link['attribs']['']['rel'] === 'avatar' || $link['attribs']['']['rel'] === 'photo') - $res['author_photo'] = unxmlify($link['attribs']['']['href']); + $author['author_photo'] = unxmlify($link['attribs']['']['href']); } } } @@ -1290,16 +1290,16 @@ function get_atom_elements($feed,$item) { // No photo/profile-link on the item - look at the feed level - if((! (x($res,'author_link'))) || (! (x($res,'author_photo')))) { + if((! (x($author,'author_link'))) || (! (x($author,'author_photo')))) { $rawauthor = $feed->get_feed_tags(SIMPLEPIE_NAMESPACE_ATOM_10,'author'); if($rawauthor && $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']) { $base = $rawauthor[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']; foreach($base as $link) { - if($link['attribs']['']['rel'] === 'alternate' && (! $res['author_link'])) - $res['author_link'] = unxmlify($link['attribs']['']['href']); - if(! $res['author_photo']) { + if($link['attribs']['']['rel'] === 'alternate' && (! $author['author_link'])) + $author['author_link'] = unxmlify($link['attribs']['']['href']); + if(! $author['author_photo']) { if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') - $res['author_photo'] = unxmlify($link['attribs']['']['href']); + $author['author_photo'] = unxmlify($link['attribs']['']['href']); } } } @@ -1312,10 +1312,10 @@ function get_atom_elements($feed,$item) { if($base && count($base)) { foreach($base as $link) { if($link['attribs']['']['rel'] === 'alternate' && (! $res['author_link'])) - $res['author_link'] = unxmlify($link['attribs']['']['href']); - if(! (x($res,'author_photo'))) { + $author['author_link'] = unxmlify($link['attribs']['']['href']); + if(! (x($author,'author_photo'))) { if($link['attribs']['']['rel'] === 'avatar' || $link['attribs']['']['rel'] === 'photo') - $res['author_photo'] = unxmlify($link['attribs']['']['href']); + $author['author_photo'] = unxmlify($link['attribs']['']['href']); } } } @@ -1340,6 +1340,12 @@ function get_atom_elements($feed,$item) { $res['body'] = str_replace(array(' ',"\t","\r","\n"), array('','','',''),$res['body']); // make sure nobody is trying to sneak some html tags by us $res['body'] = notags(base64url_decode($res['body'])); + + // We could probably turn these old Friendica bbcode bookmarks into bookmark tags but we'd have to + // create a term table item for them. For now just make sure they stay as links. + + $res['body'] = preg_replace('/\[bookmark(.*?)\](.*?)\[\/bookmark\]','[url$1]$2[/url]',$res['body']); + } @@ -1419,22 +1425,25 @@ function get_atom_elements($feed,$item) { $res['edited'] = datetime_convert(); $rawowner = $item->get_item_tags(NAMESPACE_DFRN, 'owner'); + if(! $rawowner) + $rawowner = $item->get_item_tags(NAMESPACE_ZOT,'owner'); + if($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']) - $res['owner_name'] = unxmlify($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']); + $author['owner_name'] = unxmlify($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['name'][0]['data']); elseif($rawowner[0]['child'][NAMESPACE_DFRN]['name'][0]['data']) - $res['owner_name'] = unxmlify($rawowner[0]['child'][NAMESPACE_DFRN]['name'][0]['data']); + $author['owner_name'] = unxmlify($rawowner[0]['child'][NAMESPACE_DFRN]['name'][0]['data']); if($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']) - $res['owner_link'] = unxmlify($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']); + $author['owner_link'] = unxmlify($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['uri'][0]['data']); elseif($rawowner[0]['child'][NAMESPACE_DFRN]['uri'][0]['data']) - $res['owner_link'] = unxmlify($rawowner[0]['child'][NAMESPACE_DFRN]['uri'][0]['data']); + $author['owner_link'] = unxmlify($rawowner[0]['child'][NAMESPACE_DFRN]['uri'][0]['data']); if($rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']) { $base = $rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']; foreach($base as $link) { - if(!x($res, 'owner_photo') || !$res['owner_photo']) { + if(!x($author, 'owner_photo') || ! $author['owner_photo']) { if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') - $res['owner_photo'] = unxmlify($link['attribs']['']['href']); + $author['owner_photo'] = unxmlify($link['attribs']['']['href']); } } } @@ -1579,39 +1588,11 @@ function get_atom_elements($feed,$item) { $res['target'] = $obj; } - // This is some experimental stuff. By now retweets are shown with "RT:" - // But: There is data so that the message could be shown similar to native retweets - // There is some better way to parse this array - but it didn't worked for me. - -/* - $child = $item->feed->data["child"][SIMPLEPIE_NAMESPACE_ATOM_10]["feed"][0]["child"][SIMPLEPIE_NAMESPACE_ATOM_10]["entry"][0]["child"]["http://activitystrea.ms/spec/1.0/"][object][0]["child"]; - if (is_array($child)) { - $message = $child["http://activitystrea.ms/spec/1.0/"]["object"][0]["child"][SIMPLEPIE_NAMESPACE_ATOM_10]["content"][0]["data"]; - $author = $child[SIMPLEPIE_NAMESPACE_ATOM_10]["author"][0]["child"][SIMPLEPIE_NAMESPACE_ATOM_10]; - $uri = $author["uri"][0]["data"]; - $name = $author["name"][0]["data"]; - $avatar = @array_shift($author["link"][2]["attribs"]); - $avatar = $avatar["href"]; - - if (($name != "") and ($uri != "") and ($avatar != "") and ($message != "")) { - $res["owner-name"] = $res["author-name"]; - $res["owner-link"] = $res["author-link"]; - $res["owner-avatar"] = $res["author-avatar"]; - - $res["author-name"] = $name; - $res["author-link"] = $uri; - $res["author-avatar"] = $avatar; - - $res["body"] = html2bbcode($message); - } - } - -*/ - $arr = array('feed' => $feed, 'item' => $item, 'result' => $res); call_hooks('parse_atom', $arr); - logger('get_atom_elements: ' . print_r($res,true)); + logger('get_atom_elements: author: ' . print_r($author,true),LOGGER_DATA); + logger('get_atom_elements: ' . print_r($res,true),LOGGER_DATA); return $res; } @@ -1621,9 +1602,6 @@ function encode_rel_links($links) { if(! ((is_array($links)) && (count($links)))) return $o; -//fixme - return ''; - foreach($links as $link) { $o .= '<link '; if($link['attribs']['']['rel']) @@ -1686,8 +1664,8 @@ function item_store($arr,$allow_exec = false) { } - $arr['title'] = ((x($arr,'title')) ? trim($arr['title']) : ''); - $arr['body'] = ((x($arr,'body')) ? trim($arr['body']) : ''); + $arr['title'] = ((array_key_exists('title',$arr) && strlen($arr['title'])) ? trim($arr['title']) : ''); + $arr['body'] = ((array_key_exists('body',$arr) && strlen($arr['body'])) ? trim($arr['body']) : ''); $arr['allow_cid'] = ((x($arr,'allow_cid')) ? trim($arr['allow_cid']) : ''); $arr['allow_gid'] = ((x($arr,'allow_gid')) ? trim($arr['allow_gid']) : ''); @@ -2158,7 +2136,6 @@ function item_store_update($arr,$allow_exec = false) { $arr['commented'] = $orig[0]['commented']; $arr['received'] = datetime_convert(); $arr['changed'] = datetime_convert(); - $arr['title'] = ((x($arr,'title')) ? notags(trim($arr['title'])) : ''); $arr['location'] = ((x($arr,'location')) ? notags(trim($arr['location'])) : $orig[0]['location']); $arr['coord'] = ((x($arr,'coord')) ? notags(trim($arr['coord'])) : $orig[0]['coord']); $arr['verb'] = ((x($arr,'verb')) ? notags(trim($arr['verb'])) : $orig[0]['verb']); @@ -2174,7 +2151,8 @@ function item_store_update($arr,$allow_exec = false) { $arr['deny_gid'] = ((array_key_exists('deny_gid',$arr)) ? trim($arr['deny_gid']) : $orig[0]['deny_gid']); $arr['item_private'] = ((array_key_exists('item_private',$arr)) ? intval($arr['item_private']) : $orig[0]['item_private']); - $arr['body'] = ((x($arr,'body')) ? trim($arr['body']) : ''); + $arr['title'] = ((array_key_exists('title',$arr) && strlen($arr['title'])) ? trim($arr['title']) : ''); + $arr['body'] = ((array_key_exists('body',$arr) && strlen($arr['body'])) ? trim($arr['body']) : ''); $arr['attach'] = ((x($arr,'attach')) ? notags(trim($arr['attach'])) : $orig[0]['attach']); $arr['app'] = ((x($arr,'app')) ? notags(trim($arr['app'])) : $orig[0]['app']); // $arr['item_restrict'] = ((x($arr,'item_restrict')) ? intval($arr['item_restrict']) : $orig[0]['item_restrict'] ); @@ -2374,8 +2352,9 @@ function tag_deliver($uid,$item_id) { $item = $i[0]; - if(($item['source_xchan']) && ($item['item_flags'] & ITEM_UPLINK) && ($item['item_flags'] & ITEM_THREAD_TOP) && ($item['edited'] != $item['created'])) { - // this is an update to a post which was already processed by us and has a second delivery chain + if(($item['source_xchan']) && ($item['item_flags'] & ITEM_UPLINK) + && ($item['item_flags'] & ITEM_THREAD_TOP) && ($item['edited'] != $item['created'])) { + // this is an update (edit) to a post which was already processed by us and has a second delivery chain // Just start the second delivery chain to deliver the updated post proc_run('php','include/notifier.php','tgroup',$item['id']); return; @@ -2472,78 +2451,14 @@ function tag_deliver($uid,$item_id) { // This might be a followup (e.g. comment) by the original post author to a tagged forum // If so setup a second delivery chain - $r = null; - if( ! ($item['item_flags'] & ITEM_THREAD_TOP)) { $x = q("select * from item where id = parent and parent = %d and uid = %d limit 1", intval($item['parent']), intval($uid) ); - if(($x) && ($x[0]['item_flags'] & ITEM_UPLINK)) { - - logger('tag_deliver: creating second delivery chain for comment to tagged post.'); - - // now change this copy of the post to a forum head message and deliver to all the tgroup members - // also reset all the privacy bits to the forum default permissions - - $private = (($u[0]['channel_allow_cid'] || $u[0]['channel_allow_gid'] || $u[0]['channel_deny_cid'] || $u[0]['channel_deny_gid']) ? 1 : 0); - - $new_public_policy = map_scope($u[0]['channel_r_stream'],true); - - if((! $private) && $new_public_policy) - $private = 1; - - $flag_bits = $item['item_flags'] | ITEM_WALL|ITEM_ORIGIN; - - // maintain the original source, which will be the original item owner and was stored in source_xchan - // when we created the delivery fork - - $r = q("update item set source_xchan = '%s' where id = %d limit 1", - dbesc($x[0]['source_xchan']), - intval($item_id) - ); - - $title = $item['title']; - $body = $item['body']; - - if($private) { - if(!($flag_bits & ITEM_OBSCURED)) { - $key = get_config('system','pubkey'); - $flag_bits = $flag_bits|ITEM_OBSCURED; - $title = json_encode(aes_encapsulate($title,$key)); - $body = json_encode(aes_encapsulate($body,$key)); - } - } - else { - if($flag_bits & ITEM_OBSCURED) { - $key = get_config('system','prvkey'); - $flag_bits = $flag_bits ^ ITEM_OBSCURED; - $title = json_encode(aes_unencapsulate($title,$key)); - $body = json_encode(aes_unencapsulate($body,$key)); - } - } - - $r = q("update item set item_flags = %d, owner_xchan = '%s', allow_cid = '%s', allow_gid = '%s', - deny_cid = '%s', deny_gid = '%s', item_private = %d, public_policy = '%s', comment_policy = '%s', title = '%s', body = '%s' where id = %d limit 1", - intval($flag_bits), - dbesc($u[0]['channel_hash']), - dbesc($u[0]['channel_allow_cid']), - dbesc($u[0]['channel_allow_gid']), - dbesc($u[0]['channel_deny_cid']), - dbesc($u[0]['channel_deny_gid']), - intval($private), - dbesc($new_public_policy), - dbesc(map_scope($u[0]['channel_w_comment'])), - dbesc($title), - dbesc($body), - intval($item_id) - ); - if($r) - proc_run('php','include/notifier.php','tgroup',$item_id); - else - logger('tag_deliver: failed to update item'); + start_delivery_chain($u[0],$item,$item_id,$x[0]); } } @@ -2577,8 +2492,6 @@ function tag_deliver($uid,$item_id) { intval($item_id) ); - - // At this point we've determined that the person receiving this post was mentioned in it or it is a union. // Now let's check if this mention was inside a reshare so we don't spam a forum // If it's private we may have to unobscure it momentarily so that we can parse it. @@ -2650,81 +2563,20 @@ function tag_deliver($uid,$item_id) { return; } - // tgroup delivery - setup a second delivery chain // prevent delivery looping - only proceed // if the message originated elsewhere and is a top-level post - if(($item['item_flags'] & ITEM_WALL) || ($item['item_flags'] & ITEM_ORIGIN) || (!($item['item_flags'] & ITEM_THREAD_TOP)) || ($item['id'] != $item['parent'])) { + if(($item['item_flags'] & ITEM_WALL) + || ($item['item_flags'] & ITEM_ORIGIN) + || (!($item['item_flags'] & ITEM_THREAD_TOP)) + || ($item['id'] != $item['parent'])) { logger('tag_deliver: item was local or a comment. rejected.'); return; } - /** - * At this point we're committed to setting up a second delivery chain. We just have to mangle some bits first. - */ - logger('tag_deliver: creating second delivery chain.'); - - // now change this copy of the post to a forum head message and deliver to all the tgroup members - // also reset all the privacy bits to the forum default permissions - - $private = (($u[0]['channel_allow_cid'] || $u[0]['channel_allow_gid'] || $u[0]['channel_deny_cid'] || $u[0]['channel_deny_gid']) ? 1 : 0); - - $new_public_policy = map_scope($u[0]['channel_r_stream'],true); - - if((! $private) && $new_public_policy) - $private = 1; - - $flag_bits = $item['item_flags'] | ITEM_WALL|ITEM_ORIGIN|ITEM_UPLINK; - - // preserve the source - - $r = q("update item set source_xchan = owner_xchan where id = %d limit 1", - intval($item_id) - ); - - // make sure encryption matches the new scope - - $title = $item['title']; - $body = $item['body']; - - if($private) { - if(!($flag_bits & ITEM_OBSCURED)) { - $key = get_config('system','pubkey'); - $flag_bits = $flag_bits|ITEM_OBSCURED; - $title = json_encode(aes_encapsulate($title,$key)); - $body = json_encode(aes_encapsulate($body,$key)); - } - } - else { - if($flag_bits & ITEM_OBSCURED) { - $key = get_config('system','prvkey'); - $flag_bits = $flag_bits ^ ITEM_OBSCURED; - $title = json_encode(aes_unencapsulate($title,$key)); - $body = json_encode(aes_unencapsulate($body,$key)); - } - } - - $r = q("update item set item_flags = %d, owner_xchan = '%s', allow_cid = '%s', allow_gid = '%s', - deny_cid = '%s', deny_gid = '%s', item_private = %d, public_policy = '%s', comment_policy = '%s', title = '%s', body = '%s' where id = %d limit 1", - intval($flag_bits), - dbesc($u[0]['channel_hash']), - dbesc($u[0]['channel_allow_cid']), - dbesc($u[0]['channel_allow_gid']), - dbesc($u[0]['channel_deny_cid']), - dbesc($u[0]['channel_deny_gid']), - intval($private), - dbesc($new_public_policy), - dbesc(map_scope($u[0]['channel_w_comment'])), - dbesc($title), - dbesc($body), - intval($item_id) - ); - if($r) - proc_run('php','include/notifier.php','tgroup',$item_id); - else - logger('tag_deliver: failed to update item'); + start_delivery_chain($u[0],$item,$item_id,null); } @@ -2808,6 +2660,90 @@ function tgroup_check($uid,$item) { } +/** + * Sourced and tag-delivered posts are re-targetted for delivery to the connections of the channel + * receiving the post. This starts the second delivery chain, by resetting permissions and ensuring + * that ITEM_UPLINK is set on the parent post, and storing the current owner_xchan as the source_xchan. + * We'll become the new owner. If called without $parent, this *is* the parent post. + */ + +function start_delivery_chain($channel,$item,$item_id,$parent) { + + + // Change this copy of the post to a forum head message and deliver to all the tgroup members + // also reset all the privacy bits to the forum default permissions + + $private = (($channel['channel_allow_cid'] || $channel['channel_allow_gid'] + || $channel['channel_deny_cid'] || $channel['channel_deny_gid']) ? 1 : 0); + + $new_public_policy = map_scope($channel['channel_r_stream'],true); + + if((! $private) && $new_public_policy) + $private = 1; + + $flag_bits = $item['item_flags'] | ITEM_WALL|ITEM_ORIGIN; + + // maintain the original source, which will be the original item owner and was stored in source_xchan + // when we created the delivery fork + + if($parent) { + $r = q("update item set source_xchan = '%s' where id = %d limit 1", + dbesc($parent['source_xchan']), + intval($item_id) + ); + } + else { + $flag_bits = $flag_bits | ITEM_UPLINK; + $r = q("update item set source_xchan = owner_xchan where id = %d limit 1", + intval($item_id) + ); + } + + $title = $item['title']; + $body = $item['body']; + + if($private) { + if(!($flag_bits & ITEM_OBSCURED)) { + $key = get_config('system','pubkey'); + $flag_bits = $flag_bits|ITEM_OBSCURED; + $title = json_encode(aes_encapsulate($title,$key)); + $body = json_encode(aes_encapsulate($body,$key)); + } + } + else { + if($flag_bits & ITEM_OBSCURED) { + $key = get_config('system','prvkey'); + $flag_bits = $flag_bits ^ ITEM_OBSCURED; + $title = json_encode(aes_unencapsulate($title,$key)); + $body = json_encode(aes_unencapsulate($body,$key)); + } + } + + $r = q("update item set item_flags = %d, owner_xchan = '%s', allow_cid = '%s', allow_gid = '%s', + deny_cid = '%s', deny_gid = '%s', item_private = %d, public_policy = '%s', comment_policy = '%s', title = '%s', body = '%s' where id = %d limit 1", + intval($flag_bits), + dbesc($channel['channel_hash']), + dbesc($channel['channel_allow_cid']), + dbesc($channel['channel_allow_gid']), + dbesc($channel['channel_deny_cid']), + dbesc($channel['channel_deny_gid']), + intval($private), + dbesc($new_public_policy), + dbesc(map_scope($channel['channel_w_comment'])), + dbesc($title), + dbesc($body), + intval($item_id) + ); + + if($r) + proc_run('php','include/notifier.php','tgroup',$item_id); + else + logger('start_delivery_chain: failed to update item'); + + return; +} + + /** * @function check_item_source($uid,$item) @@ -3014,15 +2950,8 @@ function consume_feed($xml,$importer,&$contact,$pass = 0) { return; } - // Want to see this work as a content source for the matrix? - // Read this: https://github.com/friendica/red/wiki/Service_Federation - $feed = new SimplePie(); $feed->set_raw_data($xml); - if($datedir) - $feed->enable_order_by_date(true); - else - $feed->enable_order_by_date(false); $feed->init(); if($feed->error()) @@ -3032,7 +2961,6 @@ function consume_feed($xml,$importer,&$contact,$pass = 0) { // Check at the feed level for updated contact name and/or photo - // process any deleted entries $del_entries = $feed->get_feed_tags(NAMESPACE_TOMB, 'deleted-entry'); @@ -3052,41 +2980,18 @@ function consume_feed($xml,$importer,&$contact,$pass = 0) { if($deleted && is_array($contact)) { -/* - $r = q("SELECT `item`.*, `contact`.`self` FROM `item` left join `contact` on `item`.`contact-id` = `contact`.`id` - WHERE `mid` = '%s' AND `item`.`uid` = %d AND `contact-id` = %d AND NOT `item`.`file` LIKE '%%[%%' LIMIT 1", + $r = q("SELECT * from item where mid = '%s' and author_xchan = '%s' and uid = %d limit 1", dbesc($mid), - intval($importer['channel_id']), - intval($contact['id']) + dbesc($contact['xchan_hash']), + intval($importer['channel_id']) ); -*/ - if(count($r)) { + + if($r) { $item = $r[0]; - if(! $item['deleted']) + if(! ($item['item_restrict'] & ITEM_DELETED)) { logger('consume_feed: deleting item ' . $item['id'] . ' mid=' . $item['mid'], LOGGER_DEBUG); - - if($item['mid'] == $item['parent_mid']) { - $r = q("UPDATE `item` SET item_restrict = (item_restrict | %d), `edited` = '%s', `changed` = '%s', - `body` = '', `title` = '' - WHERE `parent_mid` = '%s' AND `uid` = %d", - intval(ITEM_DELETED), - dbesc($when), - dbesc(datetime_convert()), - dbesc($item['mid']), - intval($importer['channel_id']) - ); - } - else { - $r = q("UPDATE `item` SET item_restrict = ( item_restrict | %d ), `edited` = '%s', `changed` = '%s', - `body` = '', `title` = '' - WHERE `mid` = '%s' AND `uid` = %d LIMIT 1", - intval(ITEM_DELETED), - dbesc($when), - dbesc(datetime_convert()), - dbesc($mid), - intval($importer['channel_id']) - ); + drop_item($item['id'],false); } } } @@ -3097,21 +3002,16 @@ function consume_feed($xml,$importer,&$contact,$pass = 0) { if($feed->get_item_quantity()) { - logger('consume_feed: feed item count = ' . $feed->get_item_quantity()); - - // in inverse date order - if ($datedir) - $items = array_reverse($feed->get_items()); - else - $items = $feed->get_items(); + logger('consume_feed: feed item count = ' . $feed->get_item_quantity(), LOGGER_DEBUG); + $items = $feed->get_items(); foreach($items as $item) { $is_reply = false; $item_id = $item->get_id(); -logger('consume_feed: processing ' . $item_id); + logger('consume_feed: processing ' . $item_id, LOGGER_DEBUG); $rawthread = $item->get_item_tags( NAMESPACE_THREAD,'in-reply-to'); if(isset($rawthread[0]['attribs']['']['ref'])) { @@ -3128,23 +3028,17 @@ logger('consume_feed: processing ' . $item_id); // Have we seen it? If not, import it. $item_id = $item->get_id(); - $datarray = get_atom_elements($feed,$item); - -/* - if((! x($datarray,'author-name')) && ($contact['network'] != NETWORK_DFRN)) - $datarray['author-name'] = $contact['name']; - if((! x($datarray,'author-link')) && ($contact['network'] != NETWORK_DFRN)) - $datarray['author-link'] = $contact['url']; - if((! x($datarray,'author-avatar')) && ($contact['network'] != NETWORK_DFRN)) - $datarray['author-avatar'] = $contact['thumb']; -*/ - if((! x($datarray,'author_name')) || (! x($datarray,'author_link'))) { - logger('consume_feed: no author information! ' . print_r($datarray,true)); - continue; - } + $author = array(); + $datarray = get_atom_elements($feed,$item,$author); + if(! x($author,'author_name')) + $author['author_name'] = $contact['xchan_name']; + if(! x($author,'author_link')) + $author['author_link'] = $contact['xchan_url']; + if(! x($author,'author_photo')) + $author['author_photo'] = $contact['xchan_photo_m']; - $r = q("SELECT `uid`, `edited`, `body` FROM `item` WHERE `mid` = '%s' AND `uid` = %d LIMIT 1", + $r = q("SELECT edited FROM item WHERE mid = '%s' AND uid = %d LIMIT 1", dbesc($item_id), intval($importer['channel_id']) ); @@ -3152,70 +3046,28 @@ logger('consume_feed: processing ' . $item_id); // Update content if 'updated' changes if($r) { - if((x($datarray,'edited') !== false) && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { + if((x($datarray,'edited') !== false) + && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { // do not accept (ignore) an earlier edit than one we currently have. if(datetime_convert('UTC','UTC',$datarray['edited']) < $r[0]['edited']) continue; - $r = q("UPDATE `item` SET `title` = '%s', `body` = '%s', `edited` = '%s' WHERE `mid` = '%s' AND `uid` = %d LIMIT 1", - dbesc($datarray['title']), - dbesc($datarray['body']), - dbesc(datetime_convert('UTC','UTC',$datarray['edited'])), - dbesc($item_id), - intval($importer['channel_id']) - ); + update_feed_item($importer['channel_id'],$datarray); } - continue; } - $datarray['parent_mid'] = $parent_mid; $datarray['uid'] = $importer['channel_id']; -// $datarray['contact-id'] = $contact['id']; - - if((activity_match($datarray['verb'],ACTIVITY_LIKE)) || (activity_match($datarray['verb'],ACTIVITY_DISLIKE))) { - $datarray['type'] = 'activity'; - $datarray['gravity'] = GRAVITY_LIKE; - // only one like or dislike per person - $r = q("select id from item where uid = %d and `contact-id` = %d and verb ='%s' and deleted = 0 and (`parent_mid` = '%s' OR `thr_parent` = '%s') limit 1", - intval($datarray['uid']), - intval($datarray['contact-id']), - dbesc($datarray['verb']), - dbesc($parent_mid), - dbesc($parent_mid) - ); - if($r && count($r)) - continue; - } - if(($datarray['verb'] === ACTIVITY_TAG) && ($datarray['obj_type'] === ACTIVITY_OBJ_TAGTERM)) { - $xo = parse_xml_string($datarray['object'],false); - $xt = parse_xml_string($datarray['target'],false); +//FIXME + $datarray['author_xchan'] = $contact['xchan_hash']; - if($xt->type == ACTIVITY_OBJ_NOTE) { - $r = q("select * from item where `mid` = '%s' AND `uid` = %d limit 1", - dbesc($xt->id), - intval($importer['channel_id']) - ); - if(! count($r)) - continue; + // FIXME pull out the author and owner - // extract tag, if not duplicate, add to parent item - if($xo->id && $xo->content) { - $newtag = '#[zrl=' . $xo->id . ']'. $xo->content . '[/zrl]'; - if(! (stristr($r[0]['tag'],$newtag))) { - q("UPDATE item SET tag = '%s' WHERE id = %d LIMIT 1", - dbesc($r[0]['tag'] . (strlen($r[0]['tag']) ? ',' : '') . $newtag), - intval($r[0]['id']) - ); - } - } - } - } -logger('consume_feed: ' . print_r($datarray,true)); + logger('consume_feed: ' . print_r($datarray,true),LOGGER_DATA); // $xx = item_store($datarray); $r = $xx['item_id']; @@ -3227,47 +3079,25 @@ logger('consume_feed: ' . print_r($datarray,true)); // Head post of a conversation. Have we seen it? If not, import it. $item_id = $item->get_id(); - - $datarray = get_atom_elements($feed,$item); + $author = array(); + $datarray = get_atom_elements($feed,$item,$author); if(is_array($contact)) { - if((! x($datarray,'author-name')) && ($contact['network'] != NETWORK_DFRN)) - $datarray['author-name'] = $contact['name']; - if((! x($datarray,'author-link')) && ($contact['network'] != NETWORK_DFRN)) - $datarray['author-link'] = $contact['url']; - if((! x($datarray,'author-avatar')) && ($contact['network'] != NETWORK_DFRN)) - $datarray['author-avatar'] = $contact['thumb']; + if(! x($author,'author_name')) + $author['author_name'] = $contact['xchan_name']; + if(! x($author,'author_link')) + $author['author_link'] = $contact['xchan_url']; + if(! x($author,'author_photo')) + $author['author_photo'] = $contact['xchan_photo_m']; } - if((! x($datarray,'author-name')) || (! x($datarray,'author-link'))) { - logger('consume_feed: no author information! ' . print_r($datarray,true)); + if((! x($author,'author_name')) || (! x($author,'author_link'))) { + logger('consume_feed: no author information! ' . print_r($author,true)); continue; } - // special handling for events - - if((x($datarray,'obj_type')) && ($datarray['obj_type'] === ACTIVITY_OBJ_EVENT)) { - $ev = bbtoevent($datarray['body']); - if(x($ev,'desc') && x($ev,'start')) { - $ev['uid'] = $importer['channel_id']; - $ev['mid'] = $item_id; - $ev['edited'] = $datarray['edited']; - $ev['private'] = $datarray['private']; - - if(is_array($contact)) - $ev['cid'] = $contact['id']; - $r = q("SELECT * FROM `event` WHERE `mid` = '%s' AND `uid` = %d LIMIT 1", - dbesc($item_id), - intval($importer['channel_id']) - ); - if(count($r)) - $ev['id'] = $r[0]['id']; -// $xyz = event_store($ev); - continue; - } - } - $r = q("SELECT `uid`, `edited`, `body` FROM `item` WHERE `mid` = '%s' AND `uid` = %d LIMIT 1", + $r = q("SELECT edited FROM item WHERE mid = '%s' AND uid = %d LIMIT 1", dbesc($item_id), intval($importer['channel_id']) ); @@ -3275,79 +3105,33 @@ logger('consume_feed: ' . print_r($datarray,true)); // Update content if 'updated' changes if($r) { - if((x($datarray,'edited') !== false) && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { + if((x($datarray,'edited') !== false) + && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { // do not accept (ignore) an earlier edit than one we currently have. if(datetime_convert('UTC','UTC',$datarray['edited']) < $r[0]['edited']) continue; - $r = q("UPDATE `item` SET `title` = '%s', `body` = '%s', `edited` = '%s' WHERE `mid` = '%s' AND `uid` = %d LIMIT 1", - dbesc($datarray['title']), - dbesc($datarray['body']), - dbesc(datetime_convert('UTC','UTC',$datarray['edited'])), - dbesc($item_id), - intval($importer['channel_id']) - ); + update_feed_item($importer['channel_id'],$datarray); } continue; } - if(activity_match($datarray['verb'],ACTIVITY_FOLLOW)) { - logger('consume-feed: New follower'); - new_follower($importer,$contact,$datarray,$item); - return; - } - if(activity_match($datarray['verb'],ACTIVITY_UNFOLLOW)) { - lose_follower($importer,$contact,$datarray,$item); - return; - } - - if(activity_match($datarray['verb'],ACTIVITY_REQ_FRIEND)) { - logger('consume-feed: New friend request'); - new_follower($importer,$contact,$datarray,$item,true); - return; - } - if(activity_match($datarray['verb'],ACTIVITY_UNFRIEND)) { - lose_sharer($importer,$contact,$datarray,$item); - return; - } - - -// if(! is_array($contact)) -// return; - - - // This is my contact on another system, but it's really me. - // Turn this into a wall post. - - if($contact['remote_self']) { - $datarray['wall'] = 1; - } $datarray['parent_mid'] = $item_id; $datarray['uid'] = $importer['channel_id']; - $datarray['contact-id'] = $contact['id']; +//FIXME + $datarray['author_xchan'] = $contact['author_xchan']; - if(! link_compare($datarray['owner-link'],$contact['url'])) { - // The item owner info is not our contact. It's OK and is to be expected if this is a tgroup delivery, - // but otherwise there's a possible data mixup on the sender's system. - // the tgroup delivery code called from item_store will correct it if it's a forum, - // but we're going to unconditionally correct it here so that the post will always be owned by our contact. + if(! link_compare($author['owner_link'],$contact['xchan_url'])) { logger('consume_feed: Correcting item owner.', LOGGER_DEBUG); - $datarray['owner-name'] = $contact['name']; - $datarray['owner-link'] = $contact['url']; - $datarray['owner-avatar'] = $contact['thumb']; + $author['owner-name'] = $contact['name']; + $author['owner-link'] = $contact['url']; + $author['owner-avatar'] = $contact['thumb']; } - // We've allowed "followers" to reach this point so we can decide if they are - // posting an @-tag delivery, which followers are allowed to do for certain - // page types. Now that we've parsed the post, let's check if it is legit. Otherwise ignore it. - - if(($contact['rel'] == CONTACT_IS_FOLLOWER) && (! tgroup_check($importer['channel_id'],$datarray))) - continue; - -logger('consume_feed: ' . print_r($datarray,true)); + logger('consume_feed: ' . print_r($datarray,true),LOGGER_DATA); // $xx = item_store($datarray); $r = $xx['item_id']; @@ -3360,6 +3144,13 @@ logger('consume_feed: ' . print_r($datarray,true)); } +function update_feed_item($uid,$datarray) { + + logger('update_feed_item: ' . $uid . ' ' . print_r($datarray,true), LOGGER_DATA); + + +} + function handle_feed($uid,$abook_id,$url) { diff --git a/include/network.php b/include/network.php index 1a974a681..614049299 100644 --- a/include/network.php +++ b/include/network.php @@ -965,4 +965,168 @@ logger('fetch_xrd_links: ' . $url); logger('fetch_xrd_links: ' . print_r($links,true), LOGGER_DATA); return $links; -}
\ No newline at end of file +} + + +function scrape_vcard($url) { + + $a = get_app(); + + $ret = array(); + + logger('scrape_vcard: url=' . $url); + + $x = z_fetch_url($url); + if(! $x['success']) + return $ret; + + $s = $x['body']; + + if(! $s) + return $ret; + + $headers = $x['header']; + $lines = explode("\n",$headers); + if(count($lines)) { + foreach($lines as $line) { + // don't try and run feeds through the html5 parser + if(stristr($line,'content-type:') && ((stristr($line,'application/atom+xml')) || (stristr($line,'application/rss+xml')))) + return ret; + } + } + + try { + $dom = HTML5_Parser::parse($s); + } catch (DOMException $e) { + logger('scrape_vcard: parse error: ' . $e); + } + + if(! $dom) + return $ret; + + // Pull out hCard profile elements + + $largest_photo = 0; + + $items = $dom->getElementsByTagName('*'); + foreach($items as $item) { + if(attribute_contains($item->getAttribute('class'), 'vcard')) { + $level2 = $item->getElementsByTagName('*'); + foreach($level2 as $x) { + if(attribute_contains($x->getAttribute('class'),'fn')) + $ret['fn'] = $x->textContent; + if((attribute_contains($x->getAttribute('class'),'photo')) + || (attribute_contains($x->getAttribute('class'),'avatar'))) { + $size = intval($x->getAttribute('width')); + if(($size > $largest_photo) || (! $largest_photo)) { + $ret['photo'] = $x->getAttribute('src'); + $largest_photo = $size; + } + } + if((attribute_contains($x->getAttribute('class'),'nickname')) + || (attribute_contains($x->getAttribute('class'),'uid'))) { + $ret['nick'] = $x->textContent; + } + } + } + } + + return $ret; +} + + + +function scrape_feed($url) { + + $a = get_app(); + + $ret = array(); + $level = 0; + $x = z_fetch_url($url,false,$level,array('novalidate' => true)); + + if(! $x['success']) + return $ret; + + $headers = $x['header']; + $code = $x['return_code']; + $s = $x['body']; + + logger('scrape_feed: returns: ' . $code . ' headers=' . $headers, LOGGER_DEBUG); + + if(! $s) { + logger('scrape_feed: no data returned for ' . $url); + return $ret; + } + + + $lines = explode("\n",$headers); + if(count($lines)) { + foreach($lines as $line) { + if(stristr($line,'content-type:')) { + if(stristr($line,'application/atom+xml') || stristr($s,'<feed')) { + $ret['feed_atom'] = $url; + return $ret; + } + if(stristr($line,'application/rss+xml') || stristr($s,'<rss')) { + $ret['feed_rss'] = $url; + return $ret; + } + } + } + // perhaps an RSS version 1 feed with a generic or incorrect content-type? + if(stristr($s,'</item>')) { + $ret['feed_rss'] = $url; + return $ret; + } + } + + try { + $dom = HTML5_Parser::parse($s); + } catch (DOMException $e) { + logger('scrape_feed: parse error: ' . $e); + } + + if(! $dom) { + logger('scrape_feed: failed to parse.'); + return $ret; + } + + + $head = $dom->getElementsByTagName('base'); + if($head) { + foreach($head as $head0) { + $basename = $head0->getAttribute('href'); + break; + } + } + if(! $basename) + $basename = implode('/', array_slice(explode('/',$url),0,3)) . '/'; + + $items = $dom->getElementsByTagName('link'); + + // get Atom/RSS link elements, take the first one of either. + + if($items) { + foreach($items as $item) { + $x = $item->getAttribute('rel'); + if(($x === 'alternate') && ($item->getAttribute('type') === 'application/atom+xml')) { + if(! x($ret,'feed_atom')) + $ret['feed_atom'] = $item->getAttribute('href'); + } + if(($x === 'alternate') && ($item->getAttribute('type') === 'application/rss+xml')) { + if(! x($ret,'feed_rss')) + $ret['feed_rss'] = $item->getAttribute('href'); + } + } + } + + // Drupal and perhaps others only provide relative URL's. Turn them into absolute. + + if(x($ret,'feed_atom') && (! strstr($ret['feed_atom'],'://'))) + $ret['feed_atom'] = $basename . $ret['feed_atom']; + if(x($ret,'feed_rss') && (! strstr($ret['feed_rss'],'://'))) + $ret['feed_rss'] = $basename . $ret['feed_rss']; + + return $ret; +} + diff --git a/include/text.php b/include/text.php index 680e6fe95..d3d8b84a6 100755 --- a/include/text.php +++ b/include/text.php @@ -1002,9 +1002,9 @@ function smilies($s, $sample = false) { ':facepalm', ':like', ':dislike', + 'red#matrix', 'red#', - 'r#', - 'red#matrix' + 'r#' ); $icons = array( @@ -1040,9 +1040,9 @@ function smilies($s, $sample = false) { '<img class="smiley" src="' . $a->get_baseurl() . '/images/smiley-facepalm.gif" alt=":facepalm" />', '<img class="smiley" src="' . $a->get_baseurl() . '/images/like.gif" alt=":like" />', '<img class="smiley" src="' . $a->get_baseurl() . '/images/dislike.gif" alt=":dislike" />', + '<a href="http://getzot.com"><strong>red<img class="smiley" src="' . $a->get_baseurl() . '/images/rm-16.png" alt="red#matrix" />matrix</strong></a>', '<a href="http://getzot.com"><strong>red<img class="smiley" src="' . $a->get_baseurl() . '/images/rm-16.png" alt="red#" />matrix</strong></a>', - '<a href="http://getzot.com"><strong>red<img class="smiley" src="' . $a->get_baseurl() . '/images/rm-16.png" alt="r#" />matrix</strong></a>', - '<a href="http://getzot.com"><strong>red<img class="smiley" src="' . $a->get_baseurl() . '/images/rm-16.png" alt="red#matrix" />matrix</strong></a>' + '<a href="http://getzot.com"><strong>red<img class="smiley" src="' . $a->get_baseurl() . '/images/rm-16.png" alt="r#" />matrix</strong></a>' ); diff --git a/include/zot.php b/include/zot.php index 8b0efe09d..41d0bc1eb 100644 --- a/include/zot.php +++ b/include/zot.php @@ -507,6 +507,22 @@ function zot_refresh($them,$channel = null, $force = false) { function zot_gethub($arr) { if($arr['guid'] && $arr['guid_sig'] && $arr['url'] && $arr['url_sig']) { + + $blacklisted = false; + $bl1 = get_config('system','blacklisted_sites'); + if(is_array($bl1) && $bl1) { + foreach($bl1 as $bl) { + if($bl && strpos($arr['url'],$bl) !== false) { + $blacklisted = true; + break; + } + } + } + if($blacklisted) { + logger('zot_gethub: blacklisted site: ' . $arr['url']); + return null; + } + $r = q("select * from hubloc where hubloc_guid = '%s' and hubloc_guid_sig = '%s' and hubloc_url = '%s' and hubloc_url_sig = '%s' diff --git a/mod/admin.php b/mod/admin.php index 14657bd1a..5df63636a 100644 --- a/mod/admin.php +++ b/mod/admin.php @@ -265,50 +265,10 @@ function admin_page_site_post(&$a){ $delivery_interval = ((x($_POST,'delivery_interval'))? intval(trim($_POST['delivery_interval'])) : 0); $poll_interval = ((x($_POST,'poll_interval'))? intval(trim($_POST['poll_interval'])) : 0); $maxloadavg = ((x($_POST,'maxloadavg'))? intval(trim($_POST['maxloadavg'])) : 50); -// $ssl_policy = ((x($_POST,'ssl_policy')) ? intval($_POST['ssl_policy']) : 0); -/* - if($ssl_policy != intval(get_config('system','ssl_policy'))) { - if($ssl_policy == SSL_POLICY_FULL) { - q("update `contact` set - `url` = replace(`url` , 'http:' , 'https:'), - `photo` = replace(`photo` , 'http:' , 'https:'), - `thumb` = replace(`thumb` , 'http:' , 'https:'), - `micro` = replace(`micro` , 'http:' , 'https:'), - `request` = replace(`request`, 'http:' , 'https:'), - `notify` = replace(`notify` , 'http:' , 'https:'), - `poll` = replace(`poll` , 'http:' , 'https:'), - `confirm` = replace(`confirm`, 'http:' , 'https:'), - `poco` = replace(`poco` , 'http:' , 'https:') - where `self` = 1" - ); - q("update `profile` set - `photo` = replace(`photo` , 'http:' , 'https:'), - `thumb` = replace(`thumb` , 'http:' , 'https:') - where 1 " - ); - } - elseif($ssl_policy == SSL_POLICY_SELFSIGN) { - q("update `contact` set - `url` = replace(`url` , 'https:' , 'http:'), - `photo` = replace(`photo` , 'https:' , 'http:'), - `thumb` = replace(`thumb` , 'https:' , 'http:'), - `micro` = replace(`micro` , 'https:' , 'http:'), - `request` = replace(`request`, 'https:' , 'http:'), - `notify` = replace(`notify` , 'https:' , 'http:'), - `poll` = replace(`poll` , 'https:' , 'http:'), - `confirm` = replace(`confirm`, 'https:' , 'http:'), - `poco` = replace(`poco` , 'https:' , 'http:') - where `self` = 1" - ); - q("update `profile` set - `photo` = replace(`photo` , 'https:' , 'http:'), - `thumb` = replace(`thumb` , 'https:' , 'http:') - where 1 " - ); - } - } -*/ -// set_config('system','ssl_policy',$ssl_policy); + $feed_contacts = ((x($_POST,'feed_contacts')) ? intval($_POST['feed_contacts']) : 0); + + + set_config('system','feed_contacts',$feed_contacts); set_config('system','delivery_interval',$delivery_interval); set_config('system','poll_interval',$poll_interval); set_config('system','maxloadavg',$maxloadavg); @@ -464,7 +424,7 @@ function admin_page_site(&$a) { '$theme_mobile' => array('theme_mobile', t("Mobile system theme"), get_config('system','mobile_theme'), t("Theme for mobile devices"), $theme_choices_mobile), '$theme_accessibility' => array('theme_accessibility', t("Accessibility system theme"), get_config('system','accessibility_theme'), t("Accessibility theme"), $theme_choices_accessibility), '$site_channel' => array('site_channel', t("Channel to use for this website's static pages"), get_config('system','site_channel'), t("Site Channel")), -// '$ssl_policy' => array('ssl_policy', t("SSL link policy"), (string) intval(get_config('system','ssl_policy')), t("Determines whether generated links should be forced to use SSL"), $ssl_choices), + '$feed_contacts' => array('feed_contacts', t('Allow Feeds as Connections'),get_config('system','feed_contacts'),t('(Heavy system resource usage)')), '$maximagesize' => array('maximagesize', t("Maximum image size"), intval(get_config('system','maximagesize')), t("Maximum size in bytes of uploaded images. Default is 0, which means no limits.")), '$register_policy' => array('register_policy', t("Does this site allow new member registration?"), get_config('system','register_policy'), "", $register_choices), '$access_policy' => array('access_policy', t("Which best describes the types of account offered by this hub?"), get_config('system','access_policy'), "This is displayed on the public server site list.", $access_choices), diff --git a/mod/dirsearch.php b/mod/dirsearch.php index b72d303b7..96e576a19 100644 --- a/mod/dirsearch.php +++ b/mod/dirsearch.php @@ -154,7 +154,7 @@ function dirsearch_content(&$a) { else { $qlimit = " LIMIT " . intval($startrec) . " , " . intval($perpage); if($return_total) { - $r = q("SELECT COUNT(xchan_hash) AS `total` FROM xchan left join xprof on xchan_hash = xprof_hash where $logic $sql_extra and not ( xchan_flags & %d) and not ( xchan_flags & %d ) and not ( xchan_flags & %d ) $safesql ", + $r = q("SELECT COUNT(xchan_hash) AS `total` FROM xchan left join xprof on xchan_hash = xprof_hash where $logic $sql_extra and xchan_network = 'zot' and not ( xchan_flags & %d) and not ( xchan_flags & %d ) and not ( xchan_flags & %d ) $safesql ", intval(XCHAN_FLAGS_HIDDEN), intval(XCHAN_FLAGS_ORPHAN), intval(XCHAN_FLAGS_DELETED) @@ -199,7 +199,7 @@ function dirsearch_content(&$a) { json_return_and_die($spkt); } else { - $r = q("SELECT xchan.*, xprof.* from xchan left join xprof on xchan_hash = xprof_hash where ( $logic $sql_extra ) and not ( xchan_flags & %d ) and not ( xchan_flags & %d ) and not ( xchan_flags & %d ) $safesql $order $qlimit ", + $r = q("SELECT xchan.*, xprof.* from xchan left join xprof on xchan_hash = xprof_hash where ( $logic $sql_extra ) and xchan_network = 'zot' and not ( xchan_flags & %d ) and not ( xchan_flags & %d ) and not ( xchan_flags & %d ) $safesql $order $qlimit ", intval(XCHAN_FLAGS_HIDDEN), intval(XCHAN_FLAGS_ORPHAN), intval(XCHAN_FLAGS_DELETED) diff --git a/mod/frphotos.php b/mod/frphotos.php deleted file mode 100644 index 8d6197fa3..000000000 --- a/mod/frphotos.php +++ /dev/null @@ -1,87 +0,0 @@ -<?php - - - -function frphotos_init(&$a) { - - if(! local_user()) - return; - - if(intval(get_pconfig(local_user(),'frphotos','complete'))) - return; - - $channel = $a->get_channel(); - - $fr_server = $_REQUEST['fr_server']; - $fr_username = $_REQUEST['fr_username']; - $fr_password = $_REQUEST['fr_password']; - - $cookies = 'store/[data]/frphoto_cookie_' . $channel['channel_address']; - - if($fr_server && $fr_username && $fr_password) { - - $ch = curl_init($fr_server . '/api/friendica/photos/list'); - - curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); - curl_setopt ($ch, CURLOPT_COOKIEFILE, $cookies); - curl_setopt ($ch, CURLOPT_COOKIEJAR, $cookies); - curl_setopt($ch, CURLOPT_HTTPAUTH, CURLAUTH_BASIC); - curl_setopt($ch, CURLOPT_USERPWD, $fr_username . ':' . $fr_password); - curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); - curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); - curl_setopt($ch, CURLOPT_USERAGENT, 'RedMatrix'); - - $output = curl_exec($ch); - curl_close($ch); - - $j = json_decode($output,true); - -// echo print_r($j,true); - - $total = 0; - if(count($j)) { - foreach($j as $jj) { - - $r = q("select uid from photo where resource_id = '%s' and uid = %d limit 1", - dbesc($jj), - intval($channel['channel_id']) - ); - if($r) - continue; - - $total ++; - proc_run('php','util/frphotohelper.php',$jj, $channel['channel_address'], urlencode($fr_server)); - sleep(3); - } - } - if($total) { - set_pconfig(local_user(),'frphotos','complete','1'); - } - @unlink($cookies); - goaway(z_root() . '/photos/' . $channel['channel_address']); - } -} - - -function frphotos_content(&$a) { - - if(! local_user()) { - notice( t('Permission denied') . EOL); - return; - } - - if(intval(get_pconfig(local_user(),'frphotos','complete'))) { - info('Friendica photos have already been imported into this channel.'); - return; - } - - $o = replace_macros(get_markup_template('frphotos.tpl'),array( - '$header' => t('Friendica Photo Album Import'), - '$desc' => t('This will import all your Friendica photo albums to this Red channel.'), - '$fr_server' => array('fr_server', t('Friendica Server base URL'),'',''), - '$fr_username' => array('fr_username', t('Friendica Login Username'),'',''), - '$fr_password' => array('fr_password', t('Friendica Login Password'),'',''), - '$submit' => t('Submit'), - )); - return $o; -} diff --git a/mod/item.php b/mod/item.php index 92dc3e7c6..27691eb4f 100644 --- a/mod/item.php +++ b/mod/item.php @@ -790,7 +790,6 @@ function item_post(&$a) { else $post_id = 0; - $post = item_store($datarray,$execflag); $post_id = $post['item_id']; diff --git a/mod/profiles.php b/mod/profiles.php index b938e836b..d6df09e9a 100644 --- a/mod/profiles.php +++ b/mod/profiles.php @@ -568,6 +568,24 @@ function profiles_content(&$a) { '$no_selected' => (($r[0]['hide_friends'] == 0) ? " checked=\"checked\" " : "") )); + $q = q("select * from profdef where true"); + if($q) { + $extra_fields = array(); + + foreach($q as $qq) { + $mine = q("select v from profext where k = '%s' and hash = '%s' and channel_id = %d limit 1", + dbesc($qq['field_name']), + dbesc($r[0]['profile_guid']), + intval(local_user()) + ); + + if(array_key_exists($qq['field_name'],$fields)) { + $extra_fields[] = array($qq['field_name'],$qq['field_desc'],(($mine) ? $mine[0]['v'] : ''), $qq['field_help']); + } + } + } + +logger('extra_fields: ' . print_r($extra_fields,true)); $f = get_config('system','birthday_input_format'); if(! $f) @@ -674,6 +692,7 @@ function profiles_content(&$a) { '$education' => $r[0]['education'], '$contact' => $r[0]['contact'], '$channels' => $r[0]['channels'], + '$extra_fields' => $extra_fields, )); $arr = array('profile' => $r[0], 'entry' => $o); diff --git a/mod/receive.php b/mod/receive.php index c5a2dc4e0..4071b169b 100644 --- a/mod/receive.php +++ b/mod/receive.php @@ -4,8 +4,6 @@ * Diaspora endpoint */ - -//require_once('include/salmon.php'); require_once('include/crypto.php'); require_once('include/diaspora.php'); @@ -31,8 +29,11 @@ function receive_post(&$a) { $guid = argv(2); - $r = q("SELECT * FROM channel left join account on account_id = channel_account_id WHERE channel_guid = '%s' AND account_flags = 0 LIMIT 1", - dbesc($guid) + // Diaspora sites *may* provide a truncated guid. + + $r = q("SELECT * FROM channel left join xchan on channel_hash = xchan_hash WHERE channel_guid like '%s' AND NOT (channel_pageflags & %d ) LIMIT 1", + dbesc($guid . '%'), + intval(PAGE_REMOVED) ); if(! $r) http_status_exit(500); diff --git a/mod/xrd.php b/mod/xrd.php index 4d6a530e4..d059bec9b 100644 --- a/mod/xrd.php +++ b/mod/xrd.php @@ -22,7 +22,20 @@ function xrd_init(&$a) { if(! $r) killme(); -// $salmon_key = salmon_key($r[0]['pubkey']); + if(get_config('system','diaspora_enabled')) { + $tpl = get_markup_template('xrd_diaspora.tpl'); + $dspr = replace_macros($tpl,array( + '$baseurl' => $a->get_baseurl(), + '$dspr_guid' => $r[0]['channel_guid'], + '$dspr_key' => base64_encode(pemtorsa($r[0]['channel_pubkey'])) + )); + } + else + $dspr = ''; + + + + $salmon_key = salmon_key($r[0]['channel_pubkey']); header('Access-Control-Allow-Origin: *'); header("Content-type: text/xml"); @@ -34,15 +47,15 @@ function xrd_init(&$a) { '$nick' => $r[0]['channel_address'], '$accturi' => $uri, '$profile_url' => $a->get_baseurl() . '/channel/' . $r[0]['channel_address'], -// '$hcard_url' => $a->get_baseurl() . '/hcard/' . $r[0]['channel_address'], + '$hcard_url' => $a->get_baseurl() . '/hcard/' . $r[0]['channel_address'], '$atom' => $a->get_baseurl() . '/feed/' . $r[0]['channel_address'], '$zot_post' => $a->get_baseurl() . '/post/' . $r[0]['channel_address'], '$poco_url' => $a->get_baseurl() . '/poco/' . $r[0]['channel_address'], '$photo' => $a->get_baseurl() . '/photo/profile/l/' . $r[0]['channel_id'], -// '$dspr' => $dspr, + '$dspr' => $dspr, // '$salmon' => $a->get_baseurl() . '/salmon/' . $r[0]['channel_address'], // '$salmen' => $a->get_baseurl() . '/salmon/' . $r[0]['channel_address'] . '/mention', -// '$modexp' => 'data:application/magic-public-key,' . $salmon_key, + '$modexp' => 'data:application/magic-public-key,' . $salmon_key, // '$bigkey' => salmon_key($r[0]['pubkey']) )); diff --git a/util/frphotohelper.php b/util/frphotohelper.php deleted file mode 100644 index 484e7fcaf..000000000 --- a/util/frphotohelper.php +++ /dev/null @@ -1,75 +0,0 @@ -<?php - -require_once('include/cli_startup.php'); - -cli_startup(); - -$a = get_app(); - - -$photo_id = $argv[1]; -$channel_address = $argv[2]; -$fr_server = urldecode($argv[3]); -require_once('include/photos.php'); - -$cookies = 'store/[data]/frphoto_cookie_' . $channel_address; - - $c = q("select * from channel left join xchan on channel_hash = xchan_hash where channel_address = '%s' limit 1", - dbesc($channel_address) - ); - if(! $c) { - logger('frphotohelper: channel not found'); - killme(); - } - $channel = $c[0]; - - - $ch = curl_init($fr_server . '/api/friendica/photo?f=&photo_id=' . $photo_id); - - curl_setopt($ch, CURLOPT_RETURNTRANSFER, 1); - curl_setopt ($ch, CURLOPT_COOKIEFILE, $cookies); - curl_setopt ($ch, CURLOPT_COOKIEJAR, $cookies); - curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); - curl_setopt($ch, CURLOPT_FOLLOWLOCATION, true); - curl_setopt($ch, CURLOPT_USERAGENT, 'RedMatrix'); - - $output = curl_exec($ch); - curl_close($ch); - - $j = json_decode($output,true); - -// logger('frphotohelper: ' . print_r($j,true)); - - $args = array(); - $args['data'] = base64_decode($j['data']); - $args['filename'] = $j['filename']; - $args['resource_id'] = $j['resource-id']; - $args['scale'] = $j['scale']; - $args['album'] = $j['album']; - $args['not_visible'] = 1; - $args['created'] = $j['created']; - $args['edited'] = $j['edited']; - $args['title'] = $j['title']; - $args['description'] = $j['desc']; - - if($j['allow_cid'] || $j['allow_gid'] || $j['deny_cid'] || $j['deny_gid']) - $args['contact_allow'] = $channel['channel_hash']; - - $args['type'] = $j['type']; - - - - $r = q("select * from photo where resource_id = '%s' and uid = %d limit 1", - dbesc($args['resource_id']), - intval($channel['channel_id']) - ); - if($r) { - killme(); - } - - - $ret = photo_upload($channel,$channel,$args); - logger('photo_import: ' . print_r($ret,true)); - - killme(); - diff --git a/version.inc b/version.inc index 6ca87b875..8936c7bc8 100644 --- a/version.inc +++ b/version.inc @@ -1 +1 @@ -2014-08-19.772 +2014-08-21.774 diff --git a/view/tpl/admin_site.tpl b/view/tpl/admin_site.tpl index c6c15cec4..2a7742a3e 100755 --- a/view/tpl/admin_site.tpl +++ b/view/tpl/admin_site.tpl @@ -65,6 +65,7 @@ <h3>{{$corporate}}</h3> {{include file="field_checkbox.tpl" field=$block_public}} + {{include file="field_checkbox.tpl" field=$feed_contacts}} {{include file="field_checkbox.tpl" field=$force_publish}} {{include file="field_checkbox.tpl" field=$disable_discover_tab}} diff --git a/view/tpl/diaspora_vcard.tpl b/view/tpl/diaspora_vcard.tpl new file mode 100644 index 000000000..9d234a398 --- /dev/null +++ b/view/tpl/diaspora_vcard.tpl @@ -0,0 +1,57 @@ +<div style="display:none;"> + <dl class='entity_nickname'> + <dt>Nickname</dt> + <dd> + <a class="nickname url uid" href="{{$diaspora.podloc}}/" rel="me">{{$diaspora.nickname}}</a> + </dd> + </dl> + <dl class='entity_fn'> + <dt>Full name</dt> + <dd> + <span class='fn'>{{$diaspora.fullname}}</span> + </dd> + </dl> + + <dl class='entity_given_name'> + <dt>First name</dt> + <dd> + <span class='given_name'>{{$diaspora.firstname}}</span> + </dd> + </dl> + <dl class='entity_family_name'> + <dt>Family name</dt> + <dd> + <span class='family_name'>{{$diaspora.lastname}}</span> + </dd> + </dl> + <dl class="entity_url"> + <dt>URL</dt> + <dd> + <a class="url" href="{{$diaspora.podloc}}/" id="pod_location" rel="me">{{$diaspora.podloc}}/</a> + </dd> + </dl> + <dl class="entity_photo"> + <dt>Photo</dt> + <dd> + <img class="photo avatar" height="300" width="300" src="{{$diaspora.photo300}}"> + </dd> + </dl> + <dl class="entity_photo_medium"> + <dt>Photo</dt> + <dd> + <img class="photo avatar" height="100" width="100" src="{{$diaspora.photo100}}"> + </dd> + </dl> + <dl class="entity_photo_small"> + <dt>Photo</dt> + <dd> + <img class="photo avatar" height="50" width="50" src="{{$diaspora.photo50}}"> + </dd> + </dl> + <dl class="entity_searchable"> + <dt>Searchable</dt> + <dd> + <span class="searchable">{{$diaspora.searchable}}</span> + </dd> + </dl> +</div> diff --git a/view/tpl/field_acheckbox.tpl b/view/tpl/field_acheckbox.tpl index 342491ded..89de170b7 100755 --- a/view/tpl/field_acheckbox.tpl +++ b/view/tpl/field_acheckbox.tpl @@ -6,7 +6,7 @@ <input type="checkbox" name='them_{{$field.0}}' id='them_id_{{$field.0}}' value="1" disabled="disabled" {{if $field.2}}checked="checked"{{/if}} /> </td> <td class="abook-me"> - <input type="checkbox" name='{{$field.0}}' id='me_id_{{$field.0}}' value="{{$field.4}}" {{if $field.3}}checked="checked"{{/if}} /> + <input type="checkbox" name='{{$field.0}}' class='abook-edit-me' id='me_id_{{$field.0}}' value="{{$field.4}}" {{if $field.3}}checked="checked"{{/if}} /> </td> <td> {{if $field.5}}<span class="permission-inherited">{{$inherited}}</span> {{/if}} diff --git a/view/tpl/frphotos.tpl b/view/tpl/frphotos.tpl deleted file mode 100644 index b8e978825..000000000 --- a/view/tpl/frphotos.tpl +++ /dev/null @@ -1,13 +0,0 @@ -<h3>{{$header}}</h3> - -<p class="descriptive-text">{{$desc}}</p> - -<form action="frphotos" method="post" autocomplete="off" > - -{{include file="field_input.tpl" field=$fr_server}} -{{include file="field_input.tpl" field=$fr_username}} -{{include file="field_password.tpl" field=$fr_password}} - -<input type="submit" name="submit" value="{{$submit}}" /> -</form> - diff --git a/view/tpl/profile_edit.tpl b/view/tpl/profile_edit.tpl index 0e902e9e2..b453b1cfa 100755 --- a/view/tpl/profile_edit.tpl +++ b/view/tpl/profile_edit.tpl @@ -9,12 +9,12 @@ <div id="profile-edit-links"> <span class="btn btn-default"><a href="profile_photo" id="profile-photo_upload-link" title="{{$profpic}}">{{$profpic}}</a></span> <span class="btn btn-default"><a href="profile/{{$profile_id}}/view" id="profile-edit-view-link" title="{{$viewprof}}">{{$viewprof}}</a></span> -{{if ! $default}}<span class="btn btn-default"><a href="profperm/{{$profile_id}}" id="profile-edit-view-link" title="{{$editvis}}">{{$editvis}}</a></span>{{/if}} +{{if ! $is_default}}<span class="btn btn-default"><a href="profperm/{{$profile_id}}" id="profile-edit-view-link" title="{{$editvis}}">{{$editvis}}</a></span>{{/if}} {{if $profile_clone_link}}<span class="btn btn-default"><a href="{{$profile_clone_link}}" id="profile-edit-clone-link" title="{{$cr_prof}}">{{$cl_prof}}</a></span>{{/if}} {{if $exportable}}<br /><span class="btn btn-default"><a href="profiles/export/{{$profile_id}}" target="_blank">{{$lbl_export}}</a></span> <span class="btn btn-default profile-import"><b>{{$lbl_import}}</b> <input type="file" name="userfile" class="profile-import" ></span> {{/if}} -{{if ! $default}}<span class="btn btn-danger"><a href="{{$profile_drop_link}}" id="profile-edit-drop-link" title="{{$del_prof}}" onclick="return confirmDelete();" {{$disabled}} >{{$del_prof}}</a></span>{{/if}} +{{if ! $is_default}}<span class="btn btn-danger"><a href="{{$profile_drop_link}}" id="profile-edit-drop-link" title="{{$del_prof}}" onclick="return confirmDelete();" {{$disabled}} >{{$del_prof}}</a></span>{{/if}} </div> @@ -349,6 +349,11 @@ <div id="education-jot-end"></div> {{/if}} +{{if $extra_fields}} +{{foreach $extra_fields as $field }} +{{include file="field_input.tpl" field=$field}} +{{/foreach}} +{{/if}} <div class="profile-edit-submit-wrapper" > <input type="submit" name="submit" class="profile-edit-submit-button" value="{{$submit}}" /> diff --git a/view/tpl/profile_vcard.tpl b/view/tpl/profile_vcard.tpl index a653dca7d..7dff8fdeb 100755 --- a/view/tpl/profile_vcard.tpl +++ b/view/tpl/profile_vcard.tpl @@ -43,6 +43,9 @@ {{if $homepage}}<dl class="homepage"><dt class="homepage-label">{{$homepage}}</dt><dd class="homepage-url"><a href="{{$profile.homepage}}" >{{$profile.homepage}}</a></dd></dl>{{/if}} + {{if $diaspora}} + {{include file="diaspora_vcard.tpl"}} + {{/if}} {{if $connect}} <a href="{{$connect_url}}" class="rconnect"><i class="icon-plus connect-icon"></i> {{$connect}}</a> diff --git a/view/tpl/xrd_diaspora.tpl b/view/tpl/xrd_diaspora.tpl new file mode 100644 index 000000000..143980bcc --- /dev/null +++ b/view/tpl/xrd_diaspora.tpl @@ -0,0 +1,8 @@ +{{* + * AUTOMATICALLY GENERATED TEMPLATE + * DO NOT EDIT THIS FILE, CHANGES WILL BE OVERWRITTEN + * + *}} + <Link rel="http://joindiaspora.com/seed_location" type="text/html" href="{{$baseurl}}/" /> + <Link rel="http://joindiaspora.com/guid" type="text/html" href="{{$dspr_guid}}" /> + <Link rel="diaspora-public-key" type="RSA" href="{{$dspr_key}}" /> diff --git a/view/tpl/xrd_person.tpl b/view/tpl/xrd_person.tpl index 20d438dd5..631ed3f18 100755 --- a/view/tpl/xrd_person.tpl +++ b/view/tpl/xrd_person.tpl @@ -14,5 +14,13 @@ <Link rel="http://webfinger.net/rel/avatar" type="image/jpeg" href="{{$photo}}" /> - + <Link rel="http://microformats.org/profile/hcard" + type="text/html" + href="{{$hcard_url}}" /> + + <Link rel="magic-public-key" + href="{{$modexp}}" /> + + {{$dspr}} + </XRD> |