Class String
In: lib/rbot/irc.rb
lib/rbot/ircsocket.rb
lib/rbot/core/utils/extends.rb
lib/rbot/load-gettext.rb
lib/rbot/botuser.rb
Parent: Object
BasicUserMessage JoinMessage NamesMessage WhoisMessage ModeChangeMessage KickMessage MotdMessage QuitMessage BanlistMessage UserMessage NoSuchTargetMessage TopicMessage NickMessage WelcomeMessage UnknownMessage InviteMessage PartMessage NetmaskList UserList ArrayOf ChannelList Netmask User\n[lib/rbot/botuser.rb\nlib/rbot/irc.rb] Channel Singleton RfcCasemap StrictRfcCasemap AsciiCasemap Casemap PrivMessage NoticeMessage TokyoCabinet::BDB CIBDB Btree CIBtree Socket MessageQueue QueueRing Client DBHash\n[lib/rbot/registry/bdb.rb\nlib/rbot/registry/tc.rb] DBTree\n[lib/rbot/registry/bdb.rb\nlib/rbot/registry/tc.rb] Server NetmaskDb Bot\n[lib/rbot/botuser.rb\nlib/rbot/config.rb\nlib/rbot/ircbot.rb\nlib/rbot/language.rb\nlib/rbot/message.rb\nlib/rbot/messagemapper.rb\nlib/rbot/plugins.rb\nlib/rbot/rbotconfig.rb\nlib/rbot/registry/bdb.rb\nlib/rbot/registry/tc.rb] Symbol String\n[lib/rbot/botuser.rb\nlib/rbot/core/utils/extends.rb\nlib/rbot/irc.rb\nlib/rbot/ircsocket.rb\nlib/rbot/load-gettext.rb] lib/rbot/ircsocket.rb lib/rbot/rfc2812.rb lib/rbot/registry/tc.rb lib/rbot/irc.rb lib/rbot/maskdb.rb lib/rbot/message.rb lib/rbot/messagemapper.rb lib/rbot/botuser.rb lib/rbot/registry/tc.rb (null) BotConfig PKGConfig ServerOrCasemap Irc dot/f_32.png

Extension for String class.

String#% method which accept "named argument". The translator can know the meaning of the msgids using "named argument" instead of %s/%d style.

Methods

External Aliases

% -> _old_format_m

Public Instance methods

Format - Uses str as a format specification, and returns the result of applying it to arg. If the format specification contains more than one substitution, then arg must be an Array containing the values to be substituted. See Kernel::sprintf for details of the format string. This is the default behavior of the String class.

  • arg: an Array or other class except Hash.
  • Returns: formatted String
 (e.g.) "%s, %s" % ["Masao", "Mutoh"]

Also you can use a Hash as the "named argument". This is recommanded way for Ruby-GetText because the translators can understand the meanings of the msgids easily.

  • hash: {:key1 => value1, :key2 => value2, … }
  • Returns: formatted String
 (e.g.) "%{firstname}, %{familyname}" % {:firstname => "Masao", :familyname => "Mutoh"}

[Source]

     # File lib/rbot/load-gettext.rb, line 185
185:     def %(args)
186:       if args.kind_of?(Hash)
187:         ret = dup
188:         args.each {|key, value|
189:           ret.gsub!(/\%\{#{key}\}/, value.to_s)
190:         }
191:         ret
192:       else
193:         ret = gsub(/%\{/, '%%{')
194:         begin
195:     ret._old_format_m(args)
196:         rescue ArgumentError
197:     $stderr.puts "  The string:#{ret}"
198:     $stderr.puts "  args:#{args.inspect}"
199:         end
200:       end
201:     end

This method tries to find an HTML title in the string, and returns it if found

[Source]

     # File lib/rbot/core/utils/extends.rb, line 338
338:   def get_html_title
339:     if defined? ::Hpricot
340:       Hpricot(self).at("title").inner_html
341:     else
342:       return unless Irc::Utils::TITLE_REGEX.match(self)
343:       $1
344:     end
345:   end

This method checks if the receiver contains IRC glob characters

IRC has a very primitive concept of globs: a * stands for "any number of arbitrary characters", a ? stands for "one and exactly one arbitrary character". These characters can be escaped by prefixing them with a slash (\).

A known limitation of this glob syntax is that there is no way to escape the escape character itself, so it‘s not possible to build a glob pattern where the escape character precedes a glob.

[Source]

     # File lib/rbot/irc.rb, line 332
332:   def has_irc_glob?
333:     self =~ /^[*?]|[^\\][*?]/
334:   end

This method returns a string which is the downcased version of the receiver, according to the given casemap

[Source]

     # File lib/rbot/irc.rb, line 289
289:   def irc_downcase(casemap='rfc1459')
290:     cmap = casemap.to_irc_casemap
291:     self.tr(cmap.upper, cmap.lower)
292:   end

This is the same as the above, except that the string is altered in place

See also the discussion about irc_downcase

[Source]

     # File lib/rbot/irc.rb, line 298
298:   def irc_downcase!(casemap='rfc1459')
299:     cmap = casemap.to_irc_casemap
300:     self.tr!(cmap.upper, cmap.lower)
301:   end

Calculate the penalty which will be assigned to this message by the IRCd

[Source]

    # File lib/rbot/ircsocket.rb, line 14
14:   def irc_send_penalty
15:     # According to eggdrop, the initial penalty is
16:     penalty = 1 + self.size/100
17:     # on everything but UnderNET where it's
18:     # penalty = 2 + self.size/120
19: 
20:     cmd, pars = self.split($;,2)
21:     debug "cmd: #{cmd}, pars: #{pars.inspect}"
22:     case cmd.to_sym
23:     when :KICK
24:       chan, nick, msg = pars.split
25:       chan = chan.split(',')
26:       nick = nick.split(',')
27:       penalty += nick.size
28:       penalty *= chan.size
29:     when :MODE
30:       chan, modes, argument = pars.split
31:       extra = 0
32:       if modes
33:         extra = 1
34:         if argument
35:           extra += modes.split(/\+|-/).size
36:         else
37:           extra += 3 * modes.split(/\+|-/).size
38:         end
39:       end
40:       if argument
41:         extra += 2 * argument.split.size
42:       end
43:       penalty += extra * chan.split.size
44:     when :TOPIC
45:       penalty += 1
46:       penalty += 2 unless pars.split.size < 2
47:     when :PRIVMSG, :NOTICE
48:       dests = pars.split($;,2).first
49:       penalty += dests.split(',').size
50:     when :WHO
51:       args = pars.split
52:       if args.length > 0
53:         penalty += args.inject(0){ |sum,x| sum += ((x.length > 4) ? 3 : 5) }
54:       else
55:         penalty += 10
56:       end
57:     when :PART
58:       penalty += 4
59:     when :AWAY, :JOIN, :VERSION, :TIME, :TRACE, :WHOIS, :DNS
60:       penalty += 2
61:     when :INVITE, :NICK
62:       penalty += 3
63:     when :ISON
64:       penalty += 1
65:     else # Unknown messages
66:       penalty += 1
67:     end
68:     if penalty > 99
69:       debug "Wow, more than 99 secs of penalty!"
70:       penalty = 99
71:     end
72:     if penalty < 2
73:       debug "Wow, less than 2 secs of penalty!"
74:       penalty = 2
75:     end
76:     debug "penalty: #{penalty}"
77:     return penalty
78:   end

Upcasing functions are provided too

See also the discussion about irc_downcase

[Source]

     # File lib/rbot/irc.rb, line 307
307:   def irc_upcase(casemap='rfc1459')
308:     cmap = casemap.to_irc_casemap
309:     self.tr(cmap.lower, cmap.upper)
310:   end

In-place upcasing

See also the discussion about irc_downcase

[Source]

     # File lib/rbot/irc.rb, line 316
316:   def irc_upcase!(casemap='rfc1459')
317:     cmap = casemap.to_irc_casemap
318:     self.tr!(cmap.lower, cmap.upper)
319:   end

This method will return a purified version of the receiver, with all HTML stripped off and some of it converted to IRC formatting

[Source]

     # File lib/rbot/core/utils/extends.rb, line 214
214:   def ircify_html(opts={})
215:     txt = self.dup
216: 
217:     # remove scripts
218:     txt.gsub!(/<script(?:\s+[^>]*)?>.*?<\/script>/im, "")
219: 
220:     # remove styles
221:     txt.gsub!(/<style(?:\s+[^>]*)?>.*?<\/style>/im, "")
222: 
223:     # bold and strong -> bold
224:     txt.gsub!(/<\/?(?:b|strong)(?:\s+[^>]*)?>/im, "#{Bold}")
225: 
226:     # italic, emphasis and underline -> underline
227:     txt.gsub!(/<\/?(?:i|em|u)(?:\s+[^>]*)?>/im, "#{Underline}")
228: 
229:     ## This would be a nice addition, but the results are horrible
230:     ## Maybe make it configurable?
231:     # txt.gsub!(/<\/?a( [^>]*)?>/, "#{Reverse}")
232:     case val = opts[:a_href]
233:     when Reverse, Bold, Underline
234:       txt.gsub!(/<(?:\/a\s*|a (?:[^>]*\s+)?href\s*=\s*(?:[^>]*\s*)?)>/, val)
235:     when :link_out
236:       # Not good for nested links, but the best we can do without something like hpricot
237:       txt.gsub!(/<a (?:[^>]*\s+)?href\s*=\s*(?:([^"'>][^\s>]*)\s+|"((?:[^"]|\\")*)"|'((?:[^']|\\')*)')(?:[^>]*\s+)?>(.*?)<\/a>/) { |match|
238:         debug match
239:         debug [$1, $2, $3, $4].inspect
240:         link = $1 || $2 || $3
241:         str = $4
242:         str + ": " + link
243:       }
244:     else
245:       warning "unknown :a_href option #{val} passed to ircify_html" if val
246:     end
247: 
248:     # If opts[:img] is defined, it should be a String. Each image
249:     # will be replaced by the string itself, replacing occurrences of
250:     # %{alt} %{dimensions} and %{src} with the alt text, image dimensions
251:     # and URL
252:     if val = opts[:img]
253:       if val.kind_of? String
254:         txt.gsub!(/<img\s+(.*?)\s*\/?>/) do |imgtag|
255:           attrs = Hash.new
256:           imgtag.scan(/([[:alpha:]]+)\s*=\s*(['"])?(.*?)\2/) do |key, quote, value|
257:             k = key.downcase.intern rescue 'junk'
258:             attrs[k] = value
259:           end
260:           attrs[:alt] ||= attrs[:title]
261:           attrs[:width] ||= '...'
262:           attrs[:height] ||= '...'
263:           attrs[:dimensions] ||= "#{attrs[:width]}x#{attrs[:height]}"
264:           val % attrs
265:         end
266:       else
267:         warning ":img option is not a string"
268:       end
269:     end
270: 
271:     # Paragraph and br tags are converted to whitespace
272:     txt.gsub!(/<\/?(p|br)(?:\s+[^>]*)?\s*\/?\s*>/i, ' ')
273:     txt.gsub!("\n", ' ')
274:     txt.gsub!("\r", ' ')
275: 
276:     # Superscripts and subscripts are turned into ^{...} and _{...}
277:     # where the {} are omitted for single characters
278:     txt.gsub!(/<sup>(.*?)<\/sup>/, '^{\1}')
279:     txt.gsub!(/<sub>(.*?)<\/sub>/, '_{\1}')
280:     txt.gsub!(/(^|_)\{(.)\}/, '\1\2')
281: 
282:     # List items are converted to *). We don't have special support for
283:     # nested or ordered lists.
284:     txt.gsub!(/<li>/, ' *) ')
285: 
286:     # All other tags are just removed
287:     txt.gsub!(/<[^>]+>/, '')
288: 
289:     # Convert HTML entities. We do it now to be able to handle stuff
290:     # such as &nbsp;
291:     txt = Utils.decode_html_entities(txt)
292: 
293:     # Keep unbreakable spaces or conver them to plain spaces?
294:     case val = opts[:nbsp]
295:     when :space, ' '
296:       txt.gsub!([160].pack('U'), ' ')
297:     else
298:       warning "unknown :nbsp option #{val} passed to ircify_html" if val
299:     end
300: 
301:     # Remove double formatting options, since they only waste bytes
302:     txt.gsub!(/#{Bold}(\s*)#{Bold}/, '\1')
303:     txt.gsub!(/#{Underline}(\s*)#{Underline}/, '\1')
304: 
305:     # Simplify whitespace that appears on both sides of a formatting option
306:     txt.gsub!(/\s+(#{Bold}|#{Underline})\s+/, ' \1')
307:     txt.sub!(/\s+(#{Bold}|#{Underline})\z/, '\1')
308:     txt.sub!(/\A(#{Bold}|#{Underline})\s+/, '\1')
309: 
310:     # And finally whitespace is squeezed
311:     txt.gsub!(/\s+/, ' ')
312:     txt.strip!
313: 
314:     if opts[:limit] && txt.size > opts[:limit]
315:       txt = txt.slice(0, opts[:limit]) + "#{Reverse}...#{Reverse}"
316:     end
317: 
318:     # Decode entities and strip whitespace
319:     return txt
320:   end

As above, but modify the receiver

[Source]

     # File lib/rbot/core/utils/extends.rb, line 324
324:   def ircify_html!(opts={})
325:     old_hash = self.hash
326:     replace self.ircify_html(opts)
327:     return self unless self.hash == old_hash
328:   end

This method returns the IRC-formatted version of an HTML title found in the string

[Source]

     # File lib/rbot/core/utils/extends.rb, line 349
349:   def ircify_html_title
350:     self.get_html_title.ircify_html rescue nil
351:   end

This method will strip all HTML crud from the receiver

[Source]

     # File lib/rbot/core/utils/extends.rb, line 332
332:   def riphtml
333:     self.gsub(/<[^>]+>/, '').gsub(/&amp;/,'&').gsub(/&quot;/,'"').gsub(/&lt;/,'<').gsub(/&gt;/,'>').gsub(/&ellip;/,'...').gsub(/&apos;/, "'").gsub("\n",'')
334:   end

Returns an Irc::Bot::Auth::Comand from the receiver

[Source]

     # File lib/rbot/botuser.rb, line 119
119:   def to_irc_auth_command
120:     Irc::Bot::Auth::Command.new(self)
121:   end

This method returns the Irc::Casemap whose name is the receiver

[Source]

     # File lib/rbot/irc.rb, line 275
275:   def to_irc_casemap
276:     begin
277:       Irc::Casemap.get(self)
278:     rescue
279:       # raise TypeError, "Unkown Irc::Casemap #{self.inspect}"
280:       error "Unkown Irc::Casemap #{self.inspect} requested, defaulting to rfc1459"
281:       Irc::Casemap.get('rfc1459')
282:     end
283:   end

We keep extending String, this time adding a method that converts a String into an Irc::Channel object

[Source]

      # File lib/rbot/irc.rb, line 1513
1513:   def to_irc_channel(opts={})
1514:     Irc::Channel.new(self, opts)
1515:   end

Returns an Irc::Channel::Topic with self as text

[Source]

      # File lib/rbot/irc.rb, line 1318
1318:   def to_irc_channel_topic
1319:     Irc::Channel::Topic.new(self)
1320:   end

We keep extending String, this time adding a method that converts a String into an Irc::Netmask object

[Source]

     # File lib/rbot/irc.rb, line 915
915:   def to_irc_netmask(opts={})
916:     Irc::Netmask.new(self, opts)
917:   end

This method is used to convert the receiver into a Regular Expression that matches according to the IRC glob syntax

[Source]

     # File lib/rbot/irc.rb, line 339
339:   def to_irc_regexp
340:     regmask = Regexp.escape(self)
341:     regmask.gsub!(/(\\\\)?\\[*?]/) { |m|
342:       case m
343:       when /\\(\\[*?])/
344:         $1
345:       when /\\\*/
346:         '.*'
347:       when /\\\?/
348:         '.'
349:       else
350:         raise "Unexpected match #{m} when converting #{self}"
351:       end
352:     }
353:     Regexp.new("^#{regmask}$")
354:   end

We keep extending String, this time adding a method that converts a String into an Irc::User object

[Source]

      # File lib/rbot/irc.rb, line 1108
1108:   def to_irc_user(opts={})
1109:     Irc::User.new(self, opts)
1110:   end

This method is used to wrap a nonempty String by adding the prefix and postfix

[Source]

     # File lib/rbot/core/utils/extends.rb, line 355
355:   def wrap_nonempty(pre, post, opts={})
356:     if self.empty?
357:       String.new
358:     else
359:       "#{pre}#{self}#{post}"
360:     end
361:   end

[Validate]