2016-04-22 12 views
2

Ich entwerfe eine Decorator-Klasse, die eine News-Suchmaschine umschließt, so dass wir diese Klasse mit einer Bibliothek versenden können, die von anderen Teams verwendet werden kann.Java - Wie man eine Methode für die Suche entwickelt?

Die exponierte Schnittstelle dieser Klasse ist eine im Java-Stil, sie braucht eine Menge Parameter, dann setzt dieser Dekorator diese Parameter als Suchtext für die Suchmaschine zusammen.

Meine Methode ist so etwas wie die folgenden:

public List<News> search(List<String> keywords, List<String> categories, List<String> authors, List<Location> locactions, List<LocalDate> dates, List<SortRule> sortRules, int offset, int limit); 

Ja, ich weiß ... Diese Methode sieht lächerlich lange, sehr fehler Sonde und hart für die Kunden zu bedienen.

Also, wie kann ich eine bessere API für eine solche Suchfunktionalität entwerfen?

+2

Wenn Sie versuchen, gute API-Design herauszufinden, ist es nie eine schlechte Idee, um andere gute Bibliotheken Design zu betrachten. Eine gute, die in den Sinn kommt, ist Hibernates "Kriterien" -Klasse https://docs.jboss.org/hibernate/orm/3.3/reference/en/html/querycriteria.html –

+0

Danke, es ist wirklich eine gute Referenz! –

Antwort

6

Sie können versuchen, eine Wrapper-Klasse zum Anwenden der Regelfilter zu schreiben und dann das neue Objekt dieser Klasse in Ihre aktuelle Klasse aufzunehmen. Auf diese Weise wäre es viel einfacher und sauberer.

Zum Beispiel

RuleFilters r = new RuleFilters(); 
r.addFilters(Type.Keywords, keywords); 
r.addFilters(Type.Categories, categories); 
r.addFilters(Type.Authors, authors); 

Hier Type ist eine Enumeration, die die Einzelheiten der verschiedenen Regel Filter wie {Categories, Authors, Keywords} usw.

schließlich in der Hauptklasse gilt:

public List<News> search(RuleFilters r) { 
    /* Do Something with the rule filters */ 
}; 

Schnittstelle :

List<News> search(RuleFilters r); 

Hinweis:public Schlüsselwort ist in Schnittstellen nicht erforderlich.

3

Wie in Effective Java erwähnt, können Sie Builder-Muster verwenden. Und das wäre eine saubere Lösung.

0

Eine andere Möglichkeit ist die Verwendung von Bean oder POJO für den Transport von Suchparametern. Danach können Sie einige Entwurfsmuster oder Filter verwenden, um Ergebnisse zu erhalten. Aber für einen einfachen Transport ist es gut, Bean zu benutzen.

public class SearchParameters{ 

private List<String> keywords; 
private List<String> categories; 
private List<String> authors; 
private List<Location> locactions; 
private List<LocalDate> dates; 
private List<SortRule> sortRules; 
private int offset; 
private int limit; 
//Getters and Setters 

} 

//For one request 
public List<News> search(SearchParameters param) { 
    /* Do Something with the rule filters */ 
}; 

//for multiple request you could use List<SearchParameters> params 
0

Vielleicht können Sie auf der Elasticsearch Java library und anschauen:

SearchResponse response = client.prepareSearch("news") 
     .setQuery(QueryBuilders.termQuery("author", "jack"))    // Query 
     .setPostFilter(QueryBuilders.rangeQuery("date_published").from('2016-04-01').to('2016-04-30')) // Filter 
     .setFrom(0).setSize(10) 
     .execute() 
     .actionGet(); 

, die im Grunde eine spezielle Implementierung des Builder-Muster ist.