IT story

REST URI 버전을 지정하는 방법

hot-time 2020. 8. 9. 09:43
반응형

REST URI 버전을 지정하는 방법


REST URI를 버전 화하는 가장 좋은 방법은 무엇입니까? 현재 URI 자체에 버전 #이 있습니다.

http://example.com/users/v4/1234/

이 표현의 버전 4를 위해.

버전이 queryString에 속합니까? 즉.

http://example.com/users/1234?version=4

아니면 버전 관리가 다른 방법으로 가장 잘 수행됩니까?


v4가 v3과 다른 리소스를 식별하기 때문에 URI 자체 (옵션 1)의 일부로 만드는 것이 가장 좋습니다. 두 번째 옵션과 같은 쿼리 매개 변수 리소스가 아닌 요청 과 관련된 추가 (쿼리) 정보를 전달하는 데 가장 잘 사용할 수 있습니다 .


URL을 버전 화하지 마십시오.

  • 당신은 영구 링크를 끊습니다
  • URL 변경은 인터페이스를 통해 질병처럼 퍼질 것입니다. 변경되지 않았지만 변경된 표현을 가리키는 표현으로 무엇을합니까? URL을 변경하면 이전 클라이언트가 손상됩니다. URL을 떠나면 새 클라이언트가 작동하지 않을 수 있습니다.
  • 미디어 유형 버전 관리는 훨씬 더 유연한 솔루션입니다.

리소스가 application / vnd.yourcompany.user + xml의 일부 변형을 반환한다고 가정하면 새 application / vnd.yourcompany.userV2 + xml 미디어 유형에 대한 지원을 만들고 v1과 콘텐츠 협상의 마법을 통해 v2 클라이언트는 평화롭게 공존 할 수 있습니다.

RESTful 인터페이스에서 계약에 가장 가까운 것은 클라이언트와 서버간에 교환되는 미디어 유형의 정의입니다.

클라이언트가 서버와 상호 작용하는 데 사용하는 URL은 이전에 검색된 표현에 임베드 된 서버에서 제공해야합니다. 클라이언트가 알아야하는 유일한 URL은 인터페이스의 루트 URL입니다. URL에 버전 번호를 추가하는 것은 클라이언트에서 URL을 구성하는 경우에만 가치가 있으며 RESTful 인터페이스로 수행 할 수는 없습니다.

기존 클라이언트를 손상시킬 미디어 유형을 변경해야하는 경우 새 클라이언트를 만들고 URL은 그대로 두십시오!

그리고 현재 내가 application / xml 및 application / json을 미디어 유형으로 사용하는 경우 이것이 의미가 없다고 말하는 독자들에게. 그것들을 어떻게 버전 화해야합니까? 넌 아니야. 이러한 미디어 유형은 버전 관리가 논쟁 점이되는 코드 다운로드를 사용하여 구문 분석하지 않는 한 RESTful 인터페이스에 거의 쓸모가 없습니다.


아, 다시 낡은 심술 모자를 쓰고 있어요.

ReST 관점에서는 전혀 문제가되지 않습니다. 소시지가 아닙니다.

클라이언트는 따르려는 URI를 수신하고이를 불투명 한 문자열로 취급합니다. 원하는 것을 넣으면 클라이언트는 버전 식별자와 같은 것을 알지 못합니다 .

클라이언트가 알고있는 것은 미디어 유형을 처리 할 수 ​​있다는 것입니다. Darrel의 조언을 따르는 것이 좋습니다. 또한 저는 개인적으로 편안한 아키텍처에서 사용되는 형식을 4 번 변경해야 심각한 문제를 일으킨다는 거대한 경고 신호를 가져오고 변경 복원력을 위해 미디어 유형을 디자인 할 필요성을 완전히 우회해야한다고 생각합니다.

그러나 어느 쪽이든 클라이언트는 이해할 수있는 형식의 문서 만 처리하고 그 안의 링크를 따라갈 수 있습니다. 링크 관계 (전환)에 대해 알아야합니다. 따라서 URI에있는 것은 완전히 관련이 없습니다.

개인적으로 http : // localhost / 3f3405d5-5984-4683-bf26-aca186d21c04에 투표합니다.

더 이상 클라이언트 개발자 또는 시스템을 만지는 사람이 URI의 시작 부분이나 끝에 v4를 넣어야하는지 질문하는 것을 방지하는 완벽하게 유효한 식별자 (서버 관점에서 4 개가 없어야한다고 제안합니다. 버전, 4 가지 미디어 유형).


URL에 버전을 넣지 말고 요청의 Accept Header에 버전을 넣어야합니다.이 스레드에 대한 내 게시물을 참조하십시오.

API 버전 관리에 대한 모범 사례?

URL에 버전을 고정하기 시작하면 http://company.com/api/v3.0/customer/123/v2.0/orders/4321/ 과 같은 어리석은 URL로 끝납니다 .

그리고 다른 문제도 많이 발생합니다. 내 블로그를 참조하세요. http://thereisnorightway.blogspot.com/2011/02/versioning-and-types-in-resthttp-api.html


REST API 버전 관리에 대한 다음 (덜 구체적인) SO 질문이 도움이 될 수 있습니다.


REST 서비스를 사용하기 전에 인증이 필요한 경우 API 키 / 토큰을 API 버전과 쉽게 연결하고 내부적으로 라우팅을 수행 할 수 있습니다. 새 버전의 API를 사용하려면 해당 버전에 연결된 새 API 키가 필요할 수 있습니다.

불행히도이 솔루션은 인증 기반 API에서만 작동합니다. 그러나 URI에서 버전을 유지합니다.


버전 화 된 API를 만들고 싶었고이 기사가 매우 유용하다는 것을 알았습니다.

http://blog.steveklabnik.com/posts/2011-07-03-nobody-understands-rest-or-http

"내 API의 버전을 지정하고 싶습니다"에 대한 작은 섹션이 있습니다. 간단하고 이해하기 쉬웠습니다. 핵심은 헤더의 Accept 필드를 사용하여 버전 정보를 전달하는 것입니다.


API 버전 관리에는 4 가지 접근 방식이 있습니다.

  • URI 경로에 버전 추가 :

    http://example.com/api/v1/foo
    
    http://example.com/api/v2/foo
    

    주요 변경 사항이있는 경우 v1, v2, v3 ...과 같은 버전을 늘려야합니다.

    다음과 같이 코드에서 컨트롤러를 구현할 수 있습니다.

    @RestController
    public class FooVersioningController {
    
    @GetMapping("v1/foo")
    public FooV1 fooV1() {
        return new FooV1("firstname lastname");
    }
    
    @GetMapping("v2/foo")
    public FooV2 fooV2() {
        return new FooV2(new Name("firstname", "lastname"));
    }
    
  • 매개 변수 버전 관리 요청 :

    http://example.com/api/v2/foo/param?version=1
    http://example.com/api/v2/foo/param?version=2
    

    버전 매개 변수는 API 사용 방법에 따라 선택 사항이거나 필수 일 수 있습니다.

    구현은 다음과 유사 할 수 있습니다.

    @GetMapping(value = "/foo/param", params = "version=1")
    public FooV1 paramV1() {
        return new FooV1("firstname lastname");
    }
    
    @GetMapping(value = "/foo/param", params = "version=2")
    public FooV2 paramV2() {
        return new FooV2(new Name("firstname", "lastname"));
    }
    
  • 사용자 정의 헤더 전달 :

    http://localhost:8080/foo/produces
    

    헤더 포함 :

    headers[Accept=application/vnd.company.app-v1+json]
    

    또는:

    headers[Accept=application/vnd.company.app-v2+json]
    

    Largest advantage of this scheme is mostly semantics: You aren’t cluttering the URI with anything to do with the versioning.

    Possible implementation:

    @GetMapping(value = "/foo/produces", produces = "application/vnd.company.app-v1+json")
    public FooV1 producesV1() {
        return new FooV1("firstname lastname");
    }
    
    @GetMapping(value = "/foo/produces", produces = "application/vnd.company.app-v2+json")
    public FooV2 producesV2() {
        return new FooV2(new Name("firstname", "lastname"));
    }
    
  • Changing Hostnames or using API Gateways:

    Essentially, you’re moving the API from one hostname to another. You might even just call this building a new API to the same resources.

    Also,you can do this using API Gateways.


I'd include the version as an optional value at the end of the URI. This could be a suffix like /V4 or a query parameter like you've described. You might even redirect the /V4 to the query parameter so you support both variations.


If you use URIs for versioning, then the version number should be in the URI of the API root, so every resource identifier can include it.

Technically a REST API does not break by URL changes (the result of the uniform interface constraint). It breaks only when the related semantics (for example an API specific RDF vocab) changes in a non backward compatible way (rare). Currently a lot of ppl do not use links for navigation (HATEOAS constraint) and vocabs to annotate their REST responses (self-descriptive message constraint) that's why their clients break.

Custom MIME types and MIME type versioning does not help, because putting the related metadata and the structure of the representation into a short string does not work. Ofc. the metadata and the structure will frequently change, and so the version number too...

So to answer your question the best way to annotate your requests and responses with vocabs (Hydra, linked data) and forget versioning or use it only by non backward compatible vocab changes (for example if you want to replace a vocab with another one).


I vote up for doing this in mime type but not in URL. But the reason is not the same as other guys.

I think the URL should be unique (excepting those redirects) for locating the unique resource. So, if you accept /v2.0 in URLs, why it is not /ver2.0 or /v2/ or /v2.0.0? Or even -alpha and -beta? (then it totally becomes the concept of semver)

So, the version in mime type is more acceptable than the URL.

참고URL : https://stackoverflow.com/questions/972226/how-to-version-rest-uris

반응형