Перейти к контенту

Читабельные везде ссылки


Рекомендуемые сообщения

Следующие изменения позволят преобразовывать автоматически любые ссылки в читабельный вид

 

В этом трике также включена тема "Читабельные внутри ссылки"

 

вот результат действия мода

linkstestxb0.jpg

(_http://ya.ru -- Яndex )

 

открываем файл

 

sources/classes/bbcode/class_bbcode_core.php

 

находим

 

  //-----------------------------------------
 // Make sure it's a "proper" url
 //-----------------------------------------

 if ( ! preg_match( "/^(http|ftp|https|news):\/\//i", $url['show'] )) $skip_it = 1;

 $show = $url['show'];

 if ($skip_it != 1)
 {
  $stripped = preg_replace( "#^(http|ftp|https|news)://(\S+)$#i", "[url="file://\\2"]\\2[/url]", $url['show'] );
  $uri_type = preg_replace( "#^(http|ftp|https|news)://(\S+)$#i", "[url="file://\\1"]\\1[/url]", $url['show'] );

  $show = $uri_type.'://'.substr( $stripped , 0, 35 ).'...'.substr( $stripped , -15   );
 }

 return $url['st'] . "<a href=\"".$url['html']."\" target=\"_blank\">".$show."</a>" . $url['end'];
}

 

и заменяем на

 

		//-----------------------------------------
	// Make sure it's a "proper" url
	//-----------------------------------------

	if ( ! preg_match( "/^(http|ftp|https|news):\/\//i", $url['show'] )) $skip_it = 1;

		$show = $url['show'];

		if ( strpos($show, $this->ipsclass->base_url) !== false )
		{
			$match = array();

			if ( preg_match("/showtopic=(\d+)/", $show, $match) OR preg_match("/&t=(\d+)/", $show, $match) ) {
		   				$show = $this->_getUrlLocalName('topics', $match[1]);
				}

				elseif ( preg_match("/showforum=(\d+)/", $show, $match) ) {
   			   		$show = $this->_getUrlLocalName('forums', $match[1]);
   			}

				elseif ( preg_match("/showuser=(\d+)/", $show, $match) ) {
   						$show = $this->_getUrlLocalName('members', $match[1]);
   			}

		else
		{
			if (( preg_match( "/^<img src/i", $show ) ) or ( preg_match( "/^<img style/i", $show ) ) or ( preg_match( "/^<img width/i", $show ) ) )
			{
				$show = stripslashes($show);
			}
			elseif (preg_match("#^(http|news|https|ftp|aim)://#", $show))
			{
				$show = $this->get_url_title($show);
				$this->ipsclass->load_language('lang_error');

				if (strpos(" ".$show,$this->ipsclass->lang['error_title']))
				{
					$show = $this->ipsclass->vars['board_name'];
				}
			}
			else $show = $url['show'];

			if ((strlen($show)>60)and(! preg_match( "/^<img src/i", $show ) )and(! preg_match( "/^<img style/i", $show ) )and(! preg_match( "/^<img width/i", $show ) )  )
			{
				$show = substr($show,0,59);
			}
		}

	   	if (!$show)//if it is a file, it hasn't got title
		{
			$title = @parse_url($url['html']);
			$show = substr(strrchr($title['path'],"/"),1);//filename
			if (!$show)// and if there is no anything at this url
			{
				$show = $url['html'];
			}
		}
   	} 
	elseif ($skip_it != 1)
	{
		$stripped = preg_replace( "#^(http|ftp|https|news)://(\S+)$#i", "\\2", $url['show'] );
		$uri_type = preg_replace( "#^(http|ftp|https|news)://(\S+)$#i", "\\1", $url['show'] );

		$show = $uri_type.'://'.substr( $stripped , 0, 35 ).'...'.substr( $stripped , -15   );
	}

	//get_url_title
	else
	{
		if (( preg_match( "/^<img src/i", $show ) )or ( preg_match( "/^<img style/i", $show ) ) or ( preg_match( "/^<img width/i", $show ) ) )
		{
			$show = stripslashes($show);
		}
		elseif (preg_match("#^(http|news|https|ftp|aim)://#", $show))
		{
			$show = $this->get_url_title($show);
		}
		else $show = $url['show'];

		if ((strlen($show)>60)and(! preg_match( "/^<img src/i", $show ) )and(! preg_match( "/^<img style/i", $show ) )and(! preg_match( "/^<img width/i", $show ) )  )
		{
			$show = substr($show,0,59);
		}
	}
	if (!$show)//if it is a file, it hasn't got title
	{
		$title = @parse_url($url['html']);
		$show = substr(strrchr($title['path'],"/"),1);//filename
		if (!$show)// and if there is no anything at this url
		{
			$show = $url['html'];
		}
	}
	return $url['st'] . "<a href=\"".$url['html']."\" target=\"_blank\">".$show."</a>" . $url['end'];
}

function get_url_title($url)
{
	  $url = parse_url($url);

	if(!in_array($url['scheme'],array('','http')))
		return;

	$fp = @fsockopen ($url['host'], ($url['port'] > 0 ? $url['port'] : 80), $errno, $errstr, 2);
	if (!$fp)
  		{
   		return;
		//echo "$errstr ($errno)<br>\n";
  		}
  		else
  		{
   			fputs ($fp, "GET /".$url['path'].($url['query'] ? '?'.$url['query'] : '')." HTTP/1.0\r\nHost: ".$url['host']."\r\n\r\n");
   			$d = '';
		while (!feof($fp))
   			{
	   			$d .= fgets ($fp,2048);

				if(preg_match('~(</head>|<body>|(<title>\s*(.*?)\s*</title>))~i', $d, $m))
		   				break;
   			}
   			fclose ($fp);

			$m[3] = str_replace("("," ",$m[3]);
			$m[3] = str_replace(")"," ",$m[3]);
			$m[3] = addslashes($m[3]);
		   return $m[3];
	}
}


function _getUrlLocalName( $from = '',  $for = '' )
{
	// сколько раз разбирали ссылки
	static $parsedUrls;

	// проверка на лимит разбора ссылок, чем больше число, тем больше
	// вероятность, что злоумышленник может создать нагрузку на БД
	if ( ++$parsedUrls >= 10 ) return false;

	if ( !$from OR !$for ) return false;

	// оптимизация для ссылок на форумы/разделы. Берем имя не через запрос
	// к базе, а из кэша форумов.
	// Спасибо улетает к SAT
	if ( $from == 'forums' ) {
		return $this->ipsclass->cache['forum_cache'][ $for ]['name'];
	}

	// pk		- имя первичного ключа (id'ентификатора) в таблице 
	// fieldName - имя поля в таблице, в котором хранится возвращаемое имя
	$pk		 = 'id';	 // в большинстве случаев имя первичного ключа - id
	$fieldName  = 'members_display_name';   // имя поля - name

	// однако в случае с темами у нас другие pk и fieldName
	if ( $from == 'topics' ) {
		$pk		 = 'tid';   // имя первичного ключа - tid
		$fieldName  = 'title'; // имя поля с названием - title
	}

	$this->ipsclass->DB->simple_select( $fieldName, $from, $pk . "= '" . $for . "'" );
	$ci   = $this->ipsclass->DB->exec_query();
	$row  = $this->ipsclass->DB->fetch_row( $ci );

	if ( $fieldValue = $row[ $fieldName ] ) {
		return $fieldValue;
	}

	return false;
}

в этом посте мог поломатся код, поэтому выкладываю дублирующий конечный вариант

также возможно, что у вас отсутствует обязательная часть кода, расположенная сразу НАД изменяемым фрагментом

эта часть должна содержать

		if ( (strlen($url['show']) -58 ) < 3 )  $skip_it = 1;

Ссылка на комментарий
Поделиться на других сайтах

  • Ответы 90
  • Создана
  • Последний ответ

Лучшие авторы в этой теме

Лучшие авторы в этой теме

глюки есть, проапдейтил первый пост на предмет найденных..

осталось отключить показ ошибок в случае отсутствия в реальности сайта

типа http://www.nettakogosaita.ru

выдает ошибку

 

size появился сам по себе...

Ссылка на комментарий
Поделиться на других сайтах

я именно его включил в состав своего

в моем на данный момент нужно сделать только одно, о чем я не могу догадаться пока-что - убрать показ ошибки при отсутствии сайта в природе

тоесть вопрос коротко звучит так:

 

Как убрать показ ошибки в случае неудачи команды fsockopen() и перейти к следующей?

Ссылка на комментарий
Поделиться на других сайтах

ну в общем проблема такая:

1.ввожу http://www.nettakogosaita.ru

2.получаю

IPB Предупреждение [2] fsockopen() [function.fsockopen]: php_network_getaddresses: gethostbyname failed (Строка: 1620 файла \sources\classes\bbcode\class_bbcode_core.php)

IPB Предупреждение [2] fsockopen() [function.fsockopen]: unable to connect to www.nettakogosaita.ru:80 (Строка: 1620 файла \sources\classes\bbcode\class_bbcode_core.php)

3. получаю успешно сообщение

 

Успешно, тоесть программа дальше идет

но смущает появившаяся ошибка

Ссылка на комментарий
Поделиться на других сайтах

спасибо, вот этого не знал

обновлю мануал

после обновления на данный момент нет никаких известных багов

 

несмотря на заимствование мода "читабельные Внутри ссылки", даже в этот мод внес некоторые изменения

первое - получение титла в случае, если это не форум, не тема и не профиль пользователя (также замена в случае недоступности гостям некой функции титла этой функции на главное название форума)

второе - получение members_display_name вместо name, для защиты от возможного получения злоумышленником логина

Ссылка на комментарий
Поделиться на других сайтах

на линк с конечным файлом, например на вот этот: http://www.virtualzone.de/files/resizer.zip, после установки этого мода, форум никак не отреагировал.. вернее, он его просто проигнорировал.. не показал ничего
Ссылка на комментарий
Поделиться на других сайтах

подумал, что если в титл попадет " то возможно нарушится строчка

		return $url['st'] . "<a href=\"".$url['html']."\" target=\"_blank\">".$show."</a>" . $url['end'];

поэтому перед

			   return $m[3];

добавил

				$m[3] = str_replace("("," ",$m[3]);
			$m[3] = str_replace(")"," ",$m[3]);
			$m[3] = addslashes($m[3]);

также убираю скобки

 

тоесть вместо

",(');

получилось

\", \' ;

вместо

phpinfo()

получилось

phpinfo
Ссылка на комментарий
Поделиться на других сайтах

найден баг во взаимодействии с тегом

устранение:

ДВА РАЗА ПЕРЕД

if (preg_match("#^(http|news|https|ftp|aim)://#", $show))
			{
				$show = $this->get_url_title($show);

ДОБАВИТЬ

				if ( preg_match( "/^<img src/i", $show ) )
			{
				$show = stripslashes($show);
			}
			else

не ошибитесь с else!

 

А также

ДВА РАЗА

if (strlen($show)>60)

заменить на

if ((strlen($show)>60)and(! preg_match( "/^<img src/i", $show ) ))

Ссылка на комментарий
Поделиться на других сайтах

первый пост обновляю всегда, это так, чтобы было понятно

 

вот результат действия мода

http://img403.imageshack.us/img403/6100/linkstestxb0.jpg

Ссылка на комментарий
Поделиться на других сайтах

!!

возможно у вас не правильно присваивается значение переменной $skip_it

сравните все места ее обработки в этом коде И чуть выше с моими:

	function regex_build_url( $url=array() )
{
	$skip_it = 0;

...

	//-----------------------------------------
	// Tidy up the viewable URL
	//-----------------------------------------

	if ( preg_match( "/^<img src/i", $url['show'] ) )
	{
		$skip_it	 = 1;
		$url['show'] = stripslashes($url['show']);
	}

	$url['show'] = str_replace( "&" , "&" , $url['show'] );
	$url['show'] = preg_replace( "/java script:/i", "java script: ", $url['show'] );

	if ( (strlen($url['show']) -58 ) < 3 )  $skip_it = 1;

	//-----------------------------------------
	// Make sure it's a "proper" url
	//-----------------------------------------

	if ( ! preg_match( "/^(http|ftp|https|news):\/\//i", $url['show'] )) $skip_it = 1;

Ссылка на комментарий
Поделиться на других сайтах

Присоединиться к обсуждению

Вы можете ответить сейчас, а зарегистрироваться позже. Если у вас уже есть аккаунт, войдите, чтобы ответить от своего имени.

Гость
Ответить в этой теме...

×   Вы вставили отформатированный текст.   Удалить форматирование

  Допустимо не более 75 смайлов.

×   Ваша ссылка была автоматически заменена на медиа-контент.   Отображать как ссылку

×   Ваши публикации восстановлены.   Очистить редактор

×   Вы не можете вставить изображения напрямую. Загрузите или вставьте изображения по ссылке.

Зарузка...

×
×
  • Создать...

Важная информация

Находясь на нашем сайте, вы соглашаетесь на использование файлов cookie, а также с нашим положением о конфиденциальности Политика конфиденциальности и пользовательским соглашением Условия использования.