emacs-devel
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

Re: Proposal: emacsclient --readonly


From: Michael Mauger
Subject: Re: Proposal: emacsclient --readonly
Date: Sat, 23 Mar 2013 20:45:55 -0700 (PDT)

[I got a message this bounced on the mailing list, twice; trying again.
Sorry if this is a dupe.

I've polished the text and the code bit; it was originally sent while I
was attending LibrePlanet.]

> > I'd be interested in any suggestions people have on how to accomplish
> > this using emacsclient currently.  In the absence of any ideas, I'd like
> > to propose the folowing patch which adds a `--readonly,-r' option to
> > emacsclient (and server.el) (I had originally called it --view-mode,-v but
> > getopt_long_only complained that it was ambiguous if abbreviated.)
>
> I think the way to do it is to change emacsclient.c so that any "--foo"
> arg simply gets sent to server.el.  This way the addition of --readonly
>
> support can be implemented all in server.el.  Then server.el should be
> changed to provide a hook that lets user add handling for their
> own --foo args so that you can even do it without changing server.el.
>
>        Stefan

Adding a feature to allow custom options in emacsclient is an idea that
I've had in the past and failed at implementing it in the past miserably
because I came up with too many complex situations.  So I've spent the
last week or so trying again.  I've been through several iterations and
have reduced it to this simplified solution.  The code is still a
little rough, but the idea is stable.  The doc strings probably need
lots of work...

Basically, there are two variables used to control the parsing and
processing of custom emacsclient options:

server-custom-option-functions:
  A list of functions to handle custom options.

  The functions accept four arguments: a buffer, a process, the option
  string and the option value.  If this variable is nil, then no options
  are accepted, regardless of the setting of
  `server-custom-option-list'.  The functions on this hook variable are
  called once before files or expressions are processed with the buffer
  set to nil.  After each file is opened, the hooks will be called
  again, this time with the file buffer passed as the first argument.

server-custom-option-list:
  A list that defines the acceptable custom options.

  If this variable is nil, all unrecognized options are assumed to be
  valid custom options.  If this variable is a list then each element
  defines an acceptable option.  Each list entry should be either a
  string with the option name that does not accept a value, or a list
  whose first entry is a string containing the option name and the
  optional second entry is a type predicate.  If the type predicate is
  `string-only', then the option value is simply treated as a string;
  any other predicate forces the value to be interpreted by the elisp
  reader and passed to the predicate to validate it's value.


So, in my user-init-file, I have:

  (defun my-server-custom-options (buf proc option value)
    (if buf  ;; options processed for each file opened
        (pcase option
          (`"readonly"
           (view-mode +1)
           (when (and view-mode server-buffer-clients)  ;; not nowait
             (setq-local view-exit-action 'server-buffer-done)))
          (t nil))

      (pcase option ;; global options
        (`"banner"  ;; display banner value
         (cond
          ((executable-find "figlet")
           (call-process-shell-command "figlet" nil
                                       "*Banner*" t value))
          ((executable-find "banner")
           (call-process-shell-command "banner" nil
                                       "*Banner*" t value))
          (t (progn
               (get-buffer-create "*Banner*")
               (with-current-buffer "*Banner*"
                 (insert (propertize value 'face
                                     'font-lock-warning-face))))))
             (display-buffer "*Banner*"))
         (t nil))))

  ;; define option syntax
  (setq server-custom-option-list
        '("readonly"                ;; --readonly
          ("banner" string-only)))  ;; --banner=text

  ;; Process options
  (add-hook 'server-custom-option-functions 'my-server-custom-options)

In the end, the changes were pretty small and localized.  I have not
tested it that hard, so it's not difficult to break.

--
Michael R. Mauger       FSF Member #4247       Emacs sql.el Maintainer
michael # mauger com     mmaug # member fsf org     mmaug # yahoo com

Attachment: custom-option.diff
Description: Text Data


reply via email to

[Prev in Thread] Current Thread [Next in Thread]