Serialize arguments via json on restart.

We want to ignore some positional arguments without ignoring flags/values - and
since there's no easy way to "unparse" an argparse namespace, we instead pass
it as json.

Also note we can't pass it as a file easily, as args have to be available very
early. Passing it as an argument shouldn't be an issue though.
This commit is contained in:
Florian Bruhin 2015-04-01 21:28:56 +02:00
parent 8748420b1b
commit 11bd4a13f6
2 changed files with 25 additions and 6 deletions

View File

@ -31,6 +31,7 @@ import functools
import traceback import traceback
import faulthandler import faulthandler
import datetime import datetime
import json
from PyQt5.QtWidgets import QApplication, QDialog, QMessageBox from PyQt5.QtWidgets import QApplication, QDialog, QMessageBox
from PyQt5.QtGui import QDesktopServices, QPixmap, QIcon from PyQt5.QtGui import QDesktopServices, QPixmap, QIcon
@ -683,19 +684,28 @@ class Application(QApplication):
# cwd=None and see if that works out. # cwd=None and see if that works out.
# See https://github.com/The-Compiler/qutebrowser/issues/323 # See https://github.com/The-Compiler/qutebrowser/issues/323
cwd = None cwd = None
for arg in sys.argv[1:]:
if arg.startswith('-'):
# We only want to preserve options on a restart.
args.append(arg)
# Add all open pages so they get reopened. # Add all open pages so they get reopened.
page_args = [] page_args = []
for win in pages: for win in pages:
page_args.extend(win) page_args.extend(win)
page_args.append('') page_args.append('')
if page_args:
args.extend(page_args[:-1]) # Serialize the argparse namespace into json and pass that to the new
# process via --json-args.
# We do this as there's no way to "unparse" the namespace while
# ignoring some arguments.
argdict = vars(self._args)
argdict['session'] = None
argdict['url'] = []
argdict['command'] = page_args[:-1]
argdict['json_args'] = None
data = json.dumps(argdict)
args += ['--json-args', data]
log.destroy.debug("args: {}".format(args)) log.destroy.debug("args: {}".format(args))
log.destroy.debug("cwd: {}".format(cwd)) log.destroy.debug("cwd: {}".format(cwd))
return args, cwd return args, cwd
@cmdutils.register(instance='app', ignore_args=True) @cmdutils.register(instance='app', ignore_args=True)

View File

@ -20,6 +20,7 @@
"""Early initialization and main entry point.""" """Early initialization and main entry point."""
import sys import sys
import json
import qutebrowser import qutebrowser
try: try:
@ -58,6 +59,7 @@ def get_argparser():
parser.add_argument('-R', '--override-restore', help="Don't restore a " parser.add_argument('-R', '--override-restore', help="Don't restore a "
"session even if one would be restored.", "session even if one would be restored.",
action='store_true') action='store_true')
parser.add_argument('--json-args', help=argparse.SUPPRESS)
debug = parser.add_argument_group('debug arguments') debug = parser.add_argument_group('debug arguments')
debug.add_argument('-l', '--loglevel', dest='loglevel', debug.add_argument('-l', '--loglevel', dest='loglevel',
@ -118,6 +120,13 @@ def main():
"""Main entry point for qutebrowser.""" """Main entry point for qutebrowser."""
parser = get_argparser() parser = get_argparser()
args = parser.parse_args() args = parser.parse_args()
if args.json_args is not None:
# Restoring after a restart.
# When restarting, we serialize the argparse namespace into json, and
# construct a "fake" argparse.Namespace here based on the data loaded
# from json.
data = json.loads(args.json_args)
args = argparse.Namespace(**data)
earlyinit.earlyinit(args) earlyinit.earlyinit(args)
# We do this imports late as earlyinit needs to be run first (because of # We do this imports late as earlyinit needs to be run first (because of
# the harfbuzz fix and version checking). # the harfbuzz fix and version checking).