8 #include "GaudiKernel/Bootstrap.h"
9 #include "GaudiKernel/IOpaqueAddress.h"
10 #include "GaudiKernel/GenericAddress.h"
11 #include "GaudiKernel/IAddressCreator.h"
12 #include "GaudiKernel/ISvcLocator.h"
15 #include "CoolKernel/IObject.h"
16 #include "CoolKernel/IObjectIterator.h"
17 #include "CoolKernel/IRecord.h"
18 #include "CoolKernel/IRecordIterator.h"
19 #include "CoralBase/AttributeList.h"
20 #include "CoralBase/AttributeListSpecification.h"
21 #include "CoralBase/Attribute.h"
22 #include "CoralBase/AttributeSpecification.h"
23 #include "CoralBase/Blob.h"
24 #include "TStopwatch.h"
59 #include "CrestApi/CrestApiFs.h"
65 using namespace Crest;
68 const std::string fileSuffix{
".json"};
76 const bool checklock,
const bool outputToFile,
77 const std::string &
source,
const bool crestToFile,
78 const std::string &
crestServer,
const std::string & crestTag,
79 const bool crestCoolToFile):
82 p_metaDataTool(metadatatool),
84 m_checklock(checklock),
86 m_chansel(
cool::ChannelSelection::
all()),
87 m_outputToFile{outputToFile},
88 m_crestToFile{crestToFile},
89 m_crestCoolToFile{crestCoolToFile},
98 m_foldername=folderprop.folderName();
102 m_key=folderprop.key();
103 m_jokey=folderprop.hasKey();
105 m_jotag=folderprop.tag();
107 m_eventstore=folderprop.eventStoreName();
109 m_cachepar = folderprop.cache();
111 m_notagoverride=folderprop.noTagOverride();
112 if (m_source ==
"CREST")
114 if (m_notagoverride)
ATH_MSG_INFO(
"Inputfile tag override disabled for " << m_foldername );
119 std::string chanspec;
120 if (folderprop.getKey(
"channelSelection",
"",chanspec) && !chanspec.empty()) {
121 m_chanrange=IOVDbNamespace::parseChannelSpec<cool::ChannelId>(chanspec);
126 for(
const auto &
i:m_chanrange){
129 m_chansel = cool::ChannelSelection(
i.first,
i.second);
131 m_chansel.addRange(
i.first,
i.second);
134 }
catch (cool::Exception&
e) {
135 ATH_MSG_ERROR(
"defining channel range (must be given in ascending order)");
139 if (folderprop.overridesIov(
msg)){
140 m_iovoverridden=
true;
141 m_iovoverride=folderprop.iovOverrideValue(
msg);
143 ATH_MSG_INFO(
"Override timestamp to " << m_iovoverride <<
" for folder " << m_foldername );
146 ATH_MSG_INFO(
"Override run/LB number to [" <<
run <<
":" <<
lumi <<
"] for folder " << m_foldername );
150 m_fromMetaDataOnly=folderprop.onlyReadMetadata();
151 if (m_fromMetaDataOnly) {
152 ATH_MSG_INFO(
"Read from meta data only for folder " << m_foldername );
155 m_extensible=folderprop.extensible();
194 const unsigned int time) {
221 return (
m_timestamp ? reftime.timestamp() : reftime.re_time());
227 const unsigned int cacheDiv,
229 const bool ignoreMissChan) {
236 TStopwatch cachetimer;
239 bool vectorPayload{};
240 std::string strCrestNodeDesc;
249 vectorPayload = (strCrestNodeDesc.find(
"CondAttrListVec") != std::string::npos);
268 if (cacheq>0) changedCacheLo=vkey - vkey % cacheq;
274 changedCacheLo=vkey & (0x7FFFFFFFLL << 32);
280 if (changedCacheHi>cool::ValidityKeyMax) changedCacheHi=cool::ValidityKeyMax;
311 bool retrievedone=
false;
320 unsigned int attempts=0;
322 ATH_MSG_DEBUG(
"loadCache: Expecting to see " << nChannelsExpected <<
" channels" );
324 while (attempts<2 && !retrievedone) {
331 if (not
m_conn->
valid())
throw std::runtime_error(
"COOL database pointer invalidated");
347 while (itr->hasNext()) {
377 while (itr->goToNext()) {
378 const cool::IObject&
ref=itr->currentRef();
386 cool::IRecordIterator& pitr=
ref.payloadIterator();
387 const cool::IRecordVectorPtr&
pvec=pitr.fetchAllAsVector();
388 for (cool::IRecordVector::const_iterator vitr=
pvec->begin();vitr!=
pvec->end();++vitr) {
420 ATH_MSG_WARNING(
"COOL retrieve attempt " << attempts <<
" failed: " <<
e.what() );
429 std::vector<BasicFolder> crestObjs;
437 unsigned int iadd = 0;
440 ATH_MSG_DEBUG(
"loadCache: Expecting to see " << nChannelsExpected <<
" channels" );
443 const auto & channelNumbers=basicFolder.channelIds();
444 ATH_MSG_DEBUG(
"ChannelIds is " << channelNumbers.size() <<
" long" );
445 for (
const auto &
chan: channelNumbers){
446 addIOVtoCache(basicFolder.iov().first, basicFolder.iov().second);
448 if (basicFolder.isVectorPayload()) {
449 const auto & vPayload = basicFolder.getVectorPayload(
chan);
451 for (
const auto & attList:vPayload){
461 auto const & attList = basicFolder.getPayload(
chan);
480 "," <<
until <<
"]" );
486 const auto missing=std::pair<unsigned int, unsigned int>(nChannelsExpected-nChannelsLo, nChannelsExpected-nChannelsHi);
487 ATH_MSG_DEBUG(
"Cache retrieve missing " << missing.first <<
" lower and " << missing.second <<
" upper channels" );
493 ATH_MSG_DEBUG(
"Lower cache limit extended from " << cacheStart <<
" to " <<
span.first );
497 ATH_MSG_DEBUG(
"Upper cache limit extended from " << cacheStop <<
" tp " <<
span.second );
501 const float timeinc=cachetimer.RealTime();
504 m_iovs.
size() <<
" objects stored in" << std::fixed <<
505 std::setw(8) << std::setprecision(2) << timeinc <<
" s" );
511 const cool::IDatabasePtr& ,
520 unsigned int attempts = 0;
521 bool retrievedone =
false;
524 ATH_MSG_DEBUG(
"loadCacheIfDbChanged: Expecting to see " << nChannelsExpected <<
" channels" );
526 while (attempts<2 && !retrievedone) {
555 const cool::IObject&
ref=itr->currentRef();
565 ATH_MSG_WARNING(
"COOL retrieve attempt " << attempts <<
" failed: " <<
e.what() );
579 ATH_MSG_ERROR(
"IOVDbFolder::specialCacheUpdate - setRange failed for folder "
605 ATH_MSG_ERROR(
"IOVDbFolder::specialCacheUpdate - setRange failed for folder "
635 IAddressCreator* persSvc,
636 const unsigned int poolSvcContext,
637 std::unique_ptr<IOpaqueAddress>&
address,
638 IOVRange&
range,
bool& poolPayloadReq) {
642 std::string strAddress;
646 cool::ValidityKey naystart=0;
647 cool::ValidityKey naystop=cool::ValidityKeyMax;
651 if (not readFromMetaData.
isValid()){
681 if (thisIov.first<=reftime && reftime<thisIov.second) {
687 strAddress=
"POOLContainer_AthenaAttributeList][CLID=x";
705 ATH_MSG_ERROR(
"Writing of CoraCool folders to file metadata not implemented");
712 }
else if (thisIov.second<=reftime && thisIov.second>naystart) {
713 naystart=thisIov.second;
714 }
else if (thisIov.first>reftime && thisIov.first<naystop) {
715 naystop=thisIov.first;
722 std::vector<std::string>::const_iterator nitr=
m_channames.begin();
723 for (std::vector<cool::ChannelId>::const_iterator chitr=
m_channums.begin();
725 attrListColl->
add(*chitr,*nitr);
730 strAddress=
"POOLContainer_CondAttrListCollection][CLID=x";
733 strAddress=
"POOLContainer_CondAttrListVec][CLID=x";
737 ATH_MSG_ERROR(
"COOL object not found in single-channel retrieve, folder "
742 " valid objects found for single-channel retrieve, folder " <<
748 <<
" at IOV " << reftime <<
" channels " << nobj <<
" has range "
753 IOVTime rstart=
range.start();
754 IOVTime rstop=
range.stop();
755 if (tnaystart > rstart || rstop > tnaystop) {
757 <<
" from [" << rstart <<
":" << rstop <<
"] to ["
758 << tnaystart <<
":" << tnaystop <<
"]" );
759 if (tnaystart > rstart) rstart=tnaystart;
760 if (tnaystop < rstop) rstop=tnaystop;
761 range=IOVRange(rstart,rstop);
779 IOpaqueAddress* addrp =
nullptr;
780 if (StatusCode::SUCCESS!=persSvc->createAddress(0,0,strAddress,addrp)) {
781 ATH_MSG_ERROR(
"Could not get IOpaqueAddress from string address "<< strAddress );
784 address = std::unique_ptr<IOpaqueAddress>(addrp);
785 GenericAddress* gAddr=
dynamic_cast<GenericAddress*
>(
address.get());
787 ATH_MSG_ERROR(
"Could not cast IOpaqueAddress to GenericAddress");
792 auto addr = std::make_unique<CondAttrListCollAddress>(*gAddr);
793 addr->setAttrListColl(attrListColl);
796 auto addr = std::make_unique<CondAttrListCollAddress>(gAddr->svcType(),
797 gAddr->clID(),gAddr->par()[0],gAddr->par()[1],
798 poolSvcContext,gAddr->ipar()[1]);
800 addr->setAttrListColl(attrListColl);
805 auto addr = std::make_unique<AthenaAttrListAddress>(*gAddr);
806 addr->setAttrList(attrList);
809 auto addr = std::make_unique<CondAttrListVecAddress>(*gAddr);
810 addr->setAttrListVec(attrListVec);
824 << std::setprecision(2) <<
m_readtime <<
" ))s" );
837 if (
auto newkey=parsedDescription.
key(); not newkey.empty() and not
m_jokey) {
848 if (
auto newAddrHeader = parsedDescription.
addressHeader();not newAddrHeader.empty()){
873 std::unique_ptr<SG::TransientAddress>
875 auto tad = std::make_unique<SG::TransientAddress>(
m_clid,
m_key);
877 for (
const auto & linkname:symlinks){
878 if (not linkname.empty()) {
880 if (StatusCode::SUCCESS==
p_clidSvc->getIDOfTypeName(linkname,sclid)) {
881 tad->setTransientID(sclid);
884 ATH_MSG_ERROR(
"Could not get clid for symlink: "<< linkname );
892 std::unique_ptr<SG::TransientAddress>
939 for (
int i = 0;
i < n_size;
i++) {
944 chan_list.push_back(elem);
952 tag_meta[
"description"] =
"";
953 tag_meta[
"chansize"] = n_size;
954 tag_meta[
"colsize"] = colsize;
957 tagInfo[
"channel_list"] = chan_list;
961 tag_meta[
"tagInfo"] = tagInfo.dump();
963 std::string crest_work_dir=std::filesystem::current_path();
964 crest_work_dir +=
"/crest_data";
965 bool crest_rewrite =
true;
967 Crest::CrestApiFs crestFSClient = Crest::CrestApiFs(crest_rewrite, crest_work_dir);
970 TagMetaDto dto = TagMetaDto();
971 dto = dto.fromJson(tag_meta);
972 crestFSClient.createTagMeta(dto);
999 const auto & linknameVector = folderpar.
symLinks();
1011 if (timeIs_nsOfEpoch){
1012 long long int clen=600;
1021 ATH_MSG_DEBUG(
"Cache length set to " << clen <<
" seconds" );
1054 if (
tag==
"HEAD")
return true;
1057 ATH_MSG_ERROR(
"No IOVDbSvc.GlobalTag specified on job options or input file" );
1070 const std::vector<std::string>&
taglist=
fptr->listTags();
1077 std::string restag=
fptr->resolveTag(
tag);
1082 }
catch (cool::Exception&
e) {
1091 if (not tagLock.has_value()){
1095 if (not tagLock.value()){
1096 ATH_MSG_ERROR(
"Tag " <<
tag <<
" is not locked and IOVDbSvc.CheckLock is set" );
1107 return (not
tag.empty());
1114 const IOVRange&
range) {
1119 tmpColl.
add(0xFFFF,atrlist);
1140 m_cachespec=
new coral::AttributeListSpecification;
1141 for (
const auto & attribute:atrlist){
1142 const coral::AttributeSpecification& aspec=attribute.specification();
1146 " in folder " <<
m_foldername <<
" will not be counted for bytes-read statistics" );
1168 ATH_MSG_DEBUG(
"channelID:\t"<<(*ci++)<<
"\t since: "<<
iov.first<<
"\t until: "<<
iov.second);
1176 std::vector<IOVHash>
result;
1180 if(crestIOVs.empty()){
1184 std::vector<IOV2Index> iov2IndexVect;
1185 iov2IndexVect.reserve(crestIOVs.size());
1187 for(
const auto& crestIOV : crestIOVs) {
1188 iov2IndexVect.emplace_back(std::stoull(crestIOV.first),hashInd++);
1191 size_t nIOVs = iov2IndexVect.size();
1195 for(
size_t ind=0; ind<nIOVs-1; ++ind) {
1197 , iov2IndexVect[ind+1].
first)
1202 , cool::ValidityKeyMax)
1210 ,
const cool::ValidityKey& vkey
1214 ,
const std::string& crestNodeDescr
1215 ,
const std::string& specString)
const
1218 std::string fMain(dumpName);
1221 std::filesystem::create_directory(fMain);
1223 if (not
myFile.is_open()) {
1224 std::string errorMessage{
"File creation for "+fabricatedName+
" failed."};
1226 throw std::runtime_error(errorMessage);
1235 myFile<<
json->description()<<s_delimiterJson<<std::endl;
1236 myFile<<
json->payloadSpec()<<s_delimiterJson<<std::endl;
1238 myFile<<
json->iov()<<s_delimiterJson<<std::endl;
1244 std::string newNodeDescription = std::regex_replace(crestNodeDescr,
std::regex(
"\""),
"\\\"");
1245 std::string newSpecString = std::regex_replace(specString,
std::regex(
":"),
": ");
1246 newSpecString = std::regex_replace(newSpecString,
std::regex(
","), s_delimiterJson);
1247 myFile<<
"\"node_description\" : \""<<newNodeDescription<<
'\"'<<s_delimiterJson<<std::endl;
1248 myFile<<
"\"folder_payloadspec\": \""<<newSpecString<<
'\"'<<s_delimiterJson<<std::endl;
1255 , cool::ValidityKey
until
1256 ,
bool vectorPayloadFlag
1257 , cool::ValidityKey vkey
1258 ,
const std::string& nodeDesc)
1261 std::string crestPayloadType=
"crest-json-single-iov";
1263 if(tagProperties!=
nullptr
1264 && tagProperties.contains(
"payloadSpec")) {
1265 crestPayloadType=tagProperties[
"payloadSpec"].get<std::string>();
1268 if(crestPayloadType.compare(
"crest-json-multi-iov")==0) {
1354 std::string errorMessage =
m_foldername +
": has multi-iov payload. Folders with multi-iov payloads currently not supported!";
1356 throw std::runtime_error{errorMessage};
1359 if (specString.empty()) {
1360 std::string errorMessage =
"Reading payload spec from " +
m_foldername +
" failed.";
1362 throw std::runtime_error{errorMessage};
1365 std::vector<BasicFolder> retVector;
1370 if(iovHashVect.empty() ||
until<=iovHashVect[0].first.first) {
1371 if(iovHashVect.empty()) {
1379 retVector.push_back(basicFolder);
1383 unsigned indIOVStart = 0;
1384 for(
const auto& iovhash : iovHashVect) {
1385 if(
since < iovhash.first.first)
break;
1386 if(
since < iovhash.first.second
1387 &&
since >= iovhash.first.first) {
1392 unsigned indIOVEnd = indIOVStart;
1393 while(indIOVEnd < iovHashVect.size()) {
1394 if(iovHashVect[indIOVEnd].
first.first <
until
1395 && iovHashVect[indIOVEnd].first.second >=
until) {
1401 for(
unsigned ind = indIOVStart; ind <= indIOVEnd; ++ind) {
1405 unsigned long long sinceT = iovHashVect[ind].first.first;
1407 std::string crest_work_dir=std::filesystem::current_path();
1408 crest_work_dir +=
"/crest_data";
1409 bool crest_rewrite =
true;
1410 Crest::CrestApiFs crestFSClient = Crest::CrestApiFs(crest_rewrite, crest_work_dir);
1414 {
"description",
"none"},
1415 {
"endOfValidity", 0},
1416 {
"lastValidatedTime", 0},
1418 {
"payloadSpec",
"none"},
1419 {
"synchronization",
"none"},
1420 {
"timeType",
"time"}};
1422 TagDto dto = TagDto();
1423 dto = dto.fromJson(js);
1426 crestFSClient.createTag(dto);
1440 {
"streamerInfo",
"none"}
1444 jResources.push_back(elem);
1449 {
"datatype",
"data"},
1450 {
"format",
"StoreSetDto"},
1451 {
"resources", jResources}
1454 StoreSetDto storeSetDto = StoreSetDto::fromJson(jsStoreSet);
1457 crestFSClient.storeData(
m_crestTag, storeSetDto,
"JSON",
"test",
"test",
"1", endtime);
1469 std::istringstream
ss(reply);
1470 Json2Cool inputJson(
ss, basicFolder, specString, &(iovHashVect[ind].
first));
1471 if (basicFolder.
empty()){
1472 std::string errorMessage =
"Reading channel data from "+
m_foldername+
" failed.";
1474 throw std::runtime_error{errorMessage};
1478 dumpFile(
"crest_dump",vkey,
nullptr,
false,&basicFolder,nodeDesc,specString);
1481 retVector.push_back(basicFolder);