2 minute read

리액트 백앤드 연동(개발)

개발서버를 연동한다.

  • 백앤드 서버
    1. 백앤드서버 라이브러리 설정
    2. 백앤드서버 코드 작성
  • 프론트 서버
    1. 프론트서버 프록시 설정
    2. 프론트서버 코드 작성

1. 백앤드서버 라이브러리 설정

(pom.xml)

<!-- 리액트에서 ajax 요청시 Map객체 리턴하는 컨트롤러에서 json 관련에러를 잡아줌. -23.07.16 CTH -->
<dependency>
	<groupId>com.google.code.gson</groupId>
	<artifactId>gson</artifactId>
	<version>2.8.0</version>
</dependency>

위와 같은 라이브러리를 추가한 이유
연동을 완료 하고나서 프론트에 접속하면 프록시를 통해 backend 서버로 요청이 간다. (json으로 RequestBody 응답의 map객체를 리턴한다.) 그런데 자꾸 HashMap에 관련한 아래와 같은 에러를 백앤드에서 응답했다.

# 이 경우는 스프링에서 HttpMessageConverter로 사용할 객체를 자동으로 찾지 못해서 발생한다.
# jackson의 ObjectMapper 객체나 Gson의 Gson 객체가 있으면 스프링 4 이상에서는 자동으로 Jackson2MessageConverter 또는 GsonMessageConverter를 설정한다.
Request processing failed; nested exception is java.lang.IllegalArgumentException: No converter found for return value of type: class java.util.HashMap

찾아보니 버전을 4버전 이상으로 올리면 대부분 해결된다고 하며, 문제시에는 List, Map 형태에서 발생 가능하다고 한다. 이러한 이유로 gson 라이브러리를 추가 한다.

2. 백앤드서버 코드 작성

(HomeController.java)

@ResponseBody
@RequestMapping(value="/app/test",method = RequestMethod.GET)
public Map<String, Object> test() throws Exception{
	
  logger.info("HomeController test start  >>");
  
  //1. 객체생성
  Map<String, Object> resultJSON = new HashMap<>();
    
  try {
    resultJSON.put("message", "Hello from the backend!");
    
  } catch (Exception e) {
    //jsp쪽으로 보내는 오류정보
    logger.debug("ExceptionMsg : {}", e.getMessage());
    e.printStackTrace();
    throw e;
		
  } finally {
    logger.debug("test finally : {}", "Ok");
  }
    
  return resultJSON;
}

3. 프론트서버 프록시 설정

(package.json)

{
...
"proxy": "https://blang.co.kr/",
...
}

요청시 백앤드와 통신하기 위해 프록시를 위처럼 설정했다. (나의 경우 집에 물리적인 웹서버 2대, WAS서버 2대가 연동되어 있으므로 기본 도메인을 넣었다.)

4. 프론트서버 코드 작성

(App.js)

function App() {
    const [data, setData] = useState(null);
   
    /*
    위의 코드에서는 fetch 함수를 사용하여 /dbd/app/test 경로로 GET 요청을 보내고, 
    응답을 JSON 형식으로 파싱하여 상태 변수 data에 저장합니다. useEffect 훅을 사용하여 
    컴포넌트가 마운트될 때 한 번만 요청을 보내도록 합니다.
    응답이 성공적으로 받아지면, data 상태 변수를 사용하여 데이터를 렌더링합니다. 
    응답이 아직 도착하지 않은 경우에는 "Loading..." 메시지를 표시합니다.
    위의 코드에서 /api/test 는 백엔드 API의 실제 엔드포인트로 대체되어야 합니다. 
    또한, 응답 형식 및 데이터 구조는 백엔드 API의 설계에 따라 달라질 수 있습니다. 
    따라서 실제 백엔드 API와의 통신을 위해서는 해당 API의 엔드포인트와 
    응답 처리 방식에 맞게 코드를 수정해야 합니다.
    */
    useEffect(() => {
		const fetchData = async() => {
		  try {
			const response = await fetch('/dbd/app/test');
			const jsonData = await response.json();
			setData(jsonData);
			
		  } catch (error) {
			console.error('Error:', error);
		  }
		};
		
		fetchData();
    }, []);
	
	  return (
        {/* 기본구조 */}
        <div id="wrap" className="wrap">
			
          {/* 백앤드 데이터 */}
          {data ? (
            <div>
              <h1>현재 백앤드: 백앤드가 연결되었습니다.</h1>
              <p>{data.message}</p>
            </div>
          ) : (
            <p>현재 백앤드: Loading...</p>
          )}
        <div>
    );
}

export default App;

테스트

  1. 백앤드(web/was) 실행 && 프론트(react) 실행
  2. 클라이언트(크롬)로 프론트서버 요청
  3. 프록시를 통한 백앤드 측으로 요청됨 > 컨트롤러 실행 > Map 리턴
  4. 프론트서버에서 응답결과 UseState 값을 셋팅. > 결과에 따라 화면 핸들링

Tags:

Categories:

Updated:

Leave a comment