【问题标题】:Image loaded using send_data are half broken when loading multiple images in iOS在 iOS 中加载多个图像时,使用 send_data 加载的图像会损坏一半
【发布时间】:2020-11-27 19:42:16
【问题描述】:

由于我不想进入这里的原因,我需要在使用此标签加载时动态调整来自用户手机的图像(并且是愚蠢的大)的大小

image_tag thumbnail_document_path(document.id), alt: "#{document.document_title}", class: "document-thumbnail"

这会调用缩略图控制器操作

  def thumbnail
    document = Document.find params[:id]
    image_meta = document.image_details.first
    image = Document.get_image_for_display image_meta
    send_data image, type: "image/jpg", disposition: "inline"
  end

Document.get_image_for_display 从数据库中提取 blob,检查我们单独保存的元数据,看看它是需要转换为图像的 PDF 还是需要调整大小的大图像,然后执行所有操作并异步发送斑点。这适用于除 iOS 之外的所有设备。在 iOS Safari 和 Chrome 上,如果您同时以这种方式加载多个图像this happens。如果有人对此有解释或解决方案,我很乐意听到!

编辑:此应用程序与 C++ 桌面应用程序共享服务器和数据库,并且不能(也不能)访问服务器上存储这些文件的位置,并且在数百个客户端中存在数十万个文件服务器,因此由于物理存储限制,将调整大小的版本存储在完整大小的旁边是不可能的。仅在尝试转换和加载超过 3 张大图像时才会出现此问题,然后只有第一张图像仍然损坏,其他图像将完全加载,尽管它们需要一段时间才能完成。

【问题讨论】:

  • 仅供参考,我尝试在图像加载完成后使用 javascript 强制重绘,但仍未修复
  • “异步发送 blob”是什么意思?您在控制器操作中使用它,我不明白这怎么可能是异步的。
  • 抱歉,非阻塞可能是更好的描述。控制器操作的其余部分运行,页面的其余部分在图像缩放时加载。

标签: ios ruby-on-rails ruby


【解决方案1】:

您的thumbnail 操作代码暗示get_image_for_display 必须是同步的,因为它的返回值会立即使用。如果您使用的是线程服务器(如 puma),它也应该是可重新输入的 - 这样两个实例就可以在一个进程中同时运行。这要求它不写入任何状态(类变量、其他全局变量),或者至少通过同步来完成。 (互斥体等)。

但即使您的服务器是单线程的,在生产中通常也有多个进程。因此,对于函数的每个步骤,请考虑并发运行如何干扰。

例如:我可以猜测该函数运行一些外部应用程序来处理数据。首先要检查是否存在临时文件名冲突——当两个实例将数据写入同一个文件时(即使数据将相同)——显然它会被破坏。

【讨论】:

    【解决方案2】:

    这通常发生在服务器由于网络或其他原因而在流式传输数据时中断与浏览器的连接。

    这里推荐的方法是使用send_file 或通过执行类似的操作使用buffer。分块流式传输始终确保数据完全流式传输到客户端

    File.open('filename.jpeg', 'rb') do |file|
      send_data(file.read, type: "image/jpg", disposition: "inline")
    end
    

    【讨论】:

      猜你喜欢
      • 2015-03-29
      • 2019-10-19
      • 2015-12-11
      • 1970-01-01
      • 2015-03-22
      • 1970-01-01
      • 2015-08-02
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多