Mi Lugarcito

React & Node.js - Node.js Express에서 파일 업로드 요청 처리 및 db 데이터 사입하기 본문

React & Next.js

React & Node.js - Node.js Express에서 파일 업로드 요청 처리 및 db 데이터 사입하기

selene park 2021. 3. 13. 11:18

이미지파일처리를 위해서 라이브러리 추가 해야함

npm install --save multer

 

Customer.js

import React from 'react'; 
import TableRow from '@material-ui/core/TableRow';
import TableCell from '@material-ui/core/TableCell';

class Customer extends React.Component{ // 한명의 고객에 대한 정보를 출력하는 역할
    render(){
       return(
           <TableRow>
               <TableCell>{this.props.id}</TableCell>
               <TableCell><img src={this.props.image} alt="profile" style={{width:64, height:64}}/></TableCell>
               <TableCell>{this.props.name}</TableCell>
               <TableCell>{this.props.birthday}</TableCell>
               <TableCell>{this.props.gender}</TableCell>
               <TableCell>{this.props.job}</TableCell>
           </TableRow>
       )
    }
}
export default Customer;

 

CustomerAdd.js

//고객추가 양식 만들기
//서버와의 통신 목적의 라이브러리 설치하기
import React from 'react';
import {post} from 'axios';

class CustomerAdd extends React.Component{
    constructor(props){
        super(props);
        //모든 변수 초기화해주기
        this.state={
            file:null,
            userName:'',
            birthday:'',
            gender:'',
            job:'',
            fileName:''
        }
    }
    //함수 만들어야한다. 총 3가지
    handleFormSubmit = (e) =>{
        e.preventDefault()
        this.addCustomer()
            .then ((response) => {
                console.log(response.data);
            })
        this.setState({
            file:null,
            userName:'',
            birthday:'',
            gender:'',
            job:'',
            fileName:''
        })
        window.location.reload();
    }

    handleFileChange =(e) =>{//file[0]이게 아니라 files[0] 이거임@@@
        this.setState({
            file:e.target.files[0],
            fileName:e.target.value
        })
    }

    handleValueChange=(e)=>{
        let nextState ={};
        nextState[e.target.name] = e.target.value;
        this.setState(nextState);
    }

    
    addCustomer =() =>{
        const url ='/api/customers';
        const formData = new FormData();
        formData.append('image', this.state.file);
        formData.append('name', this.state.userName);
        formData.append('birthday', this.state.birthday);
        formData.append('gender', this.state.gender);
        formData.append('job', this.state.job);
        const config ={
            headers:{
                'content-type': 'multipart/form-data'
            }
        }

        return post(url, formData, config);//환경설정 :  config ---> 이렇게 3개의 요소를 headers에 맞추어서 실제 서버로 데이터 보내도록 하는 기능
    }

    render(){
        return(
            <form onSubmit={this.handleFormSubmit}>
                <h1>고객추가</h1>
                프로필 이미지 : <input type="file" name="file" file={this.state.file} value={this.state.fileName} onChange={this.handleFileChange}/><br/>
                이름 : <input type="text" name="userName" value={this.state.userName} onChange={this.handleValueChange}/><br/>
                생년월일 : <input type="text" name="birthday" value={this.state.birthday} onChange={this.handleValueChange}/><br/>
                성별 : <input type="text" name="gender" value={this.state.gender} onChange={this.handleValueChange}/><br/>
                직업 : <input type="text" name="job" value={this.state.job} onChange={this.handleValueChange}/><br/>
                <button type="submit">추가하기</button>
            </form>
        )
    }
}

export default CustomerAdd;

 

server.js

//디비 환경설정 정보 읽어오기
const fs = require('fs');

const express =require('express');
const bodyParser = require('body-parser');
const app =express();
const port = process.env.port || 5000;

app.use(bodyParser.json());//기본적으로 REST API 에서는 데이터 주고받을때 json 데이터 형식으로 주고받음
app.use(bodyParser.urlencoded({extended:true}));



 
//디비연동 코드
const data = fs.readFileSync('./database.json');
const conf = JSON.parse(data);
const mysql = require('mysql');
const connection = mysql.createConnection({
  host : conf.host,
  user : conf.user,
  password : conf.password,
  port : conf.port,
  database : conf.database
});
connection.connect();

//이미지파일처리를 위해서 라이브러리 추가 해야함
const multer = require('multer');
const upload = multer({dest: './upload'})




//실제로 고객데이터삽입요청 처리해아한다. 
app.get('/api/customers', (req,res) => {
    //디비 접근하기
    connection.query(
      //쿼리 날리기
      "select * from CUSTOMER",
      (err, rows, fields)=>{
        res.send(rows);
      }
       
    );
});


//이미지 파일 처리하는 부분
app.use('/image', express.static('./upload'));//'./image' 말고 '/image'하니까 이미지 잘 출력된다......
app.post('/api/customers', upload.single('image'), (req, res) =>{ // var대신 let을 사용한다. 
  let sql ='insert into CUSTOMER values (null,?,?,?,?,?)';
  //let image ='/image/' + req.file.filename; //이렇게 하니까 사진은 디비에 올라가긴 하는데 깨져서 올라감...
  let image ='http://localhost:5000/image/' + req.file.filename;
  let name = req.body.name;
  let birthday = req.body.birthday;
  let gender = req.body.gender;
  let job = req.body.job;


  //디버깅
  // console.log(name);
  // console.log(image);
  // console.log(birthday);
  // console.log(gender);
  // console.log(job);


  let params=[image, name, birthday, gender, job];
  connection.query(sql, params, 
    (err, rows, field) => {
        res.send(rows);
        //디버깅용
        console.log(image);
    }
  );
});


app.listen(port, ()=> console.log(`listening on port ${port}`));