Here are the grinder properties file and the script. As I mentioned, the database is populated with 1000 users before this script is run. If I play around with the wait time (current 500 milliseconds) and the number of processors (currently 8), I can get a clean run (for example, running only 4 users with 5000 millisecond wait time). But with the current settings, I get the exception I posted earlier thrown many times, and not all auction items are created (last time I ran it I got 136 of the expected 160 items).
grinder.processes=8
grinder.threads=1
grinder.runs=20
grinder.processIncrementInterval=200
grinder.processIncrement=2
grinder.useConsole=true
grinder.jvm.arguments=-Xms128m -Xmx128m -Dpython.home=C:/apps/Java/jython2.2.1
grinder.logDirectory=d:/opt/cmg/grinder/log
grinder.numberOfOldLogs=30
grinder.script=d:/opt/cmg/grinder/createItem2.py
# The Grinder 3.0.1
# HTTP script recorded by TCPProxy at Mar 14, 2008 11:53:17 AM
import random
from net.grinder.script import Test
from net.grinder.script.Grinder import grinder
from net.grinder.plugin.http import HTTPPluginControl, HTTPRequest
from HTTPClient import NVPair
connectionDefaults = HTTPPluginControl.getConnectionDefaults()
httpUtilities = HTTPPluginControl.getHTTPUtilities()
# To use a proxy server, uncomment the next line and set the host and port.
# connectionDefaults.setProxyServer("localhost", 8001)
# These definitions at the top level of the file are evaluated once,
# when the worker process is started.
connectionDefaults.defaultHeaders = \
( NVPair('Accept-Language', 'en-us,en;q=0.7,de;q=0.3'),
NVPair('Accept-Charset', 'ISO-8859-1,utf-8;q=0.7,*;q=0.7'),
NVPair('Accept-Encoding', 'gzip,deflate'),
NVPair('User-Agent', 'Mozilla/5.0 (Windows; U; Windows NT 5.1; en-US; rv:1.8.1.12) Gecko/20080201 Firefox/2.0.0.12'), )
headers0= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/home.seam'), )
headers1= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/login.seam'), )
headers2= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/home.seam'), )
headers3= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell.seam'), )
headers4= \
( NVPair('Accept', '*/*'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell2.seam'), )
headers5= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell2.seam'),
NVPair('Cache-Control', 'no-cache'), )
headers6= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell2.seam'), )
headers7= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell3.seam'), )
headers8= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell4.seam'), )
headers9= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/sell5.seam'), )
headers10= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/preview.seam'), )
headers11= \
( NVPair('Accept', 'text/xml,application/xml,application/xhtml+xml,text/html;q=0.9,text/plain;q=0.8,image/png,*/*;q=0.5'),
NVPair('Referer', 'http://localhost:8080/seam-bay/home.seam'), )
url0 = 'http://localhost:8080'
#PETER BEGIN
# Init the random number generator:
random.seed()
# A 6-digit sequential serial number suffix is added to each item name
itemNumber = 100000
# The SeamBay category ids:
CATEGORY_ID = [
'1001' ,
'1002',
'2001',
'2002',
'2003',
'3001',
'3002',
'3003',
'3004',
'4001',
'4002',
'4003',
'4004',
'5001',
'5002',
'5003',
'6001',
'6002',
'6003',
'7001',
'7002',
'7003',
'7004',
'7005',
'8001',
'8002',
'8003',
'8004',
'8005',
'9001',
'9002',
'10001',
'10002',
'10003',
'10004',
'11001',
'11002',
'11003',
'12001',
'12002',
'12003',
'12004',
'13001',
'13002',
'13003',
'14001',
'14002',
'14003',
'14004',
'15001',
'15002',
'15003',
'15004']
#PETER END
# Create an HTTPRequest for each request, then replace the
# reference to the HTTPRequest with an instrumented version.
# You can access the unadorned instance using request101.__target__.
request101 = HTTPRequest(url=url0, headers=headers0)
request101 = Test(101, 'GET login.seam').wrap(request101)
request201 = HTTPRequest(url=url0, headers=headers1)
request201 = Test(201, 'POST login.seam').wrap(request201)
request202 = HTTPRequest(url=url0, headers=headers1)
request202 = Test(202, 'GET home.seam').wrap(request202)
request301 = HTTPRequest(url=url0, headers=headers2)
request301 = Test(301, 'GET sell.seam').wrap(request301)
request401 = HTTPRequest(url=url0, headers=headers3)
request401 = Test(401, 'POST sell.seam').wrap(request401)
request402 = HTTPRequest(url=url0, headers=headers3)
request402 = Test(402, 'GET sell2.seam').wrap(request402)
request403 = HTTPRequest(url=url0, headers=headers4)
request403 = Test(403, 'GET remote.js').wrap(request403)
request404 = HTTPRequest(url=url0, headers=headers4)
request404 = Test(404, 'GET interface.js').wrap(request404)
request501 = HTTPRequest(url=url0, headers=headers5)
request501 = Test(501, 'POST execute').wrap(request501)
request601 = HTTPRequest(url=url0, headers=headers6)
request601 = Test(601, 'POST sell2.seam').wrap(request601)
request602 = HTTPRequest(url=url0, headers=headers6)
request602 = Test(602, 'GET sell3.seam').wrap(request602)
request701 = HTTPRequest(url=url0, headers=headers7)
request701 = Test(701, 'POST sell3.seam').wrap(request701)
request702 = HTTPRequest(url=url0, headers=headers7)
request702 = Test(702, 'GET sell4.seam').wrap(request702)
request801 = HTTPRequest(url=url0, headers=headers8)
request801 = Test(801, 'POST sell4.seam').wrap(request801)
request802 = HTTPRequest(url=url0, headers=headers8)
request802 = Test(802, 'GET sell5.seam').wrap(request802)
request901 = HTTPRequest(url=url0, headers=headers9)
request901 = Test(901, 'POST sell5.seam').wrap(request901)
request902 = HTTPRequest(url=url0, headers=headers9)
request902 = Test(902, 'GET preview.seam').wrap(request902)
request1001 = HTTPRequest(url=url0, headers=headers10)
request1001 = Test(1001, 'POST preview.seam').wrap(request1001)
request1002 = HTTPRequest(url=url0, headers=headers10)
request1002 = Test(1002, 'GET home.seam').wrap(request1002)
request1101 = HTTPRequest(url=url0, headers=headers11)
request1101 = Test(1101, 'GET home.seam').wrap(request1101)
request1102 = HTTPRequest(url=url0, headers=headers11)
request1102 = Test(1102, 'GET home.seam').wrap(request1102)
class TestRunner:
"""A TestRunner instance is created for each worker thread."""
# A method for each recorded page.
def page1(self):
"""GET login.seam (request 101)."""
result = request101.GET('/seam-bay/login.seam')
self.token_cid = \
httpUtilities.valueFromBodyURI('cid') # '3406'
self.token_j_id9 = \
httpUtilities.valueFromHiddenInput('j_id9') # 'j_id9'
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1XXWwUVRS+XfpHaaClpJQYyEKR...'
return result
def page2(self):
"""POST login.seam (requests 201-202)."""
# PETER BEGIN
numb = random.randint(100,999)
userName = "user00" + str(numb)
userPwd = "password00" + str(numb)
# PETER END
# Expecting 302 'Moved Temporarily'
result = request201.POST('/seam-bay/login.seam',
( NVPair('j_id9', self.token_j_id9),
NVPair('j_id9:username', userName),
NVPair('j_id9:password', userPwd),
NVPair('j_id9:j_id13', 'Sign In > '),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
self.token_cid = \
httpUtilities.valueFromLocationURI('cid') # '3407'
grinder.sleep(79)
request202.GET('/seam-bay/home.seam' +
'?cid=' +
self.token_cid)
# 16 different values for token_actionMethod found in response, using the first one.
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'home.xhtml:identity.logout'
# 15 different values for token_categoryId found in response, using the first one.
self.token_categoryId = \
httpUtilities.valueFromBodyURI('categoryId') # '1'
self.token_j_id8 = \
httpUtilities.valueFromHiddenInput('j_id8') # 'j_id8'
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1YW2wcVxk+3tSxY8dp4kDqCpqs...'
return result
def page3(self):
"""GET sell.seam (request 301)."""
result = request301.GET('/seam-bay/sell.seam')
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'sell.xhtml:identity.logout'
# 2 different values for token_javaxfacesViewState found in response, using the first one.
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1YW2wcVxk+Xsex4ySOk5TEBSVs...'
self.token_j_id26 = \
httpUtilities.valueFromHiddenInput('j_id26') # 'j_id26'
return result
def page4(self):
global itemNumber
"""POST sell.seam (requests 401-404)."""
#PETER BEGIN
itemNumber = itemNumber + 1
rndNumber = random.randint(100000,999999);
itemTitle = 'item' + str(rndNumber) + '_' + str(itemNumber)
print "itemTitle=" + itemTitle
#PETER END
# Expecting 302 'Moved Temporarily'
result = request401.POST('/seam-bay/sell.seam',
( NVPair('j_id26', self.token_j_id26),
NVPair('j_id26:title', itemTitle),
NVPair('j_id26:j_id35', 'Next >'),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
self.token_cid = \
httpUtilities.valueFromLocationURI('cid') # '3408'
grinder.sleep(31)
request402.GET('/seam-bay/sell2.seam' +
'?cid=' +
self.token_cid)
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'sell2.xhtml:identity.logout'
# 2 different values for token_javaxfacesViewState found in response, using the first one.
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1Yb2wbZxl/4zRN6mRZ26A2FXQ4...'
self.token_catSelection = \
httpUtilities.valueFromHiddenInput('catSelection') # 'catSelection'
grinder.sleep(109)
request403.GET('/seam-bay/seam/resource/remoting/resource/remote.js')
grinder.sleep(47)
request404.GET('/seam-bay/seam/resource/remoting/interface.js' +
'?categoryAction')
return result
def page5(self):
"""POST execute (request 501)."""
result = request501.POST('/seam-bay/seam/resource/remoting/execute',
'<envelope><header><context></context></header><body><eval expr=\"#{allCategories}\" id=\"0\"/></body></envelope>',
( NVPair('Content-Type', 'application/xml'), ))
return result
def page6(self):
"""POST sell2.seam (requests 601-602)."""
# PETER BEGIN
cat = random.choice(CATEGORY_ID)
# PETER END
# Expecting 302 'Moved Temporarily'
result = request601.POST('/seam-bay/sell2.seam',
( NVPair('catSelection', self.token_catSelection),
NVPair('catSelection:categoryId', cat),
NVPair('catSelection:j_id30', 'Next >'),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
grinder.sleep(15)
request602.GET('/seam-bay/sell3.seam' +
'?cid=' +
self.token_cid)
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'sell3.xhtml:identity.logout'
# 2 different values for token_javaxfacesViewState found in response, using the first one.
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAM1ZW2wbxxUdUZYlS7Is24Uto7FD...'
return result
def page7(self):
"""POST sell3.seam (requests 701-702)."""
# PETER BEGIN
duration = str(random.randint(7,31))
price = str(random.randint(0,1000)) + ".00"
# PETER END
# Expecting 302 'Moved Temporarily'
result = request701.POST('/seam-bay/sell3.seam',
( NVPair('j_id26', self.token_j_id26),
NVPair('j_id26:duration', duration),
NVPair('j_id26:price', price),
NVPair('j_id26:j_id42', 'Next >'),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
grinder.sleep(125)
request702.GET('/seam-bay/sell4.seam' +
'?cid=' +
self.token_cid)
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'sell4.xhtml:identity.logout'
# 2 different values for token_javaxfacesViewState found in response, using the first one.
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1ZaYwbVx1/9ibZzW7uhCQtPZzd...'
self.token_j_id27 = \
httpUtilities.valueFromHiddenInput('j_id27') # 'j_id27'
self.token_j_id42 = \
httpUtilities.valueFromHiddenInput('j_id42') # 'j_id42'
return result
def page8(self):
"""POST sell4.seam (requests 801-802)."""
# Expecting 302 'Moved Temporarily'
result = request801.POST('/seam-bay/sell4.seam',
( NVPair('j_id42', self.token_j_id42),
NVPair('j_id42:j_id46', 'Next >'),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
grinder.sleep(31)
request802.GET('/seam-bay/sell5.seam' +
'?cid=' +
self.token_cid)
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'sell5.xhtml:identity.logout'
# 2 different values for token_javaxfacesViewState found in response, using the first one.
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1YXWwcVxW+XsexYyfBsavUUUm7...'
return result
def page9(self):
"""POST sell5.seam (requests 901-902)."""
# Expecting 302 'Moved Temporarily'
result = request901.POST('/seam-bay/sell5.seam',
( NVPair('j_id26', self.token_j_id26),
NVPair('j_id26:description', 'interesting description'),
NVPair('j_id26:j_id33', 'Next >'),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
grinder.sleep(31)
request902.GET('/seam-bay/preview.seam' +
'?cid=' +
self.token_cid)
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'preview.xhtml:identity.logout'
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAM1aW4wb1Rk+dkh2s7kQEpSEQqiz...'
self.token_j_id45 = \
httpUtilities.valueFromHiddenInput('j_id45') # 'j_id45'
return result
def page10(self):
"""POST preview.seam (requests 1001-1002)."""
# Expecting 302 'Moved Temporarily'
result = request1001.POST('/seam-bay/preview.seam',
( NVPair('j_id45', self.token_j_id45),
NVPair('j_id45:j_id49', 'Confirm Listing'),
NVPair('javax.faces.ViewState', self.token_javaxfacesViewState), ),
( NVPair('Content-Type', 'application/x-www-form-urlencoded'), ))
request1002.GET('/seam-bay/home.seam' +
'?cid=' +
self.token_cid)
# 16 different values for token_actionMethod found in response, using the first one.
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'home.xhtml:identity.logout'
# 14 different values for token_categoryId found in response; the first matched
# the last known value of token_categoryId - don't update the variable.
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1YW2wcVxk+3tSxY8dp4kDqCpqs...'
return result
def page11(self):
"""GET home.seam (requests 1101-1102)."""
# Expecting 302 'Moved Temporarily'
result = request1101.GET('/seam-bay/home.seam' +
'?actionMethod=' +
self.token_actionMethod)
grinder.sleep(31)
request1102.GET('/seam-bay/home.seam')
# 14 different values for token_categoryId found in response; the first matched
# the last known value of token_categoryId - don't update the variable.
self.token_actionMethod = \
httpUtilities.valueFromBodyURI('actionMethod') # 'home.xhtml:auctionSearch.queryAuctions'
self.token_javaxfacesViewState = \
httpUtilities.valueFromHiddenInput('javax.faces.ViewState') # 'H4sIAAAAAAAAAL1YW2wcVxk+3tSxY8dp4kDqCpqs...'
return result
def __call__(self):
"""This method is called for every run performed by the worker thread."""
self.page1() # GET login.seam (request 101)
grinder.sleep(500)
self.page2() # POST login.seam (requests 201-202)
grinder.sleep(500)
self.page3() # GET sell.seam (request 301)
grinder.sleep(500)
self.page4() # POST sell.seam (requests 401-404)
grinder.sleep(500)
self.page5() # POST execute (request 501)
grinder.sleep(500)
self.page6() # POST sell2.seam (requests 601-602)
grinder.sleep(500)
self.page7() # POST sell3.seam (requests 701-702)
grinder.sleep(500)
self.page8() # POST sell4.seam (requests 801-802)
grinder.sleep(500)
self.page9() # POST sell5.seam (requests 901-902)
grinder.sleep(500)
self.page10() # POST preview.seam (requests 1001-1002)
grinder.sleep(500)
self.page11() # GET home.seam (requests 1101-1102)
def instrumentMethod(test, method_name, c=TestRunner):
"""Instrument a method with the given Test."""
unadorned = getattr(c, method_name)
import new
method = new.instancemethod(test.wrap(unadorned), None, c)
setattr(c, method_name, method)
# Replace each method with an instrumented version.
# You can call the unadorned method using self.page1.__target__().
instrumentMethod(Test(100, 'Page 1'), 'page1')
instrumentMethod(Test(200, 'Page 2'), 'page2')
instrumentMethod(Test(300, 'Page 3'), 'page3')
instrumentMethod(Test(400, 'Page 4'), 'page4')
instrumentMethod(Test(500, 'Page 5'), 'page5')
instrumentMethod(Test(600, 'Page 6'), 'page6')
instrumentMethod(Test(700, 'Page 7'), 'page7')
instrumentMethod(Test(800, 'Page 8'), 'page8')
instrumentMethod(Test(900, 'Page 9'), 'page9')
instrumentMethod(Test(1000, 'Page 10'), 'page10')
instrumentMethod(Test(1100, 'Page 11'), 'page11')