eggdrop script: search on SearXNG instance, by cage
Written by Simone
You can try this script on #fediverso at irc.libera.chat, where me, cage, ndo and other friends hang out
bot: "verne", running on @wpn
SearXNG instance: https://search.woodpeckersnest.space/
Thanks to cage for the script and ndo for creating the channel o/
# © cage released under CC0, public domain
# https://creativecommons.org/publicdomain/zero/1.0/
# Date: 16-08-2024
# Version: 0.1
# Package description: do a web search using your searxng instance
# Public ones won't probably work because of "limiter"
# Authorize your channel from the partyline with:
# .chanset +searxng #your-channel
# Do a search
# .search <query> | .search paris (this query goes to default engine)
# .search +<engine> <query> | .search +wp paris (this query goes to
# wikipedia)
# .search !images paris | this query search only paris' images
# List of engines: https://docs.searxng.org/user/configured_engines.html
# tcllib is required
############## configuration directives ############################
# url of the HTTP(S) server of the search engine
set searxconfig(website_url) "https://example.com/searxng"
# serach command to trigger the search
set searxconfig(cmd) ".search"
# default search engine
set searxconfig(default_engine) "ddg"
# maximum number of search results printed
set searxconfig(max_results) 3
# time tracker file
# NB: when this script runs any file with the same name within the path in the
# working directory (depending of what is considered the working
# directory of the script) will be erased and overwritten!
set searxconfig(file_millis) "searx_millis.tmp"
# Minimum search frequency in milliseconds.
# This is the minimum time that must pass between two consecutive
# search
set searxconfig(max_freq) 30000
############## configuration ends here #############
# tcllib is required
package require csv
setudef flag searxng
if { !([info exists searxconfig(lastmillis)]) } {
set searxconfig(lastmillis) 0
}
bind pub - $searxconfig(cmd) search:searxng
proc send_message {message} {
putserv "PRIVMSG $message"
}
proc slurp_file {path} {
set fp [open $path r]
set file_data [read $fp]
close $fp
return $file_data
}
proc process_csv {csv channel} {
global searxconfig
set rows [split $csv "\n"]
set count 0
#remove the header
set rows [lrange $rows 1 [llength $rows]]
if {[llength $rows] < 1} {
send_message "$channel :Something gone wrong."
} else {
foreach row $rows {
if {$count < $searxconfig(max_results)} {
set row_splitted [csv::split $row]
set title [lindex $row_splitted 0]
set url [lindex $row_splitted 1]
send_message "$channel :$title $url"
incr count
} else {
break
}
}
}
}
proc encode {query} {
set query [regsub -all { } $query "%20"]
set query [regsub -all {&} $query "%26"]
set query [regsub -all {=} $query "%3D"]
set query [regsub -all {!} $query "%21"]
}
proc get_query_results {engine query} {
global searxconfig
set query [encode $query]
set engine [encode $engine]
set url "$searxconfig(website_url)search?q=$query&format=csv&engines=$engine"
## decomment the line below for debugging purposes
# putlog $url
return [exec curl -sS $url]
}
proc get_last_millis { } {
global searxconfig
if {[file exists $searxconfig(file_millis)]} {
set searxconfig(lastmillis) [slurp_file $searxconfig(file_millis)]
} else {
set fp [open $searxconfig(file_millis) w]
puts $fp 0
close $fp
get_last_millis
}
}
proc set_last_millis { } {
global searxconfig
set fp [open $searxconfig(file_millis) w]
puts $fp [clock milliseconds]
close $fp
}
proc search:searxng {nick host hand chan text} {
global searxconfig
if {!([channel get $chan searxng])} {
send_message "$chan :This script has not been authorized to run in this channel."
return 0
}
set millis [clock milliseconds]
get_last_millis
if { [expr $millis - $searxconfig(lastmillis)] > $searxconfig(max_freq) } {
## test antiflood superato
set_last_millis
set text_splitted [split $text " {}"]
set engine [lindex $text_splitted 0]
set text_length [llength $text_splitted]
set query [lrange $text_splitted 1 $text_length]
if {![regexp {^\+} $engine]} {
set engine $searxconfig(default_engine)
set query $text_splitted
} else {
set engine [string range $engine 1 [string length $engine]]
}
if {$query == {}} {
send_message "$chan :Missing search criteria."
} else {
set csv [get_query_results $engine $query]
process_csv $csv $chan
}
return 1;
}
send_message "$chan :Try again later."
return 0
}
putlog "SearXNG Loaded"`