기존에 Yona 를 구축해서 버전관리를 잘해오고 있는데, 문제는 알림 메일이였다.
지금까지 계속 google의 SMTP로 잘 운영해오다가, 어느 순간 google의 로그인 방식이 보안 정책에 따라, OAuth 방식이 아니면 더 이상 예전 처럼 아이디/패스워드 기반의 로그인을 지원하지 않는 것이다.
그래서 naver.com 내에 계정을 하나 파서 그 안에 있는 POP3/IMAP 기능을 활성화 했고, 거기서 제공하는 SMTP 설정 값을 이용해 Yona의 application.conf 값을 아래와 같이 수정했다.

smtp.startssl = true
smtp.host = smtp.naver.com
smtp.port = 587
smtp.auth = true
#smtp.ssl = true
smtp.password = "xxxxxxx"
smtp.domain = naver.com
smtp.user = "xxxxxxx@naver.com"

설정을 변경한 뒤 Yona를 다시 시작했는데.. 왠걸.. 아래와 같은 에러가 떨어진다.

2024-03-06 13:26:51,466 - [WARN] - from application in play-akka.actor.default-dispatcher-974 
Failed to send a notification: org.apache.commons.mail.HtmlEmail@1720365d
org.apache.commons.mail.EmailException: Sending the email to the following server failed : smtp.naver.com:465
	at org.apache.commons.mail.Email.sendMimeMessage(Email.java:1410)
	at org.apache.commons.mail.Email.send(Email.java:1437)
	at info.schleichardt.play2.mailplugin.MailPlugin$$anonfun$6.apply(MailPlugin.scala:60)
	at info.schleichardt.play2.mailplugin.MailPlugin$$anonfun$6.apply(MailPlugin.scala:54)
	at info.schleichardt.play2.mailplugin.MailPlugin.send(MailPlugin.scala:68)
	at info.schleichardt.play2.mailplugin.api.Mailer$.send(Mailer.scala:8)
	at info.schleichardt.play2.mailplugin.Mailer.send(Mailer.java:15)
	at controllers.ProjectApp.sendTransferRequestMail(ProjectApp.java:775)
	at controllers.ProjectApp.transferProject(ProjectApp.java:634)
	at Routes$$anonfun$routes$1$$anonfun$applyOrElse$191$$anonfun$apply$191.apply(routes_routing.scala:3708)
	at Routes$$anonfun$routes$1$$anonfun$applyOrElse$191$$anonfun$apply$191.apply(routes_routing.scala:3708)
	at play.core.Router$HandlerInvokerFactory$$anon$4.resultCall(Router.scala:264)
	at play.core.Router$HandlerInvokerFactory$JavaActionInvokerFactory$$anon$15$$anon$1.invocation(Router.scala:255)
	at play.core.j.JavaAction$$anon$1.call(JavaAction.scala:55)
	at Global$2.call(Global.java:274)
	at actions.AnonymousCheckAction.call(AnonymousCheckAction.java:57)
	at actions.IsAllowedAction.call(IsAllowedAction.java:68)
	at actions.AbstractProjectCheckAction.call(AbstractProjectCheckAction.java:93)
	at play.db.ebean.TransactionalAction$1.call(TransactionalAction.java:21)
	at play.db.ebean.TransactionalAction$1.call(TransactionalAction.java:18)
	at com.avaje.ebeaninternal.server.core.DefaultServer.execute(DefaultServer.java:715)
	at com.avaje.ebeaninternal.server.core.DefaultServer.execute(DefaultServer.java:709)
	at com.avaje.ebean.Ebean.execute(Ebean.java:1264)
	at play.db.ebean.TransactionalAction.call(TransactionalAction.java:18)
	at play.core.j.JavaAction$$anonfun$11.apply(JavaAction.scala:82)
	at play.core.j.JavaAction$$anonfun$11.apply(JavaAction.scala:82)
	at scala.concurrent.impl.Future$PromiseCompletingRunnable.liftedTree1$1(Future.scala:24)
	at scala.concurrent.impl.Future$PromiseCompletingRunnable.run(Future.scala:24)
	at play.core.j.HttpExecutionContext$$anon$2.run(HttpExecutionContext.scala:40)
	at play.api.libs.iteratee.Execution$trampoline$.execute(Execution.scala:46)
	at play.core.j.HttpExecutionContext.execute(HttpExecutionContext.scala:32)
	at scala.concurrent.impl.Future$.apply(Future.scala:31)
	at scala.concurrent.Future$.apply(Future.scala:485)
	at play.core.j.JavaAction$class.apply(JavaAction.scala:82)
	at play.core.Router$HandlerInvokerFactory$JavaActionInvokerFactory$$anon$15$$anon$1.apply(Router.scala:252)
	at play.api.mvc.Action$$anonfun$apply$1$$anonfun$apply$4$$anonfun$apply$5.apply(Action.scala:130)
	at play.api.mvc.Action$$anonfun$apply$1$$anonfun$apply$4$$anonfun$apply$5.apply(Action.scala:130)
	at play.utils.Threads$.withContextClassLoader(Threads.scala:21)
	at play.api.mvc.Action$$anonfun$apply$1$$anonfun$apply$4.apply(Action.scala:129)
	at play.api.mvc.Action$$anonfun$apply$1$$anonfun$apply$4.apply(Action.scala:128)
	at scala.Option.map(Option.scala:145)
	at play.api.mvc.Action$$anonfun$apply$1.apply(Action.scala:128)
	at play.api.mvc.Action$$anonfun$apply$1.apply(Action.scala:121)
	at play.api.libs.iteratee.Iteratee$$anonfun$mapM$1.apply(Iteratee.scala:483)
	at play.api.libs.iteratee.Iteratee$$anonfun$mapM$1.apply(Iteratee.scala:483)
	at play.api.libs.iteratee.Iteratee$$anonfun$flatMapM$1.apply(Iteratee.scala:519)
	at play.api.libs.iteratee.Iteratee$$anonfun$flatMapM$1.apply(Iteratee.scala:519)
	at play.api.libs.iteratee.Iteratee$$anonfun$flatMap$1$$anonfun$apply$14.apply(Iteratee.scala:496)
	at play.api.libs.iteratee.Iteratee$$anonfun$flatMap$1$$anonfun$apply$14.apply(Iteratee.scala:496)
	at scala.concurrent.impl.Future$PromiseCompletingRunnable.liftedTree1$1(Future.scala:24)
	at scala.concurrent.impl.Future$PromiseCompletingRunnable.run(Future.scala:24)
	at akka.dispatch.TaskInvocation.run(AbstractDispatcher.scala:41)
	at akka.dispatch.ForkJoinExecutorConfigurator$AkkaForkJoinTask.exec(AbstractDispatcher.scala:393)
	at scala.concurrent.forkjoin.ForkJoinTask.doExec(ForkJoinTask.java:260)
	at scala.concurrent.forkjoin.ForkJoinPool$WorkQueue.runTask(ForkJoinPool.java:1339)
	at scala.concurrent.forkjoin.ForkJoinPool.runWorker(ForkJoinPool.java:1979)
	at scala.concurrent.forkjoin.ForkJoinWorkerThread.run(ForkJoinWorkerThread.java:107)
Caused by: javax.mail.MessagingException: Could not connect to SMTP host: smtp.naver.com, port: 465;
  nested exception is:
	javax.net.ssl.SSLHandshakeException: No appropriate protocol (protocol is disabled or cipher suites are inappropriate)
	at com.sun.mail.smtp.SMTPTransport.openServer(SMTPTransport.java:1972)
	at com.sun.mail.smtp.SMTPTransport.protocolConnect(SMTPTransport.java:642)
	at javax.mail.Service.connect(Service.java:317)
	at javax.mail.Service.connect(Service.java:176)
	at javax.mail.Service.connect(Service.java:125)
	at javax.mail.Transport.send0(Transport.java:194)
	at javax.mail.Transport.send(Transport.java:124)
	at org.apache.commons.mail.Email.sendMimeMessage(Email.java:1400)
	... 56 more
Caused by: javax.net.ssl.SSLHandshakeException: No appropriate protocol (protocol is disabled or cipher suites are inappropriate)
	at sun.security.ssl.HandshakeContext.<init>(HandshakeContext.java:171)
	at sun.security.ssl.ClientHandshakeContext.<init>(ClientHandshakeContext.java:103)
	at sun.security.ssl.TransportContext.kickstart(TransportContext.java:227)
	at sun.security.ssl.SSLSocketImpl.startHandshake(SSLSocketImpl.java:433)
	at com.sun.mail.util.SocketFetcher.configureSSLSocket(SocketFetcher.java:548)
	at com.sun.mail.util.SocketFetcher.createSocket(SocketFetcher.java:352)
	at com.sun.mail.util.SocketFetcher.getSocket(SocketFetcher.java:207)
	at com.sun.mail.smtp.SMTPTransport.openServer(SMTPTransport.java:1938)
	... 63 more

그런데 에러를 찬찬히 살펴보니 아래와 같은 문장이 눈에 딱 띄었다.

Caused by: javax.mail.MessagingException: Could not connect to SMTP host: smtp.naver.com, port: 465;
  nested exception is:
	javax.net.ssl.SSLHandshakeException: No appropriate protocol (protocol is disabled or cipher suites are inappropriate)
	at com.sun.mail.smtp.SMTPTransport.openServer(SMTPTransport.java:1972)
	at com.sun.mail.smtp.SMTPTransport.protocolConnect(SMTPTransport.java:642)

이상해서, 과거 Yona의 Issue 창을 뒤져보니, 답글 중에 아래와 같은 답변을 발견했다.

https://github.com/yona-projects/yona/issues/746

 

이메일 발송관련 · Issue #746 · yona-projects/yona

안녕하세요, 프로젝트 이관 중에 확인 메일이 안와서 이상하다 싶어서 확인하니까, 현재 메일에서 계속 오류가 발생합니다. 먼저 제쪽 환경은 아래와 같습니다. [OS] Ubuntu - 16.04.7 LTS (Xenial Xerus) [J

github.com

저 내용에서 중요한 건 Stackoverflow 링크 안의 답글인데, 답글 중에,

JRE_HOME/lib/security/java.security:

파일 안에 있는

jdk.tls.disabledAlgorithms

값을 수정하면 된다는 것이다.

해결 방법

일단, 지금 운영 중인 서버의 Java 파일 중에 java.security를 찾는다.
리눅스를 기준으로 이야기하면 다음과 같이 넣으면 찾을 수 있다.

find | grep java.security

root 권한이 있어야 수정되므로 sudo 로 해당 파일을 열어준다.

그리고 jdk.tls 를 검색하면 아래와 같은 내용을 볼 수 있다.

jdk.tls.disabledAlgorithms=SSLv3, TLSv1, TLSv1.1, RC4, DES, MD5withRSA, \
    DH keySize < 1024, EC keySize < 224, 3DES_EDE_CBC, anon, NULL, \
    include jdk.disabled.namedCurves

저 항목 중에 SSLv3, TLSv1, TLSv1.1 을 삭제하고 저장하도록 한다.

그러면 해결된다.

728x90

+ Recent posts