org.springframework.beans.factory.BeanCreationException 에러 이유

Error 2021. 2. 3. 23:38

오늘은 Spring boot 프로젝트를 기본설정 하던중 org.springframework.beans.factory.BeanCreationException 이라는 에러에 부딪혔다. 

 

처음에는 어딘가 부족한 라이브러리가 있다던가 properties 파일에서 설정이 잘못된줄 알고 있엇다.

※ 시도해본 방법

1. odbc8에서 부족한 라이브러리 있는거 같아서 구글링을 한 후 [ osdt_core.jar ] 같은 라이브러리를 추가해주었다.

하지만 문제의 이유는 이것이 아니였다. 

 

2. properties 파일에서 설정이 잘못 됫나 하고 애꿎은 설정만 건드렷엇다.

 

에러의 이유를 찾아서 이곳 저곳 건들다가 Console 창 에러내용의 끝부분을 보았더니.

 

 

xml 파일쪽에서 뭔가 에러가 나는 모양이다.

하지만 나는 해당 xml파일에 아무것도 개발한 것이 없었기 때문에 당연히 이 파일에서는 에러의 원인이 아닌줄 알았다.

 

하지만 에러의 원인은 아무것도 안한 index,xml 이 파일에서 나타나는 것이였다.

 

에러의 원인은 해당 xml 파일에

<mapper namespace="경로"> </mapper>

이 것을 안만들어 줘서 에러가 나는 것이엿다.   

해당 에러의 원인을 알았으니 다음부터는 이러한 비슷한 에러가 나왓을때 실수하지 말아야 겠다.

 

해당 에러는 여러가지의 이유로 나타날 수 있습니다.

 

'Error' 카테고리의 다른 글

TypeError: Cannot read property 'msie' of undefined 에러잡기  (0) 2020.12.31

설정

트랙백

댓글

스프링 @Bean 의 LifeCycle 주기에 대해서

Spring & Spring Boot 2021. 1. 19. 23:36

우리가 개발을 할때 사용하는 JAVA나 Spring @Bean 에 대해서 많이 들어봣을 것이다.

우리가 사용하는 Spring boot 에서는 처음 어플리케이션을 시작을 할때 @Bean 을 컨테이너에 사용하기 좋게 미리 넣어둔다. 

우리는 스프링이 DI컨테이너에 넣어둔 Bean을 꺼내어 사용하는것을 잘 알고 있을 것이다.

그렇다면 Bean은 언제 생성이 되고 언제 소멸이 되는지 궁금해 졋다.

◈ Spring Bean 이벤트 처리 

컨테이너 생성 

              ☞ 빈 생성

                          ☞ 외존관계 주입

                                              ☞ 초기화 콜백

                                                                  ☞ 실제 사용

                                                                                    ☞ 소멸되전 콜백

                                                                                                          ☞ 종료

 

 여기서 초기화 콜백소멸되기 전 콜백은 무엇을 말하는 것일까?

 

초기화 콜백 : 빈이 생성된 후 의존관계 주입이 일어난다. 의존관계 주입이 끝나면 호출

소멸되기 전 콜백 : 빈이 소멸되기 직전에 호출된다.

간단하게 Bean의 LifeCycle 생명 주기에 대해서 알아보았습니다.

설정

트랙백

댓글

@ComponentScan 이란?

Spring & Spring Boot 2021. 1. 15. 23:45

스프링 부트에서 공부를 하다보면은 @ComponentScan 이라는 어노테이션을 본적이 있을 것이다.

@ComponentScan 은 어떤 역할을 해주는가?

특정 어노테이션들을 자동으로 스캔을 해주는 아주 유용한 어노테이션이다.

기본적으로 @ComponentScan 어노테이션이 스캔해주는 대상은 5가지로 나뉠수 있다.

  1. @Component
  2. @Controller
  3. @Service
  4. @Repository
  5. @Configuration

5가지로 나뉘어 진다. 

 

그리고 @ConponentScan 은 자기가 위치하고 있는곳부터 스캔을 시작한다.

무슨말이냐면은 프로젝트 파일구조가 

java / com / spring / boot 라고 가정했을때 @ComponentScan 어노테이션을 가지고 있는 파일 현 위치가 com폴더에 존재고 있다고 하면은 com 위치부터 @Componet 가 붙어있는 녀석들을 찾아주는 것이다.

하지만 스프링 부트에서는 @ComponetScan 의 위치를 조절해야 하는 것들은 기본적으로 제공을 해주고 있다.

어떻게 제공을 해주고 있는가?

 

스프링 부트에서는

스프링 부트를 시작해주는 메인 메소드가 있다. 사진에 보이는 @SpringbootApplication 해당 어노테이션을 들어가 보면은

스프링 부트를 시작해주는 어노테이션에 우리가 알고싶어 하던 @ConponentScan 어노테이션이 정의 되어 있는 것을 확인 할 수 있다. 

그렇다면 당연히 부트를 시작 Run을 하게되면은 우리가 @ComponentScan 으로 하나하나 조절해가야 하는것을 자연스럽게 스프링 부트가 기능을 대신 해주는 것을 확인 할 수 가 있을 것이다.

설정

트랙백

댓글

#3 알고리즘 문제 풀기

코딩테스트 2021. 1. 5. 22:16

※ 문제 설명

 

※ 제한 사항 

 

풀이 코드 ※

 

☞ 해당 문제는 3진법으로 진행하여 문제풀이를 하였다. 풀이는 간단하다.

1. n의 숫자를 변수로 선언한다.

2. 해당 숫자의 나눈 후 나머지를 String 타입에 이어 붙있다.

3. n의 숫자를 선언한 변수를 /3씩 해준다.

4. 마지막으로 String에 0010 이런식으로 문자열이 만들어져 있는 것을 Integer 타입으로 변환을 시켜준다.

└ 뒤에 3을 추가한 이유는 변환할 진수값을 넣는 것이다.

5. 3진수로 변환된 변수를리턴 시켜준다.

'코딩테스트' 카테고리의 다른 글

#2 알고리즘 문제 풀기  (0) 2021.01.03
#1 알고리즘 문제 풀기  (0) 2021.01.03

설정

트랙백

댓글

#2 알고리즘 문제 풀기

코딩테스트 2021. 1. 3. 20:38

해당문제는 2016년 1월1일이 금요일이라고 가정했을 때 입력받은 month , day 의 요일을 구하는 문제입니다.

※ #1 달마다의 마지막 일수 , 요일 구하기 

☞ day에서 FRI 가 맨앞에 있는 이유는 1월1일이 금요일이기에 이순서로 지정을 한 것입니다.

☞ 2개의 배열을 사용하여 해당 몇월/몇일 은 무슨요일인기 어떻게 구하는 것인가?

 

※ #2 배열을 활용하여 요일 구하기 

☞ 1번째 해당 월의 일수를 total 변수에 모두 더한다.

 

☞ 2번째 일수를 total 변수에 더한다.

- 일수를 더할때 -1을 해주는 이유는 배열의 index는 0부터 시작이기때문에 -1을 해준 것입니다.

 

☞ total 일수의 더해진 것을 total % 7  연산자를 사용하면은 해당 주의 무슨 요일인지 나올 것입니다.

 

※ #3 전체 코드 

 

'코딩테스트' 카테고리의 다른 글

#3 알고리즘 문제 풀기  (0) 2021.01.05
#1 알고리즘 문제 풀기  (0) 2021.01.03

설정

트랙백

댓글

#1 알고리즘 문제 풀기

코딩테스트 2021. 1. 3. 03:46

오늘은 해당 문제를 풀어볼 것이다. 

 이라고 가정을 하고 진행을 해봅시다.

내가 생각한 방법은 HashSet으로 중복을 제거된 상태의 객체를 만든 후 그 set을 List에 담고 그것을 배열에 담아서 리턴해주는 방식으로 진행을 하였다.

 

 

※ #1 HashSet에 서로 다른 index의 값을 넣어주기 

   HashSet<Integer> set = new HashSet<Integer>();
	        
       for(int i=0; i<numbers.length;i++){
	       for(int i2=0; i2<numbers.length; i2++){
	           if(i == i2) {
	               continue;
	           }
	           set.add(numbers[i] + numbers[i2]);
	       }  
	   }  
	   return test(set);

☞ 이중for문을 돌면서 서로 다른 index에 있는 값들을 set에 넣어준다.

☞ HashSet은 중복된 값을 넣을 수 없기때문에 중복이 제거된 수만 넣어지게 된다.

☞ 리턴을 test 라는 함수에 인자값으로 던져준다.

 

※ #2 HashSet의 인자값을 배열형식으로 변환하기

  public static int[] test(HashSet set) {
			
	    	System.out.println(set);
	    	List<Integer> list = new ArrayList<Integer>(set);
			Collections.sort(list);
            
	    	int[] arr = new int[list.size()];
	    	
	    	for(int i=0; i<list.size(); i++) {
	    		arr[i] = list.get(i);
	    	}
	    	return arr;
	    }

☞ HashSet 을 List로 변환하기

☞ List에 있는 값들을 배열으로 변환하여 리턴시키기

방법은 간단합니다. 

변환된 List를 for문을 돌면서 배열에 넣어주고 그 배열을 리턴시켜주면 끝입니다.

 

※ #3 전체 코드 

    public static int[] solution(int[] numbers) {

	        HashSet<Integer> set = new HashSet<Integer>();
	        
	        for(int i=0; i<numbers.length;i++){
	            for(int i2=0; i2<numbers.length; i2++){
	                if(i == i2) {
	                    continue;
	                }
	                set.add(numbers[i] + numbers[i2]);
	            }  
	        }  
	        return test(set);
	    }
	
	    public static int[] test(HashSet set) {
			
	    	System.out.println(set);
	    	List<Integer> list = new ArrayList<Integer>(set);
	    	
	    	int[] arr = new int[list.size()];
	    	
	    	for(int i=0; i<list.size(); i++) {
	    		arr[i] = list.get(i);
	    	}
	    	return arr;
	    }

 

◈ 햇갈렷던 부분 

  1. 서로다른 index를 더하면 수많은 더한 값들은 어떻게 처리를 해야하는가?
  2.  
  3. 중복된 값들은 어떻게 중복제거를 할 것인가?
  4.  
  5. HashSet 을 어떻게 배열형식으로 리턴을 해주도록 할것인가?

위의 3개의 관점에서 햇갈렷던거 같습니다.

사람마다의 생각하는 것과 처리하는 것을 수많가지 이므로 이보다 더 좋은 처리방법or다른처리방법 댓글로 남겨주시면 감사하겠습니다.

 

'코딩테스트' 카테고리의 다른 글

#3 알고리즘 문제 풀기  (0) 2021.01.05
#2 알고리즘 문제 풀기  (0) 2021.01.03

설정

트랙백

댓글

Spring @Bean 등록과 사용

Spring & Spring Boot 2020. 12. 20. 13:28

스프링에서는 DI컨테이너라는 핵심기술이 있다. DI컨테이너는 무엇일까?

DI컨테이너는 @Bean으로 등록한 객체들을 관리해주는 컨테이너 라고 생각해도 좋다.

그렇다면 @Bean 으로 DI컨테이너에 어떻게 등록을 할까?

기존 외부에서 관리해주는 ConfigApp 이라는 클래스에 @Configuration 이라는 어노테이션을 등록을 해준다.

그렇다면 그 클래스안에 있는 메소드들을 @Bean이라는 어노테이션을 작성하여 DI컨테이너에 Bean으로 등록을 할 수 있다.

 

그렇다면 @Bean 으로 등록을 한 객체들을 어떻게 사용을 하는 것 인가?

 

 

위 사진의 에서 주석이 된 코드를 보면은 개발자가 직접 객체를 생성하고 사용을 하는 것을 확인할 수 있다.

하지만 아래 코드에서는 DI컨테이너에 등록된 Bean을 Bean의 이름과 타입을 지정해서 사용하는 것을 볼 수 있다.

 

설정

트랙백

댓글

Spring 관심사의 분리 (의존관계 주입 개념)

Spring & Spring Boot 2020. 12. 17. 23:26

관심사의 분리란 무엇일까?

말그대로 서로의 관심사를 따로따로 향하도록 분리를 시키는 것이다.

예로 들어 한 식당의 주방장이 요리를 하면서 서빙을 하는 것 VS 주방장은 요리만 서빙은 알바만 하도록 하는 것

코드로 예시로 이해해보자.

1번째 주방장이 요리를 하면서 서빙도 같이 한다는 것을 코드로 하는게 어떤식일까? 

여기서 보면은 해당 A라는 클래스에는 MemberService와 구현클래스인 MemberServiceImpl 을 둘다 의존하고 있다.

이러한 경우에는 DIP(Dependercy Inversion Principle) 을 위반하는 것과 같다고 생각한다.

※ 위같은 경우 문제점은 해당 인터페이스의 다른 로직을 수행해야 할 경우 MemberServiceImpl의 클래스에서 수정이 이루어 져야 한다. 수정이 이루어 지는 순간 OCP (Open / Close Principle) 원칙을 위반 하게 된다.

그러하면 DIP원칙,OCP원칙을 지키게 하기위해서는 어떻게 코드를 해야하는 것일까?

위 사진에서는 [ 인터페이스 변수명 = new 구현체; ]  이런식이지만 오로지 인터페이스만 의존하도록 코드를 바꾸면

이렇게 코드를 수정을 하게 된다면? 구현체가 아닌 오로지 Only 인터페이스만 의존하게 되는 것이다.

그렇다면 ConfigApp 이라는 클래스를 만들어서 의존관계 주입 개념을 도입을 하게 되면 더욱 DIP,OCP 원칙을 지키면서 개발을 할 수 있게 된다.

 

MemberSericeImpl 클래스에는 MemberRepository 라는 인터페이를 의존하고 있다.

그와동시에 MemberRepository 의 구현체는 생성자를 통해서 받아오고 있다.

ConfigApp 이라는 클래스에서 리턴해주는것이 MemberServiceImpl 과 위 사진에서 생성자로 받을 수 있게 해둔 MemberRepository 구현체를 리턴해주는 것이다.

한마디로 MemberServiceImpl 과 MemoryMemberRepository 를 리턴해주는 것이다.

 

그렇다면 ConfigApp 클래스를 어떻게 사용하여야 하는 것일까?

 

아래 사진은맨 처음 사진과 같은 메인 클래스 이다.

일단 첫번째로 ConfigApp을 인스턴스화를 해야한다.

아래코드를 보면 처음 코드방식과 조금 다를것이다. 처음사진은 바로 new MemberServiceImpl 을 했엇지만

이 사진은 config.MemberService() 를 사용하였다.

config에서는 2가지 역할이 있다.

1번째 MemberService의 구현체인 Impl을 생성한다.

2번째 생성자로 Impl에서 사용하는 인터페이스도 같이  생성을 하게 되면은 

Impl에서 사용하는 인터페이스에서 기능 추가/ 다른 기능 사용 등등 다양한 이유가 있지만 수정이 일어날 경우 Impl을 고칠 필요가 없다. 

오로지 interface에만 의존을 하고 있기 때문이다. 

그렇다면 메인 메소드에서는 오로지 무엇을 사용할지만 관심을 가지면 될 것이다.

 

아주 간단하면서도 복잡한 개념인거 같다.

 

※ 해당 블로그는 공부용/기록용으로 쓰입니다. 간단한 피드백 주시면 감사히 받겠습니다.

설정

트랙백

댓글

Spring Project 생성 방법

Spring & Spring Boot 2020. 12. 13. 15:22

◈ Spring Project 생성 

오늘은 스프링부트 프로젝트를 간단하게 생성하는 방법을 알아보도록 합니다.

프로젝트에 사용할 것은 ☞ Spring boot ☞ Gradle IDE은Eclipse를 사용합니다.

방법으로 프로젝트를 생성해보도록 합니다.

start.spring.io/

해당 페이지에서 Artifact은 사용하실 프로젝트 명을 입력하시면 됩니다.

Maven/Gradle 사용유무에 따라 체크박스를 선택하시면 됩니다.

 

해당 항목을 입력후에 "GENERATE" 를 클릭하시면 study.zip 파일이 다운로드가 되는 것을 확인 할 수있습니다.

사용하실 폴더에 압축을 풀어주시면 해당 프로젝트가 생성된 것을 확인 할 수있습니다.

이제 Eclipse에 생성한 프로젝트를 import 하겠습니다.

import 하는 창에서 Existing Gradle Project를 선택하여 생성한 프로젝트의 경로를 선택합니다.

 

로그가 찍힌걸 보니 정상적으로 실행되는 것을 확인 할 수 있습니다.

 

☞ 해당 블로거는 공부/기록용 으로 사용되오니 잘못된 정보나 부족한 정보는 공유해주시면 감사드립니다. ☜

설정

트랙백

댓글

스프링에서 사용하는 좋은 객체지향 원칙

Spring & Spring Boot 2020. 12. 12. 01:33

◈ 좋은 객체지향 원칙 5가지

지금 소개할 것은 SOLID 라는 객체지향 원칙입니다.

이 원칙은 스프링에서 뿐만 아니라 객체지향 개발을 할때 알아두면은 도움이 될 것입니다.

①. SRP (Single Responsibility principle) 단일 책임 원칙

②. OCP (Open / Closed Principle) 개방-폐쇄 원칙

③. LSP (Liskov Substitution Principle) 리스코프 치환 원칙

④. ISP (Intterface Segregation Principle) 인터페이스 분리 원칙

⑤. DIP (Dependency Inversion Principle) 의존관계 역전 원칙

위 5가지에 원칙에 대해서 알아보도록 합니다.

 

▶ SRP (단일 책임 원칙) 이란? ◀

Single Responsibility Principle 의 약자인 SRP 단일책임 원칙이란 간단하게 말해서 1개의 Class는 하나의 책임만 가지고 있어야 한다.

그럼 여기서 책임이란 무엇을 뜻하는가? 라는것이 생각이 들것이다. 

책임은 그때 상황에 따라 책임이 클수도 있고 작을 수도 유동적일 것이다 그럼 어떠한 기준으로 SRP 원칙 을 잘 지켯다고 말할 수 있을까?

어떠한 작업이 UPDATE가 되엇을 시점에 판단을 할 수가 있다. 예로 들어 A라는 Class 파일을 수정해야 하는 상황이 오면은 그 수정한 A.Class 파일로 인해 다른 Class파일들까지 영향이 미치는 것 이 적으면은 단일 책임 원칙을 잘 수행 한 것이다.

그와 반대로 1개의 Class 파일을 고쳣을뿐인데 여러 파일에서도 문제가 생기면은 단일 책임 원칙을 위반 한것이다.

 

OCP (개방-폐쇄 원칙) 이란? ◀

개방-폐쇄 원칙에는 다형성을 이용하는 것이다. 확장에는 OPEN 되어 있지만 수정에는 CLOSE 되어 있다 라고 생각하면 좋다. 

확장에는 열려있고 그게 아닌 변경되는 시점에는 닫혀있어야 한다? 이게 무슨 어이없는 말인가 예시로 간단하게 이해를 해보자

나(클라이언트) 는 명품브랜드에 옷을 입고 있다고 생각해보자. 여기서 다른 옷을 입고 싶어질때 다해져있는 품질을 옷입으라고 했을때 어느 누가 명품브랜드를 입다가 싸구려 옷을 입는것을 좋아 하겠는가? 이같은 경우에 다른 옷을 입을려고 하는 행위를 확장 이라고 할 수 있다. 그렇다면 확장 하는데에는 매우 문제가 될 것이다.

그와 반대로 

나(클라이언트) 는 추상적인 옷(Interface) 에만 의존하고 있다고 생각해보자.

그렇다면 나(클라이언트)는 명품옷을 입든 싸구려입을 입든 언제든지 다른 옷으로 대체 가능한 상황이 되는 것이다. 

즉 나(클라이언트) 는 옷(Interface) 라는 것에만 바라보고 있고 옷(Interface)은 다른 옷을 입히고 싶은 것(구현된 클래스) 만 만들면 언제든지 유연하게 확장이 가능한 것이다.

 

LSP (리스코프 치환 원칙) 이란? ◀

리스코프 치환 원칙은 간단하게 생각해볼 수 있다.

위의 OCP(개방-폐쇄 원칙) 원칙은 Interface를 바라보고 있고 해당 Interface는 특정 기능을 구현된 Class파일들이 있을 것이다.

여기서 LSP(리스코프 치환 원칙)을 잘 지켯을때와 원칙을 위반 했을때의 차이점을 알아보자.

※ LSP(리스코프 치환 원칙)을 잘 시켯을 경우 

축구선수 라는 인터페이스가 있다고 생각했을때 발로 공을 차다 라는 기능을 선언하고 구현된 기능 Class파일은 축구공을 차는 기능을 만들었을 것이다.

이경우에는 리스코프 치환 원칙을 잘 짙켯다고 할 수 있다.

※ LSP(리스코프 치환 원칙) 위반 

리스코프 치환 원칙을 위반 하는경우는 간단하다. 축구선수 인터페이스에서 발로 축구공을 차는 기능을 선언 후 

구현하는 Class파일에서 축구공을 손으로 던지는 기능을 만들 경우에 리스코프 치환 원칙을 위반 하는 것이다.

해당 목적을대로 기능을 만들어야 한다.

 

ISP (인터페이스 분리 원칙) 이란? ◀

인터페이스를 분리시킨다는 것이 무엇을 말하는건가? 여기서 객체지향이라는 개념도 생각하면 좋다.

인터페이스란 간단히 말해 기능들의 집합소 라고 생각해보자. 지하철이라는 인터페이스안에는

교통카드 라는것이 있을 수 도 있고 지하철운행 이라는 것도 있을 수도 있고 수없이 많을 것이다.

여기서 인터페이스를 분리를 시켜보자. 교통카드라는 인터페이스는 이에 관련된 요금,벌금 등같은것만

관련된 기능들이 있을 것이고,

지하철 운행이라는 인터페이스는 지하철 운전, 기사관리, 급행, 같은 지하철운행에 관한 수많은 기능들이 있을

것이다. 여기서 이러한 모든 기능들을 1개의 인터페이스에서 관리한다고 했을때 무척 골치가 아플 것이다.

이러한 골치아픔을 피하기 위해 각각의 인터페이스를 분리를 시켜놓으면은 어떠한 수정이 일어낫을때 해당 인터페이스만 수정하면 되니깐 관리하기에 아주 편리 해질 것이다.

 

DIP (의존관계 역전 원칙) 이란? ◀

위에서 말한 OCP(개방-폐쇄 원칙)을 다시 생각해보자.

간단하게 설명해자면 클라이언트는 인터페이스의 구현객체를 알면 안된다는 뜻이다.

클라이언트는 오로직 인터페이스에만 의존 하도록 잘 설계하여 만들어야 하는 것이다.

 

☞ 부족한 설명이나 잘못된 부분은 댓글로 언제나 환영입니다. ☜

설정

트랙백

댓글