source: TI05-delivery/ows_framework/trunk/ows_server/ows_server/models/Utilities.py @ 2646

Subversion URL: http://proj.badc.rl.ac.uk/svn/ndg/TI05-delivery/ows_framework/trunk/ows_server/ows_server/models/Utilities.py@2646
Revision 2646, 6.1 KB checked in by lawrence, 13 years ago (diff)

Interim check in for citation trackback support and
metadata correction from logged in ndg users.

Line 
1from collections import deque # python 2.4
2try: #python 2.5
3    from xml.etree import ElementTree as ET
4except ImportError:
5    try:
6        # if you've installed it yourself it comes this way
7        import ElementTree as ET
8    except ImportError:
9        # if you've egged it this is the way it comes
10        from elementtree import ElementTree as ET
11from ETxmlView import *
12import ConfigParser
13import os
14import re
15import urllib
16import logging
17
18
19class myConfig:
20   
21   ''' Handle missing sections and variables in a config file a bit gracefully. Also
22   instantiates a logger if necessary '''
23   
24   def __init__(self,configfile,logName='NDGLOG'):
25       self.config=ConfigParser.ConfigParser()
26       if not os.path.exists(configfile): 
27           
28           raise ValueError("Config file [%s] doesn't exist in [%s]"%(configfile,os.getcwd()))
29       self.config.read(configfile)
30       logfile=self.get('logging','debugLog',None)
31       # move to a wsgi logger ... safer I think in a multithread environment
32       #
33       #self.logfile=None #deprecated
34       self.logger=None
35       self.logfile=logfile
36       #
37       if logfile is not None:
38           #logger=logging.getLogger(logName)
39           #handler=logging.FileHandler(logfile)
40           #formatter=logging.Formatter('%(asctime)s %(levelname)s %(message)s')
41           #handler.setFormatter(formatter)
42           #logger.addHandler(handler)
43           #logger.setLevel(logging.INFO)
44           #self.logger=logger
45           self.logger=None
46       
47   def get(self,section,key,default=None):
48       ''' Return a config file value for key frm section '''
49       try:
50           return self.config.get(section,key)
51       except:
52           return default
53       
54   def log(self,string):
55       ''' Log some debug information '''
56       if self.logger is None: return
57       if string is not None:
58          self.logger.info(string)
59       else:
60          self.logger.info('empty log entry')
61         
62   def getLog(self):
63       return self.logger
64
65class RingBuffer(deque):
66    #deque is a python 2.4 class!
67    #credit http://www.onlamp.com/pub/a/python/excerpt/pythonckbk_chap1/index1.html
68    def __init__(self, size_max):
69        deque.__init__(self)
70        self.size_max = size_max
71    def append(self, datum):
72        deque.append(self, datum)
73        if len(self) > self.size_max:
74            self.popleft( )
75    def tolist(self):
76        return list(self)
77
78def wrapGetText(element,xpathExpression,multiple=0):
79        ''' Wraps a call to ET to get a text object in an error handler '''
80        def none2txt(i):
81            if i is None: return ''
82            return i
83        if element is None:
84            if multiple:
85                 return ['',]
86            else: return ''
87        if multiple:
88                r=element.findall(xpathExpression)
89        else:
90                r=[element.find(xpathExpression),]
91        try:
92                rr=[i.text for i in r]
93        except:
94                rr=['',]
95        rr=map(none2txt,rr) 
96        if multiple: 
97                return rr
98        else: return rr[0] 
99
100def getURLdict(cgiFieldStorage):
101    ''' takes a cgi field storage object and converts it to a dictionary '''
102    result={}
103    for item in cgiFieldStorage:
104            result[item]=cgiFieldStorage[item].value
105    return result
106##
107### convert the followign two methods into one class that can handle
108## xml directly too if necessary
109##
110def DIFid2NDGid(string):
111    ''' takes a dif thing parses it and produces an ET ndg element id ...
112    and use this in dif ... '''
113    s=string.split(':')
114    try:
115        r='''<DIFid><schemeIdentifier>%s</schemeIdentifier>
116         <repositoryIdentifier>%s</repositoryIdentifier>
117         <localIdentifier>%s</localIdentifier></DIFid>'''%(s[1],s[0],s[2])
118        return ET.fromstring(r)
119    except:
120        r='''<DIFid><schemeIdentifier>DIF</schemeIdentifier>
121        <repositoryIdentifier>Unknown</repositoryIdentifier>
122        <localIdentifier>%s</localIdentifier></DIFid>'''%string
123        return ET.fromstring(r)
124
125def EnumerateString(string):
126    ''' Takes a string, and if it's got a number on the end, increments it,
127    otherwise adds a number on the end, used to differentiate strings which
128    would otherwise be identical '''
129    def addNum(matchObj):
130        s=matchObj.group()
131        return str(int(s)+1)
132    r=re.sub('\d+$',addNum,string)
133    if r==string: r=r+'1'
134    return r
135
136def dateParse(string,instruction):
137    ''' Simple date manipulations on a string, if it is understood ...
138       if instruction = YYYY, return the year '''
139    s=string.split('-')
140    if instruction=='YYYY':
141        if len(s)==3: # expecting year,mon,day or day,mon,year ...
142            if int(s[0])>int(s[2]): 
143                return s[0]
144            else:
145                return s[2]
146        else:
147            return string # unknown format as yet ...
148    else:
149        return 'unknown instruction to dateParse %s'%instruction
150
151def idget(xml,dataType='DIF'):
152    ''' Given an xml document (string), parse it using ElementTree and
153    find the identifier within it. Supports dataTypes of 'DIF' ...
154    (actually only DIF for now).
155    '''
156    et=loadET(xml)
157    helper=nsdumb(et)
158    if dataType=='DIF':
159        return helper.getText(et,'Entry_ID')
160    else:
161        raise TypeError,'idget does not support datatype [%s]'%dataType
162   
163
164
165       
166import unittest
167
168class TestCase(unittest.TestCase):
169    """ Tests as required """
170
171    configFile='examples/example.config'
172    difFile='examples/neodc.eg1.dif'
173   
174    def setUp(self):
175        # If pkg_resources is available assume the module is eggified and
176        # get a stream to the input data from the egg.
177        #try:
178        #    import pkg_resources
179        #    f = pkg_resources.resource_stream(__name__, self.configFile)
180        #except ImportError:
181            # Else take the input file from __file__
182            #import os
183        self.config=myConfig(self.configFile)
184        f=file(self.difFile,'r')
185        self.difxml=f.read()
186            #f=file(os.path.join(os.path.basepath(__file__), self.configFile))
187
188        #self.config=myConfig(f)
189
190    def testConfig(self):
191        print 'Discovery Icon [%s]'%self.config.get('DISCOVERY','icon')
192       
193    def testidget(self):
194        self.assertEqual(idget(self.difxml),'NOCSDAT192')
195
196
197if __name__=="__main__":
198    unittest.main()
199
200
201
Note: See TracBrowser for help on using the repository browser.