Hello community, here is the log from the commit of package python-ioflo for openSUSE:Factory checked in at 2014-10-23 14:21:00 ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Comparing /work/SRC/openSUSE:Factory/python-ioflo (Old) and /work/SRC/openSUSE:Factory/.python-ioflo.new (New) ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Package is "python-ioflo" Changes: -------- --- /work/SRC/openSUSE:Factory/python-ioflo/python-ioflo.changes 2014-07-31 07:42:07.000000000 +0200 +++ /work/SRC/openSUSE:Factory/.python-ioflo.new/python-ioflo.changes 2014-10-23 14:21:21.000000000 +0200 @@ -1,0 +2,8 @@ +Wed Oct 22 20:52:37 UTC 2014 - [email protected] + +- Major update to v1.0.1 + - Changed license to Apache 2.0 1.0 release + - Added WinMailslotNb Class for non blocking comms on windows to replace SocketUxdNb + - Added better support for Python3 + +------------------------------------------------------------------- Old: ---- ioflo-0.9.39.tar.gz New: ---- ioflo-1.0.1.tar.gz ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ Other differences: ------------------ ++++++ python-ioflo.spec ++++++ --- /var/tmp/diff_new_pack.0DQqJP/_old 2014-10-23 14:21:22.000000000 +0200 +++ /var/tmp/diff_new_pack.0DQqJP/_new 2014-10-23 14:21:22.000000000 +0200 @@ -1,7 +1,7 @@ # # spec file for package python-ioflo # -# Copyright (c) 2012 SUSE LINUX Products GmbH, Nuernberg, Germany. +# Copyright (c) 2014 SUSE LINUX Products GmbH, Nuernberg, Germany. # # All modifications and additions to the file contributed by third parties # remain the property of their copyright owners, unless otherwise agreed @@ -16,9 +16,9 @@ # Name: python-ioflo -Version: 0.9.39 +Version: 1.0.1 Release: 0 -License: MIT +License: Apache-2.0 Summary: Python IoFlo Url: https://github.com/ioflo/ioflo Group: Development/Languages/Python ++++++ ioflo-0.9.39.tar.gz -> ioflo-1.0.1.tar.gz ++++++ diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/PKG-INFO new/ioflo-1.0.1/PKG-INFO --- old/ioflo-0.9.39/PKG-INFO 2014-07-24 20:17:35.000000000 +0200 +++ new/ioflo-1.0.1/PKG-INFO 2014-10-02 18:31:29.000000000 +0200 @@ -1,11 +1,11 @@ Metadata-Version: 1.1 Name: ioflo -Version: 0.9.39 +Version: 1.0.1 Summary: Flow Based Programming Automated Reasoning Engine and Automation Operation System Home-page: https://github.com/ioflo/ioflo Author: Samuel M. Smith Author-email: [email protected] -License: MIT +License: Apache 2.0 Download-URL: https://github.com/ioflo/ioflo/archive/master.zip Description: Enabling the Programmable World. http://ioflo.com Keywords: Automation Operating System Automated Reasoning Engine Flow Based Programming Intelligent Automation Pub/Sub ioflo FloScript diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/__init__.py new/ioflo-1.0.1/ioflo/__init__.py --- old/ioflo-0.9.39/ioflo/__init__.py 2014-07-24 20:14:19.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/__init__.py 2014-10-02 18:30:46.000000000 +0200 @@ -1,15 +1,13 @@ """ ioflo package """ -#print("\nPackage at {0}".format( __path__[0])) - from __future__ import division import importlib -__version__ = "0.9.39" +__version__ = "1.0.1" __author__ = "Samuel M. Smith" -__license__ = "MIT" +__license__ = "Apache 2.0" __all__ = ['base', 'trim'] diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/base/acting.py new/ioflo-1.0.1/ioflo/base/acting.py --- old/ioflo-0.9.39/ioflo/base/acting.py 2014-04-17 18:19:42.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/base/acting.py 2014-09-24 04:41:11.000000000 +0200 @@ -14,7 +14,7 @@ from .odicting import odict from . import aiding -from .aiding import NonStringIterable, nameToPath +from .aiding import nonStringIterable, nameToPath from . import excepting from . import registering from . import storing @@ -380,7 +380,7 @@ if not ival: #empty mapping ival = odict(value=copy.copy(ival)) #make copy so each instance unique # otherwise don't change since ival is non-empty mapping - elif isinstance(ival, NonStringIterable): # not mapping and NonStringIterable + elif nonStringIterable(ival): # not mapping and nonStringIterable ival = odict(value=copy.copy(ival)) else: ival = odict(value=ival) diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/base/aiding.py new/ioflo-1.0.1/ioflo/base/aiding.py --- old/ioflo-0.9.39/ioflo/base/aiding.py 2014-07-24 19:06:14.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/base/aiding.py 2014-09-24 05:33:19.000000000 +0200 @@ -6,39 +6,29 @@ from __future__ import division import sys -if sys.version > '3': - xrange = range - -if sys.version < '3': - def b(x): - return x - - def u(x): - return unicode(x) -else: - def b(x): - return x.encode('ISO-8859-1') - - def u(x): - return x - - import math import types import socket import os +import sys import errno import time import struct import re import string -from collections import deque +from collections import deque, Iterable, Sequence +from abc import ABCMeta try: import simplejson as json except ImportError: import json +try: + import win32file +except ImportError: + pass + # Import ioflo libs from .globaling import * from .odicting import odict @@ -46,8 +36,6 @@ from .consoling import getConsole console = getConsole() - - def metaclassify(metaclass): """ Class decorator for creating a class with a metaclass. @@ -83,6 +71,54 @@ return metaclass(cls.__name__, cls.__bases__, originals) return wrapper +@metaclassify(ABCMeta) +class NonStringIterable: + """ Allows isinstance check for iterable that is not a string + """ + #__metaclass__ = ABCMeta + + @classmethod + def __subclasshook__(cls, C): + if cls is NonStringIterable: + if (not issubclass(C, basestring) and issubclass(C, Iterable)): + return True + return NotImplemented + +@metaclassify(ABCMeta) +class NonStringSequence: + """ Allows isinstance check for sequence that is not a string + """ + #__metaclass__ = ABCMeta + + @classmethod + def __subclasshook__(cls, C): + if cls is NonStringSequence: + if (not issubclass(C, basestring) and issubclass(C, Sequence)): + return True + return NotImplemented + +def nonStringIterable(obj): + """ + Returns True if obj is non-string iterable, False otherwise + + Future proof way that is compatible with both Python3 and Python2 to check + for non string iterables. + Assumes in Python3 that, basestring = (str, bytes) + + Faster way that is less future proof + return (hasattr(x, '__iter__') and not isinstance(x, basestring)) + """ + return (not isinstance(obj, basestring) and isinstance(obj, Iterable)) + +def nonStringSequence(obj): + """ + Returns True if obj is non-string sequence, False otherwise + + Future proof way that is compatible with both Python3 and Python2 to check + for non string sequences. + Assumes in Python3 that, basestring = (str, bytes) + """ + return (not isinstance(obj, basestring) and isinstance(obj, Sequence) ) class Fifo(deque): #new-style class to add put get methods """ Extends deque to support more convenient FIFO queue access @@ -624,7 +660,8 @@ return (data,sa) except socket.error as ex: # 2.6 socket.error is subclass of IOError - if ex.errno == errno.EAGAIN: #Resource temporarily unavailable on os x + # Some OSes define errno differently so check for both + if ex.errno == errno.EAGAIN or ex.errno == errno.EWOULDBLOCK: return ('',None) #receive has nothing empty string for data else: emsg = "socket.error = {0}: receiving at {1}\n".format(ex, self.ha) @@ -835,6 +872,175 @@ return result +class WinMailslotNb(object): + """ + Class to manage non-blocking reads and writes from a + Windows Mailslot + + Opens a non-blocking mailslot + Use instance method to close socket + + Needs Windows Python Extensions + """ + + def __init__(self, ha=None, bufsize=1024, path='', log=False): + """ + Init method for instance + + bufsize = default mailslot buffer size + path = path to directory where logfiles go. Must end in /. + ha = basename for mailslot path. + """ + self.ha = ha + self.bs = bufsize + self.ms = None # Mailslot needs to be opened + + self.path = path + self.txLog = None # Transmit log + self.rxLog = None # receive log + self.log = log + + def open(self): + """ + Opens mailslot in nonblocking mode + """ + try: + self.ms = win32file.CreateMailslot(self.ha, 0, 0, None) + # ha = path to mailslot + # 0 = MaxMessageSize, 0 for unlimited + # 0 = ReadTimeout, 0 to not block + # None = SecurityAttributes, none for nothing special + except win32file.error as ex: + console.terse('mailslot.error = {0}'.format(ex)) + return False + + if self.log: + if not self.openLogs(): + return False + + return True + + def reopen(self): + """ + Clear the ms and reopen + """ + self.close() + return self.open() + + def close(self): + ''' + Close the mailslot + ''' + if self.ms: + win32file.CloseHandle(self.ms) + self.ms = None + + self.closeLogs() + + def receive(self): + """ + Perform a non-blocking read on the mailslot + + Returns tuple of form (data, sa) + if no data, returns ('', None) + but always returns a tuple with 2 elements + + Note win32file.ReadFile returns a tuple: (errcode, data) + + """ + try: + data = win32file.ReadFile(self.ms, self.bs) + + # Mailslots don't send their source address + # We can pick this up in a higher level of the stack if we + # need + sa = None + + message = "Server at {0} received {1}\n".format( + self.ha, data[1]) + + console.profuse(message) + + if self.log and self.rxLog: + self.rxLog.write("%s\n%s\n" % (sa, repr(data[1]))) + + return (data[1], sa) + + except win32file.error: + return ('', None) + + def send(self, data, destmailslot): + """ + Perform a non-blocking write on the mailslot + data is string in python2 and bytes in python3 + da is destination mailslot path + """ + + try: + f = win32file.CreateFile(destmailslot, + win32file.GENERIC_WRITE | win32file.GENERIC_READ, + win32file.FILE_SHARE_READ, + None, win32file.OPEN_ALWAYS, 0, None) + except win32file.error as ex: + emsg = 'mailslot.error = {0}: opening mailslot from {1} to {2}\n'.format( + ex, self.ha, destmailslot) + console.terse(emsg) + result = 0 + raise + + try: + result = win32file.WriteFile(f, data) + console.profuse("Server at {0} sent {1} bytes\n".format(self.ha, + result)) + except win32file.error as ex: + emsg = 'mailslot.error = {0}: sending from {1} to {2}\n'.format(ex, self.ha, destmailslot) + console.terse(emsg) + result = 0 + raise + + finally: + win32file.CloseHandle(f) + + if self.log and self.txLog: + self.txLog.write("%s %s bytes\n%s\n" % + (str(destmailslot), str(result), repr(data))) + + # WriteFile returns a tuple, we only care about the number of bytes + return result[1] + + def openLogs(self, path = ''): + """Open log files + + """ + date = time.strftime('%Y%m%d_%H%M%S',time.gmtime(time.time())) + name = "%s%s_%s_%s_tx.txt" % (self.path, self.ha[0], str(self.ha[1]), date) + try: + self.txLog = open(name, 'w+') + except IOError: + self.txLog = None + self.log = False + return False + name = "%s%s_%s_%s_rx.txt" % (self.path, self.ha[0], str(self.ha[1]), date) + try: + self.rxLog = open(name, 'w+') + except IOError: + self.rxLog = None + self.log = False + return False + + return True + + def closeLogs(self): + """Close log files + + """ + if self.txLog and not self.txLog.closed: + self.txLog.close() + if self.rxLog and not self.rxLog.closed: + self.rxLog.close() + + + #Utility Functions def TotalSeconds(td): @@ -959,27 +1165,6 @@ just = Just #alias -from abc import ABCMeta, abstractmethod -@metaclassify(ABCMeta) -class NonStringIterable: - """ Check for iterable that is not a string - Works in python 2.6 to 3.x with isinstance(x, NonStringIterable) - - """ - #__metaclass__ = ABCMeta - - @abstractmethod - def __iter__(self): - while False: - yield None - - @classmethod - def __subclasshook__(cls, C): - if cls is NonStringIterable: - if any("__iter__" in B.__dict__ for B in C.__mro__): - return True - return NotImplemented - # Faster to use precompiled versions in globaling def IsPath(s): """Returns True if string s is valid Store path name @@ -2115,4 +2300,3 @@ return it loadJson = LoadJson - diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/base/deeding.py new/ioflo-1.0.1/ioflo/base/deeding.py --- old/ioflo-0.9.39/ioflo/base/deeding.py 2014-04-17 18:19:42.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/base/deeding.py 2014-09-24 04:42:03.000000000 +0200 @@ -22,7 +22,7 @@ from .consoling import getConsole console = getConsole() -from .aiding import NonStringIterable, just, nameToPath +from .aiding import nonStringIterable, just, nameToPath def deedify(name, base=None, registry=None, inits=None, ioinits=None, parms=None, parametric=None): diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/base/globaling.py new/ioflo-1.0.1/ioflo/base/globaling.py --- old/ioflo-0.9.39/ioflo/base/globaling.py 2014-04-15 19:08:14.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/base/globaling.py 2014-09-24 04:02:20.000000000 +0200 @@ -4,17 +4,45 @@ #print("module {0}".format(__name__)) import sys +import math +import re + + +# Python2to3 support if sys.version > '3': long = int basestring = (str, bytes) unicode = str + xrange = range + + def ns2b(x): + """ + Converts from native str type to native bytes type + """ + return x.encode('ISO-8859-1') + + def ns2u(x): + """ + Converts from native str type to native unicode type + """ + return x + else: - long = long - basestring = basestring - unicode = unicode + #long = long + #basestring = basestring + #unicode = unicode -import math -import re + def ns2b(x): + """ + Converts from native str type to native bytes type + """ + return x + + def ns2u(x): + """ + Converts from native str type to native unicode type + """ + return unicode(x) #Globals diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/base/logging.py new/ioflo-1.0.1/ioflo/base/logging.py --- old/ioflo-0.9.39/ioflo/base/logging.py 2014-04-17 18:19:42.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/base/logging.py 2014-09-24 04:37:02.000000000 +0200 @@ -23,7 +23,6 @@ from .globaling import * from .odicting import odict -from .aiding import u from . import excepting from . import registering @@ -369,23 +368,23 @@ #build header cf = io.StringIO() - cf.write(u(self.kind)) + cf.write(ns2u(self.kind)) cf.write(u'\t') - cf.write(u(LogRuleNames[self.rule])) + cf.write(ns2u(LogRuleNames[self.rule])) cf.write(u'\t') - cf.write(u(self.fileName)) + cf.write(ns2u(self.fileName)) cf.write(u'\n') cf.write(u'_time') for tag, loggee in self.loggees.items(): if len(loggee) > 1: for field in loggee: cf.write(u'\t') - cf.write(u(tag)) + cf.write(ns2u(tag)) cf.write(u'.') - cf.write(u(field)) + cf.write(ns2u(field)) else: cf.write(u'\t') - cf.write(u(tag)) + cf.write(ns2u(tag)) cf.write(u'\n') self.header = cf.getvalue() @@ -433,7 +432,7 @@ text = self.formats['_time'] % self.stamp except TypeError: text = '%s' % self.stamp - cf.write(u(text)) + cf.write(ns2u(text)) for tag, loggee in self.loggees.items(): if loggee: #len non zero @@ -442,7 +441,7 @@ text = self.formats[tag][field] % value except TypeError: text = '%s' % value - cf.write(u(text)) + cf.write(ns2u(text)) else: #no items so just write tab cf.write(u'\t') diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo/base/test/testAiding.py new/ioflo-1.0.1/ioflo/base/test/testAiding.py --- old/ioflo-0.9.39/ioflo/base/test/testAiding.py 2014-07-24 19:06:14.000000000 +0200 +++ new/ioflo-1.0.1/ioflo/base/test/testAiding.py 2014-09-24 05:32:11.000000000 +0200 @@ -114,6 +114,27 @@ b = Blend0(d,u,s) print(d, b) +def TestNonStringIterableSequence(w=dict(a=1, b=2, c=3), x='abc', y=b'abc', z=[1, 2, 3]): + """ + """ + result = isinstance(w, aiding.NonStringIterable) + print("{0} is NonStringIterable = {1}".format(repr(w), result)) + result = isinstance(x, aiding.NonStringIterable) + print("{0} is NonStringIterable = {1}".format(repr(x), result)) + result = isinstance(y, aiding.NonStringIterable) + print("{0} is NonStringIterable = {1}".format(repr(y), result)) + result = isinstance(z, aiding.NonStringIterable) + print("{0} is NonStringIterable = {1}".format(repr(z), result)) + print() + result = isinstance(w, aiding.NonStringSequence) + print("{0} is NonStringSequence = {1}".format(repr(w), result)) + result = isinstance(x, aiding.NonStringSequence) + print("{0} is NonStringSequence = {1}".format(repr(x), result)) + result = isinstance(y, aiding.NonStringSequence) + print("{0} is NonStringSequence = {1}".format(repr(y), result)) + result = isinstance(z, aiding.NonStringSequence) + print("{0} is NonStringSequence = {1}".format(repr(z), result)) + def Test(): """Module self test @@ -124,4 +145,5 @@ if __name__ == "__main__": #Test() - TestSocketUxdNB() + #TestSocketUxdNB() + TestNonStringIterableSequence() diff -urN '--exclude=CVS' '--exclude=.cvsignore' '--exclude=.svn' '--exclude=.svnignore' old/ioflo-0.9.39/ioflo.egg-info/PKG-INFO new/ioflo-1.0.1/ioflo.egg-info/PKG-INFO --- old/ioflo-0.9.39/ioflo.egg-info/PKG-INFO 2014-07-24 20:17:26.000000000 +0200 +++ new/ioflo-1.0.1/ioflo.egg-info/PKG-INFO 2014-10-02 18:31:18.000000000 +0200 @@ -1,11 +1,11 @@ Metadata-Version: 1.1 Name: ioflo -Version: 0.9.39 +Version: 1.0.1 Summary: Flow Based Programming Automated Reasoning Engine and Automation Operation System Home-page: https://github.com/ioflo/ioflo Author: Samuel M. Smith Author-email: [email protected] -License: MIT +License: Apache 2.0 Download-URL: https://github.com/ioflo/ioflo/archive/master.zip Description: Enabling the Programmable World. http://ioflo.com Keywords: Automation Operating System Automated Reasoning Engine Flow Based Programming Intelligent Automation Pub/Sub ioflo FloScript -- To unsubscribe, e-mail: [email protected] For additional commands, e-mail: [email protected]
