팀프로젝트/SpringBoot

스프링 부트 팀플) 20240312_Resource에 있는 이메일.html 사용하기

일일일코_장민기 2024. 3. 12. 15:34
728x90

https://komas.tistory.com/142

 

[Spring] 스프링 Resources 파일 읽기, 복사

resoruces에 위치한 data.json을 읽어야 한다. { "hello": "123" } data.json의 내용은 다음과 같다. @SpringBootApplication public class RestApIsApplication { public static void main(String[] args) throws IOException { SpringApplication.run(Re

komas.tistory.com

https://born2bedeveloper.tistory.com/70

 

[Spring Boot] 이메일 보내기 (3) - html 템플릿 적용 (feat. Thymeleaf)

++) 해당 포스팅은 이전 작성한 포스팅들과 연계되어 있으므로 먼저 보고 오는 것을 추천합니다! https://born2bedeveloper.tistory.com/68?category=1038709 [Spring Boot] 이메일 보내기 (2) - 참조(cc), 첨부 파일 꽤

born2bedeveloper.tistory.com

참고자료

 

 

@GetMapping("/sendFileEmail")

public String sendFileEmail(String userEmail) throws Exception {

String TO_EMAIL =

"cjstkrhdfk@naver.com";

//userEmail;

String EMAIL_SUBJECT = "[회원정보알림] 문화인의 밤을 이용해주셔서 감사합니다.";

String EMAIL_BODY = "Email body";

serv.sendEmailWithFiles(FROM_EMAIL, TO_EMAIL, EMAIL_SUBJECT, EMAIL_BODY);

return "send";

}

 

 

기존 방식은 직접 EMAIL_BODY에 html형식으로 코드를 입력해야 했다.

따옴표와 +가 섞이며 매우 불편하게 코드를 만들어야 이메일 본문을 만들 수 있었다.

이런 불편한 이메일 본문 형성을 해결하고, 이메일을 더 쉽게 관리하며, 이메일을 꾸미기 위해 방법을 구상했다.


1. resource에 html 파일을 만든다. 어차피 이메일 본문은 html 형식으로 만들어져야 된다.

2. 컨트롤러에서 resource 폴더의 html과 연결한다.

3. Profit!?

 

 

 

public void sendEmail(String userEmail, MemberDTO dto) throws Exception {

 

//Resources 폴더부터 경로 설정

ClassPathResource resource = new ClassPathResource("static/emailFiles/PWEmail.html");

//BufferedReader를 통해 한줄씩 읽어옴 || InputStreamReader를 통해 byte를 String Stream으로 변경

BufferedReader br = new BufferedReader(new InputStreamReader(resource.getInputStream()));

//StringBuilder: 문자열 연산을 수행할 때마다, 기존 문자열에 변경사항을 반영하여 작업

StringBuilder emailBody = new StringBuilder();

 

String line;

//HTML의 각 줄을 읽어오고, 특정 글자는 치환

while ((line = br.readLine()) != null) {

line = line.replace("##유저_아이디##", dto.getUserId())

.replace("##유저_이름##", dto.getUserName())

.replace("##유저_비밀번호##", dto.getUserPw());

//각 줄을 StringBuilder에 더하고, 개행

emailBody.append(line).append("\n");

}

 

String TO_EMAIL = userEmail;

String EMAIL_SUBJECT = "[회원정보알림] 문화인의 밤을 이용해주셔서 감사합니다.";

 

//StringBuilder를 String으로 전환하고 이메일 본문으로 저장

String EMAIL_BODY = emailBody.toString();

 

serv.sendEmail(FROM_EMAIL, TO_EMAIL, EMAIL_SUBJECT, EMAIL_BODY);

}

Java 코드는 열심히 공부해야 한다...Replace와 append가 여기서 쓰일 줄이야...

replace가 없으면 유저 아이디나 쿠키 등, 원하는 데이터를 이메일에 넣을 수 없다. 

 

이미지 하단의 HTML파일을 MailController에서 불어온다. 그런데 왜 이리 복잡하지?

 

 

잘 보내지니 기부니가 좋다

 

그런데 이걸 만들고 나니까 이메일 함수 하나하나가 지독하게 두꺼워진다.
이걸 해결해야 한다...

 

MailController

//단순 메일 전송

public void sendEmail(String userEmail, MemberDTO dto) throws Exception {

 

Map<String, String> changeData = new HashMap<>();

 

//******************복사 후 수정하는 부분******************

String emailPath = "static/emailFiles/PWEmail.html";

changeData.put("##유저_아이디##", dto.getUserId());

changeData.put("##유저_이름##", dto.getUserName());

changeData.put("##유저_비밀번호##", dto.getUserPw());

//******************복사 후 수정하는 부분******************

 

String TO_EMAIL = userEmail;

String EMAIL_SUBJECT = "[회원정보알림] 문화인의 밤을 이용해주셔서 감사합니다.";

 

//StringBuilder를 String으로 전환하고 이메일 본문으로 저장

String EMAIL_BODY = serv.EmailBody(emailPath, changeData);

serv.sendEmail(FROM_EMAIL, TO_EMAIL, EMAIL_SUBJECT, EMAIL_BODY);

}

 

MailService

public String EmailBody(String emailPath, Map<String, String> changeData) throws IOException {

 

//Resources 폴더부터 경로 설정

ClassPathResource resource = new ClassPathResource(emailPath);

//BufferedReader를 통해 한줄씩 읽어옴 || InputStreamReader를 통해 byte를 String Stream으로 변경

BufferedReader br = new BufferedReader(new InputStreamReader(resource.getInputStream()));

//StringBuilder: 문자열 연산을 수행할 때마다, 기존 문자열에 변경사항을 반영하여 작업

StringBuilder emailBody = new StringBuilder();

 

String line;

//HTML의 각 줄을 읽어오고, 특정 글자는 치환

while ((line = br.readLine()) != null) {

for (Map.Entry<String, String> entry : changeData.entrySet()) {

line = line.replace(entry.getKey(), entry.getValue());

}

//각 줄을 StringBuilder에 더하고, 개행

emailBody.append(line).append("\n");

}

String mesg = emailBody.toString();

 

return mesg;

 

}

 

앞서 추가한 부분은 Service에 떠넘기면서 컨트롤러가 가벼워졌다.
사용자는 표시해둔 부분만 수정하면 경로와 데이터를 입력할 수 있다.
내친 김에 파일 전송 이메일 시스템도 만들었다.

 

 

깔끔하게 잘 전송된다.

 

이메일 시스템을 전반적으로 다 만들었다.
이제 이메일을 꾸밀 시간이다.

문제는 꾸며지지 않는다는 것이었다.

 

 

 

스타일 태그도 Body에 스타일 지정도, 글자에 color 지정도 안 먹혔다...글씨체랑 이미지 크기 외에는 조절이 안 되는게 너무 열 받았다..

 

 

https://unlayer.com/templates

 

Free HTML Email Templates and Editor

Browse hundreds of HTML email templates and choose the best for your business. Wide range of templates available for every industry and usage. Start for free.

unlayer.com

 

그러던 도중, 이 사이트를 찾았다.
믿져야 본전이라는 마음으로 하나를 다운 받고 적용

 

희망이 보인다.

 

놀랍게도 틀이 적용되었다.
이미지 오류는 cid를 사용해서 컨트롤러를 경유하면 될 것이다.

나름 이미지가 출력되었다.

 

 

그런데 무슨 짓을 해도 배경 이미지가 들어가지지 않았다.
background-image: url('링크')에 cid가 절대경로, 상대경로, cid 아무것도 적용되지 않았다.
그러다 Base64로 이미지를 데이터값으로 변환하는 것을 알게 되었고, 용량 작은 이미지를 적용시켜서 넣었다.

 

https://blog.freezner.com/archives/1938

https://zangzangs.tistory.com/46

 

[JAVA] SMTP 메일 이미지 첨부 방법 3가지

SMTP 메일 이미지 첨부 에러 자바로 메일을 보내야하는 일이 생겨 SMTP를 사용해 메일을 보내는 코드를 작성했다. 메일내에 이미지를 첨부해서 전송해야 했고 CID 방식을 사용해서 코드를 작성했다

zangzangs.tistory.com

 

 

 

 

드디어 온전한 형태로 이메일이 발송되었다.
힘들었다...백그라운드 이미지 하나가 이런게 시간을 잡아먹을 줄이야.
정렬 맞추는 거 정신 나갈 것 같다...

 

https://products.aspose.app/imaging/ko/conversion/image-to-base64/navigation/uploaded/result

 

온라인에서 이미지를 BASE64 형식으로 변환

Chrome, Opera 또는 Firefox와 같은 최신 브라우저를 사용하여 무료 온라인에서 이미지를 BASE64 형식으로 변환하십시오. 이미지를 업로드하기만 하면 모든 기기에서 무료로 BASE64 형식의 결과를 얻을

products.aspose.app

 

 

내일은 아마도 이메일 형식 2개를 만들고 끝나지 않을까