A Second Ferret
Now that we have the framework, using another type of ferret is simply a matter of creating another class that implements the Ferret interface and instantiating it within the application. The GoogleSpecificFinder class is shown in Listing 4.
Listing 4 GoogleSpecificFinder Class
package org.chase.ferrets; import com.google.soap. search.GoogleSearch; import com.google.soap. search.GoogleSearchResult; import com.google.soap. search.GoogleSearchFault; import com.google.soap. search.GoogleSearchResultElement; import org.chase.research.Ferret; public class GoogleSpecificFinder implements Ferret { GoogleSearchResult result = null; public void find (String searchTerm) { try { GoogleSearch search = new GoogleSearch(); search.setKey("00000000000000000000000000000000"); search.setQueryString(searchTerm); result = search.doSearch(); } catch (GoogleSearchFault gsf) { System.out.println("Google Search Fault: "+gsf.getMessage()); } } public int getNumResults() { int numResults = result.getEstimatedTotalResultsCount(); if ( result.getEstimateIsExact() ){ return numResults; } else { return -1; } } public String getResults() { int startIndex = result.getStartIndex() - 1; int endIndex = result.getEndIndex() - 1; String resultString = ""; GoogleSearchResultElement[] resultElements = result.getResultElements(); for (int i = startIndex; i <= endIndex; i++) { GoogleSearchResultElement resultElement = resultElements[(i)]; String title = resultElement.getTitle(); if (title.equals("")) { title = "No Title Available"; } String url = resultElement.getURL(); resultString = resultString + title + "\n"; resultString = resultString + url + "\n\n"; } return resultString; } public String getFirstResult() { String resultString = ""; if (result.getEndIndex() > 0) { GoogleSearchResultElement[] resultElements = result.getResultElements(); GoogleSearchResultElement resultElement = resultElements[(0)]; String title = resultElement.getTitle(); if (title.equals("")) { title = "No Title Available"; } String url = resultElement.getURL(); resultString = resultString + title + "\n"; resultString = resultString + url + "\n\n"; } return resultString; } }
This class also uses the four Ferret methods, but it doesn't use the same "brute-force" approach that GoogleFinder does. Instead of simply converting the result to a string wholesale, it instead picks out the name and URL of each listing. Also, if the result count is an estimate (and it usually is), GoogleSpecificFinder returns -1 to signal the lack of an exact count.
So, how do we use this new class? It's simple: We just replace GoogleFinder with it in the application, as shown in Listing 5.
Listing 5 Using GoogleSpecificFinder
import org.chase.research.Ferret; import org.chase.ferrets.GoogleSpecificFinder; public class ResearchProject { public static void main(String[] args) { if (args.length > 0) { String searchTerm = args[0]; Ferret theFerret = new GoogleSpecificFinder(); System.out.println("Getting Results ..."); theFerret.find(searchTerm); int numResults = theFerret.getNumResults(); ...
Everything about the ResearchProject application is exactly as it was before, except that we're using GoogleSpecificFinder to instantiate the Ferret instead of GoogleFinder. The results, however, are very different:
Getting Results ... Result count not available. ========================= First Result: ========================= No Title Available http://www.hyperdrive.com/ ========================= All available results: ========================= No Title Available http://www.hyperdrive.com/ <b>Hyperdrive</b> http://www.hyperdriveuk.com/hyperdrive_/hyperdrive.html <b>Hyperdrive</b> Solutions http://www.hyperdrive.co.uk/ ...
Because the result count was not exact, we get a message rather than the estimate; for each result, we get only the title and the URL, rather than all of the information.
And we barely had to touch the base application.