dialects can be used on their own without the engine being present  
(such as, to generate SQL), also you can construct an engine passing  
in your own module object which might have been procured from  
somewhere else (or could be a mock object,for example).

On Mar 26, 2007, at 11:45 PM, Monty Taylor wrote:

>
> Always one in every bunch. :)
>
> I hear what you're saying about the import errors. But does it really
> help to allow work to get done before throwing the error? I would  
> think
> you'd want to know right up front if you don't have a driver loaded
> rather then letting a program actually get started up and think you  
> can
> write data (think fat client app) only to get a connection exception.
>
> But I, of course, could be very wrong about this. I am about many  
> things...
>
> Monty
>
> Michael Bayer wrote:
>>
>> yeah i dont like setup.py develop either :)....but anyway,  patch is
>> good.  one thing i have to nail down though is ticket #480.   the
>> main point of that ticket is to cleanly isolate ImportErrors of
>> actual DBAPI modules apart from the containing dialect module
>> itself.   the dialects are catching all the DBAPI-related
>> ImportErrors though so its not necessarily blocking this patch (its
>> just they cant report them nicely).
>>
>>
>> On Mar 26, 2007, at 1:34 PM, Monty Taylor wrote:
>>
>>> Michael Bayer wrote:
>>>> i think using entry points to load in external database dialects  
>>>> is a
>>>> great idea.
>>>>
>>>> though the current six core dialects i think i still want to  
>>>> load via
>>>> __import__ though since im a big fan of running SA straight out of
>>>> the source directory (and therefore thered be no entry points for
>>>> those in that case).
>>>>
>>>> so probably a check via __import__('sqlalchemy.databases') first,
>>>> then an entry point lookup.  does that work ?
>>> Here is a patch that implements use of entry points to load  
>>> dialects.
>>> The largest change is actually adding a get_dialect to replace the
>>> functionality of get_module, since entry points really want to  
>>> return
>>> classes, and we only ever use the dialect class from the returned
>>> module
>>> anyway...
>>>
>>> This does not break code that I have that loads the mysql  
>>> dialect, and
>>> it does work with my new code that adds a new dialect - although I
>>> suppose it's possible it could have broken something I didn't find.
>>>
>>> As a side note, I agree with Gaetan - you can run entry points and
>>> stuff
>>> out of the current directory, especially if you use setup.py
>>> develop ...
>>> but this code does the entry points second, after a check for the
>>> module
>>> the old way.
>>>
>>> Monty
>>>
>>>
>>> === modified file 'lib/sqlalchemy/engine/strategies.py'
>>> --- lib/sqlalchemy/engine/strategies.py     2007-02-25 22:44:52 +0000
>>> +++ lib/sqlalchemy/engine/strategies.py     2007-03-26 17:03:13 +0000
>>> @@ -42,16 +42,16 @@
>>>          u = url.make_url(name_or_url)
>>>
>>>          # get module from sqlalchemy.databases
>>> -        module = u.get_module()
>>> +        dialect_cls = u.get_dialect()
>>>
>>>          dialect_args = {}
>>>          # consume dialect arguments from kwargs
>>> -        for k in util.get_cls_kwargs(module.dialect):
>>> +        for k in util.get_cls_kwargs(dialect_cls):
>>>              if k in kwargs:
>>>                  dialect_args[k] = kwargs.pop(k)
>>>
>>>          # create dialect
>>> -        dialect = module.dialect(**dialect_args)
>>> +        dialect = dialect_cls(**dialect_args)
>>>
>>>          # assemble connection arguments
>>>          (cargs, cparams) = dialect.create_connect_args(u)
>>> @@ -71,7 +71,7 @@
>>>                      raise exceptions.DBAPIError("Connection
>>> failed", e)
>>>              creator = kwargs.pop('creator', connect)
>>>
>>> -            poolclass = kwargs.pop('poolclass', getattr(module,
>>> 'poolclass', poollib.QueuePool))
>>> +            poolclass = kwargs.pop('poolclass', getattr
>>> (dialect_cls, 'poolclass', poollib.QueuePool))
>>>              pool_args = {}
>>>              # consume pool arguments from kwargs, translating a
>>> few of the arguments
>>>              for k in util.get_cls_kwargs(poolclass):
>>>
>>> === modified file 'lib/sqlalchemy/engine/url.py'
>>> --- lib/sqlalchemy/engine/url.py    2007-03-18 22:35:19 +0000
>>> +++ lib/sqlalchemy/engine/url.py    2007-03-26 16:47:01 +0000
>>> @@ -2,6 +2,7 @@
>>>  import cgi
>>>  import sys
>>>  import urllib
>>> +import pkg_resources
>>>  from sqlalchemy import exceptions
>>>
>>>  """Provide the URL object as well as the make_url parsing
>>> function."""
>>> @@ -69,6 +70,23 @@
>>>              s += '?' + "&".join(["%s=%s" % (k, self.query[k]) for
>>> k in keys])
>>>          return s
>>>
>>> +    def get_dialect(self):
>>> +        """Return the SQLAlchemy database dialect class
>>> corresponding to this URL's driver name."""
>>> +        dialect=None
>>> +        try:
>>> +          module=getattr(__import__('sqlalchemy.databases.%s' %
>>> self.drivername).databases, self.drivername)
>>> +          dialect=module.dialect
>>> +        except ImportError:
>>> +            if sys.exc_info()[2].tb_next is None:
>>> +              for res in pkg_resources.iter_entry_points
>>> ('sqlalchemy.databases'):
>>> +                if res.name==self.drivername:
>>> +                  dialect=res.load()
>>> +            else:
>>> +               raise
>>> +        if dialect is not None:
>>> +            return dialect
>>> +        raise exceptions.ArgumentError('unknown database %r' %
>>> self.drivername)
>>> +
>>>      def get_module(self):
>>>          """Return the SQLAlchemy database module corresponding to
>>> this URL's driver name."""
>>>          try:
>>>
>>> === modified file 'setup.py'
>>> --- setup.py        2007-03-23 21:33:24 +0000
>>> +++ setup.py        2007-03-26 17:01:51 +0000
>>> @@ -10,6 +10,10 @@
>>>      url = "http://www.sqlalchemy.org";,
>>>      packages = find_packages('lib'),
>>>      package_dir = {'':'lib'},
>>> +    entry_points = {
>>> +      'sqlalchemy.databases': [
>>> +        '%s = sqlalchemy.databases.%s:dialect' % (f,f) for f in
>>> +          ['sqlite', 'postgres', 'mysql', 'oracle', 'mssql',
>>> 'firebird']]},
>>>      license = "MIT License",
>>>      long_description = """\
>>>  SQLAlchemy is:
>>>
>>
>>
>>>
>
>
> >


--~--~---------~--~----~------------~-------~--~----~
You received this message because you are subscribed to the Google Groups 
"sqlalchemy" group.
To post to this group, send email to sqlalchemy@googlegroups.com
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