]> git.netwichtig.de Git - user/henk/code/ruby/rbot.git/blob - data/rbot/plugins/dict.rb
d486e97b3c3c292b90530afbc785ce8907b238d7
[user/henk/code/ruby/rbot.git] / data / rbot / plugins / dict.rb
1 #-- vim:sw=2:et\r
2 #++\r
3 #\r
4 # :title: Dictionary lookup plugin for rbot\r
5 #\r
6 # Author:: Giuseppe "Oblomov" Bilotta <giuseppe.bilotta@gmail.com>\r
7 # Copyright:: (C) 2006-2007 Giuseppe Bilotta\r
8 # License:: GPL v2\r
9 #\r
10 # Provides a link to the definition of a word in one of the supported\r
11 # dictionaries. Currently available are\r
12 #   * the Oxford dictionary for (British) English\r
13 #   * the De Mauro/Paravia dictionary for Italian\r
14 #   * the Chambers dictionary for English (accepts both US and UK)\r
15 #\r
16 # Other plugins can use this one to check if a given word is valid in italian\r
17 # or english by using the is_italian?/is_british?/is_english? methods\r
18 #\r
19 # TODO: cache results and reuse them if get_cached returns a cache copy\r
20 \r
21 require 'uri'\r
22 \r
23 DEMAURO_LEMMA = /<anchor>(.*?)(?: - (.*?))<go href="lemma.php\?ID=(\d+)"\/><\/anchor>/\r
24 \r
25 class DictPlugin < Plugin\r
26   BotConfig.register BotConfigIntegerValue.new('dict.hits',\r
27     :default => 3,\r
28     :desc => "Number of hits to return from a dictionary lookup")\r
29   BotConfig.register BotConfigIntegerValue.new('dict.first_par',\r
30     :default => 0,\r
31     :desc => "When set to n > 0, the bot will return the first paragraph from the first n dictionary hits")\r
32 \r
33   def initialize\r
34     super\r
35     @dmurl = "http://www.demauroparavia.it/"\r
36     @dmwapurl = "http://wap.demauroparavia.it/index.php?lemma=%s"\r
37     @dmwaplemma = "http://wap.demauroparavia.it/lemma.php?ID=%s"\r
38     @oxurl = "http://www.askoxford.com/concise_oed/%s"\r
39     @chambersurl = "http://www.chambersharrap.co.uk/chambers/features/chref/chref.py/main?query=%s&title=21st"\r
40   end\r
41 \r
42 \r
43   def help(plugin, topic="")\r
44     case topic\r
45     when "demauro"\r
46       return "demauro <word> => provides a link to the definition of <word> from the De Mauro/Paravia dictionary"\r
47     when "oxford"\r
48       return "oxford <word> => provides a link to the definition of <word> (it can also be an expression) from the Concise Oxford dictionary"\r
49     when "chambers"\r
50       return "chambers <word> => provides a link to the definition of <word> (it can also be an expression) from the Chambers 21st Century Dictionary"\r
51     end\r
52     return "<dictionary> <word>: check for <word> on <dictionary> where <dictionary> can be one of: demauro, oxford, chambers"\r
53   end\r
54 \r
55   def demauro(m, params)\r
56     justcheck = params[:justcheck]\r
57 \r
58     word = params[:word].downcase\r
59     url = @dmwapurl % URI.escape(word)\r
60     xml = nil\r
61     info = @bot.httputil.get_response(url) rescue nil\r
62     xml = info.body if info\r
63     if xml.nil?\r
64       info = info ? " (#{info.code} - #{info.message})" : ""\r
65       return false if justcheck\r
66       m.reply "An error occurred while looking for #{word}#{info}"\r
67       return\r
68     end\r
69     if xml=~ /Non ho trovato occorrenze per/\r
70       return false if justcheck\r
71       m.reply "Nothing found for #{word}"\r
72       return\r
73     end\r
74     entries = xml.scan(DEMAURO_LEMMA)\r
75     text = word\r
76     urls = []\r
77     if !entries.assoc(word) and !entries.assoc(word.upcase)\r
78       return false if justcheck\r
79       text += " not found. Similar words"\r
80     end\r
81     return true if justcheck\r
82     text += ": "\r
83     n = 0\r
84     hits = @bot.config['dict.hits']\r
85     text += entries[0...hits].map { |ar|\r
86       n += 1\r
87       urls << @dmwaplemma % ar[2]\r
88       "#{n}. #{Bold}#{ar[0]}#{Bold} - #{ar[1].gsub(/<\/?em>/,'')}: #{@dmurl}#{ar[2]}"\r
89     }.join(" | ")\r
90     m.reply text\r
91 \r
92     first_pars = @bot.config['dict.first_par']\r
93 \r
94     return unless first_pars > 0\r
95 \r
96     Utils.get_first_pars urls, first_pars, :message => m,\r
97       :strip => /^\S+\s+-\s+/\r
98 \r
99   end\r
100 \r
101   def is_italian?(word)\r
102     return demauro(nil, :word => word, :justcheck => true)\r
103   end\r
104 \r
105 \r
106   def oxford(m, params)\r
107     justcheck = params[:justcheck]\r
108 \r
109     word = params[:word].join\r
110     [word, word + "_1"].each { |check|\r
111       url = @oxurl % URI.escape(check)\r
112       h = @bot.httputil.head(url, :max_redir => 5)\r
113       if h\r
114         m.reply("#{word} found: #{url}") unless justcheck\r
115         return true\r
116       end\r
117     }\r
118     return false if justcheck\r
119     m.reply "#{word} not found"\r
120   end\r
121 \r
122   def is_british?(word)\r
123     return oxford(nil, :word => word, :justcheck => true)\r
124   end\r
125 \r
126 \r
127   def chambers(m, params)\r
128     justcheck = params[:justcheck]\r
129 \r
130     word = params[:word].to_s.downcase\r
131     url = @chambersurl % URI.escape(word)\r
132     xml = nil\r
133     info = @bot.httputil.get_response(url) rescue nil\r
134     xml = info.body if info\r
135     case xml\r
136     when nil\r
137       info = info ? " (#{info.code} - #{info.message})" : ""\r
138       return false if justcheck\r
139       m.reply "An error occurred while looking for #{word}#{info}"\r
140       return\r
141     when /Sorry, no entries for <b>.*?<\/b> were found./\r
142       return false if justcheck\r
143       m.reply "Nothing found for #{word}"\r
144       return\r
145     when /No exact matches for <b>.*?<\/b>, but the following may be helpful./\r
146       return false if justcheck\r
147       m.reply "Nothing found for #{word}, but see #{url} for possible suggestions"\r
148     else\r
149       return true if justcheck\r
150       m.reply "#{word}: #{url}"\r
151     end\r
152   end\r
153 \r
154   def is_english?(word)\r
155     return chambers(nil, :word => word, :justcheck => true)\r
156   end\r
157 \r
158 end\r
159 \r
160 plugin = DictPlugin.new\r
161 plugin.map 'demauro :word', :action => 'demauro'\r
162 plugin.map 'oxford *word', :action => 'oxford'\r
163 plugin.map 'chambers *word', :action => 'chambers'\r
164 \r