2011-03-12 136 views
13

我在想,是否有任何語言允許您在不重新加載整個應用程序的情況下即時添加/刪除/更新任何類? (假設我可以接受一些不便之處,例如確保目前沒有方法運行+額外的努力來「遷移」類數據成員)。哪種編程語言允許即時更新任何類?

Web應用程序,其中您替換1個文件,它用於下一個客戶端請求是不是我所需要的(如Perl,PHP)。應用程序必須連續運行,並且它有一些內部狀態。

其它要求是

  1. 沒有GIL或從利用SMP
  2. 優選地防止類似的問題 - JIT狀VM(即,其中性能接近於本機代碼)的存在。理想的解決方案是能夠在CLang或任何其他基於LLVM的語言中重新加載模塊。這將是完美的。

關於已取得的回答:

  • .NET/Java是不適合 - 它們都具有體積太大虛擬機,以及應用程序的顯著部分將在Linux上運行。
  • Erlang - 看起來好像是可能的,但這對我的肉眼來說太可怕了,我只是不能冷靜對待它,如果是,案例和字符串。此外,我寧願避免將裸源傳輸到客戶端,編譯的字節碼會更好。
+5

Appart從那個討厭的表現的事情,現代Ruby可能會適合您的需求。 – 2011-03-12 17:33:27

+0

我假設你需要一個JIT編譯器,而不是一個兼作DVCS的虛擬機? – delnan 2011-03-12 17:50:49

+0

JIT很高興有,但不是一個嚴格的要求。 – BarsMonster 2011-03-12 17:51:54

回答

5

Objective-C可能適合該法案。您可以使用here中記錄的函數在運行時添加新的類和交換方法實現,並且如果需要額外的實現,則可以在現有類上加載新的NSBundles和其他類或類別。 GNUStep雖然沒有實現蘋果最新的語言附加功能,但聲稱實現了這些功能(請參閱[1][2])。

+0

不是。你不能添加實例變量。 Pieter Schoenmakers在他的1999年論文中解釋了這一點。請參閱http://gerbil.org/tom/ – 2011-03-22 09:30:17

+0

當然,您可以通過創建子類來添加實例變量。對於現有的類,可以使用'objc_setAssociatedObject'來輕鬆地「僞造」它。 – Anomie 2011-03-22 11:26:27

3

你試圖寫什麼類型的應用程序?在什麼平臺上?

GUI與服務器的問題可能會排除Linux與Windows的問題。

下列語言是動態的:

  • Smalltalk的
  • 的Perl
  • 的JavaScript
  • 的VBScript
  • 紅寶石

現代JavaScript是目前在軍備競賽是爲儘可能快,所以應該很快ny平臺。

+1

儘管JS沒有類,所以從字面上來說......並不是說基於原型的OOP不是很整齊。 – delnan 2011-03-12 17:51:41

+0

動態只是問題的10%。我不知道用這些語言即時更新類的好方法,以便已創建的實例可以照常運行。平臺是Win/Linux。它是分佈式的服務器客戶端應用程序,沒有gui。 – BarsMonster 2011-03-12 17:54:25

+0

我不清楚你寫的內容:你希望類的所有實例在類更新時改變,還是隻希望新實例改變。不要說「兩個」.... :-)另外爲什麼客戶端不能定期重啓升級?這不能解決客戶端的問題嗎? – Ben 2011-03-13 09:04:17

1
+0

這看起來非常非常多汁,唯一的問題是與笨重的JVM輕微的個人不兼容:-) – BarsMonster 2011-03-12 18:13:58

+0

使用第三方實用程序http://www.zeroturnaround.com/jrebel/ – mindas 2011-03-15 16:23:04

15

二郎被設計爲支持熱代碼交換其高的一個可用性功能。

+1

可以做更多熱切換/重新部署Erlang確實是這個問題的一個很好的答案。它甚至與原始的askers知識相反,編譯成你可以發佈的字節碼,所以源碼不在客戶端機器上。 – 2011-03-21 16:40:28

0

Smalltalk可以自然地做到這一點,Common Lisp(CLOS)有一些技巧。

3

Python可以做到這一點。請注意以下幾點:

  • multiprocessing模塊。
  • GIL特定於CPython它是而不是 Python固有的。
  • GIL不是你問題think它是。它不會影響重要的IO使用,並且doesn't apply to C code或C庫(如果wrapped correctly)。如果你正在做計算密集型的任何事情,無論如何都應該用C語言(無論如何都是這些部分)。
+0

我真的需要線程,我需要它們之間共享的所有數據,而且對於進程來說更難。另外,不能安全地啓動1000個進程。由於IronPyton&JPython不適用於我,因此我檢查了PyPy並發現它也遭受GIL的攻擊,以便不破壞與現有C庫的兼容性。 – BarsMonster 2011-03-17 10:25:23

+0

@BarsMonster:如果不知道你的問題是什麼,我會補充一點,你的觀點只代表CPU密集型,算法相關的數據共享,比如重型並行計算,或者你在Windows上。如果是這種情況,您應該考慮C,並將計算包裝在模塊中以供更高級別的語言使用。所有其他情況下只求求基於進程的並行化:http://stackoverflow.com/questions/3609469/what-are-the-thread-limitations-when-working-on-linux-compared-to-processes-for- n/3705919#3705919 – 2011-03-17 21:51:29

+0

一個人無法安全地啓動1000個進程?新聞給任何人誰程序Erlang .... – 2011-03-21 12:12:57

2

看看Scheme吧。您可以使用非常簡單的擴展名在Scheme中執行面向對象的編程,例如Berkeley extensions。只需擴展代碼以允許替換方法(應該很容易),然而,無論您想要如何都可以熱插拔它們 - 語法仍然保持簡單,因爲,它是Scheme。 :)

眼下,對於classlooks類似代碼:

(define-class (person name) 
    (method (greet) (print `Hello!)) 
    ...) 

其中person是一個lambda。例如,將define-class宏更改爲person應該很容易,因此您可以動態添加或刪除該列表。

3

我最近做了一些零停機服務遷移的研究。我的解決方案不是一種與語言相關的解決方案。這裏有個想法,我們可以轉儲當前服務的狀態,創建另一個進程,將連接狀態描述轉移到新進程,最終終止舊進程。如下面的圖中示出:

enter image description here

具有良好定義抽象服務描述格式和遷移協議,則可以從一個過程到另一個,這意味着,可以用C的服務器遷移的任何種類的服務++ ,並將服務遷移到用Python編寫的新進程中,而不會發生任何斷開連接。詛咒,你可以將你的服務從舊版本遷移到新版本。添加/刪除/更新類不會成爲問題。欲瞭解更多的細節,你可以參考我的文章

Zero-downtime service migration

這種技術的難度,你必須轉儲正在運行的服務的所有狀態並加載它們對另一個進程。對於大多數圖書館你可以發現,很難獲得這些類的內部狀態,這意味着你可能需要對它們進行一些破解或者編寫自己的圖書館。爲複雜的服務轉移服務狀態將是一場噩夢,但對於簡單的服務來說,這並不是什麼大問題。

0

您可以在列表中查看http://en.wikipedia.org/wiki/List_of_programming_languages_by_category#Reflective_languages。我在這裏沒有提到的一個是Lua,與其他動態語言相比,Lua聲名狼借。

另一個策略可能是看看學術研究。一個可能的起點是http://scholar.google.com/scholar?q=ksplice,它是關於修補正在運行的linux內核的。

我不確定你要找什麼樣的自動化程度。很明顯,無縫地用A代替一個運行的程序A實例的一般情況很難,即使有一些保證允許在A中允許改變。

根據程序是如何的需要進行更新可以分組和孤立的作品,你可以把它們放在一個共享庫,並(重新)加載在運行時共享庫​​(例如使用了dlopen的家庭的功能,如果你在Unix上)。

1

取決於您的項目的具體情況 - Javascript可能是通過Node.js(nodejs.com)的答案,它允許您使用由V8引擎解釋的JavaScript編寫基於事件的服務器。

與傳統網絡服務器相比,在一次有很多連接的情況下,特別是在服務器有很多空閒的情況下,這種方法可以非常有效。這是由於Javascript的基於事件的特性導致空閒成本非常低的原因。

有如何使用Node.js用於熱交換代碼的幾種方法 - 這應該讓你開始:Node.Js in Erlang style?https://github.com/kriszyp/nodules

+0

由於無共享構造node.js,SMP *可能成爲問題。 – 2011-03-21 16:41:52

3

我們這樣做是對寶石的免費版本上運行的海邊Smalltalk的web應用。寶石在過去20年左右一直在這樣做,所以他們擁有你需要的一切。某些高可用性功能不是免費的。

開源smalltalks沒有廣泛的類版本/遷移寶石有。簡單的「加載新版本並遷移所有實例」適用於所有smalltalks。

0

你應該使用PHP對於這一點,我也有一臺Linux服務器,這是非常好的有權更改文件,就像我有這個PHP代碼打開一個文本框,可編輯的站點文件,

<?php 
$fn = "test.txt"; //the path to any file 

if (isset($_POST['content'])) 
{ 
    $content = stripslashes($_POST['content']); 
    $fp = fopen($fn,"w") or die ("Error opening file in write mode!"); 
    fputs($fp,$content); 
    fclose($fp) or die ("Error closing file!"); 
} 
?> 
<h4>You are editing <?php echo $fn ?> </h4> 
<form action="<?php echo $_SERVER["PHP_SELF"] ?>" method="post"> 
    <textarea rows="25" cols="40" name="content"><?php readfile($fn); ?></textarea> 
    <br/> 
    <input type="submit" value="Save"> 
</form> 
0

Objective-C允許你熱切換代碼,並且有一個允許這樣做的插件。我回答了類似的問題Objective-C here