【问题标题】:How to read a file from a cloud storage bucket via a python app in a local Docker container如何通过本地 Docker 容器中的 python 应用程序从云存储桶中读取文件
【发布时间】:2020-04-06 07:56:50
【问题描述】:

让我以我对 Docker、Jenkins、GCP/云存储和 Python 相当陌生的事实作为开头。

基本上,我想编写一个 Python 应用程序,它在 Docker 容器(alpine3.7 映像)中本地运行,并从放入 GCP 云存储桶的非常大的文本文件中逐行读取块.每一行现在应该只是输出到控制台。

我通过查看工作代码学得最好,我正在转动我的车轮,试图使用这些技术将所有部分组合在一起(对我来说是新的)。

我的本​​地计算机上已经有了该云存储桶的密钥文件。

我也知道这些帖子:

我只是需要一些帮助将所有这些部分组合成一个工作应用程序。

我了解我需要将 GOOGLE_APPLICATION_CREDENTIALS 环境变量设置为容器中密钥文件的路径。但是,我不知道如何以适用于多个开发人员和多个环境(本地、开发、阶段和生产)的方式很好地做到这一点。

【问题讨论】:

  • 不要问“告诉我怎么做”,而是学习每个你不知道的部分。从一些示例开始并实施它们。 Google 的网站、Internet、Stackoverflow 等上有很多示例。然后研究它们的作用。 Stackoverflow 将帮助您解决编码问题。当您的代码有问题时,我们可以为您提供帮助。请记住,最好的起点是阅读所有文档,当有一项让您感到困惑时不要停下来。
  • 第一步大概是写程序,完全无视Docker和Jenkins。如果你可以让它在虚拟环境中工作,那么你可以将它打包在 Docker 中;这里的 Docker 环境没有什么特别之处。

标签: python-3.x docker jenkins google-cloud-platform google-cloud-storage


【解决方案1】:

这只是一个简单的快速入门(我相信它可以做得更好),通过 python 应用程序(部署到 Google Cloud Run 的 Docker 容器)从 Google Cloud Storage 存储桶中读取文件:

您可以在这里找到更多信息link

  1. 创建一个包含以下文件的目录:

    一个。应用程序.py

    import os
    from flask import Flask
    from google.cloud import storage
    
    app = Flask(__name__)
    
    @app.route('/')
    def hello_world():
    
      storage_client = storage.Client()
      file_data = 'file_data'
      bucket_name = 'bucket'
      temp_file_name = 'temp_file_name'
      bucket = storage_client.get_bucket(bucket_name)
      blob = bucket.get_blob(file_data)
      blob.download_to_filename(temp_file_name)
    
      temp_str=''
      with open (temp_file_name, "r") as myfile:
         temp_str = myfile.read().replace('\n', '')
    
     return temp_str
    
    if __name__ == "__main__":
        app.run(debug=True,host='0.0.0.0',port=int(os.environ.get('PORT', 8080))) 
    

    b. Dockerfile

    # Use an official Python runtime as a parent image
    FROM python:2.7-slim
    
    # Set the working directory fo /app 
    WORKDIR /app
    
    # Copy the current directory contents into the container /app
    COPY . /app
    
    # Install any needed packages specified in requirements.txt
    RUN pip install --trusted-host pypi.python.org -r requirements.txt
    RUN pip install google-cloud-storage
    
    # Make port 80 available to the world outside the container
    EXPOSE 80
    
    # Define environment variable
    ENV NAME World
    
    # Run app.py when the container launches
    CMD ["python", "app.py"] 
    

    c。 requirements.txt

    Flask==1.1.1
    gunicorn==19.9.0
    google-cloud-storage==1.19.1
    
  2. 创建服务帐号以访问 Cloud Run 的存储表单:

    gcloud iam service-accounts create cloudrun --description 'cloudrun'
    
  3. 设置服务帐号的权限:

    gcloud projects add-iam-policy-binding wave25-vladoi --member serviceAccount:cloud-run@project.iam.gserviceaccount.com  --role roles/storage.admin 
    
  4. 构建容器镜像:

    gcloud builds submit --tag gcr.io/project/hello
    
  5. 将应用部署到 Cloud Run:

    gcloud run deploy --image gcr.io/project/hello --platform managed ----service-account cloud-run@project.iam.gserviceaccount.com
    

编辑:

本地开发的一种方式是:

  1. 您的 Dev Opp 团队将获得服务帐户 key.json:

    gcloud iam service-accounts keys create ~/key.json --iam-account serviceAccount:cloudrun@project.iam.gserviceaccount.com
    
  2. 将key.json文件存放在同一个工作目录中

  3. Dockerfile 命令 `COPY 。 /app ' 将文件复制到 Docker 容器中

  4. 将 app.py 更改为:

     storage.Client.from_service_account_json('key.json')
    

【讨论】:

  • 非常感谢玛丽安。不幸的是,我无权创建服务帐户、构建应用程序或将应用程序部署到 GCP,我们的 DevOps 团队为我们完成了这些工作。我需要做的是先在本地开发和测试代码,然后让他们为我部署包。如何在本地运行此容器并为其提供允许我的远程计算机访问云存储的环境变量 GOOGLE_APPLICATION_CREDENTIALS(包含 DevOps 提供给我的密钥文件)?我也知道 DevOps 已经设置了 Vault,所以我也在尝试了解它是如何工作的。
  • ENV GOOGLE_APPLICATION_CREDENTIALS /path/to/your/credentials/file/in/container
  • 非常感谢,我想我现在已经解禁了。我仍然不确定什么是最佳实践。我最终做的是将密钥文件移动到名为 .key 的项目文件夹中。然后我将该文件夹添加到 .gitignore 和 .dockerignore 文件中,这样密钥就不会被复制或存储在任何地方(为了安全起见)。然后我用这些行更新了 Dockerfile: COPY .key/key.json /root/key.json ENV GOOGLE_APPLICATION_CREDENTIALS /root/key.json
  • 你可以在这里查看如何分块读取大文件,python link
  • 我可以问一个关于参数“temp_file_name”的问题吗?它是本地 PC 还是云存储中的位置?通过 gloud 命令部署应用程序后,应用程序是否能够从“temp_file_name”读取文件?
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2021-11-25
  • 2021-09-01
  • 2020-10-14
  • 2021-03-27
  • 1970-01-01
相关资源
最近更新 更多