X-Git-Url: https://git.mxchange.org/?a=blobdiff_plain;f=include%2Fitems.php;h=250d023cec1b2687a630dda4d0da7815b34b89fc;hb=c462ed9fc50e2c2a60e8cb01314a7d5fa498b412;hp=b32861c42821d9f5d6677635f2785011e293e456;hpb=53efeb8d1ff2a8232baa968b2f060d79f23aa9c6;p=friendica.git diff --git a/include/items.php b/include/items.php old mode 100644 new mode 100755 index b32861c428..250d023cec --- a/include/items.php +++ b/include/items.php @@ -118,7 +118,7 @@ function get_feed_for(&$a, $dfrn_id, $owner_nick, $last_update, $direction = 0) `sign`.`signed_text`, `sign`.`signature`, `sign`.`signer` FROM `item` LEFT JOIN `contact` ON `contact`.`id` = `item`.`contact-id` LEFT JOIN `sign` ON `sign`.`iid` = `item`.`id` - WHERE `item`.`uid` = %d AND `item`.`visible` = 1 AND `item`.`parent` != 0 + WHERE `item`.`uid` = %d AND `item`.`visible` = 1 and `item`.`moderated` = 0 AND `item`.`parent` != 0 AND `item`.`wall` = 1 AND `contact`.`blocked` = 0 AND `contact`.`pending` = 0 AND ( `item`.`edited` > '%s' OR `item`.`changed` > '%s' ) $sql_extra @@ -143,7 +143,7 @@ function get_feed_for(&$a, $dfrn_id, $owner_nick, $last_update, $direction = 0) $salmon = feed_salmonlinks($owner_nick); $atom .= replace_macros($feed_template, array( - '$version' => xmlify(FRIENDIKA_VERSION), + '$version' => xmlify(FRIENDICA_VERSION), '$feed_id' => xmlify($a->get_baseurl() . '/profile/' . $owner_nick), '$feed_title' => xmlify($owner['name']), '$feed_updated' => xmlify(datetime_convert('UTC', 'UTC', 'now' , ATOM_TIME)) , @@ -295,6 +295,11 @@ function get_atom_elements($feed,$item) { $res['body'] = unxmlify($item->get_content()); $res['plink'] = unxmlify($item->get_link(0)); + if($res['plink']) + $base_url = implode('/', array_slice(explode('/',$res['plink']),0,3)); + else + $base_url = ''; + // look for a photo. We should check media size and find the best one, // but for now let's just find any author photo @@ -303,7 +308,7 @@ 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(! $res['author-avatar']) { + if(!x($res, 'author-avatar') || !$res['author-avatar']) { if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') $res['author-avatar'] = unxmlify($link['attribs']['']['href']); } @@ -318,7 +323,7 @@ function get_atom_elements($feed,$item) { foreach($base as $link) { if($link['attribs']['']['rel'] === 'alternate' && (! $res['author-link'])) $res['author-link'] = unxmlify($link['attribs']['']['href']); - if(! $res['author-avatar']) { + if(!x($res, 'author-avatar') || !$res['author-avatar']) { if($link['attribs']['']['rel'] === 'avatar' || $link['attribs']['']['rel'] === 'photo') $res['author-avatar'] = unxmlify($link['attribs']['']['href']); } @@ -414,11 +419,9 @@ function get_atom_elements($feed,$item) { if((strpos($res['body'],'<') !== false) || (strpos($res['body'],'>') !== false)) { - $res['body'] = preg_replace('#]+>.+?' . 'http://www.youtube.com/((?:v|cp)/[A-Za-z0-9\-_=]+).+?#s', - '[youtube]$1[/youtube]', $res['body']); + $res['body'] = reltoabs($res['body'],$base_url); - $res['body'] = preg_replace('#].+?' . 'http://www.youtube.com/embed/([A-Za-z0-9\-_=]+).+?#s', - '[youtube]$1[/youtube]', $res['body']); + $res['body'] = html2bb_video($res['body']); $res['body'] = oembed_html2bbcode($res['body']); @@ -500,7 +503,7 @@ function get_atom_elements($feed,$item) { $base = $rawowner[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['link']; foreach($base as $link) { - if(! $res['owner-avatar']) { + if(!x($res, 'owner-avatar') || !$res['owner-avatar']) { if($link['attribs']['']['rel'] === 'photo' || $link['attribs']['']['rel'] === 'avatar') $res['owner-avatar'] = unxmlify($link['attribs']['']['href']); } @@ -586,12 +589,7 @@ function get_atom_elements($feed,$item) { $res['object'] .= '' . xmlify($body) . '' . "\n"; if((strpos($body,'<') !== false) || (strpos($body,'>') !== false)) { - $body = preg_replace('#]+>.+?' . 'http://www.youtube.com/((?:v|cp)/[A-Za-z0-9\-_=]+).+?#s', - '[youtube]$1[/youtube]', $body); - - $res['body'] = preg_replace('#].+?' . 'http://www.youtube.com/embed/([A-Za-z0-9\-_=]+).+?#s', - '[youtube]$1[/youtube]', $res['body']); - + $body = html2bb_video($body); $config = HTMLPurifier_Config::createDefault(); $config->set('Cache.DefinitionImpl', null); @@ -626,14 +624,10 @@ function get_atom_elements($feed,$item) { if(! $body) $body = $rawobj[0]['child'][SIMPLEPIE_NAMESPACE_ATOM_10]['summary'][0]['data']; // preserve a copy of the original body content in case we later need to parse out any microformat information, e.g. events - $res['object'] .= '' . xmlify($body) . '' . "\n"; + $res['target'] .= '' . xmlify($body) . '' . "\n"; if((strpos($body,'<') !== false) || (strpos($body,'>') !== false)) { - $body = preg_replace('#]+>.+?' . 'http://www.youtube.com/((?:v|cp)/[A-Za-z0-9\-_=]+).+?#s', - '[youtube]$1[/youtube]', $body); - - $res['body'] = preg_replace('#].+?' . 'http://www.youtube.com/embed/([A-Za-z0-9\-_=]+).+?#s', - '[youtube]$1[/youtube]', $res['body']); + $body = html2bb_video($body); $config = HTMLPurifier_Config::createDefault(); $config->set('Cache.DefinitionImpl', null); @@ -690,7 +684,7 @@ function item_store($arr,$force_parent = false) { if($arr['gravity']) $arr['gravity'] = intval($arr['gravity']); - elseif($arr['parent-uri'] == $arr['uri']) + elseif($arr['parent-uri'] === $arr['uri']) $arr['gravity'] = 0; elseif(activity_match($arr['verb'],ACTIVITY_POST)) $arr['gravity'] = 6; @@ -743,6 +737,7 @@ function item_store($arr,$force_parent = false) { $arr['tag'] = ((x($arr,'tag')) ? notags(trim($arr['tag'])) : ''); $arr['attach'] = ((x($arr,'attach')) ? notags(trim($arr['attach'])) : ''); $arr['app'] = ((x($arr,'app')) ? notags(trim($arr['app'])) : ''); + $arr['origin'] = ((x($arr,'origin')) ? intval($arr['origin']) : 0 ); $arr['guid'] = ((x($arr,'guid')) ? notags(trim($arr['guid'])) : get_guid()); if($arr['parent-uri'] === $arr['uri']) { @@ -757,7 +752,7 @@ function item_store($arr,$force_parent = false) { // find the parent and snarf the item id and ACL's // and anything else we need to inherit - $r = q("SELECT * FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + $r = q("SELECT * FROM `item` WHERE `uri` = '%s' AND `uid` = %d ORDER BY `id` ASC LIMIT 1", dbesc($arr['parent-uri']), intval($arr['uid']) ); @@ -771,7 +766,8 @@ function item_store($arr,$force_parent = false) { if($r[0]['uri'] != $r[0]['parent-uri']) { $arr['thr-parent'] = $arr['parent-uri']; $arr['parent-uri'] = $r[0]['parent-uri']; - $z = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `parent-uri` = '%s' AND `uid` = %d LIMIT 1", + $z = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `parent-uri` = '%s' AND `uid` = %d + ORDER BY `id` ASC LIMIT 1", dbesc($r[0]['parent-uri']), dbesc($r[0]['parent-uri']), intval($arr['uid']) @@ -809,7 +805,7 @@ function item_store($arr,$force_parent = false) { $r = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", dbesc($arr['uri']), - dbesc($arr['uid']) + intval($arr['uid']) ); if($r && count($r)) { logger('item-store: duplicate item ignored. ' . print_r($arr,true)); @@ -818,6 +814,11 @@ function item_store($arr,$force_parent = false) { call_hooks('post_remote',$arr); + if(x($arr,'cancel')) { + logger('item_store: post cancelled by plugin.'); + return 0; + } + dbesc_array($arr); logger('item_store: ' . print_r($arr,true), LOGGER_DATA); @@ -830,18 +831,10 @@ function item_store($arr,$force_parent = false) { // find the item we just created - $r = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + $r = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `uid` = %d ORDER BY `id` ASC ", $arr['uri'], // already dbesc'd intval($arr['uid']) ); - if(! count($r)) { - // This is not good, but perhaps we encountered a rare race/cache condition, so back off and try again. - sleep(3); - $r = q("SELECT `id` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", - $arr['uri'], // already dbesc'd - intval($arr['uid']) - ); - } if(count($r)) { $current_post = $r[0]['id']; @@ -851,6 +844,14 @@ function item_store($arr,$force_parent = false) { logger('item_store: could not locate created item'); return 0; } + if(count($r) > 1) { + logger('item_store: duplicated post occurred. Removing duplicates.'); + q("DELETE FROM `item` WHERE `uri` = '%s' AND `uid` = %d AND `id` != %d ", + $arr['uri'], + intval($arr['uid']), + intval($current_post) + ); + } if((! $parent_id) || ($arr['parent-uri'] === $arr['uri'])) $parent_id = $current_post; @@ -904,6 +905,8 @@ function item_store($arr,$force_parent = false) { ); } + tag_deliver($arr['uid'],$current_post); + return $current_post; } @@ -920,12 +923,111 @@ function get_item_contact($item,$contacts) { } +function tag_deliver($uid,$item_id) { + + // look for mention tags and setup a second delivery chain for forum/community posts if appropriate + + $a = get_app(); + + $mention = false; + + $u = q("select uid, nickname, language, username, email, `page-flags`, `notify-flags` from user where uid = %d limit 1", + intval($uid) + ); + if(! count($u)) + return; + + $community_page = (($u[0]['page-flags'] == PAGE_COMMUNITY) ? true : false); + + $i = q("select * from item where id = %d and uid = %d limit 1", + intval($item_id), + intval($uid) + ); + if(! count($i)) + return; + + $item = $i[0]; + + $link = normalise_link($a->get_baseurl() . '/profile/' . $u[0]['nickname']); + + // Diaspora uses their own hardwired link URL in @-tags + // instead of the one we supply with webfinger + + $dlink = normalise_link($a->get_baseurl() . '/u/' . $u[0]['nickname']); + + $cnt = preg_match_all('/[\@\!]\[url\=(.*?)\](.*?)\[\/url\]/ism',$item['body'],$matches,PREG_SET_ORDER); + if($cnt) { + foreach($matches as $mtch) { + if(link_compare($link,$mtch[1]) || link_compare($dlink,$mtch[1])) { + $mention = true; + logger('tag_deliver: mention found: ' . $mtch[2]); + } + } + } + + if(! $mention) + return; + + // send a notification + + require_once('include/enotify.php'); + notification(array( + 'type' => NOTIFY_TAGSELF, + 'notify_flags' => $u[0]['notify-flags'], + 'language' => $u[0]['language'], + 'to_name' => $u[0]['username'], + 'to_email' => $u[0]['email'], + 'uid' => $u[0]['uid'], + 'item' => $item, + 'link' => $a->get_baseurl() . '/display/' . $u[0]['nickname'] . '/' . $item['id'], + 'source_name' => $item['author-name'], + 'source_link' => $item['author-link'], + 'source_photo' => $item['author-avatar'], + 'verb' => ACTIVITY_TAG, + 'otype' => 'item' + )); + + if(! $community_page) + 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['wall']) || ($item['origin']) || ($item['id'] != $item['parent'])) + return; + + // now change this copy of the post to a forum head message and deliver to all the tgroup members + + + $c = q("select name, url, thumb from contact where self = 1 and uid = %d limit 1", + intval($u[0]['uid']) + ); + if(! count($c)) + return; + + q("update item set wall = 1, origin = 1, forum_mode = 1, `owner-name` = '%s', `owner-link` = '%s', `owner-avatar` = '%s' where id = %d limit 1", + dbesc($c[0]['name']), + dbesc($c[0]['url']), + dbesc($c[0]['thumb']), + intval($item_id) + ); + + proc_run('php','include/notifier.php','tgroup',$item_id); + +} + + + + + + function dfrn_deliver($owner,$contact,$atom, $dissolve = false) { $a = get_app(); - if((! strlen($contact['issued-id'])) && (! $contact['duplex']) && (! ($owner['page-flags'] == PAGE_COMMUNITY))) - return 3; +// if((! strlen($contact['issued-id'])) && (! $contact['duplex']) && (! ($owner['page-flags'] == PAGE_COMMUNITY))) +// return 3; $idtosend = $orig_id = (($contact['dfrn-id']) ? $contact['dfrn-id'] : $contact['issued-id']); @@ -976,7 +1078,9 @@ function dfrn_deliver($owner,$contact,$atom, $dissolve = false) { $final_dfrn_id = ''; - if(($contact['duplex'] && strlen($contact['pubkey'])) || ($owner['page-flags'] == PAGE_COMMUNITY)) { + if(($contact['duplex'] && strlen($contact['pubkey'])) + || ($owner['page-flags'] == PAGE_COMMUNITY && strlen($contact['pubkey'])) + || ($contact['rel'] == CONTACT_IS_SHARING && strlen($contact['pubkey']))) { openssl_public_decrypt($sent_dfrn_id,$final_dfrn_id,$contact['pubkey']); openssl_public_decrypt($challenge,$postvars['challenge'],$contact['pubkey']); } @@ -1019,7 +1123,10 @@ function dfrn_deliver($owner,$contact,$atom, $dissolve = false) { if($dfrn_version >= 2.1) { - if(($contact['duplex'] && strlen($contact['pubkey'])) || ($owner['page-flags'] == PAGE_COMMUNITY)) { + if(($contact['duplex'] && strlen($contact['pubkey'])) + || ($owner['page-flags'] == PAGE_COMMUNITY && strlen($contact['pubkey'])) + || ($contact['rel'] == CONTACT_IS_SHARING && strlen($contact['pubkey']))) { + openssl_public_encrypt($key,$postvars['key'],$contact['pubkey']); } else { @@ -1201,12 +1308,28 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) } if((is_array($contact)) && ($name_updated) && (strlen($new_name)) && ($name_updated > $contact['name-date'])) { - q("UPDATE `contact` SET `name` = '%s', `name-date` = '%s' WHERE `uid` = %d AND `id` = %d LIMIT 1", + $r = q("select * from contact where uid = %d and id = %d limit 1", + intval($contact['uid']), + intval($contact['id']) + ); + + $x = q("UPDATE `contact` SET `name` = '%s', `name-date` = '%s' WHERE `uid` = %d AND `id` = %d LIMIT 1", dbesc(notags(trim($new_name))), dbesc(datetime_convert()), intval($contact['uid']), intval($contact['id']) ); + + // do our best to update the name on content items + + if(count($r)) { + q("update item set `author-name` = '%s' where `author-name` = '%s' and `author-link` = '%s' and uid = %d", + dbesc(notags(trim($new_name))), + dbesc($r[0]['name']), + dbesc($r[0]['url']), + intval($contact['uid']) + ); + } } if(strlen($birthday)) { @@ -1274,7 +1397,8 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) $when = datetime_convert('UTC','UTC','now','Y-m-d H:i:s'); } if($deleted && is_array($contact)) { - $r = q("SELECT * FROM `item` WHERE `uri` = '%s' AND `uid` = %d AND `contact-id` = %d LIMIT 1", + $r = q("SELECT `item`.*, `contact`.`self` FROM `item` left join `contact` on `item`.`contact-id` = `contact`.`id` + WHERE `uri` = '%s' AND `item`.`uid` = %d AND `contact-id` = %d LIMIT 1", dbesc($uri), intval($importer['uid']), intval($contact['id']) @@ -1285,6 +1409,41 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) if(! $item['deleted']) logger('consume_feed: deleting item ' . $item['id'] . ' uri=' . $item['uri'], LOGGER_DEBUG); + if(($item['verb'] === ACTIVITY_TAG) && ($item['object-type'] === ACTVITY_OBJ_TAGTERM)) { + $xo = parse_xml_string($item['object'],false); + $xt = parse_xml_string($item['target'],false); + if($xt->type === ACTIVITY_OBJ_NOTE) { + $i = q("select * from `item` where uri = '%s' and uid = %d limit 1", + dbesc($xt->id), + intval($importer['importer_uid']) + ); + if(count($i)) { + + // For tags, the owner cannot remove the tag on the author's copy of the post. + + $owner_remove = (($item['contact-id'] == $i[0]['contact-id']) ? true: false); + $author_remove = (($item['origin'] && $item['self']) ? true : false); + $author_copy = (($item['origin']) ? true : false); + + if($owner_remove && $author_copy) + continue; + if($author_remove || $owner_remove) { + $tags = explode(',',$i[0]['tag']); + $newtags = array(); + if(count($tags)) { + foreach($tags as $tag) + if(trim($tag) !== trim($xo->body)) + $newtags[] = trim($tag); + } + q("update item set tag = '%s' where id = %d limit 1", + dbesc(implode(',',$newtags)), + intval($i[0]['id']) + ); + } + } + } + } + if($item['uri'] == $item['parent-uri']) { $r = q("UPDATE `item` SET `deleted` = 1, `edited` = '%s', `changed` = '%s', `body` = '', `title` = '' @@ -1312,7 +1471,7 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) intval($item['uid']) ); // who is the last child now? - $r = q("SELECT `id` FROM `item` WHERE `parent-uri` = '%s' AND `type` != 'activity' AND `deleted` = 0 AND `uid` = %d + $r = q("SELECT `id` FROM `item` WHERE `parent-uri` = '%s' AND `type` != 'activity' AND `deleted` = 0 AND `moderated` = 0 AND `uid` = %d ORDER BY `created` DESC LIMIT 1", dbesc($item['parent-uri']), intval($importer['uid']) @@ -1352,20 +1511,28 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) $parent_uri = $rawthread[0]['attribs']['']['ref']; } - if(($is_reply) && is_array($contact) && $pass != 1) { + if(($is_reply) && is_array($contact)) { + + if($pass == 1) + continue; // Have we seen it? If not, import it. $item_id = $item->get_id(); $datarray = get_atom_elements($feed,$item); - if(! x($datarray,'author-name')) + + if((! x($datarray,'author-name')) && ($contact['network'] != NETWORK_DFRN)) $datarray['author-name'] = $contact['name']; - if(! x($datarray,'author-link')) + if((! x($datarray,'author-link')) && ($contact['network'] != NETWORK_DFRN)) $datarray['author-link'] = $contact['url']; - if(! x($datarray,'author-avatar')) + 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; + } $r = q("SELECT `uid`, `last-child`, `edited`, `body` FROM `item` WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", dbesc($item_id), @@ -1376,7 +1543,8 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) if(count($r)) { if((x($datarray,'edited') !== false) && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { - $r = q("UPDATE `item` SET `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + $r = q("UPDATE `item` SET `title` = '%s', `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + dbesc($datarray['title']), dbesc($datarray['body']), dbesc(datetime_convert('UTC','UTC',$datarray['edited'])), dbesc($item_id), @@ -1404,8 +1572,9 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) } $force_parent = false; - if($contact['network'] === NETWORK_OSTATUS) { - $force_parent = true; + if($contact['network'] === NETWORK_OSTATUS || stristr($contact['url'],'twitter.com')) { + if($contact['network'] === NETWORK_OSTATUS) + $force_parent = true; if(strlen($datarray['title'])) unset($datarray['title']); $r = q("UPDATE `item` SET `last-child` = 0, `changed` = '%s' WHERE `parent-uri` = '%s' AND `uid` = %d", @@ -1428,6 +1597,31 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) $datarray['gravity'] = GRAVITY_LIKE; } + if(($datarray['verb'] === ACTIVITY_TAG) && ($datarray['object-type'] === ACTIVITY_OBJ_TAGTERM)) { + $xo = parse_xml_string($datarray['object'],false); + $xt = parse_xml_string($datarray['target'],false); + + if($xt->type == ACTIVITY_OBJ_NOTE) { + $r = q("select * from item where `uri` = '%s' AND `uid` = %d limit 1", + dbesc($xt->id), + intval($importer['importer_uid']) + ); + if(! count($r)) + continue; + + // extract tag, if not duplicate, add to parent item + if($xo->id && $xo->content) { + $newtag = '#[url=' . $xo->id . ']'. $xo->content . '[/url]'; + 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']) + ); + } + } + } + } + $r = item_store($datarray,$force_parent); continue; } @@ -1441,14 +1635,19 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) $datarray = get_atom_elements($feed,$item); if(is_array($contact)) { - if(! x($datarray,'author-name')) + if((! x($datarray,'author-name')) && ($contact['network'] != NETWORK_DFRN)) $datarray['author-name'] = $contact['name']; - if(! x($datarray,'author-link')) + if((! x($datarray,'author-link')) && ($contact['network'] != NETWORK_DFRN)) $datarray['author-link'] = $contact['url']; - if(! x($datarray,'author-avatar')) + 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; + } + // special handling for events if((x($datarray,'object-type')) && ($datarray['object-type'] === ACTIVITY_OBJ_EVENT)) { @@ -1481,7 +1680,8 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) if(count($r)) { if((x($datarray,'edited') !== false) && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { - $r = q("UPDATE `item` SET `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + $r = q("UPDATE `item` SET `title` = '%s', `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + dbesc($datarray['title']), dbesc($datarray['body']), dbesc(datetime_convert('UTC','UTC',$datarray['edited'])), dbesc($item_id), @@ -1527,7 +1727,7 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) if(! is_array($contact)) return; - if($contact['network'] === NETWORK_OSTATUS || stristr($permalink,'twitter.com')) { + if($contact['network'] === NETWORK_OSTATUS || stristr($contact['url'],'twitter.com')) { if(strlen($datarray['title'])) unset($datarray['title']); $datarray['last-child'] = 1; @@ -1555,14 +1755,14 @@ function consume_feed($xml,$importer,&$contact, &$hub, $datedir = 0, $pass = 0) } } -function local_delivery($importer,$xml) { +function local_delivery($importer,$data) { $a = get_app(); if($importer['readonly']) { // We aren't receiving stuff from this person. But we will quietly ignore them // rather than a blatant "go away" message. - logger('dfrn_notify: ignoring'); + logger('local_delivery: ignoring'); return 0; //NOTREACHED } @@ -1619,9 +1819,9 @@ function local_delivery($importer,$xml) { // Does our member already have a friend matching this description? - $r = q("SELECT * FROM `contact` WHERE `name` = '%s' AND `url` = '%s' AND `uid` = %d LIMIT 1", + $r = q("SELECT * FROM `contact` WHERE `name` = '%s' AND `nurl` = '%s' AND `uid` = %d LIMIT 1", dbesc($fsugg['name']), - dbesc($fsugg['url']), + dbesc(normalise_link($fsugg['url'])), intval($fsugg['uid']) ); if(count($r)) @@ -1670,7 +1870,21 @@ function local_delivery($importer,$xml) { intval(0) ); - // TODO - send email notify (which may require a new notification preference) + notification(array( + 'type' => NOTIFY_SUGGEST, + 'notify_flags' => $importer['notify-flags'], + 'language' => $importer['language'], + 'to_name' => $importer['username'], + 'to_email' => $importer['email'], + 'uid' => $importer['importer_uid'], + 'item' => $fsugg, + 'link' => $a->get_baseurl() . '/notifications/intros', + 'source_name' => $importer['name'], + 'source_link' => $importer['url'], + 'source_photo' => $importer['photo'], + 'verb' => ACTIVITY_REQ_FRIEND, + 'otype' => 'intro' + )); return 0; } @@ -1680,7 +1894,7 @@ function local_delivery($importer,$xml) { $rawmail = $feed->get_feed_tags( NAMESPACE_DFRN, 'mail' ); if(isset($rawmail[0]['child'][NAMESPACE_DFRN])) { - logger('dfrn_notify: private message received'); + logger('local_delivery: private message received'); $ismail = true; $base = $rawmail[0]['child'][NAMESPACE_DFRN]; @@ -1704,88 +1918,32 @@ function local_delivery($importer,$xml) { $r = dbq("INSERT INTO `mail` (`" . implode("`, `", array_keys($msg)) . "`) VALUES ('" . implode("', '", array_values($msg)) . "')" ); - // send email notification if requested. - - require_once('bbcode.php'); - if($importer['notify-flags'] & NOTIFY_MAIL) { - - push_lang($importer['language']); - - // name of the automated email sender - $msg['notificationfromname'] = t('Administrator'); - // noreply address to send from - $msg['notificationfromemail'] = t('noreply') . '@' . $a->get_hostname(); - - // text version - // process the message body to display properly in text mode - // 1) substitute a \n character for the "\" then "n", so it behaves properly (it doesn't come in as a \n character) - // 2) remove escape slashes - // 3) decode any bbcode from the message editor - // 4) decode any encoded html tags - // 5) remove html tags - $msg['textversion'] - = strip_tags(html_entity_decode(bbcode(stripslashes(str_replace(array("\\r\\n", "\\r", "\\n"), "\n",$msg['body']))),ENT_QUOTES,'UTF-8')); - - // html version - // process the message body to display properly in text mode - // 1) substitute a
tag for the "\" then "n", so it behaves properly (it doesn't come in as a \n character) - // 2) remove escape slashes - // 3) decode any bbcode from the message editor - // 4) decode any encoded html tags - $msg['htmlversion'] - = html_entity_decode(bbcode(stripslashes(str_replace(array("\\r\\n", "\\r","\\n\\n" ,"\\n"), "
\n",$msg['body'])))); - - // load the template for private message notifications - $tpl = get_intltext_template('mail_received_html_body_eml.tpl'); - $email_html_body_tpl = replace_macros($tpl,array( - '$username' => $importer['username'], - '$siteName' => $a->config['sitename'], // name of this site - '$siteurl' => $a->get_baseurl(), // descriptive url of this site - '$thumb' => $importer['thumb'], // thumbnail url for sender icon - '$email' => $importer['email'], // email address to send to - '$url' => $importer['url'], // full url for the site - '$from' => $msg['from-name'], // name of the person sending the message - '$title' => stripslashes($msg['title']), // subject of the message - '$htmlversion' => $msg['htmlversion'], // html version of the message - '$mimeboundary' => $msg['mimeboundary'], // mime message divider - '$hostname' => $a->get_hostname() // name of this host - )); + // send notifications. + + require_once('include/enotify.php'); + + $notif_params = array( + 'type' => NOTIFY_MAIL, + 'notify_flags' => $importer['notify-flags'], + 'language' => $importer['language'], + 'to_name' => $importer['username'], + 'to_email' => $importer['email'], + 'uid' => $importer['importer_uid'], + 'item' => $msg, + 'source_name' => $msg['from-name'], + 'source_link' => $importer['url'], + 'source_photo' => $importer['thumb'], + 'verb' => ACTIVITY_POST, + 'otype' => 'mail' + ); - // load the template for private message notifications - $tpl = get_intltext_template('mail_received_text_body_eml.tpl'); - $email_text_body_tpl = replace_macros($tpl,array( - '$username' => $importer['username'], - '$siteName' => $a->config['sitename'], // name of this site - '$siteurl' => $a->get_baseurl(), // descriptive url of this site - '$thumb' => $importer['thumb'], // thumbnail url for sender icon - '$email' => $importer['email'], // email address to send to - '$url' => $importer['url'], // full url for the site - '$from' => $msg['from-name'], // name of the person sending the message - '$title' => stripslashes($msg['title']), // subject of the message - '$textversion' => $msg['textversion'], // text version of the message - '$mimeboundary' => $msg['mimeboundary'], // mime message divider - '$hostname' => $a->get_hostname() // name of this host - )); - - // use the EmailNotification library to send the message - require_once("include/EmailNotification.php"); - EmailNotification::sendTextHtmlEmail( - $msg['notificationfromname'], - $msg['notificationfromemail'], - $msg['notificationfromemail'], - $importer['email'], - t('New mail received at ') . $a->config['sitename'], - $email_html_body_tpl, - $email_text_body_tpl - ); - - pop_lang(); - } + notification($notif_params); return 0; + // NOTREACHED } - logger('dfrn_notify: feed item count = ' . $feed->get_item_quantity()); + logger('local_delivery: feed item count = ' . $feed->get_item_quantity()); // process any deleted entries @@ -1805,7 +1963,8 @@ function local_delivery($importer,$xml) { } if($deleted) { - $r = q("SELECT * FROM `item` WHERE `uri` = '%s' AND `uid` = %d AND `contact-id` = %d LIMIT 1", + $r = q("SELECT `item`.*, `contact`.`self` FROM `item` left join contact on `item`.`contact-id` = `contact`.`id` + WHERE `uri` = '%s' AND `item`.`uid` = %d AND `contact-id` = %d LIMIT 1", dbesc($uri), intval($importer['importer_uid']), intval($importer['id']) @@ -1814,8 +1973,45 @@ function local_delivery($importer,$xml) { if(count($r)) { $item = $r[0]; - if(! $item['deleted']) - logger('dfrn_notify: deleting item ' . $item['id'] . ' uri=' . $item['uri'], LOGGER_DEBUG); + if($item['deleted']) + continue; + + logger('local_delivery: deleting item ' . $item['id'] . ' uri=' . $item['uri'], LOGGER_DEBUG); + + if(($item['verb'] === ACTIVITY_TAG) && ($item['object-type'] === ACTVITY_OBJ_TAGTERM)) { + $xo = parse_xml_string($item['object'],false); + $xt = parse_xml_string($item['target'],false); + if($xt->type === ACTIVITY_OBJ_NOTE) { + $i = q("select * from `item` where uri = '%s' and uid = %d limit 1", + dbesc($xt->id), + intval($importer['importer_uid']) + ); + if(count($i)) { + + // For tags, the owner cannot remove the tag on the author's copy of the post. + + $owner_remove = (($item['contact-id'] == $i[0]['contact-id']) ? true: false); + $author_remove = (($item['origin'] && $item['self']) ? true : false); + $author_copy = (($item['origin']) ? true : false); + + if($owner_remove && $author_copy) + continue; + if($author_remove || $owner_remove) { + $tags = explode(',',$i[0]['tag']); + $newtags = array(); + if(count($tags)) { + foreach($tags as $tag) + if(trim($tag) !== trim($xo->body)) + $newtags[] = trim($tag); + } + q("update item set tag = '%s' where id = %d limit 1", + dbesc(implode(',',$newtags)), + intval($i[0]['id']) + ); + } + } + } + } if($item['uri'] == $item['parent-uri']) { $r = q("UPDATE `item` SET `deleted` = 1, `edited` = '%s', `changed` = '%s' @@ -1871,29 +2067,61 @@ function local_delivery($importer,$xml) { } if($is_reply) { + $community = false; + if($importer['page-flags'] == PAGE_COMMUNITY) { + $sql_extra = ''; + $community = true; + logger('local_delivery: possible community reply'); + } + else + $sql_extra = " and contact.self = 1 and item.wall = 1 "; + // was the top-level post for this reply written by somebody on this site? // Specifically, the recipient? - $r = q("select `item`.`id`, `contact`.`name`, `contact`.`url`, `contact`.`thumb` from `item` + $is_a_remote_comment = false; + + $r = q("select `item`.`id`, `item`.`uri`, `item`.`tag`, `item`.`forum_mode`,`item`.`origin`,`item`.`wall`, + `contact`.`name`, `contact`.`url`, `contact`.`thumb` from `item` LEFT JOIN `contact` ON `contact`.`id` = `item`.`contact-id` - WHERE `contact`.`self` = 1 AND `item`.`wall` = 1 AND `item`.`uri` = '%s' AND `item`.`uid` = %d LIMIT 1", + WHERE `item`.`uri` = '%s' AND `item`.`parent-uri` = '%s' + AND `item`.`uid` = %d + $sql_extra + LIMIT 1", + dbesc($parent_uri), dbesc($parent_uri), intval($importer['importer_uid']) ); - if($r && count($r)) { - + if($r && count($r)) + $is_a_remote_comment = true; + + // Does this have the characteristics of a community comment? + // If it's a reply to a wall post on a community page it's a + // valid community comment. Also forum_mode makes it valid for sure. + // If neither, it's not. + + if($is_a_remote_comment && $community) { + if((! $r[0]['forum_mode']) && (! $r[0]['wall'])) { + $is_a_remote_comment = false; + logger('local_delivery: not a community reply'); + } + } - logger('dfrn_notify: received remote comment'); + if($is_a_remote_comment) { + logger('local_delivery: received remote comment'); $is_like = false; // remote reply to our post. Import and then notify everybody else. $datarray = get_atom_elements($feed,$item); - if(! link_compare($datarray['author-link'],$importer['url'])) { - logger('dfrn_notify: received relay claiming to be from ' . $importer['url'] . ' however comment author url is ' . $datarray['author-link'] ); + + // TODO: make this next part work against both delivery threads of a community post + +// if((! link_compare($datarray['author-link'],$importer['url'])) && (! $community)) { +// logger('local_delivery: received relay claiming to be from ' . $importer['url'] . ' however comment author url is ' . $datarray['author-link'] ); // they won't know what to do so don't report an error. Just quietly die. - return 0; - } +// return 0; +// } $datarray['type'] = 'remote-comment'; $datarray['wall'] = 1; @@ -1903,12 +2131,51 @@ function local_delivery($importer,$xml) { $datarray['owner-link'] = $r[0]['url']; $datarray['owner-avatar'] = $r[0]['thumb']; $datarray['contact-id'] = $importer['id']; - if(($datarray['verb'] == ACTIVITY_LIKE) || ($datarray['verb'] == ACTIVITY_DISLIKE)) { + if(($datarray['verb'] === ACTIVITY_LIKE) || ($datarray['verb'] === ACTIVITY_DISLIKE)) { $is_like = true; $datarray['type'] = 'activity'; $datarray['gravity'] = GRAVITY_LIKE; $datarray['last-child'] = 0; } + + if(($datarray['verb'] === ACTIVITY_TAG) && ($datarray['object-type'] === ACTIVITY_OBJ_TAGTERM)) { + + + $xo = parse_xml_string($datarray['object'],false); + $xt = parse_xml_string($datarray['target'],false); + + if(($xt->type == ACTIVITY_OBJ_NOTE) && ($xt->id == $r[0]['uri'])) { + + // extract tag, if not duplicate, and this user allows tags, add to parent item + + if($xo->id && $xo->content) { + $newtag = '#[url=' . $xo->id . ']'. $xo->content . '[/url]'; + + if(! (stristr($r[0]['tag'],$newtag))) { + $i = q("SELECT `blocktags` FROM `user` where `uid` = %d LIMIT 1", + intval($importer['importer_uid']) + ); + if(count($i) && ! ($i[0]['blocktags'])) { + q("UPDATE item SET tag = '%s' WHERE id = %d LIMIT 1", + dbesc($r[0]['tag'] . (strlen($r[0]['tag']) ? ',' : '') . $newtag), + intval($r[0]['id']) + ); + } + } + } + } + } + +// if($community) { +// $newtag = '@[url=' . $a->get_baseurl() . '/profile/' . $importer['nickname'] . ']' . $importer['username'] . '[/url]'; +// if(! stristr($datarray['tag'],$newtag)) { +// if(strlen($datarray['tag'])) +// $datarray['tag'] .= ','; +// $datarray['tag'] .= $newtag; +// } +// } + + $posted_id = item_store($datarray); $parent = 0; @@ -1938,70 +2205,32 @@ function local_delivery($importer,$xml) { proc_run('php',"include/notifier.php","comment-import","$posted_id"); - if((! $is_like) && ($importer['notify-flags'] & NOTIFY_COMMENT) && (! $importer['self'])) { - push_lang($importer['language']); - require_once('bbcode.php'); - $from = stripslashes($datarray['author-name']); - - // name of the automated email sender - $msg['notificationfromname'] = stripslashes($datarray['author-name']);; - // noreply address to send from - $msg['notificationfromemail'] = t('noreply') . '@' . $a->get_hostname(); - - // text version - // process the message body to display properly in text mode - $msg['textversion'] - = html_entity_decode(strip_tags(bbcode(stripslashes($datarray['body']))), ENT_QUOTES, 'UTF-8'); - - // html version - // process the message body to display properly in text mode - $msg['htmlversion'] - = html_entity_decode(bbcode(stripslashes(str_replace(array("\\r\\n", "\\r","\\n\\n" ,"\\n"), "
\n",$datarray['body'])))); - - $imgtouse = ((link_compare($datarray['author-link'],$importer['url'])) ? $importer['thumb'] : $datarray['author-avatar']); - - // load the template for private message notifications - $tpl = get_intltext_template('cmnt_received_html_body_eml.tpl'); - $email_html_body_tpl = replace_macros($tpl,array( - '$username' => $importer['username'], - '$sitename' => $a->config['sitename'], // name of this site - '$siteurl' => $a->get_baseurl(), // descriptive url of this site - '$thumb' => $imgtouse, // thumbnail url for sender icon - '$email' => $importer['email'], // email address to send to - '$url' => $datarray['author-link'], // full url for the site - '$from' => $from, // name of the person sending the message - '$body' => $msg['htmlversion'], // html version of the message - '$display' => $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $posted_id, - )); - - // load the template for private message notifications - $tpl = get_intltext_template('cmnt_received_text_body_eml.tpl'); - $email_text_body_tpl = replace_macros($tpl,array( - '$username' => $importer['username'], - '$sitename' => $a->config['sitename'], // name of this site - '$siteurl' => $a->get_baseurl(), // descriptive url of this site - '$thumb' => $imgtouse, // thumbnail url for sender icon - '$email' => $importer['email'], // email address to send to - '$url' => $datarray['author-link'], // full url for the site - '$from' => $from, // name of the person sending the message - '$body' => $msg['textversion'], // text version of the message - '$display' => $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $posted_id, + if((! $is_like) && (! $importer['self'])) { + + require_once('include/enotify.php'); + + notification(array( + 'type' => NOTIFY_COMMENT, + 'notify_flags' => $importer['notify-flags'], + 'language' => $importer['language'], + 'to_name' => $importer['username'], + 'to_email' => $importer['email'], + 'uid' => $importer['importer_uid'], + 'item' => $datarray, + 'link' => $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $posted_id, + 'source_name' => stripslashes($datarray['author-name']), + 'source_link' => $datarray['author-link'], + 'source_photo' => ((link_compare($datarray['author-link'],$importer['url'])) + ? $importer['thumb'] : $datarray['author-avatar']), + 'verb' => ACTIVITY_POST, + 'otype' => 'item', + 'parent' => $parent, + )); - // use the EmailNotification library to send the message - require_once("include/EmailNotification.php"); - EmailNotification::sendTextHtmlEmail( - $msg['notificationfromname'], - t("Administrator") . '@' . $a->get_hostname(), - t("noreply") . '@' . $a->get_hostname(), - $importer['email'], - sprintf( t('%s commented on an item at %s'), $from , $a->config['sitename']), - $email_html_body_tpl, - $email_text_body_tpl - ); - pop_lang(); } } + return 0; // NOTREACHED } @@ -2022,7 +2251,8 @@ function local_delivery($importer,$xml) { if(count($r)) { if((x($datarray,'edited') !== false) && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { - $r = q("UPDATE `item` SET `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + $r = q("UPDATE `item` SET `title` = '%s', `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + dbesc($datarray['title']), dbesc($datarray['body']), dbesc(datetime_convert('UTC','UTC',$datarray['edited'])), dbesc($item_id), @@ -2056,82 +2286,73 @@ function local_delivery($importer,$xml) { $datarray['type'] = 'activity'; $datarray['gravity'] = GRAVITY_LIKE; } + + if(($datarray['verb'] === ACTIVITY_TAG) && ($datarray['object-type'] === ACTIVITY_OBJ_TAGTERM)) { + + $xo = parse_xml_string($datarray['object'],false); + $xt = parse_xml_string($datarray['target'],false); + + if($xt->type == ACTIVITY_OBJ_NOTE) { + $r = q("select * from item where `uri` = '%s' AND `uid` = %d limit 1", + dbesc($xt->id), + intval($importer['importer_uid']) + ); + if(! count($r)) + continue; + + // extract tag, if not duplicate, add to parent item + if($xo->content) { + if(! (stristr($r[0]['tag'],trim($xo->content)))) { + q("UPDATE item SET tag = '%s' WHERE id = %d LIMIT 1", + dbesc($r[0]['tag'] . (strlen($r[0]['tag']) ? ',' : '') . '#[url=' . $xo->id . ']'. $xo->content . '[/url]'), + intval($r[0]['id']) + ); + } + } + } + } + $posted_id = item_store($datarray); // find out if our user is involved in this conversation and wants to be notified. - if(($datarray['type'] != 'activity') && ($importer['notify-flags'] & NOTIFY_COMMENT)) { + if($datarray['type'] != 'activity') { - $myconv = q("SELECT `author-link`, `author-avatar` FROM `item` WHERE `parent-uri` = '%s' AND `uid` = %d AND `parent` != 0 ", + $myconv = q("SELECT `author-link`, `author-avatar`, `parent` FROM `item` WHERE `parent-uri` = '%s' AND `uid` = %d AND `parent` != 0 ", dbesc($parent_uri), intval($importer['importer_uid']) ); + if(count($myconv)) { $importer_url = $a->get_baseurl() . '/profile/' . $importer['nickname']; foreach($myconv as $conv) { + if(! link_compare($conv['author-link'],$importer_url)) continue; - push_lang($importer['language']); - require_once('bbcode.php'); - $from = stripslashes($datarray['author-name']); + require_once('include/enotify.php'); - // name of the automated email sender - $msg['notificationfromname'] = stripslashes($datarray['author-name']);; - // noreply address to send from - $msg['notificationfromemail'] = t('noreply') . '@' . $a->get_hostname(); - - // text version - // process the message body to display properly in text mode - $msg['textversion'] - = html_entity_decode(strip_tags(bbcode(stripslashes($datarray['body']))), ENT_QUOTES, 'UTF-8'); - - // html version - // process the message body to display properly in text mode - $msg['htmlversion'] - = html_entity_decode(bbcode(stripslashes(str_replace(array("\\r\\n", "\\r","\\n\\n" ,"\\n"), "
\n",$datarray['body'])))); - - $imgtouse = ((link_compare($datarray['author-link'],$importer['url'])) ? $importer['thumb'] : $datarray['author-avatar']); - - - // load the template for private message notifications - $tpl = get_intltext_template('cmnt_received_html_body_eml.tpl'); - $email_html_body_tpl = replace_macros($tpl,array( - '$username' => $importer['username'], - '$sitename' => $a->config['sitename'], // name of this site - '$siteurl' => $a->get_baseurl(), // descriptive url of this site - '$thumb' => $imgtouse, // thumbnail url for sender icon - '$url' => $datarray['author-link'], // full url for the site - '$from' => $from, // name of the person sending the message - '$body' => $msg['htmlversion'], // html version of the message - '$display' => $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $posted_id, - )); - - // load the template for private message notifications - $tpl = get_intltext_template('cmnt_received_text_body_eml.tpl'); - $email_text_body_tpl = replace_macros($tpl,array( - '$username' => $importer['username'], - '$sitename' => $a->config['sitename'], // name of this site - '$siteurl' => $a->get_baseurl(), // descriptive url of this site - '$thumb' => $imgtouse, // thumbnail url for sender icon - '$url' => $datarray['author-link'], // full url for the site - '$from' => $from, // name of the person sending the message - '$body' => $msg['textversion'], // text version of the message - '$display' => $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $posted_id, + $conv_parent = $conv['parent']; + + notification(array( + 'type' => NOTIFY_COMMENT, + 'notify_flags' => $importer['notify-flags'], + 'language' => $importer['language'], + 'to_name' => $importer['username'], + 'to_email' => $importer['email'], + 'uid' => $importer['importer_uid'], + 'item' => $datarray, + 'link' => $a->get_baseurl() . '/display/' . $importer['nickname'] . '/' . $posted_id, + 'source_name' => stripslashes($datarray['author-name']), + 'source_link' => $datarray['author-link'], + 'source_photo' => ((link_compare($datarray['author-link'],$importer['url'])) + ? $importer['thumb'] : $datarray['author-avatar']), + 'verb' => ACTIVITY_POST, + 'otype' => 'item', + 'parent' => $conv_parent, + )); - // use the EmailNotification library to send the message - require_once("include/EmailNotification.php"); - EmailNotification::sendTextHtmlEmail( - $msg['notificationfromname'], - t("Administrator@") . $a->get_hostname(), - t("noreply") . '@' . $a->get_hostname(), - $importer['email'], - sprintf( t('%s commented on an item at %s'), $from , $a->config['sitename']), - $email_html_body_tpl, - $email_text_body_tpl - ); - pop_lang(); break; } } @@ -2177,7 +2398,8 @@ function local_delivery($importer,$xml) { if(count($r)) { if((x($datarray,'edited') !== false) && (datetime_convert('UTC','UTC',$datarray['edited']) !== $r[0]['edited'])) { - $r = q("UPDATE `item` SET `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + $r = q("UPDATE `item` SET `title` = '%s', `body` = '%s', `edited` = '%s' WHERE `uri` = '%s' AND `uid` = %d LIMIT 1", + dbesc($datarray['title']), dbesc($datarray['body']), dbesc(datetime_convert('UTC','UTC',$datarray['edited'])), dbesc($item_id), @@ -2202,7 +2424,7 @@ function local_delivery($importer,$xml) { // This is my contact on another system, but it's really me. // Turn this into a wall post. - if($contact['remote_self']) + if($importer['remote_self']) $datarray['wall'] = 1; $datarray['parent-uri'] = $item_id; @@ -2243,12 +2465,13 @@ function new_follower($importer,$contact,$datarray,$item,$sharing = false) { // create contact record - $r = q("INSERT INTO `contact` ( `uid`, `created`, `url`, `name`, `nick`, `photo`, `network`, `rel`, + $r = q("INSERT INTO `contact` ( `uid`, `created`, `url`, `nurl`, `name`, `nick`, `photo`, `network`, `rel`, `blocked`, `readonly`, `pending`, `writable` ) - VALUES ( %d, '%s', '%s', '%s', '%s', '%s', '%s', %d, 0, 0, 1, 1 ) ", + VALUES ( %d, '%s', '%s', '%s', '%s', '%s', '%s', '%s', %d, 0, 0, 1, 1 ) ", intval($importer['uid']), dbesc(datetime_convert()), dbesc($url), + dbesc(normalise_link($url)), dbesc($name), dbesc($nick), dbesc($photo), @@ -2392,6 +2615,9 @@ function atom_entry($item,$type,$author,$owner,$comment = false) { $a = get_app(); + if(! $item['parent']) + return; + if($item['deleted']) return '' . "\r\n"; @@ -2411,8 +2637,8 @@ function atom_entry($item,$type,$author,$owner,$comment = false) { if(strlen($item['owner-name'])) $o .= atom_author('dfrn:owner',$item['owner-name'],$item['owner-link'],80,80,$item['owner-avatar']); - if($item['parent'] != $item['id']) - $o .= '' . "\r\n"; + if(($item['parent'] != $item['id']) || ($item['parent-uri'] !== $item['uri'])) + $o .= '' . "\r\n"; $o .= '' . xmlify($item['uri']) . '' . "\r\n"; $o .= '' . xmlify($item['title']) . '' . "\r\n"; @@ -2517,7 +2743,7 @@ function item_getfeedtags($item) { $matches = false; $cnt = preg_match_all('|\#\[url\=(.*?)\](.*?)\[\/url\]|',$item['tag'],$matches); if($cnt) { - for($x = 0; $x < count($matches); $x ++) { + for($x = 0; $x < $cnt; $x ++) { if($matches[1][$x]) $ret[] = array('#',$matches[1][$x], $matches[2][$x]); } @@ -2525,9 +2751,9 @@ function item_getfeedtags($item) { $matches = false; $cnt = preg_match_all('|\@\[url\=(.*?)\](.*?)\[\/url\]|',$item['tag'],$matches); if($cnt) { - for($x = 0; $x < count($matches); $x ++) { + for($x = 0; $x < $cnt; $x ++) { if($matches[1][$x]) - $ret[] = array('#',$matches[1][$x], $matches[2][$x]); + $ret[] = array('@',$matches[1][$x], $matches[2][$x]); } } return $ret; @@ -2571,14 +2797,32 @@ function item_expire($uid,$days) { if(! count($r)) return; + + $expire_items = get_pconfig($uid, 'expire','items'); + $expire_items = (($expire_items===false)?1:intval($expire_items)); // default if not set: 1 + + $expire_notes = get_pconfig($uid, 'expire','notes'); + $expire_notes = (($expire_notes===false)?1:intval($expire_notes)); // default if not set: 1 + + $expire_starred = get_pconfig($uid, 'expire','starred'); + $expire_starred = (($expire_starred===false)?1:intval($expire_starred)); // default if not set: 1 + + $expire_photos = get_pconfig($uid, 'expire','photos'); + $expire_photos = (($expire_photos===false)?0:intval($expire_photos)); // default if not set: 0 - logger('expire: # items=' . count($r) ); + logger('expire: # items=' . count($r). "; expire items: $expire_items, expire notes: $expire_notes, expire starred: $expire_starred, expire photos: $expire_photos"); foreach($r as $item) { // Only expire posts, not photos and photo comments - if(strlen($item['resource-id'])) + if($expire_photos==0 && strlen($item['resource-id'])) + continue; + if($expire_starred==0 && intval($item['starred'])) + continue; + if($expire_notes==0 && $item['type']=='note') + continue; + if($expire_items==0 && $item['type']!='note') continue; $r = q("UPDATE `item` SET `deleted` = 1, `edited` = '%s', `changed` = '%s' WHERE `id` = %d LIMIT 1", @@ -2599,13 +2843,16 @@ function item_expire($uid,$days) { } proc_run('php',"include/notifier.php","expire","$uid"); - + } function drop_items($items) { $uid = 0; + if((! local_user()) && (! $remote_user())) + return; + if(count($items)) { foreach($items as $item) { $owner = drop_item($item,false); @@ -2648,7 +2895,7 @@ function drop_item($id,$interactive = true) { // delete the item - $r = q("UPDATE `item` SET `deleted` = 1, `body` = '', `edited` = '%s', `changed` = '%s' WHERE `id` = %d LIMIT 1", + $r = q("UPDATE `item` SET `deleted` = 1, `title` = '', `body` = '', `edited` = '%s', `changed` = '%s' WHERE `id` = %d LIMIT 1", dbesc(datetime_convert()), dbesc(datetime_convert()), intval($item['id']) @@ -2681,7 +2928,7 @@ function drop_item($id,$interactive = true) { // If it's the parent of a comment thread, kill all the kids if($item['uri'] == $item['parent-uri']) { - $r = q("UPDATE `item` SET `deleted` = 1, `edited` = '%s', `changed` = '%s', `body` = '' + $r = q("UPDATE `item` SET `deleted` = 1, `edited` = '%s', `changed` = '%s', `body` = '' , `title` = '' WHERE `parent-uri` = '%s' AND `uid` = %d ", dbesc(datetime_convert()), dbesc(datetime_convert()), @@ -2727,4 +2974,4 @@ function drop_item($id,$interactive = true) { //NOTREACHED } -} \ No newline at end of file +}