Implementing DuckDuckGo Api in SUSI Android

As we know that Susi is an open source intelligent chatbot, it must be able to reply with user’s query on any topic. Therefore we have implemented DuckDuckGo API in Susi Android(https://github.com/fossasia/susi_android) which will help us to generate search result for the query asked by the user.

 

DuckDuckGo is an API which provides instant search results. This basically works as a search engine having information about various things. The most important thing about DuckDuckGo is that it is non tracking. It does not track its users and show results based on their search history. Thus the search results remain uniform across all the clients irrespective of their search history. The information inside the API is fed from more than 120 different independent sources. This is what makes it different from other search engines. The response in the form of answers include different types of links, description, categories, and definition about various stuffs.

For more details about the Api please check this link.

 

API endpoints:

http://api.duckduckgo.com/?q=DuckDuckGo&format=json

This is one of the links generated to test the api. Here we can see different parameters, the parameter q is the query parameter where we write our question/query to get the response from the API. The format here defines the format in which we want the response to be. Here in this case we are obtaining the response in the form of JSON which can be parsed to obtain the desired result in the client.

The response obtained by the following query is as follow:-

{  

  "DefinitionSource":"",

  "Heading":"DuckDuckGo",

  "ImageWidth":340,

  "RelatedTopics":[  

     {  

        "Result":"<a href=\"https://duckduckgo.com/Names_Database\">Names Database</a> - The Names Database is a partially defunct social network, owned and operated by Classmates.com, a wholly owned subsidiary of United Online. The site does not appear to be significantly updated since 2008, and has many broken links and display issues.",

        "Icon":{  

           "URL":"",

           "Height":"",

           "Width":""

        },

        "FirstURL":"https://duckduckgo.com/Names_Database",

        "Text":"Names Database - The Names Database is a partially defunct social network, owned and operated by Classmates.com, a wholly owned subsidiary of United Online. The site does not appear to be significantly updated since 2008, and has many broken links and display issues."

     }

}

 

Implementation in Susi android

In Susi Android we are using Retrofit library by Square for API calling. Retrofit is one of the best libraries present for the network calling. It helps the developer to migrate from the old way of using AsyncTask in the Android app which creates a lot of mess and ugly code.

For the implementation in Susi Android, we have made a WebSearchClient class that stores the base address for the API calling.

public class WebSearchClient {

  public static final String BASE_URL = "http://api.duckduckgo.com";

  private static Retrofit retrofit = null;



  public static Retrofit getClient() {

      if (retrofit==null) {

          retrofit = new Retrofit.Builder()

                  .baseUrl(BASE_URL)

                  .addConverterFactory(GsonConverterFactory.create())

                  .build();

      }

      return retrofit;

  }

}

To get the response we call the API with get method passing the query and format parameter in the following way.





public interface WebSearchService {



  @GET("/?format=json&pretty=1")

  Call<WebSearch> getresult(@Query("q") String query);

}



The results obtained from the server in the form of JSON is parsed in the form of objects in this way:-



public class WebSearch{



  @SerializedName("Heading")

  @Expose

  private String heading;



  @SerializedName("RelatedTopics")

  @Expose

  private List<RelatedTopics> relatedTopics;



  public WebSearch(String heading, List<RelatedTopics> relatedTopics) {

      this.heading = heading;

      this.relatedTopics = relatedTopics;

  }





public class RelatedTopics {



  @SerializedName("FirstURL")

  @Expose

  private String url;



  @SerializedName("Text")

  @Expose

  private String text;



  @SerializedName("Icon")

  @Expose

  private WebIcon icon;



  @SerializedName("Result")

  @Expose

  private String result;



  public RelatedTopics(String url, String text, WebIcon icon) {

      this.url = url;

      this.text = text;

      this.icon = icon;

  }



At the end after setting up all the above things, we call the API and store the result in the realm or local storage.

final WebSearchService apiService = WebSearchClient.getClient().create(WebSearchService.class);



Call<WebSearch> call = apiService.getresult(webquery);



call.enqueue(new Callback<WebSearch>() {

  @Override

  public void onResponse(Call<WebSearch> call, Response<WebSearch> response) {

      Log.e(TAG, response.toString());

      if (response.body() != null ) {

          realm.beginTransaction();

          RealmList<WebSearchModel> searchResults = new RealmList<>();


    }
}

This completes the calling of DuckDuckGo API and storing the results in the database.

To know more about API calling using Retrofit you can refer to this link.

Published by

mayank408

Android Developer at Fossasia