Steven D'Aprano <st...@remove-this-cybersource.com.au> writes: > I have a bunch of related functions and objects which are private to a > module, with a single public function that acts as the API to those > functions. I'd like to have these private functions in a namespace, > separate from the rest of the module. Ignore the fact that they are > private functions -- I can deal with that by the usual naming > convention. Focus on the "separate namespace" aspect. > > What I want is the ability to write this: > > create Namespace: > def function(x): > return x > > def func(y): > return function("spam") + "'n'" + y > > dispatch = {1: func, 2: function} > > def another_func(z): > return len(dispatch[2](z))
Can you make it concrete, by naming the namespace something meaningful or arbitrary? It's as though you wanted to discuss a function, and named it “function”. (Oh, you did that too :-) I'll assume an example of a namespace for the storage backends of a library, and that you want a namespace of ‘storage’. If you can provide the actual use case that presents this problem to you, that would be best. Running with my contrived example, I take your option (2) below: use a private module as a private namespace. In the file ‘_storage’: def backend_foo(x): return x def backend_bar(x): return backend_foo("spam") + "'n'" + x dispatch = {1: backend_bar, 2: backend_foo} > func("eggs") # raises NameError > Namespace.func("eggs") # returns "spam'n'eggs" > > Namespace.dispatch[1]("cheese") # returns "spam'n'cheese" import _storage backend_bar("eggs") # raises NameError _storage.backend_bar("eggs") # returns "spam'n'eggs" _storage.dispatch[1]("cheese") # returns "spam'n'cheese" > (2) Place them in a separate module, and import the module, similar to > the way that the os module imports path. This is certainly possible, > and it works well, but it splits code into two files when it should be > in one. Why should it be in one? If a separate module works well, there needs to be a good reason not to do it. > It pollutes the module namespace, and Guido has recently expressed > mild objection to new code doing what os does. Or at least he > suggested that we shouldn't *encourage* doing what os does. The single-leading-underscore naming convention makes it clear that the module is a private implementation detail, and signals to the reader that the module is not advisable for import except as part of that implementation. That refutes the charge of polluting the module namespace. As for Guido's opinion on the matter, for whatever it's worth, those interested are invited to read recent ‘python-dev’ discussions on APIs <URL:http://mail.python.org/pipermail/python-dev/2010-November/105703.html>. In short, I think he agrees with my position above. > (3) Redesign my module to use a full package structure, and place the > functions in a separate module in the package. It's overkill to have a > package for just two namespaces (modules). I disagree strongly. Two modules is not too few for a package; it certainly isn't “overkill”. Packages are quite lightweight for what they do. If they solve a problem well, I don't see why to discard them without a better reason. For all the other options you enumerated I am in agreement with your position. Thanks for making it more concrete so we know what problem we're supposed to be grappling. -- \ “Nothing is more sacred than the facts.” —Sam Harris, _The End | `\ of Faith_, 2004 | _o__) | Ben Finney -- http://mail.python.org/mailman/listinfo/python-list