Merge remote-tracking branch 'zyx-i/no-update_lock' into develop
This commit is contained in:
commit
40436c549a
|
@ -1,9 +1,18 @@
|
||||||
# vim:fileencoding=utf-8:noet
|
# vim:fileencoding=utf-8:noet
|
||||||
import zsh
|
import zsh
|
||||||
|
import atexit
|
||||||
from powerline.shell import ShellPowerline
|
from powerline.shell import ShellPowerline
|
||||||
from powerline.lib import parsedotval
|
from powerline.lib import parsedotval
|
||||||
|
|
||||||
|
|
||||||
|
used_powerlines = []
|
||||||
|
|
||||||
|
|
||||||
|
def shutdown():
|
||||||
|
for powerline in used_powerlines:
|
||||||
|
powerline.renderer.shutdown()
|
||||||
|
|
||||||
|
|
||||||
def get_var_config(var):
|
def get_var_config(var):
|
||||||
try:
|
try:
|
||||||
return [parsedotval(i) for i in zsh.getvalue(var).items()]
|
return [parsedotval(i) for i in zsh.getvalue(var).items()]
|
||||||
|
@ -69,17 +78,17 @@ class Environment(object):
|
||||||
|
|
||||||
|
|
||||||
class Prompt(object):
|
class Prompt(object):
|
||||||
__slots__ = ('render', 'side', 'savedpsvar', 'savedps', 'args')
|
__slots__ = ('powerline', 'side', 'savedpsvar', 'savedps', 'args')
|
||||||
|
|
||||||
def __init__(self, powerline, side, savedpsvar=None, savedps=None):
|
def __init__(self, powerline, side, savedpsvar=None, savedps=None):
|
||||||
self.render = powerline.renderer.render
|
self.powerline = powerline
|
||||||
self.side = side
|
self.side = side
|
||||||
self.savedpsvar = savedpsvar
|
self.savedpsvar = savedpsvar
|
||||||
self.savedps = savedps
|
self.savedps = savedps
|
||||||
self.args = powerline.args
|
self.args = powerline.args
|
||||||
|
|
||||||
def __str__(self):
|
def __str__(self):
|
||||||
r = self.render(width=zsh.columns(), side=self.side, segment_info=self.args)
|
r = self.powerline.renderer.render(width=zsh.columns(), side=self.side, segment_info=self.args)
|
||||||
if type(r) is not str:
|
if type(r) is not str:
|
||||||
if type(r) is bytes:
|
if type(r) is bytes:
|
||||||
return r.decode('utf-8')
|
return r.decode('utf-8')
|
||||||
|
@ -90,6 +99,9 @@ class Prompt(object):
|
||||||
def __del__(self):
|
def __del__(self):
|
||||||
if self.savedps:
|
if self.savedps:
|
||||||
zsh.setvalue(self.savedpsvar, self.savedps)
|
zsh.setvalue(self.savedpsvar, self.savedps)
|
||||||
|
used_powerlines.remove(self.powerline)
|
||||||
|
if self.powerline not in used_powerlines:
|
||||||
|
self.powerline.renderer.shutdown()
|
||||||
|
|
||||||
|
|
||||||
def set_prompt(powerline, psvar, side):
|
def set_prompt(powerline, psvar, side):
|
||||||
|
@ -103,5 +115,8 @@ def set_prompt(powerline, psvar, side):
|
||||||
def setup():
|
def setup():
|
||||||
environ = Environment()
|
environ = Environment()
|
||||||
powerline = ShellPowerline(Args(), environ=environ, getcwd=lambda: environ['PWD'])
|
powerline = ShellPowerline(Args(), environ=environ, getcwd=lambda: environ['PWD'])
|
||||||
|
used_powerlines.append(powerline)
|
||||||
|
used_powerlines.append(powerline)
|
||||||
set_prompt(powerline, 'PS1', 'left')
|
set_prompt(powerline, 'PS1', 'left')
|
||||||
set_prompt(powerline, 'RPS1', 'right')
|
set_prompt(powerline, 'RPS1', 'right')
|
||||||
|
atexit.register(shutdown)
|
||||||
|
|
|
@ -4,21 +4,18 @@ from __future__ import absolute_import
|
||||||
|
|
||||||
from powerline.lib.time import monotonic
|
from powerline.lib.time import monotonic
|
||||||
|
|
||||||
from time import sleep
|
from threading import Thread, Lock, Event
|
||||||
from threading import Thread, Lock
|
|
||||||
|
|
||||||
|
|
||||||
class ThreadedSegment(object):
|
class ThreadedSegment(object):
|
||||||
daemon = True
|
|
||||||
min_sleep_time = 0.1
|
min_sleep_time = 0.1
|
||||||
update_first = True
|
update_first = True
|
||||||
interval = 1
|
interval = 1
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
super(ThreadedSegment, self).__init__()
|
super(ThreadedSegment, self).__init__()
|
||||||
self.update_lock = Lock()
|
self.shutdown_event = Event()
|
||||||
self.write_lock = Lock()
|
self.write_lock = Lock()
|
||||||
self.keep_going = True
|
|
||||||
self.run_once = True
|
self.run_once = True
|
||||||
self.did_set_interval = False
|
self.did_set_interval = False
|
||||||
self.thread = None
|
self.thread = None
|
||||||
|
@ -39,6 +36,8 @@ class ThreadedSegment(object):
|
||||||
if update_first and self.update_first:
|
if update_first and self.update_first:
|
||||||
self.update()
|
self.update()
|
||||||
self.start()
|
self.start()
|
||||||
|
elif not self.updated:
|
||||||
|
self.update()
|
||||||
|
|
||||||
if self.skip:
|
if self.skip:
|
||||||
return self.crashed_value
|
return self.crashed_value
|
||||||
|
@ -49,40 +48,29 @@ class ThreadedSegment(object):
|
||||||
return self.thread and self.thread.is_alive()
|
return self.thread and self.thread.is_alive()
|
||||||
|
|
||||||
def start(self):
|
def start(self):
|
||||||
|
self.keep_going = True
|
||||||
self.thread = Thread(target=self.run)
|
self.thread = Thread(target=self.run)
|
||||||
self.thread.daemon = self.daemon
|
|
||||||
self.thread.start()
|
self.thread.start()
|
||||||
|
|
||||||
def sleep(self, adjust_time):
|
def sleep(self, adjust_time):
|
||||||
sleep(max(self.interval - adjust_time, self.min_sleep_time))
|
self.shutdown_event.wait(max(self.interval - adjust_time, self.min_sleep_time))
|
||||||
|
if self.shutdown_event.is_set():
|
||||||
|
self.keep_going = False
|
||||||
|
|
||||||
def run(self):
|
def run(self):
|
||||||
while self.keep_going:
|
while self.keep_going:
|
||||||
start_time = monotonic()
|
start_time = monotonic()
|
||||||
|
|
||||||
try:
|
try:
|
||||||
if self.update_lock.acquire(False):
|
self.update()
|
||||||
try:
|
except Exception as e:
|
||||||
self.update()
|
self.error('Exception while updating: {0}', str(e))
|
||||||
except Exception as e:
|
self.skip = True
|
||||||
self.error('Exception while updating: {0}', str(e))
|
else:
|
||||||
self.skip = True
|
self.skip = False
|
||||||
else:
|
|
||||||
self.skip = False
|
|
||||||
else:
|
|
||||||
return
|
|
||||||
finally:
|
|
||||||
# Release lock in any case. If it is not locked in this thread,
|
|
||||||
# it was done in main thread in .shutdown method, and the lock
|
|
||||||
# will never be released.
|
|
||||||
self.update_lock.release()
|
|
||||||
|
|
||||||
self.sleep(monotonic() - start_time)
|
self.sleep(monotonic() - start_time)
|
||||||
|
|
||||||
def shutdown(self):
|
def shutdown(self):
|
||||||
if self.keep_going:
|
self.shutdown_event.set()
|
||||||
self.keep_going = False
|
|
||||||
self.update_lock.acquire()
|
|
||||||
|
|
||||||
def set_interval(self, interval=None):
|
def set_interval(self, interval=None):
|
||||||
# Allowing “interval” keyword in configuration.
|
# Allowing “interval” keyword in configuration.
|
||||||
|
@ -93,9 +81,10 @@ class ThreadedSegment(object):
|
||||||
self.interval = interval
|
self.interval = interval
|
||||||
self.has_set_interval = True
|
self.has_set_interval = True
|
||||||
|
|
||||||
def set_state(self, interval=None, **kwargs):
|
def set_state(self, interval=None, update_first=True, **kwargs):
|
||||||
if not self.did_set_interval or interval:
|
if not self.did_set_interval or interval:
|
||||||
self.set_interval(interval)
|
self.set_interval(interval)
|
||||||
|
self.updated = not (update_first and self.update_first)
|
||||||
|
|
||||||
def startup(self, pl, **kwargs):
|
def startup(self, pl, **kwargs):
|
||||||
self.run_once = False
|
self.run_once = False
|
||||||
|
@ -124,12 +113,13 @@ def printed(func):
|
||||||
|
|
||||||
class KwThreadedSegment(ThreadedSegment):
|
class KwThreadedSegment(ThreadedSegment):
|
||||||
drop_interval = 10 * 60
|
drop_interval = 10 * 60
|
||||||
update_first = False
|
update_first = True
|
||||||
|
|
||||||
def __init__(self):
|
def __init__(self):
|
||||||
super(KwThreadedSegment, self).__init__()
|
super(KwThreadedSegment, self).__init__()
|
||||||
self.queries = {}
|
self.queries = {}
|
||||||
self.crashed = set()
|
self.crashed = set()
|
||||||
|
self.updated = True
|
||||||
|
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def key(**kwargs):
|
def key(**kwargs):
|
||||||
|
@ -170,7 +160,7 @@ class KwThreadedSegment(ThreadedSegment):
|
||||||
for key in removes:
|
for key in removes:
|
||||||
self.queries.pop(key)
|
self.queries.pop(key)
|
||||||
|
|
||||||
def set_state(self, interval=None, **kwargs):
|
def set_state(self, interval=None, update_first=True, **kwargs):
|
||||||
if not self.did_set_interval or (interval < self.interval):
|
if not self.did_set_interval or (interval < self.interval):
|
||||||
self.set_interval(interval)
|
self.set_interval(interval)
|
||||||
|
|
||||||
|
|
|
@ -193,6 +193,7 @@ class TestCommon(TestCase):
|
||||||
|
|
||||||
def test_network_load(self):
|
def test_network_load(self):
|
||||||
from time import sleep
|
from time import sleep
|
||||||
|
|
||||||
def gb(interface):
|
def gb(interface):
|
||||||
return None
|
return None
|
||||||
|
|
||||||
|
@ -251,6 +252,7 @@ class TestCommon(TestCase):
|
||||||
{'divider_highlight_group': 'background:divider', 'contents': 'r 1 KiB/s', 'highlight_group': ['network_load_recv', 'network_load']},
|
{'divider_highlight_group': 'background:divider', 'contents': 'r 1 KiB/s', 'highlight_group': ['network_load_recv', 'network_load']},
|
||||||
{'divider_highlight_group': 'background:divider', 'contents': 's 2 KiB/s', 'highlight_group': ['network_load_sent_gradient', 'network_load_gradient', 'network_load_sent', 'network_load'], 'gradient_level': ApproxEqual()},
|
{'divider_highlight_group': 'background:divider', 'contents': 's 2 KiB/s', 'highlight_group': ['network_load_sent_gradient', 'network_load_gradient', 'network_load_sent', 'network_load'], 'gradient_level': ApproxEqual()},
|
||||||
])
|
])
|
||||||
|
common.network_load.shutdown()
|
||||||
|
|
||||||
def test_virtualenv(self):
|
def test_virtualenv(self):
|
||||||
with replace_env('VIRTUAL_ENV', '/abc/def/ghi') as pl:
|
with replace_env('VIRTUAL_ENV', '/abc/def/ghi') as pl:
|
||||||
|
|
Loading…
Reference in New Issue