Ejemplo n.º 1
0
def test_functions():
    assert formatDuration(1) == '1 second'
    assert formatDuration(4) == '4 seconds'
    assert formatDuration(154, precise=False) == '3 min'
    assert formatDuration(154, precise=True) == '2 min, 34 sec'
    assert formatDuration(7199) == '2 h, 0 min'
    assert formatDuration(3700) == '1 h, 2 min'
    assert formatDuration(24 * 3600 + 7240, precise=False) == '1 day, 2 h'
    assert formatDuration(48 * 3600 - 1) == '2 days, 0 h'

    assert bitDescription(0x5, (0, 'a'), (1, 'b', 'c'),
                          (2, 'd', 'e')) == 'a, c, d'

    assert parseConnectionString('[email protected]:pass@host:1301', 1302) == \
        {'user': '******', 'password': '******', 'host': 'host',
         'port': 1301}
    assert parseConnectionString('user:@host', 1302) == \
        {'user': '******', 'password': '', 'host': 'host', 'port': 1302}
    assert parseConnectionString('user@host:1301', 1302) == \
        {'user': '******', 'password': None, 'host': 'host', 'port': 1301}
    assert parseConnectionString('user@ho-st:1301', 1302) == \
        {'user': '******', 'password': None, 'host': 'ho-st', 'port': 1301}
    assert parseConnectionString('', 1302) is None
    assert parseConnectionString('host?', 1302) is None

    # pylint: disable=range-builtin-not-iterating
    assert [tuple(x) for x in chunks(range(10), 3)] == \
        [(0, 1, 2), (3, 4, 5), (6, 7, 8), (9,)]
Ejemplo n.º 2
0
def sleep(secs):
    """Sleep for a given number of seconds.

    This is different from Python's `time.sleep()` in that it allows breaking
    and stopping the sleep, and supports dry run mode.  Fractional values are
    supported.

    Examples:

    >>> sleep(10)     # sleep for 10 seconds
    >>> sleep(0.5)    # sleep for half a second
    """
    session.log.info('sleeping for %.1f seconds...', secs)

    if session.mode == SIMULATION:
        session.clock.tick(secs)
        return

    def f_notify(tmr):
        session.breakpoint(2)  # allow break and continue here
        session.action('%s left' % formatDuration(tmr.remaining_time()))

    session.beginActionScope('Sleeping')
    session.action('%s left' % formatDuration(secs))
    try:
        tmr = Timer(secs)
        tmr.wait(interval=1.0, notify_func=f_notify)
    finally:
        session.endActionScope()
Ejemplo n.º 3
0
 def on_range_change(self):
     try:
         rng = abs(float(self.start.text()) - float(self.stop.text()))
         secs = rng / float(self.speed.text())
         pnts = int(secs / float(self.delta.text()))
         self.totalLabel.setText('Total: %d points, %s' %
                                 (pnts, formatDuration(secs)))
     except (ValueError, ArithmeticError):
         self.totalLabel.setText('Total:')
     self.changed()
Ejemplo n.º 4
0
 def on_range_change(self):
     try:
         pnts = self.numpoints.value()
         rng = abs(float(self.step.text()))
         secs = pnts * rng / float(self.speed.text())
         self.totalLabel.setText('Total: %d points, %s' %
                                 (pnts, formatDuration(secs)))
     except (ValueError, ArithmeticError):
         self.totalLabel.setText('Total:')
     self.changed()
Ejemplo n.º 5
0
def _RunScript(filename, statdevices, debug=False):
    fn = _scriptfilename(filename)
    if not path.isfile(fn) and os.access(fn, os.R_OK):
        raise UsageError('The file %r does not exist or is not readable' % fn)
    if session.mode == SIMULATION:
        starttime = session.clock.time
        for dev in statdevices:
            if not isinstance(dev, Readable):
                session.log.warning('unable to collect statistics on %r', dev)
                continue
            dev._sim_min = None
            dev._sim_max = None
    session.log.info('running user script: %s', fn)
    try:
        fp = io.open(fn, 'r', encoding='utf-8')
    except Exception as e:
        if session.mode == SIMULATION:
            session.log.exception('Dry run: error opening script')
            return
        raise NicosError('cannot open script %r: %s' % (filename, e))
    with fp:
        code = fp.read()
        # guard against bare excepts
        code = fixupScript(code)
        # quick guard against self-recursion
        if session.experiment and session.experiment.scripts and \
                code.strip() == session.experiment.scripts[-1].strip():
            raise NicosError('script %r would call itself, aborting' %
                             filename)

        def compiler(src):
            return compile(src + '\n', fn, 'exec', CO_DIVISION)
        compiled = session.scriptHandler(code, fn, compiler)
        with _ScriptScope(path.basename(fn), code):
            try:
                exec_(compiled, session.namespace)
            except Exception:
                if debug:
                    traceback.print_exc()
                raise
    session.log.info('finished user script: %s', fn)
    if session.mode == SIMULATION:
        session.log.info('simulated minimum runtime: %s',
                         formatDuration(session.clock.time - starttime,
                                        precise=False))
        for dev in statdevices:
            if not isinstance(dev, Readable):
                continue
            session.log.info('%s: min %s, max %s, last %s %s',
                             dev.name,
                             dev.format(dev._sim_min),
                             dev.format(dev._sim_max),
                             dev.format(dev._sim_value), dev.unit)
Ejemplo n.º 6
0
 def on_range_change(self):
     try:
         start = float(self.start.text())
         end = float(self.stop.text())
         step = float(self.step.text())
         counttime = float(self.delta.text())
         numpoints = int(round((end - start) / step + 1))
         secs = numpoints * counttime
         self.totalLabel.setText("Total: %d points, %s" %
                                 (numpoints, formatDuration(secs)))
     except (ValueError, ArithmeticError):
         self.totalLabel.setText("Total:")
     self.changed()
Ejemplo n.º 7
0
def _RunCode(code, debug=False):
    if session.mode == SIMULATION:
        starttime = session.clock.time
    code = fixupScript(code)
    try:
        exec_(code, session.namespace)
    except Exception:
        if debug:
            traceback.print_exc()
        raise
    if session.mode == SIMULATION:
        session.log.info('simulated minimum runtime: %s',
                         formatDuration(session.clock.time - starttime,
                                        precise=False))
Ejemplo n.º 8
0
 def updateTable(self):
     self.table.setRowCount(0)
     table = self.measdef.getTable()
     if not table:
         return
     first = table[0]
     self.table.setRowCount(len(table))
     self.table.setColumnCount(len(first))
     self.table.setHorizontalHeaderLabels(first.keys())
     total_time = 0
     for i, entry in enumerate(table):
         for j, element in enumerate(entry.values()):
             item = QTableWidgetItem(element.getDispValue())
             self.table.setItem(i, j, item)
             if element.eltype == 'time':
                 total_time += element.getValue()
     self.table.resizeRowsToContents()
     self.totalTime.setText(formatDuration(total_time))
     self.changed()
Ejemplo n.º 9
0
    def on_client_simresult(self, data):
        timing, devinfo, uuid = data
        if uuid != self.simuuid:
            return
        self.simuuid = None

        # show timing
        if timing < 0:
            self.simTotalTime.setText('Error occurred')
            self.simFinished.setText('See messages')
        else:
            self.simTotalTime.setText(formatDuration(timing, precise=False))
            self.simFinished.setText(formatEndtime(timing))

        # device ranges
        for devname, (_dval, dmin, dmax, aliases) in devinfo.items():
            if dmin is not None:
                aliascol = 'aliases: ' + ', '.join(aliases) if aliases else ''
                item = QTreeWidgetItem([devname, dmin, '-', dmax, '', aliascol])
                self.simRanges.addTopLevelItem(item)

        self.simRanges.sortByColumn(0, Qt.AscendingOrder)
Ejemplo n.º 10
0
 def f_notify(tmr):
     session.breakpoint(2)  # allow break and continue here
     session.action('%s left' % formatDuration(tmr.remaining_time()))
Ejemplo n.º 11
0
 def signal(self, name, data=None, exc=None):
     """Handles any kind of signal/event sent by the daemon."""
     try:
         # try to order the elifs by frequency
         if name == 'message':
             if self.in_editing:
                 self.message_queue.append(data)
             else:
                 self.put_message(data)
         elif name == 'status':
             status, line = data
             if status == STATUS_IDLE or status == STATUS_IDLEEXC:
                 new_status = 'idle'
                 self.stop_pending = False
             elif status != STATUS_INBREAK:
                 new_status = 'running'
             else:
                 new_status = 'paused'
             if status != self.status:
                 self.set_status(new_status)
             if line != self.current_line:
                 self.current_line = line
         elif name == 'cache':
             if data[1].endswith('/scriptpath'):
                 self.scriptpath = self.eval(
                     'session.experiment.scriptpath', '.')
         elif name == 'processing':
             script = data.get('script')
             if script is None:
                 return
             self.current_filename = data.get('name') or ''
             script = script.splitlines() or ['']
             if script != self.current_script:
                 self.current_script = script
             self.pending_requests.pop(data['reqid'], None)
             self.set_status(self.status)
         elif name == 'request':
             if 'script' in data:
                 self.pending_requests[data['reqid']] = data
             self.set_status(self.status)
         elif name == 'blocked':
             removed = [
                 _f for _f in (self.pending_requests.pop(reqid, None)
                               for reqid in data) if _f
             ]
             if removed:
                 self.put_client('%d script(s) or command(s) removed from '
                                 'queue.' % len(removed))
                 self.show_pending()
             self.set_status(self.status)
         elif name == 'updated':
             if 'script' in data:
                 self.pending_requests[data['reqid']] = data
         elif name == 'rearranged':
             old_reqs = self.pending_requests.copy()
             self.pending_requests.clear()
             for reqid in data:
                 self.pending_requests[reqid] = old_reqs[reqid]
         elif name == 'connected':
             self.reconnect_count = 0
             self.initial_update()
         elif name == 'disconnected':
             self.put_client('Disconnected from server, use /reconnect to '
                             'try reconnecting.')
             self.current_mode = MASTER
             self.debug_mode = False
             self.pending_requests.clear()
             self.set_status('disconnected')
         elif name == 'showhelp':
             self.showhelp(data[1])
         elif name == 'simmessage':
             if data[5] in [self.simuuid, '0']:
                 if not self.in_editing:
                     self.put_message(data, sim=True)
         elif name == 'simresult':
             if data and data[2] in [self.simuuid, '0']:
                 timing, devinfo, _ = data
                 if timing < 0:
                     self.put_client('Dry run resulted in an error.')
                     return
                 self.put_client(
                     'Simulated minimum runtime: %s '
                     '(finishes approximately %s). Device ranges:' %
                     (formatDuration(timing,
                                     precise=False), formatEndtime(timing)))
                 if devinfo:
                     dnwidth = max(map(len, devinfo))
                     sorteditems = sorted(devinfo.items(),
                                          key=lambda x: x[0].lower())
                     for devname, (_, dmin, dmax, aliases) in sorteditems:
                         aliascol = 'aliases: ' + ', '.join(
                             aliases) if aliases else ''
                         self.put('#   %-*s: %10s  <->  %-10s %s' %
                                  (dnwidth, devname, dmin, dmax, aliascol))
         elif name == 'mode':
             self.current_mode = data
             self.set_status(self.status)
         elif name == 'setup':
             self.scriptpath = self.eval('session.experiment.scriptpath',
                                         '.')
             self.instrument = self.eval('session.instrument.instrument',
                                         self.instrument)
         elif name == 'debugging':
             self.debug_mode = data
             readline_finish_callback(False)
         elif name == 'plugplay':
             if data[0] == 'added':
                 self.put_client('new sample environment detected: load '
                                 'setup %r to activate' % data[1])
             elif data[0] == 'removed':
                 self.put_client('sample environment removed: unload '
                                 'setup %r to clear devices' % data[1])
         elif name == 'eta':
             self.handle_eta(data)
         elif name == 'broken':
             self.put_error(data)
             self.reconnect_count = self.RECONNECT_TRIES
             self.reconnect_time = self.RECONNECT_INTERVAL_SHORT
             self.schedule_reconnect()
         elif name == 'failed':
             if self.reconnect_count:
                 self.schedule_reconnect()
             else:
                 self.put_error(data)
         elif name == 'error':
             self.put_error(data)
         # and we ignore all other signals
     except Exception as e:
         self.put_error('In %s event handler: %s.' % (name, e))
Ejemplo n.º 12
0
 def _update_time(self):
     self.totalLbl.setText('Total time: %s' %
                           formatDuration(self.getSettings()['totaltime']))
Ejemplo n.º 13
0
def multiWait(devices):
    """Wait for the *devices*.

    Returns a dictionary mapping devices to current values after waiting.

    This is the main waiting loop to be used when waiting for multiple devices.
    It checks the device status until all devices are OK or errored.

    Errors raised are handled like in the following way:
    The error is logged, and the first exception with the highest serverity
    (exception in `CONTINUE_EXECPTIONS` < `SKIP_EXCPTIONS` < other exceptions)
    is re-raised at the end.

    *baseclass* allows to restrict the devices waited on.
    """
    from nicos.core.device import Waitable

    def get_target_str():
        return ', '.join(
            '%s -> %s' %
            (dev,
             dev.format(dev.target)) if hasattr(dev, 'target') else str(dev)
            for dev in reversed(devlist))

    delay = 0.3
    final_exc = None
    devlist = list(devIter(devices, baseclass=Waitable, allwaiters=True))
    session.log.debug('multiWait: initial devices %s, all waiters %s', devices,
                      devlist)
    values = {}
    loops = -2  # wait 2 iterations for full loop
    eta_update = 1 if session.mode != SIMULATION else 0
    first_ts = currenttime()
    session.beginActionScope('Waiting')
    eta_str = ''
    target_str = get_target_str()
    session.action(target_str)
    try:
        while devlist:
            session.log.debug('multiWait: iteration %d, devices left %s',
                              loops, devlist)
            loops += 1
            for dev in devlist[:]:
                try:
                    done = dev.isCompleted()
                    if done:
                        dev.finish()
                except Exception:
                    final_exc = filterExceptions(sys.exc_info(), final_exc)
                    # remove this device from the waiters - we might still have
                    # its subdevices in the list so that multiWait() should not
                    # return until everything is either OK or ERROR
                    devlist.remove(dev)
                    if devlist:
                        # at least one more device left, show the exception now
                        dev.log.exception('while waiting')
                    continue
                if not done:
                    # we found one busy dev, normally go to next iteration
                    # until this one is done (saves going through the whole
                    # list of devices and doing unnecessary HW communication)
                    if loops % 10:
                        break
                    # every 10 loops, go through everything to get an accurate
                    # display in the action line
                    continue
                if dev in devices:
                    # populate the results dictionary, but only with the values
                    # of excplicitly given devices
                    values[dev] = dev.read()
                # this device is done: don't wait for it anymore
                devlist.remove(dev)
                target_str = get_target_str()
                session.action(eta_str + target_str)
            if devlist:
                if eta_update >= 1:
                    eta_update -= 1
                    now = currenttime()
                    eta = {dev.estimateTime(now - first_ts) for dev in devlist}
                    eta.discard(None)
                    # use max here as we wait for ALL movements to finish
                    eta_str = ('estimated %s left / ' %
                               formatDuration(max(eta)) if eta else '')
                    session.action(eta_str + target_str)
                session.delay(delay)
                eta_update += delay
        if final_exc:
            reraise(*final_exc)
    finally:
        session.endActionScope()
        session.log.debug('multiWait: finished')
    return values