草庐IT

Docker 和 "The OpenSSL library reported an error"部署时

coder 2023-05-06 原文

我正在通过 Rust 和 Rocket 通过 Amazon Elastic Container Service 提供 API。每当我将对象放入或获取到 Amazon S3 时,它在本地运行良好,但如果部署在 Amazon ECS 上,我会收到以下运行时错误:

HttpDispatch(HttpDispatchError { message: "The OpenSSL library reported an error" })

当我在我的机器上运行 Docker 镜像时也会发生这种情况。

我在发生错误的地方添加了评论:

use super::types::SomeCustomType;
use rusoto_core::{DefaultCredentialsProvider, Region, default_tls_client};
use rusoto_s3::{S3, S3Client, GetObjectRequest};

pub fn load_data_from_s3(object_name: String) -> SomeCustomType {
    let credentials = DefaultCredentialsProvider::new().unwrap();
    let client = S3Client::new(default_tls_client().unwrap(), credentials, Region::UsWest2);
    let mut request = GetObjectRequest::default();
    request.bucket = "bucket-name".to_string();
    request.key = object_name.to_string();
    match client.get_object(&request) {
        // *** This is going to fail in docker container on run-time ***
        Ok(file) => {
            // this part is actually not important for this example,
            // so code has been omitted
            someCustomType
        }
        Err(e) => {
            println!("{:?}", e); // *** errors out here! ***
            SomeCustomType::default()
        }
    }
}

Cargo.toml

[dependencies]
brotli="1.0.8"
chrono = "0.3.1"
fnv = "1.0.5"
rusted_cypher = "1.1.0"
rocket = { git = "https://github.com/SergioBenitez/Rocket", rev = "614297eb9bc8fa5d9c54f653dc35b8cc3a22891f" }
rocket_codegen = { git = "https://github.com/SergioBenitez/Rocket", rev = "614297eb9bc8fa5d9c54f653dc35b8cc3a22891f" }
rocket_contrib = { git = "https://github.com/SergioBenitez/Rocket", rev = "614297eb9bc8fa5d9c54f653dc35b8cc3a22891f" }
rusoto_core = "0.25.0"
rusoto_s3 = "0.25.0"
serde = "1.0.8"
serde_json = "1.0.2"
serde_derive = "1.0.8"

这就是我在 macOS 上构建 Docker 镜像的方式:

cargo clean &&
docker run -v $PWD:/volume -w /volume -t manonthemat/muslrust cargo build --release &&
docker build -t dockerimagename .

Docker 镜像 manonthemat/muslrust 本质上是 clux/muslrust。我必须构建自己的镜像,因为我需要更新的 Rust 夜间构建。

这是(简化的)Dockerfile,到目前为止对我来说效果很好:

FROM scratch
ADD target/x86_64-unknown-linux-musl/release/project /
CMD ["/project"]

我尝试解决的一些问题......

  1. 在 Cargo.toml 中添加了 openssl = "0.9.14"

  2. 将我的 Dockerfile 更改为:

    FROM alpine:edge
    
    ADD target/x86_64-unknown-linux-musl/release/project /    
    RUN apk add --no-cache curl perl openssl-dev ca-certificates linux-headers build-base zsh
    
    CMD ["/project"]
    

    这也没有改变任何东西,但给了我更多的选择。

  3. 我把cargo clean之后的交叉编译步骤改成这样:

    docker run -v $PWD:/volume -w /volume -e RUST_LOG="rusoto,hyper=debug" -e OPENSSL_STATIC=1 -e OPENSSL_DIR=/usr/local -t manonthemat/muslrust cargo build --release --features "logging"
    

    新建 docker 镜像后,获取 shell:

    docker run -i -e ROCKET_ENV=prod -e ROCKET_ADDRESS=0.0.0.0 -e RUST_LOG="rusoto,hyper=debug" dockerimagename /bin/zsh
    

    在那里,我通过为不存在的 ssl 证书提供不同的路径来执行我的项目,但没有不同的效果。

    在下一次运行中,我将其设置为指向不同的路径: SSL_CERT_DIR=/etc/ssl/certs/project 打印出 client.get_object(&request) 调用的错误时,我得到了一个有趣的结果:

    Unknown("<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<Error><Code>SignatureDoesNotMatch</Code><Message>The request signature we calculated does not match the signature you provided. Check your key and signing method.</Message><AWSAccessKeyId>...
    
  4. 我用 aws-sdk-rust crate 替换了 rusoto

thread 'main' panicked at 'Error dispatching request: HttpDispatchError { message: "the handshake failed" }', /checkout/src/libcore/result.rs:860            stack backtrace:
    0: std::sys::imp::backtrace::tracing::imp::unwind_backtrace                                                                                                            at ./checkout/src/libstd/sys/unix/backtrace/tracing/gcc_s.rs:49
    1: std::sys_common::backtrace::_print                                                                                                                                  at ./checkout/src/libstd/sys_common/backtrace.rs:71
    2: std::panicking::default_hook::{{closure}}                                                                                                                           at ./checkout/src/libstd/sys_common/backtrace.rs:60
              at ./checkout/src/libstd/panicking.rs:355
    3: std::panicking::default_hook
              at ./checkout/src/libstd/panicking.rs:371
    4: std::panicking::rust_panic_with_hook
             at ./checkout/src/libstd/panicking.rs:549
    5: std::panicking::begin_panic
             at ./checkout/src/libstd/panicking.rs:511
    6: std::panicking::begin_panic_fmt
             at ./checkout/src/libstd/panicking.rs:495
    7: rust_begin_unwind
             at ./checkout/src/libstd/panicking.rs:471
    8: core::panicking::panic_fmt
             at ./checkout/src/libcore/panicking.rs:69
    9: core::result::unwrap_failed
   10: <aws_sdk_rust::aws::s3::s3client::S3Client<P, D>>::get_object
   11: himitsu::ingest::load_data_from_s3
   12: himitsu::ingest::load_data
   13: himitsu::main
   14: __rust_maybe_catch_panic
             at ./checkout/src/libpanic_unwind/lib.rs:98
   15: std::rt::lang_start
             at ./checkout/src/libstd/panicking.rs:433
             at ./checkout/src/libstd/panic.rs:361
             at ./checkout/src/libstd/rt.rs:59
  1. 我通过 VirtualBox 在我的 Mac 上安装了 Linux 发行版,更新了库,安装了 OpenSSL 头文件和 rust,然后导入了项目。现在我马上收到 SignatureDoesNotMatch 错误。我验证了我可以通过主机的 vpn 通过 https 访问 Neo4j 服务器,因此 SSL 似乎至少可以部分工作。

  2. 在 Amazon ECS-Optimized Amazon Linux AMI 2017.03.a 上编译和运行该项目有效。构建 docker 镜像也可以。从该系统中运行 docker 镜像不会,因为它返回 standard_init_linux.go:178: exec user process cause "no such file or directory" 即使该文件存在,具有正确的权限,可以对其运行其他操作等...只是不执行它。回滚到没有任何 S3/OpenSSL 依赖项的先前状态时也是如此。这适用于 scratchalpine 基本图像。但是,如果我使用 ubuntu 作为基础镜像构建 docker 镜像,我会运行 S3/OpenSSL 之前的版本。对于带有 rusuto 的版本,我会收到 OpenSSL 错误,即使在安装 OpenSSL 库及其头文件时也是如此。

  3. 在我的 Mac 上编译 Docker 镜像,推送到私有(private)仓库到 docker hub。通过 ssh session 将该 docker 镜像拉到 EC2 实例上(与 6 中的相同)。现在运行它不会像 6 中那样给我“没有这样的文件或目录”错误,而是好的 ol' HttpDispatch(HttpDispatchError { message: "The OpenSSL library reports an error"}) (现在即使将 SSL_CERTS_DIR=/etc/ssl/certs 传递到容器的环境中)

最佳答案

这些是我为在 AWS 上进行部署所采取的步骤。

我确信有办法对此进行优化,我将编辑这篇文章,因为我将了解有关该过程的更多信息,但这些是我已采取的步骤。

  1. 我在 macOS 上构建了二进制文件:

    docker run -v $PWD:/volume -w/volume -e RUST_LOG="rusoto,hyper=debug"-e OPENSSL_STATIC=1 -e OPENSSL_DIR=/usr/local -e SSL_CERT_DIR=/etc/ssl/certs -t manonthemat/muslrust cargo build --release --features "logging"

  2. 我修改了 Dockerfile

    FROM alpine:edge 复制目标/x86_64-unknown-linux-musl/release/project/ RUN apk update && apk add --no-cache pkgconfig openssl-dev ca-certificates linux-headers && update-ca-certificates CMD [ "/project"]

  3. 我构建了 docker 镜像

    • 然后我将 docker 镜像推送到一个私有(private)仓库,并通过 EC2 实例上的 ssh-session 拉取它以进行测试。我通过 docker run -e SSL_CERT_DIR=/etc/ssl/certs secretuser/secretrepo:notsosecrettag
    • 成功运行了它
  4. 我标记了 docker 镜像并将其推送到 AWS 存储库

  5. 为了在 Amazon Elastic Container Service 上成功运行,我必须修改任务定义。在 containerDefinitions 中,我必须增加内存并将其添加到环境数组中:

    `{
      "name": "SSL_CERT_DIR",
      "value": "/etc/ssl/certs"
    }`
    
  6. 由于某些未知且可能不相关的原因,我还必须更新 EC2 实例上的代理,然后重新启动它们。

关于Docker 和 "The OpenSSL library reported an error"部署时,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/44728421/

有关Docker 和 "The OpenSSL library reported an error"部署时的更多相关文章

  1. ruby-on-rails - rails : "missing partial" when calling 'render' in RSpec test - 2

    我正在尝试测试是否存在表单。我是Rails新手。我的new.html.erb_spec.rb文件的内容是:require'spec_helper'describe"messages/new.html.erb"doit"shouldrendertheform"dorender'/messages/new.html.erb'reponse.shouldhave_form_putting_to(@message)with_submit_buttonendendView本身,new.html.erb,有代码:当我运行rspec时,它失败了:1)messages/new.html.erbshou

  2. ruby-on-rails - 由于 "wkhtmltopdf",PDFKIT 显然无法正常工作 - 2

    我在从html页面生成PDF时遇到问题。我正在使用PDFkit。在安装它的过程中,我注意到我需要wkhtmltopdf。所以我也安装了它。我做了PDFkit的文档所说的一切......现在我在尝试加载PDF时遇到了这个错误。这里是错误:commandfailed:"/usr/local/bin/wkhtmltopdf""--margin-right""0.75in""--page-size""Letter""--margin-top""0.75in""--margin-bottom""0.75in""--encoding""UTF-8""--margin-left""0.75in""-

  3. ruby - 检查 "command"的输出应该包含 NilClass 的意外崩溃 - 2

    为了将Cucumber用于命令行脚本,我按照提供的说明安装了arubagem。它在我的Gemfile中,我可以验证是否安装了正确的版本并且我已经包含了require'aruba/cucumber'在'features/env.rb'中为了确保它能正常工作,我写了以下场景:@announceScenario:Testingcucumber/arubaGivenablankslateThentheoutputfrom"ls-la"shouldcontain"drw"假设事情应该失败。它确实失败了,但失败的原因是错误的:@announceScenario:Testingcucumber/ar

  4. ruby-on-rails - 迷你测试错误 : "NameError: uninitialized constant" - 2

    我遵循MichaelHartl的“RubyonRails教程:学习Web开发”,并创建了检查用户名和电子邮件长度有效性的测试(名称最多50个字符,电子邮件最多255个字符)。test/helpers/application_helper_test.rb的内容是:require'test_helper'classApplicationHelperTest在运行bundleexecraketest时,所有测试都通过了,但我看到以下消息在最后被标记为错误:ERROR["test_full_title_helper",ApplicationHelperTest,1.820016791]test

  5. ruby-on-rails - 相关表上的范围为 "WHERE ... LIKE" - 2

    我正在尝试从Postgresql表(table1)中获取数据,该表由另一个相关表(property)的字段(table2)过滤。在纯SQL中,我会这样编写查询:SELECT*FROMtable1JOINtable2USING(table2_id)WHEREtable2.propertyLIKE'query%'这工作正常:scope:my_scope,->(query){includes(:table2).where("table2.property":query)}但我真正需要的是使用LIKE运算符进行过滤,而不是严格相等。然而,这是行不通的:scope:my_scope,->(que

  6. 使用 ACL 调用 upload_file 时出现 Ruby S3 "Access Denied"错误 - 2

    我正在尝试编写一个将文件上传到AWS并公开该文件的Ruby脚本。我做了以下事情:s3=Aws::S3::Resource.new(credentials:Aws::Credentials.new(KEY,SECRET),region:'us-west-2')obj=s3.bucket('stg-db').object('key')obj.upload_file(filename)这似乎工作正常,除了该文件不是公开可用的,而且我无法获得它的公共(public)URL。但是当我登录到S3时,我可以正常查看我的文件。为了使其公开可用,我将最后一行更改为obj.upload_file(file

  7. ruby-on-rails - 每次我尝试部署时,我都会得到 - (gcloud.preview.app.deploy) 错误响应 : [4] DEADLINE_EXCEEDED - 2

    我是Google云的新手,我正在尝试对其进行首次部署。我的第一个部署是RubyonRails项目。我基本上是在关注thisguideinthegoogleclouddocumentation.唯一的区别是我使用的是我自己的项目,而不是他们提供的“helloworld”项目。这是我的app.yaml文件runtime:customvm:trueentrypoint:bundleexecrackup-p8080-Eproductionconfig.ruresources:cpu:0.5memory_gb:1.3disk_size_gb:10当我转到我的项目目录并运行gcloudprevie

  8. ruby - 安装 Ruby 时遇到问题(无法下载资源 "readline--patch") - 2

    当我尝试安装Ruby时遇到此错误。我试过查看this和this但无济于事➜~brewinstallrubyWarning:YouareusingOSX10.12.Wedonotprovidesupportforthispre-releaseversion.Youmayencounterbuildfailuresorotherbreakages.Pleasecreatepull-requestsinsteadoffilingissues.==>Installingdependenciesforruby:readline,libyaml,makedepend==>Installingrub

  9. ruby - RVM "ERROR: Unable to checkout branch ."单用户 - 2

    我在新的Debian6VirtualBoxVM上安装RVM时遇到问题。我已经安装了所有需要的包并使用下载了安装脚本(curl-shttps://rvm.beginrescueend.com/install/rvm)>rvm,但以单个用户身份运行时bashrvm我收到以下错误消息:ERROR:Unabletocheckoutbranch.安装在这里停止,并且(据我所知)没有安装RVM的任何文件。如果我以root身份运行脚本(对于多用户安装),我会收到另一条消息:Successfullycheckedoutbranch''安装程序继续并指示成功,但未添加.rvm目录,甚至在修改我的.bas

  10. ruby - 如何关闭 ruby​​ gem "Spreadsheet?"中的文件 - 2

    下面的代码在我第一次运行它时就可以正常工作:require'rubygems'require'spreadsheet'book=Spreadsheet.open'/Users/me/myruby/Mywks.xls'sheet=book.worksheet0row=sheet.row(1)putsrow[1]book.write'/Users/me/myruby/Mywks.xls'当我再次运行它时,我会收到更多消息,例如:/Library/Ruby/Gems/1.8/gems/spreadsheet-0.6.5.9/lib/spreadsheet/excel/reader.rb:11

随机推荐