마이크로서비스 조립성 및 정리

web/마이크로서비스|2018. 10. 23. 11:17

마이크로서비스의 조립성은 서비스 디자인 원칙의 하나이다. 서비스를 어떻게 디자인해서 효율적으로 할 수 있는 원칙을 이야기하며 크게  두 가지 요소로 나뉜다.


1. 오케스트레이션(Orchestration)

- 여러개의 서비스를 모아 하나의 완전한 기능을 만드는 서비스가 마이크로 서비스이다. 그럴 경우 중앙에서 두뇌 역할을 하는 오케이스트레이터가 여러 서비스를 묶어서 조율할 수 있어야 한다. 이 오케스트레이터는 외부에 노출되는 접점이다.

- 예를들어 주문이라는 서비스가 들어오면 고객 서비스, 상품 서비스, 배송 서비스에 역할을 분배하여 요청하는 중재자를 의미한다.


2. 연출 (Choreography)

- 특정한 서비스가 실행되면 메시키큐에 producer가 이벤트를 넣고 그 곳을 바라보면서 대기하던 consumer들이 자신에 맞는 이벤트 동작을 실행하는 것을 말한다. 

- ESB에 메시지가 푸시되면 그 이후에 처리되는 모든 결정은 메시지를 소비하는 서버에 의해 자동으로 결정된다.



마이크로 서비스의 현명한 종단점 개수는 몇 개일까?

- 마이크로 서비스를 만들 때 종단점의 수는 그렇게 중요하지 않다. 필요에 따라 여러개 일수도 있고 하나가 될 수도 있다.

- 하지만 서로 연결돼서 공통의 데이터를 사용하거나 비슷한 업무를 처리하는 부분을 모두 종단점으로 구분하게 된다면 결과적으로 동일한 부분을 잘게 쪼개놓은 꼴이된다. 결국 성능적으로 더 떨어진 시스템이 될 수도 있다.

- 결론적으로 종단점의 개수는 중요한 것이 아니고 마이크로서비스 크기에 적합하게 경계 지어진 컨텍스트를 적절하게 설계하는 것이 중요하다.


가상머신에 여러개의 마이크로서비스 

- 하나의 가성머신에 여러 마이크로서비스를 올려놓을 수 있다. 이는 용량을 포함하는 리소스가 충분하고 별도의 서비스로 동작하고 서비스 요구사항 (OS, JDK 등등)이 서로 충돌하지 않는다면 가능하다.

- 운영하는 서비스의 인프라의 가용성 특징, 배포 등을 잘 따져가며 설계해야한다.


마이크로서비스의 데이터 스토어 공유 

- 마이크로서비스에서 데이터 스토어를 공유하는 것은 처음에는 별로 어려움이 없어보이지만, 서비스가 많아지고 테이블이 많아지고 하다보면 서비스간에 결합이 생기게 된다. 그러면 두 개의 마이크로서비스도 결국 결합이 생기게 된다. 그러면 효율적인 마이크로서비스라고 할 수 없다.

- 데이터베이스 서버를 별도로 두기에 여유가 없다면 데이터베이스 서버의 스키마를 구분해서 사용해도 된다.

- 또 다른 방법으로 하나의 트랜잭션 관리가 필요한 데이터베이스는 별도로 분리해서 마이크로서비스로 관리하는 것이다.


분산 트랜잭션 시나리오

- 마이크로서비스에서 로컬 트랜잭션만을 이용하고 분산 트랜잭션을 피하는 것이 이상적이다.

- 하나의 서비스에서 식사 예약을 한다고 가정해봤을 때 식사 예약을 완료하기전에 픽업 예약 서비스를 해당 마이크로서비스에 요청한다고 했을 때 픽업 예약은 완료되었지만 식사 예약이 실패할 경우 픽업만 예약되는 사태가 발생할ㄹ 수 있다. 이런 문제를 해결하기 위해 픽업 예약을 식사 예약이 성공적으로 끝나고 나면 보내는 방법이 있으나 메시지를 보내고 나서 갑자기 실패하는 경우 등에 대한 문제를 해결하기에는 부족하다.


서비스 종단점 설계 고려사항

- 마이크로서비스에서 서비스 설계는 Contract Design (계약설계), Protocol Selection (프로토콜 선택) 이라는 두 가지 핵심요소로 나뉜다.

1. 계약 설계

- 서비스 설계에서 가장 주요한 원칙은 단순함이다. 서비스는 소비자가 소비할 수 있게 설계되어야한다. 복잡한 서비스 계약은 서비스의 사용성을 떨어트린다.


2. 프로토콜 선택

- 마이크로서비스는 SOA(서비스 지향 아키텍처)와 동일하게 HTTP/SOAP와 메시징 서비스 상호작용을 위한 기본 서비스 프로토콜을 따른다.

- 메시지 방식이나 REST 방식을 사용한다.

- API 문서는 Swagger 등을 사용한다.


공유 라이브러리 처리

- 마이크로서비스의 기본원칙은  자율성과 자기 완비성이다. 그래서 다른 서비스에서 같은 라이브러리가 필요한 경우가 있을 있다.

만약 동일 코드나 라이브러리를 서로 다른 마이크로서비스에서 가지게 된다면 중복 문제가 있지만 그렇지 않으면 한쪽 마이크로서비스에 다른 마이크로서비스가 의존하게 되는 문제가 발생할 있다. 

만약 동일한 코드를 둘다 가지고 있게 된다면 모든 지식은 하나의 시스템 안에서 오직 하나의 모호하지 않은 권위를 가진 표현으로 존재해야 한다는 DRY 원칙을 어긋나게 된다.

하지만 그렇다고 공통 서비스를 또다른 마이크로서비스로써 값을 참조하게 한다면 또다른 복잡도를 가질 있기 때문에 상황에 맞게 선택해서 진행하는것이 좋다.


API 게이트웨이

- 출국관리 애플리케이션에서 체크인, 라운지관리, 탑승수속등의 기능이 필요하다고 가정해보자. 각 서비스들은 별도의 API로 개발되어 있다. 하지만 이는 출국 관리 애플리케이션에서 봤을 때 하나의 웹 애플리케이션에 담아서 관리할 필요성이 있다고 느껴진다. 이럴 경우에 마이크로서비스(API들)를 연결해주는 컨테이너 웹 애플리케이션이나 Placeholder가 필요한데 이 경우 별도의 API 게이트 웨이를 만들어서 사용할 수 있다.

- 요청에 따라 모든 데이터를 한번에 전달하는 API는 쓸데없는 오버헤드를 발생시킬 수 있다. 그래서 필요한 데이터만 필드에 보내줄 수 있다. 하지만 그럴 경우 필요에 따라 전달되는 형식이 바뀌어야한다. 그래서 API 게이트웨이에서 데이터 명세에 따라 필요 데이터만 클라이언트 쪽으로 내보내주도록 만들어서 기존의 API들은 원래 하던대로 동작해도 무관하게 설계할 수 있다.







댓글()

프로그래밍 코드 작성 시 주요원칙

단일 책임 원칙 (Single Responsibility Principle) SRP
-> 객체는 오직 하나의 책임만을 가져야한다.
-> 객체에서 책임이라고 한다면 객체의 역할을 의미한다.

좋은 설계란
=> 기본적으로 시스템에 새로운 요구사항이나 변경이 있을 때 가능한 한 영향 받는 부분을 줄여야 한다.

프로그램의 요구사항은 계속해서 변경되기 마련이다.
이를 위해서 항상 변경이 가능하도록 조치가 되어있어야 하며, 이런 시스템이 변화에 잘 적용되도록 설계되어 있는지 확인 하는 것을 회귀 테스트(regression)라고 한다.

개방폐쇄원칙 (Open-Closed principle) OCP 
- 기존의 코드를 변경하지 않으면서 기능을 추가할 수 있도록 설계가 되어야 한다.


리스코프 치한원칙 
- 자식클래스는 최소한 자신의 부모 클래스에서 가능한 행위는 수행할 수 있어야한다.
- 자식 클래스와 부모클래스 사이의 행위가 일관성이 있어야 한다.
- is a kind of 관계 사이를 유지하라.

의존 역전 원칙 Dependency Inversion Priciple 
- 의존 관계를 맺을 때 변화하기 쉬운 것 또는 자주 변화하는 것보다는 변화하기 어려운 거, 거의 변화가 없는 것에 의존하라.
- 아이가 장난감을 가지고 노는 행위자체는 변화하기 어렵지만, 가지고 노는 장난감은 변화가 쉽다.
- 행위를 적는 인터페이스는 변화가 적고, 실채가 있는 구체 클래스는 변하기 쉽다.

인터페이스 분리 원칙 (Interface Segregation Principle)
- 복합기라는 하나의 커다란 인터페이스를 구현한 팩스 클래스가 갑작스러운 복합기 기능의 변경으로 인해 인터페이스가 변경되면 영향을 받을 수 있다. 그러한 이유로 자신이외에 다른 곳에서 크게 사용하지 않는 특징일 경우 별도의 인터페이스로 관리하는 것이 좋다.
- 진짜 변하지 않는 인터페이스를 상속 받아 재 구현한 인터페이스를 이용하여 클래스를 구현하는 방식을 이용하면 된다.
- SRP (단일 책임 원칙)을 생각하면서 인터페이스도 분리를 해야한다.

결론.
하나의 객체의 하나의 역할을. 관련이 없는 것 끼리는 서로 독립시킬 것.
섣부른 상속은 큰 문제를 야기할 수 있다.



'IT 지식 > 소프트웨어 공학' 카테고리의 다른 글

프로그래밍 코드 작성 시 주요원칙  (0) 2018.05.30
피터 코드의 상속 규칙  (0) 2018.05.30

댓글()

클래스와 인터페이스 - 규칙 17 계승을 위한 설계와 문서를 갖추거나, 그럴 수 없다면 계승을 금지하라.

JAVA/Effective Java|2018. 5. 29. 22:34


16번에서 정의한 것처럼 계승 (이하 상속)을 받을 경우 문제를 야기할 수 있다.

그렇기에 이를 예방하기 위해서 문서를 잘 갖추고 있어야 하는데 
문서를 갖춘다는 것은 어떤 의미일까?

이는 재정의 가능 메서드를 내부적으로 어떻게 사용하는지(self-use)반드시 남기라는 것이다.
-> 어떤 재정의 가능 메서드를 어떤 순서로 호출하는지, 그리고 호출결과가 추후 어떤 영향을 미치는지 문서로 남기라는 의미이다.

여러 문제를 야기할 수 있기에, 계승에 맞도록 설계하고 문서화하지 않은 클래스에 대한 하위 클래스는 만들지 않아야 한다.


출처 : 조슈아 블로크, 『 Effective Java 2/E』, 이병준 옮김, 인사이트(2014.9.1), 규칙17 인용.

댓글()

스트래티지 패턴 (Strategy Pattern)

JAVA/Design Pattern|2018. 5. 28. 22:39

공통적인 특징을 가진 객체를 

만들 경우 우리는 대게 다음과 같이 

추상클래스나 인터페이스를 만들어 놓고, 그 것을 상속받아 객체를 구현한다.

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
// 추상 클래스
package com.wedul.study.strategy;
 
public abstract class Animals {
 
    public Animals() {}
 
    private String name;
    
    public Animals(String name) {
        this.name = name;
    }
 
    public void eat() {
     System.out.println("a gu a gu");
    }
    
    abstract void attck();
}
 
// 고양이
public class Cat extends Animals {
    public Cat() {}
 
    public Cat(String name) {
        super(name);
    }
 
    @Override
    void attck() {
        System.out.println("scretch and bite");
    }
 
}
 
// 강아지
public class Dog extends Animals {
    public Dog() {}    
 
    public Dog(String name) {
        super(name);
    }
 
    @Override
    void attck() {
        System.out.println("bark and bite");
    }
 
}
 
// main
public class Main {
    public static void main(String args[]) {
        Animals dog = new Dog();
        Animals cat = new Cat();
        
        dog.attck();
        cat.attck();
    }
}
 
 
// 결과
bark and bite
scretch and bite
cs



하지만 이런 유형의 경우 

몇가지 문제점이 발생할 수 있다.

문제점
1. 기존 추가된 객체의 동작을 변경하려는 경우.

강아지는 물지 않고, 고양이는 할퀴지 않는경우에 

기존의 코드를 수정을 해주어야 한다.

하지만 그런 경우 새로운 기능을 위해 기존의 속성을 변경해야 하기에 

OCP를 위반하는 행위이다.

2. 새로운 객체가 추가되었을 경우

새로운 rabbit이라는 객체가 추가되었을 때 고양이의 attack 메소드를 동일하게 사용하고 싶은 경우에도

별도로 만들어 주어야 한다.

이는 중복된 코드를 만드는 좋지 않은 코드 습관이 될 수 있다.

또한 attack의 의 성격이 변경될 경우 토끼와 고양이의 메소드를 모두 수정해 주어야 한다.

해결방법

이렇게 자주 변경되는 속성에 관해서는 

그 속성에 대한 인터페이스를 구분하는 것이 좋다.

위의 예제에서 보면 공격이라는 속성이 자주 변경 되는 경우

공격이라는 인터페이스를 만들고 

공격유형에 따른 객체를 인터페이스를 구현하여 만들고 동물에게 해당 속성을 부여해 주는 방식으로 진행해야 한다.


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
// 공격 타입 인터페이스
public interface AttactType {
    void attack();
}
 
// bite 타입
public class BiteAttackType implements AttactType {
 
    @Override
    public void attack() {
        System.out.println("bite you");
    }
 
}
 
// scretch 타입
public class ScretchType implements AttactType {
 
    @Override
    public void attack() {
        System.out.println("scretch use");
    }
 
}
 
// 공격 속성 부여
public abstract class Animals {
    private String name;
    private AttactType attactType;
    
    public Animals() {}
    
    public Animals(String name) {
        this.name = name;
    }
 
    public String getName() {
        return name;
    }
 
    public void setName(String name) {
        this.name = name;
    }
 
    public AttactType getAttactType() {
        return attactType;
    }
 
    public void setAttactType(AttactType attactType) {
        this.attactType = attactType;
    }
    
}
 
// main (동적으로 속성 부여)
public class Main {
    public static void main(String args[]) {
        Animals dog = new Dog();
        Animals cat = new Cat();
 
        // 속성 부여
        dog.setAttactType(new BiteAttackType());
        cat.setAttactType(new ScretchType());
        
        dog.getAttactType().attack();
        cat.getAttactType().attack();
    }
}
cs




위와 같이 스트래티지 패턴은 전략을 쉽게 바꿀 수 있도록 해주는 디자인 패턴이다.

스트래트지 패턴은 

역할에 따라 3가지 요소로 구분된다.

1) Strategy 
- 인터페이스나 추상화로 외부에서 동일한 방식으로 알고리즘을 호출하는 방법을 명시 ( 위의 예에서 Attack Type 인터페이스)
2) ConcreteStrategy
- 인터페이스를 구현한 실제 전략 객체들 (위의 예에서 bite Attack Type, Scretech Attack Type)
3) Context 
- 스트래티지 패턴을 이용하는 역할을 수행한다.  (위의 예에서 Animals)
- 위에서 생성된 전략을 setter을 통해서 매핑한다.



정리하면 

어떤 주체의 행위는 동일하나,
그 도구가 계속 변경된다면 그 도구를 인터페이스로 정의하고
인터페이스 메서드로 그 행위를 기재 한후.

주체에게 그 도구를 주입해서 동적으로 사용하는 방식을 고려하라.

댓글()

엔티티 관계와 속성 추출 방법

새로운 속성으로 주 식별자 선정의 장 단점

대출일, 회원번호, 도서관리번호를 주식별자로 가져야 하는 경우, 너무 많은 속성이 주 식별자가 되어 구별하기 어려울 때, 대출 번호라는 새로운 주 식별자를 도입할 수 있다.

-> 하지만 새로운 주 식별자를 도입한경우, 다음과 같은 문제가 발생할 수 있다.

-> 대출번호가 키가 되는경우 대출일, 회원번호, 도서관리번호가 중복된 데이터가 있을 수 있다.

-> 새로운 개념의 속성을 만들어 주식별자로 지정할 경우 단점과 장점이 있으니 잘 사용해야 한다.



필요없는 속성을 주 식별자로 지정하는 경우.

필요없는 속성이 주 식별자가 되는 경우, 문제가 발생할 수 있다.

제품번호와 제품가격이 주 식별자가 되었을 때, 제품번호별로 제품가격은 하나여야 하는데 서로 다른 데이터가 존재할 수 있는 의미적 중복문제를 발생시킬 수 있다.

제품번호 가격

1111111 11

1111111 22


 

관계의 정의 방법

엔티티는 명사를 도출 하였다면 관계정의는 요청서에서 동사를 보고 판단하라.

부모 관계를 확인하라.

=> A 엔티티가 만들어지기 위해서 B엔티티가 필요하다면, B엔티티는 A엔티티의 부모의

관계를 가지고 있다.

=> 두 엔티티 중 정보를 먼저 생성하여 가지고 있는 쪽이 부모이고, 가져다 쓰는 쪽이

자식이다.



외래식별자 정의

=> 부모 엔티티의 속성이 자식 엔티티에도 공통적으로 존재한다면 자식 엔티티에 있는 공통

속성이 외래 식별자가 된다.


관계/외래식별자에 대한 규칙

=> 두 엔티티가 관련이 있다는 의미는 두 엔티티가 공유하는 속성이 있다는

의미.

=> 공통 속성의 값이 먼저 생성되는 쪽이 부모 엔티티고 , 가져다 쓰는 쪽이

자식 엔티티

=> 부모엔티티에 있는 공통 속성은 주 식별자가 되고, 자식 엔티티의 공통

속성은 외래 식별자가 된다.

=> 부모 엔티티와 자식 엔티티의 카디낼러티는 1:N

댓글()

정규화를 고려한 모델링

정규화

정규화는 ERD 내에서 중복을 찾아 제거해 나가는 과정을 말한다.

관계형 데이터베이스 모델의 기본은 동일한 정보는 한곳에서만 관리하는 것이다.


제 1정규화

엔티티에서 하나의 속성이 복수의 값을 갖도록 설계 되었을 때 이를 단일 값을 갖도록 하는 것이다.


 

정규화 전.

사원번호 취미

1001 등산, 낚시

1002 테니스, 등산


 

정규화 후

사원번호 취미

1001 등산

1001 낚시

1002 테니스

1002 등산


다음과 같은 사유도 동일하게 제 1정규화 대상이 된다.

사원번호 취미1 취미2 취미3

1001 등산 낚시

1002 테니스

1003 테니스 운동 독서


해당 테이블 구조는 단일 값을 가지고 있기 때문에 아무 문제가 없어보이지만, 동일한 성격을 가지는 데이터를 다른 속성에 저장하는 것도 문제가 된다.


제 2정규화

제 2정규화는 주 식별자가 아닌 속성 중에서 주 식별자가 전체가 아닌 일부 속성에 종속된 속성을 찾아 제거하는 과정이다.

여기서 말하는 제거는 다른 엔티티를 만들어 속성을 옮기는 것을 말한다.


정규화 전

판매 엔티티

#판매일자

#판매부서

#판매번호

부서명

판매사원번호

사원명

고객번호

고객명

고객주소


판매 엔티티안에 부서번호를 가지고 있을 필요가 없다. 분리를 해야한다.


정규화 후

판매 엔티티

#판매일자

#판매부서

#판매번호

판매사원번호

사원명

고객번호

고객명

고객주소


부서

#부서번호

부서명




제 3정규화

제 3정규화는 주 식별자가 아닌 속성들 중에서 종속 관계에 있는 속성을 찾아 제거하는 단계이다.


정규화 전

판매 엔티티

#판매일자

#판매부서

#판매번호

판매사원번호

사원명

고객번호

고객명

고객주소


위의 엔티티는 사원과 고객 엔티티 속성들이 종속관계를 보인다.

이들을 별도의 엔티티로 구분하여 지정할 수 있다.


정규화 후

판매 엔티티

#판매일자

#판매부서

#판매번호

판매사원번호(FK)

고객번호(FK)


사원

사원번호(PK)

사원명


고객명

고객번호(PK)

고객명

고객주소






정규화를 고려하여 데이터 설계시 주의사항


제 1정규화

제 1정규화 작업을 거치지 않게 설계를 하기 위해서는 반복 속성이 존재하지 않도록 모델링 해야한다.


이를 위해서는 설계를 해야하는 데이터에서 정보를 포함하는 머리부분과 속성을 나타내는 서술 부분을 나눠서 생각해야 한다.


머리부분이 서술부분의 부모 엔티티가 된다.(1:N 관계)


제 2, 3정규화

제 2, 3정규화의 공통점은 종속관계에 있는 속성들을 제거하는 과정이다.

코드-코드값의 관계에 있는 속성들은 별도의 엔티티로 구성한다.

-> 종속관계에 있는 데이터들을 하나의 엔티티에 모두 그리지 않도록 주의한다.

댓글()

설계시 도메인 고려 방법 및 완성된 ERD 검토

도메인

도메인은 엔티티의 속성들이 가질 수 있는 값들의 집합.

DBMS에서 도메인이란 엔티티와 속성에 대응하는 테이블의 컬럼에 대한 데이터 타입과 길이를 의미



도메인 추출 및 데이터 타입 추출방법

1. 테이블에 구성될 컬럼들을 나열한 후 테이블의 도메인을 먼저 지정한다.

대출일 - 날짜

우수회원여부 - 예아니오

회원이름 - 회원이름



2. 도메인에 맞는 데이터 타입을 지정한다.

대출일 - date

우수회원여부 - char(1)

회원이름 - varchar(20)


 



ERD 검토


1. 엔티티 검토


 1) 엔티티가 적절히 구성되었는지의 여부

2) 엔티티의 주 식별자가 적절히 선정되었는지 여부

-> 주식별자에 불필요한 요소가 없는지

-> 인스턴스의 유일성을 보장해 주는지

3) 유사한 내용을 관리하는 엔티티가 없는지

-> 분리, 통합이 필요 없는지.


2. 속성 검토

1) 필요한 정보를 담기위해 속성이 잘 구성되어 있는지.

2) 여러 엔티티 사이에 중복된 속성이 없는지

-> 사원정보에도 이름이 있고, 제품정보에도 이름이 있을 경우 사원정보에는 사원명, 제품정보에는 제품명으로 지정해 준다.

3) 날짜를 저장하는 속성이 올바르게 구성되었는지

-> 연도, 월,일이 서로 나누어져 컬럼으로 되어있다면, 합쳐서 일자로 지정


3. 관계의 검토

1) 카디낼러티와 참여도가 올바른지 검토

2) 카디낼러티가 M:N 관계가 있는 것이 없는지 (조정이 가능한지)

3) 홀로 떨어져 있는(관계가 없는) 엔티티가 있는지 확인.

-> 홀로 떨어져 있는경우, 존재할 이유가 없거나 적절한 관계가 맺어지지 않은상태.

4) 관계가 너무 복잡하지 않은지.


※ M:N 관계 해소


제품 엔티티

제품명(pk), 제품분류, 판매코너


제조업체

업체명(pk), 공장위치


두개의 관계가 M:N 일때 두 개의 엔티티의 주 식별자를 포함한 하나의 연결 엔티티를 이용하여 M:N 관계를 해소

해 줄 수 있다.


업체별 제품 (연결 엔티티)

제품명(PK), 업체명(PK)

댓글()

REST API 효율적인 설계 방법

web/Web|2018. 5. 27. 10:43

REST 구성

구성 요소
표현방법
내용
Resource
HTTP URI
자원을 정의
Verb
HTTP Method
자원에 대한 행위를 정의
Representations
HTTP Message Pay Load
자원에 대한 행위의 내용을 정의

ex)
Resource : /wedul/member
Verb : HTTP POST
Representations : 
{
   "id" : "wedul"
}

REST 특성

1. 유니폼 인터페이스
-> HTTP 표준만 따르면 어떠한 기술이든 사용가능 (HTTP/JSON, HTTP XML)

2. 무상태성 (STATELESS)

3. 캐시 가능
-> 웹 캐시, CD을 이용한 캐싱 가능

4. 자체 표현 구조 (SELF-DESCRIPTIVENESS)
-> API 내용만 보고도 별도의 문서 없이도 쉽게 이해가 가능하다.


REST 설계 패턴

- API URL만 보고도 무슨 API인지 쉽게 직간적으로
- URL을 길게 만들지 말고 2 depth 수준 까지만 
  > /dogs/
  > /dogs/uki
- 대상은 명사가 되야한다.
ex) getDogs (X), /dogs/ (O)
- 단수보다는 복수형을 사용
/dog (X), /dogs (O)

HTTP Response code
- 총 70개있는 것 중에 권장하는 Response code 사용
> 200 : 성공
> 400 : Bad Request - Field validation 실패
> 401 : 인증, 인가 실패
> 404 : 해당 리소스 찾을 수 없음
> 500 : Internal Error - 서버에러

에러처리
-> 상세 내용은 HTTP body에 표현해 주어야 한다.
-> Error Stack이 노출되지 않도록 조심해야한다.
{
  "error" : 200,
  "message" : "massage sending failed",
  "detail" : "Id Logouted"
}



API 인증방식
1. API 키 방식
-> API 호출할때, API KEY를 보내는 방식 
-> 키가 한번 뚫리면 문제가 발생

2. API 토큰 방식
-> ID, PASSWORD를 사용하여 일정 기간 유효한 API 토큰을 리턴하고, 매 호출마다 토큰 사용
2.1) HTTP BASIC AUTH
  => ID, PASSWORD를 직접 보낸다.
 2.2) DIGEST ACCESS AUTHENTICATION
  => 패스워드를 네트워크를 통해서 보내지 않고, 클라이언트와 서버에서 공통적인 키를 이용해서 패스
  워드에 대한 해쉬를 생성하고 이를 비교하는 방식 (프로젝트에서 경험해 봄)

3. 사용자 인증 방식
 1.1) 3자 인증 방식
  => 계정 정보를 다른 서비스가 가지고 진행
 1.2) 클라이언트 인증
  => 서비스가 여러 클라이언트에 의해 사용될때, 클라이언트별 접근 토큰을 발급하여 인증을 강화



댓글()