// text-google.go package main import ( "fmt" "log" "net/http" "net/url" "strconv" "strings" "github.com/PuerkitoBio/goquery" ) func PerformGoogleTextSearch(query, safe, lang string, page int) ([]TextSearchResult, error) { const resultsPerPage = 10 var results []TextSearchResult client := &http.Client{} safeParam := "&safe=off" if safe == "active" { safeParam = "&safe=active" } langParam := "" if lang != "" { langParam = "&lr=" + lang } // Calculate the start index based on the page number startIndex := (page - 1) * resultsPerPage searchURL := "https://www.google.com/search?q=" + url.QueryEscape(query) + safeParam + langParam + "&udm=14&start=" + strconv.Itoa(startIndex) req, err := http.NewRequest("GET", searchURL, nil) if err != nil { return nil, fmt.Errorf("failed to create request: %v", err) } req.Header.Set("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/107.0.0.0 Safari/537.36") resp, err := client.Do(req) if err != nil { return nil, fmt.Errorf("making request: %v", err) } defer resp.Body.Close() if resp.StatusCode != http.StatusOK { return nil, fmt.Errorf("unexpected status code: %d", resp.StatusCode) } doc, err := goquery.NewDocumentFromReader(resp.Body) if err != nil { return nil, fmt.Errorf("loading HTML document: %v", err) } doc.Find(".yuRUbf").Each(func(i int, s *goquery.Selection) { link := s.Find("a") href, exists := link.Attr("href") if !exists { if debugMode { log.Printf("No href attribute found for result %d\n", i) } return } header := link.Find("h3").Text() header = strings.TrimSpace(strings.TrimSuffix(header, "›")) descSelection := doc.Find(".VwiC3b").Eq(i) description := "" if descSelection.Length() > 0 { description = descSelection.Text() } result := TextSearchResult{ URL: href, Header: header, Description: description, } results = append(results, result) if debugMode { log.Printf("Google result: %+v\n", result) } }) if len(results) == 0 { if debugMode { log.Println("No results found from Google") } } return results, nil }