Index: /fact/tools/pyscripts/new_pyfact/pyfact.py
===================================================================
--- /fact/tools/pyscripts/new_pyfact/pyfact.py	(revision 17977)
+++ /fact/tools/pyscripts/new_pyfact/pyfact.py	(revision 17978)
@@ -8,4 +8,5 @@
 import numpy as np
 import ROOT
+ROOT.gROOT.SetBatch(True)
 
 ########## BUILDING OF THE SHARED OBJECT FILES ###############################
@@ -65,4 +66,92 @@
 del path
 
+raw_base = '/fact/raw'
+aux_base = '/fact/aux'
+
+
+def stub_to_auxfile(s, s2=None, basep=aux_base, basen="*"):
+    """ FIXME :-) 
+        It's not yet clear how to generate aux file names from stubs, or iterables
+    """
+    if s2 is not None:
+        s = "{0}_{1:03d}".format(s,s2)
+    y = s[0:4]
+    m = s[4:6]
+    d = s[6:8]
+    date = s[0:8]
+    r = s[9:12]
+    return os.path.join(basep,y,m,d,date+'.'+basen+'.fits')
+
+
+def make_path(s):
+    """ make path to fits file
+        
+        s : string or iterable
+        
+        Fits files in pyfact do not need to be specified by full paths
+        A so called stub path is sufficient. A valid stub path looks like:
+        yyyymmdd_rrr
+        or in case of a drs calibration file like
+        yyyymmdd_rrr.drs
+
+        In addition a file can be specified by a 2-element integer iterable,
+        e.g. a list or a tuple, whose first element is the integer denoting the 
+        'night' : yyyymmdd
+        the 2nd integer is the 'run' : rrr
+        so valid specifiers are also:
+        (yyyymmdd, rrr) or [yyyymmdd, rrr]
+
+        the pyfact.Fits class can handle .fits, .fits.gz, and .fits.fz files.
+        stubs dont's specify which one should be used, so we need to check 
+        which one exists, if more than one file exists fitting to the stub, 
+        the order of precendence is:
+            * .fits    -- since access should be pretty fast
+            * .fits.fz -- newer format should be mostly the case
+            * .fits.gz -- still possible
+    """
+    import re
+    import os
+    if not isinstance(s, (str, unicode)):
+        # s is (hopefully) some kind of iterable, so we read out two integers
+        night = int(s[0])
+        run = int(s[1])
+        _s = "{0:08d}_{1:03d}".format(night,run)
+    else:
+        _s = s
+
+    # so now s is some kind of string
+    # maybe it is already a path:
+    if os.path.isabs( _s ):
+        # s is already an absolute path. 
+        # maybe the file is not there, but we don't care about that
+        return _s
+
+    # it was not an absolute path, maybe it's a relative path, let's check if 
+    # it points to a file.
+    elif os.path.exists( _s ):
+        # s is certainly a path, it even points to a file :-)
+        return os.path.abspath(_s)
+
+    # okay ... s was not a path, so let's generate a nice absolute path 
+    # from the stub, in case it is a stub ..
+    elif re.match('\d{8}_\d{3}', _s):
+        # s is a stub, so we can make a full path from it
+        y = _s[0:4]
+        m = _s[4:6]
+        d = _s[6:8]
+        r = _s[9:12]
+        start = os.path.join(raw_base,y,m,d,_s[:12]+'.fits')
+        candidates = [start, start+'.fz', start+'.gz']
+        for c in candidates:
+            if os.path.exists(c):
+                return c
+        # if we reached this point, s was a stub, but we were not 
+        # able to find a file on the file system... 
+        # let's return our best guess, the '.fz' file path 
+        # the Fits.__init__() will complain, if it can't find the file.
+        return candidates[1]
+    else:
+        raise IOError("{0} can't be used for path generation".format(s))
+
 class Fits( object ):
     """ General FITS file access
@@ -74,6 +163,11 @@
     __module__ = 'pyfact'
     def __init__(self, path):
-        """
-        """
+        """ Open fits file, parse header and setup table colums
+
+        path : string : path to the fits file (.fits, .fits.gz, .zfits)
+        """
+        path = make_path(path)
+        self._path = path
+        self._current_row = None
         if not os.path.exists(path):
             raise IOError(path+' was not found')
@@ -81,4 +175,16 @@
         self._make_header()
         self._setup_columns()
+
+    def __repr__(self):
+        return '{s.__class__.__name__}(path="{s._path}")'.format(s=self)
+    
+    def __str__(self):
+        s = """Fits object: 
+        path = {s._path}
+        row = {s._current_row}
+        self.cols.keys = {col_names}
+        """.format(s=self, col_names=self.cols.keys())
+        return s
+
 
     def __len__(self):
@@ -121,9 +227,16 @@
         """
         if row is None:
+            if self._current_row is None:
+                self._current_row = 0
+            else:
+                self._current_row += 1
             if self.f.GetNextRow() == False:
+                self._current_row = None
                 raise StopIteration
         else:
             row = int(row)
+            self._current_row = row
             if self.f.GetRow(row) == False:
+                self._current_row = None
                 raise StopIteration
         return self
@@ -162,6 +275,4 @@
             for key in self._cols:
                 self.cols[key][i,:] = self._cols[key]
-
-
 
 
