codeigniter4 / CodeIgniter4

Open Source PHP Framework (originally from EllisLab)
https://codeigniter.com/
MIT License
5.3k stars 1.89k forks source link

Bug: Parsing lang on loops prints pure html instead of parsed html #3928

Closed LucasKovacs closed 2 years ago

LucasKovacs commented 3 years ago

Describe the bug The following block of code is a good example of the issue

        foreach ((new Requirements)->getRequirements() as $requirement => $status) {
            $requirements[] = [
                'requirement' => lang('in_' . $requirement), // this line has html, but fails to parse html.
            ];
        }

        $this->page->setData(array_merge(
            $this->lang->all(), // there are lines with html here, these lines are properly parsed, bold set, links set
            [
                'base_url' => $this->baseUrl,
                'requirements' => $requirements,
            ]
        ))->display('requirements');

Parser was set to raw

\Config\Services::parser()->setData($data, 'raw')->render($template);

In the example above parser receives the template 'requirements' and an array with all the language lines (some including html), and also receives another array with other languages lines that contain html on them.

This is some of the html

            <ul class="list-group">
            {requirements}
                <li class="list-group-item list-group-item-{status}">
                   {requirement}
                </li>
            {/requirements}
            </ul>

A print of $data on this line \Config\Services::parser()->setData($data, 'raw')->render($template); produces the following:

Notice that all the lines below are parsed, but only "line_with_html" gets it's html properly parsed. While the ones [requirements][0][requirement] is ignoring the HTML and parsing the whole thing displaying on the page the html. So users will read PHP <a href="https://www.php.net/manual/en/book.intl.php" target="_blank">intl Extension</a>. instead of PHP intl Extension.

<pre>Array
(
    [in_something] => something
    [in_test] => <strong>some strong text</strong>
    [line_with_html] => PHP <a href="https://www.php.net/manual/en/book.mbstring.php" target="_blank">mbstring Extension</a>.
    [requirements] => Array
        (
            [0] => Array
                (
                    [requirement] => Minimum PHP version required (7.4)
                )

            [1] => Array
                (
                    [requirement] => PHP <a href="https://www.php.net/manual/en/book.intl.php" target="_blank">intl Extension</a>.
                )

            [2] => Array
                (
                    [requirement] => PHP <a href="https://www.php.net/manual/en/book.curl.php" target="_blank">libcurl Extension</a>.
                )
        )
)
</pre>

CodeIgniter 4 version 4.0.4

Affected module(s)

Expected behavior, and steps to reproduce if appropriate Issue was explained above. I'd expect that any html set on for a parser loop is parsed also as if it was set on the main block.

Context

kenjis commented 2 years ago

Thank you for your report.

But unfortunately, I don't understand what is the bug. Could you show us small code to reproduce it?

While the ones [requirements][0][requirement] is ignoring the HTML and parsing the whole thing displaying on the page the html.

It seems [requirements][0][requirement] does not include HTML at all.

LucasKovacs commented 2 years ago

All the code is above, not sure what else is needed.

kenjis commented 2 years ago

Sorry, your code does not work at all on my environment. So I don't know this is a true bug or not.

We need minimum working sample code that reproduces the bug. Because we need test code to ensure the bug is fixed.

If you could, I recommend you send PR to fix. It is the best and quick way to fix a bug.

<?php

namespace App\Controllers;

class Home extends BaseController
{
    public function index()
    {
        foreach ((new Requirements())->getRequirements() as $requirement => $status) {
            $requirements[] = [
                'requirement' => lang('in_' . $requirement), // this line has html, but fails to parse html.
            ];
        }

        $this->page->setData(array_merge(
            $this->lang->all(), // there are lines with html here, these lines are properly parsed, bold set, links set
            [
             'base_url'     => $this->baseUrl,
             'requirements' => $requirements,
            ]
        ))->display('requirements');
    }
}
$ php public/index.php 

[Error]

Class "App\Controllers\Requirements" not found

at APPPATH/Controllers/Home.php:9

Backtrace:
  1    SYSTEMPATH/CodeIgniter.php:823
       App\Controllers\Home()->index()

  2    SYSTEMPATH/CodeIgniter.php:410
       CodeIgniter\CodeIgniter()->runController(Object(App\Controllers\Home))

  3    SYSTEMPATH/CodeIgniter.php:318
       CodeIgniter\CodeIgniter()->handleRequest(null, Object(Config\Cache), false)

  4    FCPATH/index.php:37
       CodeIgniter\CodeIgniter()->run()
kenjis commented 2 years ago

No feedback, so I close.