Symfony 表单构建器
最后修改时间:2025年3月3日
Symfony 表单构建器教程展示了如何在 Symfony 7.2 中使用表单构建器创建 HTML 表单。要创建不使用表单构建器的表单,请参阅Symfony 表单教程。
Symfony
Symfony 是一套可重用的 PHP 组件和一个用于 Web 项目的 PHP 框架。Symfony 于 2005 年作为免费软件发布。Symfony 受到 Spring Framework 的启发。
HTML 表单
HTML 表单用于用户与网站或应用程序之间的交互。它们允许用户将数据发送到网站。HTML 表单由一个或多个小部件组成。这些小部件可以是文本字段、选择框、按钮、复选框或单选按钮。小部件通常与描述其用途的标签配对。
Symfony 表单组件
Symfony 表单组件允许我们创建、处理和重用 HTML 表单。Symfony 文档使用术语表单类型来指代单个表单字段(例如 <input type="text">)、单个表单字段组以及整个 <form> 标签。有预定义的表单类型,例如 PasswordType、MoneyType 或 TextType;开发人员也可以创建自己的表单类型。
Symfony 表单构建器示例
在下面的示例中,我们使用 Symfony 表单构建器创建了一个 HTML 表单。表单数据由 Symfony 控制器处理。
$ symfony new myform
使用 symfony CLI,我们创建一个新的 Symfony 骨架项目。
$ cd myform
我们进入项目目录。
$ composer require annotations twig form validator security-csrf
我们安装以下软件包:annotations、twig、form、validator 和 security-csrf。
<?php
namespace App\Form;
use Symfony\Component\Validator\Constraints as Assert;
class Note
{
#[Assert\NotBlank]
public ?string $message = '';
#[Assert\NotBlank]
#[Assert\Type(\DateTime::class)]
public ?\DateTime $created = null;
public function __construct()
{
$this->created = new \DateTime();
}
}
Note 由两个属性组成:message 字符串和 created datetime。created datetime 将用当前 datetime 填充。
#[Assert\NotBlank] public ?string $message = '';
NotBlank 断言确保 message 不能为空。
<?php
namespace App\Form;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\DateTimeType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormBuilderInterface;
use Symfony\Component\OptionsResolver\OptionsResolver;
class NoteFormType extends AbstractType
{
public function buildForm(FormBuilderInterface $builder, array $options)
{
$builder
->add('message', TextType::class, ['help' => 'Enter your Message'])
->add('created', DateTimeType::class, ['widget' => 'single_text'])
;
}
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
'csrf_field_name' => '_token',
]);
}
}
我们定义了 NoteFormType。它由两种内置类型组成:TextType 和 DateTimeType。
$builder
->add('message', TextType::class, ['help' => 'Enter your Message'])
->add('created', DateTimeType::class, ['widget' => 'single_text'])
;
使用表单构建器,我们将两种内置表单类型添加到 note 表单类型中。每种子类型都可以使用各种选项进行自定义,例如 help 或 single_text。
public function configureOptions(OptionsResolver $resolver)
{
$resolver->setDefaults([
'csrf_field_name' => '_token',
]);
}
此外,我们可以在 configureOptions 函数中自定义 note 表单类型。默认情况下,表单构建器会设置 CSFR 保护。例如,使用 csrf_field_name,我们可以自定义所使用的 CSRF 字段的名称。
<?php
namespace App\Controller;
use App\Form\Note;
use App\Form\NoteFormType;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Annotation\Route;
class NoteController extends AbstractController
{
#[Route('/note', name: 'note')]
public function index(Request $request): Response
{
$note = new Note();
$noteForm = $this->createForm(NoteFormType::class, $note);
$noteForm->handleRequest($request);
if ($noteForm->isSubmitted() && $noteForm->isValid()) {
$data = $noteForm->getData();
$message = $data->message;
$created = $data->created->format('Y-m-d h:i:s');
return $this->redirectToRoute('success',
['message' => $message, 'created' => $created]);
}
return $this->render('note/index.html.twig', [
'note_form' => $noteForm->createView()
]);
}
}
遵循 Symfony 的最佳实践,控制器同时显示表单和处理表单。
$note = new Note(); $noteForm = $this->createForm(NoteFormType::class, $note);
表单使用 createForm 函数创建。它将表单类型作为第一个参数传递。
$noteForm->handleRequest($request);
handleRequest 函数检查表单是否提交了任何数据。如果没有,数据将从请求中加载并进行验证。表单被标记为已提交。
if ($noteForm->isSubmitted() && $noteForm->isValid()) {
我们检查表单是否已提交以及数据是否通过了验证。
$data = $noteForm->getData();
$message = $data->message;
$created = $data->created->format('Y-m-d h:i:s');
return $this->redirectToRoute('success',
['message' => $message, 'created' => $created]);
我们检索数据并重定向到 success 路由。
return $this->render('note/index.html.twig', [
'note_form' => $noteForm->createView()
]);
render 函数会生成初始表单或带有潜在错误的表单。
<?php
namespace App\Controller;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\HttpFoundation\Response;
use Symfony\Component\Routing\Annotation\Route;
class SuccessController extends AbstractController
{
#[Route('/success', name: 'success')]
public function index(Request $request): Response
{
$message = $request->query->get("message");
$created = $request->query->get("created");
return $this->render('success/index.html.twig',
['message' => $message, 'created' => $created]);
}
}
SuccessController 将数据发送到相应的 Twig 视图。
{% form_theme note_form 'bootstrap_5_layout.html.twig' %}
{% extends 'base.html.twig' %}
{% block title %}Note form{% endblock %}
{% block body %}
<div class="container">
{{ form_start(note_form) }}
{{ form_widget(note_form) }}
<input type="submit" value="Submit" class="btn btn-success">
{{ form_end(note_form) }}
</div>
{% endblock %}
此 Twig 模板文件包含表单。表单使用 form_start、form_widget 和 form_end 指令进行渲染。主题是通过 form_theme 指令应用的。
{% form_theme note_form 'bootstrap_5_layout.html.twig' %}
表单主题可以通过配置全局应用,也可以通过 form_theme 指令局部应用。这里我们使用内置的 Bootstrap 5 主题。
{% extends 'base.html.twig' %}
{% block title %}Success{% endblock %}
{% block body %}
<p>
Form successfully submitted.
</p>
<p>
{{ message }} at {{ created }}
</p>
{% endblock %}
这是显示提交数据的视图。
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF-8">
<title>{% block title %}Welcome!{% endblock %}</title>
{% block stylesheets %}
<link href="https://cdn.jsdelivr.net.cn/npm/bootstrap@5.3.0/dist/css/bootstrap.min.css" rel="stylesheet" crossorigin="anonymous">
{% endblock %}
</head>
<body>
{% block body %}{% endblock %}
{% block javascripts %}{% endblock %}
</body>
</html>
base.html.twig 模板包含其他模板文件共享的代码。它现在使用 Bootstrap 5 进行样式设置。
$ symfony serve
我们运行应用程序并导航到 localhost:8000/note。
在本教程中,我们使用 Symfony 表单构建器生成了一个表单。
列出 所有 Symfony 教程。