在Drupal8自定义模块中,能否通过自定义JS向PHP控制器请求并获取响应?
实现Drupal 8自定义模块中JS向后端发送POST请求并获取响应
没问题是没问题,但你现在的写法其实不符合Drupal 8的开发规范,而且会有安全风险和路径问题,我给你捋捋正确的实现方式:
为什么直接访问custom.php不可取?
Drupal有一套完整的请求处理和安全验证机制,直接访问模块目录下的PHP文件会绕过这些机制:
- 路径问题:Drupal启用干净URL后,
modules/mymodule/custom.php这个路径可能无法被正确解析,因为Drupal的路由系统会接管所有请求。 - 安全风险:没有CSRF防护、权限验证,容易被恶意请求攻击,也无法使用Drupal的核心功能(比如用户权限、数据库操作)。
正确的实现步骤(推荐)
1. 定义自定义路由
在你的模块目录下创建mymodule.routing.yml文件,定义一个后端接口路由:
mymodule.custom_endpoint: path: '/mymodule/custom-endpoint' defaults: _controller: '\Drupal\mymodule\Controller\CustomController::getData' requirements: _permission: 'access content' # 根据你的需求设置权限,比如自定义权限 methods: [POST] # 指定只接受POST请求
2. 创建控制器类
在模块的src/Controller目录下创建CustomController.php,处理POST请求并返回响应:
<?php namespace Drupal\mymodule\Controller; use Drupal\Core\Controller\ControllerBase; use Symfony\Component\HttpFoundation\JsonResponse; use Symfony\Component\HttpFoundation\Request; class CustomController extends ControllerBase { public function getData(Request $request) { // 获取POST提交的参数(如果有的话) $postParams = $request->request->all(); // 这里写你的业务逻辑,比如返回"test" $response = ['message' => 'test']; // 返回JSON格式响应(推荐用JSON,方便JS解析) return new JsonResponse($response); } }
3. 修改前端JS代码
Drupal会验证POST请求的CSRF令牌,所以要在请求头里带上令牌,同时使用正确的路由路径:
(function ($, Drupal) { Drupal.behaviors.currency = { attach: function (context, settings) { // 获取Drupal提供的CSRF令牌 const csrfToken = drupalSettings.csrf_token; // 路由对应的URL,也可以用Drupal.url('mymodule/custom-endpoint')生成 const endpointUrl = '/mymodule/custom-endpoint'; $.ajax({ url: endpointUrl, type: "POST", headers: { 'X-CSRF-Token': csrfToken }, // 如果需要提交数据,添加data字段 // data: {param1: 'value1', param2: 'value2'}, success: function(data) { console.log(data); // 如果是JSON响应,直接访问data.message就能拿到"test" }, error: function(xhr, status, error) { console.error('请求失败:', error); } }); } }; })(jQuery, Drupal);
4. 安全注意事项
- 权限控制:一定要在路由的
requirements里设置合适的权限,避免未授权用户访问接口。 - 数据验证:如果前端提交了数据,一定要在控制器里验证、过滤,防止SQL注入等安全问题。
- 使用Drupal响应类:尽量用
JsonResponse、Response等Drupal提供的响应类,而不是直接echo,这样符合Drupal的响应流程。
不推荐的方案(直接访问PHP文件)
如果你非要用自定义的custom.php文件,需要先初始化Drupal的环境,否则无法使用Drupal的功能,而且存在安全隐患:
<?php // 引入Drupal的自动加载文件,路径根据你的Drupal根目录调整 require_once '../../autoload.php'; // 初始化Drupal内核 $request = \Symfony\Component\HttpFoundation\Request::createFromGlobals(); $kernel = \Drupal\Core\DrupalKernel::createFromRequest($request); $kernel->boot(); // 处理逻辑 echo "test";
但再次强调,这种方法不符合Drupal规范,不建议使用。
内容的提问来源于stack exchange,提问作者Sathish Sundar
相关产品推荐
相关产品推荐

