1

I want to write a function which takes the name of a variable, a file name, and a third string, and tries to import the given variable from the file and if it can not do that, it sets the variable to the third string. Let me show you. This is in my config.py:

variable = 'value'

This is my function (it doesn't work):

#!/usr/bin/python

def importvar (var, fname, notfound) :

    try:
        from fname import var

    except:
        var = notfound

    return var;

value = importvar ('variable', 'config', 'value not found')

print value     #prints 'value not found'

This is what I am trying to achieve:

from config import variable

print variable     #prints 'value'

This question is similar to "How to use a variable name as a variable in python?", but the answers I found to those didn't seem to work for me. I don't necessarily need to store them in a variable, but I couldn't come up with anything better. I know this is a perfect example of "What you shouldn't do in python", but I still need this. Thanks for the help!

3
  • What you want to do is using import_module docs.python.org/3/library/… Commented Aug 4, 2018 at 16:51
  • But really you should explain why you think you need this. Commented Aug 4, 2018 at 17:06
  • @DanielRoseman I need to import many variables from many different files in one project, and i want do not want to type this try... else... so many times Commented Aug 4, 2018 at 17:08

4 Answers 4

4

What you want to do is dynamically importing a module starting from a string describing the path of the module. You can do this by using import_module from the importlib package.

import importlib

def importvar (var, fname, notfound) :
    try:
        return getattr(importlib.import_module(fname), var)
    except:
        return notfound
Sign up to request clarification or add additional context in comments.

1 Comment

Great answer! Exactly what I was looking for!
2

This should give you the clue:

>>> from importlib import import_module
>>> config = import_module('config')
>>> print( getattr(config, 'variable') )
value

See the docs for getattr.
Basically, getattr(x, 'variable') is equivalent to x.variable

2 Comments

This is not enough, since the OP wants to pass the module (config in this case) dynamically as well.
This doesn't handle the case where variable is submodule of config.
1

a function for import & return imported variable:

def importvar (var, fname, notfound):
    try:
        exec('from {f} import {v}'.format(f=fname, v=var))
        return locals().get(var, notfound)
    except:
        return notfound

3 Comments

return locals().get(var) is enough, you don't need to provide an 'else' because try stops when it cannot execute importing the variable
@TheAdam122 Not true. locals().get(value) == locals().get(value, None)
@ppperry I know, but less typing is always better in my opinion :)
0

If you just want a simple import from a string, the __import__ builtin may be good enough. It takes the module name as a string and returns it. If you also need to get an attribute from it programmatically use the builtin getattr, which takes the attribute name as a string.

If you're trying to import a package submodule, though, importlib.import_module is easier--you can import a name with a dot in it and get the module directly. This just calls __import__ for you. Compare __import__("logging.config").config vs import_module("logging.config").

If you're trying to import an arbitrary file not on the Python path, it gets a little more involved. The Python docs have a recipe for this.

import importlib.util

spec = importlib.util.spec_from_file_location(module_name, file_path)
module = importlib.util.module_from_spec(spec)
spec.loader.exec_module(module)

Unlike __import__, this doesn't add the module to the cache, because it doesn't have a canonical import name. But you can add it yourself (using whatever name you want) if you want to import it normally later, e.g.

import sys
sys.modules["foo_module"] = module

After running this, it allows you to get the same module instance again with a simple

import foo_module

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.