什么是 etcd 

etcd 是 CoreOS 团队于 2013 年 6 月发起的开源项目,它的目标是构建一个高可用的分布式键值( key-value )数据库,基于 Go 语言实现。

 

 

安装

源码地址

go get github.com/etcd-io/etcd

github.com 域名无法解析~  后来发现虚拟机里的网络没有打开!

 

构建

make build

2018年8月29日, etcd源码路径改了。也就是说 之前的源码可以编译通过,之后的源码得mv下目录。

-	\"github.com/coreos/etcd/version\"
+	\"go.etcd.io/etcd/version\"

把   $GOPATH/github.com/coreos/etcd  目录, mv 到  $GOPATH/go.etcd.io/etcd 

 

构建时,我还遇到个问题,提示如下

etcd on unsupported platform without ETCD_UNSUPPORTED_ARCH=386 set

既然源码在手,就全局搜索下源码。发现了下面这个函数

func checkSupportArch() {
	// TODO qualify arm64
	if runtime.GOARCH == \"amd64\" || runtime.GOARCH == \"ppc64le\" {
		return
	}
	// unsupported arch only configured via environment variable
	// so unset here to not parse through flag
	defer os.Unsetenv(\"ETCD_UNSUPPORTED_ARCH\")
	if env, ok := os.LookupEnv(\"ETCD_UNSUPPORTED_ARCH\"); ok && env == runtime.GOARCH {
		fmt.Printf(\"running etcd on unsupported architecture %q since ETCD_UNSUPPORTED_ARCH is set\\n\", env)
		return
	}

	fmt.Printf(\"etcd on unsupported platform without ETCD_UNSUPPORTED_ARCH=%s set\\n\", runtime.GOARCH)
	os.Exit(1)
}

 

原来我安装 go 的 环境变量 GOARCH 一直写错了,写成了386. 我运行在ubuntu 16.04 64位系统上 应该是 amd64

编辑 /etc/environment  文件 把 386 改成 amd64. 保存 注销系统,再登陆,解决。

 

生成了下面的文件

~/go/gopath/src/github.com/coreos/etcd/bin $ ls
default.etcd  etcd  etcdctl

为了方便在各个目录下都可以运行 etcd 和 etcdctl

把它们文件拷贝到系统可执行目录
sudo cp etcd* /usr/local/bin/

 

制作docker

打开 Makefile 文件,找到了写好的制作docker 命令。 那就拿来用吧

make build-docker-release-master

 

生成后发现 docker 的 image 名字老长老长,手痒改了个短的,重新编译

build-docker-release-master:
	$(info ETCD_VERSION: $(ETCD_VERSION))
	cp ./Dockerfile-release ./bin/Dockerfile-release
	docker build \\
	  --tag etcd:$(ETCD_VERSION) \\
	  --file ./bin/Dockerfile-release \\
	  ./bin
	rm -f ./bin/Dockerfile-release

	docker run \\
	  --rm \\
	  etcd:$(ETCD_VERSION) \\
	  /bin/sh -c \"/usr/local/bin/etcd --version && ETCDCTL_API=3 /usr/local/bin/etcdctl version\"

 

于是生成的image如下:

REPOSITORY             TAG                 IMAGE ID            CREATED             SIZE
etcd                   93be31d             24cb021159ce        23 hours ago        66.1MB

 

简单使用

命令行下直接运行 etcd 即可

etcd

然后 用客户端  etcdctl 试试。    如下,保存了键 wjs, 值为 \"hello world\"。 然后取出来看看,值,果然是 \"hello world\"

~/go/gopath/src/github.com/coreos/etcd $ etcdctl put wjs \"hello world\" 
OK
~/go/gopath/src/github.com/coreos/etcd $ etcdctl get wjs 
wjs
hello world

网上好多文章都用的 etcdctl set wjs \"hello world\"。  set 命令已经没有了,用 put 吧,etcd 变化挺快的啊。

 

利用docker-compose制作集群

我就一台电脑,又想试试集群。那就用docker 吧

version : \"3.6\"

services:

    node1:
        image: etcd:93be31d
        volumes:
            - node1-data:/etcd-data
        expose:
            - 2379
            - 2380
        networks:
            cluster_net:
                ipv4_address: 172.16.238.100
        environment:
            - ETCDCTL_API=3
        command:
            - /usr/local/bin/etcd
            - --data-dir=/etcd-data
            - --name
            - node1
            - --initial-advertise-peer-urls
            - http://172.16.238.100:2380
            - --listen-peer-urls
            - http://0.0.0.0:2380
            - --advertise-client-urls
            - http://172.16.238.100:2379
            - --listen-client-urls
            - http://0.0.0.0:2379
            - --initial-cluster
            - node1=http://172.16.238.100:2380,node2=http://172.16.238.101:2380,node3=http://172.16.238.102:2380
            - --initial-cluster-state
            - new
            - --initial-cluster-token
            - docker-etcd

    node2:
        image: etcd:93be31d
        volumes:
            - node2-data:/etcd-data
        expose:
            - 2379
            - 2380
        networks:
            cluster_net:
                ipv4_address: 172.16.238.101
        environment:
            - ETCDCTL_API=3
        command:
            - /usr/local/bin/etcd
            - --data-dir=/etcd-data
            - --name
            - node2
            - --initial-advertise-peer-urls
            - http://172.16.238.101:2380
            - --listen-peer-urls
            - http://0.0.0.0:2380
            - --advertise-client-urls
            - http://172.16.238.101:2379
            - --listen-client-urls
            - http://0.0.0.0:2379
            - --initial-cluster
            - node1=http://172.16.238.100:2380,node2=http://172.16.238.101:2380,node3=http://172.16.238.102:2380
            - --initial-cluster-state
            - new
            - --initial-cluster-token
            - docker-etcd

    node3:
        image: etcd:93be31d
        volumes:
            - node3-data:/etcd-data
        expose:
            - 2379
            - 2380
        networks:
            cluster_net:
                ipv4_address: 172.16.238.102
        environment:
            - ETCDCTL_API=3
        command:
            - /usr/local/bin/etcd
            - --data-dir=/etcd-data
            - --name
            - node3
            - --initial-advertise-peer-urls
            - http://172.16.238.102:2380
            - --listen-peer-urls
            - http://0.0.0.0:2380
            - --advertise-client-urls
            - http://172.16.238.102:2379
            - --listen-client-urls
            - http://0.0.0.0:2379
            - --initial-cluster
            - node1=http://172.16.238.100:2380,node2=http://172.16.238.101:2380,node3=http://172.16.238.102:2380
            - --initial-cluster-state
            - new
            - --initial-cluster-token
            - docker-etcd

volumes:
    node1-data:
    node2-data:
    node3-data:

networks:
    cluster_net:
        driver: bridge
        ipam:
            driver: default
            config:
            -   
                subnet: 172.16.238.0/24

然后

docker-compose up

运行起来后,看看, 恩集群跑起来了,蛮健康的。

~/go/gopath/src/github.com/coreos/etcd $ etcdctl --endpoints=172.16.238.100:2379,172.16.238.101:2379,172.16.238.102:2379 endpoint status --write-out=table
+---------------------+------------------+-----------+---------+-----------+-----------+------------+--------------------+--------+
|      ENDPOINT       |        ID        |  VERSION  | DB SIZE | IS LEADER | RAFT TERM | RAFT INDEX | RAFT APPLIED INDEX | ERRORS |
+---------------------+------------------+-----------+---------+-----------+-----------+------------+--------------------+--------+
| 172.16.238.100:2379 | 422a74f03b622fef | 3.3.0+git |   20 kB |     false |         2 |         12 |                 12 |        |
| 172.16.238.101:2379 | ed635d2a2dbef43d | 3.3.0+git |   20 kB |      true |         2 |         12 |                 12 |        |
| 172.16.238.102:2379 |  daf3fd52e3583ff | 3.3.0+git |   20 kB |     false |         2 |         12 |                 12 |        |
+---------------------+------------------+-----------+---------+-----------+-----------+------------+--------------------+--------+
~/go/gopath/src/github.com/coreos/etcd $ etcdctl --endpoints=172.16.238.100:2379,172.16.238.101:2379,172.16.238.102:2379 endpoint health --write-out=table
+---------------------+--------+-------------+-------+
|      ENDPOINT       | HEALTH |    TOOK     | ERROR |
+---------------------+--------+-------------+-------+
| 172.16.238.101:2379 |   true |  37.75884ms |       |
| 172.16.238.100:2379 |   true | 39.935792ms |       |
| 172.16.238.102:2379 |   true | 41.891148ms |       |
+---------------------+--------+-------------+-------+

再试试存储值。

我操作 238.100 的etcd,添加了 wjs 值为 “hello world\"。

然后在从100 101 102的 etcd 获取 wjs。 和我预想的一样,都返回了 “hello world”。 集群应该正确的

~/gol/etcd $ etcdctl --endpoints=172.16.238.100:2379 put wjs \"hello world\"
OK
~/gol/etcd $ etcdctl --endpoints=172.16.238.100:2379 get wjs 
wjs
hello world
~/gol/etcd $ etcdctl --endpoints=172.16.238.101:2379 get wjs 
wjs
hello world
~/gol/etcd $ etcdctl --endpoints=172.16.238.102:2379 get wjs 
wjs
hello world

 

收藏 打印