diff --git a/CHANGELOG.rst b/CHANGELOG.rst index c0083d12..49935615 100644 --- a/CHANGELOG.rst +++ b/CHANGELOG.rst @@ -7,10 +7,20 @@ Features * Support static columns in schemas, which are available starting in Cassandra 2.1. (github issue #91) +Bug Fixes +--------- +* Correctly supply compaction and compression parameters in CREATE statements + for tables when working with Cassandra 2.0+ +* Lowercase boolean literals when generating schemas +* Ignore SSL_ERROR_WANT_READ and SSL_ERROR_WANT_WRITE socket errors. Previously, + these resulted in the connection being defuncted, but they can safely be + ignored by the driver. + Other ----- * Don't ignore column names when parsing typestrings. This is needed for user-defined type support. (github issue #90) +* Better error message when libevwrapper is not found 1.0.2 ===== diff --git a/benchmarks/base.py b/benchmarks/base.py index 90f41703..f00df6b0 100644 --- a/benchmarks/base.py +++ b/benchmarks/base.py @@ -15,7 +15,6 @@ sys.path.append(os.path.join(dirname, '..')) from cassandra.cluster import Cluster from cassandra.io.asyncorereactor import AsyncoreConnection from cassandra.policies import HostDistance -from cassandra.query import SimpleStatement log = logging.getLogger() handler = logging.StreamHandler() @@ -86,11 +85,10 @@ def benchmark(thread_class): log.debug("Sleeping for two seconds...") time.sleep(2.0) - query = SimpleStatement(""" - INSERT INTO {table} (thekey, col1, col2) - VALUES (%(key)s, %(a)s, %(b)s) + query = session.prepare(""" + INSERT INTO {table} (thekey, col1, col2) VALUES (?, ?, ?)) """.format(table=TABLE)) - values = {'key': 'key', 'a': 'a', 'b': 'b'} + values = ('key', 'a', 'b') per_thread = options.num_ops / options.threads threads = [] diff --git a/cassandra/io/asyncorereactor.py b/cassandra/io/asyncorereactor.py index a54aeeb9..f3f9f4e4 100644 --- a/cassandra/io/asyncorereactor.py +++ b/cassandra/io/asyncorereactor.py @@ -258,7 +258,11 @@ class AsyncoreConnection(Connection, asyncore.dispatcher): if len(buf) < self.in_buffer_size: break except socket.error as err: - if err.args[0] not in NONBLOCKING: + if ssl and isinstance(err, ssl.SSLError): + if err.args[0] not in (ssl.SSL_ERROR_WANT_READ, ssl.SSL_ERROR_WANT_WRITE): + self.defunct(err) + return + elif err.args[0] not in NONBLOCKING: self.defunct(err) return diff --git a/cassandra/io/libevreactor.py b/cassandra/io/libevreactor.py index 76b9be83..be5fbc9b 100644 --- a/cassandra/io/libevreactor.py +++ b/cassandra/io/libevreactor.py @@ -14,7 +14,16 @@ from cassandra.connection import (Connection, ResponseWaiter, ConnectionShutdown MAX_STREAM_PER_CONNECTION) from cassandra.decoder import RegisterMessage from cassandra.marshal import int32_unpack -import cassandra.io.libevwrapper as libev +try: + import cassandra.io.libevwrapper as libev +except ImportError: + raise ImportError( + "The C extension needed to use libev was not found. This " + "probably means that you didn't have the required build dependencies " + "when installing the driver. See " + "http://datastax.github.io/python-driver/installation.html#c-extensions " + "for instructions on installing build dependencies and building " + "the C extension.") try: from cStringIO import StringIO @@ -311,7 +320,11 @@ class LibevConnection(Connection): if len(buf) < self.in_buffer_size: break except socket.error as err: - if err.args[0] not in NONBLOCKING: + if ssl and isinstance(err, ssl.SSLError): + if err.args[0] not in (ssl.SSL_ERROR_WANT_READ, ssl.SSL_ERROR_WANT_WRITE): + self.defunct(err) + return + elif err.args[0] not in NONBLOCKING: self.defunct(err) return diff --git a/cassandra/metadata.py b/cassandra/metadata.py index d054d30c..e2bdd14e 100644 --- a/cassandra/metadata.py +++ b/cassandra/metadata.py @@ -792,7 +792,7 @@ def protect_value(value): if value is None: return 'NULL' if isinstance(value, (int, float, bool)): - return str(value) + return str(value).lower() return "'%s'" % value.replace("'", "''") diff --git a/tests/integration/__init__.py b/tests/integration/__init__.py index e5b27a00..0b09b885 100644 --- a/tests/integration/__init__.py +++ b/tests/integration/__init__.py @@ -20,7 +20,6 @@ CLUSTER_NAME = 'test_cluster' CCM_CLUSTER = None DEFAULT_CASSANDRA_VERSION = '2.0.5' - path = os.path.join(os.path.abspath(os.path.dirname(__file__)), 'ccm') if not os.path.exists(path): os.mkdir(path) diff --git a/tests/unit/test_metadata.py b/tests/unit/test_metadata.py index ce7b20dd..5464fb3a 100644 --- a/tests/unit/test_metadata.py +++ b/tests/unit/test_metadata.py @@ -169,8 +169,8 @@ class TestNameEscaping(unittest.TestCase): """ Test cassandra.metadata.protect_value output """ - self.assertEqual(protect_value(True), "True") - self.assertEqual(protect_value(False), "False") + self.assertEqual(protect_value(True), "true") + self.assertEqual(protect_value(False), "false") self.assertEqual(protect_value(3.14), '3.14') self.assertEqual(protect_value(3), '3') self.assertEqual(protect_value('test'), "'test'")