# How we connected Elastic Search to dgraph

**URL:** <https://discuss.dgraph.io/t/how-we-connected-elastic-search-to-dgraph/15151>\
**Category:** Showcase\
**Tags:** graphql, dgraph\
**Created:** [July 31, 2021, 5:44pm UTC](https://discuss.dgraph.io/t/how-we-connected-elastic-search-to-dgraph/15151 "2021-07-31T17:44:50Z")\
**Posts on this page:** 1\
**Page:** 1

<div class="post-metadata">

**Author:** ![pshaddel](https://yyz1.discourse-cdn.com/flex007/user_avatar/discuss.dgraph.io/pshaddel/32/11584_2.png) [@pshaddel](https://discuss.dgraph.io/u/pshaddel)\
**Post date:** [July 31, 2021, 5:44pm UTC](https://discuss.dgraph.io/t/how-we-connected-elastic-search-to-dgraph/15151/1 "2021-07-31T17:44:50Z")

</div>

We wanted to perform search queries using **ElasticSearch** and we didn’t want users to query Elasticsearch directly so we decided to make requests with dgraph using [custom directive](https://dgraph.io/docs/graphql/custom/directive/):

## Define a schema that matches the result of elastic search

Here is the schema you need:

```auto
type ElasticResult @remote {
  took: Int
  timed_out: Boolean
  _shards: Shard_Data
  hits: Hits
}

type Shard_Data @remote {
  total: Int
  successful: Int
  skipped: Int
  failed: Int
}

type Hits @remote {
  max_score: Float
  hits: [Hit]
}

type Hit @remote {
  _index: String
  _source: Doc
}

# This is the structure of your data in ElasticSearch
type Doc @remote {
  EpisodeID: String
  type: String
  title: String
  tags: String
}

```

## Prepare authorization header

ElasticSearch uses a username password authentication and we can use pass it by using proper authorization header. You can use [this link](https://www.blitter.se/utils/basic-authentication-header-generator/) or [postman](https://www.postman.com/) to generate an authorization header based on your username and password:  
For example in Postman you can use `Basic Auth` and enter your username and password:

 ![Screen Shot 2021-07-31 at 9.49.39 PM](https://canada1.discourse-cdn.com/flex007/uploads/dgraph/original/2X/0/03958e3b9798a3df58a595d701abaf860f7cda3f.png)

After doing this Postman will generate Authorization header for you:

 ![Screen Shot 2021-07-31 at 9.50.37 PM](https://canada1.discourse-cdn.com/flex007/uploads/dgraph/original/2X/2/21018df9fbe3a24c2e7ff0f5122cce2e58d1cdd5.png)

We will use this header to make requests to ElasticSearch.

## Implement Query

We need to make an external http request so we need [custom directive](https://dgraph.io/docs/graphql/custom/directive/) Also we need secret headers to pass the authorization header we have to ElasticSearch server. If you look at the document of custom headers you can see that we can pass this header using ` # Dgraph.Secret` and `secretHeaders`.

Also I have used `first` and `offset` parameters similar to autogenerated queries to tell ElasticSearch how many documents I want.  
We have another argument which is `phrase` that we are searching for it.  
  
The return type is `ElasticSearch` that we implemented in first section.

```graphql
type Query {
  ElasticSearch(
    first: Int = 30
    offset: Int = 0
    phrase: String!
  ): ElasticResult
    @custom(
      http: {
        url: "https://your_elastic_server_address/your_index/_search"
        method: POST
        secretHeaders: ["Authorization:Elastic-Search-Token"]
        body: "{query: {match: {name_of_your_field_in_elasticsearch: \"$phrase\"}},size: $first,from: $offset}"
      }
    )
}

# Dgraph.Secret Elastic-Search-Token "Basic ZWxhc3RpYzo3NjgwcTBRR00NEhTMGZoFUEI2WEQ="

```

## Execute Query

After loading this schema we can send a query like this:

```auto
query search {
     ElasticSearch(offset: 0, first: 2, phrase: "mySearchPhrase") {
          took
          timed_out
          hits {
               max_score
               hits {
                    _index
                    _source {
# These are your fields from elastic search
                         title
                         tags
                         type
                    }
               }
          }
     }
}

```

Let me know if I can improve this doc and if I can put it in a better place.
