Commit a2f9f4e2 authored by Guido van Rossum's avatar Guido van Rossum

Refactored the tests, removing some unnecessary structure.

Got rid of PackWaitWrapper (since pack now waits by default).

Moved the connection test scaffolding to testConnection.py (new);
moved the openClientStorage() implementation into ConnectionTests.py
since it is not platform dependent.
parent b053cb74
......@@ -23,7 +23,7 @@ import time
import zLOG
import ZEO.ClientStorage
from ZEO.ClientStorage import ClientStorage
from ZEO.Exceptions import Disconnected
from ZEO.zrpc.marshal import Marshaller
......@@ -32,6 +32,10 @@ from ZODB.POSException import ReadOnlyError
from ZODB.tests import StorageTestBase
from ZODB.tests.StorageTestBase import zodb_unpickle, MinPO
class DummyDB:
def invalidate(self, *args):
pass
class ConnectionTests(StorageTestBase.StorageTestBase):
"""Tests that explicitly manage the server process.
......@@ -67,7 +71,16 @@ class ConnectionTests(StorageTestBase.StorageTestBase):
def openClientStorage(self, cache='', cache_size=200000, wait=1,
read_only=0, read_only_fallback=0):
raise NotImplementedError
base = ClientStorage(self.addr,
client=cache,
cache_size=cache_size,
wait=wait,
min_disconnect_poll=0.1,
read_only=read_only,
read_only_fallback=read_only_fallback)
storage = base
storage.registerDB(DummyDB(), None)
return storage
def shutdownServer(self, index=0):
raise NotImplementedError
......@@ -490,4 +503,3 @@ class ConnectionTests(StorageTestBase.StorageTestBase):
self._storage = self.openClientStorage()
self._dostore()
##############################################################################
#
# Copyright (c) 2001, 2002 Zope Corporation and Contributors.
# All Rights Reserved.
#
# This software is subject to the provisions of the Zope Public License,
# Version 2.0 (ZPL). A copy of the ZPL should accompany this distribution.
# THIS SOFTWARE IS PROVIDED "AS IS" AND ANY AND ALL EXPRESS OR IMPLIED
# WARRANTIES ARE DISCLAIMED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
# WARRANTIES OF TITLE, MERCHANTABILITY, AGAINST INFRINGEMENT, AND FITNESS
# FOR A PARTICULAR PURPOSE
#
##############################################################################
"""Test setup for ZEO connection logic.
The actual tests are in ConnectionTests.py; this file provides the
platform-dependent scaffolding.
"""
# System imports
import os
import time
import socket
import unittest
# Zope/ZODB3 imports
import zLOG
# ZEO test support
from ZEO.tests import forker
# Import the actual test class
from ZEO.tests.ConnectionTests import ConnectionTests
class UnixConnectionTests(ConnectionTests):
"""Add Unix-specific scaffolding to the generic test suite."""
def startServer(self, create=1, index=0, read_only=0, ro_svr=0):
zLOG.LOG("testZEO", zLOG.INFO,
"startServer(create=%d, index=%d, read_only=%d)" %
(create, index, read_only))
path = "%s.%d" % (self.file, index)
addr = self.addr[index]
pid, server = forker.start_zeo_server(
'FileStorage', (path, create, read_only), addr, ro_svr)
self._pids.append(pid)
self._servers.append(server)
def shutdownServer(self, index=0):
zLOG.LOG("testZEO", zLOG.INFO, "shutdownServer(index=%d)" % index)
self._servers[index].close()
if self._pids[index] is not None:
try:
os.waitpid(self._pids[index], 0)
self._pids[index] = None
except os.error, err:
print err
class WindowsConnectionTests(ConnectionTests):
"""Add Windows-specific scaffolding to the generic test suite."""
def startServer(self, create=1, index=0, read_only=0, ro_svr=0):
zLOG.LOG("testZEO", zLOG.INFO,
"startServer(create=%d, index=%d, read_only=%d)" %
(create, index, read_only))
path = "%s.%d" % (self.file, index)
addr = self.addr[index]
args = (path, '='+str(create), '='+str(read_only))
_addr, test_addr, test_pid = forker.start_zeo_server(
'FileStorage', args, addr, ro_svr)
self._pids.append(test_pid)
self._servers.append(test_addr)
def shutdownServer(self, index=0):
zLOG.LOG("testZEO", zLOG.INFO, "shutdownServer(index=%d)" % index)
if self._servers[index] is not None:
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(self._servers[index])
s.close()
self._servers[index] = None
# XXX waitpid() isn't available until Python 2.3
time.sleep(0.5)
if os.name == "posix":
test_classes = [UnixConnectionTests]
elif os.name == "nt":
test_classes = [WindowsConnectionTests]
else:
raise RuntimeError, "unsupported os: %s" % os.name
def test_suite():
# shutup warnings about mktemp
import warnings
warnings.filterwarnings("ignore", "mktemp")
suite = unittest.TestSuite()
for klass in test_classes:
sub = unittest.makeSuite(klass, 'check')
suite.addTest(sub)
return suite
if __name__ == "__main__":
unittest.main(defaultTest='test_suite')
......@@ -11,23 +11,32 @@
# FOR A PARTICULAR PURPOSE
#
##############################################################################
"""Test suite for ZEO based on ZODB.tests"""
"""Test suite for ZEO based on ZODB.tests."""
import asyncore
# System imports
import os
import sys
import time
import random
import select
import socket
import sys
import tempfile
import thread
import time
import asyncore
import tempfile
import unittest
# Zope/ZODB3 imports
import zLOG
# ZODB imports
from ZODB.Transaction import get_transaction
from ZODB.POSException import ReadOnlyError
import zLOG
# ZODB test support
from ZODB.tests.MinPO import MinPO
from ZODB.tests.StorageTestBase import zodb_unpickle
# Handle potential absence of removefs
try:
from ZODB.tests.StorageTestBase import removefs
except ImportError:
......@@ -44,81 +53,29 @@ except ImportError:
if err[0] != errno.ENOENT:
raise
from ZEO.ClientStorage import ClientStorage
from ZEO.tests import forker, Cache, CommitLockTests, ThreadTests
from ZEO.tests.ConnectionTests import ConnectionTests
from ZEO.Exceptions import Disconnected
# ZODB test mixin classes
from ZODB.tests import StorageTestBase, BasicStorage, VersionStorage, \
TransactionalUndoStorage, TransactionalUndoVersionStorage, \
PackableStorage, Synchronization, ConflictResolution, RevisionStorage, \
MTStorage, ReadOnlyStorage
from ZODB.tests.MinPO import MinPO
from ZODB.tests.StorageTestBase import zodb_unpickle
class DummyDB:
def invalidate(self, *args):
pass
# ZEO imports
from ZEO.ClientStorage import ClientStorage
from ZEO.Exceptions import Disconnected
class PackWaitWrapper:
def __init__(self, storage):
self.storage = storage
def __getattr__(self, attr):
return getattr(self.storage, attr)
def pack(self, t, f):
self.storage.pack(t, f, wait=1)
class GenericTests(StorageTestBase.StorageTestBase,
TransactionalUndoStorage.TransactionalUndoStorage,
TransactionalUndoVersionStorage.TransactionalUndoVersionStorage,
ConflictResolution.ConflictResolvingStorage,
ConflictResolution.ConflictResolvingTransUndoStorage,
Cache.StorageWithCache,
Cache.TransUndoStorageWithCache,
BasicStorage.BasicStorage,
VersionStorage.VersionStorage,
RevisionStorage.RevisionStorage,
PackableStorage.PackableStorage,
Synchronization.SynchronizedStorage,
MTStorage.MTStorage,
ReadOnlyStorage.ReadOnlyStorage,
CommitLockTests.CommitLockTests,
ThreadTests.ThreadTests,
):
"""An abstract base class for ZEO tests
A specific ZEO test run depends on having a real storage that the
StorageServer provides access to. The GenericTests must be
subclassed to provide an implementation of getStorage() that
returns a specific storage, e.g. FileStorage.
"""
# ZEO test support
from ZEO.tests import forker, Cache
def setUp(self):
zLOG.LOG("testZEO", zLOG.INFO, "setUp() %s" % self.id())
client, exit, pid = forker.start_zeo(*self.getStorage())
self._pids = [pid]
self._servers = [exit]
self._storage = PackWaitWrapper(client)
client.registerDB(DummyDB(), None)
# ZEO test mixin classes
from ZEO.tests import CommitLockTests, ThreadTests
def tearDown(self):
self._storage.close()
for server in self._servers:
server.close()
for pid in self._pids:
os.waitpid(pid, 0)
self.delStorage()
class DummyDB:
def invalidate(self, *args):
pass
def open(self, read_only=0):
# XXX Needed to support ReadOnlyStorage tests. Ought to be a
# cleaner way.
class MiscZEOTests:
addr = self._storage._addr
self._storage.close()
self._storage = ClientStorage(addr, read_only=read_only, wait=1)
"""ZEO tests that don't fit in elsewhere."""
def checkLargeUpdate(self):
obj = MinPO("X" * (10 * 128 * 1024))
......@@ -146,13 +103,59 @@ class GenericTests(StorageTestBase.StorageTestBase,
finally:
storage2.close()
class GenericTests(
# Base class for all ZODB tests
StorageTestBase.StorageTestBase,
# ZODB test mixin classes (in the same order as imported)
BasicStorage.BasicStorage,
VersionStorage.VersionStorage,
TransactionalUndoStorage.TransactionalUndoStorage,
TransactionalUndoVersionStorage.TransactionalUndoVersionStorage,
PackableStorage.PackableStorage,
Synchronization.SynchronizedStorage,
ConflictResolution.ConflictResolvingStorage,
ConflictResolution.ConflictResolvingTransUndoStorage,
RevisionStorage.RevisionStorage,
MTStorage.MTStorage,
ReadOnlyStorage.ReadOnlyStorage,
# ZEO test mixin classes (in the same order as imported)
Cache.StorageWithCache,
Cache.TransUndoStorageWithCache,
CommitLockTests.CommitLockTests,
ThreadTests.ThreadTests,
MiscZEOTests # Locally defined (see above)
):
"""Combine tests from various origins in one class."""
class ZEOFileStorageTests(GenericTests):
__super_setUp = GenericTests.setUp
def open(self, read_only=0):
# XXX Needed to support ReadOnlyStorage tests. Ought to be a
# cleaner way.
addr = self._storage._addr
self._storage.close()
self._storage = ClientStorage(addr, read_only=read_only, wait=1)
class UnixTests(GenericTests):
"""Add Unix-specific scaffolding to the generic test suite."""
def setUp(self):
self.__fs_base = tempfile.mktemp()
self.__super_setUp()
zLOG.LOG("testZEO", zLOG.INFO, "setUp() %s" % self.id())
client, exit, pid = forker.start_zeo(*self.getStorage())
self._pids = [pid]
self._servers = [exit]
self._storage = client
client.registerDB(DummyDB(), None)
def tearDown(self):
self._storage.close()
for server in self._servers:
server.close()
for pid in self._pids:
os.waitpid(pid, 0)
self.delStorage()
def getStorage(self):
self.__fs_base = tempfile.mktemp()
......@@ -161,13 +164,9 @@ class ZEOFileStorageTests(GenericTests):
def delStorage(self):
removefs(self.__fs_base)
class WindowsGenericTests(GenericTests):
"""Subclass to support server creation on Windows.
class WindowsTests(GenericTests):
On Windows, the getStorage() design won't work because the storage
can't be created in the parent process and passed to the child.
All the work has to be done in the server's process.
"""
"""Add Windows-specific scaffolding to the generic test suite."""
def setUp(self):
zLOG.LOG("testZEO", zLOG.INFO, "setUp() %s" % self.id())
......@@ -177,7 +176,7 @@ class WindowsGenericTests(GenericTests):
zeo_addr, self.test_addr, self.test_pid = \
forker.start_zeo_server(name, args)
storage = ClientStorage(zeo_addr, wait=1, min_disconnect_poll=0.1)
self._storage = PackWaitWrapper(storage)
self._storage = storage
storage.registerDB(DummyDB(), None)
def tearDown(self):
......@@ -189,8 +188,6 @@ class WindowsGenericTests(GenericTests):
time.sleep(0.5)
self.delStorage()
class WindowsZEOFileStorageTests(WindowsGenericTests):
def getStorageInfo(self):
self.__fs_base = tempfile.mktemp()
return 'FileStorage', (self.__fs_base, '1') # create=1
......@@ -198,73 +195,10 @@ class WindowsZEOFileStorageTests(WindowsGenericTests):
def delStorage(self):
removefs(self.__fs_base)
class BaseConnectionTests(ConnectionTests):
# provide an openClientStorage() method shared by Unix and Windows
def openClientStorage(self, cache='', cache_size=200000, wait=1,
read_only=0, read_only_fallback=0):
base = ClientStorage(self.addr,
client=cache,
cache_size=cache_size,
wait=wait,
min_disconnect_poll=0.1,
read_only=read_only,
read_only_fallback=read_only_fallback)
storage = PackWaitWrapper(base)
storage.registerDB(DummyDB(), None)
return storage
class UnixConnectionTests(BaseConnectionTests):
def startServer(self, create=1, index=0, read_only=0, ro_svr=0):
zLOG.LOG("testZEO", zLOG.INFO,
"startServer(create=%d, index=%d, read_only=%d)" %
(create, index, read_only))
path = "%s.%d" % (self.file, index)
addr = self.addr[index]
pid, server = forker.start_zeo_server(
'FileStorage', (path, create, read_only), addr, ro_svr)
self._pids.append(pid)
self._servers.append(server)
def shutdownServer(self, index=0):
zLOG.LOG("testZEO", zLOG.INFO, "shutdownServer(index=%d)" % index)
self._servers[index].close()
if self._pids[index] is not None:
try:
os.waitpid(self._pids[index], 0)
self._pids[index] = None
except os.error, err:
print err
class WindowsConnectionTests(BaseConnectionTests):
def startServer(self, create=1, index=0, read_only=0, ro_svr=0):
zLOG.LOG("testZEO", zLOG.INFO,
"startServer(create=%d, index=%d, read_only=%d)" %
(create, index, read_only))
path = "%s.%d" % (self.file, index)
addr = self.addr[index]
args = (path, '='+str(create), '='+str(read_only))
_addr, test_addr, test_pid = forker.start_zeo_server(
'FileStorage', args, addr, ro_svr)
self._pids.append(test_pid)
self._servers.append(test_addr)
def shutdownServer(self, index=0):
zLOG.LOG("testZEO", zLOG.INFO, "shutdownServer(index=%d)" % index)
if self._servers[index] is not None:
s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
s.connect(self._servers[index])
s.close()
self._servers[index] = None
# XXX waitpid() isn't available until Python 2.3
time.sleep(0.5)
if os.name == "posix":
test_classes = ZEOFileStorageTests, UnixConnectionTests
test_classes = [UnixTests]
elif os.name == "nt":
test_classes = WindowsZEOFileStorageTests, WindowsConnectionTests
test_classes = [WindowsTests]
else:
raise RuntimeError, "unsupported os: %s" % os.name
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment