I'm building a search engine using Lucene.NET / Solr.NET, and I'm wondering should search hits be returned as a dictionary or strongly typed object.
public class SearchResult
{
public string SearchTerm { get; set; }
public List<Dictionary<string, object>> SearchHits { get; set; }
...
}
// where search hit looks like this
Dictionary<string, object> searchHit = new Dictionary<string, object>
{
{ "Name", "John Doe" },
{ "Address", "Some street" },
};
vs
public class SearchResult
{
public string SearchTerm { get; set; }
public List<Foo> SearchHits { get; set; }
...
}
// where search hit looks like this
var searchHit = new SearchHit
{
Name = "John Doe",
Address = "Some address"
};
I will be indexing different types of objects (People, Web pages, Files, etc.).
Each object has a different set of properties (people have name and address, while web pages have URLs and titles), and search hits don't have the same set of properties as original objects (WebPage
class has the MainContent
property, but after indexing, the search hit that represents this object will have the PreviewText
property (the first 300 characters of MainContent
property with stripped HTML tags).
I don't want to duplicate the code all over the place and have: IPeopleSearchService
, IWebPagesSearchService
, IFilesSearchService
, etc. and corresponding search results: PeopleSearchResult
, FileSearchResult
, etc.
interface IFooService
{
FooSearchResult Search(string text);
void Index(Foo foo);
...
}
interface IBarService
{
BarSearchResult Search(string text);
void Index(Bar bar);
...
}
...
I would like to have a more generic solution, but I don't like over-complexity. It should be readable and easily understandable by junior developer.
interface ISearchService<TEntity, TSearchHit>
{
SearchResult<TSearchHit> Search(string text);
void Index(TEntity entity);
}
How would you design such a system? Any help would be greatly appreciated!
TEntity
I have to defineTSearchHit
. Does this look like overkill? Would I benefit from returning aDictionary
instead ofTSearchHit
?Dictionary<string, object> Search (string text, IEntityMappingStrategy mapper)
andvoid Index (object entity, IEntityMappingStrategy mapper)
methods, and then define / instantiate different strategies for each entity? Would that be more SOLID?