Commit e4ea2e12 authored by Justin Bronn's avatar Justin Bronn
Browse files

Fixed #9448 -- `Layer` objects now carry a reference to their parent...

Fixed #9448 -- `Layer` objects now carry a reference to their parent `DataSource`.  Thanks, Matthew D. Hancher for the bug report.

Backport of r9284 from trunk.


git-svn-id: http://code.djangoproject.com/svn/django/branches/releases/1.0.X@9285 bcc190cf-cafb-0310-a4f2-bffc1f526a37
parent 3517f8a5
Loading
Loading
Loading
Loading
+1 −1
Original line number Diff line number Diff line
@@ -111,7 +111,7 @@ class DataSource(object):
            l = get_layer(self._ptr, index)
        else:
            raise TypeError('Invalid index type: %s' % type(index))
        return Layer(l)
        return Layer(l, self)
        
    def __len__(self):
        "Returns the number of layers within the data source."
+8 −2
Original line number Diff line number Diff line
@@ -25,12 +25,18 @@ class Layer(object):
    "A class that wraps an OGR Layer, needs to be instantiated from a DataSource object."

    #### Python 'magic' routines ####
    def __init__(self, layer_ptr):
        "Needs a C pointer (Python/ctypes integer) in order to initialize."
    def __init__(self, layer_ptr, ds):
        """
        Initializes on an OGR C pointer to the Layer and the `DataSource` object
        that owns this layer.  The `DataSource` object is required so that a 
        reference to it is kept with this Layer.  This prevents garbage 
        collection of the `DataSource` while this Layer is still active.
        """
        self._ptr = None # Initially NULL
        if not layer_ptr:
            raise OGRException('Cannot create Layer, invalid pointer given')
        self._ptr = layer_ptr
        self._ds = ds
        self._ldefn = get_layer_defn(self._ptr)
        # Does the Layer support random reading?
        self._random_read = self.test_capability('RandomRead')
+17 −0
Original line number Diff line number Diff line
@@ -130,6 +130,23 @@ class DataSourceTest(unittest.TestCase):
            control_vals = source.field_values[fld_name][sl]
            self.assertEqual(control_vals, test_vals)

    def test03c_layer_references(self):
        "Test to make sure Layer access is still available without the DataSource."
        source = ds_list[0]

        # See ticket #9448.
        def get_layer():
            # This DataSource object is not accessible outside this
            # scope.  However, a reference should still be kept alive
            # on the `Layer` returned.
            ds = DataSource(source.ds)
            return ds[0]

        # Making sure we can call OGR routines on the Layer returned.
        lyr = get_layer()
        self.assertEqual(source.nfeat, len(lyr))
        self.assertEqual(source.gtype, lyr.geom_type.num)        

    def test04_features(self):
        "Testing Data Source Features."
        for source in ds_list: