CMS 3D CMS Logo

cmsLHEtoEOSManager.py
Go to the documentation of this file.
1 #! /usr/bin/env python
2 
3 from __future__ import print_function
4 print('Starting cmsLHEtoEOSManager.py')
5 
6 __version__ = "$Revision: 1.13 $"
7 
8 import os
9 import subprocess
10 import time
11 import re
12 
13 defaultEOSRootPath = '/eos/cms/store/lhe'
14 if "CMSEOS_LHE_ROOT_DIRECTORY" in os.environ:
15  defaultEOSRootPath = os.environ["CMSEOS_LHE_ROOT_DIRECTORY"]
16 defaultEOSLoadPath = 'root://eoscms.cern.ch/'
17 defaultEOSlistCommand = 'xrdfs '+defaultEOSLoadPath+' ls '
18 defaultEOSmkdirCommand = 'xrdfs '+defaultEOSLoadPath+' mkdir '
19 defaultEOSfeCommand = 'xrdfs '+defaultEOSLoadPath+' stat -q IsReadable '
20 defaultEOSchecksumCommand = 'xrdfs '+defaultEOSLoadPath+' query checksum '
21 defaultEOScpCommand = 'xrdcp -np '
22 
23 def findXrdDir(theDirRecord):
24 
25  elements = theDirRecord.split(' ')
26  if len(elements):
27  return elements[-1].rstrip('\n').split('/')[-1]
28  else:
29  return None
30 
31 def articleExist(artId):
32 
33  itExists = False
34  theCommand = defaultEOSlistCommand+' '+defaultEOSRootPath
35  dirList = subprocess.Popen(["/bin/sh","-c",theCommand], stdout=subprocess.PIPE, universal_newlines=True)
36  for line in dirList.stdout.readlines():
37  if findXrdDir(line) == str(artId):
38  itExists = True
39 
40  return itExists
41 
43 
44  artList = [0]
45 
46  theCommand = defaultEOSlistCommand+' '+defaultEOSRootPath
47  dirList = subprocess.Popen(["/bin/sh","-c",theCommand], stdout=subprocess.PIPE, universal_newlines=True)
48  for line in dirList.stdout.readlines():
49  try:
50  if line.rstrip('\n') != '':
51  artList.append(int(findXrdDir(line)))
52  except:
53  break
54 
55  return max(artList)
56 
57 
58 def fileUpload(uploadPath,lheList, checkSumList, reallyDoIt, force=False):
59 
60  inUploadScript = ''
61  index = 0
62  for f in lheList:
63  realFileName = f.split('/')[-1]
64  # Check the file existence
65  newFileName = uploadPath+'/'+str(realFileName)
66  addFile = True
67  additionalOption = ''
68  theCommand = defaultEOSfeCommand+' '+newFileName
69  exeFullList = subprocess.Popen(["/bin/sh","-c",theCommand], stdout=subprocess.PIPE, universal_newlines=True)
70  result = exeFullList.stdout.readlines()
71  if [line for line in result if ("flags:" in line.lower()) and ("isreadable" in line.lower())] and (not force):
72  addFile = False
73  print('File '+newFileName+' already exists: do you want to overwrite? [y/n]')
74  reply = raw_input()
75  if reply == 'y' or reply == 'Y':
76  addFile = True
77  additionalOption = ' -f '
78  print('')
79  print('Overwriting file '+newFileName+'\n')
80  # add the file
81  if addFile:
82 # print 'Adding file '+str(f)+'\n'
83  inUploadScript = defaultEOScpCommand + additionalOption + ' ' + str(f) + ' ' + defaultEOSLoadPath+uploadPath + '/' + str(realFileName)
84  print('Uploading file %s...' % str(f))
85  if reallyDoIt:
86  exeRealUpload = subprocess.Popen(["/bin/sh","-c",inUploadScript])
87  exeRealUpload.communicate()
88  eosCheckSumCommand = defaultEOSchecksumCommand + uploadPath + '/' + str(realFileName) + ' | awk \'{print $2}\' | cut -d= -f2'
89  exeEosCheckSum = subprocess.Popen(eosCheckSumCommand ,shell=True, stdout=subprocess.PIPE, universal_newlines=True)
90  EosCheckSum = exeEosCheckSum.stdout.read()
91  assert exeEosCheckSum.wait() == 0
92  # print 'checksum: eos = ' + EosCheckSum + 'orig file = ' + checkSumList[index] + '\n'
93  if checkSumList[index] not in EosCheckSum:
94  print('WARNING! The checksum for file ' + str(realFileName) + ' in EOS\n')
95  print(EosCheckSum + '\n')
96  print('does not match the checksum of the original one\n')
97  print(checkSumList[index] + '\n')
98  print('please try to re-upload file ' + str(realFileName) + ' to EOS.\n')
99  else:
100  print('Checksum OK for file ' + str(realFileName))
101  index = index+1
102 
103 # launch the upload shell script
104 
105 # print '\n Launching upload script \n'+inUploadScript+'\n at '+time.asctime(time.localtime(time.time()))+' ...\n'
106 # if reallyDoIt:
107 # exeRealUpload = subprocess.Popen(["/bin/sh","-c",inUploadScript])
108 # exeRealUpload.communicate()
109  print('\n Upload ended at '+time.asctime(time.localtime(time.time())))
110 
111 
112 
113 if __name__ == '__main__':
114 
115  import optparse
116 
117  # Here we define an option parser to handle commandline options..
118  usage='cmsLHEtoEOSManager.py <options>'
119  parser = optparse.OptionParser(usage)
120  parser.add_option('-f', '--file',
121  help='LHE local file list to be uploaded, separated by ","' ,
122  default='',
123  dest='fileList')
124 
125  parser.add_option('-F', '--files-from', metavar = 'FILE',
126  help='File containing the list of LHE local files be uploaded, one file per line')
127 
128  parser.add_option('-n', '--new',
129  help='Create a new article' ,
130  action='store_true',
131  default=False,
132  dest='newId')
133 
134  parser.add_option('-u', '--update',
135  help='Update the article <Id>' ,
136  default=0,
137  type=int,
138  dest='artIdUp')
139 
140  parser.add_option('-l', '--list',
141  help='List the files in article <Id>' ,
142  default=0,
143  type=int,
144  dest='artIdLi')
145 
146  parser.add_option('-d', '--dry-run',
147  help='dry run, it does nothing, but you can see what it would do',
148  action='store_true',
149  default=False,
150  dest='dryRun')
151 
152  parser.add_option('-c', '--compress',
153  help='compress the local .lhe file with xz before upload',
154  action='store_true',
155  default=False,
156  dest='compress')
157 
158  parser.add_option('--force',
159  help='Force update if file already exists.',
160  action='store_true',
161  default=False,
162  dest='force')
163 
164  (options,args) = parser.parse_args()
165 
166  # print banner
167 
168  print('')
169  print('cmsLHEtoEOSmanager '+__version__[1:-1])
170  print('')
171  print('Running on ',time.asctime(time.localtime(time.time())))
172  print('')
173 
174  reallyDoIt = not options.dryRun
175 
176  # Now some fault control. If an error is found we raise an exception
177  if not options.newId and options.artIdUp==0 and options.artIdLi==0:
178  raise Exception('Please specify the action to be taken, either "-n", "-u" or "-l"!')
179 
180  if options.fileList == '' and not options.files_from and (options.newId or options.artIdUp!=0):
181  raise Exception('Please provide the input file list!')
182 
183  if (options.newId and (options.artIdUp != 0 or options.artIdLi != 0)) or (options.artIdUp != 0 and options.artIdLi != 0):
184  raise Exception('Options "-n", "-u" and "-l" are mutually exclusive, please choose only one!')
185 
186  if options.newId:
187  print('Action: create new article\n')
188  elif options.artIdUp != 0:
189  print('Action: update article '+str(options.artIdUp)+'\n')
190  elif options.artIdLi != 0:
191  print('Action: list content of article '+str(options.artIdLi)+'\n')
192 
193  if options.artIdLi==0:
194  theList = []
195  if len(options.fileList) > 0:
196  theList=(options.fileList.split(','))
197 
198  if options.files_from:
199  try:
200  f = open(options.files_from)
201  except IOError:
202  raise Exception('Cannot open the file list, \'%s\'' % options.files_from)
203  for l in f:
204  l = l.strip()
205  if len(l) == 0 or l[0] == '#':
206  continue
207  theList.append(l)
208 
209  theCompressedFilesList = []
210  theCheckSumList = []
211  for f in theList:
212  # Check the file name extension
213  print(f)
214  if not ( f.lower().endswith(".lhe") or f.lower().endswith(".lhe.xz") ):
215  raise Exception('Input file name must have the "lhe" or "lhe.xz" final extension!')
216  if( f.lower().endswith(".lhe.xz") ):
217  print("Important! Input file "+f+" is already zipped: please make sure you verified its integrity with xmllint before zipping it. You can do it with:\n")
218  print("xmllint file.lhe\n")
219  print("Otherwise it is best to pass the unzipped file to this script and let it check its integrity and compress the file with the --compress option\n")
220  # Check the local file existence
221  if not os.path.exists(f):
222  raise Exception('Input file '+f+' does not exists')
223  if( f.lower().endswith(".lhe") ):
224  theCheckIntegrityCommand = 'xmllint -noout '+f
225  exeCheckIntegrity = subprocess.Popen(["/bin/sh","-c", theCheckIntegrityCommand])
226  intCode = exeCheckIntegrity.wait()
227  if(intCode != 0):
228  raise Exception('Input file '+f+ ' is corrupted')
229  if reallyDoIt and options.compress:
230  print("Compressing file",f)
231  if( f.lower().endswith(".lhe.xz") ):
232  raise Exception('Input file '+f+' is already compressed! This is inconsistent with the --compress option!')
233  theCompressionCommand = 'xz '+f
234  exeCompression = subprocess.Popen(["/bin/sh","-c",theCompressionCommand])
235  exeCompression.communicate()
236  theCompressedFilesList.append(f+'.xz')
237  if reallyDoIt and options.compress:
238  theList = theCompressedFilesList
239  for f in theList:
240  try:
241  exeCheckSum = subprocess.Popen(["/afs/cern.ch/cms/caf/bin/cms_adler32",f], stdout=subprocess.PIPE, universal_newlines=True)
242  getCheckSum = subprocess.Popen(["awk", "{print $1}"], stdin=exeCheckSum.stdout, stdout=subprocess.PIPE, universal_newlines=True)
243  exeCheckSum.stdout.close()
244  output,err = getCheckSum.communicate()
245  theCheckSumList.append(output.strip())
246  except:
247  theCheckSumList.append("missing-adler32")
248 
249  newArt = 0
250  uploadPath = ''
251 
252 # new article
253 
254  if options.newId:
255  oldArt = lastArticle()
256  newArt = oldArt+1
257  print('Creating new article with identifier '+str(newArt)+' ...\n')
258  uploadPath = defaultEOSRootPath+'/'+str(newArt)
259  theCommand = defaultEOSmkdirCommand+' '+uploadPath
260  if reallyDoIt:
261  exeUpload = subprocess.Popen(["/bin/sh","-c",theCommand])
262  exeUpload.communicate()
263 
264 # update article
265 
266  elif options.artIdUp != 0:
267  newArt = options.artIdUp
268  if articleExist(newArt):
269  uploadPath = defaultEOSRootPath+'/'+str(newArt)
270  else:
271  raise Exception('Article '+str(newArt)+' to be updated does not exist!')
272 
273 # list article
274 
275  elif options.artIdLi !=0:
276  listPath = defaultEOSRootPath+'/'+str(options.artIdLi)
277  theCommand = defaultEOSlistCommand+' '+listPath
278  exeList = subprocess.Popen(["/bin/sh","-c",theCommand], stdout=subprocess.PIPE, universal_newlines=True)
279  for line in exeList.stdout.readlines():
280  if findXrdDir(line) != None:
281  print(findXrdDir(line))
282 
283 
284  if newArt > 0:
285  fileUpload(uploadPath,theList, theCheckSumList, reallyDoIt, options.force)
286  listPath = defaultEOSRootPath+'/'+str(newArt)
287  print('')
288  print('Listing the '+str(newArt)+' article content after upload:')
289  theCommand = defaultEOSlistCommand+' '+listPath
290  if reallyDoIt:
291  exeFullList = subprocess.Popen(["/bin/sh","-c",theCommand])
292  exeFullList.communicate()
293  else:
294  print('Dry run, nothing was done')
295 
cmsLHEtoEOSManager.lastArticle
def lastArticle()
Definition: cmsLHEtoEOSManager.py:42
if
if(0==first)
Definition: CAHitNtupletGeneratorKernelsImpl.h:48
submitPVValidationJobs.split
def split(sequence, size)
Definition: submitPVValidationJobs.py:352
str
#define str(s)
Definition: TestProcessor.cc:52
cmsLHEtoEOSManager.findXrdDir
def findXrdDir(theDirRecord)
Definition: cmsLHEtoEOSManager.py:23
cmsLHEtoEOSManager.articleExist
def articleExist(artId)
Definition: cmsLHEtoEOSManager.py:31
print
void print(TMatrixD &m, const char *label=nullptr, bool mathematicaFormat=false)
Definition: Utilities.cc:46
SiStripPI::max
Definition: SiStripPayloadInspectorHelper.h:169
Exception
createfilelist.int
int
Definition: createfilelist.py:10
cmsLHEtoEOSManager.fileUpload
def fileUpload(uploadPath, lheList, checkSumList, reallyDoIt, force=False)
Definition: cmsLHEtoEOSManager.py:58