【问题标题】:how to set one container to allow it's entire volume access to another container using docker-compose如何使用 docker-compose 设置一个容器以允许其整个卷访问另一个容器
【发布时间】:2020-03-28 09:59:29
【问题描述】:

我有 4 个使用 docker-compose 运行的服务

1) python-api 2)python-model 3)python-celery 4)redis-server

流程:

1) python-api 被邮递员用图像和一些文本作为 8000 端口上的参数命中。

2) python-api 将图像和数据传递到端口 8001 上的 python-model 以进行一些 ML 预测。

3) 然后将修改后的 JSON 格式的图片和响应数据传递给python-celery 用于触发邮件。

错误:python-celery 能够抓取python-model 在步骤 3 中发送的图像和响应。但目前无法读取图片

错误日志:

========================
python-celery_1      | Received task: classify_crack.tasks.queue_task_v3[d71f976f-b2e7-4b29-9147-35996668de17]
python-celery_1      | == unique_file_index
python-celery_1      | AANJkaNIJSDHURHQEYRQ(*R
python-celery_1      | /python-model/server/classify_crack/inference/images/202003251237371/202003251237371_0.jpg 64
python-celery_1      | Task classify_crack.tasks.queue_task_v3[d71f976f-b2e7-4b29-9147-35996668de17] raised unexpected: AttributeError("'NoneType' object has no attribute 'shape'",)
python-celery_1      | Traceback (most recent call last):
python-celery_1      |   File "/usr/local/lib/python3.6/site-packages/celery/app/trace.py", line 385, in trace_task
python-celery_1      |     R = retval = fun(*args, **kwargs)
python-celery_1      |   File "/usr/local/lib/python3.6/site-packages/celery/app/trace.py", line 648, in __protected_call__
python-celery_1      |     return self.run(*args, **kwargs)
python-celery_1      |   File "/python-api/classify_crack/tasks.py", line 690, in queue_task_v3
python-celery_1      |     save_heat_map_v2(predictions, img_path, _dir, unique_file_index, original_image_index, i, grid_size=grid_size, metadata=metadata, StoredFileLinks=StoredFileLinks, row_stride=row_stride, col_stride=col_stride)
python-celery_1      |   File "/python-api/classify_crack/tasks.py", line 128, in save_heat_map_v2
python-celery_1      |     num_row_splits = int(np.ceil(img.shape[0]/row_stride))
python-celery_1      | AttributeError: 'NoneType' object has no attribute 'shape'

python-celery 代码中出现错误的行:

  img = cv2.imread(img_path)
  print(img_path)
  print(img)
  # print(img_path,grid_size)
  splits = int(np.ceil(img.shape[0]/row_stride))

这里,img_path 是正在打印的容器内的有效路径。但我无法读取图像,因为img 返回None。和splits 行给了我上述错误。

我收到错误的原因:

我收到此错误是因为它正在尝试访问文件夹路径: /python-model/server/classify_crack/inference/images/202003251237371/202003251237371.jpg,但 python-celery 无法访问名为 202003251237371 的文件夹。

证明:

我尝试使用命令:

command: >
      sh -c "ls '/python-model/server/classify_crack/inference/images' &&

python-modelpython-celery 服务的 docker-compose 中,当我再次运行所有容器时,我得到以下结果:

python-model_1       | 201801151543500
python-model_1       | 201801151543500.jpg
python-model_1       | IMG_20190307_184100
python-model_1       | IMG_20190307_184100.jpg
python-model_1       | extracted_input_0_0 (15)
python-model_1       | extracted_input_0_0 (15).jpg
python-model_1       | extracted_input_0_0 (16)
python-model_1       | extracted_input_0_0 (16).jpg
python-model_1       | extracted_input_0_0 (18)
python-model_1       | extracted_input_0_0 (18).jpg
python-model_1       | extracted_input_0_0 (19)
python-model_1       | extracted_input_0_0 (19).jpg
python-model_1       | extracted_input_0_0 (9)
python-model_1       | extracted_input_0_0 (9).jpg
python-model_1       | file
python-model_1       | image (2)
python-model_1       | image (2).png
python-model_1       | 202003251237371
python-model_1       | 202003251237371.jpg
python-model_1       | image_X
python-model_1       | image_X.png
python-model_1       | original
python-model_1       | original.jpg
python-model_1       | original_image_0
python-model_1       | original_image_0.jpg



python-celery_1      | 20013V_Y.JPG
python-celery_1      | extracted_input_0_0 (15).jpg
python-celery_1      | extracted_input_0_0 (16).jpg
python-celery_1      | extracted_input_0_0 (18).jpg
python-celery_1      | extracted_input_0_0 (19).jpg
python-celery_1      | extracted_input_0_0 (4).jpg
python-celery_1      | 202003251237371.jpg

现在很明显,python-celery 无法显示文件夹 202003251237371 的图像名称为 202003251237371.jpg,我可以在 python-model 中看到。

如何解决这种情况并允许python-celery 访问此类图像文件夹?

docker-compose

version: "3"
networks:
  app-tier:
    driver: bridge

volumes:
  app-volume: {}

services:
  python-api-celery: &python-api-celery
    build:
      context: /Users/AjayB/Desktop/python-api/
    networks:
      - app-tier
    volumes:
      - app-volume:/python-model/server/classify_crack/:rw
    environment:
      - PYTHON_API_ENV=development

    command: >
      sh -c "python manage.py makemigrations &&
             python manage.py migrate"

  python-api: &python-api
    <<: *python-api-celery
    ports:
      - "8000:8000"
    command: >
      sh -c "python manage.py runserver 0.0.0.0:8000"

  python-celery: &python-celery
    <<: *python-api-celery
    depends_on:
      - redis
    links:
      - python-model

    command: >
      sh -c "ls '/python-model/server/classify_crack/inference/images' &&
             celery -A server worker -l info"

  redis:
    image: redis:5.0.8-alpine
    hostname: redis
    networks:
          - app-tier
    expose:
      - "6379"
    volumes:
      - app-volume:/python-model/server/classify_crack/:rw
    ports:
      - "6379:6379"
    command: ["redis-server"]

  python-model: &python-model
    build:
      context: /Users/AjayB/Desktop/Python/python/
    ports:
      - "8001:8001"
    networks:
      - app-tier
    environment:
      - PYTHON_API_ENV=development
    volumes:
      - app-volume
    depends_on:
      - python-api
    command: >
      sh -c "ls '/python-model/server/classify_crack/inference/images' &&
             cd /python-model/server/ &&
             python manage.py migrate &&
             python manage.py runserver 0.0.0.0:8001"

容器实例:

CONTAINER ID        IMAGE                          COMMAND                  CREATED             STATUS              PORTS                    NAMES
7374a7b0b051        integrated_python-celery       "sh -c 'celery -A se…"   13 minutes ago      Up 5 seconds        8000/tcp                 integrated_python-celery_1
8eb9a754996a        integrated_python-model        "sh -c 'cd /python-m…"   20 minutes ago      Up 5 seconds        0.0.0.0:8001->8001/tcp   integrated_python-model_1
b268b7bd1ac4        integrated_python-api-celery   "sh -c 'python manag…"   20 minutes ago      Up 6 seconds        8000/tcp                 integrated_python-api-celery_1
869bb5fc21b2        integrated_python-api          "sh -c 'python manag…"   20 minutes ago      Up 6 seconds        0.0.0.0:8000->8000/tcp   integrated_python-api_1
c85a1becea34        redis:5.0.8-alpine             "docker-entrypoint.s…"   About an hour ago   Up 6 seconds        0.0.0.0:6379->6379/tcp   integrated_redis_1

【问题讨论】:

  • 这似乎与the question you asked yesterday 基本相同;有什么不同?
  • @DavidMaze - 是的,还没有得到答案,所以我想也许我可以用更好的方式改写它。删除了我昨天的帖子。很抱歉引起骚动。
  • 我不明白您显示的堆栈跟踪如何与文件读取错误相关联,您能澄清一下吗?涉及哪些文件?一个容器在卷中创建的文件是如何被另一个容器读取的?
  • @PierreB。难道我们不能有 1 个公用卷供 1 个容器使用来写入它,而另一个容器可以在一段时间后从它读取吗?在本地运行相同的系统可以使 celery 运行顺畅。即使在这里,在这种情况下,python-modelpython-api 中提取图像并正确进行预测。问题只发生在芹菜上。由于它是一个 django 应用程序,python-apipython-model 的 views.py 被用于通信。 celery 在 python-api 存储库中的一个单独的 python 文件中
  • 是的,这是可能的,但只有堆栈跟踪,我不明白你是如何从每个容器中写入和读取有问题的文件的。显示应该写入和读取文件的代码的 sn-p 可能有助于理解您的上下文;)

标签: python python-3.x docker docker-compose celery


【解决方案1】:

来自OpenCV-Python 文档:`

即使图片路径错误,也不会抛出任何错误,但是 print img 会给你 None

这似乎正是这里发生的事情。也许您的图像路径看起来正确但实际上是错误的,可能的原因:

  • 您使用的相对或绝对路径不正确
  • 图像文件存在但无效
  • 文件夹或文件/python-model/server/classify_crack/inference/images/202003251237371/202003251237371.jpg 的权限不允许运行python-celery 的用户读取它

否则,您的 Compose 卷定义看起来不错。

【讨论】:

  • 我们可以通过检查文件的所有者:组和模式以及每个容器下运行的用户来验证这一点。如果您可以将其添加到您的问题中,我将相应地进行编辑
  • 我刚刚将图像路径编辑为img_path: /python-model/server/classify_crack/inference/images/202003251237371_0.jpg。然而,它给出了同样的错误。我在 celery 和 model 中都使用命令 ls '/python-model/server/classify_crack/inference/images 来查看内容计数。python-celery 不显示 images 文件夹内的图像名称文件夹。芹菜打印的图像数量也少于模型打印的图像数量。 (同一时间同一地点)。对我来说似乎是一个访问问题。如何解决这个问题?并授予芹菜权限?
  • 我还尝试了命令docker run --entrypoint "" &lt;image-name&gt; whoami 来查找每个图像的用户。它打印了root。好像我的安装工作不正常。
  • 最糟糕的是,这个错误只存在于少数 API 中,其余的 API 是给出错误的 API 的子集,这些都可以正常工作。
  • 感谢您的帮助。图像路径是正确的,图像也存在。似乎访问问题。终于解决了并没有做太多。只是我在我的部分答案中提到的东西。,它奏效了。你的贡献给你满分。
【解决方案2】:

在我看来,你应该遵循一个深入的教程,了解如何在 Docker 和 Kubernetes 中使用 celery 和 python API :)

【讨论】:

    【解决方案3】:

    错误终于解决了:

    它在 python-api 的 views.py 开头包含以下行:

        self.cur_file_dir_path = '/data/'
        self.cur_file_folder_path = '/'.join(file_path.split('/')[:-1])
        if not os.path.exists('{}/inference'.format(self.cur_file_folder_path)):
          os.makedirs('{}/inference'.format(self.cur_file_folder_path))
    

    另外,修改了docker-compose 中的卷名,以避免混淆。不敢相信花了将近 1 周的时间才解决了这个问题。

    码头工人撰写:

    version: "3"
    
    networks:
      app-tier:
        driver: bridge
    
    volumes:
      app-volume: {}
    
    services:
      python-api-celery: &python-api-celery
        build:
          context: /Users/AjayB/Desktop/python-api/
        networks:
          - app-tier
        volumes:
          - app-volume:/data/:rw
        environment:
          - PYTHON_API_ENV=development
    
        command: >
          sh -c "python manage.py makemigrations &&
                 python manage.py migrate"
    
      python-api: &python-api
        <<: *python-api-celery
        ports:
          - "8000:8000"
        command: >
          sh -c "python manage.py runserver 0.0.0.0:8000"
    
      python-celery: &python-celery
        <<: *python-api-celery
        depends_on:
          - redis
        command: >
          sh -c "ls '/data/' &&
                 celery -A server worker -l info"
    
      redis:
        image: redis:5.0.8-alpine
        hostname: redis
        networks:
              - app-tier
        expose:
          - "6379"
        volumes:
          - app-volume:/data/:rw
        ports:
          - "6379:6379"
        command: ["redis-server"]
    
      python-model: &python-model
        build:
          context: /Users/AjayB/Desktop/Python/python/
        ports:
          - "8001:8001"
        networks:
          - app-tier
        environment:
          - PYTHON_API_ENV=development
        volumes:
          - app-volume:/data/:rw
        depends_on:
          - python-api
    
        command: >
          sh -c "ls '/data/' &&
                 cd /python-model/server/ &&
                 python manage.py migrate &&
                 python manage.py runserver 0.0.0.0:8001"
    

    【讨论】:

      猜你喜欢
      • 2021-03-04
      • 2021-12-08
      • 2022-01-11
      • 2017-07-12
      • 2023-02-24
      • 1970-01-01
      • 1970-01-01
      • 2019-06-13
      • 1970-01-01
      相关资源
      最近更新 更多