mercurial/ui.py
changeset 31690 2d11d278279a
parent 31688 c5fe0c7dad94
child 31691 c3ca0ad8ab9c
equal deleted inserted replaced
31689:57a22f699179 31690:2d11d278279a
   854         if not pagercmd:
   854         if not pagercmd:
   855             return
   855             return
   856 
   856 
   857         self.debug('starting pager for command %r\n' % command)
   857         self.debug('starting pager for command %r\n' % command)
   858         self.flush()
   858         self.flush()
   859         self.pageractive = True
   859 
   860         # Preserve the formatted-ness of the UI. This is important
   860         wasformatted = self.formatted()
   861         # because we mess with stdout, which might confuse
       
   862         # auto-detection of things being formatted.
       
   863         self.setconfig('ui', 'formatted', self.formatted(), 'pager')
       
   864         self.setconfig('ui', 'interactive', False, 'pager')
       
   865         if util.safehasattr(signal, "SIGPIPE"):
   861         if util.safehasattr(signal, "SIGPIPE"):
   866             signal.signal(signal.SIGPIPE, _catchterm)
   862             signal.signal(signal.SIGPIPE, _catchterm)
   867         self._runpager(pagercmd)
   863         if self._runpager(pagercmd):
       
   864             self.pageractive = True
       
   865             # Preserve the formatted-ness of the UI. This is important
       
   866             # because we mess with stdout, which might confuse
       
   867             # auto-detection of things being formatted.
       
   868             self.setconfig('ui', 'formatted', wasformatted, 'pager')
       
   869             self.setconfig('ui', 'interactive', False, 'pager')
       
   870         else:
       
   871             # If the pager can't be spawned in dispatch when --pager=on is
       
   872             # given, don't try again when the command runs, to avoid a duplicate
       
   873             # warning about a missing pager command.
       
   874             self.disablepager()
   868 
   875 
   869     def _runpager(self, command):
   876     def _runpager(self, command):
   870         """Actually start the pager and set up file descriptors.
   877         """Actually start the pager and set up file descriptors.
   871 
   878 
   872         This is separate in part so that extensions (like chg) can
   879         This is separate in part so that extensions (like chg) can
   873         override how a pager is invoked.
   880         override how a pager is invoked.
   874         """
   881         """
   875         if command == 'cat':
   882         if command == 'cat':
   876             # Save ourselves some work.
   883             # Save ourselves some work.
   877             return
   884             return False
   878         # If the command doesn't contain any of these characters, we
   885         # If the command doesn't contain any of these characters, we
   879         # assume it's a binary and exec it directly. This means for
   886         # assume it's a binary and exec it directly. This means for
   880         # simple pager command configurations, we can degrade
   887         # simple pager command configurations, we can degrade
   881         # gracefully and tell the user about their broken pager.
   888         # gracefully and tell the user about their broken pager.
   882         shell = any(c in command for c in "|&;<>()$`\\\"' \t\n*?[#~=%")
   889         shell = any(c in command for c in "|&;<>()$`\\\"' \t\n*?[#~=%")
   889             # determine which one to use.
   896             # determine which one to use.
   890             fullcmd = util.findexe(command)
   897             fullcmd = util.findexe(command)
   891             if not fullcmd:
   898             if not fullcmd:
   892                 self.warn(_("missing pager command '%s', skipping pager\n")
   899                 self.warn(_("missing pager command '%s', skipping pager\n")
   893                           % command)
   900                           % command)
   894                 return
   901                 return False
   895 
   902 
   896             command = fullcmd
   903             command = fullcmd
   897 
   904 
   898         try:
   905         try:
   899             pager = subprocess.Popen(
   906             pager = subprocess.Popen(
   902                 stdout=util.stdout, stderr=util.stderr)
   909                 stdout=util.stdout, stderr=util.stderr)
   903         except OSError as e:
   910         except OSError as e:
   904             if e.errno == errno.ENOENT and not shell:
   911             if e.errno == errno.ENOENT and not shell:
   905                 self.warn(_("missing pager command '%s', skipping pager\n")
   912                 self.warn(_("missing pager command '%s', skipping pager\n")
   906                           % command)
   913                           % command)
   907                 return
   914                 return False
   908             raise
   915             raise
   909 
   916 
   910         # back up original file descriptors
   917         # back up original file descriptors
   911         stdoutfd = os.dup(util.stdout.fileno())
   918         stdoutfd = os.dup(util.stdout.fileno())
   912         stderrfd = os.dup(util.stderr.fileno())
   919         stderrfd = os.dup(util.stderr.fileno())
   922             # restore original fds, closing pager.stdin copies in the process
   929             # restore original fds, closing pager.stdin copies in the process
   923             os.dup2(stdoutfd, util.stdout.fileno())
   930             os.dup2(stdoutfd, util.stdout.fileno())
   924             os.dup2(stderrfd, util.stderr.fileno())
   931             os.dup2(stderrfd, util.stderr.fileno())
   925             pager.stdin.close()
   932             pager.stdin.close()
   926             pager.wait()
   933             pager.wait()
       
   934 
       
   935         return True
   927 
   936 
   928     def interface(self, feature):
   937     def interface(self, feature):
   929         """what interface to use for interactive console features?
   938         """what interface to use for interactive console features?
   930 
   939 
   931         The interface is controlled by the value of `ui.interface` but also by
   940         The interface is controlled by the value of `ui.interface` but also by