id,summary,reporter,owner,description,type,status,priority,component,severity,resolution,keywords,cc
34,Making it easier to use libyaml in PyYAML,edemaine@…,xi,"I really like PyYAML with the libyaml ""plugin"".  I've been using it a lot without any troubles.  So hopefully it will make it out of alpha soon :-).  I have a couple of suggestions with respect to seamlessness between PyYAML in Python mode and PyYAML in C mode.

1. {{{yaml.load}}}'s default {{{Loader}}}.  I would suggest that this becomes {{{CLoader}}} when it is available (i.e., when {{{yaml.cyaml}}} imports successfully).

2. {{{yaml.dump}}}'s and {{{yaml.safe_dump}}}'s default {{{Dumper}}}s.  Ditto.

3. {{{Loader}}} vs. {{{CLoader}}}, {{{Dumper}}} vs. {{{CDumper}}}, {{{Emitter}}} vs. {{{CEmitter}}}, etc.   I would like a uniform way (without using {{{if}}}'s) to subclass from the C version of these classes when they are available, and otherwise the Python versions of these classes.  One possible solution:
  * Python {{{Loader}}} etc. classes get renamed to {{{PyLoader}}}, {{{PythonLoader}}}, {{{PLoader}}}, or something along those lines.
  * {{{Loader}}} becomes an alias to {{{CLoader}}} or {{{PyLoader}}}, whichever is the best available.
  * It could also be possible to control the aliases by a function call, e.g., to force them to the Python version.  Perhaps:
    {{{
def set_language(lang):
  """"""default supported languages: 'C', 'Python'""""""
  import yaml
  global Loader, Dumper, Emitter, ...
  Loader = yaml.__dict__[lang + 'Loader']
  Dumper = yaml.__dict__[lang + 'Dumper']
  Emitter = yaml.__dict__[lang + 'Emitter']
  ...
try:
  set_language('C')
except KeyError:
  set_language('Py')
}}}

Currently all of my code that imports {{{yaml}}} starts like this:

{{{
import yaml
if hasattr (yaml, 'CLoader'):
  Loader = yaml.CLoader
else:
  Loader = yaml.Loader
if hasattr (yaml, 'CDumper'):
  Dumper = yaml.CDumper
  SafeDumper = yaml.CSafeDumper
else:
  Dumper = yaml.Dumper
  SafeDumper = yaml.SafeDumper
def yaml_load (x):
  return yaml.load (x, Loader = Loader)
def yaml_dump (x):
  return yaml.dump (x, Dumper = Dumper)
def yaml_safe_dump (x):
  return yaml.dump (x, Dumper = SafeDumper)
}}}

Then I use {{{yaml_load}}} in place of {{{yaml.load}}}, {{{yaml_dump}}} in place of {{{yaml.dump}}}, and I use {{{Loader}}} etc. whenever I want to subclass.  Needless to say, it's annoying to have to repeat this in all of my projects.

Another motivation for all this, I think, is that it's not obvious out-of-the-box how to use {{{CLoader}}} and friends.  I don't think the average user should have to know about this distinction.  If libyaml is installed, it should just work (faster).

A more minor point: Once out of alpha, could we replace {{{setup.py}}} and {{{setup_with_libyaml.py}}} with a single {{{setup.py}}} that does the right thing depending on what's available in the environment?  (If PyRex is installed, I don't see why we shouldn't install, unless a command-line option tells us not to.  Or even if RyRex isn't installed, as suggested in anotehr ticket.)",defect,assigned,normal,pyyaml,normal,,,
