Mercurial > dotfiles
view .elisp/http-twiddle.el @ 157:95b7dc384677
textmate.el: bring in upstream changes
author | Augie Fackler <durin42@gmail.com> |
---|---|
date | Tue, 24 Nov 2009 14:24:09 -0600 |
parents | 35eef880a5ac |
children |
line wrap: on
line source
;;; http-twiddle.el -- send & twiddle & resend HTTP requests ;; ;; Version 1.0 written by Luke Gorrie <luke@synap.se> in February 2006 ;; This program belongs to the public domain. ;; ;; (downloaded from http://fresh.homeunix.net/~luke/misc/emacs/http-twiddle.el) ;; ;; This is a program for testing hand-written HTTP requests. You write ;; your request in an Emacs buffer (using http-twiddle-mode) and then ;; press `C-c C-c' each time you want to try sending it to the server. ;; This way you can interactively debug the requests. To change port or ;; destination do `C-u C-c C-c'. ;; ;; The program is particularly intended for the POST-"500 internal ;; server error"-edit-POST loop of integration with SOAP programs. ;; ;; The mode is activated by `M-x http-twiddle-mode' or automatically ;; when opening a filename ending with .http-twiddle. ;; ;; The request can either be written from scratch or you can paste it ;; from a snoop/tcpdump and then twiddle from there. ;; ;; See the documentation for the `http-twiddle-mode' and ;; `http-twiddle-mode-send' functions below for more details and try ;; `M-x http-twiddle-mode-demo' for a simple get-started example. ;; ;; Tested with GNU Emacs 21.4.1 and not tested/ported on XEmacs yet. ;;; Example buffer: ;; POST / HTTP/1.0 ;; Connection: close ;; Content-Length: $Content-Length ;; ;; The request body goes here (require 'font-lock) ; faces (eval-when-compile (unless (fboundp 'define-minor-mode) (require 'easy-mmode) (defalias 'define-minor-mode 'easy-mmode-define-minor-mode)) (require 'cl)) (define-minor-mode http-twiddle-mode "Major mode for twiddling around with HTTP requests and sending them. Use `http-twiddle-mode-send' (\\[http-twiddle-mode-send]) to send the request." nil " http-twiddle" '(("\C-c\C-c" . http-twiddle-mode-send))) (defvar http-twiddle-show-request t "*Show the request in the transcript.") (add-to-list 'auto-mode-alist '("\\.http-twiddle$" . http-twiddle-mode)) (defvar http-twiddle-endpoint nil "Cache of the (HOST PORT) to send the request to.") (defvar http-twiddle-process nil "Socket connected to the webserver.") (defvar http-twiddle-port-history '() "History of port arguments entered in the minibuffer. \(To make XEmacs happy.)") (defvar http-twiddle-host-history '() "History of port arguments entered in the minibuffer. \(To make XEmacs happy.)") (defun http-twiddle-mode-send (host port) "Send the current buffer to the server. Linebreaks are automatically converted to CRLF (\\r\\n) format and any occurences of \"$Content-Length\" are replaced with the actual content length." (interactive (http-twiddle-read-endpoint)) ;; close any old connection (when http-twiddle-process (kill-buffer (process-buffer http-twiddle-process))) (let ((content (buffer-string))) (with-temp-buffer (insert content) (http-twiddle-convert-cr-to-crlf) (http-twiddle-expand-content-length) (let ((request (buffer-string))) (setq http-twiddle-process (open-network-stream "http-twiddle" "*HTTP Twiddle*" host port)) (set-process-filter http-twiddle-process 'http-twiddle-process-filter) (set-process-sentinel http-twiddle-process 'http-twiddle-process-sentinel) (process-send-string http-twiddle-process request) (save-selected-window (pop-to-buffer (process-buffer http-twiddle-process)) (when http-twiddle-show-request (insert request) (set-window-start (selected-window) (point)) (add-text-properties (point-min) (point-max) '(face font-lock-comment-face))) (set-mark (point))))))) (defun http-twiddle-read-endpoint () "Return the endpoint (HOST PORT) to send the request to." (if (and http-twiddle-endpoint (null current-prefix-arg)) http-twiddle-endpoint (setq http-twiddle-endpoint (list (read-string "Host: (default localhost) " nil 'http-twiddle-host-history "localhost") (let ((input (read-from-minibuffer "Port: " nil nil t 'http-twiddle-port-history))) (if (integerp input) input (error "Not an integer: %S" input))))))) (defun http-twiddle-convert-cr-to-crlf () "Convert \\n linebreaks to \\r\\n in the whole buffer." (save-excursion (goto-char (point-min)) (while (re-search-forward "[^\r]\n" nil t) (backward-char) (insert "\r")))) (defun http-twiddle-expand-content-length () "Replace any occurences of $Content-Length with the actual Content-Length." (save-excursion (goto-char (point-min)) (let ((content-length (save-excursion (when (search-forward "\r\n\r\n" nil t) (- (point-max) (point)))))) (unless (null content-length) (let ((case-fold-search t)) (while (search-forward "$content-length" nil t) (replace-match (format "%d" content-length) nil t))))))) (defun http-twiddle-process-filter (process string) "Process data from the socket by inserting it at the end of the buffer." (with-current-buffer (process-buffer process) (goto-char (point-max)) (insert string))) (defun http-twiddle-process-sentinel (process what) (with-current-buffer (process-buffer process) (goto-char (point-max)) (let ((start (point))) (insert "Connection closed\n") (add-text-properties start (point) '(face font-lock-string-face))))) (defun http-twiddle-mode-demo () (interactive) (pop-to-buffer (get-buffer-create "*http-twiddle demo*")) (http-twiddle-mode 1) (erase-buffer) (insert "POST / HTTP/1.0\nContent-Length: $Content-Length\nConnection: close\n\nThis is the POST body.\n") (message "Now press `C-c C-c' and enter a webserver address (e.g. google.com port 80).")) (provide 'http-twiddle)