2011-06-04 36 views
6

假設有一個TCP服務器在localhost:8080上運行,並且在另一個可以理解列表的Lisp方言中運行。現在我打開的elispEmacs Lisp網絡連接 - 如何處理對象?

網絡連接
setq pserv (open-network-stream plisp "test1.l" "localhost" 8080) 

,併成功地分配一個開放的網絡處理對象變量PSERV。但是,接下來呢,我該如何使用這個過程對象向服務器發送請求呢?我想要做的是將列表發送到其他服務器(代碼作爲數據),並將結果返回。

在上述語句中,「test1.l」是與進程關聯的Emacs緩衝區,所以結果應該打印在該緩衝區中。如果我將nil放在那裏,並且進程不與任何緩衝區關聯 - 如何從Elisp或進程對象訪問服務器結果(可能以列表形式)?

Elisp手冊似乎認爲這種知識是理所當然的,但我在這裏有點失落。每個提示將不勝感激。

回答

10

客戶端/服務器通信通過異步進程處理。這意味着不幸的是,你沒有一個函數「發送」你傳遞你的數據被髮送到服務器,並返回給你服務器的答覆。原因是網絡通信速度可能會很慢,並且會阻止Emacs中的所有其他操作,這是單線程程序。

要發送數據到您的服務器,請使用(process-send-string process string)。第一個參數是您的網絡連接,Emacs將其視爲異步進程。既然你有子對象已經存儲在變量pserv,你可以寫:

(process-send-string pserv "(my data (can be (in) (list) form))") 

將字符串發送到服務器。

要讀取服務器的回覆,請使用process filter function,這是回調,無論服務器發回給您的回調都會被調用。所以,你首先要確定這樣一個回調函數,說:

(defun handle-server-reply (process content) 
    "Gets invoked whenever the server sends data to the client." 
    ...) 

這個函數有兩個參數,網絡程序和服務器發送的內容數據。但有一點棘手:服務器回覆可能會被分成多個子內容。也就是說,當調用handle-server-reply時,參數content可能只包含服務器回覆的部分內容。它可能會在稍後與更多內容再次呼叫。所以請確保你正確處理。

聲明你的函數作爲回調,使用:

(set-process-filter pserv 'handle-server-reply) 

與往常一樣,字符編碼可以是皮塔餅,所以看爲以下兩種功能,並決定是否可能需要他們:

(set-process-filter-multibyte pserv t) 
(set-process-coding-system pserv 'utf-8 'utf-8) 

請確保在之前設置這些分配過程過濾器功能。

您可能也有興趣調查網絡連接的狀態,例如,以處理連接意外關閉的情況。對於可以使用所謂sentinel functions,回調的另一種類型,通過它你得到了解的過程狀態的變化:

(set-process-sentinel pserv 'sentinel-function) 

(defun sentinel-function (process event) 
    "Gets called when the status of the network connection changes." 
    ...) 

event參數包含在其中的連接狀態改變了的信息。

我想Emacs process documentation已經被指出過。這絕對值得一讀。

+0

謝謝托馬斯,一個非常詳細和有益的答案! – Thorsten 2011-06-05 22:27:29

+0

實際上已將其從手冊中複製出來。手冊非常好。你應該閱讀它。 – 2014-02-23 11:19:05

+0

@nicferrier我同意,這就是爲什麼我的答案包含指向手冊的多個鏈接。 – Thomas 2014-02-23 12:26:33

4

在Emacs中,網絡連接被視爲異步子進程。因此,發送輸入或從子流程讀取輸出的說明也適用於此。

要發送一些東西到服務器,請參閱Input to Processes,並閱讀結果,請參閱Output from Processes

信息在以字符串形式在網絡上傳輸,所以你可能需要使用readread-from-string從服務器接收數據之後。見Input Functions

+0

您的回答已經給出了關鍵信息:將網絡連接視爲異步子進程。所以我可以閱讀Elisp手冊瞭解更多信息......謝謝。 – Thorsten 2011-06-05 22:32:19