super-test 1.0.9

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (108) hide show
  1. checksums.yaml +7 -0
  2. data/CHANGE.txt +9 -0
  3. data/README.txt +13 -0
  4. data/bin/idb +19 -0
  5. data/bin/ii +113 -0
  6. data/bin/istart_mock +36 -0
  7. data/bin/istop_mock +16 -0
  8. data/bin/kk +181 -0
  9. data/bin/rubyatp +42 -0
  10. data/bin/start_mock +36 -0
  11. data/bin/stop_mock +16 -0
  12. data/bin/xgo +45 -0
  13. data/conf/conf.rb +11 -0
  14. data/conf/db03.yml +31 -0
  15. data/conf/db13.yml +37 -0
  16. data/conf/db19.yml +33 -0
  17. data/conf/online.yml +32 -0
  18. data/conf/super_test.yml +40 -0
  19. data/conf/system.yml +26 -0
  20. data/conf/sz00.yml +31 -0
  21. data/conf/sz06.yml +34 -0
  22. data/conf/wise00.yml +11 -0
  23. data/data/case.house +0 -0
  24. data/data/char.house +0 -0
  25. data/data/images/Bluehills.jpg +0 -0
  26. data/data/images/Sunset.jpg +0 -0
  27. data/data/images/Waterlilies.jpg +0 -0
  28. data/data/images/Winter.jpg +0 -0
  29. data/data/query.house +18595 -0
  30. data/data/user.house +8 -0
  31. data/lib/action/module/check_action.rb +58 -0
  32. data/lib/action/module/cnnt_action.rb +161 -0
  33. data/lib/action/module/datacenter_action.rb +48 -0
  34. data/lib/action/module/http_pack_helper.rb +163 -0
  35. data/lib/action/module/httpserver_action.rb +297 -0
  36. data/lib/action/module/inc.rb +21 -0
  37. data/lib/action/module/mcpack_action.rb +57 -0
  38. data/lib/action/module/sql_action.rb +84 -0
  39. data/lib/action/module/ssh_action.rb +37 -0
  40. data/lib/action/system/user_action.rb +180 -0
  41. data/lib/common/appium_helper.rb +217 -0
  42. data/lib/common/atp_helper.rb +74 -0
  43. data/lib/common/atp_report.rb +344 -0
  44. data/lib/common/data_house.rb +405 -0
  45. data/lib/common/data_model.rb +87 -0
  46. data/lib/common/http/assert_helper.rb +343 -0
  47. data/lib/common/http/fix_hpricot.rb +118 -0
  48. data/lib/common/http/html_helper.rb +362 -0
  49. data/lib/common/http/http_helper.rb +469 -0
  50. data/lib/common/http/multipart.rb +81 -0
  51. data/lib/common/isandbox_helper.rb +195 -0
  52. data/lib/common/json_helper.rb +43 -0
  53. data/lib/common/mock_helper.rb +168 -0
  54. data/lib/common/mtop_helper.rb +141 -0
  55. data/lib/common/myconf_helper.rb +49 -0
  56. data/lib/common/mylog_helper.rb +77 -0
  57. data/lib/common/pairwise.rb +121 -0
  58. data/lib/common/query_house.rb +89 -0
  59. data/lib/common/report_helper.rb +97 -0
  60. data/lib/common/robot_helper.rb +85 -0
  61. data/lib/common/socket/check.rb +325 -0
  62. data/lib/common/socket/conf_modifier.rb +149 -0
  63. data/lib/common/socket/context.rb +55 -0
  64. data/lib/common/socket/data.rb +392 -0
  65. data/lib/common/socket/data_helper.rb +41 -0
  66. data/lib/common/socket/env.rb +317 -0
  67. data/lib/common/socket/inc.rb +24 -0
  68. data/lib/common/socket/log.rb +213 -0
  69. data/lib/common/socket/log4s.rb +58 -0
  70. data/lib/common/socket/log_helper.rb +332 -0
  71. data/lib/common/socket/my_sql.rb +77 -0
  72. data/lib/common/socket/net.rb +74 -0
  73. data/lib/common/socket/network.rb +115 -0
  74. data/lib/common/socket/rlib/conf_modifier.rb +130 -0
  75. data/lib/common/socket/rlib/data_helper.rb +33 -0
  76. data/lib/common/socket/rlib/log_helper.rb +303 -0
  77. data/lib/common/socket/rlib/process_helper.rb +91 -0
  78. data/lib/common/socket/stub.rb +276 -0
  79. data/lib/common/socket/util.rb +266 -0
  80. data/lib/patterns/inc.rb +10 -0
  81. data/lib/patterns/mc_base_pattern.rb +474 -0
  82. data/lib/patterns/some_pattern.rb +145 -0
  83. data/lib/super_test.rb +114 -0
  84. data/log/super_test.log +0 -0
  85. data/log/super_test.log.wf +0 -0
  86. data/test/cover_me.rb +6 -0
  87. data/tool/jenny +0 -0
  88. data/tool/mcsend/mcsend2 +0 -0
  89. data/tool/mcsend/mcsend2_shead +0 -0
  90. data/tool/mcserver/conf/mcserver.conf +77 -0
  91. data/tool/mcserver/conf/mcserverauthip +17 -0
  92. data/tool/mcserver/mcserver +0 -0
  93. data/tool/mcserver/mcserver_trans +0 -0
  94. data/tool/mysql +0 -0
  95. data/tool/net/mcsend/mcsend +0 -0
  96. data/tool/net/mcsend/mcsend_trans +0 -0
  97. data/tool/net/mcsend/nshead.data +7 -0
  98. data/tool/net/mcsend/res_nshead.data +7 -0
  99. data/tool/net/my_client/my_client +0 -0
  100. data/tool/net/tsclient/client.tcl +205 -0
  101. data/tool/others/kk +190 -0
  102. data/tool/others/rubyatp +42 -0
  103. data/tool/others/supertest_install.sh +34 -0
  104. data/tool/trip/idb +0 -0
  105. data/tool/ts-agent/nshead.bft +12 -0
  106. data/tool/ts-agent/server.conf +10 -0
  107. data/tool/ts-agent/server.tcl +376 -0
  108. metadata +275 -0
@@ -0,0 +1,8 @@
1
+ - name: hanyu
2
+ pasw: ll
3
+ - name: lfsjlaf
4
+ type: his
5
+ - name: ruguo
6
+ password: aaaa
7
+ spaceurl: ruguo32
8
+ tag : slfs
@@ -0,0 +1,58 @@
1
+ #!/usr/bin/env ruby
2
+ # coding: utf-8
3
+ $LOAD_PATH << File.join(File.dirname(__FILE__), '.')
4
+
5
+ module CheckActionHelper
6
+ include MylogHelper
7
+
8
+ # === 功能
9
+ # IOHEAD的正则匹配
10
+ #
11
+ # === 参数
12
+ # - pattern 正则式
13
+ #
14
+ # Example
15
+ # assert_head "log_id:10"
16
+ def assert_head pattern
17
+ assert_match(pattern, Context.get("IOHEAD"), "IOHEAD mismatch")
18
+ puts "AssertOK IOHEAD #{pattern}"
19
+ $log.info "AssertOK IOHEAD #{pattern}"
20
+ end
21
+
22
+ # === 功能
23
+ # IOBODY的正则匹配
24
+ #
25
+ # === 参数
26
+ # - pattern 正则式
27
+ #
28
+ # Example
29
+ # assert_body "a.*b.*c"
30
+ def assert_body pattern
31
+ assert_match(pattern, Context.get("IOBODY"), "IOBODY mismatch")
32
+ puts "AssertOK IOBODY #{pattern}"
33
+ $log.info "AssertOK IOBODY #{pattern}"
34
+ end
35
+
36
+ # === 检查是否存在core文件
37
+ #
38
+ # === 参数
39
+ # - host 机器
40
+ #
41
+ # === Example:
42
+ # core_check
43
+ def core_check host=HOST, user=USERNAME, password=PASSWORD
44
+ if Util.is_localhost? (host) then
45
+ ret = system "file ~/*.core"
46
+ else
47
+ ret = Util.exe_ssh_cmd! host, "file ~/*.core", user, password
48
+ end
49
+ Context.set("IOBODY", ret)
50
+ assert_body("cannot open")
51
+ $log.info "core_check"
52
+ end
53
+
54
+
55
+ end
56
+
57
+
58
+
@@ -0,0 +1,161 @@
1
+ #!/usr/bin/env ruby
2
+ # coding: utf-8
3
+ $LOAD_PATH << File.join(File.dirname(__FILE__), '.')
4
+
5
+ require 'socket'
6
+
7
+
8
+ module CNNTActionHelper
9
+ include Socket::Constants
10
+
11
+ # === 建立连接 用于长连接操作
12
+ #
13
+ # === 参数
14
+ # - ip
15
+ # - port
16
+ #
17
+ # === 返回
18
+ # socekt 句柄
19
+ #
20
+ # === Example:
21
+ # socket = cnnt_connect 127.0.0.1, 1900
22
+ def cnnt_connect ip, port
23
+ socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
24
+ sockaddr = Socket.pack_sockaddr_in( port, ip )
25
+ socket.connect( sockaddr )
26
+ return socket
27
+ end
28
+
29
+ # === 发送数据 用于长连接操作
30
+ #
31
+ # === 参数
32
+ # socket 用于发送的socket句柄
33
+ # cont 发送的内容
34
+ #
35
+ # === 返回
36
+ # 发送的数据长度
37
+ #
38
+ # === Example
39
+ # cnnt_send socket, "dddd"
40
+ def cnnt_send socket, cont
41
+ socket.send cont, 0
42
+ end
43
+
44
+ # === 关闭连接 用于长连接操作
45
+ #
46
+ # === 参数
47
+ # socket 用于操作的socket句柄
48
+ #
49
+ # === Example
50
+ # cnnt_close socket
51
+ def cnnt_close socket
52
+ socket.close
53
+ end
54
+
55
+ # === 发送一次数据 用于短连接操作
56
+ #
57
+ # === 参数
58
+ # ip ip
59
+ # port 端口
60
+ # cont 要发送的内容
61
+ #
62
+ # === 返回
63
+ # 发送的数据长度
64
+ #
65
+ # === Example
66
+ # cnnt_short_send "127.0.0.1", 1900, "dddd"
67
+ def cnnt_direct_send ip, port, cont
68
+ socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
69
+ sockaddr = Socket.pack_sockaddr_in( port, ip )
70
+ socket.connect( sockaddr )
71
+ ret = socket.send cont, 0
72
+ socket.close
73
+ return ret
74
+ end
75
+
76
+ # === 创建一个server 处理部分需要用户自己完成
77
+ # 该server可以接收多线程的连接
78
+ #
79
+ # === 参数
80
+ # port 端口
81
+ # yield 处理函数
82
+ #
83
+ # === 返回
84
+ # 服务器线程句柄
85
+ #
86
+ # === Example
87
+ # a1 = cnnt_create_server(1999) {|client|
88
+ # data = client.recvfrom(200)[0]
89
+ # if data.length>0
90
+ # p data
91
+ # end
92
+ #}
93
+ def cnnt_create_server port
94
+ svr_t = Thread.new {
95
+ socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
96
+ sockaddr = Socket.pack_sockaddr_in( port, 'localhost' )
97
+ socket.bind( sockaddr )
98
+ socket.listen( 5 )
99
+ loop do
100
+ client, client_sockaddr = socket.accept
101
+ Thread.new{
102
+ loop do
103
+ yield client
104
+ end
105
+ }
106
+ end
107
+ socket.close
108
+ }
109
+ return svr_t
110
+ end
111
+
112
+ # === 创建一个server 接收到的数据被放到cont数组中
113
+ # 该函数仅支持一个线程的连接请求
114
+ #
115
+ # === 参数
116
+ # port 端口
117
+ # cont 接收数据用的数组
118
+ #
119
+ # === 返回
120
+ # 服务器线程句柄
121
+ #
122
+ # === Example
123
+ # cont=[]
124
+ # cnnt_create_practical_server 1999, cont
125
+ # cnnt_direct_send "127.0.0.1", 1999, "dddd"
126
+ # p cont[0]
127
+ def cnnt_create_practical_server port, cont
128
+ svr_t = Thread.new {
129
+ socket = Socket.new( AF_INET, SOCK_STREAM, 0 )
130
+ sockaddr = Socket.pack_sockaddr_in( port, 'localhost' )
131
+ socket.bind( sockaddr )
132
+ socket.listen( 5 )
133
+ client, client_sockaddr = socket.accept
134
+ loop do
135
+ cont << client.recvfrom(1024)[0]
136
+ end
137
+ socket.close
138
+ }
139
+ return svr_t
140
+ end
141
+
142
+ # === 停止服务线程
143
+ #
144
+ # === 参数
145
+ # svr 服务器线程句柄
146
+ #
147
+ # === Example
148
+ # cnnt_stop_server svr
149
+ def cnnt_stop_server svr
150
+ svr.exit
151
+ end
152
+
153
+
154
+ end
155
+
156
+
157
+
158
+ if __FILE__ == $0
159
+ end
160
+
161
+
@@ -0,0 +1,48 @@
1
+ #!/usr/bin/env ruby
2
+ # coding: utf-8
3
+ $LOAD_PATH << File.join(File.dirname(__FILE__), '.')
4
+
5
+
6
+ module DataCenterActionHelper
7
+
8
+ # 功能
9
+ # 对模块进行基线数据的恢复
10
+ #
11
+ # Example
12
+ =begin
13
+ mdl_friend = ModuleHouse.get_instance.get_by_name "friend"
14
+ datacenter = DCHouse.get_instance.get_by_name "datacenter"
15
+ new_conf = {
16
+ "adr"=>datacenter["host"],
17
+ "username"=>datacenter["db01"]["dbuser"],
18
+ "port"=>datacenter["db01"]["dbport"],
19
+ "passwd"=>datacenter["db01"]["dbpass"],
20
+ "dbname"=>mdl_friend["dbname"],
21
+ "dbport"=>datacenter["db01"]["dbport"]
22
+ }
23
+ MoudleHouse.get_instance.set_new_conf(mdl_friend, new_conf)
24
+ module_prepare datacenter, mdl_friend
25
+ =end
26
+ def module_prepare datacenter, mdl
27
+ if mdl["recoversql"] == 1
28
+ if mdl["dbversion"] == "5.1.30"
29
+ ssh_cmd datacenter["host"], datacenter["user"], datacenter["pass"], "#{datacenter["db01"]["dbpath"]}/bin/mysql -u#{datacenter["db01"]["dbuser"]} -p#{datacenter["db01"]["dbpass"]} #{mdl["dbname"]} < #{datacenter["datacenterpath"]}/#{mdl["basesql"]}"
30
+ end
31
+ if mdl["dbversion"] == "5.22"
32
+ ssh_cmd datacenter["host"], datacenter["user"], datacenter["pass"], "#{datacenter["db02"]["dbpath"]}/bin/mysql -u#{datacenter["db02"]["dbuser"]} -p#{datacenter["db02"]["dbpass"]} #{mdl["dbname"]} < #{datacenter["datacenterpath"]}/#{mdl["basesql"]}"
33
+ end
34
+ end
35
+ if mdl["recoverdata"] == 1
36
+ ssh_cmd datacenter["host"], datacenter["user"], datacenter["pass"], "H #{mdl["h_name"]} -pub #{datacenter["datacenterpath"]}/#{mdl["basedata"]} #{datacenter["datadownloadto"]}"
37
+ end
38
+ end
39
+
40
+
41
+ end
42
+
43
+
44
+
45
+ #if __FILE__ =
46
+ #end
47
+
48
+
@@ -0,0 +1,163 @@
1
+ #!/usr/bin/env ruby
2
+ # coding: utf-8
3
+ #
4
+ # Author:: wangkaihua.
5
+ # Date:: 2009.12.18
6
+
7
+ require 'webrick'
8
+
9
+ class HttpRequest < WEBrick::HTTPRequest
10
+ attr_reader :io, :config
11
+
12
+ def initialize(io)
13
+ @io=io
14
+ @config={
15
+ :RequestTimeout =>30,
16
+ :InputBufferSize =>65536,
17
+ :HTTPVersion =>WEBrick::HTTPVersion.new("1.1"),
18
+ :Logger =>WEBrick::Log.new,
19
+ :Escape8bitURI =>false,
20
+ :ServerSoftware =>"Ruby HttpServer 1.0"
21
+ }
22
+ super(@config)
23
+ parse(io)
24
+ end
25
+
26
+ def content
27
+ query
28
+ end
29
+ end
30
+
31
+ class HttpResponse
32
+ attr_reader :header
33
+ attr_accessor :body, :status, :status_message
34
+
35
+ def initialize(status=200)
36
+ @status = status
37
+ @status_message = nil
38
+ @header = Table.new
39
+ end
40
+
41
+ def charset
42
+ return nil if @header["Content-Type"]==nil
43
+ charset_array=@header["Content-Type"].scan(/charset=([^; ]*)/)[0]
44
+ return nil if charset_array==nil
45
+ return charset_array[0]
46
+ end
47
+
48
+ def to_http_pack(status_code=nil, status_message=nil, header=nil, body=nil)
49
+ _status_code_=(status_code==nil) ? @status : status_code
50
+ _status_message_=(status_message==nil) ? StatusCodeMapping[_status_code_] : status_message
51
+ _header_=(header==nil) ? @header : header
52
+ _body_=(body==nil) ? @body : body
53
+
54
+ # _status_message_ ||= StatusCodeMapping[_status_code_]
55
+
56
+ #encoding body.
57
+ unless _body_.nil?
58
+ if charset==nil
59
+ _body_=_body_.force_encoding("gbk")
60
+ else
61
+ encod=charset.downcase
62
+ if encod=="gbk" or encod=="gb2312"
63
+ _body_=_body_.force_encoding("gbk")
64
+ else
65
+ _body_=_body_.force_encoding("gbk").encode(encod)
66
+ end
67
+ end
68
+ end
69
+
70
+ #to pack.
71
+ http_pack = ""
72
+ http_pack << "#{HTTP_PROTO} #{_status_code_} #{_status_message_}" << CRLF
73
+ http_header(_header_, _body_).writeTo(http_pack)
74
+ http_pack << CRLF
75
+
76
+ http_pack << _body_ unless _body_.nil?
77
+ http_pack
78
+ end
79
+
80
+
81
+ private
82
+ # Helper Methods ------------------------------------------
83
+
84
+ def http_header(header=nil, body=nil)
85
+ new_header = Table.new(DEFAULT_HEADER)
86
+
87
+ #auto modify content-length.
88
+ new_header["Content-Length"] = "0"
89
+ new_header["Content-Length"] = body.bytesize unless body == nil
90
+ new_header["Connection"] = "close"
91
+ new_header["Date"] = http_date(Time.now)
92
+
93
+ new_header.update(header) unless header.nil?
94
+ new_header
95
+ end
96
+
97
+ def http_date( aTime )
98
+ aTime.gmtime.strftime( "%a, %d %b %Y %H:%M:%S GMT" )
99
+ end
100
+
101
+
102
+ end
103
+
104
+ # Constants -----------------------------------------------
105
+
106
+ CRLF = "\r\n"
107
+ HTTP_PROTO = "HTTP/1.0"
108
+ SERVER_NAME = "HttpServer (Ruby #{RUBY_VERSION})"
109
+
110
+ DEFAULT_HEADER = {
111
+ "Server" => SERVER_NAME
112
+ }
113
+
114
+ ##
115
+ # Mapping of status code and error message
116
+ #
117
+ StatusCodeMapping = {
118
+ 200 => "OK",
119
+ 400 => "Bad Request",
120
+ 403 => "Forbidden",
121
+ 405 => "Method Not Allowed",
122
+ 411 => "Length Required",
123
+ 500 => "Internal Server Error"
124
+ }
125
+
126
+ ##
127
+ # a case-insensitive Hash class for HTTP header
128
+ #
129
+ class Table
130
+ include Enumerable
131
+
132
+ def initialize(hash={})
133
+ @hash = hash
134
+ update(hash)
135
+ end
136
+
137
+ def [](key)
138
+ # @hash[key.to_s.capitalize]
139
+ @hash[key.to_s]
140
+ end
141
+
142
+ def []=(key, value)
143
+ #@hash[key.to_s.capitalize] = value
144
+ @hash[key.to_s] = value
145
+ end
146
+
147
+ def update(hash)
148
+ hash.each {|k,v| self[k] = v}
149
+ self
150
+ end
151
+
152
+ def each
153
+ #@hash.each {|k,v| yield k.capitalize, v }
154
+ @hash.each {|k,v| yield k, v }
155
+ end
156
+
157
+ def writeTo(port)
158
+ each { |k,v|
159
+ port << "#{k}: #{v}" << CRLF
160
+ }
161
+ end
162
+ end # class Table
163
+
@@ -0,0 +1,297 @@
1
+ #!/usr/bin/env ruby
2
+ # coding: utf-8
3
+ #
4
+ # Author:: wangkaihua.
5
+ # Date:: Wed Dec 16 22:21:34 CST 2009
6
+
7
+ ##to-do-list:
8
+ ##
9
+ ##
10
+
11
+ require "socket"
12
+ require "thread"
13
+ require "#{File.dirname(__FILE__)}/http_pack_helper"
14
+
15
+
16
+ module HttpServerActionHelper
17
+
18
+ class GeneralServer
19
+
20
+ DEFAULT_HOST = "127.0.0.1"
21
+
22
+ def serve(io)
23
+ yield if block_given?
24
+ end
25
+
26
+ @@services = {} # Hash of opened ports, i.e. services
27
+ @@servicesMutex = Mutex.new
28
+
29
+ def GeneralServer.stop(port, host = DEFAULT_HOST)
30
+ @@servicesMutex.synchronize {
31
+ @@services[host][port].stop
32
+ }
33
+ end
34
+
35
+ def GeneralServer.in_service?(port, host = DEFAULT_HOST)
36
+ @@services.has_key?(host) and
37
+ @@services[host].has_key?(port)
38
+ end
39
+
40
+ def stop
41
+ @connectionsMutex.synchronize {
42
+ if @tcpServerThread
43
+ @tcpServerThread.raise "stop"
44
+ end
45
+ }
46
+ @tcpServerThread.join
47
+ end
48
+
49
+ def stopped?
50
+ @tcpServerThread == nil
51
+ end
52
+
53
+ def shutdown
54
+ @shutdown = true
55
+ end
56
+
57
+ def connections
58
+ @connections.size
59
+ end
60
+
61
+ def join
62
+ @tcpServerThread.join if @tcpServerThread
63
+ end
64
+
65
+ attr_reader :port, :host, :maxConnections
66
+ attr_accessor :stdlog, :audit, :debug
67
+
68
+ def connecting(client)
69
+ addr = client.peeraddr
70
+ log("#{self.class.to_s} #{@host}:#{@port} client:#{addr[1]} " +
71
+ "#{addr[2]}<#{addr[3]}> connect")
72
+ true
73
+ end
74
+
75
+ def disconnecting(clientPort)
76
+ log("#{self.class.to_s} #{@host}:#{@port} " +
77
+ "client:#{clientPort} disconnect")
78
+ end
79
+
80
+ protected :connecting, :disconnecting
81
+
82
+ def starting()
83
+ log("#{self.class.to_s} #{@host}:#{@port} start")
84
+ end
85
+
86
+ def stopping()
87
+ log("#{self.class.to_s} #{@host}:#{@port} stop")
88
+ end
89
+
90
+ protected :starting, :stopping
91
+
92
+ def error(detail)
93
+ log(detail.backtrace.join("\n"))
94
+ end
95
+
96
+ def log(msg)
97
+ if @stdlog
98
+ @stdlog.puts("[#{Time.new.ctime}] %s" % msg)
99
+ @stdlog.flush
100
+ end
101
+ end
102
+
103
+ protected :error, :log
104
+
105
+
106
+ def initialize(port, host = DEFAULT_HOST, maxConnections = 4,
107
+ stdlog = $stderr, audit = false, debug = false)
108
+ @tcpServerThread = nil
109
+ @port = port
110
+ @host = host
111
+ @maxConnections = maxConnections
112
+ @connections = []
113
+ @connectionsMutex = Mutex.new
114
+ @connectionsCV = ConditionVariable.new
115
+ @stdlog = stdlog
116
+ @audit = audit
117
+ @debug = debug
118
+ end
119
+
120
+ def start(maxConnections = -1, &blk)
121
+ raise "running" if !stopped?
122
+ @shutdown = false
123
+ @maxConnections = maxConnections if maxConnections > 0
124
+ @@servicesMutex.synchronize {
125
+ if GeneralServer.in_service?(@port,@host)
126
+ raise "Port already in use: #{host}:#{@port}!"
127
+ end
128
+ @tcpServer = TCPServer.new(@host,@port)
129
+ @port = @tcpServer.addr[1]
130
+ @@services[@host] = {} unless @@services.has_key?(@host)
131
+ @@services[@host][@port] = self;
132
+ }
133
+ @tcpServerThread = Thread.new {
134
+ begin
135
+ starting if @audit
136
+ while !@shutdown
137
+ @connectionsMutex.synchronize {
138
+ while @connections.size >= @maxConnections
139
+ @connectionsCV.wait(@connectionsMutex)
140
+ end
141
+ }
142
+ client = @tcpServer.accept
143
+ @connections << Thread.new(client) { |myClient|
144
+ begin
145
+ myPort = myClient.peeraddr[1]
146
+ serve(myClient, &blk) if !@audit or connecting(myClient)
147
+ rescue => detail
148
+ error(detail) if @debug
149
+ ensure
150
+ begin
151
+ myClient.close
152
+ rescue
153
+ end
154
+ @connectionsMutex.synchronize {
155
+ @connections.delete(Thread.current)
156
+ @connectionsCV.signal
157
+ }
158
+ disconnecting(myPort) if @audit
159
+ end
160
+ }
161
+ end
162
+ rescue => detail
163
+ error(detail) if @debug
164
+ ensure
165
+ begin
166
+ @tcpServer.close
167
+ rescue
168
+ end
169
+ if @shutdown
170
+ @connectionsMutex.synchronize {
171
+ while @connections.size > 0
172
+ @connectionsCV.wait(@connectionsMutex)
173
+ end
174
+ }
175
+ else
176
+ @connections.each { |c| c.raise "stop" }
177
+ end
178
+ @tcpServerThread = nil
179
+ @@servicesMutex.synchronize {
180
+ @@services[@host].delete(@port)
181
+ }
182
+ stopping if @audit
183
+ end
184
+ }
185
+ self
186
+ end
187
+
188
+ end
189
+
190
+ class HttpServer < GeneralServer
191
+ def initialize(port, host = DEFAULT_HOST, maxConnections = 4,
192
+ stdlog = $stdout, audit = false, debug = false)
193
+ super(port, host, maxConnections, stdlog, audit, debug)
194
+ end
195
+
196
+ private
197
+
198
+ # Main Serve Loop -----------------------------------------
199
+
200
+ def serve(io)
201
+ # # perform IP authentification
202
+ # unless @handler.ip_auth_handler(io)
203
+ # io << http_resp(403, "Forbidden")
204
+ # return
205
+ # end
206
+ #
207
+ # # parse first line
208
+ # if io.gets =~ /^(\S+)\s+(\S+)\s+(\S+)/
209
+ # request = Request.new(io, $1, $2, $3)
210
+ # else
211
+ # io << http_resp(400, "Bad Request")
212
+ # return
213
+ # end
214
+ #
215
+ # # parse HTTP headers
216
+ # while (line=io.gets) !~ /^(\n|\r)/
217
+ # if line =~ /^([\w-]+):\s*(.*)$/
218
+ # request.header[$1] = $2.strip
219
+ # end
220
+ # end
221
+ request = HttpRequest.new(io)
222
+ response = HttpResponse.new
223
+
224
+ # execute request handler
225
+ yield(request, response)
226
+
227
+ # write response back to the client
228
+ io << response.to_http_pack
229
+
230
+ rescue Exception => e
231
+ # io << http_resp(500, "Internal Server Error")
232
+ raise "[ERROR] Exception:#{e.to_s}"
233
+ end
234
+
235
+ end # class HttpServer
236
+
237
+ end
238
+
239
+
240
+ if __FILE__ == $0
241
+ require 'wise_test'
242
+ class MyTest <WiseTest
243
+ def test_httpserver_get
244
+ server=HttpServer.new(8787)
245
+ server.start do |request, response|
246
+ #process request
247
+ puts "[SERVER][get] request from client:"
248
+ p request.header
249
+ p request.body
250
+
251
+ #customize your own response
252
+ puts "[SERVER][get] response to client:"
253
+ #response.status=403
254
+ response.header["Content-Type"]= "application/xhtml+xml;charset=gbk"
255
+ response.body="hello world!<-------path:/-------->哈喽我热烈的" if request.path=='/'
256
+ response.body="hello world!<-------path:/test/-------->哈喽我热烈的" if request.path.include? '/test/'
257
+ p response
258
+ end
259
+
260
+ get "http://127.0.0.1:8787/"
261
+ puts "[CLIENT] [1st] received from server:"
262
+ p @response.body
263
+ p @response.header.to_hash
264
+
265
+ get "http://127.0.0.1:8787/test/b/"
266
+ puts "[CLIENT] [2nd] received from server:"
267
+ p @response.body
268
+ p @response.header.to_hash
269
+
270
+ server.stop
271
+ #HttpServer.stop(8787)
272
+ end
273
+ def test_httpserver_post
274
+ server=HttpServer.new(8787)
275
+ server.start do |request, response|
276
+ puts "[SERVER][post] request from client:"
277
+ p request.header
278
+ p request.content
279
+
280
+ puts "[SERVER][post] response to client:"
281
+ response.header["Content-Type"]= "application/xhtml+xml;charset=utf-8"
282
+ response.body="hello world!<-------path:/-------->哈喽我热烈的" if request.path=='/'
283
+ p response
284
+ end
285
+
286
+ `echo "this is a file" >/tmp/test`
287
+ post "http://127.0.0.1:8787/", {}, {}, {"testfile"=>"/tmp/test"}
288
+ puts "[CLIENT][post] received from server:"
289
+ p @response.body
290
+ p @response.header.to_hash
291
+
292
+ server.stop
293
+ end
294
+ end
295
+ end
296
+
297
+