- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
inc/core/class.dc.trackback.php
r1179 r1674 80 80 } 81 81 82 $data = array( 83 'title' => $post_title, 84 'excerpt' => $post_excerpt, 85 'url' => $post_url, 86 'blog_name' => trim(html::escapeHTML(html::clean($this->core->blog->name))) 87 //,'__debug' => false 88 ); 89 90 # Ping 91 try 92 { 93 $http = self::initHttp($url,$path); 94 $http->post($path,$data,'UTF-8'); 95 $res = $http->getContent(); 96 } 97 catch (Exception $e) 98 { 99 throw new Exception(__('Unable to ping URL')); 100 } 101 102 $pattern = 103 '|<response>.*<error>(.*)</error>(.*)'. 104 '(<message>(.*)</message>(.*))?'. 105 '</response>|msU'; 106 107 if (!preg_match($pattern,$res,$match)) 108 { 109 throw new Exception(sprintf(__('%s is not a ping URL'),$url)); 110 } 111 112 $ping_error = trim($match[1]); 113 $ping_msg = (!empty($match[4])) ? $match[4] : ''; 82 $ping_parts = explode('|',$url); 83 84 # Let's walk by the trackback way 85 if (count($ping_parts) < 2) { 86 $data = array( 87 'title' => $post_title, 88 'excerpt' => $post_excerpt, 89 'url' => $post_url, 90 'blog_name' => trim(html::escapeHTML(html::clean($this->core->blog->name))) 91 //,'__debug' => false 92 ); 93 94 # Ping 95 try 96 { 97 $http = self::initHttp($url,$path); 98 $http->post($path,$data,'UTF-8'); 99 $res = $http->getContent(); 100 } 101 catch (Exception $e) 102 { 103 throw new Exception(__('Unable to ping URL')); 104 } 105 106 $pattern = 107 '|<response>.*<error>(.*)</error>(.*)'. 108 '(<message>(.*)</message>(.*))?'. 109 '</response>|msU'; 110 111 if (!preg_match($pattern,$res,$match)) 112 { 113 throw new Exception(sprintf(__('%s is not a ping URL'),$url)); 114 } 115 116 $ping_error = trim($match[1]); 117 $ping_msg = (!empty($match[4])) ? $match[4] : ''; 118 } 119 # Damnit ! Let's play pingback 120 else { 121 try { 122 $xmlrpc = new xmlrpcClient($ping_parts[0]); 123 $res = $xmlrpc->query('pingback.ping', $post_url, $ping_parts[1]); 124 $ping_error = '0'; 125 } 126 catch (xmlrpcException $e) { 127 $ping_error = $e->getCode(); 128 $ping_msg = $e->getMessage(); 129 } 130 catch (Exception $e) { 131 throw new Exception(__('Unable to ping URL')); 132 } 133 } 114 134 115 135 if ($ping_error != '0') { … … 289 309 } 290 310 //@} 311 312 /// @name Receive pingbacks 313 //@{ 314 /** 315 Receives a pingback and insert it as a comment of given post. 316 317 @param from_url <b>string</b> Source URL 318 @param to_url <b>string</b> Target URL 319 */ 320 public function receive_pb($from_url, $to_url) 321 { 322 $reg = '!^'.preg_quote($this->core->blog->url).'(.*)!'; 323 $type = $args = $next = ''; 324 325 # Are you dumb? 326 if (!preg_match($reg, $to_url, $m)) { 327 throw new Exception(__('Any chance you ping one of my contents? No? Really?'), 0); 328 } 329 330 # Does the targeted URL look like a registered post type? 331 $url_part = $m[1]; 332 $p_type = ''; 333 $post_types = $this->core->getPostTypes(); 334 foreach ($post_types as $k => $v) { 335 $reg = '!^'.preg_quote(str_replace('%s', '', $v['public_url'])).'(.*)!'; 336 if (preg_match($reg, $url_part, $n)) { 337 $p_type = $k; 338 $post_url = $n[1]; 339 break; 340 } 341 } 342 343 if (empty($p_type)) { 344 throw new Exception(__('Sorry but you can not ping this type of content.'), 33); 345 } 346 347 # Time to see if we've got a winner... 348 $params = array( 349 'post_type' => $p_type, 350 'post_url' => $post_url, 351 ); 352 $posts = $this->core->blog->getPosts($params); 353 354 # Missed! 355 if ($posts->isEmpty()) { 356 throw new Exception(__('Oops. Kinda "not found" stuff. Please check the target URL twice.'), 33); 357 } 358 359 # Nice try. But, sorry, no. 360 if (!$posts->trackbacksActive()) { 361 throw new Exception(__('Sorry, dude. This entry does not accept pingback at the moment.'), 33); 362 } 363 364 # OK. We've found our champion. Time to check the remote part. 365 try { 366 $http = self::initHttp($from_url, $from_path); 367 368 # First round : just to be sure the ping comes from an acceptable resource type. 369 $http->setHeadersOnly(true); 370 $http->get($from_path); 371 $c_type = explode(';', $http->getHeader('content-type')); 372 373 # Bad luck. Bye, bye... 374 if (!in_array($c_type[0],array('text/html', 'application/xhtml+xml'))) { 375 throw new Exception(__('Your source URL does not look like a supported content type. Sorry. Bye, bye!'), 0); 376 } 377 378 # Second round : let's go fetch and parse the remote content 379 $http->setHeadersOnly(false); 380 $http->get($from_path); 381 $remote_content = $http->getContent(); 382 383 $charset = mb_detect_encoding($remote_content, 384 'UTF-8,ISO-8859-1,ISO-8859-2,ISO-8859-3,'. 385 'ISO-8859-4,ISO-8859-5,ISO-8859-6,ISO-8859-7,ISO-8859-8,'. 386 'ISO-8859-9,ISO-8859-10,ISO-8859-13,ISO-8859-14,ISO-8859-15'); 387 388 if (strtolower($charset) != 'utf-8') { 389 $remote_content = iconv($charset,'UTF-8',$remote_content); 390 } 391 392 # We want a title... 393 if (!preg_match('!<title>([^<].*?)</title>!mis', $remote_content, $m)) { 394 throw new Exception(__('Where\'s your title?'), 0); 395 } 396 $title = trim(html::clean($m[1])); 397 $title = html::decodeEntities($title); 398 $title = html::escapeHTML($title); 399 $title = text::cutString($title,60); 400 401 preg_match('!<body[^>]*?>(.*)?</body>!msi', $remote_content, $m); 402 $source = $m[1]; 403 $source = preg_replace('![\r\n\s]+!ms',' ',$source); 404 $source = preg_replace( "/<\/*(h\d|p|th|td|li|dt|dd|pre|caption|input|textarea|button)[^>]*>/", "\n\n", $source ); 405 $source = strip_tags($source, '<a>'); 406 $source = explode("\n\n",$source); 407 408 $excerpt = ''; 409 foreach ($source as $line) { 410 if (strpos($line, $to_url) !== false) { 411 if (preg_match("!<a[^>]+?".$to_url."[^>]*>([^>]+?)</a>!", $line, $m)) { 412 $excerpt = strip_tags($line); 413 break; 414 } 415 } 416 } 417 if ($excerpt) { 418 $excerpt = '(…) '.text::cutString(html::escapeHTML($excerpt),255).' (…)'; 419 } 420 else { 421 $excerpt = '(??)'; 422 } 423 424 $comment = 425 "<!-- TB -->\n". 426 '<p><strong>'.$title."</strong></p>\n". 427 '<p>'.$excerpt.'</p>'; 428 429 $cur = $this->core->con->openCursor($this->core->prefix.'comment'); 430 $cur->comment_author = 'Anonymous blog'; 431 $cur->comment_site = (string) $from_url; 432 $cur->comment_content = (string) $comment; 433 $cur->post_id = $posts->post_id; 434 $cur->comment_trackback = 1; 435 $cur->comment_status = $this->core->blog->settings->system->trackbacks_pub ? 1 : -1; 436 $cur->comment_ip = http::realIP(); 437 438 # --BEHAVIOR-- publicBeforeTrackbackCreate 439 $this->core->callBehavior('publicBeforeTrackbackCreate',$cur); 440 if ($cur->post_id) { 441 $comment_id = $this->core->blog->addComment($cur); 442 443 # --BEHAVIOR-- publicAfterTrackbackCreate 444 $this->core->callBehavior('publicAfterTrackbackCreate',$cur,$comment_id); 445 } 446 } 447 catch (Exception $e) { 448 throw new Exception(__('Sorry, an internal problem has occured.'), 0); 449 } 450 451 return __('Thanks, mate. It was a pleasure.'); 452 } 453 //@} 291 454 292 455 private static function initHttp($url,&$path) … … 346 509 for ($i = 0; $i<count($match); $i++) 347 510 { 348 if (preg_match('/href="( http:\/\/[^"]+)"/ms', $match[$i][1], $matches)) {511 if (preg_match('/href="((https?:\/)?\/[^"]+)"/ms', $match[$i][1], $matches)) { 349 512 $res[$matches[1]] = 1; 350 513 } … … 358 521 for ($i = 0; $i<count($match); $i++) 359 522 { 360 if (preg_match('/cite="( http:\/\/[^"]+)"/ms', $match[$i][2], $matches)) {523 if (preg_match('/cite="((https?:\/)?\/[^"]+)"/ms', $match[$i][2], $matches)) { 361 524 $res[$matches[1]] = 1; 362 525 } … … 369 532 private function getPingURL($url) 370 533 { 534 if (strpos($url,'/') === 0) { 535 $url = http::getHost().$url; 536 } 537 371 538 try 372 539 { … … 374 541 $http->get($path); 375 542 $page_content = $http->getContent(); 543 $pb_url = $http->getHeader('x-pingback'); 376 544 } 377 545 catch (Exception $e) … … 380 548 } 381 549 550 # If we've got a X-Pingback header and it's a valid URL, it will be enough 551 if ($pb_url && filter_var($pb_url,FILTER_VALIDATE_URL) && preg_match('!^https?:!',$pb_url)) { 552 return $pb_url.'|'.$url; 553 } 554 555 # No X-Pingback header. A link rel=pingback, maybe ? 556 $pattern_pingback = '!<link rel="pingback" href="(.*?)"( /)?>!msi'; 557 558 if (preg_match($pattern_pingback,$page_content,$m)) { 559 $pb_url = $m[1]; 560 if (filter_var($pb_url,FILTER_VALIDATE_URL) && preg_match('!^https?:!',$pb_url)) { 561 return $pb_url.'|'.$url; 562 } 563 } 564 565 # No pingback ? OK, let's check for a trackback data chunk... 382 566 $pattern_rdf = 383 567 '/<rdf:RDF.*?>.*?'. … … 388 572 preg_match_all($pattern_rdf,$page_content,$rdf_all,PREG_SET_ORDER); 389 573 574 $url_path = parse_url($url, PHP_URL_PATH); 575 $sanitized_url = str_replace($url_path, html::sanitizeURL($url_path), $url); 576 390 577 for ($i=0; $i<count($rdf_all); $i++) 391 578 { 392 579 $rdf = $rdf_all[$i][1]; 393 394 if (preg_match('/dc:identifier="'.preg_quote($url,'/').'"/msi',$rdf)) {580 if (preg_match('/dc:identifier="'.preg_quote($url,'/').'"/msi',$rdf) || 581 preg_match('/dc:identifier="'.preg_quote($sanitized_url,'/').'"/msi',$rdf)) { 395 582 if (preg_match('/trackback:ping="(.*?)"/msi',$rdf,$tb_link)) { 396 583 return $tb_link[1];
Note: See TracChangeset
for help on using the changeset viewer.