티스토리 뷰
백엔드 배운지 일주일 정도 되었는데 쉽지않다!
그래도 계속해서 반복하면 언젠간 쉬워지겠지 제발
오늘 배운 파일업로드와 실습문제에서 가장 헤맸던 부분을 기록해 보았다.
실습 - 이미지를 업로드 하고 render된 페이지에서 이미지 보여주기
1. 폼페이지 만들기
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<script src="https://cdn.jsdelivr.net/npm/axios/dist/axios.min.js"></script>
<title>실습</title>
</head>
<body>
<h1>개인정보</h1>
//multer 사용시 enctype="multipart/form-data" 꼭!!
<form action="/join" method="POST" enctype="multipart/form-data">
<label for="userid">아이디 :</label>
<input type="text" id="userid" name="userid" />
<br />
<label for="userpw">비밀번호 :</label>
<input type="password" id="userpw" name="userpw" />
<br />
<label for="username">이름 :</label>
<input type="text" id="username" name="username" />
<br />
<label for="userage">나이 :</label>
<input type="number" id="userage" name="userage" />
<br />
<label for="userfile">프로필사진 :</label>
<input type="file" name="fileName" id="fileName" />
<br />
<button type="submit">회원가입</button>
</form>
</body>
</html>
*multer이용시 form태그에 속성으로 enctype="multipart/form-data" 꼭!!
2. 결과 페이지 만들기
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>실습결과</title>
</head>
<body>
<h3>아이디 : <%= userInfo.id%></h3>
<h3>비밀번호 : <%= userInfo.pw%></h3>
<h3>이름 : <%= userInfo.name%></h3>
<h3>나이 : <%= userInfo.age%></h3>
<img src="/uploads/<%= userInfo.file%>" width="100px" />
</body>
</html>
3. 대망의 서버
const express = require("express");
const app = express();
const PORT = 8000;
const path = require("path");
//multer 설정
const multer = require("multer");
const upload = multer({
// 파일 저장 경로 ( 설정이 없으면 기본 저장만 되므로 설정까지 같이 하는 작업 필요)
dest: "uploads/",
});
//요게 업로드 설정하는 작업
const uploadDetail = multer({
storage: multer.diskStorage({
destination(req, file, done) {
done(null, "uploads/");
},
//파일이름 넣어주기
filename(req, file, done) {
const ext = path.extname(file.originalname); //파일의 확장자만 가져옴 ex)jpg,pdf등
done(null, path.basename(file.originalname, ext) + Date.now() + ext); //파일의 원래 이름만 가져오기 위해 위에서 구한 확장자명을 지우고 날짜를 넣고 다시 확장자를 붙임
},
}),
limits: { fileSize: 5 * 1024 * 1024 }, //파일 사이즈
});
//템플릿
app.set("view engine", "ejs");
app.use(express.urlencoded({ extended: true }));
app.use(express.json());
//폴더에서 파일가져올수있음
app.use("/views", express.static(__dirname + "/views"));
app.use("/uploads", express.static(__dirname + "/uploads"));
//맨앞에 경로가 붙으면 로컬호스트/경로/파일이름?
//과제
app.get("/practice", function (req, res) {
res.render("practice");
});
// /join으로 들어갔을때 result.ejs 렌더링
app.post("/join", uploadDetail.single("fileName"), function (req, res) {
// res.send(req.body);
console.log(req.file);
res.render("result", {
userInfo: {
id: req.body.userid,
pw: req.body.userpw,
name: req.body.username,
age: req.body.userage,
file: req.file.filename,
},
});
});
app.listen(PORT, () => {
console.log(`로컬호스트 ${PORT}`);
});
※ 파일이름 만드는 방법
● path.extname → 파일경로의 확장자를 반환
ex) path.extname(test.jpg) → jpg만 남음
● path.basename → 파일경로에서 파일의 기본 이름만 반환
ex)path.basename(test.jpg, .jpg) → test만 남음
//파일이름 넣어주기
filename(req, file, done) {
const ext = path.extname(file.originalname); //파일의 확장자만 가져옴 ex)jpg,pdf등
done(null, path.basename(file.originalname, ext) + Date.now() + ext);
//파일의 기본 이름만 가져오기 위해 ext 변수를 사용해서확장자명을 지우고
//파일이름에 현재 시간 나타내는 Date.now()를 붙이고 다시 확장자를 붙임
//Date.now()는 현재시간을 구해주는 함수로 파일이름의 고유성을 위해 붙이는 것,
},
그리고 서버에서 제에에일 헤맨 부분
file에 어떤 값을 넣어야 할지 계속 헤매다가
console.log(req.file) 해보고 알았다
filename......
app.post("/join", uploadDetail.single("fileName"), function (req, res) {
// res.send(req.body);
console.log(req.file);
res.render("result", {
userInfo: {
id: req.body.userid,
pw: req.body.userpw,
name: req.body.username,
age: req.body.userage,
file: req.file.filename,
},
});
});
파일 한개만 업로드
- ejs 코드
<h4>싱글 파일업로드</h4>
<!--multer는 멀티파트폼데이터만 사용할 수 있음-->
<form action="/upload" method="POST" enctype="multipart/form-data">
<input type="text" name="title" />
<!--여기 name값이 백엔드의 /upload로 들어감-->
<input type="file" name="fileName" />
<br />
<button type="submit">업로드</button>
</form>
- 서버 코드
app.post('form 경로', uploadDetail.single("클라이언트에서 input 태그 name 값"),function(req,res){ 실행할 코드 })
//single : 싱글파일 업로드
app.post("/upload", uploadDetail.single("fileName"), function (req, res) {
//위의 upload때문에 upload.single 해준것
res.send("싱글 파일업로드");
});
*uploadDetail.single을 사용하여 파일에 접근 후
multer을 사용하여 파일을 업로드 하고
' req.file ' 객체에 저장!
라우터에서 req.file을 통해 해당 파일에 접근할 수 있음
파일 여러개 업로드 버전 2개
● 여러개 파일 업로드
- ejs 코드
*파일 여러개 업로드시 input에 multiple 속성을 추가해야함
<form action="/upload/array" method="POST" enctype="multipart/form-data">
<!--multiple 붙여야 파일 여러개 고를수있음-->
<input type="file" name="fileName" multiple />
<button type="submit">업로드</button>
</form>
- 서버 코드
app.post('form 경로', uploadDetail.array("클라이언트에서 input 태그 name 값"),function(req,res){ 실행할 코드 })
//array : 파일 여러개 업로드
app.post("/upload/array", uploadDetail.array("fileName"), function (req, res) {
res.send("멀티파일 업로드");
});
*uploadDetail.single을 사용하여 파일에 접근 후
multer을 사용하여 파일을 업로드 하고
' req.files ' 객체에 저장!
라우터에서 req.files을 통해 해당 파일에 접근할 수 있음
● 여러개 파일 개별 업로드
- ejs 코드
*파일 여러개 업로드시 input에 multiple 속성을 추가해야함
<h4>여러개 각각 파일 업로드</h4>
<form action="/upload/fields" method="POST" enctype="multipart/form-data">
<input type="file" name="fileName1" multiple />
<br />
<input type="file" name="fileName2" multiple />
<input type="submit" value="업로드" />
</form>
- 서버 코드
//fields : 파일 여러개 따로 업로드
app.post(
"/upload/fields",
uploadDetail.fields([{ name: "fileName1" }, { name: "fileName2" }]),
function (req, res) {
res.send("각각 멀티파일 업로드");
}
);
axios로 동적파일 업로드
- ejs 코드
<h4>동적 파일 업로드</h4>
<input type="file" name="dynamicUpload" id="dynamicUpload" />
<button type="button" onclick="upload()">업로드</button>
<br />
<img id="img" width="100px" /> <!--이미지 들어올 자리-->
<script>
function upload() {
const formData = new FormData(); //form을 동적으로 제어
const file = document.querySelector("#dynamicUpload"); //file 타입 인풋 태그 가져오기
formData.append("dynamicUpload", file.files[0]); //dynamicUpload은 서버에서 해당파일을 식별하기 위한 키값
console.log(file.files[0]); //file.files[0] : input에 넣은 사진 가져와라
axios({
method: "POST",
url: "/dynamic",
data: formData,
headers: {
"Content-Type": "multipart/form-data",
},
}).then(function (response) {
console.log(response);
const img = document.querySelector("#img");
img.setAttribute("src", response.data.path); //img태그에 src 속성 추가해서 이미지 보이게
});
}
</script>
axios는 클라이언트 측에서 HTTP 요청을 보내는 데 사용되는 js 라이브러리로 주로 서버와의 데이터 통신을 단순화하고 비동기적인 요청을 처리하는 데에 활용됨
*axios의 옵션
- method: HTTP 요청 메서드
- url : 요청을 보낼 서버의 URL
- data : 요청에 함께 전송할 데이터
- headers: 요청의 헤더를 설정, "Content-Type": "multipart/form-data"를 설정하여 멀티파트 폼 데이터를 전송
axios의 then() 메서드를 사용하여 요청이 성공적으로 완료되었을 때 처리할 콜백 함수를 등록할 수 있음
위의 코드에서는 데이터를 받아와서 response 객체에 저장하고, 이를 활용하여 이미지 태그의 src 속성을 설정하여 이미지를 표시하고 있음
'Coding > 포스코x코딩온' 카테고리의 다른 글
mvc 패턴 (0) | 2023.05.24 |
---|---|
[포스코x코딩온] 웹 풀스택 과정 5주차 데이터 베이스 기초 (0) | 2023.05.20 |
[포스코x코딩온] 웹 풀스택 과정 4주차 비동기 HTTP 통신 axios (0) | 2023.05.17 |
[포스코x코딩온] 웹 풀스택 과정 4주차 form에서 입력한 데이터 서버로 전송하기 (0) | 2023.05.17 |
[포스코x코딩온] 웹 풀스택 과정 4주차 (백엔드 시작) 노드, express, ejs (0) | 2023.05.16 |