# Stalwart-mail+Discourse: POP3 EOFに到達しました（再び）

**URL:** <https://meta.discourse.org/t/stalwart-mail-discourse-pop3-eof-reached-again/312287>\
**Category:** Support\
**Tags:** email\
**Created:** [2024 年 6 月 16 日午後 5:52 UTC](https://meta.discourse.org/t/stalwart-mail-discourse-pop3-eof-reached-again/312287 "2024-06-16T17:52:11Z")\
**Posts on this page:** 1\
**Showing post:** 1

<div class="post-metadata">

**Author:** ![hellekin](https://sea3.discourse-cdn.com/meta/user_avatar/meta.discourse.org/hellekin/32/51636_2.png) [@hellekin](https://meta.discourse.org/u/hellekin)\
**Post date:** [2024 年 6 月 16 日午後 5:52 UTC](https://meta.discourse.org/t/stalwart-mail-discourse-pop3-eof-reached-again/312287/1 "2024-06-16T17:52:11Z")

</div>

[POP3 ポーリング SSL 問題](https://meta.discourse.org/t/pop3-polling-ssl-issue/128265/3) の議論を続けます。

> [@gerhard](#):
>
> これは TLS 1.3 と Ruby の間の非互換性が原因でした。私は [回避策をコミット](https://github.com/discourse/discourse/commit/56c6e8e961ab59336953bb564debcad7288d4fc0) し、これを上流で修正できるよう努めます。
> 
> また、ご指摘の通り、タイムアウトや認証エラーだけでなく、すべての POP3 エラーを管理ダッシュボードに表示すべきです。これも修正します。

こんにちは、

Discourse で新しい [Stalwart-mail の POP3 サポート](https://stalw.art/docs/imap/overview#pop3) をテストしています…

> **DNS レコードは完了しています**
>
> ```plaintext
> DNS レコード
> タイプ	名前	内容
> MX	hack2o.eu.	10 mx.z7l.eu.
> CNAME	mail.hack2o.eu.	mx.z7l.eu.
> TXT	202406e._domainkey.hack2o.eu.	v=DKIM1; k=ed25519; h=sha256; p=J7kVdkoSKjwJcdPOcqCvvR7YtJV3LtOKEQ09c00+/fY=
> TXT	202406r._domainkey.hack2o.eu.	v=DKIM1; k=rsa; h=sha256; p=MIIBIjANBgkqhkiG9w0BAQEFAAOCAQ8AMIIBCgKCAQEAuvXE8Nf0Q9C+/coc9RgACmoTwQ9OZMkJIuWxtT0fYr6UY3CYnjzOLp+VEKoqQA2OHfNM7Q3rQSw0ghjKcMW2OqzQKQAQTGrm3hvSjsJgQvUcgjHbZngpzfqBsCun6iONGuO33UJmzH4hpnm0ljLGiOw4wv6MA918wL71oZS7HWjYU9g31uasCVBpt0Ch1U6Vfs4/ejVSXbmvNb+BDQUU48E8SnpnZS6yLoMC7gByflVvoOlLvj8tV4HYdO74FXej4gUEUUacQUQPyWKDzHhhcuhG/nmoWOrbJyiTpoq4cflKTblg6wriBZ6XPXud2Og1U0SB1yPyEtV7q3b4ZLJ1AwIDAQAB
> TXT	hack2o.eu.	v=spf1 mx ra=postmaster -all
> SRV	_imaps._tcp.hack2o.eu.	0 1 143 mx.z7l.eu.
> SRV	_imaps._tcp.hack2o.eu.	0 1 993 mx.z7l.eu.
> SRV	_pop3s._tcp.hack2o.eu.	0 1 995 mx.z7l.eu.
> SRV	_submissions._tcp.hack2o.eu.	0 1 465 mx.z7l.eu.
> SRV	_submissions._tcp.hack2o.eu.	0 1 587 mx.z7l.eu.
> CNAME	autoconfig.hack2o.eu.	mx.z7l.eu.
> CNAME	autodiscover.hack2o.eu.	mx.z7l.eu.
> CNAME	mta-sts.hack2o.eu.	mx.z7l.eu.
> TXT	_mta-sts.hack2o.eu.	v=STSv1; id=16222476092926415687
> TXT	_dmarc.hack2o.eu.	v=DMARC1; p=reject; rua=mailto:postmaster@hack2o.eu; ruf=mailto:postmaster@hack2o.eu
> TXT	_smtp._tls.hack2o.eu.	v=TLSRPTv1; rua=mailto:postmaster@hack2o.eu
> TLSA	_25._tcp.mail.hack2o.eu.	3 0 1 22eaf4d577f42a1ceeda1b8da12ab2c0eb20351b7e3f7035c2cac7dd700a3ab6
> TLSA	_25._tcp.mail.hack2o.eu.	3 0 2 16c04cca276b0d880b843f35b8f8513b7b4157907cb19c5d5f36464ea5e04972e863f24a6cb18bcd39fe5cc0cff793d6a5225d8937654ab28b2c7096a12cd858
> TLSA	_25._tcp.mail.hack2o.eu.	3 1 1 0a47742e724fe771934bbf9a5d9c721cf34b97135242042b9e0a2c030c634455
> TLSA	_25._tcp.mail.hack2o.eu.	3 1 2 ab60f26c194e0467bade96dd1a0bffd5d465065b2740e577f28f889a019ec2b455af8b8a1b1bcd66b998bba91469c5c5430c0a9f52f27316b33f93997d48f3e7
> TLSA	_25._tcp.mail.hack2o.eu.	2 0 1 76e9e288aafc0e37f4390cbf946aad997d5c1c901b3ce513d3d8fadbabe2ab85
> TLSA	_25._tcp.mail.hack2o.eu.	2 0 2 afab698cbbbf892ebb555e09175056c1d4630fe7c350f44dcc6e71843d3b290df00d30ab4e356b630c69169d7633788338922fb637cf5b9f7be20a413eeaa518
> TLSA	_25._tcp.mail.hack2o.eu.	2 1 1 d016e1fe311948aca64f2de44ce86c9a51ca041df6103bb52a88eb3f761f57d7
> TLSA	_25._tcp.mail.hack2o.eu.	2 1 2 f8a2b4e23e82a4494e9998fcc4242bef1277656a118beede55ddfadcb82e20c5dc036dcb3b6c48d2ce04e362a9f477c82ad5a557b06b6f33b45ca6662b37c1c9
> 
> ```

POP3 アカウントは Thunderbird では正常に動作し、設定も適切に自動検出されます。

しかし、TLS 1.3 の回避策を適用しても、Discourse では有効化に失敗します。

> **エラーメッセージ**
>
> ```plaintext
> メッセージ
> 
> EOFError (ファイルの終端に到達しました)
> app/services/email_settings_validator.rb:55:in `validate_pop3'
> lib/validators/pop3_polling_enabled_setting_validator.rb:35:in `authentication_works?'
> lib/validators/pop3_polling_enabled_setting_validator.rb:15:in `valid_value?'
> lib/site_settings/type_supervisor.rb:284:in `validate_value'
> lib/site_settings/type_supervisor.rb:165:in `to_db_value'
> lib/site_setting_extension.rb:368:in `add_override!'
> lib/site_setting_extension.rb:609:in `block in setup_methods'
> lib/site_setting_extension.rb:435:in `public_send'
> lib/site_setting_extension.rb:435:in `set'
> lib/site_setting_extension.rb:448:in `set_and_log'
> app/controllers/admin/site_settings_controller.rb:56:in `update'
> app/controllers/application_controller.rb:422:in `block in with_resolved_locale'
> app/controllers/application_controller.rb:422:in `with_resolved_locale'
> lib/middleware/omniauth_bypass_middleware.rb:64:in `call'
> lib/content_security_policy/middleware.rb:12:in `call'
> lib/middleware/anonymous_cache.rb:393:in `call'
> lib/middleware/csp_script_nonce_injector.rb:12:in `call'
> config/initializers/008-rack-cors.rb:14:in `call'
> config/initializers/100-quiet_logger.rb:20:in `call'
> config/initializers/100-silence_logger.rb:29:in `call'
> lib/middleware/enforce_hostname.rb:24:in `call'
> lib/middleware/request_tracker.rb:289:in `call'
> 
> バックトレース
> 
> /usr/local/lib/ruby/3.3.0/net/protocol.rb:237:in `rbuf_fill'
> /usr/local/lib/ruby/3.3.0/net/protocol.rb:199:in `readuntil'
> /usr/local/lib/ruby/3.3.0/net/protocol.rb:209:in `readline'
> net-pop (0.1.2) lib/net/pop.rb:1000:in `recv_response'
> net-pop (0.1.2) lib/net/pop.rb:996:in `get_response'
> net-pop (0.1.2) lib/net/pop.rb:984:in `block in quit'
> net-pop (0.1.2) lib/net/pop.rb:1016:in `critical'
> net-pop (0.1.2) lib/net/pop.rb:984:in `quit'
> net-pop (0.1.2) lib/net/pop.rb:603:in `do_finish'
> net-pop (0.1.2) lib/net/pop.rb:533:in `start'
> net-pop (0.1.2) lib/net/pop.rb:316:in `auth_only'
> app/services/email_settings_validator.rb:55:in `validate_pop3'
> lib/validators/pop3_polling_enabled_setting_validator.rb:35:in `authentication_works?'
> lib/validators/pop3_polling_enabled_setting_validator.rb:15:in `valid_value?'
> lib/site_settings/type_supervisor.rb:284:in `validate_value'
> lib/site_settings/type_supervisor.rb:165:in `to_db_value'
> lib/site_setting_extension.rb:368:in `add_override!'
> lib/site_setting_extension.rb:609:in `block in setup_methods'
> lib/site_setting_extension.rb:435:in `public_send'
> lib/site_setting_extension.rb:435:in `set'
> lib/site_setting_extension.rb:448:in `set_and_log'
> app/controllers/admin/site_settings_controller.rb:56:in `update'
> actionpack (7.0.8.4) lib/action_controller/metal/basic_implicit_render.rb:6:in `send_action'
> actionpack (7.0.8.4) lib/abstract_controller/base.rb:215:in `process_action'
> actionpack (7.0.8.4) lib/action_controller/metal/rendering.rb:165:in `process_action'
> actionpack (7.0.8.4) lib/abstract_controller/callbacks.rb:234:in `block in process_action'
> activesupport (7.0.8.4) lib/active_support/callbacks.rb:118:in `block in run_callbacks'
> app/controllers/application_controller.rb:422:in `block in with_resolved_locale'
> i18n (1.14.5) lib/i18n.rb:351:in `with_locale'
> app/controllers/application_controller.rb:422:in `with_resolved_locale'
> activesupport (7.0.8.4) lib/active_support/callbacks.rb:127:in `block in run_callbacks'
> activesupport (7.0.8.4) lib/active_support/callbacks.rb:138:in `run_callbacks'
> actionpack (7.0.8.4) lib/abstract_controller/callbacks.rb:233:in `process_action'
> actionpack (7.0.8.4) lib/action_controller/metal/rescue.rb:23:in `process_action'
> actionpack (7.0.8.4) lib/action_controller/metal/instrumentation.rb:67:in `block in process_action'
> activesupport (7.0.8.4) lib/active_support/notifications.rb:206:in `block in instrument'
> activesupport (7.0.8.4) lib/active_support/notifications/instrumenter.rb:24:in `instrument'
> activesupport (7.0.8.4) lib/active_support/notifications.rb:206:in `instrument'
> actionpack (7.0.8.4) lib/action_controller/metal/instrumentation.rb:66:in `process_action'
> actionpack (7.0.8.4) lib/action_controller/metal/params_wrapper.rb:259:in `process_action'
> activerecord (7.0.8.4) lib/active_record/railties/controller_runtime.rb:27:in `process_action'
> actionpack (7.0.8.4) lib/abstract_controller/base.rb:151:in `process'
> actionview (7.0.8.4) lib/action_view/rendering.rb:39:in `process'
> rack-mini-profiler (3.3.1) lib/mini_profiler/profiling_methods.rb:115:in `block in profile_method'
> actionpack (7.0.8.4) lib/action_controller/metal.rb:188:in `dispatch'
> actionpack (7.0.8.4) lib/action_controller/metal.rb:251:in `dispatch'
> actionpack (7.0.8.4) lib/action_dispatch/routing/route_set.rb:49:in `dispatch'
> actionpack (7.0.8.4) lib/action_dispatch/routing/route_set.rb:32:in `serve'
> actionpack (7.0.8.4) lib/action_dispatch/routing/mapper.rb:18:in `block in <class:Constraints>'
> actionpack (7.0.8.4) lib/action_dispatch/routing/mapper.rb:48:in `serve'
> actionpack (7.0.8.4) lib/action_dispatch/journey/router.rb:50:in `block in serve'
> actionpack (7.0.8.4) lib/action_dispatch/journey/router.rb:32:in `each'
> actionpack (7.0.8.4) lib/action_dispatch/journey/router.rb:32:in `serve'
> actionpack (7.0.8.4) lib/action_dispatch/routing/route_set.rb:852:in `call'
> lib/middleware/omniauth_bypass_middleware.rb:64:in `call'
> rack (2.2.9) lib/rack/tempfile_reaper.rb:15:in `call'
> rack (2.2.9) lib/rack/conditional_get.rb:40:in `call'
> rack (2.2.9) lib/rack/head.rb:12:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/http/permissions_policy.rb:38:in `call'
> lib/content_security_policy/middleware.rb:12:in `call'
> lib/middleware/anonymous_cache.rb:393:in `call'
> lib/middleware/csp_script_nonce_injector.rb:12:in `call'
> config/initializers/008-rack-cors.rb:14:in `call'
> rack (2.2.9) lib/rack/session/abstract/id.rb:266:in `context'
> rack (2.2.9) lib/rack/session/abstract/id.rb:260:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/cookies.rb:704:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/callbacks.rb:27:in `block in call'
> activesupport (7.0.8.4) lib/active_support/callbacks.rb:99:in `run_callbacks'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/callbacks.rb:26:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/debug_exceptions.rb:28:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/show_exceptions.rb:29:in `call'
> logster (2.19.1) lib/logster/middleware/reporter.rb:40:in `call'
> railties (7.0.8.4) lib/rails/rack/logger.rb:40:in `call_app'
> railties (7.0.8.4) lib/rails/rack/logger.rb:27:in `call'
> config/initializers/100-quiet_logger.rb:20:in `call'
> config/initializers/100-silence_logger.rb:29:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/remote_ip.rb:93:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/request_id.rb:26:in `call'
> lib/middleware/enforce_hostname.rb:24:in `call'
> rack (2.2.9) lib/rack/method_override.rb:24:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/executor.rb:14:in `call'
> rack (2.2.9) lib/rack/sendfile.rb:110:in `call'
> actionpack (7.0.8.4) lib/action_dispatch/middleware/host_authorization.rb:131:in `call'
> rack-mini-profiler (3.3.1) lib/mini_profiler.rb:334:in `call'
> message_bus (4.3.8) lib/message_bus/rack/middleware.rb:60:in `call'
> lib/middleware/request_tracker.rb:289:in `call'
> railties (7.0.8.4) lib/rails/engine.rb:530:in `call'
> railties (7.0.8.4) lib/rails/railtie.rb:226:in `public_send'
> railties (7.0.8.4) lib/rails/railtie.rb:226:in `method_missing'
> rack (2.2.9) lib/rack/urlmap.rb:74:in `block in call'
> rack (2.2.9) lib/rack/urlmap.rb:58:in `each'
> rack (2.2.9) lib/rack/urlmap.rb:58:in `call'
> unicorn (6.1.0) lib/unicorn/http_server.rb:634:in `process_client'
> unicorn (6.1.0) lib/unicorn/http_server.rb:739:in `worker_loop'
> unicorn (6.1.0) lib/unicorn/http_server.rb:547:in `spawn_missing_workers'
> unicorn (6.1.0) lib/unicorn/http_server.rb:143:in `start'
> unicorn (6.1.0) bin/unicorn:128:in `<top (required)>'
> vendor/bundle/ruby/3.3.0/bin/unicorn:25:in `load'
> vendor/bundle/ruby/3.3.0/bin/unicorn:25:in `<main>'
> 
> 環境
> 
> HTTP ホスト: forum.hack2o.eu
> 
> ```

このエラーは純粋な Ruby の `Net::POP3` でも再現できますが、認証は **失敗していません** 。単に意味のない OpenSSL エラーが発生するだけです。`openssl s_client` で直接接続すると、TLS 1.2 と TLS 1.3 の両方で正常に動作します。切断の瞬間に OpenSSL の警告が出る以外、すべてが正常に動作しているように見えるため、ここで何をすべきか分かりません。

* * *

以下は最小限の Ruby テストです。

> **Net::POP3 テスト**
>
> ```ruby
> require 'net/pop'
> 
> puts "Testing POP3 connection for #{ENV['POP3_USER']} on #{ENV['POP3_HOST']}"
> 
> Net::POP3.enable_ssl
> 
> pop = Net::POP3.new(ENV['POP3_HOST'], 995)
> 
> print " using SSL: ", pop.use_ssl?? "yes":"no", "\n"
> 
> begin
> pop.auth_only(ENV['POP3_USER'], ENV['POP3_PASS'])
> puts "Authentication succeeded!"
> rescue Net::POPAuthenticationError => err
> puts "Authentication failed."
> # p ENV['POP3_USER']
> # p ENV['POP3_PASS']
> # p pop
> exit
> end
> 
> ```

なお、`enable_ssl` に対して `ssl_params` を設定してテストも行いましたが、結果は同じでした。

- `min_version: OpenSSL::SSL::TLS1_3_VERSION`
- `max_version: OpenSSL::SSL::TLS1_2_VERSION`

以下は OpenSSL セッションです（TLS 1.2 と 1.3 の両方で同一）。

> **openssl s\_client -quiet -tls1\_3 mail.example:995**
>
> ```plaintext
> depth=2 C = US, O = Internet Security Research Group, CN = ISRG Root X1
> verify return:1
> depth=1 C = US, O = Let's Encrypt, CN = E5
> verify return:1
> depth=0 CN = mail.example
> verify return:1
> +OK Stalwart POP3 at your service.
> USER user@mail.example
> +OK user@mail.example is a valid mailbox
> PASS redacted
> +OK Authentication successful
> QUIT
> 40771049E17F0000:error:0A000126:SSL routines:ssl3_read_n:unexpected eof while reading:../ssl/record/rec_layer_s3.c:303:
> 
> ```

> **openssl s\_client -quiet -tls1\_2 mail.example:995**
>
> ```plaintext
> depth=2 C = US, O = Internet Security Research Group, CN = ISRG Root X1
> verify return:1
> depth=1 C = US, O = Let's Encrypt, CN = E5
> verify return:1
> depth=0 CN = mail.example
> verify return:1
> +OK Stalwart POP3 at your service.
> USER user@mail.example
> +OK user@mail.example is a valid mailbox
> PASS redacted
> +OK Authentication successful
> QUIT
> 40771049E17F0000:error:0A000126:SSL routines:ssl3_read_n:unexpected eof while reading:../ssl/record/rec_layer_s3.c:303:
> 
> ```

なぜ他の実装では OpenSSL エラーが出力されないのか不思議です。

これは Stalwart-mail のバグではないかと考えており、レビューのためにこのトピックに報告します。

---

_[View the full topic](https://meta.discourse.org/t/stalwart-mail-discourse-pop3-eof-reached-again/312287)._
