/*
 *  getSearchString.mm
 *  AudioUIdemo
 *
 *	Code and Sound Design by Peter "pdx" Drescher.
 *  Copyright 2010 twittering machine. All rights reserved.
 *
 *	This module receives a string when the user enters the "search" keyword.
 *	The string is formatted as a URL for the Twittering Machine's Google Custom Search Engine (CSE).
 *	The HTML result is then parsed, looking for the (up to) 10 "<a href="http:// ...> LABELS </a>" returned.
 *	The labels are '/f' (line feed) deliniated and returned to be screen printed
 *	note: the algorithm is not perfect, given the unpredictable nature of the HTML response,
 *	but it's close enough for the purpose of returning web data for screen printing.
 */

#import <Cocoa/Cocoa.h>
#import <WebKit/WebKit.h>
#include "GetSearchString.h"

string GetSearchString::fetchHTMLfromGoogle (string inSearchStr)
{
    // Get the string and percent-escape for insertion into URL
	NSString *searchString = [[NSString stringWithUTF8String:inSearchStr.c_str()] 
							  stringByAddingPercentEscapesUsingEncoding:NSUTF8StringEncoding];

    // Create the URL
    NSString *urlString = [NSString stringWithFormat:
						   @"http://www.google.com/search?q=%@%@", searchString,
						   @"&hl=en&start=0&num=10&client=google-csbe&cx=012292611867340687512:_mj7eryns6a"]; //TwitteringMachineAudioUIDemo GoogleCSE ID
	
    NSURL	 *url = [NSURL URLWithString:urlString];
    NSError  *HTMLerror;
	NSString *HTMLString = [NSString stringWithContentsOfURL:url encoding:NSUTF8StringEncoding error:&HTMLerror];

	//  if no string returned, computer is not connected to internet, so send up a red flag
    if (HTMLString == NULL) {
        return "alert2";
    } else {
		NSString *HTMLStrEsc = [(NSString *) CFXMLCreateStringByUnescapingEntities(NULL, (CFStringRef) HTMLString, NULL) autorelease];
		HTMLstr = [HTMLStrEsc UTF8String];
		return (parseHTMLString());
	}
}

string GetSearchString::parseHTMLString()
{
	std::cout << "******************parsing HTML string \n";
	std::cout << HTMLstr;
	size_t hrefFoundAt;
	string hrefStr ("<a href=\"http://");
	formattedResponse = "";
	filePos = 0;

	//get the 10 labels associated with the href links returned by the google search
	for (int x=0; x<11; x++)
	{	
		hrefFoundAt = HTMLstr.find(hrefStr,filePos);							//look for an href link
		if (hrefFoundAt != string::npos)
		{
			if (x > 0)
			{
				if (HTMLstr.substr((hrefFoundAt + 16), 8) != "webcache")		// usually indicates a "webcache.google.com/" link (view as pdf, text, etc)
				{				
					filePos = int(hrefFoundAt) + 16;
					if (formattedResponse != ""){formattedResponse += '\f';}	//concat labels together separated by "line feed" \f, after the first one
					getHrefLabel();
				}
				else
				{
					filePos = int(hrefFoundAt) + 16;							// skip past "view as pdf/text/html" links 
					x--;														// and don't count them as part of the 10 labels
				}
			}
			else
			{
				filePos = int(hrefFoundAt) + 16;								// skip past first link (the google CSE logo)
			}				
		}
	}
	
	if (formattedResponse == "") {												// no links found, send up a white flag
		return "alert1";
	} else {
		return formattedResponse;
	}
}

void GetSearchString::getHrefLabel()
{
	bool dontPrint = false;
	
	//skip to end of <a href ... > tag
	while (HTMLstr.at(filePos) != '>') {
		filePos++;
	}
	
	//get characters from HTMLstr after <a href ...> tag, ignoring tags like <em>, </em>, etc, until </a> is reached
	filePos++;
	while (HTMLstr.compare(filePos, 4, "</a>") != 0) {
		if (HTMLstr.at(filePos) == '<')
		{
			while (HTMLstr.at(filePos) != '>') {		//skip extra tags in label
				filePos++;
			}
			if (HTMLstr.at(filePos + 1) != '<')			// test for edge case (i.e. "<em></a>")
			{
				filePos++;
			} else {
				dontPrint = true;						// set flag so as not to print the extra edge case character
			}
		}
		
		if ((dontPrint == true) ||
			((HTMLstr.at(filePos) == ' ' && (HTMLstr.at(filePos - 1) == ' '))))
		{
			dontPrint = false;							//skip screen printing the edge case character, or extra spaces
			filePos++;
		} else {
			formattedResponse += HTMLstr.at(filePos);	//add the label character to the response string
			filePos++;
		}
	}
}


