| 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 1174
1174: def [](key)
1175: params = @params[key]
1176: return '' unless params
1177: value = params[0]
1178: if @multipart
1179: if value
1180: return value
1181: elsif defined? StringIO
1182: StringIO.new("")
1183: else
1184: Tempfile.new("CGI")
1185: end
1186: else
1187: str = if value then value.dup else "" end
1188: str.extend(Value)
1189: str.set_params(params)
1190: str
1191: end
1192: end
Returns true if a given parameter key exists in the query.
# File lib/cgi.rb, line 1200
1200: def has_key?(*args)
1201: @params.has_key?(*args)
1202: end
Get the raw cookies as a string.
# File lib/cgi.rb, line 951
951: def raw_cookie
952: env_table["HTTP_COOKIE"]
953: end
Get the raw RFC2965 cookies as a string.
# File lib/cgi.rb, line 956
956: def raw_cookie2
957: env_table["HTTP_COOKIE2"]
958: 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 1114
1114: def initialize_query()
1115: if ("POST" == env_table['REQUEST_METHOD']) and
1116: %r|\Amultipart/form-data.*boundary=\"?([^\";,]+)\"?|n.match(env_table['CONTENT_TYPE'])
1117: boundary = $1.dup
1118: @multipart = true
1119: @params = read_multipart(boundary, Integer(env_table['CONTENT_LENGTH']))
1120: else
1121: @multipart = false
1122: @params = CGI::parse(
1123: case env_table['REQUEST_METHOD']
1124: when "GET", "HEAD"
1125: if defined?(MOD_RUBY)
1126: Apache::request.args or ""
1127: else
1128: env_table['QUERY_STRING'] or ""
1129: end
1130: when "POST"
1131: stdinput.binmode if defined? stdinput.binmode
1132: stdinput.read(Integer(env_table['CONTENT_LENGTH'])) or ''
1133: else
1134: read_from_cmdline
1135: end
1136: )
1137: end
1138:
1139: @cookies = CGI::Cookie::parse((env_table['HTTP_COOKIE'] or env_table['COOKIE']))
1140: end
offline mode. read name=value pairs on standard input.
# File lib/cgi.rb, line 1081
1081: def read_from_cmdline
1082: require "shellwords"
1083:
1084: string = unless ARGV.empty?
1085: ARGV.join(' ')
1086: else
1087: if STDIN.tty?
1088: STDERR.print(
1089: %|(offline mode: enter name=value pairs on standard input)\n|
1090: )
1091: end
1092: array = readlines rescue nil
1093: if not array.nil?
1094: array.join(' ').gsub(/\n/n, '')
1095: else
1096: ""
1097: end
1098: end.gsub(/\\=/n, '%3D').gsub(/\\&/n, '%26')
1099:
1100: words = Shellwords.shellwords(string)
1101:
1102: if words.find{|x| /=/n.match(x) }
1103: words.join('&')
1104: else
1105: words.join('+')
1106: end
1107: end
# File lib/cgi.rb, line 973
973: def read_multipart(boundary, content_length)
974: params = Hash.new([])
975: boundary = "--" + boundary
976: quoted_boundary = Regexp.quote(boundary, "n")
977: buf = ""
978: bufsize = 10 * 1024
979: boundary_end=""
980:
981: # start multipart/form-data
982: stdinput.binmode if defined? stdinput.binmode
983: boundary_size = boundary.size + EOL.size
984: content_length -= boundary_size
985: status = stdinput.read(boundary_size)
986: if nil == status
987: raise EOFError, "no content body"
988: elsif boundary + EOL != status
989: raise EOFError, "bad content body"
990: end
991:
992: loop do
993: head = nil
994: if 10240 < content_length
995: require "tempfile"
996: body = Tempfile.new("CGI")
997: else
998: begin
999: require "stringio"
1000: body = StringIO.new
1001: rescue LoadError
1002: require "tempfile"
1003: body = Tempfile.new("CGI")
1004: end
1005: end
1006: body.binmode if defined? body.binmode
1007:
1008: until head and /#{quoted_boundary}(?:#{EOL}|--)/n.match(buf)
1009:
1010: if (not head) and /#{EOL}#{EOL}/n.match(buf)
1011: buf = buf.sub(/\A((?:.|\n)*?#{EOL})#{EOL}/n) do
1012: head = $1.dup
1013: ""
1014: end
1015: next
1016: end
1017:
1018: if head and ( (EOL + boundary + EOL).size < buf.size )
1019: body.print buf[0 ... (buf.size - (EOL + boundary + EOL).size)]
1020: buf[0 ... (buf.size - (EOL + boundary + EOL).size)] = ""
1021: end
1022:
1023: c = if bufsize < content_length
1024: stdinput.read(bufsize)
1025: else
1026: stdinput.read(content_length)
1027: end
1028: if c.nil? || c.empty?
1029: raise EOFError, "bad content body"
1030: end
1031: buf.concat(c)
1032: content_length -= c.size
1033: end
1034:
1035: buf = buf.sub(/\A((?:.|\n)*?)(?:[\r\n]{1,2})?#{quoted_boundary}([\r\n]{1,2}|--)/n) do
1036: body.print $1
1037: if "--" == $2
1038: content_length = -1
1039: end
1040: boundary_end = $2.dup
1041: ""
1042: end
1043:
1044: body.rewind
1045:
1046: /Content-Disposition:.* filename=(?:"((?:\\.|[^\"])*)"|([^;\s]*))/ni.match(head)
1047: filename = ($1 or $2 or "")
1048: if /Mac/ni.match(env_table['HTTP_USER_AGENT']) and
1049: /Mozilla/ni.match(env_table['HTTP_USER_AGENT']) and
1050: (not /MSIE/ni.match(env_table['HTTP_USER_AGENT']))
1051: filename = CGI::unescape(filename)
1052: end
1053:
1054: /Content-Type: ([^\s]*)/ni.match(head)
1055: content_type = ($1 or "")
1056:
1057: (class << body; self; end).class_eval do
1058: alias local_path path
1059: define_method(:original_filename) {filename.dup.taint}
1060: define_method(:content_type) {content_type.dup.taint}
1061: end
1062:
1063: /Content-Disposition:.* name="?([^\";\s]*)"?/ni.match(head)
1064: name = $1.dup
1065:
1066: if params.has_key?(name)
1067: params[name].push(body)
1068: else
1069: params[name] = [body]
1070: end
1071: break if buf.size == 0
1072: break if content_length == -1
1073: end
1074: raise EOFError, "bad boundary end of body part" unless boundary_end=~/--/
1075:
1076: params
1077: end