Drupal 服务 - 直接文件 URL 而不是文件资源引用

Drupal Services - Direct file URL instead of file resource reference

我正在使用 Drupal servicesservices_entity 模块来构建 Web 服务。问题是,当使用字段等将文件附加到实体时,服务端点将文件显示为资源引用:

array (
    resource: file,
    id: xx,
    uri: /entity_file/xx.json
)

事实是,每次您希望显示一个文件时,您都必须发出 2 个或更多请求:

问题是,如何直接获取文件 URL 而无需进行额外请求。因此,首选响应是:

array (
    resource: file,
    id: xx,
    uri: /entity_file/xx.json,
    url: http://.../sites/.../files/foo/bar/b-reft.jpg
)

我找了几个小时但没有找到答案,所以我想我会分享我找到的解决方案。我相信它会帮助很多人(我也希望我可以分享我的模块,以支持 services_entity 模块的复杂索引查询参数)。

声明资源控制器

由于数据由 ServicesEntityResourceController 返回,我决定使用 hook_services_entity_resource_info() 声明我自己的资源控制器.

/**
 * Implements hook_entity_resource_info()
 */
function c11n_services_entity_resource_info() {

    $output = array();

    $output['c11n'] = array (
        'title' => 'Clean Entity Processor - Customized',
        'description' => 'An entity wrapper based on the "Clean Entity Wrapper" wrapper with certain fixes and improvements.',
        'class' => 'ServicesEntityResourceControllerC11n',
    );

    return $output;

}

声明控制器Class

在此之后,我声明了控制器 class:

ServicesEntityResourceControllerC11n extends ServicesEntityResourceControllerClean

覆盖 get_resource_reference() 方法

最后一步 (toque final) 是添加文件 URL。我决定处理 parent class 的输出并在 URL 中添加一个文件。实际数据由 ServicesEntityResourceController::get_resource_reference() 方法返回。所以,我就这样覆盖了它,就完成了。

protected function get_resource_reference($resource, $id) {

    $output = parent::get_resource_reference($resource, $id);

    switch ($resource):
        case 'file':
            $file = file_load($id);
            if ($file)
                $output['url'] = file_create_url($file->uri);
            break;
        case 'taxonomy_term':
            // Do something for taxonomy terms
            break;
    endswitch;

    return $output;

}

它解决了这个问题。但是,我并不认为它是最好的解决方案,但有一些解决方案比 none.

更好

备选方案

您可以更改 entity_file 资源并添加名为 download 的 targeted_action 嵌入 。在回调中,只需为文件 mime-type 发送 headers,然后使用 fpasthru()[=46= 呈现文件内容] 或 echo file_get_contents().