   (with-current-buffer (emdocs-get-server-process-buffer)
     (goto-char (point-min))
     (insert "sentinel:" msg)
-    (newline))
+    (unless (bolp) (newline)))
   (cond ((string-match "^open from [0-9]+\\.[0-9]+\\.[0-9]+\\.[0-9]+\n$" msg)
-         (process-send-string sock "give your ip and buffer\n"))))
+         (process-send-string sock "give me buffer and ip")
+         (add-to-list '*emdocs-clients* sock))
+        ((string-match "^connection broken by remote peer\n$")
+         (setq *emdocs-clients* (delete sock *emdocs-clients*)))))
 
 (defun emdocs-server-filter (sock msg)
   "docstring"
+  ;; assumes will only receive json from emdocs-client-sentinel
   (with-current-buffer (emdocs-get-server-process-buffer)
     (goto-char (point-min))
     (insert "filter:" msg)
-    (newline)))
+    (unless (bolp) (newline)))
+  (let* ((json-object-type 'plist)
+         (json-msg (json-read-from-string msg)))
+    (emdocs-connect-client (plist-get json-msg :buffer)
+                           (plist-get json-msg :ip))))
 
 (defun emdocs-setup-server (my-ip)
   "docstring"


(defun emdocs-get-server-process-buffer ()
  "docstring"
  (concat "*emdocs-server-log*"))

(defun emdocs-get-client-process-buffer (buffer)
  "docstring"

  (with-current-buffer (emdocs-get-client-process-buffer buffer)
    (goto-char (point-min))
    (insert "sentinel:" msg)
    (unless (bolp) (newline)))
  (cond ((string-match "^give me buffer and ip\n$" msg)
         (process-send-string
          sock
          (json-encode
           `(:buffer ,(buffer-name buffer)
             :ip ,(emdocs-get-internal-ip-address)))))))

(defun emdocs-client-filter (buffer sock msg)
  "docstring"
  ;; assumes will only receive json from emdocs-after-change-function
  (with-current-buffer (emdocs-get-client-process-buffer buffer)
    (goto-char (point-min))
    (insert "filter:" msg)
    (unless (bolp) (newline)))
  (let* ((json-object-type 'plist)
         (json-msg (json-read-from-string msg)))
    (with-current-buffer (plist-get json-msg :buffer)
      (save-excursion
        (setq emdocs-is-network-insert t)
        (unwind-protect
            (cond
             ((string-equal "insert" (plist-get json-msg :edit_type))
              (goto-char (plist-get json-msg :point))
              (insert (plist-get json-msg :content)))
             ((string-equal "delete" (plist-get json-msg :edit_type))
              (goto-char (plist-get json-msg :point))
              (delete-char (plist-get json-msg :content))))
          (setq emdocs-is-network-insert nil))))))

(defun emdocs-connect-client (buffer ip)
  "docstring"
