1
\$\begingroup\$

I need to search for records based on their area, postcode, city and sort each group separately based on the value of their code field.

Table is as follows:

ID   Code Name    Area        PostCode   City 
1    15    BV     Shore        343444    Toronto
2    2     BB     North        545555    London
3    3     AA     North        343444    Munich
4    4     KH     South Shore  959595    London
5    1     XX     North Shore  343444    Toronto

I want to show following list against 'North 343444 London':

2  BB   North         545555       London
3  AA   North         343444       Munich
--------------------------------------------
1  XX   North Shore   343444       Toronto
15 BV   Shore         343444       Toronto
--------------------------------------------
4  KH   South Shore   959595       London
  • BB and AA will be returned and sorted for matched area (PostCode and City are ignored)
  • XX, BV will be returned and sorted for matched postcode. (Area and City are ignored)
  • KH will be returned for matched city. (Area and Postcode are ignored)

As you can see code of XX is 1 but in result list it comes up after BB and AA because it is sorted in its own group (XX and BV).

In controller I have:

List<Area> matchedArea = searchService.findAreaMatches(area);
List<Area> matchedPostcode = searchService.findPostcodeMatches(area);
List<Area> matchedCity = searchService.findCityMatches(area);

In the Service class I have:

@Override
@Transactional(readOnly = true)
public List<Area> findAreaMatches(String area){
     return searchRep.findAreaMatches(area);
}

@Override
@Transactional(readOnly = true)
public List<Area> findPostcodeMatches(int postcode){
     return searchRep.findPostcodeMatches(postcode);
}

@Override
@Transactional(readOnly = true)
public List<Area> findCityMatches(String city){
     return searchRep.findCityMatches(city);
}

Is there any better approach to this? Is that fine to have three different methods in which each has its own @Transactional annotation?

\$\endgroup\$
2
\$\begingroup\$

If you're concerned about repeating yourself, you can look into the Java workaround/equivalent of C# delegates, though it might be more trouble than it's worth with regard to clarity and conciseness (http://www.javacamp.org/javavscsharp/delegate.html).

Everything below is just a hyper-abridged and incomplete explanation of one use of delegates.

Think of delegates as a stand-in for any method with a specific signature. In this case, you could use it for searchRep.findAreaMatches and searchRep.findCityMatches (searchRep.findPostcodeMatches has a different signature). At a high level, it might do something like this:

delegate List<Area> functionDelegate(string s);
functionDelegate f;
if (areaMatch):
    f = searchRep.findAreaMatches
else if (cityMatch):
    f = searchRep.findCityMatches
else:
    f = /* Your choice of what goes here */
functionDelegate(areaOrCity)

As a bit of an semi-related side-note, languages like Python allow for similar behavior without the need to explicitly declare something a delegate and without worrying about signatures, though you do have to make sure your types are correct.

def findMatches(arg):
    func = someFunction
    if areaMatch:
        func = searchRep.findAreaMatches
    elif postcodeMatch:
        func = searchRep.findPostcodeMatches
    elif cityMatch:
        func = searchRep.findCityMatches
    return func(arg)

Apologies if I totally missed the mark on what you were asking, I'm new to this. Hope it helps!

\$\endgroup\$

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.