| Module | CGI::QueryExtension |
| In: |
lib/cgi.rb
|
Mixin module. It provides the follow functionality groups:
| path | -> | local_path |
Get the value for the parameter with a given key.
If the parameter has multiple values, only the first will be retrieved; use params() to get the array of values.
# File lib/cgi.rb, line 1163
1163: def [](key)
1164: params = @params[key]
1165: value = params[0]
1166: if @multipart
1167: if value
1168: return value
1169: elsif defined? StringIO
1170: StringIO.new("")
1171: else
1172: Tempfile.new("CGI")
1173: end
1174: else
1175: str = if value then value.dup else "" end
1176: str.extend(Value)
1177: str.set_params(params)
1178: str
1179: end
1180: end
Returns true if a given parameter key exists in the query.
# File lib/cgi.rb, line 1188
1188: def has_key?(*args)
1189: @params.has_key?(*args)
1190: end
Get the raw cookies as a string.
# File lib/cgi.rb, line 945
945: def raw_cookie
946: env_table["HTTP_COOKIE"]
947: end
Get the raw RFC2965 cookies as a string.
# File lib/cgi.rb, line 950
950: def raw_cookie2
951: env_table["HTTP_COOKIE2"]
952: end
Initialize the data from the query.
Handles multipart forms (in particular, forms that involve file uploads). Reads query parameters in the @params field, and cookies into @cookies.
# File lib/cgi.rb, line 1103
1103: def initialize_query()
1104: if ("POST" == env_table['REQUEST_METHOD']) and
1105: %r|\Amultipart/form-data.*boundary=\"?([^\";,]+)\"?|n.match(env_table['CONTENT_TYPE'])
1106: boundary = $1.dup
1107: @multipart = true
1108: @params = read_multipart(boundary, Integer(env_table['CONTENT_LENGTH']))
1109: else
1110: @multipart = false
1111: @params = CGI::parse(
1112: case env_table['REQUEST_METHOD']
1113: when "GET", "HEAD"
1114: if defined?(MOD_RUBY)
1115: Apache::request.args or ""
1116: else
1117: env_table['QUERY_STRING'] or ""
1118: end
1119: when "POST"
1120: stdinput.binmode if defined? stdinput.binmode
1121: stdinput.read(Integer(env_table['CONTENT_LENGTH'])) or ''
1122: else
1123: read_from_cmdline
1124: end
1125: )
1126: end
1127:
1128: @cookies = CGI::Cookie::parse((env_table['HTTP_COOKIE'] or env_table['COOKIE']))
1129: end
offline mode. read name=value pairs on standard input.
# File lib/cgi.rb, line 1075
1075: def read_from_cmdline
1076: require "shellwords"
1077:
1078: string = unless ARGV.empty?
1079: ARGV.join(' ')
1080: else
1081: if STDIN.tty?
1082: STDERR.print(
1083: %|(offline mode: enter name=value pairs on standard input)\n|
1084: )
1085: end
1086: readlines.join(' ').gsub(/\n/n, '')
1087: end.gsub(/\\=/n, '%3D').gsub(/\\&/n, '%26')
1088:
1089: words = Shellwords.shellwords(string)
1090:
1091: if words.find{|x| /=/n.match(x) }
1092: words.join('&')
1093: else
1094: words.join('+')
1095: end
1096: end
# File lib/cgi.rb, line 967
967: def read_multipart(boundary, content_length)
968: params = Hash.new([])
969: boundary = "--" + boundary
970: quoted_boundary = Regexp.quote(boundary, "n")
971: buf = ""
972: bufsize = 10 * 1024
973: boundary_end=""
974:
975: # start multipart/form-data
976: stdinput.binmode if defined? stdinput.binmode
977: boundary_size = boundary.size + EOL.size
978: content_length -= boundary_size
979: status = stdinput.read(boundary_size)
980: if nil == status
981: raise EOFError, "no content body"
982: elsif boundary + EOL != status
983: raise EOFError, "bad content body"
984: end
985:
986: loop do
987: head = nil
988: if 10240 < content_length
989: require "tempfile"
990: body = Tempfile.new("CGI")
991: else
992: begin
993: require "stringio"
994: body = StringIO.new
995: rescue LoadError
996: require "tempfile"
997: body = Tempfile.new("CGI")
998: end
999: end
1000: body.binmode if defined? body.binmode
1001:
1002: until head and /#{quoted_boundary}(?:#{EOL}|--)/n.match(buf)
1003:
1004: if (not head) and /#{EOL}#{EOL}/n.match(buf)
1005: buf = buf.sub(/\A((?:.|\n)*?#{EOL})#{EOL}/n) do
1006: head = $1.dup
1007: ""
1008: end
1009: next
1010: end
1011:
1012: if head and ( (EOL + boundary + EOL).size < buf.size )
1013: body.print buf[0 ... (buf.size - (EOL + boundary + EOL).size)]
1014: buf[0 ... (buf.size - (EOL + boundary + EOL).size)] = ""
1015: end
1016:
1017: c = if bufsize < content_length
1018: stdinput.read(bufsize)
1019: else
1020: stdinput.read(content_length)
1021: end
1022: if c.nil? || c.empty?
1023: raise EOFError, "bad content body"
1024: end
1025: buf.concat(c)
1026: content_length -= c.size
1027: end
1028:
1029: buf = buf.sub(/\A((?:.|\n)*?)(?:[\r\n]{1,2})?#{quoted_boundary}([\r\n]{1,2}|--)/n) do
1030: body.print $1
1031: if "--" == $2
1032: content_length = -1
1033: end
1034: boundary_end = $2.dup
1035: ""
1036: end
1037:
1038: body.rewind
1039:
1040: /Content-Disposition:.* filename="?([^\";]*)"?/ni.match(head)
1041: filename = ($1 or "")
1042: if /Mac/ni.match(env_table['HTTP_USER_AGENT']) and
1043: /Mozilla/ni.match(env_table['HTTP_USER_AGENT']) and
1044: (not /MSIE/ni.match(env_table['HTTP_USER_AGENT']))
1045: filename = CGI::unescape(filename)
1046: end
1047:
1048: /Content-Type: (.*)/ni.match(head)
1049: content_type = ($1 or "")
1050:
1051: (class << body; self; end).class_eval do
1052: alias local_path path
1053: define_method(:original_filename) {filename.dup.taint}
1054: define_method(:content_type) {content_type.dup.taint}
1055: end
1056:
1057: /Content-Disposition:.* name="?([^\";]*)"?/ni.match(head)
1058: name = $1.dup
1059:
1060: if params.has_key?(name)
1061: params[name].push(body)
1062: else
1063: params[name] = [body]
1064: end
1065: break if buf.size == 0
1066: break if content_length === -1
1067: end
1068: raise EOFError, "bad boundary end of body part" unless boundary_end=~/--/
1069:
1070: params
1071: end