2 * @defgroup pwglf_forward_trains_helper Analysis helpers
4 * @ingroup pwglf_forward_trains
10 * @author Christian Holm Christensen <cholm@master.hehi.nbi.dk>
11 * @date Tue Oct 16 19:00:17 2012
13 * @brief Base class for analysis helpers
15 * @ingroup pwglf_forward_trains_helper
18 #ifndef TRAIN_HELPER_C
19 #define TRAIN_HELPER_C
25 # include <TObjString.h>
29 # include <TObjArray.h>
31 # include <AliAnalysisManager.h>
42 * Helper class to set-up an analysis using a train
44 * @ingroup pwglf_forward_trains_helper
65 Helper(const Helper& o)
66 : fUrl(o.fUrl), fOptions(o.fOptions), fVerbose(o.fVerbose)
68 Helper& operator=(const Helper&) { return *this; }
70 * Create a helper object.
72 * @param verbose Verbosity
73 * @param url Url describing the job.
78 * local://<path>[#<treeName>][?[recursive[&]]]
81 * <path> can be a single ROOT file, a text file with one
82 * entry per file to add to the chain, or a directory containing the
83 * files. If <path> does not start with a '/' then it is
84 * interpreted as a relative path.
89 * alien:///<path>#<pattern>
97 * lite:///<path>[?[recursive[&]][workers=<n>]][#treeName]
98 * proof:///<path>[?[recursive[&]][workers=<n>]][#treeName]
102 * proof://<host>/<dsname>[?[workers=<n>[&]][dsname[=<outname>]]][#treeName]
105 * Note, if <host> is recognised as an Alice Analysis
106 * Facility, then the Grid handler (AliAnalysisAlien) is used unless
107 * the option <tt>plain</tt> was given.
109 * @return Newly allocated helper or null
111 static Helper* Create(const TUrl& url, Int_t verbose=0);
115 * @param name Name of library
116 * @param slave If true also load on slaves
118 * @return true on success, false otherwise
120 virtual Bool_t LoadLibrary(const TString& name,
121 Bool_t slave=true) = 0;
123 * Load a source file, and compile it
125 * @param name Name of the source file
126 * @param copy Copy rather than link
128 * @return true on success
130 virtual Bool_t LoadSource(const TString& name, bool copy=false)
132 if (!AuxFile(name, copy)) return false;
133 TString base(gSystem->BaseName(name));
134 gROOT->ProcessLine("gSystem->RedirectOutput(\"build.log\",\"a\");");
135 gROOT->LoadMacro(Form("%s++g", base.Data()));
136 gROOT->ProcessLine("gSystem->RedirectOutput(0);");
140 * Load auxillary file - not compiled or sourced. Just copied to
143 * @param name Extra file name
144 * @param copy Copy rather than link
146 * @return true on success
148 virtual Bool_t LoadAux(const TString& name, Bool_t copy=false)
150 if (!AuxFile(name, copy)) return false;
155 * Load needed ROOT libaries
157 virtual Bool_t LoadROOT()
159 if (gSystem->Load("libTree.so") < 0) return false;
160 if (gSystem->Load("libGeom.so") < 0) return false;
161 if (gSystem->Load("libVMC.so") < 0) return false;
162 if (gSystem->Load("libPhysics.so") < 0) return false;
163 if (gSystem->Load("libMinuit.so") < 0) return false;
167 * Set-up to load the AliROOT libraries
169 * @return true on success
171 virtual Bool_t LoadAliROOT()
173 if (!gSystem->Getenv("ALICE_ROOT")) {
174 Error("Helper::LoadAliROOT", "Local AliROOT not available");
177 if (!LoadLibrary("STEERBase")) return false;
178 if (!LoadLibrary("ESD")) return false;
179 if (!LoadLibrary("AOD")) return false;
180 if (!LoadLibrary("ANALYSIS")) return false;
181 if (!LoadLibrary("OADB")) return false;
182 if (!LoadLibrary("ANALYSISalice")) return false;
186 * Get the execution mode
188 * @return Execution mode set in set-up URL
190 virtual UShort_t Mode() const = 0;
192 * Get the mode string used for AliAnalysisManager::StartAnalysis
194 virtual const char* ModeString() const { return "unknown"; }
196 * Get the operation - this only makes sense for Grid jobs
198 * @return Operation type
200 virtual UShort_t Operation() const { return kFull; }
202 * Get the input data type
204 * @return Input data type
206 virtual Short_t InputType() const
208 UShort_t ret = DeduceType(fUrl.GetAnchor());
209 if (ret != kUser) return ret;
211 if (fOptions.Has("pattern")) ret = DeduceType(fOptions.Get("pattern"));
212 if (ret != kUser) return ret;
214 ret = DeduceType(fUrl.GetFile());
218 * Check if the MC option was set
220 * @return true if the MC option was given
222 virtual Bool_t IsMC() const { return fOptions.Has("mc"); }
224 * The file part of tehe output URL - overwritten by derived classes.
227 * @return File part of output URL
229 virtual TString OutputPath() const { return ""; }
231 * Get the location of the output data. Use ful to define second pass
237 virtual TString OutputLocation() const
239 AliAnalysisManager* mgr = AliAnalysisManager::GetAnalysisManager();
240 if (!mgr || !mgr->GetOutputEventHandler()) return "";
242 TString path(OutputPath());
244 path = gSystem->WorkingDirectory();
250 u.SetAnchor("aodTree");
251 TString opt(u.GetOptions());
252 opt.ReplaceAll("AliESDs", "AliAOD");
258 * Set-up done before task setup
260 * @return true on success
262 virtual Bool_t PreSetup() = 0;
264 * Set-up done after task setup
266 * @return true on success
268 virtual Bool_t PostSetup() = 0;
272 * @param nEvents Number of events to analyse
274 * @return The return value of AliAnalysisManager::StartAnalysis
276 virtual Long64_t Run(Long64_t nEvents=-1) = 0;
278 * Print information to standard output
282 virtual void Print(Option_t* ="") const
284 std::cout << "Url: " << fUrl.GetUrl() << std::endl;
285 fOptions.Show(std::cout);
288 * @return URL help string
290 virtual const Char_t* UrlHelp() const = 0;
292 * @return Short description string
294 virtual const char* Desc() const = 0;
300 const TUrl& Url() const { return fUrl; }
302 * Get the list of options
304 * @return Reference to list of options
306 const OptionList& Options() const { return fOptions; }
308 * Write auxillary ROOT (and possible shell) script for more
309 * (post-)processing e.g., terminate
312 virtual void AuxSave(const TString& /*escaped*/,
313 Bool_t /*asShellScript*/) {}
315 * Create an instance of a helper class
317 static Helper* CreateObject(const TString& cl,
321 if (verbose < 3) gSystem->RedirectOutput("/dev/null","w");
322 if (cl.Contains("proof", TString::kIgnoreCase) ||
323 cl.Contains("lite", TString::kIgnoreCase) ||
324 cl.Contains("aaf", TString::kIgnoreCase)) {
325 gSystem->Load("libProof");
326 gSystem->Load("libProofPlayer");
328 // (Always) recompile and with debug symbols
329 gROOT->LoadMacro(Form("%s.C+g",cl.Data()));
330 Long_t ptr = gROOT->ProcessLine(Form("new %s(\"%s\", %d);",
331 cl.Data(), url.GetUrl(), verbose));
332 if (verbose < 3) gSystem->RedirectOutput(0);
334 Warning("Helper::CreateObject", "Failed to instantize a %s", cl.Data());
337 Helper* h = reinterpret_cast<Helper*>(ptr);
341 * Show help on URL using the interpreter
343 * @param cl Helper class
345 static void ShowUrlHelp(const TString& cl)
347 Helper* h = CreateObject(cl, "", true);
350 std::cout << " " << h->UrlHelp() << std::endl;
353 * Show help on URL and options using the interpreter
355 * @param cl Helper class
357 static void ShowFullHelp(const TString& cl)
359 Helper* h = CreateObject(cl, "", true);
362 std::cout << h->Desc() << ":\n"
363 << "==============\n"
364 << " " << h->UrlHelp() << "\n\n"
365 << "Options: " << std::endl;
366 h->Options().Help(std::cout);
367 std::cout << std::endl;
373 * @param url Set-up URL
374 * @param verbose Verbosity level
376 Helper(const TUrl& url, Int_t verbose)
377 : fUrl(url), fOptions(), fVerbose(verbose)
379 fOptions.Add("mc", "Assume simulation input");
382 virtual Bool_t ParseOptions()
384 //std::cout << "Url options: \"" << fUrl.GetOptions() << "\"" << std::endl;
385 return fOptions.Parse(fUrl.GetOptions(), "&");
394 * Normalize a library name
400 const TString& MakeLibraryName(const TString& name)
402 static TString libName;
406 if (!libName.BeginsWith("lib")) {
407 // Check if the library corresponds to a compiled macro
408 if (!gSystem->AccessPathName(Form("%s_C.so", libName.Data())))
409 libName.Append("_C");
410 else if (!gSystem->AccessPathName(Form("../%s_C.so", libName.Data())))
411 libName = Form("../%s_C", libName.Data());
413 libName = Form("lib%s", libName.Data());
415 if (!libName.EndsWith(".so")) libName.Append(".so");
420 * Link an auxilary file to working directory
422 * @param name Name of the file
423 * @param copy Copy rather than link
425 * @return true on success
427 virtual Bool_t AuxFile(const TString& name, bool copy=false)
429 TString path(gSystem->ExpandPathName(name.Data()));
430 // If not absolute, prepend up-one
431 if (!path.BeginsWith("/")) path.Prepend("../");
432 if (gSystem->AccessPathName(path.Data())) {
433 // File not accessible
434 Warning("Helper::AuxFile", "File %s not accessible", path.Data());
437 TString base(gSystem->BaseName(path.Data()));
438 if (gSystem->AccessPathName(base.Data()) == 0) {
439 // File or link exists - remove it
440 if (gSystem->Unlink(base) != 0) {
441 Error("Helper::AuxFile", "Failed to remove old %s", base.Data());
446 TFile::Cp(path, base);
448 gSystem->Exec(Form("ln -s %s .", path.Data()));
452 * Deduce the top of job from a string
458 static UShort_t DeduceType(const TString& str)
460 if (str.IsNull()) return kUser;
461 if (str.Contains("aod", TString::kIgnoreCase)) return kAOD;
462 if (str.Contains("esd", TString::kIgnoreCase)) return kESD;
465 // --- Data members ------------------------------------------------
466 TUrl fUrl; // The URI
474 // ===================================================================
476 Helper::Create(const TUrl& url, Int_t verbose)
478 if (!url.IsValid()) {
479 Warning("Helper::Create", "URL is invalid");
483 TString prot(url.GetProtocol());
487 TString opts(tmp.GetOptions());
488 TString host(url.GetHost());
490 if (prot.EqualTo("alien")) {
491 // Create an AliEn helper
494 else if (prot.EqualTo("local")) {
495 // Create Lite helper
498 else if (prot.EqualTo("proof")) {
499 // Create a Proof helper
502 else if (host.BeginsWith("alice-caf")) {
504 cl = opts.Contains("plugin") ? "AAFPluginHelper" : "AAFHelper";
509 else if (prot.EqualTo("lite")) {
510 // Create a Proof helper
513 else if (prot.EqualTo("help")) {
514 // Special HELP protocol
515 if (host.Contains("options")) {
516 std::cout << "Possible URL types and options are:" << std::endl;
517 ShowFullHelp("LocalHelper");
518 ShowFullHelp("ProofHelper");
519 ShowFullHelp("LiteHelper");
520 ShowFullHelp("AAFHelper");
521 ShowFullHelp("AAFPluginHelper");
522 ShowFullHelp("GridHelper");
525 std::cout << "Possible URL types are:" << std::endl;
526 ShowUrlHelp("LocalHelper");
527 ShowUrlHelp("ProofHelper");
528 ShowUrlHelp("LiteHelper");
529 ShowUrlHelp("AAFHelper");
530 ShowUrlHelp("AAFPluginHelper");
531 ShowUrlHelp("GridHelper");
534 // --- Check if we got a scheme ------------------------------------
536 Error("Helper::Create", "Unknown scheme: %s", prot.Data());
540 // --- Use interpreter to make our object --------------------------
541 Helper* helper = CreateObject(cl, url, verbose);
543 Error("Helper::Create", "Failed to make object of class %s", cl.Data());
547 // --- Parse options -----------------------------------------------
548 if (!helper->ParseOptions()) {