Guest User

Untitled

a guest
Jan 23rd, 2018
66
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
text 13.04 KB | None | 0 0
  1. #-- vim:sw=2:et
  2. #++
  3. #
  4. # :title: Quotes plugin
  5. #
  6. # TODO:: switch to db
  7.  
  8. define_structure :Quote, :num, :date, :source, :quote
  9.  
  10. class QuotePlugin < Plugin
  11. def dirname
  12. 'quotes'
  13. end
  14.  
  15. def initialize
  16. super
  17. @lists = Hash.new
  18. @changed = Hash.new
  19. Dir[datafile('*')].each {|f|
  20. next if File.directory?(f)
  21. channel = File.basename(f)
  22. @lists[channel] = Array.new if(!@lists.has_key?(channel))
  23. IO.foreach(f) {|line|
  24. if(line =~ /^(\d+) \| ([^|]+) \| (\S+) \| (.*)$/)
  25. num = $1.to_i
  26. @lists[channel][num] = Quote.new(num, $2, $3, $4)
  27. end
  28. }
  29. @changed[channel] = false
  30. }
  31.  
  32. @registry['timedb'] = Hash.new
  33. @registry['spamdb'] = Hash.new
  34. end
  35.  
  36. def save
  37. Dir.mkdir(datafile) unless FileTest.directory? datafile
  38. @lists.each {|channel, quotes|
  39. begin
  40. if @changed[channel]
  41. debug "Writing new quotefile for channel #{channel} ..."
  42. Utils.safe_save(datafile(channel)) {|file|
  43. quotes.compact.each {|q|
  44. file.puts "#{q.num} | #{q.date} | #{q.source} | #{q.quote}"
  45. }
  46. }
  47. @changed[channel] = false
  48. else
  49. debug "Not writing quotefile for channel #{channel} (unchanged)"
  50. end
  51. rescue => e
  52. error "failed to write quotefile for channel #{channel}!\n#{$!}"
  53. error "#{e.class}: #{e}"
  54. error e.backtrace.join("\n")
  55. end
  56. }
  57. end
  58.  
  59. def cleanup
  60. @lists.clear
  61. @changed.clear
  62. super
  63. end
  64.  
  65. def lastquote(channel)
  66. @lists[channel].length-1
  67. end
  68.  
  69. def addquote(source, channel, quote)
  70. @lists[channel] = Array.new if(!@lists.has_key?(channel))
  71. num = @lists[channel].length
  72. @lists[channel][num] = Quote.new(num, Time.new, source.fullform, quote)
  73. @changed[channel] = true
  74. #system("/home/andy/.rbot/quotes/quotes.rb")
  75. return num
  76. end
  77.  
  78. def getquote(source, channel, num=nil)
  79. return nil unless(@lists.has_key?(channel))
  80. return nil unless(@lists[channel].length > 0)
  81. if(num)
  82. if(@lists[channel][num])
  83. return @lists[channel][num], @lists[channel].length - 1
  84. end
  85. else
  86. # random quote
  87. return @lists[channel].compact.pick_one,
  88. @lists[channel].length - 1
  89. end
  90. end
  91.  
  92. def delquote(channel, num)
  93. return false unless(@lists.has_key?(channel))
  94. return false unless(@lists[channel].length > 0)
  95. if(@lists[channel][num])
  96. @lists[channel][num] = nil
  97. @lists[channel].pop if num == @lists[channel].length - 1
  98. @changed[channel] = true
  99. #system("/home/andy/.rbot/quotes/quotes.rb")
  100. return true
  101. end
  102. #system("/home/andy/.rbot/quotes/quotes.rb")
  103. return false
  104. end
  105.  
  106. def countquote(source, channel=nil, regexp=nil)
  107. unless(channel)
  108. total=0
  109. @lists.each_value {|l|
  110. total += l.compact.length
  111. }
  112. return total
  113. end
  114. return 0 unless(@lists.has_key?(channel))
  115. return 0 unless(@lists[channel].length > 0)
  116. if(regexp)
  117. matches = @lists[channel].compact.find_all {|a| a.quote =~ /#{regexp}/i }
  118. else
  119. matches = @lists[channel].compact
  120. end
  121. return matches.length
  122. end
  123.  
  124. def searchquote(source, channel, regexp)
  125. return nil unless(@lists.has_key?(channel))
  126. return nil unless(@lists[channel].length > 0)
  127. matches = @lists[channel].compact.find_all {|a| a.quote =~ /#{regexp}/i }
  128. if(matches.length > 0)
  129. return matches[rand(matches.length)], @lists[channel].length - 1
  130. else
  131. return nil
  132. end
  133. end
  134.  
  135. def submittedby(source, channel, regexp)
  136. return nil unless(@lists.has_key?(channel))
  137. return nil unless(@lists[channel].length > 0)
  138. matches = @lists[channel].compact.find_all {|a| a.quote =~ /#{regexp}/i }
  139. if(matches.length > 0)
  140. return matches[rand(matches.length)], @lists[channel].length - 1
  141. else
  142. return nil
  143. end
  144. end
  145.  
  146. def listquotes(source, channel, regexp)
  147. return nil unless(@lists.has_key?(channel))
  148. return nil unless(@lists[channel].length > 0)
  149. matches = @lists[channel].compact.find_all {|a| a.quote =~ /#{regexp}/i }
  150. if matches.length > 0
  151. return matches
  152. else
  153. return nil
  154. end
  155. end
  156.  
  157. def help(plugin, topic="")
  158. case plugin
  159. when "addquote"
  160. _("addquote [<channel>] <quote> => Add quote <quote> for channel <channel>. You only need to supply <channel> if you are addressing %{nick} privately.") % { :nick => @bot.nick }
  161. when "delquote"
  162. _("delquote [<channel>] <num> => delete quote from <channel> with number <num>. You only need to supply <channel> if you are addressing %{nick} privately.") % { :nick => @bot.nick }
  163. when "quote"
  164. _("quote [<channel>] [<num>] => get quote from <channel> with number <num>. You only need to supply <channel> if you are addressing %{nick} privately. Without <num>, a random quote will be returned.") % { :nick => @bot.nick }
  165. when "search"
  166. _("search [<channel>] <regexp> => list the quotes from <channel> that match <regexp>. You only need to supply <channel> if you are addressing %{nick} privately.") % { :nick => @bot.nick }
  167. when "whoquote"
  168. _("whoquote [<channel>] <num> => show who added quote <num>. You only need to supply <channel> if you are addressing %{nick} privately") % { :nick => @bot.nick }
  169. when "whenquote"
  170. _("whenquote [<channel>] <num> => show when quote <num> was added. You only need to supply <channel> if you are addressing %{nick} privately") % { :nick => @bot.nick }
  171. else
  172. _("Quote module (Quote storage and retrieval) topics: addquote, delquote, quote, search, whoquote, whenquote") % { :nick => @bot.nick }
  173. end
  174. end
  175.  
  176. def cmd_addquote(m, p)
  177. userhost = m.source.host
  178. unless m.source.botuser.permit? "quotes::override"
  179. if @registry['timedb'][userhost].to_i == 0
  180. blah = @registry['timedb']
  181. blah[userhost] = Time.now
  182. @registry['timedb'] = blah
  183. else
  184. unless Time.now.to_i - @registry['timedb'][userhost].to_i > 3600
  185. m.reply "You have already added a quote this hour."
  186. return
  187. else
  188. blah = @registry['timedb']
  189. blah[userhost] = Time.now
  190. @registry['timedb'] = blah
  191. end
  192. end
  193. end
  194. channel = p[:channel] || m.channel.to_s
  195. quote = p[:quote].to_s
  196. num = addquote(m.source, channel, quote)
  197. m.reply _("added the quote (#%{num})") % { :num => num }
  198. end
  199.  
  200. def cmd_delquote(m, p)
  201. channel = p[:channel] || m.channel.to_s
  202. num = p[:num].to_i
  203. if delquote(channel, num)
  204. m.okay
  205. else
  206. m.reply _("quote not found!")
  207. end
  208. end
  209.  
  210. def cmd_getquote(m, p)
  211. userhost = m.source.host
  212. # unless m.source.botuser.permit? "quotes::override"
  213. unless @registry['spamdb'].has_key?(userhost)
  214. blah = @registry['spamdb']
  215. blah[userhost] = {"count" => 0, "time" => 0}
  216. @registry['spamdb'] = blah
  217. end
  218. if @registry['spamdb'][userhost]['count'] >= 3 or m.private?
  219. blah = @registry['spamdb']
  220. if blah[userhost]["time"] > Time.now.to_i and blah[userhost]["time"] != 0
  221. @bot.notice m.sourcenick, "Flood controlled! Wait 60 seconds."
  222. return
  223. else
  224. blah = @registry['spamdb']
  225. blah[userhost] = {"count" => 0, "time" => 0}
  226. @registry['spamdb'] = blah
  227. end
  228. else
  229. blah = @registry['spamdb']
  230. if blah[userhost]["time"] < Time.now.to_i
  231. blah[userhost]["count"] = 0
  232. end
  233. blah[userhost] = {"count" => blah[userhost]["count"] + 1, "time" => Time.now.to_i + 60}
  234. @registry['spamdb'] = blah
  235. end
  236. #end
  237. channel = p[:channel] || m.channel.to_s
  238. num = p[:num] ? p[:num].to_i : nil
  239. quote, total = getquote(m.source, channel, num)
  240. if quote
  241. m.reply _("[%{num}] %{quote}") % {
  242. :num => quote.num,
  243. :quote => quote.quote
  244. }
  245. else
  246. m.reply _("quote not found!")
  247. end
  248. end
  249.  
  250. def cmd_whoquote(m, p)
  251. channel = p[:channel] || m.channel.to_s
  252. num = p[:num] ? p[:num].to_i : nil
  253. quote, total = getquote(m.source, channel, num)
  254. if quote
  255. m.reply _("quote %{num} added by %{source}") % {
  256. :num => quote.num,
  257. :source => quote.source
  258. }
  259. else
  260. m.reply _("quote not found!")
  261. end
  262. end
  263.  
  264. def cmd_whenquote(m, p)
  265. channel = p[:channel] || m.channel.to_s
  266. num = p[:num] ? p[:num].to_i : nil
  267. quote, total = getquote(m.source, channel, num)
  268. if quote
  269. m.reply _("quote %{num} added on %{date}") % {
  270. :num => quote.num,
  271. :date => quote.date
  272. }
  273. else
  274. m.reply _("quote not found!")
  275. end
  276. end
  277.  
  278. def cmd_searchquote(m, p)
  279. channel = p[:channel] || m.channel.to_s
  280. reg = p[:reg].to_s
  281. quote, total = searchquote(m.source, channel, reg)
  282. if quote
  283. m.reply _("[%{num}] %{quote}") % {
  284. :num => quote.num,
  285. :quote => quote.quote
  286. }
  287. else
  288. m.reply _("quote not found!")
  289. end
  290. end
  291.  
  292. def cmd_submittedby(m, p)
  293. channel = p[:channel] || m.channel.to_s
  294. reg = p[:reg].to_s
  295. quote, total = submittedby(m.source, channel, reg)
  296. if quote
  297. m.reply _("[%{num}] %{submitquote}"} % {
  298. :num => quote.num
  299. :submitquote => quote.submitquote
  300. }
  301. else
  302. m.replay _("no quotes from _ found!")
  303. end
  304. end
  305.  
  306. def cmd_listquotes(m, p)
  307. channel = p[:channel] || m.channel.to_s
  308. reg = p[:reg].to_s
  309. if quotes = listquotes(m.source, channel, reg)
  310. m.reply _("%{total} quotes matching %{reg} found: %{list}") % {
  311. :total => quotes.size,
  312. :reg => reg,
  313. :list => quotes.map {|q| q.num }.join(', ')
  314. }
  315. else
  316. m.reply _("quote not found!")
  317. end
  318. end
  319.  
  320. def cmd_countquote(m, p)
  321. channel = p[:channel] || m.channel.to_s
  322. reg = p[:reg] ? p[:reg].to_s : nil
  323. total = countquote(m.source, channel, reg)
  324. if reg.length > 0
  325. m.reply _("%{total} quotes matching %{reg}") % {
  326. :total => total,
  327. :reg => reg
  328. }
  329. else
  330. m.reply _("%{total} quotes") % { :total => total }
  331. end
  332. end
  333.  
  334. def cmd_topicquote(m, p)
  335. channel = p[:channel] || m.channel.to_s
  336. num = p[:num] ? p[:num].to_i : nil
  337. quote, total = getquote(m.source, channel, num)
  338. if quote
  339. @bot.topic channel, _("[%{num}] %{quote}") % {
  340. :num => quote.num,
  341. :quote => quote.quote
  342. }
  343. else
  344. m.reply _("quote not found!")
  345. end
  346. end
  347.  
  348. def cmd_lastquote(m, p)
  349. channel = p[:channel] || m.channel.to_s
  350. quote, total = getquote(m.source, channel, lastquote(channel))
  351. if quote
  352. m.reply _("[%{num}] %{quote}") % {
  353. :num => quote.num,
  354. :quote => quote.quote
  355. }
  356. else
  357. m.reply _("quote not found!")
  358. end
  359. end
  360. end
  361.  
  362. plugin = QuotePlugin.new
  363. plugin.register("quotes")
  364.  
  365. plugin.default_auth('other::edit', false) # Prevent random people from editing other channels quote lists by default
  366. plugin.default_auth('other::view', true) # But allow them to view them
  367. plugin.default_auth('override', false)
  368.  
  369. plugin.map "addquote :channel *quote", :action => :cmd_addquote, :requirements => { :channel => Regexp::Irc::GEN_CHAN }, :auth_path => '!quote::other::edit::add!'
  370. plugin.map "delquote :channel :num", :action => :cmd_delquote, :requirements => { :channel => Regexp::Irc::GEN_CHAN, :num => /^\d+$/ }, :auth_path => '!quote::other::edit::del!'
  371. plugin.map "quote :channel [:num]", :action => :cmd_getquote, :requirements => { :channel => Regexp::Irc::GEN_CHAN, :num => /^\d+$/ }, :auth_path => '!quote::other::view::get!'
  372. plugin.map "whoquote :channel :num", :action => :cmd_whoquote, :requirements => { :channel => Regexp::Irc::GEN_CHAN, :num => /^\d+$/ }, :auth_path => '!quote::other::view::who!'
  373. plugin.map "whenquote :channel :num", :action => :cmd_whenquote, :requirements => { :channel => Regexp::Irc::GEN_CHAN, :num => /^\d+$/ }, :auth_path => '!quote::other::view::when!'
  374. plugin.map "search :channel *reg", :action => :cmd_listquotes, :requirements => { :channel => Regexp::Irc::GEN_CHAN }, :auth_path => '!quote::other::view::list!'
  375. plugin.map "lastquote", :action => :cmd_lastquote, :thread => true
  376. plugin.default_auth('edit', false) # Prevent random people from removing quotes
  377. plugin.default_auth('edit::add', true) # But allow them to add them
  378.  
  379. plugin.map "addquote *quote", :action => :cmd_addquote, :private => false, :auth_path => '!quote::edit::add!'
  380. plugin.map "delquote :num", :action => :cmd_delquote, :private => false, :requirements => { :num => /^\d+$/ }, :auth_path => '!quote::edit::del!'
  381. plugin.map "quote [:num]", :action => :cmd_getquote, :private => false, :requirements => { :num => /^\d+$/ }, :auth_path => '!quote::view::get!'
  382. plugin.map "whoquote :num", :action => :cmd_whoquote, :private => false, :requirements => { :num => /^\d+$/ }, :auth_path => '!quote::view::who!'
  383. plugin.map "whenquote :num", :action => :cmd_whenquote, :private => false, :requirements => { :num => /^\d+$/ }, :auth_path => '!quote::view::when!'
  384. plugin.map "search *reg", :action => :cmd_listquotes, :private => false, :auth_path => '!quote::view::list!'
Add Comment
Please, Sign In to add comment