zsh-workers
 help / color / mirror / code / Atom feed
* [ramk@cse.iitm.ernet.in: Bug#335190: zsh: Enhancements to zsh-mime-handler]
@ 2005-10-24 19:33 Clint Adams
  2005-10-25 22:45 ` Peter Stephenson
  0 siblings, 1 reply; 3+ messages in thread
From: Clint Adams @ 2005-10-24 19:33 UTC (permalink / raw)
  To: zsh-workers; +Cc: R.Ramkumar, 335190-forwarded

----- Forwarded message from "R.Ramkumar" <ramk@cse.iitm.ernet.in> -----

Just felt that there is much scope for customization in
zsh-mime-{handler,setup}. I have patched the files for the following
enhancements (thought that the additions were too small to merit
reporting them individually, so I am putting them together):

1. zsh-mime-setup: A mechanism for resolving conflicts when there
   are multiple entries in the mailcap files. Rather than using
   mailcap.order, it provides for generic mechanisms like matching
   flags for needsterminal and giving them priority, using the
   priority flag in the mailcap entry etc.

2. zsh-mime-handler: An option to prevent use of `eval' instead of
   `sh -c' for complex command patterns. I know these can possibly
   break if sh compatibility is assumed, but for those reasonably
   confident, this can save a new process spawn.

3. zsh-mime-handler: An option to never background the spawned
   processes.

I have documented the changes in the patch. The default behaviour
remains the same with the patch. These features need to be
explicitly activated using zstyle.

I am new to zsh scripting. So, it's very much possible that I've
messed up things. Please bear with me :)

Ramkumar.




diff -Naur orig/zsh-mime-handler new/zsh-mime-handler
--- orig/zsh-mime-handler	2005-10-22 00:25:38.000000000 +0530
+++ new/zsh-mime-handler	2005-10-22 18:07:52.000000000 +0530
@@ -44,13 +44,22 @@
 suffix=$match[1]
 context=":mime:.${suffix}:"
 
-local handler flags
+local handler flags no_sh no_bg
 
 zstyle -s $context handler handler ||
   handler="${zsh_mime_handlers[$suffix]}"
 zstyle -s $context flags flags ||
   flags="${zsh_mime_flags[$suffix]}"
 
+# Set to yes if we use eval instead of sh -c for complicated mailcap lines
+# Can possibly break some mailcap entries which expect sh compatibility,
+# is faster, as a new process is not spawned.
+zstyle -T $context current-shell && no_sh=yes
+
+# Set to yes if the process shouldn't be backgrounded even if it doesn't need a
+# terminal and display is set.
+zstyle -T $context never-background && no_bg=yes
+
 local -a files
 local hasmeta stdin
 
@@ -82,7 +91,11 @@
       files=(${(q)argv})
       zformat -f command $handler s:"$files"
     fi
-    execargs=(sh -c $command)
+    if [[ $no_sh = yes ]]; then
+      execargs=(eval $command)
+    else
+      execargs=(sh -c $command)
+    fi
   else
     # Simple command, one filename.
     # Split and add the file without extra quoting,
@@ -95,7 +108,7 @@
 else
   # If there's no %s, the input is supposed to come from stdin.
   stdin=1
-  if [[ -n $hasmeta ]]; then
+  if [[ -n $hasmeta && $no_sh != yes ]]; then
     execargs=(sh -c "$handler")
   else
     execargs=(${=handler})
@@ -113,7 +126,7 @@
   else
     $execargs | eval ${PAGER:-more}
   fi
-elif [[ $flags = *needsterminal* || -z $DISPLAY ]]; then
+elif [[ $no_bg = yes || $flags = *needsterminal* || -z $DISPLAY ]]; then
   # Needs a terminal, so run synchronously.
   # Obviously, if $DISPLAY is empty but the handler needs a
   # GUI we are in trouble anyway.  However, it's possible for
diff -Naur orig/zsh-mime-setup new/zsh-mime-setup
--- orig/zsh-mime-setup	2005-10-22 00:25:38.000000000 +0530
+++ new/zsh-mime-setup	2005-10-22 18:07:52.000000000 +0530
@@ -157,10 +157,39 @@
   unfunction mime-setup-add-type >&/dev/null
 }
 
+local -a pats_prio o_prios
+local o_overwrite sentinel
+typeset -A type_prio_flags_map type_prio_src_map type_prio_mprio_map
+integer src_id prio mprio
+
+# A list of keywords indicating the methods used to break ties amongst multiple
+# entries. The following keywords are accepted:
+# files: The order of files read: Entries from files read earlier are preferred
+#   (The default value of the variable is a list with this keyword alone)
+# priority: The priority flag is matched in the entry. Can be a value from 0 to
+# 9. The default priority is 5. Higher priorities are preferred.
+# flags: See the mailcap-prio-flags option
+# place: Always overrides. Useful for specifying that entries read later are
+# preferred.
+#
+# As the program reads mailcap entries, if it encounters a duplicate entry, each
+# of the keywords in the list are checked to see if the new entry can override
+# the existing entry. If none of the keywords are able to decide whether the new
+# entry should be preferred to the older one, the new entry is discarded.
+zstyle -a :mime: mailcap-priorities o_prios || o_prios=(files)
+
+# This style is used as an argument for the flags test in mailcap-priorities.
+# This is a list of patterns, each of which is tested against the flags for the
+# mailcap entry. An match with a pattern ahead in the list is preferred as
+# opposed to a match later in the list. An unmatched item is least preferred.
+zstyle -a :mime: mailcap-prio-flags pats_prio
+
 # Loop through files to find handlers for types.
+((src_id = 0))
 for file in $cap_files; do
   [[ -r $file ]] || continue
 
+  ((src_id = src_id + 1))
   # Oh, great.  We need to preserve backslashes inside the line,
   # but need to manage continuation lines.
   while read -r line; do
@@ -197,13 +226,66 @@
       # and remove any surrounding white space --- this might
       # make the handler empty.
       line=${${line##[[:space:]]#}%%[[:space:]]}
-      if [[ -z $type_handler_map[$type] ]]; then
-        if [[ -n $o_verbose ]]; then
-          print -r "Adding handler for type $type:
+
+      ((prio = 0))
+      for i in $pats_prio; do
+	  # print -r "Comparing $i with '$flags'" >&2
+	[[ $flags = ${~i} ]] && break
+	  # print -r "Comparison failed" >&2
+	((prio = prio + 1))
+      done
+      ((mprio=5))
+      [[ $flags = (#b)*priority=([0-9])* ]] && mprio=$match[1]
+      sentinel=no
+      if [[ -n $type_handler_map[$type] ]]; then
+	for i in $o_prios; do
+	  case $i in
+	    (files)
+	    if [[ $src_id -lt $type_prio_src_map[$type] ]]; then
+	      sentinel=yes; break
+	    elif [[ $src_id -gt $type_prio_src_map[$type] ]]; then
+	      sentinel=no; break
+	    fi
+	    ;;
+	    (priority)
+	    if [[ $mprio -gt $type_prio_mprio_map[$type] ]]; then
+	      sentinel=yes; break
+	    elif [[ $mprio -lt $type_prio_mprio_map[$type] ]]; then
+	      sentinel=no; break
+	    fi
+	    ;;
+	    (flags)
+	    if [[ $prio -lt $type_prio_flags_map[$type] ]]; then
+	      sentinel=yes; break
+	    elif [[ $prio -gt $type_prio_flags_map[$type] ]]; then
+	      sentinel=no; break
+	    fi
+	    ;;
+	    (place)
+	    sentinel=yes
+	    break
+	    ;;
+	  esac
+	done
+      else
+	sentinel=yes
+      fi
+
+      if [[ $sentinel = yes ]]; then
+	if [[ -n $o_verbose ]]; then
+	  if [[ -n $type_handler_map[$type] ]]; then
+	    print -r "Overriding" >&2
+	  else
+	    print -r "Adding" >&2
+	  fi
+	  print -r " handler for type $type:
   $line" >&2
 	fi
 	type_handler_map[$type]=$line
 	type_flags_map[$type]=$flags
+	type_prio_src_map[$type]=$src_id
+	type_prio_flags_map[$type]=$prio
+	type_prio_mprio_map[$type]=$mprio
 	if [[ -n $flags && -n $o_verbose ]]; then
 	  print -r "  with flags $flags" >&2
 	fi


----- End forwarded message -----


^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: [ramk@cse.iitm.ernet.in: Bug#335190: zsh: Enhancements to zsh-mime-handler]
  2005-10-24 19:33 [ramk@cse.iitm.ernet.in: Bug#335190: zsh: Enhancements to zsh-mime-handler] Clint Adams
@ 2005-10-25 22:45 ` Peter Stephenson
  2005-10-27 18:16   ` R.Ramkumar
  0 siblings, 1 reply; 3+ messages in thread
From: Peter Stephenson @ 2005-10-25 22:45 UTC (permalink / raw)
  To: zsh-workers, ramk, 335190-forwarded

On Mon, 24 Oct 2005 15:33:18 -0400
Clint Adams <schizo@debian.org> wrote:
> ----- Forwarded message from "R.Ramkumar" <ramk@cse.iitm.ernet.in> -----
> 
> Just felt that there is much scope for customization in
> zsh-mime-{handler,setup}. I have patched the files for the following
> enhancements (thought that the additions were too small to merit
> reporting them individually, so I am putting them together):

Thanks, I'll add these.  Here's some proposed documentation (styles now
put in alphabetical order).

It would be quite nice to have a couple of examples illustrating
mailcap-prio-flags.

Index: Doc/Zsh/contrib.yo
===================================================================
RCS file: /cvsroot/zsh/zsh/Doc/Zsh/contrib.yo,v
retrieving revision 1.51
diff -u -r1.51 contrib.yo
--- Doc/Zsh/contrib.yo	21 Oct 2005 09:51:55 -0000	1.51
+++ Doc/Zsh/contrib.yo	25 Oct 2005 22:43:22 -0000
@@ -1370,19 +1370,17 @@
 to style patterns in case the system is extended in future.  Some
 examples are given below.
 startitem()
-item(mime-types)(
-A list of files in the format of tt(~/.mime.types) and
-tt(/etc/mime.types) to be read during setup, replacing the default list
-which consists of those two files.  The context is tt(:mime:).
-A tt(PLUS()) in the list will be replaced by the default files.
+item(tt(current-shell))(
+If this boolean style is true, the mailcap handler for the context in
+question is run using the tt(eval) builtin instead of by starting a new
+tt(sh) process.  This is more efficient, but may not work in the occasional
+cases where the mailcap handler uses strict POSIX syntax.
 )
-item(mailcap)(
-A list of files in the format of tt(~/.mailcap) and
-tt(/etc/mailcap) to be read during setup, replacing the default list
-which consists of those two files.  The context is tt(:mime:).
-A tt(PLUS()) in the list will be replaced by the default files.
+item(tt(flags))(
+Defines flags to go with a handler; the context is as for the
+tt(handler) style, and the format is as for the flags in tt(mailcap).
 )
-item(handler)(
+item(tt(handler))(
 Specifies a handler for a suffix; the suffix is given by the context as
 tt(:mime:.)var(suffix)tt(:), and the format of the handler is exactly
 that in tt(mailcap).  Note in particular the `tt(.)' and trailing colon
@@ -1392,11 +1390,63 @@
 or if the output is to be displayed through a pager (but not if the
 handler is itself a pager), it should include tt(copiousoutput).
 )
-item(flags)(
-Defines flags to go with a handler; the context is as for the
-tt(handler) style, and the format is as for the flags in tt(mailcap).
+item(tt(mailcap))(
+A list of files in the format of tt(~/.mailcap) and
+tt(/etc/mailcap) to be read during setup, replacing the default list
+which consists of those two files.  The context is tt(:mime:).
+A tt(PLUS()) in the list will be replaced by the default files.
+)
+item(tt(mailcap-priorities))(
+This style is used to resolve multiple mailcap entries for the same MIME
+type.  It consists of an array of the following elements, in descending
+order of priority; later entries will be used if earlier entries are
+unable to resolve the entries being compared.  If none of the tests
+resolve the entries, the first entry encountered is retained.
+
+startitem()
+item(tt(files))(
+The order of files (entries in the tt(mailcap) style) read.  Earlier
+files are preferred.  (Note this does not resolve entries in the same file.)
+)
+item(tt(priority))(
+The priority flag from the mailcap entry.  The priority is an integer
+from 0 to 9 with the default value being 5.
+)
+item(tt(flags))(
+The test given by the tt(mailcap-prio-flags) option is used to resolve
+entries.
+)
+item(tt(place))(
+Later entries are preferred; as the entries are strictly ordered, this
+test always succeeds.
+)
+enditem()
+
+Note that as this style is handled during initialisation, the context
+is always tt(:mime:), with no discrimination by suffix.
+)
+item(tt(mailcap-prio-flags))(
+This style is used when the keyword tt(flags) is encountered in the
+list of tests specified by the tt(mailcap-priorities) style.
+It should be set to a list of patterns, each of which is tested against
+the flags specified in the mailcap entry (in other words, the sets of
+assignments found with some entries in the mailcap file).  Earlier
+patterns in the list are preferred to later ones, and matched patterns
+are preferred to unmatched ones.
 )
-item(pager)(
+item(tt(mime-types))(
+A list of files in the format of tt(~/.mime.types) and
+tt(/etc/mime.types) to be read during setup, replacing the default list
+which consists of those two files.  The context is tt(:mime:).
+A tt(PLUS()) in the list will be replaced by the default files.
+)
+item(tt(never-background))(
+If this boolean style is set, the handler for the given context is
+always run in the foreground, even if the flags provided in the mailcap
+entry suggest it need not be (for example, it doesnʼt require a
+terminal).
+)
+item(tt(pager))(
 If set, will be used instead of tt($PAGER) or tt(more) to handle
 suffixes where the tt(copiousoutput) flag is set.  The context is
 as for tt(handler), i.e. tt(:mime:.)var(suffix)tt(:) for handling


^ permalink raw reply	[flat|nested] 3+ messages in thread

* Re: [ramk@cse.iitm.ernet.in: Bug#335190: zsh: Enhancements to zsh-mime-handler]
  2005-10-25 22:45 ` Peter Stephenson
@ 2005-10-27 18:16   ` R.Ramkumar
  0 siblings, 0 replies; 3+ messages in thread
From: R.Ramkumar @ 2005-10-27 18:16 UTC (permalink / raw)
  To: Peter Stephenson; +Cc: zsh-workers, 335190-forwarded

Hi!

> It would be quite nice to have a couple of examples illustrating
> mailcap-prio-flags.

Some two examples I could think of, immediately :)

# From my .zshrc file. Prefers entries needing the terminal, then
# those using a display

'*needsterminal*' '*test=test -n "$DISPLAY"*' '*test=test "$DISPLAY" != ""*'

# This is probably good for a text-based terminal

'*needsterminal*' '*copiousoutput*'

I don't know of any non-standard flags in mailcap, except for
'priority', which is used by Debian's update-mime. If anyone knows
more of these non-standard flags, may be we can get better
examples.

Regards,
Ramkumar.

-- 
I dunno, I hear Microsoft has an app that will make Windows
run pretty damned fast. I believe they called it FDISK.
                             --from a Slashdot post



^ permalink raw reply	[flat|nested] 3+ messages in thread

end of thread, other threads:[~2005-10-27 18:34 UTC | newest]

Thread overview: 3+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2005-10-24 19:33 [ramk@cse.iitm.ernet.in: Bug#335190: zsh: Enhancements to zsh-mime-handler] Clint Adams
2005-10-25 22:45 ` Peter Stephenson
2005-10-27 18:16   ` R.Ramkumar

Code repositories for project(s) associated with this public inbox

	https://git.vuxu.org/mirror/zsh/

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).