yiisoft/yii2-twig

Form rendering incorrect with yii2-twig 2.5.0 / twig 3.9

Opened this issue ยท 8 comments

What steps will reproduce the problem?

Update yii2-twig to v2.5.0 (support for twig 3.9 -> see #154 )

What's expected?

Forms are rendered correctly

What do you get instead?

The form is rendered, but after the fields.
e.g.
instead of

<form>
<input foo... />
<input bar... />
</form>

it renders:

<input foo.../>
<input bar... />
<form></form

following twig form code is used:

{% set form = active_form_begin({'action':path(['/account/register'])}) %}
{{ form.field(customer,'email').validator('email').emailInput() | raw }}
{{ form.field(customer,'newpassword').validator('^.{8,}$').label('signup.form.password.label'|i18n).passwordInput({'autocomplete':'new-password'}) | raw }}
{{ active_form_end() }}

I'm not proficient in yii2, but from what I discovered, it happends in yii\widgets\ActiveForm::run() method.
https://github.com/yiisoft/yii2/blob/52e4a3e645eaece47c3f9dddac7c1771a5bd7804/framework/widgets/ActiveForm.php#L225

        $content = ob_get_clean();
        $html = Html::beginForm($this->action, $this->method, $this->options);
        $html .= $content;

        if ($this->enableClientScript) {
            $this->registerClientScript();
        }

        $html .= Html::endForm();

The $content is empty (I assume because of the ob_get_clean() behaviour in twig 3.9? resulting in returned $html string:
<form id="customer-signup-form" action="/account/register" method="post" data-form></form>

Since I'm new into this yii2 project, I have limited knowledge of the inner workings

Additional info

Q A
Yii version 2.0.50
Yii Twig version 2.5.0
Twig version 3.10
PHP version 8.1
Operating system Linux

@diffy0712 can you look into it?

Hello,

I had a quick look and unfortunately this test was not covering this case and did not fail on the latest fix for twig3.9 support. This for sure needs to be handled. I think I can add another test, which would fail on the same error.

The problem is indeed the 'ob_get_clean' call again, which in case of the 'end_page' could be moved outside of twig's render (the previous fix for the twig3.9 support pr), but in this case it cannot be done as the form can be anywhere in the content.
I figured that any 'Widget' which relies on the ob to have the content to override will fail similarly.

I try to come up with a solution for this one and keep you guys updated.

Until then, you can fix the package version to 2.4.3, which will prevent the 'unsupported twig version' from installing and was merged in this pr. composer require "yiisoft/yii2-twig:2.4.3"

I think I can add another test, which would fail on the same error.

That would be great as a first step.

Thanks for looking into it. I'm currently debugging another case, will do a seperate ticket for that.

Similar problem with version 2.5.0 and twig 3.10.3, after the update the register_asset_bundle function does not work

Hi,

sorry for the inactivity, I have been a bit busy lately. I tried to get around the problem, but I could not yet found a good solution with no breaking changes or overriding the Yii base classes.

Hi, anything where I can support you (even with my little yii / twig base knowledge?)

@impayru

Similar problem with version 2.5.0 and twig 3.10.3, after the update the register_asset_bundle function does not work

I was able to solve your problem by using end_page() instead of void(this.endPage()) in the page layouts.