]> git.ipfire.org Git - thirdparty/sqlalchemy/sqlalchemy.git/commitdiff
modernized "adjacencytree" example
authorMike Bayer <mike_mp@zzzcomputing.com>
Mon, 18 Jan 2010 21:29:55 +0000 (21:29 +0000)
committerMike Bayer <mike_mp@zzzcomputing.com>
Mon, 18 Jan 2010 21:29:55 +0000 (21:29 +0000)
examples/adjacency_list/__init__.py [moved from examples/adjacencytree/__init__.py with 100% similarity]
examples/adjacency_list/adjacency_list.py [new file with mode: 0644]
examples/adjacencytree/basic_tree.py [deleted file]

diff --git a/examples/adjacency_list/adjacency_list.py b/examples/adjacency_list/adjacency_list.py
new file mode 100644 (file)
index 0000000..3bf20dc
--- /dev/null
@@ -0,0 +1,139 @@
+"""
+An example of a dictionary-of-dictionaries structure mapped using
+an adjacency list model
+
+"""
+
+from sqlalchemy import MetaData, Table, Column, Sequence, ForeignKey,\
+                        Integer, String, create_engine
+                        
+from sqlalchemy.orm import sessionmaker, mapper, relation, backref,\
+                                eagerload_all
+                                
+from sqlalchemy.orm.collections import attribute_mapped_collection
+
+metadata = MetaData()
+
+tree_table = Table('tree', metadata,
+    Column('id', Integer, primary_key=True),
+    Column('parent_id', Integer, ForeignKey('tree.id')),
+    Column('name', String(50), nullable=False)
+)
+
+class TreeNode(object):
+    def __init__(self, name, parent=None):
+        self.name = name
+        self.parent = parent
+        
+    def append(self, nodename):
+        self.children[nodename] = TreeNode(nodename, parent=self)
+    
+    def __repr__(self):
+        return "TreeNode(name=%r, id=%r, parent_id=%r)" % (
+                    self.name,
+                    self.id,
+                    self.parent_id
+                )
+                
+def dump_tree(node, indent=0):
+    
+    return "   " * indent + repr(node) + \
+                "\n" + \
+                "".join([
+                    dump_tree(c, indent +1) 
+                    for c in node.children.values()]
+                )
+                    
+
+mapper(TreeNode, tree_table, properties={
+    'children': relation(TreeNode, 
+
+                        # cascade deletions
+                        cascade="all",
+    
+                        # many to one + adjacency list - remote_side
+                        # is required to reference the 'remote' 
+                        # column in the join condition.
+                        backref=backref("parent", remote_side=tree_table.c.id),
+                         
+                        # children will be represented as a dictionary
+                        # on the "name" attribute.
+                        collection_class=attribute_mapped_collection('name'),
+                    )
+    })
+
+if __name__ == '__main__':
+    engine = create_engine('sqlite://', echo=True)
+
+    def msg(msg):
+        print "\n\n\n" + "-" * len(msg)
+        print msg
+        print "-" * len(msg)
+
+    msg("Creating Tree Table:")
+
+    metadata.create_all(engine)
+
+    # session.  using expire_on_commit=False
+    # so that the session's contents are not expired
+    # after each transaction commit.
+    session = sessionmaker(engine, expire_on_commit=False)()
+
+    node = TreeNode('rootnode')
+    node.append('node1')
+    node.append('node3')
+
+    node2 = TreeNode('node2')
+    node2.append('subnode1')
+    node.children['node2'] = node2
+    node.children['node2'].append('subnode2')
+
+    msg("Created new tree structure:")
+
+    print dump_tree(node)
+
+    msg("flush + commit:")
+
+    session.add(node)
+    session.commit()
+
+    msg("Tree After Save:")
+
+    print dump_tree(node)
+
+    node.append('node4')
+    node.children['node4'].append('subnode3')
+    node.children['node4'].append('subnode4')
+    node.children['node4'].children['subnode3'].append('subsubnode1')
+
+    # mark node1 as deleted and remove
+    session.delete(node.children['node1'])
+
+    msg("Removed node1.  flush + commit:")
+    session.commit()
+
+    print "\n\n\n----------------------------"
+    print "Tree After Save:"
+    print "----------------------------"
+
+    # expire the "children" collection so that
+    # it reflects the deletion of "node1".
+    session.expire(node, ['children'])
+    print dump_tree(node)
+
+    msg("Emptying out the session entirely, "
+        "selecting tree on root, using eager loading to join four levels deep.")
+    session.expunge_all()
+    node = session.query(TreeNode).\
+                        options(eagerload_all("children", "children", 
+                                                "children", "children")).\
+                        filter(TreeNode.name=="rootnode").\
+                        first()
+
+    msg("Full Tree:")
+    print dump_tree(node)
+
+    msg( "Marking root node as deleted, flush + commit:" )
+
+    session.delete(node)
+    session.commit()
diff --git a/examples/adjacencytree/basic_tree.py b/examples/adjacencytree/basic_tree.py
deleted file mode 100644 (file)
index dec03e5..0000000
+++ /dev/null
@@ -1,129 +0,0 @@
-"""A basic Adjacency List model tree."""
-
-from sqlalchemy import MetaData, Table, Column, Sequence, ForeignKey
-from sqlalchemy import Integer, String
-from sqlalchemy.orm import create_session, mapper, relation, backref
-from sqlalchemy.orm.collections import attribute_mapped_collection
-
-metadata = MetaData('sqlite:///')
-metadata.bind.echo = True
-
-trees = Table('treenodes', metadata,
-    Column('id', Integer, Sequence('treenode_id_seq', optional=True),
-           primary_key=True),
-    Column('parent_id', Integer, ForeignKey('treenodes.id'), nullable=True),
-    Column('name', String(50), nullable=False))
-
-
-class TreeNode(object):
-    """a rich Tree class which includes path-based operations"""
-    def __init__(self, name):
-        self.name = name
-        self.parent = None
-        self.id = None
-        self.parent_id = None
-    def append(self, node):
-        if isinstance(node, str):
-            node = TreeNode(node)
-        node.parent = self
-        self.children[node.name] = node
-    def __repr__(self):
-        return self._getstring(0, False)
-    def __str__(self):
-        return self._getstring(0, False)
-    def _getstring(self, level, expand = False):
-        s = ('  ' * level) + "%s (%s,%s, %d)" % (
-            self.name, self.id,self.parent_id,id(self)) + '\n'
-        if expand:
-            s += ''.join([n._getstring(level+1, True)
-                          for n in self.children.values()])
-        return s
-    def print_nodes(self):
-        return self._getstring(0, True)
-
-mapper(TreeNode, trees, properties={
-    'children': relation(TreeNode, cascade="all",
-                         backref=backref("parent", remote_side=[trees.c.id]),
-                         collection_class=attribute_mapped_collection('name'),
-                         lazy=False, join_depth=3)})
-
-print "\n\n\n----------------------------"
-print "Creating Tree Table:"
-print "----------------------------"
-
-trees.create()
-
-node2 = TreeNode('node2')
-node2.append('subnode1')
-node = TreeNode('rootnode')
-node.append('node1')
-node.append(node2)
-node.append('node3')
-node.children['node2'].append('subnode2')
-
-print "\n\n\n----------------------------"
-print "Created new tree structure:"
-print "----------------------------"
-
-print node.print_nodes()
-
-print "\n\n\n----------------------------"
-print "Flushing:"
-print "----------------------------"
-
-session = create_session()
-session.add(node)
-session.flush()
-
-print "\n\n\n----------------------------"
-print "Tree After Save:"
-print "----------------------------"
-
-print node.print_nodes()
-
-node.append('node4')
-node.children['node4'].append('subnode3')
-node.children['node4'].append('subnode4')
-node.children['node4'].children['subnode3'].append('subsubnode1')
-del node.children['node1']
-
-print "\n\n\n----------------------------"
-print "Modified the tree"
-print "(added node4, node4/subnode3, node4/subnode4,"
-print "node4/subnode3/subsubnode1, deleted node1):"
-print "----------------------------"
-
-print node.print_nodes()
-
-print "\n\n\n----------------------------"
-print "Flushing:"
-print "----------------------------"
-session.flush()
-
-print "\n\n\n----------------------------"
-print "Tree After Save:"
-print "----------------------------"
-
-print node.print_nodes()
-
-nodeid = node.id
-
-print "\n\n\n----------------------------"
-print "Clearing session, selecting "
-print "tree new where node_id=%d:" % nodeid
-print "----------------------------"
-
-session.expunge_all()
-t = session.query(TreeNode).filter(TreeNode.id==nodeid)[0]
-
-print "\n\n\n----------------------------"
-print "Full Tree:"
-print "----------------------------"
-print t.print_nodes()
-
-print "\n\n\n----------------------------"
-print "Marking root node as deleted"
-print "and flushing:"
-print "----------------------------"
-session.delete(t)
-session.flush()