1. 외부설정이란

    1. 애플리케이션이 작동하기 위해 참조하는 변수
    2. 예시로 개발, 운영 환경에서 DB URL을 다르게 가져가는 경우 참조하는 파일을 외부설정파일이라고 칭함
  2. 이전의 외부설정 방식

    Untitled

    1. 위 예제는 외부설정을 다르게 가져가야 하는 경우, 내부 코드를 수정하고 빌드를 수행하는 방식
    2. 위 예제에서는 개발용 DB URL은 dev.db.com, **운영용 DB URL은 prod.db.com**으로 관리하는 경우임
    3. 하지만 위 예제는 좋은 방식이 아님
  3. 개선된 외부설정 방식

    Untitled

    1. 이전 외부설정 방식의 단점
      1. 이전의 외부설정 방식은 환경에 따라 빌드를 다르게 하기 때문에 각각 운영에 대해 보장 불가능
      2. 특정 용도로 빌드된 파일은 해당 환경에서만 사용가능하므로 유연성이 떨어짐
    2. 위와 같은 이유로 이미지처럼 빌드는 같은 설정을 하지않은 코드에 대해 실행하고 참조할 수 있는 외부설정 파일을 각각 용도에 맞게 작성하는 방식으로 사용
  4. 외부설정의 일반적인 방법

    1. OS 환경 변수
      1. OS에서 지원하는 외부 설정
      2. 해당 OS를 사용하는 모든 프로세스에서 사용
      3. 예시로 JAVA_HOME 등의 변수
    2. 자바 시스템 속성
      1. 자바에서 지원하는 외부 설정
      2. 해당 JVM에서 참조 가능(다른 애플리케이션이라도 같은 JVM에서 사용하면 참조가 가능함)
      3. 예시로 인텔리제이에서 VM옵션에서 입력 가능
      4. -Dusername=chobolevel
    3. 자바 커맨드 라인 인수
      1. 커맨드 라인에서 전달하는 외부 설정
      2. 애플리케이션 실행시 main() 메서드의 args 파라미터를 통해 받을 수 있음
      3. 인텔리제에서는 프로그램 인수를 통해 입력 가능
      4. --username=chobolevel
    4. 외부 파일(설정 데이터)
      1. 애플리케이션에서 외부 파일을 직접 읽어서 사용(application.properties, application.yml 등)
      2. 애플리케이션에서 특정 위치의 파일을 읽도록 설정(예: data/hello.txt)
      3. 그리고 각 서버마다 해당 파일안에 다른 설정 정보를 남겨둠
        1. 개발 서버 hello.txt: url=dev.db.com
        2. 운영 서버 hello.txt: url=prod.db.com
  5. OS 환경 변수

    1. 모든 애플리케이션에서 조회 가능한 변수

    2. 다른 외부설정에 비해 사용 범위가 가장 넓음

    3. 윈도우에서는 set 명령어로 조회 가능(cmd) → 예) set JAVA_HOME

    4. 자바 애플리케이션에서의 조회

      Untitled

      1. System.getenv() 통해 Map형식으로 조회가 가능함
      2. System.getenv() 메서드에 String 형식으로 특정 key값을 넘겨주면 특정 환경변수 조회 가능
  6. 자바 시스템 속성

    1. 실행된 JVM에서 접근 가능한 외부 설정

    2. 추가적으로 자바가 미리 설정해두고 사용하는 변수도 존재함

    3. 자바 시스템 속성 지정 방법

      1. java -Durl=dev -jar app.jar
      2. -D 옵션을 통해서 key=value 형식으로 사용, 예제는 url=dev를 지정
      3. 위 예제처럼 -jar 보다 앞에서 명령어를 입력해야함
      4. 인텔리제이에서는 VM옵션으로 지정 가능
    4. 자바 애플리케이션에서의 조회

      Untitled

      1. **System.getProperties()**를 통해 Map 형식으로 조회
      2. key는 Object형식으로 조회가 이루어짐
      3. **getProperty()**메서드에 String 형태로 key값을 넘겨주면 조회 가능
  7. 커맨드 라인 인수

    1. 애플리케이션 실행 시점에 외부 설정값을 **main()**메서드의 args 파라미터로 전달하는 방식

    2. 커맨드 라인 인수 지정 방법

      1. java -jar app.jar dataA dataB
      2. 필요한 데이터를 마지막 위치에 공백으로 구분해서 전달
      3. 앞선 자바 시스템 속성과 달리 가장 뒤에 넘겨주는 것이 중요하며 key=value 형식으로는 전달되지 않음
      4. 인텔리제이에서는 프로그램 인수를 통해 전달 가능
      5. 띄어쓰기를 사용해야 하는 변수는 “”를 통해 묶어서 전달
    3. 자바 애플리케이션에서의 조회

      String 배열의 args 파라미터를 조회 가능

      String 배열의 args 파라미터를 조회 가능

  8. 커맨드 라인 옵션 인수

    1. 앞선 커맨드 라인 인수가 key=value형식으로 조회/등록 되지 않는 단점을 극복한 외부설정 방식

    2. 커맨드 라인 옵션 인수 지정 방법

      1. -(dash)를 2개 연결하고 key=value형식으로 전달
      2. 같은 key에 여러개 전달 가능
      3. java -jar app.jar --username=chobolevel --username=chobo
    3. 자바 애플리케이션에서의 조회

      Untitled

      1. 자바에서 제공하는 ApplicationArguments 인터페이스를 구현한 DefaultApplicationArguments를 통해 조회 가능
      2. 해당 객체는 빈으로 등록되어 있기 때문에 ApplicationArguments타입으로 빈을 주입받아 사용 가능
      3. **getOptionNames()**를 통해 외부설정 key값을 set형태로 조회
      4. **getOptionValues()**를 톻해 String 타입 key를 전달하면 List형태로 조회
      5. List형식으로 조회되는 이유는 같은 key에 여러값 지정 가능
  9. 외부 설정 통합

    Untitled

    1. 스프링에서는 앞선 다양한 외부 설정을 지원하지만 각각 다른 방식으로 조회하는 불편함이 존재

    2. 스프링에서는 이를 위해 PropertySource라는 추상 클래스를 제공하고 각 외부설정에 따라 xxxPropertySource 구현체를 만들어둠

    3. 이러한 구현체를 Environment에서 사용할 수 있게 연결해둠

    4. Environment

      Untitled

      1. 외부 설정에 따라 조회방식을 다르게 하지 않고 key=value 형식으로 조회 가능함
      2. **getProperty(key)**를 통해 조회 가능
      3. 내부적으로는 여러 과정을 거쳐 xxxPropertySource 들에 접근
      4. 우리가 잘 아는 application.properties, yml 등도 접근 가능
  10. 외부 설정 파일

  11. 내부 설정 파일

  12. 프로필

  13. 내부 설정 파일 병합

  14. 전체 설정 파일의 우선순위