2010-06-03 63 views
7

我想在Python 3中創建一個構造,這將允許我輕鬆地在遠程計算機上執行一個函數。 假設我已經有將要運行它接收到的功能,在遠程服務器上運行一個Python TCP服務器,我目前考慮使用像如何將python函數複製到遠程機器然後執行它?

@execute_on(address, port) 

這是一個裝飾將創造需要必要的上下文執行正在裝飾的函數,然後將函數和上下文發送到遠程機器上的tcp服務器,然後執行它。首先,這是否有點理智?如果不是,你能推薦一個更好的方法嗎?我做了一些谷歌搜索,但沒有發現任何符合這些需求的東西。

我有一個快速和骯髒的實施tcp服務器和客戶端,所以相當肯定會工作。我可以得到的字符串表示的功能(例如FUNC)由

import inspect 
string = inspect.getsource(func) 

然後可以被髮送到其中可以執行服務器被傳遞到裝飾。問題是,我如何獲得該函數執行所需的所有上下文信息?例如,如果func被定義如下,

import MyModule 
def func(): 
    result = MyModule.my_func() 

MyModule的需要提供給FUNC或者在全球範圍內或funcs中的遠程服務器上的本地上下文。在這種情況下,這是相對平凡的,但取決於何時以及如何使用導入語句,它可能會變得更加複雜。有沒有一種簡單而優雅的方式來在Python中做到這一點?目前最好的方法是使用ast庫來提取所有導入語句,使用inspect模塊獲取這些模塊的字符串表示,然後重新構建遠程服務器上的整個上下文。不是特別優雅,我可以看到很多錯誤的空間。

感謝您的時間

回答

0

您的最終目標是什麼?從你的描述中,我可以看到沒有理由不能創建一個簡單的消息類,併發送它的實例來命令遠程機器執行'stuff'..?

無論你做什麼,你的遠程機器都需要Python源代碼來執行,爲什麼不把代碼分發到那裏然後運行呢?你可以創建一個簡單的服務器,它將接受一些python源文件,提取它們導入相關的模塊,然後運行命令?

2

除非遠程服務器受到很強的保護或「極度沙箱化」(例如BSD「監獄」) - 任何可以向其發送函數的人都可以在其中運行任意代碼。

假設你有一個你完全信任的認證系統,就會出現你意識到的「脆弱性」問題 - 該函數可以依賴於在執行時在其模塊中定義的任何全局變量(這可能與你可以通過檢查來檢測:在執行時確定導入模塊的集合,更一般地確定全局模型是一個圖靈完備問題)。

在遠程執行時,您可以通過序列化函數的全局變量以及函數本身來處理全局問題(無論是以可讀的字符串形式將所有這些內容序列化,還是以其他方式一個小問題)。但是,這仍然留下您與進口問題裏面的功能。

除非你願意戴上了「遠程的」功能一些限制,如「在函數內部沒有進口(和功能,從它的稱呼)」,我想,你可以讓服務器覆蓋__import__ (所有導入語句都使用的內置函數,並且被設計爲被特殊需要覆蓋,比如你的;-),以從發送客戶端請求額外的模塊(當然,這要求所述客戶端也有「類似服務器」的能力,因爲它必須能夠響應來自服務器的這種「模塊請求」)。

難道你不能強制一些限制了遠程功能,使這項任務重新回到理智的領域......?

2

您可能對execnet項目感興趣。

execnet提供經過仔細測試的方法,可以輕鬆與跨越版本,平臺和網絡障礙的Python解釋器進行交互。它有一個最小的和快速的API靶向以下用途:

  • 任務分配到本地或遠程的CPU
  • 編寫和部署混合多處理應用
  • 寫腳本來管理一幫高管環境

http://codespeak.net/execnet/example/test_info.html#get-information-from-remote-ssh-account

我已經看到它的演示。但是從來沒有用過它。

+0

對於execnet爲+1。我用它來以分佈式方式執行一些測試用例,它效果很好。 – 2010-06-03 05:14:27

0

這可能很難做,你會遇到安全性,參數等問題。 也許你可以遠程運行一個Python解釋器,它可以使用套接字或HTTP服務給出代碼而不是執行它在功能級別的功能?

相關問題