ArcGIS Python Toolboxでインポートされたモジュールを更新しますか?


15

ArcMapでPythonツールボックス(.pyt)を使用する場合、通常、.pytファイル自体が単なる入力引数を収集してツール自体を定義するラッパーであるパターンに従います。サポートコードは、個別のユニットテスト可能なモジュールに保持されます。

例:

import supporting_module

class MyTool(object):

    ...

    def execute(self, parameters, messages):
        """The source code of the tool."""
        some_input = parameters[0].valueAsText
        some_output = parameters[1].valueAsText

        supporting_module.do_something(some_input, some_output)
        arcpy.SetParameter(2, some_output)

これは非常にうまく機能しますが、開発中にイライラする問題に遭遇しました。ArcMapの.pytを右クリック->更新すると、.pytファイルのコードのみが更新されます。インポートされたモジュールは更新されないため、そこで何かを変更するたびにArcMapを閉じて、再度開く必要があります。幸いなことに、私は独立してコードをテストしているので、これを大量に行う必要はありませんが、それでも大きな手間がかかります。これを回避する方法はありますか?多少関連があります-Pythonコンソールを完全に更新する方法はありますか(カスタムサイトパッケージがあるので、ArcMapを閉じたり開いたりして変更を取得する必要があります)?

ArcMap 10.2.1を使用しています。

回答:


14

私はこの可能性を見つけました、https://stackoverflow.com/questions/1517038/python-refresh-reload

1つの注意点は、モジュールに変数が割り当てられている場合、変数を再度割り当てる必要があることです。

ただし、上記のとおり、次のようにできます。

import supporting_module
def execute()
  reload(supporting_module)
  ...

このようにして、ツールを実行するたびに、更新されたモジュールを確実に入手できます。開発が完了したら、これを取り出すことができます。


1
非常に役立ち、これは私が投稿した簡単な例を解決します。ただし、supporting_moduleが他のヘルパーモジュールもインポートする場合は、リロードで呼び出す必要もあります。Pythonがモジュールをロードする方法で理にかなっているので、これが最善だと思います。翌日かそれよりも堅牢なものが登場しない場合は、答えとしてマークします。
ジョシュワーツ14年

非常に役立ちます。reload()ツールボックスのPYTファイルの上部で、サポートモジュールをインポートした直後に呼び出すだけで十分であることがわかりました。したがって、ツールボックスに複数のツールが含まれている場合、各ツールのexecute()機能でリロードを複製する必要はありません。
マイクフィンチ

このanwserがどのように問題を解決するのか本当にわかりません。私がしている私のツールの.pyファイルに保存されていると私は彼らが使用して、インポートfrom pyfile import Toolの追加、reload(tool)リターンをtypeError: reload() argument must be module。何か案は?
ラタニル

2
私は解決策を見つけました!py-Fileを最初にモジュールとしてインポートし、リロードしてからモジュール内のクラスをインポートします。参照:stackoverflow.com/a/6946467/4139249
ラタニール

5

これは、以前に提案したものとは異なる、より堅牢な方法です。

私は自分でこのモジュールを使用したことはありませんが、あなたの問題は解決すると思います。

Pythonモジュールリローダー

このライブラリは、Python用の依存関係ベースのモジュールリローダーを実装しています。組み込みのreload()関数とは異なり、このリローダーは要求されたモジュールとそのモジュールに依存する他のすべてのモジュールをリロードします。

前の例を考えると、これはすべての依存関係を1回の呼び出しでロードするはずです。

import reloader
reloader.enable()

import supporting_module

def execute()
  reloader.reload(supporting_module)
  ...

このモジュールに気付いたのはこれが初めてなので、ツールに実装する場合は、それがどのように機能するかについてコメントしてください。


良い発見!これは、表示どおりに追加すると機能しました。.pytファイル自体が変更された場合、ツールボックスを右クリック->更新するだけです。サポートしているモジュールとそのサブモジュールは正常にリロードされています。ただし、注意すべき点がいくつかあります。説明のつかない例外がいくつか発生し、ArcMapがクラッシュしました(ただし、ArcMapのクラッシュは実際にはそれほど異常ではありませんが、残念ながら)。注-これは、サポートモジュールと1つの依存サブモジュールでのみテストしました。将来の安定性について報告する場合があります。
ジョシュワーツ14年

1
スーパー、ご報告ありがとうございます。ええ、ArcMapを運転するとき、時々クラッシュテストダミーのように感じます。
cndnflyr 14年

残念ながら、このリローダーでは安定性の問題が多すぎるため、選択した回答を元のreload()組み込み関数に変更しました。時にはシンプルな方が良い!
ジョシュワーツ14年
弊社のサイトを使用することにより、あなたは弊社のクッキーポリシーおよびプライバシーポリシーを読み、理解したものとみなされます。
Licensed under cc by-sa 3.0 with attribution required.