์‡ผํ•‘๋ชฐ ํ”„๋กœ์ ํŠธ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๊ธฐ๋Šฅ - ์ด๋ฉ”์ผ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ฐœ์†ก

2023. 5. 9. 17:23ใ†Spring

๋ฉ”์ผ ๋ณด๋‚ผ ์ˆ˜ ์žˆ๋Š” ๊ธฐ๋Šฅ์„ ์‚ฌ์šฉํ•˜๊ธฐ ์œ„ํ•ด build.gradle์— ์•„๋ž˜ ์ฝ”๋“œ ์ถ”๊ฐ€

implementation 'org.springframework.boot:spring-boot-starter-mail'

๋ฉ”์ผ ์„œ๋ฒ„ ์„ค์ •์„ ์œ„ํ•ด application.properties์— ์•„๋ž˜ ์ฝ”๋“œ ์ถ”๊ฐ€

#๋ฉ”์ผ smtp ์„ค์ • (๋ฉ”์ผ์„œ๋ฒ„)
spring.mail.host=smtp.gmail.com
spring.mail.port=587
#๋ฐœ์‹ ์ž์˜ ๋ฉ”์ผ๊ณผ ํŒจ์Šค์›Œ๋“œ(๋ณ„๋„์˜ ์ธ์ฆ์„ ๋ฐ›์€)
spring.mail.username=๊ตฌ๊ธ€id@gmail.com
spring.mail.password=์ƒ์„ฑ๋œ ๋น„๋ฐ€๋ฒˆํ˜ธ
spring.mail.properties.mail.smtp.starttls.enable=true
spring.mail.properties.mail.smtp.auth=true

๊ตฌ๊ธ€ ์ ‘์†ํ•ด์„œ ๊ณ„์ • ์„ค์ • 2๋‹จ๊ณ„ ์ธ์ฆ ์„ค์ • > ์•ฑ ๋น„๋ฐ€๋ฒˆํ˜ธ ์„ค์ • 

์ƒ์„ฑ๋œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ  password ์นธ์— ๋„ฃ์œผ๋ฉด ๋จ.

Util ํŒจํ‚ค์ง€ MailService ํด๋ž˜์Šค ์ƒ์„ฑ

๋ฉ”์ผ ๋ณด๋‚ด๋Š” ๋ฉ”์†Œ๋“œ ์ƒ์„ฑ

 

- ๋‹จ์ˆœ ๋ฌธ์ž ๋ฉ”์ผ ๋ณด๋‚ด๊ธฐ

 

์ˆ˜์‹ ์ž ์„ธํŒ…ํ•  ๋•Œ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ String ํ•˜๋‚˜๋งŒ ๋ฐ›๋Š” ๋ฉ”์†Œ๋“œ์™€ String ๋ฐฐ์—ด์ด ๋“ค์–ด๊ฐ€๋Š” ๋ฉ”์†Œ๋“œ ์žˆ์Œ

String ๋ฐฐ์—ด์„ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ๋ฐ›์œผ๋ฉด ํ•œ๋ช…์ด๋“ , ์—ฌ๋Ÿฌ๋ช…์ด๋“  ์ˆ˜์‹ ์ž ์ง€์ • ๊ฐ€๋Šฅ!

1. ์ˆ˜์‹ ์ž๋ฅผ ํ•œ๋ช…๋งŒ ์ง€์ •ํ•˜๋Š” ๊ฒฝ์šฐ

@Service("mailService")
public class MailService {
	
	@Autowired //๊ฐ์ฒด ๋ถˆ๋Ÿฌ์˜ด (gradle์—์„œ ์ถ”๊ฐ€ํ•œ ์ฝ”๋“œ๊ฐ€ ๊ฐ์ฒด๋ฅผ ๋งŒ๋“ค์–ด์คŒ)
	private JavaMailSender javaMailSender;
	
	
	//๋‹จ์ˆœ ๋ฌธ์ž ๋ฉ”์ผ ๋ณด๋‚ด๊ธฐ
	public void sendSimpleEmail() {
		//๋‹จ์ˆœ ๋ฌธ์ž ๋ฉ”์ผ์„ ๋ณด๋‚ผ ์ˆ˜ ์žˆ๋Š” ๊ฐ์ฒด ์ƒ์„ฑ
		SimpleMailMessage message = new SimpleMailMessage();
		message.setSubject("[book shop] ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ฐœ์†ก"); //๋ฉ”์ผ ์ œ๋ชฉ
		message.setTo("๋ฉ”์ผ์ฃผ์†Œ@naver.com"); //์ˆ˜์‹ ์ž
		message.setText("์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ์ž…๋‹ˆ๋‹ค."); //๋‚ด์šฉ
		
		javaMailSender.send(message);
	}

}

 

test๋กœ ์ƒํ’ˆ ๋ชฉ๋ก ํŽ˜์ด์ง€ ์˜ฌ ๋•Œ ๋ฉ”์ผ ๋ณด๋‚ด๋Š” ๋ฉ”์†Œ๋“œ ์‹คํ–‰.

ItemController์—์„œ ๋ฉ”์†Œ๋“œ ์‹คํ–‰์‹œ์ผœ์ฃผ๊ธฐ.

์•„๋ž˜์ฒ˜๋Ÿผ ์ƒํ’ˆ ๋ชฉ๋ก ํŽ˜์ด์ง€ ์˜ฌ ๋•Œ ๋ฉ”์ผ ๋ฐœ์†ก๋จ.

 

๋ฉ”์ผ์˜ ์ œ๋ชฉ, ์ˆ˜์‹ ์ž, ๋‚ด์šฉ์€ ๋งค๋ฒˆ ๋ฐ”๋€Œ๊ธฐ ๋•Œ๋ฌธ์— ๋ณ€์ˆ˜๋กœ ๋งŒ๋“ค์–ด์„œ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ์ฃผ๋Š” ๊ฒƒ์ด ์ข‹์Œ.

MailService์˜ ๋ฉ”์†Œ๋“œ์— ๋งค๊ฐœ๋ณ€์ˆ˜ ์ถ”๊ฐ€

ItemController์—์„œ ๋ฉ”์†Œ๋“œ ์‹คํ–‰ ์‹œ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ๋ฉ”์ผ์˜ ์ œ๋ชฉ, ์ˆ˜์‹ ์ž, ๋‚ด์šฉ ์„ธํŒ… ํ•ด์ฃผ๋ฉด ๋จ.

 

 

๋ฉ”์ผ์˜ ์ œ๋ชฉ, ์ˆ˜์‹ ์ž, ๋‚ด์šฉ์„ VO๋กœ ๋ฐ›์•„์„œ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ ์‚ฌ์šฉ ๊ฐ€๋Šฅ.

MailVO ์ƒ์„ฑ

package com.study.shop.util;

@Getter
@Setter
public class MailVO {
	
	private String title;
	private String recipient;
	private String content;
	
}

MailService์˜ sendSimpleEmail ๋ฉ”์†Œ๋“œ ๋งค๊ฐœ๋ณ€์ˆ˜์— MailVO๋ฅผ ์คŒ.

ItemController์—์„œ ์ƒํ’ˆ ๋ชฉ๋ก ํŽ˜์ด์ง€ ์˜ฌ ๋•Œ ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ MailVO ๋ฐ›์Œ

mailVO์— ๋ฉ”์ผ ๊ด€๋ จ ์ •๋ณด ์„ธํŒ…ํ•ด์ฃผ๊ณ  ๋ฉ”์†Œ๋“œ ์‹คํ–‰ํ•  ๋•Œ MailVO ๋งค๊ฐœ๋ณ€์ˆ˜ ์‚ฌ์šฉ.

 

2.์ˆ˜์‹ ์ž๋ฅผ ์—ฌ๋Ÿฌ๋ช…์œผ๋กœ ์ง€์ •ํ•˜๋Š” ๊ฒฝ์šฐ

๋ฆฌ์ŠคํŠธ๋ฅผ ์ƒ์„ฑํ•ด์„œ ์ˆ˜์‹ ์ž๋“ค์„ ์„ธํŒ…ํ•˜์—ฌ ๋ฐฐ์—ด๋กœ ๋ฐ”๊ฟ”์„œ ์‚ฌ์šฉํ•˜๋ฉด ๋จ.

MailVO์—์„œ ์ˆ˜์‹ ์ž ๋ณ€์ˆ˜๋ฅผ Listํ˜•ํƒœ๋กœ ๋ฐ”๊ฟ”์คŒ.

@Getter
@Setter
public class MailVO {
	
	private String title;
	private List<String> recipientList;
	private String content;

}

 

MailService

์ˆ˜์‹ ์ž ์„ค์ • ์ฝ”๋“œ์—์„œ ์šฐ์„  mailVO์˜ ์ˆ˜์‹ ์ž ๋ฆฌ์ŠคํŠธ๋ฅผ ๊ฐ€์ ธ์˜ด.

๊ฐ€์ ธ์˜จ ์ˆ˜์‹ ์ž ๋ฆฌ์ŠคํŠธ๋ฅผ ๋ฐฐ์—ด๋กœ ๋ฐ”๊พผ๋‹ค ๋ฐฐ์—ด๋กœ ๋ฐ”๊ฟ€ ๋•Œ ๋ฐฐ์—ด์˜ ํฌ๊ธฐ๋ฅผ ์ง€์ •ํ•ด์ค˜์•ผํ•จ.

๋ฐฐ์—ด์˜ ํฌ๊ธฐ = ๊ฐ€์ ธ์˜จ ์ˆ˜์‹ ์ž ๋ฆฌ์ŠคํŠธ ์‚ฌ์ด์ฆˆ 

์œ„์ฒ˜๋Ÿผ ์„ค์ •ํ•ด์ฃผ๋ฉด ๋จ!

๋ฐฐ์—ด๋กœ ๋ฐ”๊ฟ€ ๋•Œ toArray ๋ฉ”์†Œ๋“œ๊ฐ€ ์—ฌ๋Ÿฌ๊ฐœ ์žˆ๋Š”๋ฐ ๊ทธ ์ค‘ ์•„๋ž˜ ํ‘œ์‹œ๋œ ๊ฒƒ์œผ๋กœ ์‚ฌ์šฉํ•ด์•ผ ํ•จ.

@Service("mailService")
public class MailService {
	
	@Autowired //๊ฐ์ฒด ๋ถˆ๋Ÿฌ์˜ด (gradle์—์„œ ์ถ”๊ฐ€ํ•œ ๋ฉ”์ผ ๊ด€๋ จ ์ฝ”๋“œ๊ฐ€ ๊ฐ์ฒด๋ฅผ ๋งŒ๋“ค์–ด์คŒ)
	private JavaMailSender javaMailSender;
	
	//๋‹จ์ˆœ ๋ฌธ์ž ๋ฉ”์ผ ๋ณด๋‚ด๊ธฐ
	public void sendSimpleEmail(MailVO mailVO) {
		//๋‹จ์ˆœ ๋ฌธ์ž ๋ฉ”์ผ์„ ๋ณด๋‚ผ ์ˆ˜ ์žˆ๋Š” ๊ฐ์ฒด ์ƒ์„ฑ
		SimpleMailMessage message = new SimpleMailMessage();
		message.setSubject(mailVO.getTitle()); //๋ฉ”์ผ ์ œ๋ชฉ
		//๋ฆฌ์ŠคํŠธ๋ฅผ ๋ฐฐ์—ด๋กœ ๋ฐ”๊ฟ”์„œ?
		message.setTo(mailVO.getRecipientList().toArray(new String[mailVO.getRecipientList().size()])); //์—ฌ๋Ÿฌ๋ช…์˜ ์ˆ˜์‹ ์ž ๊ฐ€๋Šฅ
		message.setText(mailVO.getContent()); //๋‚ด์šฉ
		
		
		javaMailSender.send(message);
	}
}

ItemController์—์„œ mailVO์— ๋ฉ”์ผ ์ˆ˜์‹ ์ž ์ •๋ณด ์„ธํŒ…ํ•˜๊ธฐ ์ „์—

์—ฌ๋Ÿฌ ์ˆ˜์‹ ์ž ์ •๋ณด๋ฅผ ๋‹ด๋Š” ๋ฆฌ์ŠคํŠธ๋ฅผ ์ƒ์„ฑ

๊ทธ ๋ฆฌ์ŠคํŠธ์— ์—ฌ๋Ÿฌ ์ˆ˜์‹ ์ž๋“ค ๋‹ด์€ ํ›„ ๋ฆฌ์ŠคํŠธ๋ฅผ ์ˆ˜์‹ ์ž ์ •๋ณด ์„ธํŒ…ํ•  ๋•Œ ์‚ฌ์šฉ.

 

 

- HTML ํ˜•์‹์œผ๋กœ 6์ž๋ฆฌ ๋žœ๋คํ•œ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ฉ”์ผ ๋ณด๋‚ด๊ธฐ

 

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

์ด์šฉํ•˜์—ฌ ๋งŒ๋“ค์–ด์ง„ ํ…œํ”Œ๋ฆฟ ์‚ฌ์šฉ ๊ฐ€๋Šฅ

ํ…œํ”Œ๋ฆฟ ์„œ์น˜ํ•ด์„œ ์„ ํƒํ•˜๋ฉด ๊ธฐ์กด ํ…œํ”Œ๋ฆฟ ์ˆ˜์ •๋„ ๊ฐ€๋Šฅ

 

templates ํด๋”์— mail.html ์ƒ์„ฑ

ํƒ€์ž„๋ฆฌํ”„ ๋ฌธ๋ฒ• ์ฝ”๋“œ๋งŒ ๋‘๊ณ  ๋‚˜๋จธ์ง€ ์ฝ”๋“œ ์‚ญ์ œ ํ›„ ํ…œํ”Œ๋ฆฟ ์ฝ”๋“œ main.html์— ๋ถ™์—ฌ๋„ฃ๊ธฐ

๋‚จ๊ฒจ๋‘” ํƒ€์ž„๋ฆฌํ”„ ๋ฌธ๋ฒ• ์ฝ”๋“œ html์— ๋ถ™์—ฌ๋„ฃ๊ธฐ

๋ณต์‚ฌํ•œ ์ฝ”๋“œ ์ค‘ password ๋ถ€๋ถ„์€ ๋งค๋ฒˆ ๋ฐ”๋€Œ์–ด์•ผ ๋จ.

password ์ง€์›Œ์ฃผ๊ณ  th๋ฌธ๋ฒ• ์‚ฌ์šฉํ•˜์—ฌ password ๋ณ€์ˆ˜๋กœ ์„ค์ •.

MailService์—์„œ ๋ฉ”์†Œ๋“œ ์ž‘์„ฑ

์šฐ์„  HTML๋กœ ๋ฉ”์ผ ๋ณด๋‚ด๋Š” ์ฝ”๋“œ ์ž‘์„ฑ ์ „์—

๋žœ๋คํ•œ 6๊ธ€์ž์˜ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋งŒ๋“œ๋Š” ๋ฉ”์†Œ๋“œ ์ž‘์„ฑ.

	//6์ž๋ฆฌ์˜ ๋žœ๋ค ๋น„๋ฐ€๋ฒˆํ˜ธ ์ƒ์„ฑ
	public String createRandomPw() {
        String[] StringSet = new String[]{ "0", "1", "2", "3", "4", "5", "6", "7", "8", "9",
                "A", "B", "C", "D", "E", "F", "G", "H", "I", "J", "K", "L", "M", "N",
                "O", "P", "Q", "R", "S", "T", "U", "V", "W", "X", "Y", "Z",
                "a", "b", "c", "d", "e", "f", "g", "h", "i", "j", "k", "l", "m", "n",
                "o", "p", "q", "r", "s", "t", "u", "v", "w", "x", "y", "z"
                };
        
        //๋žœ๋คํ•œ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€์ˆ˜
        String pwd = "";

        //๋ฌธ์ž ๋ฐฐ์—ด ๊ธธ์ด์˜ ๊ฐ’์„ ๋žœ๋ค์œผ๋กœ 6๊ฐœ๋ฅผ ๋ฝ‘์•„ ์กฐํ•ฉ
        int randIndex = 0;
        for(int i = 0; i < 6; i++){
        	randIndex = (int)(StringSet.length * Math.random()); //0 <= x < 1 ์‹ค์ˆ˜ ๋ฆฌํ„ด
            pwd += StringSet[randIndex];
        }

        return pwd;
	}

 

//HTML ๋ฉ”์ผ ๋ณด๋‚ผ ์‹œ ๋‚ด์šฉ ์„ธํŒ…
public String setContext(String password) {

    Context context = new Context();
    //๋ณ€์ˆ˜ ์„ธํŒ…
    context.setVariable("password", password); //mail.html์˜ password ์ด๋ฆ„์˜ ๋ณ€์ˆ˜๋ฅผ password๋กœ ์ฑ„์›Œ์คŒ(?
        //templates์•ˆ์˜ mail.html์„ ๋‹ค๋ฃธ (mail.html์ด ํด๋” ์•ˆ์— ์žˆ๋‹ค๋ฉด ํด๋”๊นŒ์ง€ ๋„ฃ์–ด์ฃผ๋ฉด ๋จ)
    return templateEngine.process("mail", context); //๋ณ€์ˆ˜ ์ž‘์—… ํ›„ mail.html์˜ ๋‚ด์šฉ์„ return
}

 

//HTML ๋ฉ”์ผ ๋ณด๋‚ด๊ธฐ
public void sendHTMLEmail() {

    MimeMessage message = javaMailSender.createMimeMessage();
    String password = createRandomPw();

    try {
        message.setSubject("์ž„์‹œ ์ œ๋ชฉ");
                        //html ๋ณด๋ƒ„
        message.setText(setContext(password), "UTF-8", "html"); //์ด ๋‚ด์šฉ์„ html๋กœ ๋ณด๋ƒ„
        message.addRecipients(MimeMessage.RecipientType.TO, "byuuuuul@naver.com");
        javaMailSender.send(message);
    } catch (MessagingException e) {
        e.printStackTrace();
    }

}

 

header.html๋กœ ๊ฐ€์„œ ๋กœ๊ทธ์ธ๋ชจ๋‹ฌ์ฐฝ ํ•˜๋‹จ์— ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ์ƒ์„ฑ

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๊ธ€์ž ํด๋ฆญ ์‹œ ๋ชจ๋‹ฌ์ฐฝ ๋œจ๊ฒŒ ์ฝ”๋“œ ์ž‘์„ฑ

 

๋ชจ๋‹ฌ์ฐฝ ์ž‘์„ฑ ์‹œ ์•„๋ž˜ ์ฝ”๋“œ  ๋„ฃ์–ด์ฃผ๊ณ  target๊ณผ id ๋™์ผํ•˜๊ฒŒ ๋งž์ถฐ์ฃผ๋ฉด ๋จ.

data-bs-toggle="modal" data-bs-target="#findPwModal"

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๋Š” ๋ชจ๋‹ฌ์ฐฝ ์ฝ”๋“œ ์ž‘์„ฑ

<!-- ๋น„๋ฐ€๋ฒˆํ˜ธ์ฐพ๊ธฐ Modal -->
<div class="modal fade" id="findPwModal" data-bs-keyboard="false" tabindex="-1" aria-labelledby="staticBackdropLabel" aria-hidden="true">
  <div class="modal-dialog">
    <div class="modal-content">
      <div class="modal-body">
		<form id="findPwForm" >
      				<!-- mb-3 :margin-bottom -->
        <div class="row mb-3">
        	<div class="col-12">
				<input type="text" id="findPwMemId" name="memId" class="form-control" placeholder="Input your ID">        	
        	</div>
        </div>
        <div class="row mb-3">
        	<div class="col-12" id="findPwErrorDiv">
				<input type="text" id="findPwMemName" name="memName" class="form-control" placeholder="Input your Name">        	
        	</div>
        </div>
        <div class="row mb-3">
        	<div class="col-12 d-grid">
				<input type="button" class="btn btn-primary" value="๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ" onclick="findPw();">
				<!-- validation ํ•˜๋ ค๋ฉด button / ๋ฐ”๋กœ ํŽ˜์ด์ง€ ์ด๋™ : submit -->     	
        	</div>
        	<div class="col" style="font-size: 0.8rem; color: red;">
        		* ๊ฐ€์ž… ์‹œ ์ž…๋ ฅํ•œ ์ด๋ฉ”์ผ๋กœ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๊ฐ€ ๋ฐœ์†ก๋ฉ๋‹ˆ๋‹ค.
        	</div>
        </div>
      	</form>
      </div>
    </div>
  </div>
</div>

onclick ์†์„ฑ ์‚ฌ์šฉํ•˜์—ฌ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ํด๋ฆญ ์‹œ ํ•จ์ˆ˜ ์—ฐ๊ฒฐ

 

 

header.js ํ•จ์ˆ˜ ์ž‘์„ฑ

ํŽ˜์ด์ง€ ์ด๋™ ์—†์ด ์ž‘๋™์„ ์œ„ํ•ด ajax ์ด์šฉ

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ
function findPw(){
	
	//ID, ์ด๋ฆ„ input์ด ์žˆ๋Š” form ํƒœ๊ทธ
	//const findPwForm = $('#findPwForm') Jquery ๋ฌธ๋ฒ•์œผ๋กœ ํƒœ๊ทธ ์„ ํƒ
	
	//ajax start
	$.ajax({
		url: '/member/findPwAjax', //์š”์ฒญ๊ฒฝ๋กœ
		type: 'post',
		//findPwForm.serialize() : form ํƒœ๊ทธ ๋ฐ์ดํ„ฐ ๊ฐ€์ ธ๊ฐ€๋Š” Jquery ์ฝ”๋“œ, ๊ฐ€์ ธ๊ฐˆ ๋•Œ name์†์„ฑ์œผ๋กœ ๋ฐ์ดํ„ฐ ๊ฐ€์ ธ๊ฐ(submit๊ณผ ๋™์ผ)
		data: $('#findPwForm').serialize(), //ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ
		async : true, //default 
		//contentType : 'application/json; charset=UTF-8', //json ๋ฐฉ์‹
		contentType: "application/x-www-form-urlencoded; charset=UTF-8", //default ๋ฐฉ์‹
		success: function(result) {
			alert('ajax ํ†ต์‹  ์„ฑ๊ณต');
		},
		error: function() {
			alert('์‹คํŒจ');
		}
	});
//ajax end
	
}

์ฃผ์˜์‚ฌํ•ญ

ํ˜„์žฌ ์‹œํ๋ฆฌํ‹ฐ ์ฝ”๋“œ๋กœ ํŽ˜์ด์ง€ ์ธ์ฆ ์ธ๊ฐ€ ์„ค์ • ๋˜์–ด ์žˆ๊ธฐ ๋•Œ๋ฌธ์—

SecurityConfig ํด๋ž˜์Šค์— ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ์œ„ํ•œ ์ด๋™ ๊ฒฝ๋กœ๋„ ๋ชจ๋“  ์‚ฌ์šฉ์ž ์ ‘๊ทผ ๊ฐ€๋Šฅํ•˜๊ฒŒ ์ธ๊ฐ€ ํ—ˆ์šฉ ์ฝ”๋“œ ์ถ”๊ฐ€.

MemberController ์ž‘์„ฑ

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ 
@ResponseBody
@PostMapping("/findPwAjax")
public void findPw(MemberVO memberVO) {


}

 

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ์ด๋ฉ”์ผ ์กฐํšŒํ•˜๋Š” ์ฟผ๋ฆฌ ์ž‘์„ฑ

<!-- ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ์ด๋ฉ”์ผ ์ „์†ก -->
<select id="getMemEmail" resultType="String">
    SELECT MEM_EMAIL
    FROM SHOP_MEMBER
    WHERE MEM_ID = #{memId}
    AND MEM_NAME = #{memName}
</select>

ํ˜„์žฌ DB์— SHOP_MEMBER ํ…Œ์ด๋ธ”์— ์ด๋ฉ”์ผ ์ปฌ๋Ÿผ ์—†์Œ.

SHOP_MEMBER์— MEM_EMAIL ์ปฌ๋Ÿผ ์ถ”๊ฐ€

--SHOP_MEMBER ํ…Œ์ด๋ธ” MEM_EMAIL ์ปฌ๋Ÿผ ์ถ”๊ฐ€
ALTER TABLE SHOP_MEMBER ADD MEM_EMAIL VARCHAR2(100);

์•”ํ˜ธํ™”๋œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๊ฐ€์ง„ ์‚ฌ์šฉ์ž ์ค‘ MEM_EMAIL ์—…๋ฐ์ดํŠธ

UPDATE SHOP_MEMBER
SET MEM_EMAIL = 'byuuuuul@naver.com'
WHERE MEM_ID = 'user';

MemberVO์—๋„ ๋ฐ์ดํ„ฐ ๋ฐ›์•„์˜ฌ ์ˆ˜ ์žˆ๊ฒŒ memEmail ๋ณ€์ˆ˜ ์ถ”๊ฐ€

resultMap๋„ ์ถ”๊ฐ€

MemberService ๋ฉ”์†Œ๋“œ ์ž‘์„ฑ

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ
String getMemEmail(MemberVO memberVO);

MemberServiceImpl ์ž‘์„ฑ

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ํšŒ์› ์ด๋ฉ”์ผ ์กฐํšŒ
@Override
public String getMemEmail(MemberVO memberVO) {

    return sqlsession.selectOne("memberMapper.getMemEmail", memberVO);
}

 

MemberController ๋ฉ”์†Œ๋“œ ์‹คํ–‰

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ 
@ResponseBody
@PostMapping("/findPwAjax")
public boolean findPw(MemberVO memberVO) {

   //ํ•ด๋‹น ํšŒ์› ์ด๋ฉ”์ผ ์กฐํšŒ
   String memEmail = memberService.getMemEmail(memberVO);

    //์ด๋ฉ”์ผ ์ฐพ์•˜์œผ๋ฉด true ๋ชป ์ฐพ์€ ๊ฒฝ์šฐ false ๋ฐ์ดํ„ฐ ajax success ๊ตฌ๋ฌธ์œผ๋กœ
    return memEmail != null ? true : false;

}

ํšŒ์›์˜ ์ด๋ฉ”์ผ์ด ์žˆ๋Š” ๊ฒฝ์šฐ ์ž„์‹œ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ด๋ฉ”์ผ๋กœ ์ „์†กํ•ด์ฃผ๋ฉด ๋จ.

๋ฉ”์ผ ๋ฐœ์†ก ๋ฉ”์†Œ๋“œ ์‹คํ–‰์„ ์œ„ํ•ด mailService ๊ฐ์ฒด ๋ถˆ๋Ÿฌ์˜ค๊ธฐ

์ด๋ฉ”์ผ ์ „์†ก ์ „์— ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์ƒ์„ฑํ•˜๊ณ  ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์—ญ์‹œ ์•”ํ˜ธํ™” ๋˜์–ด ์žˆ์–ด์•ผ ํ•จ.

mailService์— ๋žœ๋คํ•œ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ƒ์„ฑํ•˜๋Š” ๋ฉ”์†Œ๋“œ๋ฅผ ์‹คํ–‰ํ•˜์—ฌ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋งŒ๋“  ํ›„

๊ทธ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ์•”ํ˜ธํ™” ์ž‘์—… ํ•ด์คŒ.

๋˜ํ•œ, ์ด๋ฉ”์ผ๋กœ ๋ฐœ์†ก๋œ ์ž„์‹œ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ์‹ค์ œ ๋กœ๊ทธ์ธ์ด ๊ฐ€๋Šฅํ•˜๊ฒŒ ์ž‘์—…ํ•ด์ค˜์•ผ ํ•จ.

์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋ณ€๊ฒฝํ•˜๋Š” ์ฟผ๋ฆฌ ์ž‘์„ฑ

<!-- ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝ -->
<update id="updateMemPw">
    UPDATE SHOP_MEMBER
    SET
    MEM_PW = #{memPw}
    WHERE MEM_ID = #{memId}
</update>

MemberService ๋ฉ”์†Œ๋“œ ์ž‘์„ฑ

//์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝ
void updateMemPw(MemberVO memberVO);

MemberServiceImpl ์ž‘์„ฑ

//์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝ
@Override
public void updateMemPw(MemberVO memberVO) {
    sqlsession.update("memberMapper.updateMemPw", memberVO);

}

 

MemberController ๋ฉ”์†Œ๋“œ ์‹คํ–‰

๋ฉ”์†Œ๋“œ ์‹คํ–‰ํ•˜๋ ค๋ฉด memberVO์—์„œ ์ฟผ๋ฆฌ ๋นˆ๊ฐ’ 2๊ฐœ ์ฑ„์›Œ์ค˜์•ผ ํ•จ.

memId๋Š” ํšŒ์› ์ด๋ฉ”์ผ ์กฐํšŒํ•  ๋•Œ memberVO์— ์„ธํŒ…๋˜์–ด ์žˆ๋Š” ์ƒํƒœ

memPw๋Š” ์•”ํ˜ธํ™”ํ•œ ์ž„์‹œ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ memberVO์— ๋ฐ์ดํ„ฐ ์„ธํŒ…ํ•ด์ฃผ๋ฉด ๋จ.

๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝํ•˜๋Š” ๋ฉ”์†Œ๋“œ ์‹คํ–‰.

๋น„๋ฐ€๋ฒˆํ˜ธ ์„ธํŒ… ์ž‘์—…์ด ๋‹ค ๋˜๋ฉด ๋ฉ”์ผ ์ „์†ก ๋ฉ”์†Œ๋“œ ์‹คํ–‰.

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ controller ์ „์ฒด ์ฝ”๋“œ

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ 
@ResponseBody
@PostMapping("/findPwAjax")
public boolean findPw(MemberVO memberVO) {

   //ํ•ด๋‹น ํšŒ์› ์ด๋ฉ”์ผ ์กฐํšŒ
   String memEmail = memberService.getMemEmail(memberVO);

   //์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ƒ์„ฑ
   String imsiPw = mailService.createRandomPw();
   //์•”ํ˜ธํ™” ์ž‘์—…
   String encodedPw = encoder.encode(imsiPw);
   memberVO.setMemPw(encodedPw);
   //์ž„์‹œ๋น„๋ฐ€๋ฒˆํ˜ธ๋กœ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝ
   memberService.updateMemPw(memberVO);


   //ํšŒ์›์˜ ์ด๋ฉ”์ผ ์ฐพ์€ ๊ฒฝ์šฐ ๋ฉ”์ผ ๋ณด๋‚ด๋Š” ๊ธฐ๋Šฅ
   if(memEmail != null) {
       MailVO mailVO = new MailVO();
       mailVO.setTitle("[BOOK SHOP] ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ฐœ์†ก");
       List<String> emaiList = new ArrayList<>();
       emaiList.add(memEmail);
       mailVO.setRecipientList(emaiList);
       mailVO.setContent(imsiPw);

       mailService.sendSimpleEmail(mailVO);

   }

//์ด๋ฉ”์ผ ์ฐพ์•˜์œผ๋ฉด true ๋ชป ์ฐพ์€ ๊ฒฝ์šฐ false ๋ฐ์ดํ„ฐ ajax success ๊ตฌ๋ฌธ์œผ๋กœ
return memEmail != null ? true : false;

}

๋ฉ”์ผ๋กœ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ํ™•์ธ ๊ฐ€๋Šฅ!

 

**๋งˆ์ดํŽ˜์ด์ง€์—์„œ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋กœ๊ทธ์ธ ํ›„ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝํ•˜๋Š” ๊ธฐ๋Šฅ ์žˆ์–ด์•ผ ํ•จ.

 

 

js์˜ success ๊ตฌ๋ฌธ์œผ๋กœ ๋Œ์•„์™€์„œ result๊ฐ€ true๋ฉด(์ด๋ฉ”์ผ ์žˆ๋Š” ๊ฒฝ์šฐ) alert์œผ๋กœ ์ด๋ฉ”์ผ ๋ฐœ์†ก ๋ฉ”์‹œ์ง€ ๋„์›Œ์คŒ

result false๋ฉด(์ด๋ฉ”์ผ ์—†๋Š” ๊ฒฝ์šฐ) ์—๋Ÿฌ ๋ฌธ๊ตฌ ๋„์›Œ์คŒ

 

 

header.js์˜ init ํ•จ์ˆ˜ ์ˆ˜์ •

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ชจ๋‹ฌ์ฐฝ ๋‹ซํžˆ๋ฉด ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ์„ ๋•Œ ์ž…๋ ฅํ•œ ๋‚ด์šฉ ์ง€์›Œ์ฃผ๋Š” ์ด๋ฒคํŠธ ์ž‘์„ฑ

1. form ํƒœ๊ทธ ์•ˆ์˜ input ํƒœ๊ทธ์˜ ๋‚ด์šฉ์„ ์ดˆ๊ธฐํ™” ์‹œ์ผœ์ฃผ๋Š” reset ์ฝ”๋“œ

2. ์—๋Ÿฌ ๋ฌธ๊ตฌ div ์„ ํƒํ•˜์—ฌ ์ง€์›Œ์คŒ

 

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ํ›„ ์ด๋ฉ”์ผ ์ „์†ก ๋กœ๋”ฉ ํ‘œ์‹œํ•ด์ฃผ๊ธฐ

bootstrap์˜ spinners๋ณด๋ฉด buttons๋ฅผ ๋ณด๋ฉด ๋ฒ„ํŠผ์— ๋กœ๋”ฉ ํ‘œ์‹œ ๊ฐ€๋Šฅํ•œ ์ฝ”๋“œ ์žˆ์Œ!

์•„๋ž˜ ์ฝ”๋“œ ํ™œ์šฉ

<button class="btn btn-primary" type="button" disabled>
  <span class="spinner-border spinner-border-sm" role="status" aria-hidden="true"></span>
  Loading...
</button>

ํ•œ ๋ฒˆ ๋ˆ„๋ฅด๋ฉด ๋ฒ„ํŠผ ๋น„ํ™œ์„ฑํ™” ๋˜๊ฒŒํ•˜๊ณ  ๋กœ๋”ฉ ํ‘œ์‹œ ์ฃผ๊ธฐ.

 

header.html ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ชจ๋‹ฌ์—์„œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ์ฐพ์•„๊ฐ.

์ด์ „์— ์ž‘์„ฑํ•œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ์ˆ˜์ •.

๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ํ•จ์ˆ˜์— ๋งค๊ฐœ๋ณ€์ˆ˜๋กœ this๋กœ ๋ฒ„ํŠผ ๋„˜๊ฒจ์ฃผ๊ณ  input ํƒœ๊ทธ์˜ ๋ฒ„ํŠผ์„ button ํƒœ๊ทธ๋กœ ์ˆ˜์ •

 

header.js
๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ์‹คํ–‰๋˜๋Š” ํ•จ์ˆ˜ ์ˆ˜์ •

์ฒ˜์Œ ๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํ™œ์„ฑํ™” ๋ฒ„ํŠผ ๋ˆŒ๋ €์„ ๋•Œ disabled ์†์„ฑ ์ถ”๊ฐ€ ๋˜๋ฉด ๋˜๊ณ ,

span ํƒœ๊ทธ์— ๊ฐ์‹ธ์ง„ spinner ์ถ”๊ฐ€ ๋˜๋ฉด ๋จ

 

๋ชจ๋‹ฌ์ฐฝ ๋‹ซํž ๋•Œ ์œ„์—์„œ ๋ฐ”๊ฟ”์ค€ ๋ฒ„ํŠผ(๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ) ๋‹ค์‹œ ์ด์ „ ์ƒํƒœ๋กœ ๋Œ์•„์™€์•ผ ํ•จ.

init ํ•จ์ˆ˜ ์ˆ˜์ •

๋ชจ๋‹ฌ์ฐฝ ๋‹ซํž ๋•Œ ์ด๋ฒคํŠธ ๋ฐœ์ƒํ•˜๊ฒŒ ์ฝ”๋“œ ์ž‘์„ฑ

์ฝ”๋“œ ์ž‘์„ฑ ์‹œ ํ•จ์ˆ˜์— ๋งค๊ฐœ๋ณ€์ˆ˜(event)๋ฅผ ์ถ”๊ฐ€ํ•  ์ˆ˜ ์žˆ์Œ.

๋งค๊ฐœ๋ณ€์ˆ˜.target์„ ํ•˜๋ฉด this์™€ ๋™์ผํ•œ ์—ญํ• ๋กœ ์“ธ ์ˆ˜ ์žˆ๋‹ค.

๋ชจ๋‹ฌ ํƒœ๊ทธ ์ž์ฒด๋ฅผ ์„ ํƒํ•˜์—ฌ ๋ชจ๋‹ฌ ํƒœ๊ทธ ์•ˆ์˜ ๋ฒ„ํŠผ ์„ ํƒ

๋ฒ„ํŠผ ์ด์ „ ์ƒํƒœ๋กœ ๋ฐ”๊ฟ”์ฃผ๋Š” ์ฝ”๋“œ ์‹คํ–‰ํ•˜๋ฉด ๋จ.

 

๋ฒ„ํŠผ์ด ์ด์ „ ์ƒํƒœ๋กœ ๋Œ์•„์™€์•ผ ํ•˜๋Š” ๊ฒฝ์šฐ ์ด๋ฉ”์ผ ์ฐพ์€ ๊ฒฝ์šฐ, ์ด๋ฉ”์ผ ์˜ค๋ฅ˜๋‚œ ๊ฒฝ์šฐ ๋‘˜ ๋‹ค

ajax success๋ฌธ์˜ ์ด๋ฉ”์ผ ์—†๋Š” ๊ฒฝ์šฐ ์ฝ”๋“œ์˜ if๋ฌธ ์ฝ”๋“œ ๋๋‚œ ํ›„ 

๋ฒ„ํŠผ ์ด์ „ ์ƒํƒœ๋กœ ๋Œ๋ฆฌ๋Š” ์ฝ”๋“œ ์ถ”๊ฐ€.

๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ ์‹คํ–‰๋˜๋Š” ํ•จ์ˆ˜ ์ „์ฒด ์ฝ”๋“œ

//๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ ๋ฒ„ํŠผ ํด๋ฆญ ์‹œ
function findPw(btn){
	
	btn.disabled = true;

	//๋ฒ„ํŠผ ๊ธ€์ž ๋ฐ”๊ฟ”์ฃผ๊ธฐ
	btn.querySelector('span').textContent = 'Loading';
	
	const spinner = '<span class="spinner-border spinner-border-sm" role="status" aria-hidden="true"></span>';
	btn.insertAdjacentHTML('afterbegin', spinner);
	
	
	
	//ID, ์ด๋ฆ„ input์ด ์žˆ๋Š” form ํƒœ๊ทธ
	//const findPwForm = $('#findPwForm') Jquery ๋ฌธ๋ฒ•์œผ๋กœ ํƒœ๊ทธ ์„ ํƒ
	
	//ajax start
	$.ajax({
		url: '/member/findPwAjax', //์š”์ฒญ๊ฒฝ๋กœ
		type: 'post',
		//findPwForm.serialize() : form ํƒœ๊ทธ ๋ฐ์ดํ„ฐ ๊ฐ€์ ธ๊ฐ€๋Š” Jquery ์ฝ”๋“œ, ๊ฐ€์ ธ๊ฐˆ ๋•Œ name์†์„ฑ์œผ๋กœ ๋ฐ์ดํ„ฐ ๊ฐ€์ ธ๊ฐ(submit๊ณผ ๋™์ผ)
		data: $('#findPwForm').serialize(), //ํ•„์š”ํ•œ ๋ฐ์ดํ„ฐ
		async : true, //default 
		//contentType : 'application/json; charset=UTF-8', //json ๋ฐฉ์‹
		contentType: "application/x-www-form-urlencoded; charset=UTF-8", //default ๋ฐฉ์‹
		success: function(result) {
			
			if(result){
				alert('์ด๋ฉ”์ผ๋กœ ์ž„์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ๋ฅผ ๋ฐœ์†กํ•˜์˜€์Šต๋‹ˆ๋‹ค.\n๋ฐ˜๋“œ์‹œ ๋น„๋ฐ€๋ฒˆํ˜ธ ๋ณ€๊ฒฝ ํ›„ ์‚ฌ์šฉํ•˜์‹ญ์‹œ์˜ค.');
				
			}
			//email ์—†๋Š” ๊ฒฝ์šฐ
			else{
				let str = '';
				
				str += '<div class="col-12 error-findPw">';
				str += '<span style="font-size: 0.8rem; color: red;">';
				str += '* ์ผ์น˜ํ•˜๋Š” ID์™€ ์ด๋ฆ„์ด ์—†์Šต๋‹ˆ๋‹ค. ํ™•์ธ ํ›„ ๋‹ค์‹œ ์ž…๋ ฅํ•˜์‹ญ์‹œ์˜ค.';
				str += '</span>';
				str += '</div>';
				
				document.querySelector('#findPwErrorDiv').insertAdjacentHTML('afterend', str);
				
				
			}
				//๋ฒ„ํŠผ ํด๋ฆญ ํ›„ ๊ฒฐ๊ณผ ๋‚˜์˜จ ํ›„ ๋ฒ„ํŠผ ์ด์ „ ์ƒํƒœ๋กœ ๋Œ๋ฆฌ๊ธฐ
				btn.disabled = false;
				btn.querySelector('span:first-child').remove();
				btn.querySelector('span').textContent = '๋น„๋ฐ€๋ฒˆํ˜ธ ์ฐพ๊ธฐ';
			
		},
		error: function() {
			alert('์‹คํŒจ');
		}
	});
//ajax end
	
}