sherlockode / configuration-bundle
用于用户自定义配置值的Symfony包
Requires
- php: ^8.0
- symfony/framework-bundle: ^6.0 || ^7.0
- symfony/validator: ^6.0 || ^7.0
- twig/twig: ^3.0
Requires (Dev)
- phpunit/phpunit: ^9.6
This package is auto-updated.
Last update: 2024-09-26 11:27:04 UTC
README
此包旨在允许用户定义配置选项,在管理面板中非常有用。从您的ENV
或parameters.yml
文件中删除业务逻辑变量!
可用功能
- 定义多个用户可用的配置条目
- 在代码的任何位置检索配置值以用于业务逻辑
- 使用或创建自定义参数类型以提供更好的用户体验
安装
安装此包的最佳方式是依赖Composer
$ composer require sherlockode/configuration-bundle
设置
在内核中启用此包
<?php // config/bundles.php return [ // ... Sherlockode\ConfigurationBundle\SherlockodeConfigurationBundle::class => ['all' => true], ];
您需要一个Parameter
实体以便在数据库中存储配置值。
<?php namespace App\Entity; use Doctrine\ORM\Mapping as ORM; use Sherlockode\ConfigurationBundle\Model\Parameter as BaseParameter; #[ORM\Entity] #[ORM\Table(name: 'parameter')] class Parameter extends BaseParameter { #[ORM\Id] #[ORM\Column(name: 'id', type: 'integer')] #[ORM\GeneratedValue(strategy: 'AUTO')] protected int $id; #[ORM\Column(name: 'path', type: 'string')] protected string $path; #[ORM\Column(name: 'value', type: 'text', nullable: true)] protected ?string $value = null; }
配置
您刚刚创建的实体类必须在包的配置中设置
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: entity_class: parameter: App\Entity\Parameter
现在,您可以使用parameters
键定义您想要的任何配置条目
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: entity_class: parameter: App\Entity\Parameter parameters: contact_email: label: My customer service contact email type: simple # the "simple" type renders by default as a TextType form element max_user_login_attempts: label: Max login attemps before account blocking type: simple options: # it is possible to customize the form type to use for a "simple" parameter type subtype: Symfony\Component\Form\Extension\Core\Type\IntegerType sales_date: label: Sales start date type: datetime options: required: false
翻译
默认情况下,参数标签不使用包提供的表单提供翻译。如果您想使用翻译,可以全局定义一个translation_domain
键,并为每个参数定义,然后使用您的翻译键作为标签。
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: translation_domain: my_app_domain # default domain is false (no translation) parameters: contact_email: label: customer.contact_email type: simple translation_domain: my_param_domain # overrides the global domain sales_date: # no translation domain, fallback to my_app_domain label: sales.start_date type: datetime
选项
每种类型的字段可能接受一系列可以在options
键下定义的选项。
每个字段都可以有一个required
选项,用于定义输入字段是否为必填项(默认为true)。其他选项取决于字段及其需求。例如,选择字段允许定义multiple
和choices
选项以自定义表单。
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: parameters: guess_access: label: Allow guest access type: choice options: required: true multiple: true choices: yes: 1 no: 0
每个字段还可以有一个constraints
选项,用于定义验证约束。您可以使用Symfony内置的约束或添加自己的约束。
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: parameters: website_title: label: Website title type: simple options: required: true constraints: - NotBlank: ~ - Length: min: 8 max: 255 minMessage: 'This field must be at least {{ limit }} characters long' maxMessage: 'This field must be at least {{ limit }} characters long' - App\Validator\ContainsAlphanumeric: message: "The website title can only contains alphanumeric characters"
使用方法
默认控制器
可以使用提供的控制器编辑所有配置参数。您可以通过导入路由文件来访问它,列表将在URI /parameters
中可用。
# config/routing.yaml sherlockode_configuration: resource: "@SherlockodeConfigurationBundle/Resources/config/routing.xml"
您还可以通过templates
配置入口点修改此控制器使用的默认模板
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: templates: edit_form: 'Parameter/my_parameter_list.html.twig'
自定义表单代码
如果您有更具体的用法,可以使用ParametersType
构建自己的表单,这是一个用于编辑参数的专用FormType
。表单的模型数据是一个路径和现有值的关联数组。您可以使用服务sherlockode_configuration.parameter_manager
从数据库获取现有参数。
<?php use Sherlockode\ConfigurationBundle\Form\Type\ParametersType; use Sherlockode\ConfigurationBundle\Manager\ParameterManagerInterface; // $parameterManager has been injected /** @var ParameterManagerInterface $parameterManager */ $data = $parameterManager->getAll(); // or using an associative array: // $data = ['contact_email' => 'me@example.com', 'max_user_login_attempts' => 5]; $form = $this->createForm(ParametersType::class, $data); // handle form submission $form->handleRequest($request); if ($form->isSubmitted() && $form->isValid()) { $params = $form->getData(); foreach ($params as $path => $value) { $parameterManager->set($path, $value); } $parameterManager->save(); } //...
访问配置值
现在您可以使用参数管理器的get
方法检索任何配置值。如果条目尚未设置,您还可以提供要返回的默认值。
$email = $parameterManager->get('contact_email'); $maxAttempts = $parameterManager->get('max_user_login_attempts', 5);
从浏览器导入/导出
您可以将参数导出或导入到yaml文件中。您有两个操作这些操作的路径
sherlockode_configuration.export
sherlockode_configuration.import
您还可以通过在配置中定义自己的来自定义导入表单模板
# config/packages/sherlockode_configuration.yaml sherlockode_configuration: templates: import_form: 'Parameter/my_import_form.html.twig'
从CLI导入/导出
您可以使用这两个Symfony命令导出或导入参数
sherlockode:configuration:export
sherlockode:配置:导入
这些命令依赖于Symfony密钥机制。因此,请确保使用以下命令生成您的凭据
$ php bin/console secrets:generate-keys
事件
当参数保存到数据库时,会触发多个事件
Sherlockode\ConfigurationBundle\Event\PreSaveEvent
在保存参数之前触发;Sherlockode\ConfigurationBundle\Event\SaveEvent
在数据库中新参数值保存后立即触发;Sherlockode\ConfigurationBundle\Event\PostSaveEvent
在SaveEvent之后立即触发。它可以用于自定义重定向或添加闪存消息等;
字段类型
默认类型
以下是该组件提供的字段类型,位于命名空间Sherlockode\ConfigurationBundle\FieldType
- 简单
- 复选框
- 选择
- 日期时间
- 实体
- 图片
- 密码
自定义字段类型
为了添加自定义字段类型,您应该创建一个实现FieldTypeInterface
接口的服务,并将其标记为sherlockode_configuration.field
(或使用自动配置)。
getName()
返回值是在配置中使用的字段类型的别名(如simple
或choice
)。
使用转换器
由于数据库中参数实体的格式(值存储为字符串,无论参数类型如何),无法直接存储复杂值。例如,我们可以将数组序列化以适应字符串类型,或者我们可以存储数据库实体的ID。这个过程可能因您的需求和要存储的值而异,但应用程序需要知道将PHP数据转换为字符串以及相反过程的转换。这是通过转换器完成的。
转换器是一个实现Sherlockode\ConfigurationBundle\Transformer\TransformerInterface
的对象。该接口有两个方法transform
和reverseTransform
,类似于Symfony在表单组件中使用的转换器。
transform
方法接受字符串表示形式并返回PHP值,而reverseTransform
接受您的PHP值并返回相应的标量值。
为了使用,转换器的实例应由对应字段类型的getModelTransformer
方法返回。如果此方法返回null
,则组件认为不需要转换。
组件还提供了一个CallbackTransformer
,它可以用于快速实现。例如,处理数组可以像这样完成
public function getModelTransformer(ParameterDefinition $definition): ?TransformerInterface { return new CallbackTransformer( function ($data) { if (!$data) { return null; } if (false !== ($unserialized = @unserialize($data))) { return $unserialized; } return $data; }, function ($data) { if (is_array($data)) { return serialize($data); } return $data; } ); }