By using this site, you agree to our updated Privacy Policy and our Terms of Use. Manage your Cookies Settings.
445,678 Members | 1,144 Online
Bytes IT Community
+ Ask a Question
Need help? Post your question and get tips & solutions from a community of 445,678 IT Pros & Developers. It's quick & easy.

Get importer module from imported module

P: n/a

I found this problem when trying to split a module into two.
Here's an example:

==============
#Module a (a.py):
from b import *
class Main: pass
==============

==============
#Module b (b.py)
def How():
Main_instance = module_a.Main()
return Main_instance
==============
import a
a.How()

the problem would show at How() function. I have been unable
to get variable pointing to module a from inside module b.
In short, I need to have a variable pointing to the module
whose importing me.
--
dody s wijaya <do****@gmail.com>, YM: dody, [36932B53]

Jul 18 '05 #1
Share this Question
Share on Google+
5 Replies


P: n/a
dody suria wijaya wrote:

I found this problem when trying to split a module into two.
Here's an example:

==============
#Module a (a.py):
from b import *
class Main: pass
==============

==============
#Module b (b.py)
def How():
Main_instance = module_a.Main()
return Main_instance
==============
import a
a.How()

the problem would show at How() function. I have been unable
to get variable pointing to module a from inside module b.
In short, I need to have a variable pointing to the module
whose importing me.


'import a' will let you reference module 'a', unless 'a' was invoked as a
script in which case you would need 'import __main__'.

#Module b (b.py)
import a
def How():
Main_instance = a.Main()
return Main_instance

But: keep in mind that all statements (except 'global') are executable in
Python, so you must not call How() until after the Main class has actually
been created. This is one reason why it is generally safer to import a
module and do the lookup when you need it instead of using 'from
amodule import *' which can only get at the names which exist at the time
it is executed.

A better solution would be to structure your code so that your modules
don't have any mutual dependencies. If your function 'How()' is in module b
then just call 'b.How()' wherever you use it and lose the import of 'b'
from 'a' altogether.
Jul 18 '05 #2

P: n/a
Thank you for such a quick reply. There were some details I
had left behind related to my case that I guess would now
need to be told to better illustrate the problem.

I have many different module of "a", let's called it a1, a2 ...
a100, and there is only one module "b". Here's a better
example (and using some of your tips):

#Module a1
import b
class Main(b.Basic): pass

#Module a2
import b
class Main(b.Basic): pass

#Module a3
import b
class Main(b.Basic): pass

..
..
..

#Module b
class Basic: pass
class SaltyMixIn: pass
class SugaryMixIn: pass
def Salty():
class Food(SaltyMixIn,module_importing_me.Main): pass
return Food()
def Sweet():
class Food(SugaryMixIn,module_importing_me.Main): pass
return Food()

#Module c
import sys
food_no = sys.argv[1]
m = __import__(food_no)
goodie = m.Salty()
"import a" inside b would not solve the problem, since there
are many "module a" and module b does not know beforehand
which module had imported it. I could, say, put these
additional lines on all "module a" (which I previously had
and worked):

#Module a1
import b
class Main(b.Basic): pass
class Salty(SaltyMixIn,Main): pass # new
class Sweet(SaltyMixIn,Main): pass # new
but dislike it for personal taste; code dupes (there could
be a lot of food flavouring), and sheer messiness.
--
dody suria wijaya
YahooMsgr ID: dody

Monday, February 7, 2005, 6:10:14 PM, you wrote:

DB> dody suria wijaya wrote:

I found this problem when trying to split a module into two.
Here's an example:

==============
#Module a (a.py):
from b import *
class Main: pass
==============

==============
#Module b (b.py)
def How():
Main_instance = module_a.Main()
return Main_instance
==============
import a
a.How()

the problem would show at How() function. I have been unable
to get variable pointing to module a from inside module b.
In short, I need to have a variable pointing to the module
whose importing me.


DB> 'import a' will let you reference module 'a',
DB> unless 'a' was invoked as a
DB> script in which case you would need 'import __main__'.

DB> #Module b (b.py)
DB> import a
DB> def How():
DB> Main_instance = a.Main()
DB> return Main_instance

DB> But: keep in mind that all statements (except
DB> 'global') are executable in
DB> Python, so you must not call How() until after the Main class has actually
DB> been created. This is one reason why it is
DB> generally safer to import a
DB> module and do the lookup when you need it instead of using 'from
DB> amodule import *' which can only get at the names which exist at the time
DB> it is executed.

DB> A better solution would be to structure your code so that your modules
DB> don't have any mutual dependencies. If your
DB> function 'How()' is in module b
DB> then just call 'b.How()' wherever you use it and lose the import of 'b'
DB> from 'a' altogether.

Jul 18 '05 #3

P: n/a
dody suria wijaya wrote:
"import a" inside b would not solve the problem, since there
are many "module a" and module b does not know beforehand
which module had imported it.
Ok, I understand now what you are trying to achieve, but there isn't any
concept relating a module back to the first module which tried to import
it. Instead you'll have to specify the relationship yourself.

How about this:
#Module c import sys
food_no = sys.argv[1]
m = __import__(food_no)
goodie = b.Salty(m)
#Module b ....
def Salty(module):
class Food(SaltyMixIn,module.Main): pass
return Food()
....

In fact, it looks like the importing isn't really something module c should
be concerned about. I haven't tested the following code (so it will have
bugs), but it should give you some ideas. It remembers classes it has
created so as not to duplicate them, and it also gives each class a
sensible name.
#Module c import sys
food_no = sys.argv[1]
goodie = b.Salty(food_no)
#Module b

....
import new
Classes = {}

def makeFood(classname, food, mixin):
m = __import__(food)
main = m.Main
if (mixin, main) in Classes:
return Classes[mixin, main]()

newclass = new.classobj(classname + '_' + food, (mixin, main), {})
Classes[mixin, main] = newclass
return newclass
def Salty(food):
return makeFood('Salty', food, SaltyMixIn)
....

Jul 18 '05 #4

P: n/a
Yup, Got it.

New problem though. On line:

newclass = new.classobj(classname + '_' + food, (mixin, main), {})

received "TypeError: metaclass conflict: the metaclass of a
derived class must be a (non-strict) subclass of the
metaclasses of all its bases". This had not happened when
was written using 'normal' style like:

class (SaltyMixIn, Main): pass

--
dody suria wijaya
YahooMsgr ID: dody

Monday, February 7, 2005, 7:20:14 PM, you wrote:

DB> dody suria wijaya wrote:
"import a" inside b would not solve the problem, since there
are many "module a" and module b does not know beforehand
which module had imported it.
DB> Ok, I understand now what you are trying to
DB> achieve, but there isn't any
DB> concept relating a module back to the first module which tried to import
DB> it. Instead you'll have to specify the relationship yourself.

DB> How about this:
#Module c DB> import sys
DB> food_no = sys.argv[1]
DB> m = __import__(food_no)
DB> goodie = b.Salty(m)
#Module b DB> ...
DB> def Salty(module):
DB> class Food(SaltyMixIn,module.Main): pass
DB> return Food()
DB> ...

DB> In fact, it looks like the importing isn't really
DB> something module c should
DB> be concerned about. I haven't tested the following code (so it will have
DB> bugs), but it should give you some ideas. It remembers classes it has
DB> created so as not to duplicate them, and it also gives each class a
DB> sensible name.
#Module c DB> import sys
DB> food_no = sys.argv[1]
DB> goodie = b.Salty(food_no)
#Module b

DB> ...
DB> import new
DB> Classes = {}

DB> def makeFood(classname, food, mixin):
DB> m = __import__(food)
DB> main = m.Main
DB> if (mixin, main) in Classes:
DB> return Classes[mixin, main]()

DB> newclass = new.classobj(classname + '_' + food, (mixin, main), {})
DB> Classes[mixin, main] = newclass
DB> return newclass
DB> def Salty(food):
DB> return makeFood('Salty', food, SaltyMixIn)
DB> ...
Jul 18 '05 #5

P: n/a
dsw> New problem though. On line:
dsw> newclass = new.classobj(classname + '_' + food, (mixin, main), {})
dsw> received "TypeError: metaclass conflict: the metaclass of a
dsw> derived class must be a (non-strict) subclass of the
dsw> metaclasses of all its bases".

Oops, goofed up on me. The above "main" had mistakenly
pointed to the module. main.Main did the trick.

-- dsw

Jul 18 '05 #6

This discussion thread is closed

Replies have been disabled for this discussion.