Go實踐微服務 -- 服務發現

服務的註冊發現對於微服務來講是一個很是重要的環節,在單一架構應用中,service之間的互相調用,經過一個固定的host和port來發起REST或者RPC來調用,可是在微服務架構中,各個服務每每是動態變化的,因此須要一個服務發現機制來發送客戶端的請求到動態的service實例中去。html

在利用go micro來實現服務發現便利不少,micro中默認支持使用 Consul 來作服務發現,固然它使用插件機制(go-plugins)還支持 Etcd, Gossip, NATS等其餘的第三方服務註冊發現工具。在每一個服務啓動的時候,都將本身註冊到registry上,退出時也自動解註冊,具體實現咱們能夠來看一下go-micro/service.go的相關代碼片斷:git

......

func (s *service) run(exit chan bool) {
    if s.opts.RegisterInterval <= time.Duration(0) {
        return
    }

    //定時註冊本身
    t := time.NewTicker(s.opts.RegisterInterval)

    for {
        select {
        case <-t.C:
            err := s.opts.Server.Register()
            if err != nil {
                log.Log("service run Server.Register error: ", err)
            }
        case <-exit:
            t.Stop()
            return
        }
    }
}

......

func (s *service) Start() error {
    for _, fn := range s.opts.BeforeStart {
        if err := fn(); err != nil {
            return err
        }
    }

    if err := s.opts.Server.Start(); err != nil {
        return err
    }
    // Run() 調用中也會結果run來調到這裏來註冊
    if err := s.opts.Server.Register(); err != nil {
        return err
    }

    for _, fn := range s.opts.AfterStart {
        if err := fn(); err != nil {
            return err
        }
    }

    return nil
}

func (s *service) Stop() error {
    var gerr error

    for _, fn := range s.opts.BeforeStop {
        if err := fn(); err != nil {
            gerr = err
        }
    }
   // 退出時自動解除註冊
    if err := s.opts.Server.Deregister(); err != nil {
        return err
    }

    if err := s.opts.Server.Stop(); err != nil {
        return err
    }

    for _, fn := range s.opts.AfterStop {
        if err := fn(); err != nil {
            gerr = err
        }
    }

    return gerr
}
......

關於Consul的相關使用能夠參考 《Consul 簡介和快速入門》,下面主要來利用一個酒店預訂的示例來看下Go Micro如何使用Consul的集羣來作服務發現。github

示例中會使用到一個 Micro API,它是Micro組件中的一個微服務API網關的實現,API網關模式能夠爲服務提供一個入口,該HTTP入口動態路由到合適的後端service,利用它進行服務發現,負載平衡,編碼和基於RPC的通訊。web

api

Micro API提供的HTTP API 以下 :docker

- /[service]/[method]    # HTTP路徑動態映射到services
- /rpc # 經過名稱和方法顯示調用後端service

在示例中使用 Micro API 的 RPC Handler,它是go-micro客戶端將請求主體轉發爲RPC請求的默認處理程序的替代方案,具體Micro API的使用和REST映射規則能夠查看文檔https://micro.mu/docs/api.htmljson

該酒店預約服務利用了官方 micro/examples中的booking示例改寫, 具體代碼 => https://github.com/yuansir/go...bootstrap

.
├── README.md
├── api
│   └── hotel   # booking service
├── data    # data
│   ├── bindata.go
│   ├── customers.json
│   ├── locations.json
│   ├── profiles.json
│   └── rates.json
├── docker-compose.yml # docker compose file
└── srv # services
    ├── auth    # auth token servce
    ├── geo     # geo service
    ├── profile # profile service
    └── rate    # rate service

docker-compose.yml後端

version: '3'

services:
  consul-agent-1: &consul-agent
    image: consul:latest
    networks:
      - consul-cluster
    command: "agent -retry-join consul-server-bootstrap -client 0.0.0.0"

  consul-agent-2:
    <<: *consul-agent

  consul-agent-3:
    <<: *consul-agent

  consul-server-1: &consul-server
    <<: *consul-agent
    command: "agent -server -retry-join consul-server-bootstrap -client 0.0.0.0"

  consul-server-2:
    <<: *consul-server

  consul-server-bootstrap:
    <<: *consul-agent
    ports:
      - "8400:8400"
      - "8500:8500"
      - "8600:8600"
      - "8600:8600/udp"
    command: "agent -server -bootstrap-expect 3 -ui -client 0.0.0.0"

  auth:
    build: ./srv/auth
    networks:
      - consul-cluster
    command: --registry_address=consul-server-bootstrap:8500
    links:
      - consul-server-bootstrap
  geo:
    build: ./srv/geo
    networks:
      - consul-cluster
    command: --registry_address=consul-server-bootstrap:8500
    links:
      - consul-server-bootstrap
  profile:
    build: ./srv/profile
    networks:
      - consul-cluster
    command: --registry_address=consul-server-bootstrap:8500
    links:
      - consul-server-bootstrap
  rate:
    build: ./srv/rate
    networks:
      - consul-cluster
    command: --registry_address=consul-server-bootstrap:8500
    links:
      - consul-server-bootstrap
  api:
    build: ./api/hotel
    networks:
      - consul-cluster
    command: --registry_address=consul-server-bootstrap:8500
    links:
      - consul-server-bootstrap
      - auth
      - geo
      - profile
      - rate
  micro:
    networks:
      - consul-cluster
    command: --registry_address=consul-server-bootstrap:8500  api --handler=rpc
    image: microhq/micro:latest
    links:
      - consul-server-bootstrap
      - api
    ports:
      - "8080:8080"

networks:
  consul-cluster:

consul每一個數據中心至少必須擁有一臺server,建議在一個集羣中有3或者5個server.部署單一的server,在出現失敗時會不可避免的形成數據丟失.-bootstrap-expect 選項提示Consul咱們期待加入的server節點的數量。每個服務的--registry_address就是設置註冊到的服務發現註冊表地址。api

docker-compose up 後能夠經過consul 的web ui來查看Service的狀態。
1531203571067架構

轉載請註明: 轉載自Ryan是菜鳥 | LNMP技術棧筆記

若是以爲本篇文章對您十分有益,何不 打賞一下

謝謝打賞

本文連接地址: Go實踐微服務 -- 服務發現

相關文章
相關標籤/搜索