es.go 19 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782
  1. package es
  2. import (
  3. "bytes"
  4. "context"
  5. "encoding/json"
  6. "eta/eta_mini_ht_api/common/component/config"
  7. logger "eta/eta_mini_ht_api/common/component/log"
  8. "eta/eta_mini_ht_api/common/contants"
  9. "fmt"
  10. "github.com/elastic/go-elasticsearch/v7"
  11. "github.com/elastic/go-elasticsearch/v7/esapi"
  12. "io"
  13. "strconv"
  14. "strings"
  15. "sync"
  16. )
  17. type ESBase interface {
  18. GetId() string
  19. }
  20. var (
  21. esOnce sync.Once
  22. esClient *ESClient
  23. )
  24. type ESClient struct {
  25. esOp *elasticsearch.Client
  26. }
  27. type SearchType string
  28. const (
  29. MatchAll = "match_all"
  30. Match = "match"
  31. CountWithDocIds = "count_with_doc_ids"
  32. Range = "range"
  33. MatchAllByCondition = "match_all_by_condition"
  34. RangeByCondition = "range_by_condition"
  35. RangeByConditionWithDocIds = "range_by_condition_with_doc_ids"
  36. RangeWithDocIds = "range_with_doc_ids"
  37. LimitByScore = "limit_by_score"
  38. HomeSearch = "home_search"
  39. )
  40. func GetInstance() *ESClient {
  41. esOnce.Do(func() {
  42. // 检查是否成功获取到RedisConfig实例,没有配置则不进行redis初始化
  43. if esConf, ok := config.GetConfig(contants.ES).(*config.ESConfig); ok {
  44. logger.Info("初始化es")
  45. // 这里可以添加初始化Redis的逻辑
  46. esClient = newEs(esConf)
  47. logger.Info("es地址:%v", esConf.GetUrl())
  48. }
  49. })
  50. return esClient
  51. }
  52. func (es *ESClient) es() *elasticsearch.Client {
  53. return es.esOp
  54. }
  55. func newEs(config *config.ESConfig) *ESClient {
  56. elasticsearch.NewDefaultClient()
  57. client, err := elasticsearch.NewClient(
  58. elasticsearch.Config{
  59. Addresses: []string{config.GetUrl()},
  60. // A list of Elasticsearch nodes to use.
  61. Username: config.GetUserName(),
  62. Password: config.GetPassword(), // Password for HTTP Basic Authentication.
  63. },
  64. )
  65. if err != nil {
  66. logger.Error("连接ES失败:%v", err)
  67. panic("启动es失败")
  68. }
  69. return &ESClient{esOp: client}
  70. }
  71. func init() {
  72. if GetInstance() == nil {
  73. panic("初始化es失败")
  74. }
  75. logger.Info("es初始化成功")
  76. }
  77. // BulkInsert 批量创建文档
  78. func (es *ESClient) BulkInsert(indexName string, docs []ESBase) (err error) {
  79. // 创建批量请求
  80. bulkBody := new(bytes.Buffer)
  81. for _, doc := range docs {
  82. enc := json.NewEncoder(bulkBody)
  83. if err = enc.Encode(map[string]interface{}{
  84. "index": map[string]interface{}{
  85. "_index": indexName,
  86. "_id": doc.GetId(),
  87. },
  88. }); err != nil {
  89. logger.Error("生成es批处理请求参数失败: %s", err)
  90. }
  91. if err = enc.Encode(doc); err != nil {
  92. logger.Error("生成es批处理文档失败: %s", err)
  93. }
  94. }
  95. bulkReq := esapi.BulkRequest{
  96. Body: bytes.NewReader(bulkBody.Bytes()),
  97. Refresh: "true",
  98. }
  99. res, err := bulkReq.Do(context.Background(), es.esOp)
  100. if err != nil {
  101. logger.Error("es批处理创建失败: %s", err)
  102. }
  103. defer res.Body.Close()
  104. if res.IsError() {
  105. var e map[string]interface{}
  106. if err = json.NewDecoder(res.Body).Decode(&e); err != nil {
  107. logger.Error("解析es应答失败: %v", err)
  108. } else {
  109. logger.Error("es请求失败: %s: %v\n", res.Status(), err)
  110. }
  111. }
  112. return
  113. }
  114. type ESResponse struct {
  115. Took int `json:"took"`
  116. Count int `json:"count"`
  117. TimedOut bool `json:"timedOut"`
  118. Hits Hits `json:"hits"`
  119. _Shards ShardsInfo `json:"_shards"`
  120. }
  121. type Hits struct {
  122. Total TotalHits `json:"total"`
  123. MaxScore float64 `json:"maxScore"`
  124. Hits []Hit `json:"hits"`
  125. }
  126. type TotalHits struct {
  127. Value int `json:"value"`
  128. Relation string `json:"relation"`
  129. }
  130. type Hit struct {
  131. Index string `json:"_index"`
  132. Type string `json:"_type"`
  133. ID string `json:"_id"`
  134. Score float64 `json:"_score"`
  135. Source json.RawMessage `json:"_source"`
  136. Highlight json.RawMessage `json:"highlight"`
  137. }
  138. type ShardsInfo struct {
  139. Total int `json:"total"`
  140. Successful int `json:"successful"`
  141. Skipped int `json:"skipped"`
  142. Failed int `json:"failed"`
  143. }
  144. type ESQueryRequest struct {
  145. IndexName string
  146. From int
  147. Size int
  148. Key string
  149. Column string
  150. Condition string
  151. ConditionValue string
  152. Sorts []string
  153. Type SearchType
  154. RangeColumn string
  155. DocIds []string
  156. Max interface{}
  157. Min interface{}
  158. MinScore float64
  159. }
  160. func (req *ESQueryRequest) CreateESQueryRequest(index string, column string, key string, from int, size int, sorts []string, searchType SearchType) *ESQueryRequest {
  161. return &ESQueryRequest{
  162. IndexName: index,
  163. Type: searchType,
  164. From: from,
  165. Size: size,
  166. Key: key,
  167. Column: column,
  168. Sorts: sorts,
  169. }
  170. }
  171. func (req *ESQueryRequest) Limit(limit int) *ESQueryRequest {
  172. req.Size = limit
  173. return req
  174. }
  175. func (req *ESQueryRequest) WithScore(score float64) *ESQueryRequest {
  176. req.MinScore = score
  177. return req
  178. }
  179. func (req *ESQueryRequest) Range(from int64, to int64, column string) *ESQueryRequest {
  180. req.RangeColumn = column
  181. req.Max = to
  182. req.Min = from
  183. return req
  184. }
  185. func (req *ESQueryRequest) Before(max interface{}, column string) *ESQueryRequest {
  186. req.RangeColumn = column
  187. req.Max = max
  188. return req
  189. }
  190. func (req *ESQueryRequest) ByCondition(column string, value string) *ESQueryRequest {
  191. req.Condition = column
  192. req.ConditionValue = value
  193. return req
  194. }
  195. func (req *ESQueryRequest) WithDocs(docIds []string) *ESQueryRequest {
  196. req.DocIds = docIds
  197. return req
  198. }
  199. func (req *ESQueryRequest) parseJsonQuery() (queryMap map[string]interface{}) {
  200. switch req.Type {
  201. case MatchAll:
  202. queryMap = map[string]interface{}{
  203. "query": map[string]interface{}{
  204. "match": map[string]interface{}{
  205. req.Column: req.Key,
  206. },
  207. },
  208. }
  209. return
  210. case MatchAllByCondition:
  211. queryMap = map[string]interface{}{
  212. "query": map[string]interface{}{
  213. "bool": map[string]interface{}{
  214. "must": []map[string]interface{}{
  215. {
  216. "match": map[string]interface{}{
  217. req.Column: req.Key,
  218. },
  219. },
  220. {
  221. "term": map[string]interface{}{
  222. req.Condition: req.ConditionValue,
  223. },
  224. },
  225. },
  226. },
  227. },
  228. }
  229. return
  230. case Match:
  231. queryMap = map[string]interface{}{
  232. "query": map[string]interface{}{
  233. "match": map[string]interface{}{
  234. req.Column: req.Key,
  235. },
  236. },
  237. "highlight": map[string]interface{}{
  238. "fields": map[string]interface{}{
  239. req.Column: map[string]interface{}{},
  240. },
  241. "pre_tags": []string{"<span style='color:#0078E8'>"},
  242. "post_tags": []string{"</span>"},
  243. },
  244. }
  245. return
  246. case CountWithDocIds:
  247. queryMap = map[string]interface{}{
  248. "query": map[string]interface{}{
  249. "bool": map[string]interface{}{
  250. "must": []map[string]interface{}{
  251. {
  252. "match": map[string]interface{}{
  253. req.Column: req.Key,
  254. },
  255. },
  256. },
  257. "filter": map[string]interface{}{
  258. "terms": map[string]interface{}{
  259. "_id": req.DocIds,
  260. },
  261. },
  262. },
  263. },
  264. }
  265. return
  266. case Range:
  267. queryMap = map[string]interface{}{
  268. "query": map[string]interface{}{
  269. "match": map[string]interface{}{
  270. req.Column: req.Key,
  271. },
  272. },
  273. "highlight": map[string]interface{}{
  274. "fields": map[string]interface{}{
  275. req.Column: map[string]interface{}{},
  276. },
  277. "pre_tags": []string{"<span style='color:#0078E8'>"},
  278. "post_tags": []string{"</span>"},
  279. },
  280. "post_filter": map[string]interface{}{
  281. "range": map[string]interface{}{
  282. req.RangeColumn: map[string]interface{}{
  283. "gte": req.Min,
  284. "lte": req.Max,
  285. },
  286. },
  287. },
  288. }
  289. return
  290. case RangeWithDocIds:
  291. queryMap = map[string]interface{}{
  292. "query": map[string]interface{}{
  293. "match": map[string]interface{}{
  294. req.Column: req.Key,
  295. },
  296. },
  297. "highlight": map[string]interface{}{
  298. "fields": map[string]interface{}{
  299. req.Column: map[string]interface{}{},
  300. },
  301. "pre_tags": []string{"<span style='color:#0078E8'>"},
  302. "post_tags": []string{"</span>"},
  303. },
  304. "post_filter": map[string]interface{}{
  305. "bool": map[string]interface{}{
  306. "must": []map[string]interface{}{
  307. {
  308. "range": map[string]interface{}{
  309. req.RangeColumn: map[string]interface{}{
  310. "gte": req.Min,
  311. "lte": req.Max,
  312. },
  313. },
  314. },
  315. {
  316. "terms": map[string]interface{}{
  317. "_id": req.DocIds,
  318. },
  319. },
  320. },
  321. },
  322. },
  323. }
  324. return
  325. case RangeByCondition:
  326. queryMap = map[string]interface{}{
  327. "query": map[string]interface{}{
  328. "match": map[string]interface{}{
  329. req.Column: req.Key,
  330. },
  331. },
  332. "highlight": map[string]interface{}{
  333. "fields": map[string]interface{}{
  334. req.Column: map[string]interface{}{},
  335. },
  336. "pre_tags": []string{"<span style='color:#0078E8'>"},
  337. "post_tags": []string{"</span>"},
  338. },
  339. "post_filter": map[string]interface{}{
  340. "bool": map[string]interface{}{
  341. "must": []map[string]interface{}{
  342. {
  343. "range": map[string]interface{}{
  344. req.RangeColumn: map[string]interface{}{
  345. "gte": req.Min,
  346. "lte": req.Max,
  347. },
  348. },
  349. },
  350. {
  351. "term": map[string]interface{}{
  352. req.Condition: req.ConditionValue,
  353. },
  354. },
  355. },
  356. },
  357. },
  358. }
  359. return
  360. case RangeByConditionWithDocIds:
  361. queryMap = map[string]interface{}{
  362. "query": map[string]interface{}{
  363. "match": map[string]interface{}{
  364. req.Column: req.Key,
  365. },
  366. },
  367. "highlight": map[string]interface{}{
  368. "fields": map[string]interface{}{
  369. req.Column: map[string]interface{}{},
  370. },
  371. "pre_tags": []string{"<span style='color:#0078E8'>"},
  372. "post_tags": []string{"</span>"},
  373. },
  374. "post_filter": map[string]interface{}{
  375. "bool": map[string]interface{}{
  376. "must": []map[string]interface{}{
  377. {
  378. "range": map[string]interface{}{
  379. req.RangeColumn: map[string]interface{}{
  380. "gte": req.Min,
  381. "lte": req.Max,
  382. },
  383. },
  384. },
  385. {
  386. "term": map[string]interface{}{
  387. req.Condition: req.ConditionValue,
  388. },
  389. },
  390. {
  391. "terms": map[string]interface{}{
  392. "_id": req.DocIds,
  393. },
  394. },
  395. },
  396. },
  397. },
  398. }
  399. return
  400. case LimitByScore:
  401. queryMap = map[string]interface{}{
  402. "query": map[string]interface{}{
  403. "match": map[string]interface{}{
  404. req.Column: req.Key,
  405. },
  406. },
  407. "highlight": map[string]interface{}{
  408. "fields": map[string]interface{}{
  409. req.Column: map[string]interface{}{},
  410. },
  411. "pre_tags": []string{"<span style='color:#0078E8'>"},
  412. "post_tags": []string{"</span>"},
  413. },
  414. "post_filter": map[string]interface{}{
  415. "bool": map[string]interface{}{
  416. "must": []map[string]interface{}{
  417. {
  418. "terms": map[string]interface{}{
  419. "_id": req.DocIds,
  420. },
  421. },
  422. },
  423. },
  424. },
  425. "min_score": req.MinScore,
  426. }
  427. return
  428. case HomeSearch:
  429. queryMap = map[string]interface{}{
  430. "query": map[string]interface{}{
  431. "bool": map[string]interface{}{
  432. "should": []map[string]interface{}{
  433. {
  434. "bool": map[string]interface{}{
  435. "must": []map[string]interface{}{
  436. {
  437. "match": map[string]interface{}{
  438. "title": req.Key,
  439. },
  440. },
  441. {
  442. "term": map[string]interface{}{
  443. "status": "PUBLISH",
  444. },
  445. },
  446. {
  447. "range": map[string]interface{}{
  448. "publishedTime": map[string]interface{}{
  449. "lte": req.Max,
  450. },
  451. },
  452. },
  453. },
  454. },
  455. },
  456. {
  457. "bool": map[string]interface{}{
  458. "must": []map[string]interface{}{
  459. {
  460. "match": map[string]interface{}{
  461. "mediaName": req.Key,
  462. },
  463. },
  464. {
  465. "term": map[string]interface{}{
  466. "deleted": 0,
  467. },
  468. },
  469. {
  470. "range": map[string]interface{}{
  471. req.RangeColumn: map[string]interface{}{
  472. "lte": req.Max,
  473. },
  474. },
  475. },
  476. },
  477. },
  478. },
  479. },
  480. },
  481. },
  482. "highlight": map[string]interface{}{
  483. "fields": map[string]interface{}{
  484. "title": map[string]interface{}{},
  485. "mediaName": map[string]interface{}{},
  486. },
  487. "pre_tags": []string{"<span style='color:#0078E8'>"},
  488. "post_tags": []string{"</span>"},
  489. },
  490. }
  491. return
  492. default:
  493. queryMap = map[string]interface{}{}
  494. return
  495. }
  496. }
  497. // /*
  498. // *
  499. //
  500. // 搜索
  501. //
  502. // indexName 访问索引名
  503. // query 搜索条件
  504. // from 开始搜索位置
  505. // size 搜索条数
  506. // sort 排序
  507. // */
  508. func (es *ESClient) Count(params *ESQueryRequest) (response ESResponse, err error) {
  509. queryMap := params.parseJsonQuery()
  510. jsonQuery, _ := json.Marshal(queryMap)
  511. logger.Info("查询语句: %s", string(jsonQuery))
  512. request := esapi.CountRequest{
  513. Index: []string{params.IndexName},
  514. Body: strings.NewReader(string(jsonQuery)),
  515. }
  516. res, err := request.Do(context.Background(), esClient.esOp)
  517. defer res.Body.Close()
  518. if err != nil {
  519. logger.Error("es查询失败: %s", err)
  520. }
  521. if res.IsError() {
  522. var e map[string]interface{}
  523. if err = json.NewDecoder(res.Body).Decode(&e); err != nil {
  524. logger.Error("解析es应答失败: %v", err)
  525. } else {
  526. logger.Error("es请求失败: %s: %v\n", res.Status(), e)
  527. }
  528. }
  529. body, err := io.ReadAll(res.Body)
  530. if err != nil {
  531. logger.Error("获取es应答失败: %v", err)
  532. }
  533. return parseESResponse(body)
  534. }
  535. func (es *ESClient) Search(params *ESQueryRequest) (response ESResponse, err error) {
  536. queryMap := params.parseJsonQuery()
  537. jsonQuery, _ := json.Marshal(queryMap)
  538. logger.Info("查询语句: %s", string(jsonQuery))
  539. indexes := strings.Split(params.IndexName, ",")
  540. request := esapi.SearchRequest{
  541. Index: indexes,
  542. Body: strings.NewReader(string(jsonQuery)),
  543. From: &params.From,
  544. Size: &params.Size,
  545. Sort: params.Sorts,
  546. }
  547. res, err := request.Do(context.Background(), esClient.esOp)
  548. defer res.Body.Close()
  549. if err != nil {
  550. logger.Error("es查询失败: %s", err)
  551. }
  552. if res.IsError() {
  553. var e map[string]interface{}
  554. if err = json.NewDecoder(res.Body).Decode(&e); err != nil {
  555. logger.Error("解析es应答失败: %v", err)
  556. } else {
  557. logger.Error("es请求失败: %s: %v\n", res.Status(), e)
  558. }
  559. }
  560. body, err := io.ReadAll(res.Body)
  561. if err != nil {
  562. logger.Error("获取es应答失败: %v", err)
  563. }
  564. return parseESResponse(body)
  565. }
  566. func parseESResponse(body []byte) (ESResponse, error) {
  567. var response ESResponse
  568. if err := json.Unmarshal(body, &response); err != nil {
  569. return ESResponse{}, err
  570. }
  571. for _, hit := range response.Hits.Hits {
  572. var source map[string]interface{}
  573. if err := json.Unmarshal(hit.Source, &source); err != nil {
  574. return ESResponse{}, err
  575. }
  576. }
  577. return response, nil
  578. }
  579. func (es *ESClient) GetSource(hits Hits) []Hit {
  580. return hits.Hits
  581. }
  582. func (es *ESClient) GetCount(hits Hits) []Hit {
  583. return hits.Hits
  584. }
  585. // /*
  586. // *
  587. // 添加es
  588. // indexName 索引名
  589. // id es的id
  590. // body es的值
  591. // */
  592. func (es *ESClient) Update(indexName string, id int, doc interface{}) bool {
  593. jsonUpdate := map[string]interface{}{
  594. "doc": doc,
  595. }
  596. jsonDoc, _ := json.Marshal(jsonUpdate)
  597. logger.Info("查询语句: %s", string(jsonDoc))
  598. req := esapi.UpdateRequest{
  599. Index: indexName,
  600. DocumentID: strconv.Itoa(id),
  601. Body: strings.NewReader(string(jsonDoc)),
  602. Refresh: "true",
  603. }
  604. res, err := req.Do(context.Background(), es.es())
  605. defer res.Body.Close()
  606. if err != nil {
  607. logger.Error("es查询失败: %s", err)
  608. }
  609. if res.IsError() {
  610. var e map[string]interface{}
  611. if err = json.NewDecoder(res.Body).Decode(&e); err != nil {
  612. logger.Error("解析es应答失败: %v", err)
  613. } else {
  614. logger.Error("es请求失败: %s: %v\n", res.Status(), e)
  615. }
  616. }
  617. body, err := io.ReadAll(res.Body)
  618. if err != nil {
  619. logger.Error("获取es应答失败: %v", err)
  620. }
  621. fmt.Printf("%s\n", string(body))
  622. return true
  623. }
  624. // Delete *
  625. // 删除
  626. // indexName 索引名
  627. // id es的id
  628. // */
  629. func (es *ESClient) Delete(indexName string, id int) bool {
  630. req := esapi.DeleteRequest{
  631. Index: indexName,
  632. DocumentID: strconv.Itoa(id),
  633. Refresh: "true",
  634. }
  635. res, err := req.Do(context.Background(), es.es())
  636. defer res.Body.Close()
  637. if err != nil {
  638. logger.Error("es查询失败: %s", err)
  639. }
  640. if res.IsError() {
  641. var e map[string]interface{}
  642. if err = json.NewDecoder(res.Body).Decode(&e); err != nil {
  643. logger.Error("解析es应答失败: %v", err)
  644. } else {
  645. logger.Error("es请求失败: %s: %v\n", res.Status(), e)
  646. }
  647. }
  648. body, err := io.ReadAll(res.Body)
  649. if err != nil {
  650. logger.Error("获取es应答失败: %v", err)
  651. }
  652. fmt.Printf("%s\n", string(body))
  653. return true
  654. }
  655. func (es *ESClient) Exist(indexName string, docId int) (exist bool, err error) {
  656. getRequest := esapi.GetRequest{
  657. Index: indexName,
  658. DocumentID: strconv.Itoa(docId),
  659. }
  660. // 执行请求
  661. res, err := getRequest.Do(context.Background(), es.es())
  662. if err != nil {
  663. logger.Error("es获取文档是否存在失败: %v", err)
  664. }
  665. defer res.Body.Close()
  666. // 检查文档是否存在
  667. if res.IsError() {
  668. // 如果文档不存在,通常返回 404 Not Found
  669. if res.StatusCode == 404 {
  670. logger.Info("文档不存在.")
  671. return false, nil
  672. } else {
  673. // 其他错误
  674. var e map[string]interface{}
  675. if err = json.NewDecoder(res.Body).Decode(&e); err != nil {
  676. logger.Error("解析es应答失败: %v", err)
  677. return false, err
  678. } else {
  679. // Print the response status and error information.
  680. logger.Error("[%s] %s: %s\n", res.Status(), e["error"].(map[string]interface{})["type"], e["error"].(map[string]interface{})["原因"])
  681. return false, nil
  682. }
  683. }
  684. } else {
  685. // 如果文档存在
  686. logger.Info("doc存在")
  687. return true, nil
  688. }
  689. }
  690. //
  691. //func CreateIndex(indexName string) error {
  692. // resp, err := esClient.es().Indices.
  693. // Create(indexName).
  694. // Do(context.Background())
  695. // if err != nil {
  696. // logger.Error("创建ES索引失败:%v", err)
  697. // return err
  698. // }
  699. // fmt.Printf("index:%#v\n", resp.Index)
  700. // return nil
  701. //}
  702. // DeleteIndex 删除索引
  703. //
  704. // func DeleteIndex(indexName string) error {
  705. // _, err := esClient.es().Indices. // 表明是对索引的操作,而Index则表示是要操作具体索引下的文档
  706. // Delete(indexName).
  707. // Do(context.Background())
  708. // if err != nil {
  709. // fmt.Printf("delete index failed,err:%v\n", err)
  710. // return err
  711. // }
  712. // fmt.Printf("delete index successed,indexName:%s", indexName)
  713. // return nil
  714. // }
  715. //
  716. // CreateDocument 创建文档
  717. func (es *ESClient) CreateDocument(indexName string, id int, doc interface{}) (success bool) {
  718. jsonDoc, _ := json.Marshal(doc)
  719. logger.Info("查询语句: %s", string(jsonDoc))
  720. // 添加文档
  721. indexRequest := esapi.IndexRequest{
  722. Index: indexName,
  723. DocumentID: strconv.Itoa(id),
  724. Body: strings.NewReader(string(jsonDoc)),
  725. Refresh: "true",
  726. }
  727. // 执行请求
  728. res, err := indexRequest.Do(context.Background(), es.es())
  729. if err != nil {
  730. logger.Error("ES创建文档失败: %s", err)
  731. return false
  732. }
  733. defer res.Body.Close()
  734. // 检查文档是否成功创建
  735. if res.IsError() {
  736. var e map[string]interface{}
  737. if err := json.NewDecoder(res.Body).Decode(&e); err != nil {
  738. logger.Error("解析ES应答失败: %s", err)
  739. } else {
  740. // Print the response status and error information.
  741. logger.Error("[%s] %s: %s\n", res.Status(), e["error"].(map[string]interface{})["类型"], e["错误"].(map[string]interface{})["原因"])
  742. }
  743. return false
  744. } else {
  745. // 如果文档成功创建
  746. logger.Info("创建文档成功")
  747. return true
  748. }
  749. }