Golang에서 간단한 API 게이트웨이를 구현하는 방법

藏色散人
풀어 주다: 2020-08-31 17:07:02
앞으로
3691명이 탐색했습니다.

다음 칼럼에서는 Golangtutorial 칼럼에서 Golang으로 간단한 API 게이트웨이를 구현하는 방법을 소개하겠습니다. 필요한 친구들에게 도움이 되길 바랍니다!

Golang에서 간단한 API 게이트웨이를 구현하는 방법

최근 프로젝트에서는 백엔드 개발에 마이크로서비스 아키텍처인 go-kit을 사용했습니다. 마이크로서비스 아키텍처 스타일에서는 대규모 애플리케이션이 여러 개의 소규모 서비스 시스템으로 분할됩니다. 이러한 소규모 시스템은 자체 시스템을 구성할 수 있습니다. 이는 이러한 소규모 시스템이 자체 데이터베이스, 프레임워크, 심지어 언어까지 가질 수 있음을 의미합니다. go-kit进行后端的开发。在微服务架构风格中,一个大应用被拆分成为了多个小的服务系统提供出来,这些小的系统他们可以自成体系,也就是说这些小系统可以拥有自己的数据库,框架甚至语言等,因此我们需要设计一个API 网关(API Gataway),其实网上已经有较多现成的实现框架,但是本项目的需求是比较简单的,因此将使用Golang自行实现。

实现

API网关是一个服务器,是系统的唯一入口。从面向对象设计的角度看,它与外观模式类似。API网关封装了系统内部架构,为每个客户端提供一个定制的API。它可能还具有其它职责,如身份验证、监控、负载均衡、缓存、请求分片与管理、静态响应处理。

用于实现API网关的技术有很多,大致分为这么几类:

  • 通用反向代理:NginxHaproxy、……
  • 网络编程框架:NettyServlet、……
  • API网关框架:Spring Cloud GatewayZuulZuul2、……

API网关最基本的功能就是反向代理。其实现方式有很多,本文将基于标准库net/http/httputil包中的ReverseProxy类型来实现实现一个简单的反向代理。反向代理的实现主要涉及到func NewSingleHostReverseProxy(target *url.URL) *ReverseProxytype ReverseProxy

func NewSingleHostReverseProxy(target *url.URL) *ReverseProxy
로그인 후 복사
// NewSingleHostReverseProxy returns a new ReverseProxy that routes// URLs to the scheme, host, and base path provided in target. If the// target's path is "/base" and the incoming request was for "/dir",// the target request will be for /base/dir.// NewSingleHostReverseProxy does not rewrite the Host header.// To rewrite Host headers, use ReverseProxy directly with a custom// Director policy.func NewSingleHostReverseProxy(target *url.URL) *ReverseProxy {
	targetQuery := target.RawQuery
	director := func(req *http.Request) {
		req.URL.Scheme = target.Scheme
		req.URL.Host = target.Host
		req.URL.Path = singleJoiningSlash(target.Path, req.URL.Path)
		if targetQuery == "" || req.URL.RawQuery == "" {
			req.URL.RawQuery = targetQuery + req.URL.RawQuery		} else {
			req.URL.RawQuery = targetQuery + "&" + req.URL.RawQuery		}
		if _, ok := req.Header["User-Agent"]; !ok {
			// explicitly disable User-Agent so it's not set to default value
			req.Header.Set("User-Agent", "")
		}
	}
	return &ReverseProxy{Director: director}}
로그인 후 복사

NewSingleHostReverseProxy返回一个新的ReverseProxy,将URLs请求路由到targe的指定的scheme, host, base path

// ReverseProxy is an HTTP Handler that takes an incoming request and// sends it to another server, proxying the response back to the// client.type ReverseProxy struct {
	// Director must be a function which modifies
	// the request into a new request to be sent
	// using Transport. Its response is then copied
	// back to the original client unmodified.
	// Director must not access the provided Request
	// after returning.
	Director func(*http.Request)

	Transport http.RoundTripper

	FlushInterval time.Duration

	ErrorLog *log.Logger

	BufferPool BufferPool	// ModifyResponse is an optional function that modifies the
	// Response from the backend. It is called if the backend
	// returns a response at all, with any HTTP status code.
	// If the backend is unreachable, the optional ErrorHandler is
	// called without any call to ModifyResponse.
	//
	// If ModifyResponse returns an error, ErrorHandler is called
	// with its error value. If ErrorHandler is nil, its default
	// implementation is used.
	ModifyResponse func(*http.Response) error

	ErrorHandler func(http.ResponseWriter, *http.Request, error)}
로그인 후 복사

ReverseProxy类型有两个重要的属性,分别是DirectorModifyResponse,这两个属性都是函数类型,在接收到客户端请求时,ServeHTTP函数首先调用Director函数对接受到的请求体进行修改,例如修改请求的目标地址、请求头等;然后使用修改后的请求体发起新的请求,接收到响应后,调用ModifyResponse函数对响应进行修改,最后将修改后的响应体拷贝并响应给客户端,这样就实现了反向代理的整个流程。

NewSingleHostReverseProxy中源码已经对传入的URLs进行解析并且完成了Director的修改,我们只需要调用NewSingleHostReverseProxy函数并且传入目标服务器的URL即可,一个简单的反向代理就完成了啦。

代码

实例代码只涉及微服务中 userauthAPI 게이트웨이(API Gataway)

실제로 인터넷에는 기성 구현 프레임워크가 많이 있지만 이 프로젝트의 요구 사항은 비교적 간단하므로 Golang을 사용하여 구현하겠습니다. 우리 스스로.

구현

API 게이트웨이는 서버이자 시스템에 대한 유일한 입구입니다. 객체지향 디자인 관점에서는 파사드 패턴과 유사합니다. API 게이트웨이는 시스템의 내부 아키텍처를 캡슐화하고 각 클라이언트에 대해 맞춤형 API를 제공합니다. 또한 인증, 모니터링, 로드 밸런싱, 캐싱, 요청 샤딩 및 관리, 정적 응답 처리와 같은 다른 책임도 가질 수 있습니다. 🎜🎜🎜API 게이트웨이를 구현하는 데 사용되는 많은 기술이 있으며 대략 다음 범주로 나뉩니다. 🎜
  • 일반 역방향 프록시: Nginx, Haproxy , ...
  • 네트워크 프로그래밍 프레임워크: Netty, Servlet, ...
  • API 게이트웨이 프레임워크: Spring Cloud Gateway , Zuul, Zuul2,...
🎜API 게이트웨이의 가장 기본적인 기능은 역방향 프록시입니다. 이를 구현하는 방법은 다양합니다. 이 기사에서는 표준 라이브러리 net/http/httputil 패키지의 ReverseProxy 유형을 기반으로 간단한 역방향 프록시를 구현합니다. 역방향 프록시 구현에는 주로 func NewSingleHostReverseProxy(target *url.URL) *ReverseProxytype ReverseProxy가 포함됩니다. 🎜
package mainimport (
	"fmt"
	"log"
	"net/http"
	"net/http/httputil"
	"net/url"
	"strings")type handle struct {
	host string
	port string}type Service struct {
	auth *handle
	user *handle}func (this *Service) ServeHTTP(w http.ResponseWriter, r *http.Request) {
	var remote *url.URL	if strings.Contains(r.RequestURI, "api/auth") {
		remote, _ = url.Parse("http://" + this.auth.host + ":" + this.auth.port)
	} else if strings.Contains(r.RequestURI, "api/user") {
		remote, _ = url.Parse("http://" + this.user.host + ":" + this.user.port)
	} else {
		fmt.Fprintf(w, "404 Not Found")
		return
	}
	proxy := httputil.NewSingleHostReverseProxy(remote)
	proxy.ServeHTTP(w, r)}func startServer() {
	// 注册被代理的服务器 (host, port)
	service := &Service{
		auth: &handle{host: "127.0.0.1", port: "8081"},
		user: &handle{host: "127.0.0.1", port: "8082"},
	}
	err := http.ListenAndServe(":8888", service)
	if err != nil {
		log.Fatalln("ListenAndServe: ", err)
	}}func main() {
	startServer()}
로그인 후 복사
rrreee🎜NewSingleHostReverseProxyURL 요청을 지정된 의 <code>target 체계ReverseProxy를 반환합니다. /code>, 호스트, 기본 경로. 🎜rrreee🎜ReverseProxy 유형에는 DirectorModifyResponse라는 두 가지 중요한 속성이 있습니다. 두 속성 모두 클라이언트가 수신할 때 함수 유형입니다. 요청이 있으면 ServeHTTP 함수는 먼저 Director 함수를 호출하여 요청의 대상 주소, 요청 헤더 등을 수정하는 등 수신된 요청 본문을 수정합니다. 수정된 요청을 사용합니다. 본문은 응답을 받은 후 ModifyResponse 함수를 호출하여 응답을 수정합니다. 마지막으로 수정된 응답 본문이 복사되어 클라이언트에 응답됩니다. 전체 역방향 프록시 프로세스. 🎜🎜NewSingleHostReverseProxy에서 소스 코드는 수신 URL을 구문 분석하고 Director 수정을 완료했습니다. NewSingleHostReverseProxy만 호출하면 됩니다. 함수에 대상 서버의 URL을 전달하면 간단한 역방향 프록시가 완성됩니다. 🎜

코드

🎜예제 코드에는 마이크로서비스의 userauth 모듈만 포함됩니다. 실제에 따라 일부를 수정할 수 있습니다. 필요🎜🎜rrreee🎜

위 내용은 Golang에서 간단한 API 게이트웨이를 구현하는 방법의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

관련 라벨:
원천:csdn.net
본 웹사이트의 성명
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.
인기 튜토리얼
더>
최신 다운로드
더>
웹 효과
웹사이트 소스 코드
웹사이트 자료
프론트엔드 템플릿