使用 Docker 安裝 Elasticsearch
Docker 搭建 Elasticsearch + Kibana 環境,并在過程中標注常見問題和解決方案。
1. 準備工作
在開始之前,請確認你本地已經安裝了:
工具 | 版本建議 | 檢查方式 |
---|---|---|
Docker | ≥ 20.x | docker -v |
Docker Compose | ≥ 2.x | docker compose version |
常見問題:
- 版本過低:老版本 Docker 對內存管理、網絡有兼容性問題,建議升級到最新。
- Windows 用戶:建議使用 WSL2 + Docker Desktop,不要用 Hyper-V。
2. 選擇 Elasticsearch 版本
建議選擇 8.x 穩定版本(例如 8.15.0),因為:
- 7.x 之后安全功能(TLS、認證)逐漸成為默認配置
- 新手學習時如果用最新版本,文檔和功能對齊度更高
建議鏡像:
docker.elastic.co/elasticsearch/elasticsearch:8.15.0
官方鏡像在 Elastic 倉庫,不在 DockerHub。
3. 創建 Docker Compose 配置
新建一個目錄,例如 es-docker
,然后創建 docker-compose.yml
:
version: "3.8"
services:elasticsearch:image: docker.elastic.co/elasticsearch/elasticsearch:8.15.0container_name: es01environment:- node.name=es01- cluster.name=es-docker-cluster- discovery.type=single-node- bootstrap.memory_lock=true- ES_JAVA_OPTS=-Xms1g -Xmx1g- xpack.security.enabled=false # 學習環境可以先關閉安全認證ulimits:memlock:soft: -1hard: -1volumes:- es_data:/usr/share/elasticsearch/data# 將容器內分詞器配置同步到宿主機,方便修改保存- ./ik-config:/usr/share/elasticsearch/config/analysis-ikports:- 9200:9200- 9300:9300kibana:image: docker.elastic.co/kibana/kibana:8.15.0container_name: kib01environment:- ELASTICSEARCH_HOSTS=http://es01:9200ports:- 5601:5601depends_on:- elasticsearchvolumes:es_data:driver: local
4. 配置詳解
配置項 | 作用 | 注意事項 |
---|---|---|
discovery.type=single-node | 單節點模式 | 必須加,否則容器會一直等待集群發現 |
bootstrap.memory_lock=true | 鎖定內存 | 避免 swap 導致性能下降 |
ES_JAVA_OPTS=-Xms1g -Xmx1g | JVM 內存 | 初學者建議 1g ,不要設置超過 Docker 可用內存 |
xpack.security.enabled=false | 關閉安全認證 | 學習時可關掉,否則要處理證書和密碼 |
常見問題:
內存不足容器無法啟動
- 解決:在 Docker Desktop 設置里調大內存(至少 2GB 給 ES)
安全認證卡住(出現
bootstrap check failure
)
- 解決:確認已加
xpack.security.enabled=false
Kibana 無法連上 ES
- 解決:確認
ELASTICSEARCH_HOSTS=http://es01:9200
配置正確
5. 啟動服務
在 es-docker
目錄執行:
docker compose up -d
檢查容器狀態:
docker ps
看到類似輸出說明啟動成功:
CONTAINER ID IMAGE COMMAND STATUS PORTS
abc123 docker.elastic.co/elasticsearch/elasticsearch:8.15.0 "/bin/tini -- /usr/l…" Up 2 minutes 0.0.0.0:9200->9200/tcp
def456 docker.elastic.co/kibana/kibana:8.15.0 "/bin/tini -- /usr/l…" Up 2 minutes 0.0.0.0:5601->5601/tcp
6. 驗證 Elasticsearch
在瀏覽器訪問:
-
Elasticsearch: http://localhost:9200
你應該看到類似:{"name" : "es01","cluster_name" : "es-docker-cluster","cluster_uuid" : "xxxx","version" : {"number" : "8.15.0"},"tagline" : "You Know, for Search" }
-
Kibana: http://localhost:5601
如果 Kibana 頁面空白或報錯:等 1-2 分鐘,它需要時間初始化。
7. 學習建議
安裝好之后,你可以:
-
基礎操作
curl -X GET "localhost:9200/_cat/indices?v" curl -X PUT "localhost:9200/test_index" curl -X POST "localhost:9200/test_index/_doc/1" -H 'Content-Type: application/json' -d '{"name":"Alice"}' curl -X GET "localhost:9200/test_index/_search?q=name:Alice"
-
使用 Kibana Dev Tools
- 打開 http://localhost:5601/app/dev_tools#/console
- 在左側輸入 DSL 查詢,右側返回結果,體驗比 curl 友好。
8. 常見問題匯總(FAQ)
問題 | 原因 | 解決辦法 |
---|---|---|
容器一直重啟 | 內存不足 | 調大 Docker 內存 |
max virtual memory areas vm.max_map_count [65530] is too low | Linux 內核參數限制 | sudo sysctl -w vm.max_map_count=262144 |
Kibana 502 錯誤 | ES 未啟動好 | 先等 1-2 分鐘,確認 ES 9200 可訪問 |
Windows 下訪問不了 | WSL2 網絡配置 | 訪問 localhost 而不是虛擬機 IP |
Go 語言連接 Docker 中的 Elasticsearch
1. 安裝依賴
Elastic 官方提供 Go 客戶端:
github.com/elastic/go-elasticsearch/v8
執行:
go get github.com/elastic/go-elasticsearch/v8
2. 編寫示例代碼
新建一個文件 main.go
:
package mainimport ("bytes""context""encoding/json""fmt""log""strings"elasticsearch "github.com/elastic/go-elasticsearch/v8"
)// 定義一個簡單的文檔結構
type User struct {Name string `json:"name"`Age int `json:"age"`
}func main() {// 1. 配置 ES 客戶端cfg := elasticsearch.Config{Addresses: []string{"http://192.168.132.131:9200", // 連接 Docker 里的 ES},// 如果你開啟了 xpack.security.enabled=true,需要在這里配置用戶名密碼// Username: "elastic",// Password: "your_password",}es, err := elasticsearch.NewClient(cfg)if err != nil {log.Fatalf("創建客戶端失敗: %s", err)}// 2. Ping 一下,確認連接成功res, err := es.Info()if err != nil {log.Fatalf("連接 ES 失敗: %s", err)}defer res.Body.Close()fmt.Println("已連接到 Elasticsearch:", res)// 3. 插入一條文檔user := User{Name: "Alice", Age: 25}doc, _ := json.Marshal(user)res, err = es.Index("users", // 索引名(如果不存在會自動創建)bytes.NewReader(doc), // 文檔內容es.Index.WithDocumentID("1"), // 指定 ID = 1es.Index.WithContext(context.Background()),)if err != nil {log.Fatalf("寫入文檔失敗: %s", err)}defer res.Body.Close()fmt.Println("文檔寫入成功")// 4. 搜索文檔query := `{"query": {"match": {"name": "Alice"}}}`res, err = es.Search(es.Search.WithContext(context.Background()),es.Search.WithIndex("users"), // 查詢的索引es.Search.WithBody(strings.NewReader(query)),es.Search.WithPretty(),)if err != nil {log.Fatalf("搜索失敗: %s", err)}defer res.Body.Close()var result map[string]interface{}if err := json.NewDecoder(res.Body).Decode(&result); err != nil {log.Fatalf("解析響應失敗: %s", err)}// 打印搜索結果fmt.Println("搜索結果:")hits := result["hits"].(map[string]interface{})["hits"].([]interface{})for _, hit := range hits {doc := hit.(map[string]interface{})source := doc["_source"].(map[string]interface{})fmt.Printf("ID=%s, Name=%s, Age=%.0f\n", doc["_id"], source["name"], source["age"])}
}
3. 運行測試
確保 Docker 里的 Elasticsearch 已經啟動 (9200
端口可訪問)。
然后運行:
go run main.go
你應該能看到類似輸出:
已連接到 Elasticsearch: ...
文檔寫入成功
搜索結果:
ID=1, Name=Alice, Age=25
4. 常見問題(Go 端)
問題 | 原因 | 解決方法 |
---|---|---|
connection refused | Docker 里的 ES 沒啟動 / 端口沒映射 | 檢查 docker ps ,確認 9200 端口暴露出來 |
security_exception | 你沒關閉安全認證 | 在 docker-compose 里加 xpack.security.enabled=false 或配置用戶名密碼 |
index_not_found_exception | 查詢的索引不存在 | 先寫入文檔,ES 會自動創建索引 |