2015-06-07 21:18:02 +00:00
< ? php
2015-06-20 12:40:30 +00:00
require_once ( " include/Contact.php " );
require_once ( " include/threads.php " );
require_once ( " include/html2bbcode.php " );
2015-12-14 22:02:49 +00:00
require_once ( " include/bbcode.php " );
2015-06-20 12:40:30 +00:00
require_once ( " include/items.php " );
2015-06-07 21:18:02 +00:00
require_once ( " mod/share.php " );
2015-06-20 12:40:30 +00:00
require_once ( " include/enotify.php " );
require_once ( " include/socgraph.php " );
require_once ( " include/Photo.php " );
2015-08-23 20:21:15 +00:00
require_once ( " include/Scrape.php " );
require_once ( " include/follow.php " );
2015-12-07 20:52:42 +00:00
require_once ( " include/api.php " );
2015-12-04 05:50:23 +00:00
require_once ( " mod/proxy.php " );
2015-06-20 12:40:30 +00:00
define ( 'OSTATUS_DEFAULT_POLL_INTERVAL' , 30 ); // given in minutes
define ( 'OSTATUS_DEFAULT_POLL_TIMEFRAME' , 1440 ); // given in minutes
2015-06-29 19:53:59 +00:00
define ( 'OSTATUS_DEFAULT_POLL_TIMEFRAME_MENTIONS' , 14400 ); // given in minutes
2015-06-07 21:18:02 +00:00
2015-08-23 20:21:15 +00:00
function ostatus_check_follow_friends () {
$r = q ( " SELECT `uid`,`v` FROM `pconfig` WHERE `cat`='system' AND `k`='ostatus_legacy_contact' AND `v` != '' " );
if ( ! $r )
return ;
foreach ( $r AS $contact ) {
ostatus_follow_friends ( $contact [ " uid " ], $contact [ " v " ]);
set_pconfig ( $contact [ " uid " ], " system " , " ostatus_legacy_contact " , " " );
}
}
2015-08-26 20:46:59 +00:00
// This function doesn't work reliable by now.
2015-08-23 20:21:15 +00:00
function ostatus_follow_friends ( $uid , $url ) {
$contact = probe_url ( $url );
if ( ! $contact )
return ;
$api = $contact [ " baseurl " ] . " /api/ " ;
// Fetching friends
$data = z_fetch_url ( $api . " statuses/friends.json?screen_name= " . $contact [ " nick " ]);
if ( ! $data [ " success " ])
return ;
$friends = json_decode ( $data [ " body " ]);
foreach ( $friends AS $friend ) {
$url = $friend -> statusnet_profile_url ;
$r = q ( " SELECT `url` FROM `contact` WHERE `uid` = %d AND
( `nurl` = '%s' OR `alias` = '%s' OR `alias` = '%s' ) AND
`network` != '%s' LIMIT 1 " ,
2015-11-08 10:10:20 +00:00
intval ( $uid ), dbesc ( normalise_link ( $url )),
2015-08-23 20:21:15 +00:00
dbesc ( normalise_link ( $url )), dbesc ( $url ), dbesc ( NETWORK_STATUSNET ));
if ( ! $r ) {
$data = probe_url ( $friend -> statusnet_profile_url );
if ( $data [ " network " ] == NETWORK_OSTATUS ) {
$result = new_contact ( $uid , $friend -> statusnet_profile_url );
if ( $result [ " success " ])
logger ( $friend -> name . " " . $url . " - success " , LOGGER_DEBUG );
else
logger ( $friend -> name . " " . $url . " - failed " , LOGGER_DEBUG );
} else
logger ( $friend -> name . " " . $url . " - not OStatus " , LOGGER_DEBUG );
}
}
}
2015-07-13 12:34:28 +00:00
function ostatus_fetchauthor ( $xpath , $context , $importer , & $contact , $onlyfetch ) {
2015-06-07 21:18:02 +00:00
$author = array ();
$author [ " author-link " ] = $xpath -> evaluate ( 'atom:author/atom:uri/text()' , $context ) -> item ( 0 ) -> nodeValue ;
$author [ " author-name " ] = $xpath -> evaluate ( 'atom:author/atom:name/text()' , $context ) -> item ( 0 ) -> nodeValue ;
// Preserve the value
$authorlink = $author [ " author-link " ];
$alternate = $xpath -> query ( " atom:author/atom:link[@rel='alternate'] " , $context ) -> item ( 0 ) -> attributes ;
if ( is_object ( $alternate ))
foreach ( $alternate AS $attributes )
if ( $attributes -> name == " href " )
$author [ " author-link " ] = $attributes -> textContent ;
$r = q ( " SELECT * FROM `contact` WHERE `uid` = %d AND `nurl` IN ('%s', '%s') AND `network` != '%s' " ,
intval ( $importer [ " uid " ]), dbesc ( normalise_link ( $author [ " author-link " ])),
dbesc ( normalise_link ( $authorlink )), dbesc ( NETWORK_STATUSNET ));
if ( $r ) {
$contact = $r [ 0 ];
$author [ " contact-id " ] = $r [ 0 ][ " id " ];
} else
$author [ " contact-id " ] = $contact [ " id " ];
$avatarlist = array ();
$avatars = $xpath -> query ( " atom:author/atom:link[@rel='avatar'] " , $context );
foreach ( $avatars AS $avatar ) {
$href = " " ;
$width = 0 ;
foreach ( $avatar -> attributes AS $attributes ) {
if ( $attributes -> name == " href " )
$href = $attributes -> textContent ;
if ( $attributes -> name == " width " )
$width = $attributes -> textContent ;
}
if (( $width > 0 ) AND ( $href != " " ))
$avatarlist [ $width ] = $href ;
}
if ( count ( $avatarlist ) > 0 ) {
krsort ( $avatarlist );
$author [ " author-avatar " ] = current ( $avatarlist );
}
$displayname = $xpath -> evaluate ( 'atom:author/poco:displayName/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $displayname != " " )
$author [ " author-name " ] = $displayname ;
$author [ " owner-name " ] = $author [ " author-name " ];
$author [ " owner-link " ] = $author [ " author-link " ];
$author [ " owner-avatar " ] = $author [ " author-avatar " ];
2016-01-28 10:09:08 +00:00
// Only update the contacts if it is an OStatus contact
if ( $r AND ! $onlyfetch AND ( $contact [ " network " ] == NETWORK_OSTATUS )) {
2015-06-13 07:11:17 +00:00
// Update contact data
2016-01-07 23:35:46 +00:00
$value = $xpath -> query ( " atom:link[@rel='salmon'] " , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$contact [ " notify " ] = $value ;
$value = $xpath -> evaluate ( 'atom:author/uri/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$contact [ " alias " ] = $value ;
2016-01-05 14:34:27 +00:00
$value = $xpath -> evaluate ( 'atom:author/poco:displayName/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$contact [ " name " ] = $value ;
$value = $xpath -> evaluate ( 'atom:author/poco:preferredUsername/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$contact [ " nick " ] = $value ;
$value = $xpath -> evaluate ( 'atom:author/poco:note/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$contact [ " about " ] = html2bbcode ( $value );
2015-06-13 07:11:17 +00:00
2016-01-05 14:34:27 +00:00
$value = $xpath -> evaluate ( 'atom:author/poco:address/poco:formatted/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$contact [ " location " ] = $value ;
2015-06-13 07:11:17 +00:00
2016-01-05 14:34:27 +00:00
if (( $contact [ " name " ] != $r [ 0 ][ " name " ]) OR ( $contact [ " nick " ] != $r [ 0 ][ " nick " ]) OR ( $contact [ " about " ] != $r [ 0 ][ " about " ]) OR ( $contact [ " location " ] != $r [ 0 ][ " location " ])) {
2015-06-13 07:11:17 +00:00
2016-01-05 14:34:27 +00:00
logger ( " Update contact data for contact " . $contact [ " id " ], LOGGER_DEBUG );
2015-06-13 07:11:17 +00:00
2016-01-28 10:09:08 +00:00
q ( " UPDATE `contact` SET `name` = '%s', `nick` = '%s', `about` = '%s', `location` = '%s', `name-date` = '%s' WHERE `id` = %d " ,
2015-06-13 07:11:17 +00:00
dbesc ( $contact [ " name " ]), dbesc ( $contact [ " nick " ]), dbesc ( $contact [ " about " ]), dbesc ( $contact [ " location " ]),
2016-01-28 10:09:08 +00:00
dbesc ( datetime_convert ()), intval ( $contact [ " id " ]));
2015-06-13 07:11:17 +00:00
poco_check ( $contact [ " url " ], $contact [ " name " ], $contact [ " network " ], $author [ " author-avatar " ], $contact [ " about " ], $contact [ " location " ],
2016-01-05 14:34:27 +00:00
" " , " " , " " , datetime_convert (), 2 , $contact [ " id " ], $contact [ " uid " ]);
2015-06-13 07:11:17 +00:00
}
2016-01-28 00:26:19 +00:00
if ( isset ( $author [ " author-avatar " ]) AND ( $author [ " author-avatar " ] != $r [ 0 ][ 'avatar' ])) {
2015-06-13 07:11:17 +00:00
logger ( " Update profile picture for contact " . $contact [ " id " ], LOGGER_DEBUG );
2016-01-28 10:09:08 +00:00
update_contact_avatar ( $author [ " author-avatar " ], $importer [ " uid " ], $contact [ " id " ]);
2015-06-13 07:11:17 +00:00
}
2016-01-05 14:34:27 +00:00
2016-01-28 10:09:08 +00:00
$contact [ " generation " ] = 2 ;
$contact [ " photo " ] = $author [ " author-avatar " ];
update_gcontact ( $contact );
2015-06-13 07:11:17 +00:00
}
2015-06-07 21:18:02 +00:00
return ( $author );
}
2015-07-13 06:06:51 +00:00
function ostatus_salmon_author ( $xml , $importer ) {
$a = get_app ();
if ( $xml == " " )
return ;
$doc = new DOMDocument ();
@ $doc -> loadXML ( $xml );
$xpath = new DomXPath ( $doc );
2016-01-29 22:14:01 +00:00
$xpath -> registerNamespace ( 'atom' , NAMESPACE_ATOM1 );
$xpath -> registerNamespace ( 'thr' , NAMESPACE_THREAD );
$xpath -> registerNamespace ( 'georss' , NAMESPACE_GEORSS );
$xpath -> registerNamespace ( 'activity' , NAMESPACE_ACTIVITY );
$xpath -> registerNamespace ( 'media' , NAMESPACE_MEDIA );
$xpath -> registerNamespace ( 'poco' , NAMESPACE_POCO );
$xpath -> registerNamespace ( 'ostatus' , NAMESPACE_OSTATUS );
$xpath -> registerNamespace ( 'statusnet' , NAMESPACE_STATUSNET );
2015-07-13 06:06:51 +00:00
$entries = $xpath -> query ( '/atom:entry' );
foreach ( $entries AS $entry ) {
// fetch the author
2015-07-13 12:34:28 +00:00
$author = ostatus_fetchauthor ( $xpath , $entry , $importer , $contact , true );
2015-07-13 06:06:51 +00:00
return $author ;
}
}
2015-06-09 06:27:04 +00:00
function ostatus_import ( $xml , $importer , & $contact , & $hub ) {
2015-06-07 21:18:02 +00:00
$a = get_app ();
logger ( " Import OStatus message " , LOGGER_DEBUG );
if ( $xml == " " )
return ;
$doc = new DOMDocument ();
2015-06-09 06:27:04 +00:00
@ $doc -> loadXML ( $xml );
2015-06-07 21:18:02 +00:00
$xpath = new DomXPath ( $doc );
2016-01-29 22:14:01 +00:00
$xpath -> registerNamespace ( 'atom' , NAMESPACE_ATOM1 );
$xpath -> registerNamespace ( 'thr' , NAMESPACE_THREAD );
$xpath -> registerNamespace ( 'georss' , NAMESPACE_GEORSS );
$xpath -> registerNamespace ( 'activity' , NAMESPACE_ACTIVITY );
$xpath -> registerNamespace ( 'media' , NAMESPACE_MEDIA );
$xpath -> registerNamespace ( 'poco' , NAMESPACE_POCO );
$xpath -> registerNamespace ( 'ostatus' , NAMESPACE_OSTATUS );
$xpath -> registerNamespace ( 'statusnet' , NAMESPACE_STATUSNET );
2015-06-07 21:18:02 +00:00
2015-06-09 21:53:53 +00:00
$gub = " " ;
$hub_attributes = $xpath -> query ( " /atom:feed/atom:link[@rel='hub'] " ) -> item ( 0 ) -> attributes ;
if ( is_object ( $hub_attributes ))
foreach ( $hub_attributes AS $hub_attribute )
if ( $hub_attribute -> name == " href " ) {
$hub = $hub_attribute -> textContent ;
logger ( " Found hub " . $hub , LOGGER_DEBUG );
}
2015-06-07 21:18:02 +00:00
$header = array ();
$header [ " uid " ] = $importer [ " uid " ];
$header [ " network " ] = NETWORK_OSTATUS ;
$header [ " type " ] = " remote " ;
$header [ " wall " ] = 0 ;
$header [ " origin " ] = 0 ;
$header [ " gravity " ] = GRAVITY_PARENT ;
// it could either be a received post or a post we fetched by ourselves
// depending on that, the first node is different
$first_child = $doc -> firstChild -> tagName ;
if ( $first_child == " feed " )
$entries = $xpath -> query ( '/atom:feed/atom:entry' );
else
$entries = $xpath -> query ( '/atom:entry' );
$conversation = " " ;
$conversationlist = array ();
$item_id = 0 ;
// Reverse the order of the entries
2015-06-09 06:27:04 +00:00
$entrylist = array ();
2015-06-07 21:18:02 +00:00
foreach ( $entries AS $entry )
$entrylist [] = $entry ;
foreach ( array_reverse ( $entrylist ) AS $entry ) {
$mention = false ;
// fetch the author
if ( $first_child == " feed " )
2015-07-13 12:34:28 +00:00
$author = ostatus_fetchauthor ( $xpath , $doc -> firstChild , $importer , $contact , false );
2015-06-07 21:18:02 +00:00
else
2015-07-13 12:34:28 +00:00
$author = ostatus_fetchauthor ( $xpath , $entry , $importer , $contact , false );
2015-06-07 21:18:02 +00:00
2015-07-13 21:50:33 +00:00
$value = $xpath -> evaluate ( 'atom:author/poco:preferredUsername/text()' , $context ) -> item ( 0 ) -> nodeValue ;
if ( $value != " " )
$nickname = $value ;
else
$nickname = $author [ " author-name " ];
2015-06-07 21:18:02 +00:00
$item = array_merge ( $header , $author );
// Now get the item
$item [ " uri " ] = $xpath -> query ( 'atom:id/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
2015-06-07 21:53:51 +00:00
$r = q ( " SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' " ,
intval ( $importer [ " uid " ]), dbesc ( $item [ " uri " ]));
if ( $r ) {
logger ( " Item with uri " . $item [ " uri " ] . " for user " . $importer [ " uid " ] . " already existed under id " . $r [ 0 ][ " id " ], LOGGER_DEBUG );
continue ;
}
2015-06-07 22:18:44 +00:00
$item [ " body " ] = add_page_info_to_body ( html2bbcode ( $xpath -> query ( 'atom:content/text()' , $entry ) -> item ( 0 ) -> nodeValue ));
2015-06-07 21:18:02 +00:00
$item [ " object-type " ] = $xpath -> query ( 'activity:object-type/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
2015-06-21 20:02:44 +00:00
2015-06-21 20:36:24 +00:00
if (( $item [ " object-type " ] == ACTIVITY_OBJ_BOOKMARK ) OR ( $item [ " object-type " ] == ACTIVITY_OBJ_EVENT )) {
2015-06-21 20:02:44 +00:00
$item [ " title " ] = $xpath -> query ( 'atom:title/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
$item [ " body " ] = $xpath -> query ( 'atom:summary/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
2015-06-21 20:36:24 +00:00
} elseif ( $item [ " object-type " ] == ACTIVITY_OBJ_QUESTION )
$item [ " title " ] = $xpath -> query ( 'atom:title/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
2015-06-21 20:02:44 +00:00
2015-06-20 06:44:29 +00:00
$item [ " object " ] = $xml ;
2015-06-07 21:18:02 +00:00
$item [ " verb " ] = $xpath -> query ( 'activity:verb/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
2015-12-25 22:17:34 +00:00
/// @TODO
/// Delete a message
2015-06-30 06:08:02 +00:00
if ( $item [ " verb " ] == " qvitter-delete-notice " ) {
// ignore "Delete" messages (by now)
2015-07-15 06:16:41 +00:00
logger ( " Ignore delete message " . print_r ( $item , true ));
2015-06-30 06:08:02 +00:00
continue ;
}
2015-06-20 12:40:30 +00:00
if ( $item [ " verb " ] == ACTIVITY_JOIN ) {
// ignore "Join" messages
2015-07-15 06:16:41 +00:00
logger ( " Ignore join message " . print_r ( $item , true ));
2015-06-20 12:40:30 +00:00
continue ;
}
2015-06-07 21:18:02 +00:00
if ( $item [ " verb " ] == ACTIVITY_FOLLOW ) {
2015-07-13 21:50:33 +00:00
new_follower ( $importer , $contact , $item , $nickname );
2015-06-07 21:18:02 +00:00
continue ;
}
2015-07-13 06:06:51 +00:00
if ( $item [ " verb " ] == NAMESPACE_OSTATUS . " /unfollow " ) {
2015-07-13 21:50:33 +00:00
lose_follower ( $importer , $contact , $item , $dummy );
2015-07-13 06:06:51 +00:00
continue ;
}
2015-06-07 21:18:02 +00:00
if ( $item [ " verb " ] == ACTIVITY_FAVORITE ) {
2015-07-15 06:16:41 +00:00
$orig_uri = $xpath -> query ( " activity:object/atom:id " , $entry ) -> item ( 0 ) -> nodeValue ;
logger ( " Favorite " . $orig_uri . " " . print_r ( $item , true ));
2015-11-08 10:10:20 +00:00
$item [ " verb " ] = ACTIVITY_LIKE ;
2015-07-15 06:16:41 +00:00
$item [ " parent-uri " ] = $orig_uri ;
$item [ " gravity " ] = GRAVITY_LIKE ;
}
if ( $item [ " verb " ] == NAMESPACE_OSTATUS . " /unfavorite " ) {
// Ignore "Unfavorite" message
logger ( " Ignore unfavorite message " . print_r ( $item , true ));
2015-06-07 21:18:02 +00:00
continue ;
}
2015-07-15 06:16:41 +00:00
// http://activitystrea.ms/schema/1.0/rsvp-yes
2015-07-15 16:27:44 +00:00
if ( ! in_array ( $item [ " verb " ], array ( ACTIVITY_POST , ACTIVITY_LIKE , ACTIVITY_SHARE )))
2015-07-15 06:16:41 +00:00
logger ( " Unhandled verb " . $item [ " verb " ] . " " . print_r ( $item , true ));
2015-06-07 21:18:02 +00:00
$item [ " created " ] = $xpath -> query ( 'atom:published/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
$item [ " edited " ] = $xpath -> query ( 'atom:updated/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
$conversation = $xpath -> query ( 'ostatus:conversation/text()' , $entry ) -> item ( 0 ) -> nodeValue ;
$related = " " ;
$inreplyto = $xpath -> query ( 'thr:in-reply-to' , $entry );
if ( is_object ( $inreplyto -> item ( 0 ))) {
foreach ( $inreplyto -> item ( 0 ) -> attributes AS $attributes ) {
if ( $attributes -> name == " ref " )
$item [ " parent-uri " ] = $attributes -> textContent ;
if ( $attributes -> name == " href " )
$related = $attributes -> textContent ;
}
}
$georsspoint = $xpath -> query ( 'georss:point' , $entry );
if ( $georsspoint )
$item [ " coord " ] = $georsspoint -> item ( 0 ) -> nodeValue ;
2015-12-25 22:17:34 +00:00
/// @TODO
/// $item["location"] =
2015-06-20 06:44:29 +00:00
2015-06-07 21:18:02 +00:00
$categories = $xpath -> query ( 'atom:category' , $entry );
if ( $categories ) {
foreach ( $categories AS $category ) {
foreach ( $category -> attributes AS $attributes )
if ( $attributes -> name == " term " ) {
$term = $attributes -> textContent ;
if ( strlen ( $item [ " tag " ]))
$item [ " tag " ] .= ',' ;
$item [ " tag " ] .= " #[url= " . $a -> get_baseurl () . " /search?tag= " . $term . " ] " . $term . " [/url] " ;
}
}
}
$self = " " ;
$enclosure = " " ;
$links = $xpath -> query ( 'atom:link' , $entry );
if ( $links ) {
$rel = " " ;
$href = " " ;
$type = " " ;
$length = " 0 " ;
$title = " " ;
foreach ( $links AS $link ) {
foreach ( $link -> attributes AS $attributes ) {
if ( $attributes -> name == " href " )
$href = $attributes -> textContent ;
if ( $attributes -> name == " rel " )
$rel = $attributes -> textContent ;
if ( $attributes -> name == " type " )
$type = $attributes -> textContent ;
if ( $attributes -> name == " length " )
$length = $attributes -> textContent ;
if ( $attributes -> name == " title " )
$title = $attributes -> textContent ;
}
if (( $rel != " " ) AND ( $href != " " ))
switch ( $rel ) {
case " alternate " :
$item [ " plink " ] = $href ;
2015-06-21 20:36:24 +00:00
if (( $item [ " object-type " ] == ACTIVITY_OBJ_QUESTION ) OR
( $item [ " object-type " ] == ACTIVITY_OBJ_EVENT ))
$item [ " body " ] .= add_page_info ( $href );
2015-06-07 21:18:02 +00:00
break ;
case " ostatus:conversation " :
$conversation = $href ;
break ;
case " enclosure " :
$enclosure = $href ;
if ( strlen ( $item [ " attach " ]))
$item [ " attach " ] .= ',' ;
$item [ " attach " ] .= '[attach]href="' . $href . '" length="' . $length . '" type="' . $type . '" title="' . $title . '"[/attach]' ;
break ;
case " related " :
2015-06-21 20:02:44 +00:00
if ( $item [ " object-type " ] != ACTIVITY_OBJ_BOOKMARK ) {
if ( ! isset ( $item [ " parent-uri " ]))
$item [ " parent-uri " ] = $href ;
if ( $related == " " )
$related = $href ;
} else
$item [ " body " ] .= add_page_info ( $href );
2015-06-07 21:18:02 +00:00
break ;
case " self " :
$self = $href ;
break ;
case " mentioned " :
// Notification check
if ( $importer [ " nurl " ] == normalise_link ( $href ))
$mention = true ;
break ;
}
}
}
$local_id = " " ;
$repeat_of = " " ;
$notice_info = $xpath -> query ( 'statusnet:notice_info' , $entry );
2015-06-20 06:44:29 +00:00
if ( $notice_info AND ( $notice_info -> length > 0 )) {
2015-06-07 21:18:02 +00:00
foreach ( $notice_info -> item ( 0 ) -> attributes AS $attributes ) {
if ( $attributes -> name == " source " )
$item [ " app " ] = strip_tags ( $attributes -> textContent );
if ( $attributes -> name == " local_id " )
$local_id = $attributes -> textContent ;
if ( $attributes -> name == " repeat_of " )
$repeat_of = $attributes -> textContent ;
}
2015-06-20 06:44:29 +00:00
}
2015-06-07 21:18:02 +00:00
// Is it a repeated post?
if ( $repeat_of != " " ) {
$activityobjects = $xpath -> query ( 'activity:object' , $entry ) -> item ( 0 );
if ( is_object ( $activityobjects )) {
2015-06-20 15:26:47 +00:00
$orig_uri = $xpath -> query ( " activity:object/atom:id " , $activityobjects ) -> item ( 0 ) -> nodeValue ;
if ( ! isset ( $orig_uri ))
$orig_uri = $xpath -> query ( 'atom:id/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
$orig_links = $xpath -> query ( " activity:object/atom:link[@rel='alternate'] " , $activityobjects );
if ( $orig_links AND ( $orig_links -> length > 0 ))
foreach ( $orig_links -> item ( 0 ) -> attributes AS $attributes )
2015-06-07 21:18:02 +00:00
if ( $attributes -> name == " href " )
2015-06-20 15:26:47 +00:00
$orig_link = $attributes -> textContent ;
2015-06-07 21:18:02 +00:00
2015-06-20 15:26:47 +00:00
if ( ! isset ( $orig_link ))
$orig_link = $xpath -> query ( " atom:link[@rel='alternate'] " , $activityobjects ) -> item ( 0 ) -> nodeValue ;
2015-06-07 21:18:02 +00:00
2015-06-20 15:26:47 +00:00
if ( ! isset ( $orig_link ))
$orig_link = ostatus_convert_href ( $orig_uri );
2015-06-07 21:18:02 +00:00
2015-06-20 15:26:47 +00:00
$orig_body = $xpath -> query ( 'activity:object/atom:content/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
if ( ! isset ( $orig_body ))
$orig_body = $xpath -> query ( 'atom:content/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
2015-06-07 21:18:02 +00:00
$orig_created = $xpath -> query ( 'atom:published/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
$orig_contact = $contact ;
2015-07-13 12:34:28 +00:00
$orig_author = ostatus_fetchauthor ( $xpath , $activityobjects , $importer , $orig_contact , false );
2015-06-07 21:18:02 +00:00
2015-06-13 07:11:17 +00:00
//if (!intval(get_config('system','wall-to-wall_share'))) {
2015-06-20 15:26:47 +00:00
// $prefix = share_header($orig_author['author-name'], $orig_author['author-link'], $orig_author['author-avatar'], "", $orig_created, $orig_link);
2015-06-13 07:11:17 +00:00
// $item["body"] = $prefix.add_page_info_to_body(html2bbcode($orig_body))."[/share]";
//} else {
$item [ " author-name " ] = $orig_author [ " author-name " ];
$item [ " author-link " ] = $orig_author [ " author-link " ];
$item [ " author-avatar " ] = $orig_author [ " author-avatar " ];
2015-06-11 22:39:56 +00:00
$item [ " body " ] = add_page_info_to_body ( html2bbcode ( $orig_body ));
$item [ " created " ] = $orig_created ;
2015-06-13 07:11:17 +00:00
$item [ " uri " ] = $orig_uri ;
2015-06-20 15:26:47 +00:00
$item [ " plink " ] = $orig_link ;
2015-06-13 07:11:17 +00:00
//}
2015-06-07 21:18:02 +00:00
$item [ " verb " ] = $xpath -> query ( 'activity:verb/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
2015-06-20 15:26:47 +00:00
$item [ " object-type " ] = $xpath -> query ( 'activity:object/activity:object-type/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
if ( ! isset ( $item [ " object-type " ]))
$item [ " object-type " ] = $xpath -> query ( 'activity:object-type/text()' , $activityobjects ) -> item ( 0 ) -> nodeValue ;
2015-06-07 21:18:02 +00:00
}
}
2015-06-07 22:18:44 +00:00
//if ($enclosure != "")
// $item["body"] .= add_page_info($enclosure);
2015-06-07 21:18:02 +00:00
if ( isset ( $item [ " parent-uri " ])) {
$r = q ( " SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' " ,
intval ( $importer [ " uid " ]), dbesc ( $item [ " parent-uri " ]));
if ( ! $r AND ( $related != " " )) {
$reply_path = str_replace ( " /notice/ " , " /api/statuses/show/ " , $related ) . " .atom " ;
if ( $reply_path != $related ) {
logger ( " Fetching related items for user " . $importer [ " uid " ] . " from " . $reply_path , LOGGER_DEBUG );
$reply_xml = fetch_url ( $reply_path );
$reply_contact = $contact ;
2015-06-09 06:27:04 +00:00
ostatus_import ( $reply_xml , $importer , $reply_contact , $reply_hub );
2015-06-07 21:18:02 +00:00
// After the import try to fetch the parent item again
$r = q ( " SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' " ,
intval ( $importer [ " uid " ]), dbesc ( $item [ " parent-uri " ]));
}
}
if ( $r ) {
$item [ " type " ] = 'remote-comment' ;
$item [ " gravity " ] = GRAVITY_COMMENT ;
}
} else
$item [ " parent-uri " ] = $item [ " uri " ];
2015-06-20 06:44:29 +00:00
$item_id = ostatus_completion ( $conversation , $importer [ " uid " ], $item );
2015-06-07 21:53:51 +00:00
if ( ! $item_id ) {
2015-06-21 06:32:03 +00:00
logger ( " Error storing item " , LOGGER_DEBUG );
2015-06-07 21:53:51 +00:00
continue ;
}
logger ( " Item was stored with id " . $item_id , LOGGER_DEBUG );
2015-06-07 21:18:02 +00:00
}
}
2015-06-20 12:40:30 +00:00
function ostatus_convert_href ( $href ) {
$elements = explode ( " : " , $href );
if (( count ( $elements ) <= 2 ) OR ( $elements [ 0 ] != " tag " ))
return $href ;
$server = explode ( " , " , $elements [ 1 ]);
$conversation = explode ( " = " , $elements [ 2 ]);
if (( count ( $elements ) == 4 ) AND ( $elements [ 2 ] == " post " ))
return " http:// " . $server [ 0 ] . " /notice/ " . $elements [ 3 ];
if (( count ( $conversation ) != 2 ) OR ( $conversation [ 1 ] == " " ))
return $href ;
if ( $elements [ 3 ] == " objectType=thread " )
return " http:// " . $server [ 0 ] . " /conversation/ " . $conversation [ 1 ];
else
return " http:// " . $server [ 0 ] . " /notice/ " . $conversation [ 1 ];
return $href ;
}
2015-06-29 19:53:59 +00:00
function check_conversations ( $mentions = false , $override = false ) {
2015-06-20 12:40:30 +00:00
$last = get_config ( 'system' , 'ostatus_last_poll' );
$poll_interval = intval ( get_config ( 'system' , 'ostatus_poll_interval' ));
if ( ! $poll_interval )
$poll_interval = OSTATUS_DEFAULT_POLL_INTERVAL ;
// Don't poll if the interval is set negative
if (( $poll_interval < 0 ) AND ! $override )
return ;
2015-06-29 19:53:59 +00:00
if ( ! $mentions ) {
$poll_timeframe = intval ( get_config ( 'system' , 'ostatus_poll_timeframe' ));
if ( ! $poll_timeframe )
$poll_timeframe = OSTATUS_DEFAULT_POLL_TIMEFRAME ;
} else {
$poll_timeframe = intval ( get_config ( 'system' , 'ostatus_poll_timeframe' ));
if ( ! $poll_timeframe )
$poll_timeframe = OSTATUS_DEFAULT_POLL_TIMEFRAME_MENTIONS ;
}
2015-06-20 12:40:30 +00:00
if ( $last AND ! $override ) {
$next = $last + ( $poll_interval * 60 );
if ( $next > time ()) {
logger ( 'poll interval not reached' );
return ;
}
}
logger ( 'cron_start' );
$start = date ( " Y-m-d H:i:s " , time () - ( $poll_timeframe * 60 ));
2015-06-29 19:53:59 +00:00
if ( $mentions )
$conversations = q ( " SELECT `term`.`oid`, `term`.`url`, `term`.`uid` FROM `term`
STRAIGHT_JOIN `thread` ON `thread` . `iid` = `term` . `oid` AND `thread` . `uid` = `term` . `uid`
WHERE `term` . `type` = 7 AND `term` . `term` > '%s' AND `thread` . `mention`
GROUP BY `term` . `url` , `term` . `uid` ORDER BY `term` . `term` DESC " , dbesc( $start ));
else
$conversations = q ( " SELECT `oid`, `url`, `uid` FROM `term`
WHERE `type` = 7 AND `term` > '%s'
GROUP BY `url` , `uid` ORDER BY `term` DESC " , dbesc( $start ));
2015-06-20 12:40:30 +00:00
foreach ( $conversations AS $conversation ) {
ostatus_completion ( $conversation [ 'url' ], $conversation [ 'uid' ]);
}
logger ( 'cron_end' );
set_config ( 'system' , 'ostatus_last_poll' , time ());
}
2016-02-13 20:35:05 +00:00
/**
* @ brief Updates the gcontact table with actor data from the conversation
*
* @ param object $actor The actor object that contains the contact data
*/
function ostatus_conv_fetch_actor ( $actor ) {
// We set the generation to "3" since the data here is not as reliable as the data we get on other occasions
$contact = array ( " network " => NETWORK_OSTATUS , " generation " => 3 );
if ( isset ( $actor -> url ))
$contact [ " url " ] = $actor -> url ;
if ( isset ( $actor -> displayName ))
$contact [ " name " ] = $actor -> displayName ;
if ( isset ( $actor -> portablecontacts_net -> displayName ))
$contact [ " name " ] = $actor -> portablecontacts_net -> displayName ;
if ( isset ( $actor -> portablecontacts_net -> preferredUsername ))
$contact [ " nick " ] = $actor -> portablecontacts_net -> preferredUsername ;
if ( isset ( $actor -> id ))
$contact [ " alias " ] = $actor -> id ;
if ( isset ( $actor -> summary ))
$contact [ " about " ] = $actor -> summary ;
if ( isset ( $actor -> portablecontacts_net -> note ))
$contact [ " about " ] = $actor -> portablecontacts_net -> note ;
if ( isset ( $actor -> portablecontacts_net -> addresses -> formatted ))
$contact [ " location " ] = $actor -> portablecontacts_net -> addresses -> formatted ;
if ( isset ( $actor -> image -> url ))
$contact [ " photo " ] = $actor -> image -> url ;
if ( isset ( $actor -> image -> width ))
$avatarwidth = $actor -> image -> width ;
if ( is_array ( $actor -> status_net -> avatarLinks ))
foreach ( $actor -> status_net -> avatarLinks AS $avatar ) {
if ( $avatarsize < $avatar -> width ) {
$contact [ " photo " ] = $avatar -> url ;
$avatarsize = $avatar -> width ;
}
}
update_gcontact ( $contact );
}
2015-06-20 12:40:30 +00:00
function ostatus_completion ( $conversation_url , $uid , $item = array ()) {
2015-06-26 08:41:11 +00:00
$a = get_app ();
2015-06-20 23:36:23 +00:00
$item_stored = - 1 ;
2015-06-20 12:40:30 +00:00
$conversation_url = ostatus_convert_href ( $conversation_url );
// If the thread shouldn't be completed then store the item and go away
if (( intval ( get_config ( 'system' , 'ostatus_poll_interval' )) == - 2 ) AND ( count ( $item ) > 0 )) {
2015-06-25 05:30:14 +00:00
//$arr["app"] .= " (OStatus-NoCompletion)";
2015-06-20 12:40:30 +00:00
$item_stored = item_store ( $item , true );
return ( $item_stored );
}
// Get the parent
$parents = q ( " SELECT `id`, `parent`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `id` IN
( SELECT `parent` FROM `item` WHERE `id` IN
( SELECT `oid` FROM `term` WHERE `uid` = % d AND `otype` = % d AND `type` = % d AND `url` = '%s' )) " ,
intval ( $uid ), intval ( TERM_OBJ_POST ), intval ( TERM_CONVERSATION ), dbesc ( $conversation_url ));
if ( $parents )
$parent = $parents [ 0 ];
elseif ( count ( $item ) > 0 ) {
$parent = $item ;
$parent [ " type " ] = " remote " ;
$parent [ " verb " ] = ACTIVITY_POST ;
$parent [ " visible " ] = 1 ;
} else {
// Preset the parent
$r = q ( " SELECT `id` FROM `contact` WHERE `self` AND `uid`=%d " , $uid );
if ( ! $r )
2015-06-20 23:36:23 +00:00
return ( - 2 );
2015-06-20 12:40:30 +00:00
$parent = array ();
$parent [ " id " ] = 0 ;
$parent [ " parent " ] = 0 ;
$parent [ " uri " ] = " " ;
$parent [ " contact-id " ] = $r [ 0 ][ " id " ];
$parent [ " type " ] = " remote " ;
$parent [ " verb " ] = ACTIVITY_POST ;
$parent [ " visible " ] = 1 ;
}
$conv = str_replace ( " /conversation/ " , " /api/statusnet/conversation/ " , $conversation_url ) . " .as " ;
$pageno = 1 ;
$items = array ();
logger ( 'fetching conversation url ' . $conv . ' for user ' . $uid );
do {
$conv_arr = z_fetch_url ( $conv . " ?page= " . $pageno );
// If it is a non-ssl site and there is an error, then try ssl or vice versa
if ( ! $conv_arr [ " success " ] AND ( substr ( $conv , 0 , 7 ) == " http:// " )) {
$conv = str_replace ( " http:// " , " https:// " , $conv );
$conv_as = fetch_url ( $conv . " ?page= " . $pageno );
} elseif ( ! $conv_arr [ " success " ] AND ( substr ( $conv , 0 , 8 ) == " https:// " )) {
$conv = str_replace ( " https:// " , " http:// " , $conv );
$conv_as = fetch_url ( $conv . " ?page= " . $pageno );
} else
$conv_as = $conv_arr [ " body " ];
$conv_as = str_replace ( ',"statusnet:notice_info":' , ',"statusnet_notice_info":' , $conv_as );
$conv_as = json_decode ( $conv_as );
2015-11-08 10:10:20 +00:00
$no_of_items = sizeof ( $items );
2015-06-20 12:40:30 +00:00
if ( @ is_array ( $conv_as -> items ))
2015-11-08 14:32:16 +00:00
foreach ( $conv_as -> items AS $single_item )
$items [ $single_item -> id ] = $single_item ;
2015-11-08 10:10:20 +00:00
if ( $no_of_items == sizeof ( $items ))
2015-06-20 12:40:30 +00:00
break ;
$pageno ++ ;
} while ( true );
logger ( 'fetching conversation done. Found ' . count ( $items ) . ' items' );
if ( ! sizeof ( $items )) {
if ( count ( $item ) > 0 ) {
2015-06-25 05:30:14 +00:00
//$arr["app"] .= " (OStatus-NoConvFetched)";
2015-06-20 12:40:30 +00:00
$item_stored = item_store ( $item , true );
2015-06-21 06:32:03 +00:00
if ( $item_stored ) {
logger ( " Conversation " . $conversation_url . " couldn't be fetched. Item uri " . $item [ " uri " ] . " stored: " . $item_stored , LOGGER_DEBUG );
2015-06-20 12:40:30 +00:00
ostatus_store_conversation ( $item_id , $conversation_url );
2015-06-21 06:32:03 +00:00
}
2015-06-20 12:40:30 +00:00
return ( $item_stored );
} else
2015-06-20 23:36:23 +00:00
return ( - 3 );
2015-06-20 12:40:30 +00:00
}
$items = array_reverse ( $items );
2015-06-26 08:41:11 +00:00
$r = q ( " SELECT `nurl` FROM `contact` WHERE `uid` = %d AND `self` " , intval ( $uid ));
$importer = $r [ 0 ];
2015-06-20 12:40:30 +00:00
foreach ( $items as $single_conv ) {
2016-02-13 20:35:05 +00:00
// Update the gcontact table
ostatus_conv_fetch_actor ( $single_conv -> actor );
2015-06-20 12:40:30 +00:00
// Test - remove before flight
//$tempfile = tempnam(get_temppath(), "conversation");
//file_put_contents($tempfile, json_encode($single_conv));
2015-06-26 08:41:11 +00:00
$mention = false ;
2015-06-20 12:40:30 +00:00
if ( isset ( $single_conv -> object -> id ))
$single_conv -> id = $single_conv -> object -> id ;
$plink = ostatus_convert_href ( $single_conv -> id );
if ( isset ( $single_conv -> object -> url ))
$plink = ostatus_convert_href ( $single_conv -> object -> url );
if ( @! $single_conv -> id )
continue ;
logger ( " Got id " . $single_conv -> id , LOGGER_DEBUG );
if ( $first_id == " " ) {
$first_id = $single_conv -> id ;
// The first post of the conversation isn't our first post. There are three options:
// 1. Our conversation hasn't the "real" thread starter
// 2. This first post is a post inside our thread
// 3. This first post is a post inside another thread
if (( $first_id != $parent [ " uri " ]) AND ( $parent [ " uri " ] != " " )) {
2016-03-06 13:53:30 +00:00
// Do we only want to import threads that were started by our contacts?
if ( get_config ( 'system' , 'ostatus_full_threads' )) {
logger ( " Don't import uri " . $first_id . " because we don't follow this person. " , LOGGER_DEBUG );
continue ;
}
2015-06-20 12:40:30 +00:00
$new_parents = q ( " SELECT `id`, `parent`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `id` IN
( SELECT `parent` FROM `item`
WHERE `uid` = % d AND `uri` = '%s' AND `network` IN ( '%s' , '%s' )) LIMIT 1 " ,
intval ( $uid ), dbesc ( $first_id ), dbesc ( NETWORK_OSTATUS ), dbesc ( NETWORK_DFRN ));
if ( $new_parents ) {
if ( $new_parents [ 0 ][ " parent " ] == $parent [ " parent " ]) {
// Option 2: This post is already present inside our thread - but not as thread starter
logger ( " Option 2: uri present in our thread: " . $first_id , LOGGER_DEBUG );
$first_id = $parent [ " uri " ];
} else {
// Option 3: Not so good. We have mixed parents. We have to see how to clean this up.
// For now just take the new parent.
$parent = $new_parents [ 0 ];
$first_id = $parent [ " uri " ];
logger ( " Option 3: mixed parents for uri " . $first_id , LOGGER_DEBUG );
}
} else {
// Option 1: We hadn't got the real thread starter
// We have to clean up our existing messages.
$parent [ " id " ] = 0 ;
$parent [ " uri " ] = $first_id ;
logger ( " Option 1: we have a new parent: " . $first_id , LOGGER_DEBUG );
}
} elseif ( $parent [ " uri " ] == " " ) {
$parent [ " id " ] = 0 ;
$parent [ " uri " ] = $first_id ;
}
}
2015-06-24 20:31:38 +00:00
$parent_uri = $parent [ " uri " ];
// "context" only seems to exist on older servers
2015-06-20 12:40:30 +00:00
if ( isset ( $single_conv -> context -> inReplyTo -> id )) {
2015-06-24 20:31:38 +00:00
$parent_exists = q ( " SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1 " ,
intval ( $uid ), dbesc ( $single_conv -> context -> inReplyTo -> id ), dbesc ( NETWORK_OSTATUS ), dbesc ( NETWORK_DFRN ));
if ( $parent_exists )
$parent_uri = $single_conv -> context -> inReplyTo -> id ;
}
2015-06-20 12:40:30 +00:00
2015-06-24 20:31:38 +00:00
// This is the current way
if ( isset ( $single_conv -> object -> inReplyTo -> id )) {
2015-06-20 12:40:30 +00:00
$parent_exists = q ( " SELECT `id` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1 " ,
2015-06-24 20:31:38 +00:00
intval ( $uid ), dbesc ( $single_conv -> object -> inReplyTo -> id ), dbesc ( NETWORK_OSTATUS ), dbesc ( NETWORK_DFRN ));
if ( $parent_exists )
$parent_uri = $single_conv -> object -> inReplyTo -> id ;
}
2015-06-20 12:40:30 +00:00
$message_exists = q ( " SELECT `id`, `parent`, `uri` FROM `item` WHERE `uid` = %d AND `uri` = '%s' AND `network` IN ('%s','%s') LIMIT 1 " ,
intval ( $uid ), dbesc ( $single_conv -> id ),
dbesc ( NETWORK_OSTATUS ), dbesc ( NETWORK_DFRN ));
if ( $message_exists ) {
logger ( " Message " . $single_conv -> id . " already existed on the system " , LOGGER_DEBUG );
if ( $parent [ " id " ] != 0 ) {
$existing_message = $message_exists [ 0 ];
// We improved the way we fetch OStatus messages, this shouldn't happen very often now
2015-12-25 22:17:34 +00:00
/// @TODO We have to change the shadow copies as well. This way here is really ugly.
2015-06-20 12:40:30 +00:00
if ( $existing_message [ " parent " ] != $parent [ " id " ]) {
logger ( 'updating id ' . $existing_message [ " id " ] . ' with parent ' . $existing_message [ " parent " ] . ' to parent ' . $parent [ " id " ] . ' uri ' . $parent [ " uri " ] . ' thread ' . $parent_uri , LOGGER_DEBUG );
// Update the parent id of the selected item
$r = q ( " UPDATE `item` SET `parent` = %d, `parent-uri` = '%s' WHERE `id` = %d " ,
intval ( $parent [ " id " ]), dbesc ( $parent [ " uri " ]), intval ( $existing_message [ " id " ]));
// Update the parent uri in the thread - but only if it points to itself
$r = q ( " UPDATE `item` SET `thr-parent` = '%s' WHERE `id` = %d AND `uri` = `thr-parent` " ,
dbesc ( $parent_uri ), intval ( $existing_message [ " id " ]));
// try to change all items of the same parent
$r = q ( " UPDATE `item` SET `parent` = %d, `parent-uri` = '%s' WHERE `parent` = %d " ,
intval ( $parent [ " id " ]), dbesc ( $parent [ " uri " ]), intval ( $existing_message [ " parent " ]));
// Update the parent uri in the thread - but only if it points to itself
$r = q ( " UPDATE `item` SET `thr-parent` = '%s' WHERE (`parent` = %d) AND (`uri` = `thr-parent`) " ,
dbesc ( $parent [ " uri " ]), intval ( $existing_message [ " parent " ]));
// Now delete the thread
delete_thread ( $existing_message [ " parent " ]);
}
}
// The item we are having on the system is the one that we wanted to store via the item array
if ( isset ( $item [ " uri " ]) AND ( $item [ " uri " ] == $existing_message [ " uri " ])) {
$item = array ();
$item_stored = 0 ;
}
continue ;
}
2015-06-26 08:41:11 +00:00
if ( is_array ( $single_conv -> to ))
foreach ( $single_conv -> to AS $to )
if ( $importer [ " nurl " ] == normalise_link ( $to -> id ))
$mention = true ;
2015-06-20 12:40:30 +00:00
$actor = $single_conv -> actor -> id ;
if ( isset ( $single_conv -> actor -> url ))
$actor = $single_conv -> actor -> url ;
$contact = q ( " SELECT `id` FROM `contact` WHERE `uid` = %d AND `nurl` = '%s' AND `network` != '%s' " ,
$uid , normalise_link ( $actor ), NETWORK_STATUSNET );
if ( count ( $contact )) {
logger ( " Found contact for url " . $actor , LOGGER_DEBUG );
$contact_id = $contact [ 0 ][ " id " ];
} else {
logger ( " No contact found for url " . $actor , LOGGER_DEBUG );
// Adding a global contact
2015-12-25 22:17:34 +00:00
/// @TODO Use this data for the post
2015-06-20 12:40:30 +00:00
$global_contact_id = get_contact ( $actor , 0 );
logger ( " Global contact " . $global_contact_id . " found for url " . $actor , LOGGER_DEBUG );
$contact_id = $parent [ " contact-id " ];
}
$arr = array ();
$arr [ " network " ] = NETWORK_OSTATUS ;
$arr [ " uri " ] = $single_conv -> id ;
$arr [ " plink " ] = $plink ;
$arr [ " uid " ] = $uid ;
$arr [ " contact-id " ] = $contact_id ;
$arr [ " parent-uri " ] = $parent_uri ;
$arr [ " created " ] = $single_conv -> published ;
$arr [ " edited " ] = $single_conv -> published ;
$arr [ " owner-name " ] = $single_conv -> actor -> displayName ;
if ( $arr [ " owner-name " ] == '' )
$arr [ " owner-name " ] = $single_conv -> actor -> contact -> displayName ;
if ( $arr [ " owner-name " ] == '' )
$arr [ " owner-name " ] = $single_conv -> actor -> portablecontacts_net -> displayName ;
$arr [ " owner-link " ] = $actor ;
$arr [ " owner-avatar " ] = $single_conv -> actor -> image -> url ;
$arr [ " author-name " ] = $arr [ " owner-name " ];
$arr [ " author-link " ] = $actor ;
$arr [ " author-avatar " ] = $single_conv -> actor -> image -> url ;
$arr [ " body " ] = add_page_info_to_body ( html2bbcode ( $single_conv -> content ));
if ( isset ( $single_conv -> status_net -> notice_info -> source ))
$arr [ " app " ] = strip_tags ( $single_conv -> status_net -> notice_info -> source );
elseif ( isset ( $single_conv -> statusnet -> notice_info -> source ))
$arr [ " app " ] = strip_tags ( $single_conv -> statusnet -> notice_info -> source );
elseif ( isset ( $single_conv -> statusnet_notice_info -> source ))
$arr [ " app " ] = strip_tags ( $single_conv -> statusnet_notice_info -> source );
elseif ( isset ( $single_conv -> provider -> displayName ))
$arr [ " app " ] = $single_conv -> provider -> displayName ;
else
$arr [ " app " ] = " OStatus " ;
2015-06-25 05:30:14 +00:00
//$arr["app"] .= " (Conversation)";
2015-06-20 12:40:30 +00:00
$arr [ " object " ] = json_encode ( $single_conv );
$arr [ " verb " ] = $parent [ " verb " ];
$arr [ " visible " ] = $parent [ " visible " ];
$arr [ " location " ] = $single_conv -> location -> displayName ;
$arr [ " coord " ] = trim ( $single_conv -> location -> lat . " " . $single_conv -> location -> lon );
// Is it a reshared item?
2015-06-20 15:26:47 +00:00
if ( isset ( $single_conv -> verb ) AND ( $single_conv -> verb == " share " ) AND isset ( $single_conv -> object )) {
if ( is_array ( $single_conv -> object ))
$single_conv -> object = $single_conv -> object [ 0 ];
2015-06-20 12:40:30 +00:00
logger ( " Found reshared item " . $single_conv -> object -> id );
// $single_conv->object->context->conversation;
2015-06-20 15:26:47 +00:00
if ( isset ( $single_conv -> object -> object -> id ))
$arr [ " uri " ] = $single_conv -> object -> object -> id ;
else
$arr [ " uri " ] = $single_conv -> object -> id ;
if ( isset ( $single_conv -> object -> object -> url ))
$plink = ostatus_convert_href ( $single_conv -> object -> object -> url );
else
$plink = ostatus_convert_href ( $single_conv -> object -> url );
if ( isset ( $single_conv -> object -> object -> content ))
$arr [ " body " ] = add_page_info_to_body ( html2bbcode ( $single_conv -> object -> object -> content ));
else
$arr [ " body " ] = add_page_info_to_body ( html2bbcode ( $single_conv -> object -> content ));
2015-06-20 12:40:30 +00:00
$arr [ " plink " ] = $plink ;
2015-06-20 15:26:47 +00:00
2015-06-20 12:40:30 +00:00
$arr [ " created " ] = $single_conv -> object -> published ;
$arr [ " edited " ] = $single_conv -> object -> published ;
$arr [ " author-name " ] = $single_conv -> object -> actor -> displayName ;
if ( $arr [ " owner-name " ] == '' )
$arr [ " author-name " ] = $single_conv -> object -> actor -> contact -> displayName ;
$arr [ " author-link " ] = $single_conv -> object -> actor -> url ;
$arr [ " author-avatar " ] = $single_conv -> object -> actor -> image -> url ;
$arr [ " app " ] = $single_conv -> object -> provider -> displayName . " # " ;
//$arr["verb"] = $single_conv->object->verb;
$arr [ " location " ] = $single_conv -> object -> location -> displayName ;
$arr [ " coord " ] = trim ( $single_conv -> object -> location -> lat . " " . $single_conv -> object -> location -> lon );
}
if ( $arr [ " location " ] == " " )
unset ( $arr [ " location " ]);
if ( $arr [ " coord " ] == " " )
unset ( $arr [ " coord " ]);
// Copy fields from given item array
2015-06-20 23:36:23 +00:00
if ( isset ( $item [ " uri " ]) AND (( $item [ " uri " ] == $arr [ " uri " ]) OR ( $item [ " uri " ] == $single_conv -> id ))) {
2015-06-20 12:40:30 +00:00
$copy_fields = array ( " owner-name " , " owner-link " , " owner-avatar " , " author-name " , " author-link " , " author-avatar " ,
2015-06-21 20:02:44 +00:00
" gravity " , " body " , " object-type " , " object " , " verb " , " created " , " edited " , " coord " , " tag " ,
" title " , " attach " , " app " , " type " , " location " , " contact-id " , " uri " );
2015-06-20 12:40:30 +00:00
foreach ( $copy_fields AS $field )
if ( isset ( $item [ $field ]))
$arr [ $field ] = $item [ $field ];
2015-06-25 05:30:14 +00:00
//$arr["app"] .= " (OStatus)";
2015-06-20 12:40:30 +00:00
}
$newitem = item_store ( $arr );
if ( ! $newitem ) {
logger ( " Item wasn't stored " . print_r ( $arr , true ), LOGGER_DEBUG );
continue ;
}
if ( isset ( $item [ " uri " ]) AND ( $item [ " uri " ] == $arr [ " uri " ])) {
$item = array ();
$item_stored = $newitem ;
}
logger ( 'Stored new item ' . $plink . ' for parent ' . $arr [ " parent-uri " ] . ' under id ' . $newitem , LOGGER_DEBUG );
// Add the conversation entry (but don't fetch the whole conversation)
ostatus_store_conversation ( $newitem , $conversation_url );
// If the newly created item is the top item then change the parent settings of the thread
// This shouldn't happen anymore. This is supposed to be absolote.
if ( $arr [ " uri " ] == $first_id ) {
logger ( 'setting new parent to id ' . $newitem );
$new_parents = q ( " SELECT `id`, `uri`, `contact-id`, `type`, `verb`, `visible` FROM `item` WHERE `uid` = %d AND `id` = %d LIMIT 1 " ,
intval ( $uid ), intval ( $newitem ));
if ( $new_parents )
$parent = $new_parents [ 0 ];
}
}
2015-06-20 23:36:23 +00:00
if (( $item_stored < 0 ) AND ( count ( $item ) > 0 )) {
2015-06-25 05:30:14 +00:00
//$arr["app"] .= " (OStatus-NoConvFound)";
2015-06-20 23:36:23 +00:00
$item_stored = item_store ( $item , true );
if ( $item_stored ) {
logger ( " Uri " . $item [ " uri " ] . " wasn't found in conversation " . $conversation_url , LOGGER_DEBUG );
ostatus_store_conversation ( $item_stored , $conversation_url );
}
}
2015-06-20 12:40:30 +00:00
return ( $item_stored );
}
function ostatus_store_conversation ( $itemid , $conversation_url ) {
global $a ;
$conversation_url = ostatus_convert_href ( $conversation_url );
$messages = q ( " SELECT `uid`, `parent`, `created`, `received`, `guid` FROM `item` WHERE `id` = %d LIMIT 1 " , intval ( $itemid ));
if ( ! $messages )
return ;
$message = $messages [ 0 ];
// Store conversation url if not done before
$conversation = q ( " SELECT `url` FROM `term` WHERE `uid` = %d AND `oid` = %d AND `otype` = %d AND `type` = %d " ,
intval ( $message [ " uid " ]), intval ( $itemid ), intval ( TERM_OBJ_POST ), intval ( TERM_CONVERSATION ));
if ( ! $conversation ) {
$r = q ( " INSERT INTO `term` (`uid`, `oid`, `otype`, `type`, `term`, `url`, `created`, `received`, `guid`) VALUES (%d, %d, %d, %d, '%s', '%s', '%s', '%s', '%s') " ,
intval ( $message [ " uid " ]), intval ( $itemid ), intval ( TERM_OBJ_POST ), intval ( TERM_CONVERSATION ),
dbesc ( $message [ " created " ]), dbesc ( $conversation_url ), dbesc ( $message [ " created " ]), dbesc ( $message [ " received " ]), dbesc ( $message [ " guid " ]));
logger ( 'Storing conversation url ' . $conversation_url . ' for id ' . $itemid );
}
}
2015-11-23 17:44:47 +00:00
2015-12-10 00:10:54 +00:00
function get_reshared_guid ( $item ) {
2015-12-13 23:42:36 +00:00
$body = trim ( $item [ " body " ]);
2015-12-10 00:10:54 +00:00
2015-12-13 23:42:36 +00:00
// Skip if it isn't a pure repeated messages
// Does it start with a share?
if ( strpos ( $body , " [share " ) > 0 )
return ( " " );
2015-12-10 00:10:54 +00:00
2015-12-13 23:42:36 +00:00
// Does it end with a share?
if ( strlen ( $body ) > ( strrpos ( $body , " [/share] " ) + 8 ))
return ( " " );
2015-12-10 00:10:54 +00:00
2015-12-13 23:42:36 +00:00
$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 );
2015-12-10 00:10:54 +00:00
2015-12-13 23:42:36 +00:00
$guid = " " ;
preg_match ( " /guid='(.*?)'/ism " , $attributes , $matches );
if ( $matches [ 1 ] != " " )
$guid = $matches [ 1 ];
2015-12-10 00:10:54 +00:00
2015-12-13 23:42:36 +00:00
preg_match ( '/guid="(.*?)"/ism' , $attributes , $matches );
if ( $matches [ 1 ] != " " )
$guid = $matches [ 1 ];
2015-12-10 00:10:54 +00:00
return $guid ;
}
2016-01-23 01:44:30 +00:00
function xml_create_element ( $doc , $element , $value = " " , $attributes = array ()) {
2015-11-23 22:49:14 +00:00
$element = $doc -> createElement ( $element , xmlify ( $value ));
2015-11-23 17:44:47 +00:00
foreach ( $attributes AS $key => $value ) {
$attribute = $doc -> createAttribute ( $key );
2015-11-23 22:49:14 +00:00
$attribute -> value = xmlify ( $value );
2015-11-23 17:44:47 +00:00
$element -> appendChild ( $attribute );
}
2016-01-23 01:44:30 +00:00
return $element ;
}
2015-11-23 17:44:47 +00:00
2016-01-23 01:44:30 +00:00
function xml_add_element ( $doc , $parent , $element , $value = " " , $attributes = array ()) {
$element = xml_create_element ( $doc , $element , $value , $attributes );
2015-11-23 17:44:47 +00:00
$parent -> appendChild ( $element );
}
2015-12-04 04:57:33 +00:00
function ostatus_format_picture_post ( $body ) {
$siteinfo = get_attached_data ( $body );
2015-12-04 05:50:23 +00:00
if (( $siteinfo [ " type " ] == " photo " )) {
if ( isset ( $siteinfo [ " preview " ]))
$preview = $siteinfo [ " preview " ];
else
$preview = $siteinfo [ " image " ];
// Is it a remote picture? Then make a smaller preview here
$preview = proxy_url ( $preview , false , PROXY_SIZE_SMALL );
// Is it a local picture? Then make it smaller here
$preview = str_replace ( array ( " -0.jpg " , " -0.png " ), array ( " -2.jpg " , " -2.png " ), $preview );
$preview = str_replace ( array ( " -1.jpg " , " -1.png " ), array ( " -2.jpg " , " -2.png " ), $preview );
if ( isset ( $siteinfo [ " url " ]))
$url = $siteinfo [ " url " ];
else
$url = $siteinfo [ " image " ];
$body = trim ( $siteinfo [ " text " ]) . " [url] " . $url . " [/url] \n [img] " . $preview . " [/img] " ;
2015-12-04 04:57:33 +00:00
}
return $body ;
}
2015-11-23 17:44:47 +00:00
function ostatus_add_header ( $doc , $owner ) {
$a = get_app ();
2016-01-29 22:14:01 +00:00
$root = $doc -> createElementNS ( NAMESPACE_ATOM1 , 'feed' );
2015-11-23 17:44:47 +00:00
$doc -> appendChild ( $root );
2016-01-29 22:14:01 +00:00
$root -> setAttribute ( " xmlns:thr " , NAMESPACE_THREAD );
$root -> setAttribute ( " xmlns:georss " , NAMESPACE_GEORSS );
$root -> setAttribute ( " xmlns:activity " , NAMESPACE_ACTIVITY );
$root -> setAttribute ( " xmlns:media " , NAMESPACE_MEDIA );
$root -> setAttribute ( " xmlns:poco " , NAMESPACE_POCO );
$root -> setAttribute ( " xmlns:ostatus " , NAMESPACE_OSTATUS );
$root -> setAttribute ( " xmlns:statusnet " , NAMESPACE_STATUSNET );
2015-11-23 17:44:47 +00:00
$attributes = array ( " uri " => " https://friendi.ca " , " version " => FRIENDICA_VERSION . " - " . DB_UPDATE_VERSION );
xml_add_element ( $doc , $root , " generator " , FRIENDICA_PLATFORM , $attributes );
xml_add_element ( $doc , $root , " id " , $a -> get_baseurl () . " /profile/ " . $owner [ " nick " ]);
2015-12-20 09:44:03 +00:00
xml_add_element ( $doc , $root , " title " , sprintf ( " %s timeline " , $owner [ " name " ]));
xml_add_element ( $doc , $root , " subtitle " , sprintf ( " Updates from %s on %s " , $owner [ " name " ], $a -> config [ " sitename " ]));
xml_add_element ( $doc , $root , " logo " , $owner [ " photo " ]);
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $root , " updated " , datetime_convert ( " UTC " , " UTC " , " now " , ATOM_TIME ));
2015-12-20 09:44:03 +00:00
$author = ostatus_add_author ( $doc , $owner );
2015-11-23 17:44:47 +00:00
$root -> appendChild ( $author );
$attributes = array ( " href " => $owner [ " url " ], " rel " => " alternate " , " type " => " text/html " );
xml_add_element ( $doc , $root , " link " , " " , $attributes );
2015-12-25 22:17:34 +00:00
/// @TODO We have to find out what this is
/// $attributes = array("href" => $a->get_baseurl()."/sup",
/// "rel" => "http://api.friendfeed.com/2008/03#sup",
/// "type" => "application/json");
/// xml_add_element($doc, $root, "link", "", $attributes);
2015-11-23 17:44:47 +00:00
ostatus_hublinks ( $doc , $root );
$attributes = array ( " href " => $a -> get_baseurl () . " /salmon/ " . $owner [ " nick " ], " rel " => " salmon " );
xml_add_element ( $doc , $root , " link " , " " , $attributes );
$attributes = array ( " href " => $a -> get_baseurl () . " /salmon/ " . $owner [ " nick " ], " rel " => " http://salmon-protocol.org/ns/salmon-replies " );
xml_add_element ( $doc , $root , " link " , " " , $attributes );
$attributes = array ( " href " => $a -> get_baseurl () . " /salmon/ " . $owner [ " nick " ], " rel " => " http://salmon-protocol.org/ns/salmon-mention " );
xml_add_element ( $doc , $root , " link " , " " , $attributes );
$attributes = array ( " href " => $a -> get_baseurl () . " /api/statuses/user_timeline/ " . $owner [ " nick " ] . " .atom " ,
" rel " => " self " , " type " => " application/atom+xml " );
xml_add_element ( $doc , $root , " link " , " " , $attributes );
return $root ;
}
function ostatus_hublinks ( $doc , $root ) {
$a = get_app ();
$hub = get_config ( 'system' , 'huburl' );
$hubxml = '' ;
if ( strlen ( $hub )) {
$hubs = explode ( ',' , $hub );
if ( count ( $hubs )) {
foreach ( $hubs as $h ) {
$h = trim ( $h );
if ( ! strlen ( $h ))
continue ;
if ( $h === '[internal]' )
$h = $a -> get_baseurl () . '/pubsubhubbub' ;
xml_add_element ( $doc , $root , " link " , " " , array ( " href " => $h , " rel " => " hub " ));
}
}
}
}
function ostatus_get_attachment ( $doc , $root , $item ) {
$o = " " ;
$siteinfo = get_attached_data ( $item [ " body " ]);
switch ( $siteinfo [ " type " ]) {
case 'link' :
$attributes = array ( " rel " => " enclosure " ,
" href " => $siteinfo [ " url " ],
" type " => " text/html; charset=UTF-8 " ,
" length " => " " ,
" title " => $siteinfo [ " title " ]);
xml_add_element ( $doc , $root , " link " , " " , $attributes );
break ;
case 'photo' :
$imgdata = get_photo_info ( $siteinfo [ " image " ]);
$attributes = array ( " rel " => " enclosure " ,
" href " => $siteinfo [ " image " ],
" type " => $imgdata [ " mime " ],
" length " => intval ( $imgdata [ " size " ]));
xml_add_element ( $doc , $root , " link " , " " , $attributes );
break ;
case 'video' :
$attributes = array ( " rel " => " enclosure " ,
" href " => $siteinfo [ " url " ],
" type " => " text/html; charset=UTF-8 " ,
" length " => " " ,
" title " => $siteinfo [ " title " ]);
xml_add_element ( $doc , $root , " link " , " " , $attributes );
break ;
default :
break ;
}
2015-11-27 22:16:54 +00:00
if (( $siteinfo [ " type " ] != " photo " ) AND isset ( $siteinfo [ " image " ])) {
$photodata = get_photo_info ( $siteinfo [ " image " ]);
$attributes = array ( " rel " => " preview " , " href " => $siteinfo [ " image " ], " media:width " => $photodata [ 0 ], " media:height " => $photodata [ 1 ]);
xml_add_element ( $doc , $root , " link " , " " , $attributes );
}
2015-11-23 17:44:47 +00:00
$arr = explode ( '[/attach],' , $item [ 'attach' ]);
if ( count ( $arr )) {
foreach ( $arr as $r ) {
$matches = false ;
$cnt = preg_match ( '|\[attach\]href=\"(.*?)\" length=\"(.*?)\" type=\"(.*?)\" title=\"(.*?)\"|' , $r , $matches );
if ( $cnt ) {
$attributes = array ( " rel " => " enclosure " ,
" href " => $matches [ 1 ],
" type " => $matches [ 3 ]);
if ( intval ( $matches [ 2 ]))
$attributes [ " length " ] = intval ( $matches [ 2 ]);
if ( trim ( $matches [ 4 ]) != " " )
$attributes [ " title " ] = trim ( $matches [ 4 ]);
xml_add_element ( $doc , $root , " link " , " " , $attributes );
}
}
}
}
2015-12-20 09:44:03 +00:00
function ostatus_add_author ( $doc , $owner ) {
2015-11-23 17:44:47 +00:00
$a = get_app ();
2015-12-20 09:44:03 +00:00
$r = q ( " SELECT `homepage` FROM `profile` WHERE `uid` = %d AND `is-default` LIMIT 1 " , intval ( $owner [ " uid " ]));
if ( $r )
$profile = $r [ 0 ];
2015-11-23 17:44:47 +00:00
$author = $doc -> createElement ( " author " );
xml_add_element ( $doc , $author , " activity:object-type " , ACTIVITY_OBJ_PERSON );
xml_add_element ( $doc , $author , " uri " , $owner [ " url " ]);
2015-12-12 09:41:42 +00:00
xml_add_element ( $doc , $author , " name " , $owner [ " name " ]);
2015-11-23 17:44:47 +00:00
$attributes = array ( " rel " => " alternate " , " type " => " text/html " , " href " => $owner [ " url " ]);
xml_add_element ( $doc , $author , " link " , " " , $attributes );
$attributes = array (
" rel " => " avatar " ,
" type " => " image/jpeg " , // To-Do?
" media:width " => 175 ,
" media:height " => 175 ,
2015-12-12 09:41:42 +00:00
" href " => $owner [ " photo " ]);
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $author , " link " , " " , $attributes );
2015-12-12 09:41:42 +00:00
if ( isset ( $owner [ " thumb " ])) {
$attributes = array (
" rel " => " avatar " ,
" type " => " image/jpeg " , // To-Do?
" media:width " => 80 ,
" media:height " => 80 ,
" href " => $owner [ " thumb " ]);
xml_add_element ( $doc , $author , " link " , " " , $attributes );
}
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $author , " poco:preferredUsername " , $owner [ " nick " ]);
2015-12-12 09:41:42 +00:00
xml_add_element ( $doc , $author , " poco:displayName " , $owner [ " name " ]);
xml_add_element ( $doc , $author , " poco:note " , $owner [ " about " ]);
2015-11-23 17:44:47 +00:00
if ( trim ( $owner [ " location " ]) != " " ) {
$element = $doc -> createElement ( " poco:address " );
xml_add_element ( $doc , $element , " poco:formatted " , $owner [ " location " ]);
$author -> appendChild ( $element );
}
if ( trim ( $profile [ " homepage " ]) != " " ) {
$urls = $doc -> createElement ( " poco:urls " );
xml_add_element ( $doc , $urls , " poco:type " , " homepage " );
xml_add_element ( $doc , $urls , " poco:value " , $profile [ " homepage " ]);
xml_add_element ( $doc , $urls , " poco:primary " , " true " );
$author -> appendChild ( $urls );
}
2015-12-12 09:41:42 +00:00
if ( count ( $profile )) {
xml_add_element ( $doc , $author , " followers " , " " , array ( " url " => $a -> get_baseurl () . " /viewcontacts/ " . $owner [ " nick " ]));
xml_add_element ( $doc , $author , " statusnet:profile_info " , " " , array ( " local_id " => $owner [ " uid " ]));
}
2015-11-23 17:44:47 +00:00
return $author ;
}
2015-12-25 22:17:34 +00:00
/**
* @ TODO Picture attachments should look like this :
* < a href = " https://status.pirati.ca/attachment/572819 " title = " https://status.pirati.ca/file/heluecht-20151202T222602-rd3u49p.gif "
* class = " attachment thumbnail " id = " attachment-572819 " rel = " nofollow external " > https :// status . pirati . ca / attachment / 572819 </ a >
*
2015-12-03 13:38:04 +00:00
*/
2015-12-07 20:52:42 +00:00
function ostatus_entry ( $doc , $item , $owner , $toplevel = false , $repeat = false ) {
2015-11-23 17:44:47 +00:00
$a = get_app ();
2016-02-05 20:31:11 +00:00
if (( $item [ " id " ] != $item [ " parent " ]) AND ( normalise_link ( $item [ " author-link " ]) != normalise_link ( $owner [ " url " ]))) {
logger ( " OStatus entry is from author " . $owner [ " url " ] . " - not from " . $item [ " author-link " ] . " . Quitting. " , LOGGER_DEBUG );
}
2015-12-12 09:41:42 +00:00
$is_repeat = false ;
/* if ( ! $repeat ) {
$repeated_guid = get_reshared_guid ( $item );
if ( $repeated_guid != " " ) {
$r = q ( " SELECT * FROM `item` WHERE `uid` = %d AND `guid` = '%s' LIMIT 1 " ,
intval ( $owner [ " uid " ]), dbesc ( $repeated_guid ));
if ( $r ) {
$repeated_item = $r [ 0 ];
$is_repeat = true ;
}
}
}
*/
2015-12-07 22:06:28 +00:00
if ( ! $toplevel AND ! $repeat ) {
2015-11-23 17:44:47 +00:00
$entry = $doc -> createElement ( " entry " );
$title = sprintf ( " New note by %s " , $owner [ " nick " ]);
2015-12-10 17:16:16 +00:00
} elseif ( ! $toplevel AND $repeat ) {
$entry = $doc -> createElement ( " activity:object " );
$title = sprintf ( " New note by %s " , $owner [ " nick " ]);
2015-11-23 17:44:47 +00:00
} else {
2016-01-29 22:14:01 +00:00
$entry = $doc -> createElementNS ( NAMESPACE_ATOM1 , " entry " );
$entry -> setAttribute ( " xmlns:thr " , NAMESPACE_THREAD );
$entry -> setAttribute ( " xmlns:georss " , NAMESPACE_GEORSS );
$entry -> setAttribute ( " xmlns:activity " , NAMESPACE_ACTIVITY );
$entry -> setAttribute ( " xmlns:media " , NAMESPACE_MEDIA );
$entry -> setAttribute ( " xmlns:poco " , NAMESPACE_POCO );
$entry -> setAttribute ( " xmlns:ostatus " , NAMESPACE_OSTATUS );
$entry -> setAttribute ( " xmlns:statusnet " , NAMESPACE_STATUSNET );
2015-11-23 17:44:47 +00:00
2015-12-20 09:44:03 +00:00
$author = ostatus_add_author ( $doc , $owner );
2015-11-23 17:44:47 +00:00
$entry -> appendChild ( $author );
$title = sprintf ( " New comment by %s " , $owner [ " nick " ]);
}
2015-11-24 20:03:06 +00:00
// To use the object-type "bookmark" we have to implement these elements:
//
// <activity:object-type>http://activitystrea.ms/schema/1.0/bookmark</activity:object-type>
// <title>Historic Rocket Landing</title>
// <summary>Nur ein Testbeitrag.</summary>
// <link rel="related" href="https://www.youtube.com/watch?v=9pillaOxGCo"/>
// <link rel="preview" href="https://pirati.cc/file/thumb-4526-450x338-b48c8055f0c2fed0c3f67adc234c4b99484a90c42ed3cac73dc1081a4d0a7bc1.jpg.jpg" media:width="450" media:height="338"/>
//
// But: it seems as if it doesn't federate well between the GS servers
// So we just set it to "note" to be sure that it reaches their target systems
2015-12-10 17:16:16 +00:00
if ( ! $repeat )
2015-12-07 20:52:42 +00:00
xml_add_element ( $doc , $entry , " activity:object-type " , ACTIVITY_OBJ_NOTE );
2015-12-10 17:16:16 +00:00
else
xml_add_element ( $doc , $entry , " activity:object-type " , NAMESPACE_ACTIVITY_SCHEMA . 'activity' );
2015-12-07 20:52:42 +00:00
2015-11-24 20:03:06 +00:00
xml_add_element ( $doc , $entry , " id " , $item [ " uri " ]);
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $entry , " title " , $title );
if ( $item [ 'allow_cid' ] || $item [ 'allow_gid' ] || $item [ 'deny_cid' ] || $item [ 'deny_gid' ])
$body = fix_private_photos ( $item [ 'body' ], $owner [ 'uid' ], $item , 0 );
else
$body = $item [ 'body' ];
2015-12-04 04:57:33 +00:00
$body = ostatus_format_picture_post ( $body );
2015-11-23 17:44:47 +00:00
if ( $item [ 'title' ] != " " )
$body = " [b] " . $item [ 'title' ] . " [/b] \n \n " . $body ;
2015-11-28 06:37:56 +00:00
//$body = bb_remove_share_information($body);
2015-11-23 17:44:47 +00:00
$body = bbcode ( $body , false , false , 7 );
2015-11-23 22:49:14 +00:00
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $entry , " content " , $body , array ( " type " => " html " ));
xml_add_element ( $doc , $entry , " link " , " " , array ( " rel " => " alternate " , " type " => " text/html " ,
" href " => $a -> get_baseurl () . " /display/ " . $item [ " guid " ]));
xml_add_element ( $doc , $entry , " status_net " , " " , array ( " notice_id " => $item [ " id " ]));
2015-12-07 20:52:42 +00:00
2015-12-10 17:16:16 +00:00
if ( ! $is_repeat )
2015-12-07 20:52:42 +00:00
xml_add_element ( $doc , $entry , " activity:verb " , construct_verb ( $item ));
2015-12-10 17:16:16 +00:00
else
xml_add_element ( $doc , $entry , " activity:verb " , ACTIVITY_SHARE );
2015-12-07 20:52:42 +00:00
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $entry , " published " , datetime_convert ( " UTC " , " UTC " , $item [ " created " ] . " +00:00 " , ATOM_TIME ));
xml_add_element ( $doc , $entry , " updated " , datetime_convert ( " UTC " , " UTC " , $item [ " edited " ] . " +00:00 " , ATOM_TIME ));
2015-12-10 17:16:16 +00:00
if ( $is_repeat ) {
2015-12-07 20:52:42 +00:00
$repeated_owner = array ();
$repeated_owner [ " name " ] = $repeated_item [ " author-name " ];
$repeated_owner [ " url " ] = $repeated_item [ " author-link " ];
2015-12-12 09:41:42 +00:00
$repeated_owner [ " photo " ] = $repeated_item [ " author-avatar " ];
$repeated_owner [ " nick " ] = $repeated_owner [ " name " ];
2015-12-07 20:52:42 +00:00
$repeated_owner [ " location " ] = " " ;
$repeated_owner [ " about " ] = " " ;
$repeated_owner [ " uid " ] = 0 ;
2016-01-06 21:23:12 +00:00
// Fetch the missing data from the global contacts
$r = q ( " SELECT * FROM `gcontact` WHERE `nurl` = '%s' " , normalise_link ( $repeated_item [ " author-link " ]));
2015-12-07 20:52:42 +00:00
if ( $r ) {
2016-01-06 21:23:12 +00:00
if ( $r [ 0 ][ " nick " ] != " " )
$repeated_owner [ " nick " ] = $r [ 0 ][ " nick " ];
2015-12-07 20:52:42 +00:00
$repeated_owner [ " location " ] = $r [ 0 ][ " location " ];
$repeated_owner [ " about " ] = $r [ 0 ][ " about " ];
}
$entry_repeat = ostatus_entry ( $doc , $repeated_item , $repeated_owner , false , true );
$entry -> appendChild ( $entry_repeat );
} elseif ( $repeat ) {
2015-12-12 09:41:42 +00:00
$author = ostatus_add_author ( $doc , $owner );
2015-12-07 20:52:42 +00:00
$entry -> appendChild ( $author );
2015-12-10 17:16:16 +00:00
}
2015-12-07 20:52:42 +00:00
2015-12-13 13:10:18 +00:00
$mentioned = array ();
2015-11-23 17:44:47 +00:00
if (( $item [ 'parent' ] != $item [ 'id' ]) || ( $item [ 'parent-uri' ] !== $item [ 'uri' ]) || (( $item [ 'thr-parent' ] !== '' ) && ( $item [ 'thr-parent' ] !== $item [ 'uri' ]))) {
2015-12-07 20:52:42 +00:00
$parent = q ( " SELECT `guid`, `author-link`, `owner-link` FROM `item` WHERE `id` = %d " , intval ( $item [ " parent " ]));
2015-11-23 17:44:47 +00:00
$parent_item = (( $item [ 'thr-parent' ]) ? $item [ 'thr-parent' ] : $item [ 'parent-uri' ]);
$attributes = array (
" ref " => $parent_item ,
" type " => " text/html " ,
" href " => $a -> get_baseurl () . " /display/ " . $parent [ 0 ][ " guid " ]);
xml_add_element ( $doc , $entry , " thr:in-reply-to " , " " , $attributes );
$attributes = array (
" rel " => " related " ,
" href " => $a -> get_baseurl () . " /display/ " . $parent [ 0 ][ " guid " ]);
xml_add_element ( $doc , $entry , " link " , " " , $attributes );
2015-12-13 13:10:18 +00:00
$mentioned [ $parent [ 0 ][ " author-link " ]] = $parent [ 0 ][ " author-link " ];
$mentioned [ $parent [ 0 ][ " owner-link " ]] = $parent [ 0 ][ " owner-link " ];
$thrparent = q ( " SELECT `guid`, `author-link`, `owner-link` FROM `item` WHERE `uid` = %d AND `uri` = '%s' " ,
intval ( $owner [ " uid " ]),
dbesc ( $parent_item ));
if ( $thrparent ) {
$mentioned [ $thrparent [ 0 ][ " author-link " ]] = $thrparent [ 0 ][ " author-link " ];
$mentioned [ $thrparent [ 0 ][ " owner-link " ]] = $thrparent [ 0 ][ " owner-link " ];
}
}
2015-11-23 17:44:47 +00:00
xml_add_element ( $doc , $entry , " link " , " " , array ( " rel " => " ostatus:conversation " ,
" href " => $a -> get_baseurl () . " /display/ " . $owner [ " nick " ] . " / " . $item [ " parent " ]));
xml_add_element ( $doc , $entry , " ostatus:conversation " , $a -> get_baseurl () . " /display/ " . $owner [ " nick " ] . " / " . $item [ " parent " ]);
$tags = item_getfeedtags ( $item );
if ( count ( $tags ))
foreach ( $tags as $t )
if ( $t [ 0 ] == " @ " )
2015-12-13 13:10:18 +00:00
$mentioned [ $t [ 1 ]] = $t [ 1 ];
// Make sure that mentions are accepted (GNU Social has problems with mixing HTTP and HTTPS)
$newmentions = array ();
foreach ( $mentioned AS $mention ) {
$newmentions [ str_replace ( " http:// " , " https:// " , $mention )] = str_replace ( " http:// " , " https:// " , $mention );
$newmentions [ str_replace ( " https:// " , " http:// " , $mention )] = str_replace ( " https:// " , " http:// " , $mention );
}
$mentioned = $newmentions ;
foreach ( $mentioned AS $mention ) {
$r = q ( " SELECT `forum`, `prv` FROM `contact` WHERE `uid` = %d AND `nurl` = '%s' " ,
intval ( $owner [ " uid " ]),
dbesc ( normalise_link ( $mention )));
if ( $r [ 0 ][ " forum " ] OR $r [ 0 ][ " prv " ])
xml_add_element ( $doc , $entry , " link " , " " , array ( " rel " => " mentioned " ,
" ostatus:object-type " => ACTIVITY_OBJ_GROUP ,
" href " => $mention ));
else
xml_add_element ( $doc , $entry , " link " , " " , array ( " rel " => " mentioned " ,
2015-11-23 17:44:47 +00:00
" ostatus:object-type " => ACTIVITY_OBJ_PERSON ,
2015-12-13 13:10:18 +00:00
" href " => $mention ));
}
2015-11-23 17:44:47 +00:00
if ( ! $item [ " private " ])
xml_add_element ( $doc , $entry , " link " , " " , array ( " rel " => " mentioned " ,
" ostatus:object-type " => " http://activitystrea.ms/schema/1.0/collection " ,
" href " => " http://activityschema.org/collection/public " ));
if ( count ( $tags ))
foreach ( $tags as $t )
if ( $t [ 0 ] != " @ " )
xml_add_element ( $doc , $entry , " category " , " " , array ( " term " => $t [ 2 ]));
ostatus_get_attachment ( $doc , $entry , $item );
2015-12-25 22:17:34 +00:00
/// @TODO
/// The API call has yet to be implemented
2015-11-27 07:09:19 +00:00
//$attributes = array("href" => $a->get_baseurl()."/api/statuses/show/".$item["id"].".atom",
// "rel" => "self", "type" => "application/atom+xml");
//xml_add_element($doc, $entry, "link", "", $attributes);
2015-11-23 17:44:47 +00:00
2015-11-27 07:09:19 +00:00
//$attributes = array("href" => $a->get_baseurl()."/api/statuses/show/".$item["id"].".atom",
// "rel" => "edit", "type" => "application/atom+xml");
//xml_add_element($doc, $entry, "link", "", $attributes);
2015-11-23 17:44:47 +00:00
$app = $item [ " app " ];
if ( $app == " " )
$app = " web " ;
2015-12-07 20:52:42 +00:00
$attributes = array ( " local_id " => $item [ " id " ], " source " => $app );
2015-12-10 17:16:16 +00:00
if ( $is_repeat )
$attributes [ " repeat_of " ] = $repeated_item [ " id " ];
2015-12-07 20:52:42 +00:00
xml_add_element ( $doc , $entry , " statusnet:notice_info " , " " , $attributes );
2015-11-23 17:44:47 +00:00
return $entry ;
}
function ostatus_feed ( & $a , $owner_nick , $last_update ) {
2015-11-23 22:49:14 +00:00
$r = q ( " SELECT `contact`.*, `user`.`nickname`, `user`.`timezone`, `user`.`page-flags`
2015-11-23 17:44:47 +00:00
FROM `contact` INNER JOIN `user` ON `user` . `uid` = `contact` . `uid`
WHERE `contact` . `self` AND `user` . `nickname` = '%s' LIMIT 1 " ,
dbesc ( $owner_nick ));
if ( ! $r )
return ;
$owner = $r [ 0 ];
if ( ! strlen ( $last_update ))
$last_update = 'now -30 days' ;
$check_date = datetime_convert ( 'UTC' , 'UTC' , $last_update , 'Y-m-d H:i:s' );
$items = q ( " SELECT STRAIGHT_JOIN `item`.*, `item`.`id` AS `item_id` FROM `item`
INNER JOIN `thread` ON `thread` . `iid` = `item` . `parent`
LEFT JOIN `item` AS `thritem` ON `thritem` . `uri` = `item` . `thr-parent` AND `thritem` . `uid` = `item` . `uid`
WHERE `item` . `uid` = % d AND `item` . `received` > '%s' AND NOT `item` . `private` AND NOT `item` . `deleted`
AND `item` . `allow_cid` = '' AND `item` . `allow_gid` = '' AND `item` . `deny_cid` = '' AND `item` . `deny_gid` = ''
AND (( `item` . `wall` AND ( `item` . `parent` = `item` . `id` ))
2015-12-07 20:52:42 +00:00
OR ( `item` . `network` = '%s' AND (( `thread` . `network` IN ( '%s' , '%s' )) OR ( `thritem` . `network` IN ( '%s' , '%s' )))) AND `thread` . `mention` )
AND (( `item` . `owner-link` IN ( '%s' , '%s' ) AND ( `item` . `parent` = `item` . `id` ))
OR ( `item` . `author-link` IN ( '%s' , '%s' )))
2015-11-23 17:44:47 +00:00
ORDER BY `item` . `received` DESC
LIMIT 0 , 300 " ,
2015-12-07 20:52:42 +00:00
intval ( $owner [ " uid " ]), dbesc ( $check_date ), dbesc ( NETWORK_DFRN ),
//dbesc(NETWORK_OSTATUS), dbesc(NETWORK_OSTATUS),
//dbesc(NETWORK_OSTATUS), dbesc(NETWORK_OSTATUS),
dbesc ( NETWORK_OSTATUS ), dbesc ( NETWORK_DFRN ),
dbesc ( NETWORK_OSTATUS ), dbesc ( NETWORK_DFRN ),
dbesc ( $owner [ " nurl " ]), dbesc ( str_replace ( " http:// " , " https:// " , $owner [ " nurl " ])),
2015-11-23 17:44:47 +00:00
dbesc ( $owner [ " nurl " ]), dbesc ( str_replace ( " http:// " , " https:// " , $owner [ " nurl " ]))
);
$doc = new DOMDocument ( '1.0' , 'utf-8' );
$doc -> formatOutput = true ;
$root = ostatus_add_header ( $doc , $owner );
foreach ( $items AS $item ) {
$entry = ostatus_entry ( $doc , $item , $owner );
$root -> appendChild ( $entry );
}
2015-11-27 22:16:54 +00:00
return ( trim ( $doc -> saveXML ()));
2015-11-23 17:44:47 +00:00
}
function ostatus_salmon ( $item , $owner ) {
$doc = new DOMDocument ( '1.0' , 'utf-8' );
$doc -> formatOutput = true ;
$entry = ostatus_entry ( $doc , $item , $owner , true );
$doc -> appendChild ( $entry );
2015-11-27 22:16:54 +00:00
return ( trim ( $doc -> saveXML ()));
2015-11-23 17:44:47 +00:00
}
2015-06-20 12:40:30 +00:00
?>