blackidle.tcl

blackidle.tcl

This is an unique idle script designed to implement effectively the idle kick/ban. The script allows users who have been kicked for staying idle to unban themselves (if they are in-front of the PC)

Postat de Copyright Categorie Review user Vizualizari Data
btc Simeon Simeonov protections Cod netestat 358 2023-12-24 23:20:10

###############################################INFO###########################################
## Blackmore's BlackIdle 1.0 beta
# Written by: Simeon Simeonov (Blackmore)
# Release date: 10.01.2002
##

## About this script: This is an unique idle script designed to implement effectively the idle kick/ban.
# There are so many idle kick/ban scripts. Why use this one?
# Scripts that simply kick idle users from the channel are absolutely pointless. The idle user can
# simply switch on the auto-rejoin option on his/her IRC client (most IRC clients have this option).
# Scripts that intend to ban idle users are also not complete. Let's imagine that the user is not really idle.
# Once the user realizes that he/she is banned. He/She will try to message the chanops and ask them to be
# unbanned. The point with the idle scripts is to kick/ban users who are not in front of the PC at all such as bots
# or simply users who want to make advantage of some statistic counts in the channel or just logs
# everything said in the channel (I know lots of those).
# This script allows the user to unban him/herself after being banned. The user can not unban him/herself if
# the reason for being banned is not idling. The script works that way:
# When some user is banned, he/she receive the following message: You have been
# banned from #channel for staying idle more then <some time> minutes. If you are
# online and want to re-enter the channel type: /msg TheBot unban <random password> . Otherwise
# you will be automatically unbanned in <some time> minutes."
# The random password is a 4-digit number and it's different for each idle ban.
# 
# The script allows users who have been kicked for staying idle to unban themselves (if they are in-front of the PC)
# Why random password? This prevents (makes it difficult) users from setting up a script which unbans automatically.


## Installation: I will not attempt to teach you how to use eggdrop. If you are not familiar with eggdrop
# visit http://www.egghelp.org
# Copy this file to your script directory (usually scripts/) and add the following line to your configuration file:
# source scripts/blackidle.tcl
# Now you can start your bot. If it is already running you must rehash it (.rehash)
#

## About me:
# If you have some questions or ideas how to make this script better, you can direct them to: blackmore@windows-sucks.com
#
##
##############################################################################################


##
# Blackmore's BlackIdle 1.1 beta
# Mod Written by: XeNoGear (i-Spires.net)
# Release Date: 31.05.2003
##

## -= Added function =-
# Network Services protection. This prevents the bot from kicking/banning the network services.
# Able to add in many nicks. [Not Case-Sensitive]
#

## -= Enchanced the unban mode. (Bug Fixed) =-
# Fix the bug by checking all the passwords and bans first whether both matches to any of the bans
# before issuing the msg.
#

## -= Enchanced the kick message =-
# (idea taken and copy from mc.antiidle.tcl by MC_8 - Carl M. Gregory <mc8@purehype.net>)
# Enable the kick message to use variables like %channel %idletime %bantime %nick
#
# This enchancement makes the kick message easier to manage. =)
##

#########################################CONFIGURATION#########################################
# Channels you want the script to monitor (separated by space).
# N.B The bot *MUST* be present in each specified channel.
set channels {#pichove #testcho}

# Idletime in minutes. If the user stays idle longer then the idletime, he/she will be banned/kicked.
set idletime 120

# How long will the bot wait (in minutes) before removing the ban automatically.
set bantime 30

# Global flag protection. Users with that global flag will not be kicked/banned
# N.B You can use *ONLY* 1 flag.
set protected_gflag "o"

# Channel flag protection. Users with that channel flag will not be kicked/banned
# N.B You can use *ONLY* 1 flag.
set protected_cflag "o"

# Network Services protection. Network services that should not be kicked/banned (separated by space)
# Set to "" for none which means will kicked/banned ALL users regardless of status.
# N.B If your network service is X, you can either put X or x. [Not Case-Sensitive]
set protected_services "q Q2"

# The kick message which will be displayed in the channel when the user is kicked out.
# Need not put a space in between the words and variables:
# %idletime mins | %idletimemins ==> 30 mins | 30mins (both are acceptable)
# Replacement variables:
#		%channel  = The channel in which the user is in.
#		%idletime = The max. idle time the user exceeded.
#		%bantime  = The time which the ban will last.
#		%user     = IRC nickname of the user thats in violation of idle.
set reason "%user been idling for more than %idletimemins and will be auto unban in %bantimemins at %channel."

# Allow unban. Allows the user to unban him/herself the random password. 0 = no, 1 = yes.
# If you set this to 0, there is no point for you to use this script.
# N.B The user can't unban him/herself if he/she is not banned 'cause of this script. So don't worry :)
set allow_unban 1


######################## CODE STARTS HERE ( Do not edit above this line if you are not familiar with TCL) ###########################

timer 1 pr_main
timer 2 pr_random
set flood 0
set rnd_pass 1324
bind msg - unban pr_unban

proc pr_main {} {
	
	global channels
	global idletime
	global bantime
	global protected_gflag
	global protected_cflag
	global protected_services
	global rnd_pass
	global reason
	global botnick

	foreach chan $channels {
		if {([botonchan $chan] == 1) && [isop $botnick $chan]} {
			foreach user [chanlist $chan] {
				if {[isbotnick $user] == 0} {
					set proservices 0
					if {$protected_services != ""} {
						foreach services [string tolower $protected_services] {
							set users "[string tolower $user]"
							if {[string match "$users" "$services"]} {
								set proservices 1
							}
						}
					}
					if {$proservices == 0} {
						set ch [getchanidle $user $chan]
	                                	if {$ch >= $idletime} {
							set han [nick2hand $user $chan]
							set message [pr_replace -- $reason [list %channel   $chan \
												 %bantime   $bantime \
												 %idletime  $idletime \
												 %user      $user]]
							if {$han == "*"} {
	          						set hst [getchanhost $user $chan]
	                                                        set bmask "*!$hst"
	                                                        newchanban $chan $bmask $rnd_pass $message $bantime
	                                                        putserv "KICK $chan $user :$message"
								puthelp "PRIVMSG $user :You have been banned from $chan for staying idle more then $idletime minutes. If are online and want to re-enter the channel type: /msg $botnick unban $rnd_pass . Otherwise you will be automaticly unbanned in $bantime minutes."
							} else {
								set str_gflag [chattr $han]
								set str_cflag [chattr $han $chan]
								set tmp [split $str_cflag "|"]
								set str_cflag [lindex $tmp 1]
								set trigger 0
								for {set i 0} {$i < [string length $str_gflag]} {incr i 1} {
									if {$protected_gflag == [string index $str_gflag $i]} {
										set trigger 1
									}
								}
								for {set i 0} {$i < [string length $str_cflag]} {incr i 1} {
	                                                                if {$protected_cflag == [string index $str_cflag $i]} {
	                                                                        set trigger 1
	                                                                }
								}

								if {$trigger == 0} {
									set hst [getchanhost $user $chan]
									set bmask "*!$hst"
									newchanban $chan $bmask $rnd_pass $message $bantime
	          							putserv "KICK $chan $user :$message"
									puthelp "PRIVMSG $user :You have been banned from $chan for staying idle more then $idletime minutes. If are online and wish to re-enter the channel type: /msg $botnick unban $rnd_pass . Otherwise you will be automaticly unbanned in $bantime minutes."
								}
							}
						}
					}
				}
			}
		} elseif {(![isop $botnick $chan])} {
			putlog ""
			putlog "*** $botnick is not OP on $chan."
			putlog "*** Unable to activate idling script."
			putlog ""
		} 
	}
timer 1 pr_main
}

proc pr_random {} {
	global rnd_pass
	set rnd_pass [expr [rand 9000] + 1000]
	timer 2 pr_random
}


proc pr_unban { nick uhost handle arg } {
	global channels
	global allow_unban
	if {$allow_unban == 1} {
		if {[string length $arg] == 4} {
			set password 0
			set host 0
			set check 0
			foreach chan $channels {
				foreach ban [banlist $chan] {
	                        	set bmask "*!$uhost"
					set bpass [string range $ban [expr [string length $ban] - 4] end]
					set bhost [string range $ban 0 [expr [string length $bmask] - 1]]

					if {[string match "$arg" "$bpass"] && [string match "$bmask" "$bhost"]} {
						killchanban $chan $bmask
						puthelp "PRIVMSG $nick :You can now re-enter the channel."
						set check 1
					} elseif {([string match "$arg" "$bpass"] && (![string match "$bmask" "$bhost"]))} {
						set password 1
					} elseif {((![string match "$arg" "$bpass"]) && [string match "$bmask" "$bhost"])} {
						set host 1
					}
				}
			}
			if {$check == 0} {
				if {$password == 1} {
					puthelp "PRIVMSG $nick :Nice try! It won't work that way"
                               	} elseif {$host == 1} {
					puthelp "PRIVMSG $nick :Wrong password. Try again!"
				}
			}
		}
	} else {
		puthelp "PRIVMSG $nick :Unban is turned off. Sorry!"
	}	
}


## More Tools quick procs.
## -- http://mc.purehype.net:81/script_info.tcl?script=moretools

# badargs <args> <min_llength> <max_llength|end> <argNames>
#     version:
#       v1.0
proc pr_badargs {{args ""}} {
	if {[llength $args] < 4} {
		error {
			wrong # args: should be "pr_badargs args min_llength max_llength argNames"
		}
	}

	set index 0
	foreach varName [list args min max names] {
		set check_$varName [lindex $args $index]
		incr index
	}

	if {[regexp -- {([^0-9])} $check_min -> bad]} {
		error "bad number \"$bad\" in: $check_min"
	}
	if {[regexp -- {([^0-9])} $check_max -> bad] && ($check_max != "end")} {
		error "bad number \"$bad\" in: $check_max"
	}

	# Make sure $check_args is in list format, if not then make it so.
	# Were not going to use 2list here, don't want to evoke a 'too many nested calls
	# to Tcl_EvalObj' error since '2list' uses on this proc.
	if {[catch {llength $check_args} llength]} {
		set check_args [split $check_args]
		set llength $check_args
	}

	if {($llength < $check_min) || (($llength != "end") && ($llength > $check_max))} {
		if {[info level] == "1"} {return 1}
		error "wrong # args: should be \"[lindex [info level -1] 0] $check_names\""
	}; return 0
}

# 2list <text>
#     version:
#       v1.0
proc pr_2list {{args ""}} {
	pr_badargs $args 1 1 "text"
	pr_unlist $args text

	return [expr {([catch {llength $text}])?[split $text]:$text}]
}

# unlist <argsList> [varName1] [varName2] ... [varNameN]
#     version:
#       v1.0
proc pr_unlist {{args ""}} {
	pr_badargs $args 1 end "argsList ?varName varName ...?"
	set argList [lindex $args 0]
	set argList [expr {([catch {llength $argList}])?[split $argList]:$argList}]
	set argNames [lrange $args 1 end]
	if {![llength $argNames]} {
		return [expr {(![catch {llength $argList}])?
			[join $argList]:$argList}]
	}
	for {set index 0} {$index < [llength $argNames]} {incr index 1} {
		set argName     [lindex $argNames $index]
		set argListItem [lindex $argList  $index]

		set argName_ [expr {([catch {llength $argName}])?[split $argName]:$argName}]
		set setTo   [lindex $argName_ 1]
		set argName [lindex $argName_ 0]

		if {$argName == ""} {continue}

		upvar 1 $argName var

		if {[expr $index+1] > [llength $argList]} {
			if {[llength $argName_] == "2"} {set var $setTo}
		} else {
			if {$argName == "args"} {
				set var [lrange $argList $index end]
				incr index [expr [llength $var]-1]
			} else {set var $argListItem}
		}
	}; return $index
}

# replace [switches] <text> <substitutions>
#     version:
#       v1.3
proc pr_replace {{args ""}} {
	pr_badargs $args 2 4 "?switches? text substitutions"
	set switches ""
	for {set i 0} {[string match -* [set arg [lindex $args $i]]]} {incr i} {
		if {![regexp -- {^-(nocase|-)$} $arg -> switch]} {
			error "bad switch \"$arg\": must be -nocase, or --"
		}
		if {$switch == "-"} {
			incr i
			break
		}; lappend switches $switch
	}
	set nocase [expr {([lsearch -exact $switches "nocase"] >= "0") ? 1 : 0}]
	set text [lindex $args $i]
	set substitutions [lindex $args [expr $i+1]]
	pr_badargs [lrange $args $i end] 2 2 "?switches? text substitutions"

	# Check to see if $substitutions is in list format, if not make it so.
	set substitutions [pr_2list $substitutions]

	if {[info tclversion] >= "8.1"} {
		return [expr {($nocase)?
			[string map -nocase $substitutions $text]:
			[string map $substitutions $text]}]
	}

	set re_syntax {([][\\\*\+\?\{\}\,\(\)\:\.\^\$\=\!\|])}
	foreach {a b} $substitutions {
		regsub -all -- $re_syntax $a {\\\1} a
		if {$nocase} {regsub -all -nocase -- $a $text $b text} \
		else {regsub -all -- $a $text $b text}
	}; return $text
}

## End of More Tools quick procs.


putlog "BlackIdle 1.1 beta"