Module: Ask::WebSearch

Defined in:
lib/ask/web_search.rb,
lib/ask/web_search/version.rb

Overview

Searches the web via a local SearXNG instance and returns the results as clean, numbered markdown for LLM consumption. The capability layer: one entry point (WebSearch.search) and a configurable endpoint. Tool framing — name, parameter schema, result wrapping — lives with the consumers (the MCP server, the agents) that call this library.

Constant Summary collapse

VERSION =
"0.3.0"

Class Method Summary collapse

Class Method Details

.search(query) ⇒ Object

Searches query and returns the results as numbered markdown ("No results found." when SearXNG found nothing). Raises on connection/HTTP failures — the caller decides how to surface them.



28
29
30
# File 'lib/ask/web_search.rb', line 28

def self.search(query)
  format_results(search_results(query))
end

.search_results(query) ⇒ Object

The raw result list: { url:, title:, content: } entries from the results and infoboxes, deduplicated by url.



34
35
36
37
38
39
40
41
42
43
44
45
# File 'lib/ask/web_search.rb', line 34

def self.search_results(query)
  uri = URI("#{searxng_url}/search?q=#{URI.encode_www_form_component(query)}&format=json")
  http = Net::HTTP.new(uri.host, uri.port)
  http.open_timeout = 5
  http.read_timeout = 10
  req = Net::HTTP::Get.new(uri)
  req["User-Agent"] = "ask-web-search/#{Ask::WebSearch::VERSION}"
  res = http.request(req)
  raise "SearXNG returned #{res.code}: #{res.body}" unless res.code.start_with?("2")

  parse_results(JSON.parse(res.body))
end

.searxng_urlObject

Local SearXNG endpoint. Defaults to the standard local instance; override with SEARXNG_URL or WebSearch.searxng_url=.



17
18
19
# File 'lib/ask/web_search.rb', line 17

def self.searxng_url
  @searxng_url || ENV.fetch("SEARXNG_URL", "http://localhost:8888")
end

.searxng_url=(url) ⇒ Object



21
22
23
# File 'lib/ask/web_search.rb', line 21

def self.searxng_url=(url)
  @searxng_url = url
end