From 4e7e06fa9f3e330884acb2c2dbcc239b32f3470e Mon Sep 17 00:00:00 2001
From: Kyle Robinson Young
Date: Sat, 24 Dec 2011 21:25:07 -0800
Subject: [PATCH 1/2] Prevent TextHelper::truncate() from breaking HTML
Fixes #2397
---
.../Test/Case/View/Helper/TextHelperTest.php | 47 ++++++++++++++++++-
lib/Cake/View/Helper/TextHelper.php | 26 ++++++----
2 files changed, 62 insertions(+), 11 deletions(-)
diff --git a/lib/Cake/Test/Case/View/Helper/TextHelperTest.php b/lib/Cake/Test/Case/View/Helper/TextHelperTest.php
index a10a211dc..54752c548 100644
--- a/lib/Cake/Test/Case/View/Helper/TextHelperTest.php
+++ b/lib/Cake/Test/Case/View/Helper/TextHelperTest.php
@@ -60,7 +60,7 @@ class TextHelperTest extends CakeTestCase {
$text5 = '01234567890';
$text6 = 'Extra dates have been announced for this year\'s tour.
Tickets for the new shows in
';
$text7 = 'El moño está en el lugar correcto. Eso fue lo que dijo la niña, ¿habrá dicho la verdad?';
- $text8 = 'Vive la R'.chr(195).chr(169).'publique de France';
+ $text8 = 'Vive la R' . chr(195) . chr(169) . 'publique de France';
$text9 = 'НОПРСТУФХЦЧШЩЪЫЬЭЮЯабвгдежзийклмнопрстуфхцчшщъыь';
$this->assertSame($this->Text->truncate($text1, 15), 'The quick br...');
@@ -86,6 +86,51 @@ class TextHelperTest extends CakeTestCase {
$this->assertSame($this->Text->truncate($text7, 15), 'El moño está...');
$this->assertSame($this->Text->truncate($text8, 15), 'Vive la R'.chr(195).chr(169).'pu...');
$this->assertSame($this->Text->truncate($text9, 10), 'НОПРСТУ...');
+
+ $text = 'Iamatestwithnospacesandhtml
';
+ $result = $this->Text->truncate($text, 10, array(
+ 'ending' => '...',
+ 'exact' => false,
+ 'html' => true
+ ));
+ $expected = '...
';
+ $this->assertEquals($expected, $result);
+
+ $text = 'El biógrafo de Steve Jobs, Walter
+Isaacson, explica porqué Jobs le pidió que le hiciera su biografía en
+este artículo de El País.
+Por qué Steve era distinto.
+http://www.elpais.com/articulo/primer/plano/
+Steve/era/distinto/elpepueconeg/20111009elpneglse_4/Tes
+Ya se ha publicado la biografía de
+Steve Jobs escrita por Walter Isaacson "Steve Jobs by Walter
+Isaacson", aquí os dejamos la dirección de amazon donde
+podeís adquirirla.
+http://www.amazon.com/Steve-
+Jobs-Walter-Isaacson/dp/1451648537
';
+ $result = $this->Text->truncate($text, 500, array(
+ 'ending' => '... ',
+ 'exact' => false,
+ 'html' => true
+ ));
+ $expected = 'El biógrafo de Steve Jobs, Walter
+Isaacson, explica porqué Jobs le pidió que le hiciera su biografía en
+este artículo de El País.
+Por qué Steve era distinto.
+http://www.elpais.com/articulo/primer/plano/
+Steve/era/distinto/elpepueconeg/20111009elpneglse_4/Tes
+Ya se ha publicado la biografía de
+Steve Jobs escrita por Walter Isaacson "Steve Jobs by Walter
+Isaacson", aquí os dejamos la dirección de amazon donde
+podeís adquirirla.
+...
';
+ $this->assertEquals($expected, $result);
}
/**
diff --git a/lib/Cake/View/Helper/TextHelper.php b/lib/Cake/View/Helper/TextHelper.php
index ee11b037b..2dbb28df4 100644
--- a/lib/Cake/View/Helper/TextHelper.php
+++ b/lib/Cake/View/Helper/TextHelper.php
@@ -275,20 +275,26 @@ class TextHelper extends AppHelper {
}
if (!$exact) {
$spacepos = mb_strrpos($truncate, ' ');
- if (isset($spacepos)) {
- if ($html) {
- $bits = mb_substr($truncate, $spacepos);
- preg_match_all('/<\/([a-z]+)>/', $bits, $droppedTags, PREG_SET_ORDER);
- if (!empty($droppedTags)) {
- foreach ($droppedTags as $closingTag) {
- if (!in_array($closingTag[1], $openTags)) {
- array_unshift($openTags, $closingTag[1]);
- }
+ if ($html) {
+ $truncateCheck = mb_substr($truncate, 0, $spacepos);
+ $lastOpenTag = mb_strrpos($truncateCheck, '<');
+ $lastCloseTag = mb_strrpos($truncateCheck, '>');
+ if ($lastOpenTag > $lastCloseTag) {
+ preg_match_all('/<[\w]+[^>]*>/s', $truncate, $lastTagMatches);
+ $lastTag = array_pop($lastTagMatches[0]);
+ $spacepos = mb_strrpos($truncate, $lastTag) + mb_strlen($lastTag);
+ }
+ $bits = mb_substr($truncate, $spacepos);
+ preg_match_all('/<\/([a-z]+)>/', $bits, $droppedTags, PREG_SET_ORDER);
+ if (!empty($droppedTags)) {
+ foreach ($droppedTags as $closingTag) {
+ if (!in_array($closingTag[1], $openTags)) {
+ array_unshift($openTags, $closingTag[1]);
}
}
}
- $truncate = mb_substr($truncate, 0, $spacepos);
}
+ $truncate = mb_substr($truncate, 0, $spacepos);
}
$truncate .= $ending;
From acca796d10255fc7ebbf8a51dcc1f29baf87234b Mon Sep 17 00:00:00 2001
From: Kyle Robinson Young
Date: Sun, 25 Dec 2011 09:10:50 -0800
Subject: [PATCH 2/2] Fix tag order when closing open tags with
TextHelper::truncate()
---
lib/Cake/Test/Case/View/Helper/TextHelperTest.php | 2 +-
lib/Cake/View/Helper/TextHelper.php | 12 +++++++++---
2 files changed, 10 insertions(+), 4 deletions(-)
diff --git a/lib/Cake/Test/Case/View/Helper/TextHelperTest.php b/lib/Cake/Test/Case/View/Helper/TextHelperTest.php
index 54752c548..81c36dcd6 100644
--- a/lib/Cake/Test/Case/View/Helper/TextHelperTest.php
+++ b/lib/Cake/Test/Case/View/Helper/TextHelperTest.php
@@ -129,7 +129,7 @@ Steve/era/distinto/elpepueconeg/20111009elpneglse_4/Tes
Steve Jobs escrita por Walter Isaacson "Steve Jobs by Walter
Isaacson", aquí os dejamos la dirección de amazon donde
podeís adquirirla.
-...
';
+...
';
$this->assertEquals($expected, $result);
}
diff --git a/lib/Cake/View/Helper/TextHelper.php b/lib/Cake/View/Helper/TextHelper.php
index 2dbb28df4..fc6fc10d3 100644
--- a/lib/Cake/View/Helper/TextHelper.php
+++ b/lib/Cake/View/Helper/TextHelper.php
@@ -287,9 +287,15 @@ class TextHelper extends AppHelper {
$bits = mb_substr($truncate, $spacepos);
preg_match_all('/<\/([a-z]+)>/', $bits, $droppedTags, PREG_SET_ORDER);
if (!empty($droppedTags)) {
- foreach ($droppedTags as $closingTag) {
- if (!in_array($closingTag[1], $openTags)) {
- array_unshift($openTags, $closingTag[1]);
+ if (!empty($openTags)) {
+ foreach ($droppedTags as $closingTag) {
+ if (!in_array($closingTag[1], $openTags)) {
+ array_unshift($openTags, $closingTag[1]);
+ }
+ }
+ } else {
+ foreach ($droppedTags as $closingTag) {
+ array_push($openTags, $closingTag[1]);
}
}
}