Browse Source

update sqlite3_ds zone_exist() comments and unittest

chenzhengzhang 14 years ago
parent
commit
0f06a4fca4

+ 79 - 69
src/lib/python/isc/datasrc/sqlite3_ds.py

@@ -25,17 +25,16 @@ RR_NAME_INDEX = 2
 RR_TTL_INDEX = 4
 RR_RDATA_INDEX = 7
 
-#########################################################################
-# define exceptions
-#########################################################################
 class Sqlite3DSError(Exception):
+    """ Define exceptions."""
     pass
 
-#########################################################################
-# create: set up schema for a newly created zones/records database
-#########################################################################
 def create(cur):
-    """Create new zone database"""
+    """ Set up schema for a newly created zones/records database.
+
+    Arguments:
+        cur - sqlite3 cursor.
+    """
     cur.execute("CREATE TABLE schema_version (version INTEGER NOT NULL)")
     cur.execute("INSERT INTO schema_version VALUES (1)")
     cur.execute("""CREATE TABLE zones (id INTEGER PRIMARY KEY,
@@ -62,16 +61,17 @@ def create(cur):
                    rdata STRING NOT NULL)""")
     cur.execute("CREATE INDEX nsec3_byhash ON nsec3 (hash)")
 
-#########################################################################
-# open: open a database.  if the database is not yet set up,
-# call create to do so.
-# input:
-#   dbfile - the filename for the sqlite3 database
-# returns:
-#   sqlite3 connection, sqlite3 cursor
-#########################################################################
 def open(dbfile):
-    """Open the database file.  If necessary, set it up"""
+    """ Open a database, if the database is not yet set up, call create
+    to do so. It may raise Sqlite3DSError if failed to open sqlite3
+    database file or find bad database schema version in the database.
+
+    Arguments:
+        dbfile - the filename for the sqlite3 database.
+
+    Return sqlite3 connection, sqlite3 cursor.
+    """
+    # Open the database file.  If necessary, set it up"""
     try:
         conn = sqlite3.connect(dbfile)
         cur = conn.cursor()
@@ -94,12 +94,14 @@ def open(dbfile):
     return conn, cur
 
 
-#########################################################################
-# get_zone_datas
-#   a generator function producing an iterable set of
-#   the records in the zone with the given zone name.
-#########################################################################
 def get_zone_datas(zonename, dbfile):
+    """ A generator function producing an iterable set of
+    the records in the zone with the given zone name.
+
+    Arguments:
+        zonename - the zone's origin name.
+        dbfile - the filename for the sqlite3 database.
+    """
     conn, cur = open(dbfile)
     zone_id = get_zoneid(zonename, cur)
 
@@ -113,12 +115,14 @@ def get_zone_datas(zonename, dbfile):
     conn.close()
 
 
-#########################################################################
-# get_zone_soa
-#   returns the soa record of the zone with the given zone name.
-#   If the zone doesn't exist, return None.
-#########################################################################
 def get_zone_soa(zonename, dbfile):
+    """Return the soa record of the zone with the given zone name.
+    If the zone doesn't exist, return None.
+
+    Arguments:
+        zonename - the zone's origin name.
+        dbfile - the filename for the sqlite3 database.
+    """
     conn, cur = open(dbfile)
     id = get_zoneid(zonename, cur)
     cur.execute("SELECT * FROM records WHERE zone_id = ? and rdtype = ?", [id, 'SOA'])
@@ -129,13 +133,17 @@ def get_zone_soa(zonename, dbfile):
     return datas
 
 
-#########################################################################
-# get_zone_rrset
-#   returns the rrset of the zone with the given zone name, rrset name
-#   and given rd type.
-#   If the zone doesn't exist or rd type doesn't exist, return an empty list.
-#########################################################################
 def get_zone_rrset(zonename, rr_name, rdtype, dbfile):
+    """Return the rrset of the zone with the given zone name, rrset
+    name and given rd type. If the zone doesn't exist or rd type
+    doesn't exist, return an empty list.
+
+    Arguments:
+        zonename - the zone's origin name.
+        rr_name - rr name.
+        rdtype - rdata type.
+        dbfile - the filename for the sqlite3 database.
+    """
     conn, cur = open(dbfile)
     id = get_zoneid(zonename, cur)
     cur.execute("SELECT * FROM records WHERE name = ? and zone_id = ? and rdtype = ?",
@@ -146,11 +154,12 @@ def get_zone_rrset(zonename, rr_name, rdtype, dbfile):
     return datas
 
 
-#########################################################################
-# get_zones_info:
-#   returns all the zones' information.
-#########################################################################
 def get_zones_info(db_file):
+    """ Return all the zones' information in the database.
+
+    Arguments:
+        dbfile - the filename for the sqlite3 database.
+    """
     conn, cur = open(db_file)
     cur.execute("SELECT name, rdclass FROM zones")
     info = cur.fetchone()
@@ -162,13 +171,17 @@ def get_zones_info(db_file):
     conn.close()
 
 
-#########################################################################
-# get_zoneid:
-#   returns the zone_id for a given zone name, or an empty
-#   string if the zone is not found
-#########################################################################
-def get_zoneid(zone, cur):
-    cur.execute("SELECT id FROM zones WHERE name = ?", [zone])
+def get_zoneid(zonename, cur):
+    """ Get the zone_id for a given zone name.
+
+    Arguments:
+        zonename - the zone's origin name.
+        cur - sqlite3 cursor.
+
+    Return zone id for the given zone name, or an empty string if the
+    zone is not found.
+    """
+    cur.execute("SELECT id FROM zones WHERE name = ?", [zonename])
     row = cur.fetchone()
     if row:
         return row[0]
@@ -176,18 +189,17 @@ def get_zoneid(zone, cur):
         return ''
 
 
-#########################################################################
-# zone_exist:
-#   Search for the zone with the name zonename in databse. This method
-#   may throw a exception because its underlying methods open() may
-#   throw exceptions.
-# input:
-#   zonename: the zone's origin name.
-#   dbfile: the filename for the sqlite3 database.
-# returns:
-#   returns True if the zone is found, otherwise False.
-#########################################################################
 def zone_exist(zonename, dbfile):
+    """ Search for the zone with the given zone name in databse. This
+    method may throw a Sqlite3DSError exception because its underlying
+    methods open() can throw that exception.
+
+    Arguments:
+        zonename - the zone's origin name.
+        dbfile - the filename for the sqlite3 database.
+
+    Return True if the zone is found, otherwise False.
+    """
     conn, cur = open(dbfile)
     zoneid = get_zoneid(zonename, cur)
     cur.close()
@@ -197,15 +209,14 @@ def zone_exist(zonename, dbfile):
     return False
 
 
-#########################################################################
-# reverse_name:
-#   reverse the labels of a DNS name.  (for example,
-#   "bind10.isc.org." would become "org.isc.bind10.")
-#########################################################################
 def reverse_name(name):
     """Reverse the labels of a domain name; for example,
     given 'www.isc.org.', return 'org.isc.www.'  This is needed
-    for DNSSEC sort order."""
+    for DNSSEC sort order.
+
+    Arguments:
+        name - the DNS name will be reversed.
+    """
     new = name.split('.')
     new.reverse()
     if new[0] == '':
@@ -213,16 +224,15 @@ def reverse_name(name):
     return '.'.join(new)+'.'
 
 
-#########################################################################
-# load:
-#   load a zone into the SQL database.
-# input:
-#   dbfile: the sqlite3 database fileanme
-#   zone: the zone origin
-#   reader: a generator function producing an iterable set of
-#           name/ttl/class/rrtype/rdata-text tuples
-#########################################################################
 def load(dbfile, zone, reader):
+    """  Load a zone into the SQL database.
+
+    Arguments:
+        dbfile - the sqlite3 database filename
+        zone - the zone origin
+        reader - a generator function producing an iterable set of
+        name/ttl/class/rrtype/rdata-text tuples.
+    """
     # if the zone name doesn't contain the trailing dot, automatically add it.
     if zone[-1] != '.':
         zone += '.'

+ 5 - 1
src/lib/python/isc/datasrc/tests/Makefile.am

@@ -2,10 +2,13 @@ PYCOVERAGE_RUN = @PYCOVERAGE_RUN@
 PYTESTS = master_test.py sqlite3_ds_test.py
 EXTRA_DIST = $(PYTESTS)
 
+EXTRA_DIST += testdata/brokendb.sqlite3
+EXTRA_DIST += testdata/example.com.sqlite3
+
 # test using command-line arguments, so use check-local target instead of TESTS
 check-local:
 if ENABLE_PYTHON_COVERAGE
-	touch $(abs_top_srcdir)/.coverage 
+	touch $(abs_top_srcdir)/.coverage
 	rm -f .coverage
 	${LN_S} $(abs_top_srcdir)/.coverage .coverage
 endif
@@ -14,3 +17,4 @@ endif
 	env PYTHONPATH=$(abs_top_srcdir)/src/lib/python:$(abs_top_builddir)/src/lib/python:$(abs_top_builddir)/src/lib/python/isc/log \
 	$(PYCOVERAGE_RUN) $(abs_srcdir)/$$pytest || exit ; \
 	done
+

+ 19 - 10
src/lib/python/isc/datasrc/tests/sqlite3_ds_test.py

@@ -1,4 +1,4 @@
-# Copyright (C) 2010  Internet Systems Consortium.
+# Copyright (C) 2011  Internet Systems Consortium.
 #
 # Permission to use, copy, modify, and distribute this software for any
 # purpose with or without fee is hereby granted, provided that the above
@@ -17,17 +17,26 @@ from isc.datasrc import sqlite3_ds
 import socket
 import unittest
 
+TEST_DATA_PATH = "./testdata/"
+
 class TestSqlite3_ds(unittest.TestCase):
     def test_zone_exist(self):
-        def open(db_file):
-            conn, cur = socket.socketpair()
-            return conn, cur
-        def get_zoneid(zone_name, cur):
-            return zone_name
-        sqlite3_ds.open = open
-        sqlite3_ds.get_zoneid = get_zoneid
-        self.assertTrue(sqlite3_ds.zone_exist("example.com", "sqlite3_db"))
-        self.assertFalse(sqlite3_ds.zone_exist("", "sqlite3_db"))
+        # The following file must be non existent and must be non
+        # "creatable"; the sqlite3 library will try to create a new
+        # DB file if it doesn't exist, so to test a failure case the
+        # create operation should also fail. The "nodir", a non
+        # existent directory, is inserted for this purpose.
+        nodir = "/nodir/notexist"
+        self.assertRaises(sqlite3_ds.Sqlite3DSError,
+                          sqlite3_ds.zone_exist, "example.com", nodir)
+        # Open a broken database file
+        self.assertRaises(sqlite3_ds.Sqlite3DSError,
+                          sqlite3_ds.zone_exist, "example.com",
+                          TEST_DATA_PATH + "brokendb.sqlite3")
+        self.assertTrue(sqlite3_ds.zone_exist("example.com.",
+                            TEST_DATA_PATH + "example.com.sqlite3"))
+        self.assertFalse(sqlite3_ds.zone_exist("example.org.",
+                            TEST_DATA_PATH + "example.com.sqlite3"))
 
 if __name__ == '__main__':
     unittest.main()

BIN
src/lib/python/isc/datasrc/tests/testdata/brokendb.sqlite3


BIN
src/lib/python/isc/datasrc/tests/testdata/example.com.sqlite3