On 09/02/2012 15:47, Chris Withers wrote:
My thinking was leaning towards actually abandoning the full declarative
base and coming up with a light weight one (or maybe even class
decorator) that basically added recorded the class in a sequence (much
like the declarative reflection does) and then calls
instrument_declarative with each class at the point of relfection.

Well, it's a bit vom-tastic but I got this working. Here it is minus the imports:

# The registries
meta = MetaData()
registry = {}

# The declarative bases

class ReflectedMeta(type):

    _classes_to_process = []

    def __new__(meta, classname, bases, classDict):
        cls = type.__new__(meta, classname, bases, classDict)
        meta._classes_to_process.append(cls)
        return cls

    @classmethod
    def prepare(meta, engine, metadata):

        for cls in meta._classes_to_process:

            tablename = vars(cls).get('__tablename__')
            if tablename is not None:
                try:
                    table = Table(
                        tablename,
                        MetaData(),
                        autoload=True,
                        autoload_with=engine,
                        )
                except NoSuchTableError:
                    continue

                for col in table.c:
                    if getattr(cls, col.name, None) is None:
                        col = col.copy()
                        if col is None:
                            raise Exception()
                        setattr(cls, col.name, col)

            kw = vars(cls).get('__mapper_args__')
            if kw is not None:
                # deal with cases where we need to specify the primary key
                # structure
                primary_key_names = kw.pop('primary_key_names', None)
                if primary_key_names:
                    kw['primary_key'] = pk = []
                    for name in primary_key_names:
                        pk.append(getattr(cls, name))
                # Likewise for polymorphic_on
                polymorphic_on_name = kw.pop('polymorphic_on_name', None)
                if polymorphic_on_name:
                    kw['polymorphic_on'] = getattr(cls,
polymorphic_on_name)

            instrument_declarative(cls, registry, metadata)

# The this one for reflected models:
class Reflected(object):
    __abstract__ = True
    __metaclass__ = ReflectedMeta

# Use this one for concretely mapped models:
Base = declarative_base(metadata=meta, class_registry=registry)

Then, once I have a connection and I'm ready to reflect, I do:

    ReflectedMeta.prepare(engine, meta)

Is the above sane?

Chris

--
Simplistix - Content Management, Batch Processing & Python Consulting
            - http://www.simplistix.co.uk

--
You received this message because you are subscribed to the Google Groups 
"sqlalchemy" group.
To post to this group, send email to [email protected].
To unsubscribe from this group, send email to 
[email protected].
For more options, visit this group at 
http://groups.google.com/group/sqlalchemy?hl=en.

Reply via email to