Forum code that automatically turns urls into clickable links

16 posts by 2 authors in: Forums > CMS Builder
Last Post: December 29, 2018   (RSS)

Hi All,

I’m curious about the code used in the forum to automatically turn urls in a post into clickable links.

Like: http://www.thecmsbcookbook.com

I’d like to include it in the CMSBCookbook recipes to streamline the process.

Thanks,

Jerry Kornbluth

The first CMS Builder reference book is now available on-line!







Take advantage of a free 3 month trial subscription, only for CMSB users, at: http://www.thecmsbcookbook.com/trial.php

By daniel - December 27, 2018 - edited: December 27, 2018

Hi Jerry,

The forums use a PHP library called HTML Purifier (http://htmlpurifier.org/) to - among other things - add links to message bodies in the function sforum_cleanAndFormatHTML(). This library is integrated into the CMSB core with the common function htmlPurify(), so it should be possible to use it to just add links with something like this:

$config = array();
$config['AutoFormat.Linkify'] = true;

$newHtml = htmlPurify($oldHtml, $config);

If you're looking for something standalone that can be used outside of CMSB, here's a short snippet that should be able to handle most simple cases:

$text = preg_replace("|(https?://[\w\-@:%\+.~#?&//=]+)|", '<a href="\\1">\\1</a>', $text);

Let me know any questions!

Thanks,

Daniel
Technical Lead
interactivetools.com

Hi Daniel,

Thanks as always for your expert guidance.

I think that I got both implementations to work on the cookbook recipe details pages, although I want to do a few more tests to see if other things got broken along the way.

(Like what happens if there's a url in the example code of a recipe...)

I do have one more question. Should I be using print, print_r, or echo for the built in version of the code?

Thanks,

Jerry Kornbluth

Here’s what I have so far:

The text for my recipes are pulled from a text box called $table_of_contentsRecord['recipe'].

I've left out any formatting code to simplify the examples as much as possible.

For the code built in to CMSB

<?php $recipe = ($table_of_contentsRecord['recipe']); ?>
<?php

// automatic links using code built in to CMSB
$config = array();
$config['AutoFormat.Linkify'] = true;

$recipe = htmlPurify($recipe, $config);
echo $recipe;
?>

And for the code to use outside of CMSB:

<?php $recipe = ($table_of_contentsRecord['recipe']); ?>
<?php

// standard implementation for use outside of CMSB

$recipe = preg_replace("|(https?://[\w\-@:%\+.~#?&//=]+)|", '<a href="\\1">\\1</a>', $recipe); // Added per Daniel to create links from URLs

echo $recipe;
?>

The first CMS Builder reference book is now available on-line!







Take advantage of a free 3 month trial subscription, only for CMSB users, at: http://www.thecmsbcookbook.com/trial.php

Hi Daniel,

There's still one minor issue that I’d love to solve.

I’d like to exclude htmlPurify() from acting on the code examples within a cookbook recipe.

All code examples are enclosed in block quotes which I accomplish by surrounding each code block with qzl at the beginning and lzq at the end and then using the following code:

$recipe = str_replace('qzl', '<blockquote class="snippet"> ', $recipe);
$recipe = str_replace('lzq', '</blockquote> ', $recipe);

and styling the blockquotes with:

.snippet {font-family: Verdana, sans-serif; color: #000000; font-size: 1em; font-weight:normal;
margin: 0px 0px 0px 15px;
padding: 8px 12px;
border: 1px dashed #305555;
background-color: #54ccf2;
display: block;
overflow-x: auto;
}

I think that if I could wrap the htmlPurify code in an if statement that excludes any blockquoted data in the recipe that might work automatically, but I haven’t been able to figure out how to implement that.

Any ideas?

Complete working page code is attached.

Thanks,

Jerry Kornbluth

The first CMS Builder reference book is now available on-line!







Take advantage of a free 3 month trial subscription, only for CMSB users, at: http://www.thecmsbcookbook.com/trial.php
Attachments:

recipedetail.php 10K

By daniel - December 28, 2018

Hi Jerry,

For echo vs. print vs. print_r; I'd recommend echo for any time you want to output plain text to a page. (For some more specific details, see: https://stackoverflow.com/questions/1647322/whats-the-difference-between-echo-print-and-print-r-in-php)

From what I can see, there's no easy way to exclude the code snippets from being passed through htmlPurify(), as the whole content for the recipe is contained within a single variable. You will need to find a way to split up the content to isolate the parts you want to add links to and run the purifier on those.

A full solution is a bit beyond what I can offer here, but my suggestion would be to try using explode() to split up the content around the code blocks; something like this may work (untested code):

// split on opening blockquote
$chunks = explode('qzl', $recipe);

// loop through each chunk
foreach ($chunks as $chunk) {

  // split chunk on end blockquote
  $tmp = explode('lzq', $chunk);
  
  // did we find an ending blockquote?
  if (count( $tmp ) > 1) {

    // purify content after blockquote
    $chunks[ $chunk ][1] = htmlPurify( $chunks[ $chunk ][1] );
  }
  else {

    // purify only element
    $chunks[ $chunk ][0] = htmlPurify( $chunks[ $chunk ][0] );
  }

  // replace ending blockquote
  $chunks[ $chunk ] = implode('lqz', $tmp);
}

// replace opening blockquote
$recipe = implode('qzl', $chunks);

Let me know any questions!

Thanks,

Daniel
Technical Lead
interactivetools.com

WOW!

Thanks, Daniel,

I'll give it a try and post the results.

Jerry Kornbluth

The first CMS Builder reference book is now available on-line!







Take advantage of a free 3 month trial subscription, only for CMSB users, at: http://www.thecmsbcookbook.com/trial.php

By daniel - December 28, 2018

Hey Jerry,

Just noticed a couple logic errors in the sample code. Corrected here:

// split on opening blockquote
$chunks = explode('qzl', $recipe);

// loop through each chunk
foreach ($chunks as $key => $chunk) {

  // split chunk on end blockquote
  $tmp = explode('lzq', $chunk);
  
  // did we find an ending blockquote?
  if (count( $tmp ) > 1) {

    // purify content after blockquote
    $tmp[1] = htmlPurify( $tmp[1] );
  }
  else {

    // purify only element
    $tmp[0] = htmlPurify( $tmp[0] );
  }

  // replace ending blockquote
  $chunks[ $key ] = implode('lqz', $tmp);
}

// replace opening blockquote
$recipe = implode('qzl', $chunks);

Let me know if that does any better!

Thanks,

Daniel
Technical Lead
interactivetools.com

Hey Daniel,

Almost there...

Looks and works much better, and no errors.

However, still 2 small issues:

1) the functionality the reverse of what it should be.

Currently, the URLs in the block quotes are active (they shouldn't be) and the URLs outside are inactive (they should be).

2) An lzq (lower case) is printing when it shouldn't.

Probably really quick fixes for you...

See http://www.thecmsbcookbook.com/recipedetailI.php?TEST-ONLY-589

Thanks,

Jerry Kornbluth

The first CMS Builder reference book is now available on-line!







Take advantage of a free 3 month trial subscription, only for CMSB users, at: http://www.thecmsbcookbook.com/trial.php

By daniel - December 28, 2018

Hi Jerry,

One quick thing: There's a "lzq" written as "lqz" - that should fix item 2, however, I'm not 100% sure why it's reversing the result.  Are you able to provide me with the $recipe content before it gets processed (with the qzl and lzq parts intact) so that I can test it myself?

Thanks,

Daniel
Technical Lead
interactivetools.com