2012-05-27 8 views
9

をPythonのクラスオブジェクトを取得する可能性の重複:
Dynamic module import in Python文字列から

おそらく単純な質問!私は、設定ファイルから渡されたクラスのリスト(文字列として)を反復処理する必要があります。クラスは以下のように記載されています:

TWO_FACTOR_BACKENDS = (
    'id.backends.AllowToBeDisabled', # Disable this to enforce Two Factor Authentication 
    'id.backends.TOTPBackend', 
    'id.backends.HOTPBackend', 
    #'id.backends.YubikeyBackend', 
    #'id.backends.OneTimePadBackend', 
    #'id.backends.EmailBackend', 
) 

私は今、(もちろん、コメントアウトしない限り)これらの各クラスにauthenticate()関数を呼び出す必要があります。私はリストを喜んで反復しています、私はちょうど私のforeachループでClassオブジェクトに文字列を変換する方法を知る必要があるので、私はそれにauthenticateメソッドを呼び出すことができます。これを行う簡単な方法はありますか?

+0

あなたは '()'クラスで呼び出さ認証をしたい、またはそれらのクラスのオブジェクトの上にいますか? – robert

+0

申し訳ありませんが、クラスのオブジェクトではなく、クラスに対して 'authenticate()'が呼び出されています。それをより明確にしなければならないのは残念です! –

答えて

34

the importlib moduleを使用してこのようなモジュールのロードを処理したい場合は、単にgetattr()を使用してクラスを取得します。例えば

、私はクラスTestを含むモジュール、somemodule.pyを持って言う:

import importlib 

cls = "somemodule.Test" 
module_name, class_name = cls.split(".") 

somemodule = importlib.import_module(module_name) 

print(getattr(somemodule, class_name)) 

は私を与える:

<class 'somemodule.Test'> 

それはパッケージのようなものに追加する些細です:

cls = "test.somemodule.Test" 
module_name, class_name = cls.rsplit(".", 1) 

somemodule = importlib.import_module(module_name) 

モジュール/パッケージが既にインポートされている場合はインポートされませんRTEDは、そう、あなたは喜んでロードモジュールを追跡することなくこれを行うことができます。

import importlib 

TWO_FACTOR_BACKENDS = (
    'id.backends.AllowToBeDisabled', # Disable this to enforce Two Factor Authentication 
    'id.backends.TOTPBackend', 
    'id.backends.HOTPBackend', 
    #'id.backends.YubikeyBackend', 
    #'id.backends.OneTimePadBackend', 
    #'id.backends.EmailBackend', 
) 

backends = [getattr(importlib.import_module(mod), cls) for (mod, cls) in (backend.rsplit(".", 1) for backend in TWO_FACTOR_BACKENDS)]