00001 #include "MappingRules.h"
00002
00003 #include <sstream>
00004 #include <vector>
00005 #include <cctype>
00006
00007 #include "Reflex/Type.h"
00008
00009 std::string ora::MappingRules::sequenceNameForContainerId(){
00010 static std::string s_sequenceName("CONTAINER_ID");
00011 return s_sequenceName;
00012 }
00013
00014 std::string ora::MappingRules::sequenceNameForContainer( const std::string& containerName ){
00015 std::string ret("C_");
00016 return ret+containerName;
00017 }
00018
00019 std::string
00020 ora::MappingRules::sequenceNameForDependentClass( const std::string& containerName,
00021 const std::string& className ){
00022 std::string ret("D_");
00023 ret+=containerName;
00024 ret+="_";
00025 ret+=className;
00026 return ret;
00027 }
00028
00029 std::string ora::MappingRules::sequenceNameForMapping(){
00030 static std::string s_mappingSequenceName("MAPPING_ELEMENT_ID");
00031 return s_mappingSequenceName;
00032 }
00033
00034 std::string
00035 ora::MappingRules::mappingPropertyNameInDictionary()
00036 {
00037 static std::string s_propertyName("mapping");
00038 return s_propertyName;
00039 }
00040
00041 bool
00042 ora::MappingRules::isMappedToBlob(const std::string& mappingProperty){
00043 return (mappingProperty == "Blob" || mappingProperty == "blob" || mappingProperty == "BLOB" );
00044 }
00045
00046 std::string
00047 ora::MappingRules::persistencyPropertyNameInDictionary(){
00048 static std::string s_propertyName("persistency");
00049 return s_propertyName;
00050 }
00051
00052 bool
00053 ora::MappingRules::isLooseOnReading(const std::string& persistencyProperty){
00054 return (persistencyProperty == "loose_on_reading" || persistencyProperty == "LOOSE_ON_READING" );
00055 }
00056
00057 bool
00058 ora::MappingRules::isLooseOnWriting(const std::string& persistencyProperty){
00059 return (persistencyProperty == "loose_on_writing" || persistencyProperty == "LOOSE_ON_WRITING" );
00060 }
00061
00062 std::string
00063 ora::MappingRules::classId( const std::string& className,
00064 const std::string& classVersion ){
00065 return className+".V"+classVersion;
00066 }
00067
00068 std::string ora::MappingRules::classVersionFromId( const std::string& classId ){
00069 std::string ret("");
00070 size_t idx = classId.find('.');
00071 if( idx != std::string::npos ){
00072 ret = classId.substr( idx+2 );
00073 }
00074 return ret;
00075 }
00076
00077 std::string
00078 ora::MappingRules::baseIdForClass( const std::string& className ){
00079 return className+"."+baseClassVersion();
00080 }
00081
00082 std::string
00083 ora::MappingRules::baseClassVersion()
00084 {
00085 static std::string classVersion("BASE");
00086 return classVersion;
00087 }
00088
00089 std::pair<bool,std::string> ora::MappingRules::classNameFromBaseId( const std::string& classId ){
00090 std::pair<bool,std::string> ret(false,"");
00091 size_t cut = classId.find("."+baseClassVersion() );
00092 if( cut != std::string::npos ){
00093 ret.first = true;
00094 ret.second = classId.substr(0,cut);
00095 }
00096 return ret;
00097 }
00098
00099 std::string
00100 ora::MappingRules::defaultClassVersion(const std::string& className)
00101 {
00102 std::string classVersion(className);
00103 classVersion.append("_default");
00104 return classVersion;
00105 }
00106
00107 std::string
00108 ora::MappingRules::classVersionPropertyNameInDictionary()
00109 {
00110 static std::string s_propertyName("class_version");
00111 return s_propertyName;
00112
00113 }
00114
00115 std::string
00116 ora::MappingRules::newMappingVersion( const std::string& itemName,
00117 int iteration,
00118 char versionTrailer ){
00119 std::ostringstream os;
00120 os << itemName;
00121 os << "_" << versionTrailer;
00122 if ( iteration > 0 ) {
00123 if ( iteration < 10 ) os << "0";
00124 if ( iteration < 100 ) os << "0";
00125 os << iteration;
00126 } else {
00127 os << "000";
00128 }
00129 return os.str();
00130 }
00131
00132 std::string
00133 ora::MappingRules::newMappingVersionForContainer( const std::string& containerName,
00134 int iteration ){
00135 return newMappingVersion( containerName, iteration, 'M' );
00136 }
00137
00138 std::string
00139 ora::MappingRules::newMappingVersionForDependentClass( const std::string& containerName,
00140 const std::string& className,
00141 int iteration )
00142 {
00143 std::string contDependencyName = containerName+"_"+className;
00144 return newMappingVersion( contDependencyName, iteration, 'D' );
00145 }
00146
00147 std::string
00148 ora::MappingRules::scopedVariableName( const std::string& variableName,
00149 const std::string& scope ){
00150 std::stringstream scopedName;
00151 if(!scope.empty()) scopedName << scope << "::";
00152 scopedName << variableName;
00153 return scopedName.str();
00154 }
00155
00156 std::string
00157 ora::MappingRules::variableNameForArrayIndex( const std::string& arrayVariable,
00158 unsigned int index ){
00159 std::ostringstream arrayElementLabel;
00160 arrayElementLabel << arrayVariable << "[" << index << "]";
00161 return arrayElementLabel.str();
00162 }
00163
00164 std::string
00165 ora::MappingRules::variableNameForArrayColumn( unsigned int arrayIndex ){
00166 std::ostringstream arrayElementLabel;
00167 arrayElementLabel << "I" << arrayIndex;
00168 return arrayElementLabel.str();
00169 }
00170
00171 std::string
00172 ora::MappingRules::variableNameForArrayColumn( const Reflex::Type& array ){
00173 std::stringstream contentTypeName;
00174 contentTypeName << "A" << array.ArrayLength();
00175 return contentTypeName.str();
00176 }
00177
00178 std::string ora::MappingRules::variableNameForContainerValue(){
00179 static std::string s_cv("CV");
00180 return s_cv;
00181 }
00182
00183 std::string ora::MappingRules::variableNameForContainerKey(){
00184 static std::string s_ck("CK");
00185 return s_ck;
00186 }
00187
00188 std::string
00189 ora::MappingRules::scopedVariableForSchemaObjects( const std::string& variableName,
00190 const std::string& scope ){
00191 std::stringstream scopedName;
00192 if(!scope.empty()) scopedName << formatName(scope, ClassNameLengthForSchema) << "_";
00193 scopedName << variableName;
00194 return scopedName.str();
00195 }
00196
00198 #include "CondCore/ORA/interface/Exception.h"
00199 namespace ora {
00200 static std::string validChars("ABCDEFGHIJKLMNOPQRSTUVWXYZabcdefghijklmnopqrstuvwxyz_-0123456789");
00201 void checkString( const std::string& s, int code, bool thro=true){
00202 for( size_t i=0;i<s.size();i++){
00203 if( validChars.find( s[i])==std::string::npos ) {
00204 std::stringstream mess;
00205 mess <<" code="<<code<<" in string ["<<s<<"] found a wrong char=["<<s[i]<<"].";
00206 if( thro ) throwException( mess.str(),"validChars");
00207 }
00208 }
00209 }
00210
00211 }
00212
00213 std::string
00214 ora::MappingRules::newNameForSchemaObject( const std::string& initialName,
00215 unsigned int index,
00216 size_t maxLength,
00217 char indexTrailer){
00218 unsigned int digitsForPostfix = 3;
00219 if(index<10) digitsForPostfix = 2;
00220 size_t newSize = initialName.size()+digitsForPostfix;
00221 if(newSize > maxLength) newSize = maxLength;
00222 unsigned int cutSize = newSize - digitsForPostfix;
00223 std::stringstream newStr("");
00224 if( initialName[cutSize-1]=='_' ) cutSize -= 1;
00225 std::string cutString = initialName.substr(0, cutSize );
00226 newStr << cutString << "_";
00227 if( indexTrailer !=0 ) newStr<< indexTrailer;
00228 newStr<< index;
00229
00230 return newStr.str();
00231 }
00232
00233 std::string
00234 ora::MappingRules::newNameForDepSchemaObject( const std::string& initialName,
00235 unsigned int index,
00236 size_t maxLength)
00237 {
00238 return newNameForSchemaObject( initialName, index, maxLength, 'D' );
00239 }
00240
00241 std::string
00242 ora::MappingRules::newNameForArraySchemaObject( const std::string& initialName,
00243 unsigned int index,
00244 size_t maxL)
00245 {
00246 return newNameForSchemaObject( initialName, index, maxL, 'A' );
00247 }
00248
00249 std::string
00250 ora::MappingRules::nameForSchema( const std::string& variableName ){
00251 std::string varName( variableName );
00252
00253 MappingRules::ToUpper up(std::locale::classic());
00254 std::transform(varName.begin(), varName.end(),varName.begin(),up);
00255 size_t cutPoint = varName.size();
00256 if(cutPoint && varName[varName.size()-1] == '_' ) cutPoint -= 1;
00257 if(!cutPoint) return "";
00258 size_t start = 0;
00259 if(varName.size() && varName[0]== '_' ) start = 1;
00260 return varName.substr(start,cutPoint);
00261 }
00262
00263 std::string ora::MappingRules::shortNameByUpperCase( const std::string& className,
00264 size_t maxL ){
00265 if( !maxL ) return "";
00266 if( className.size() < maxL ) return className;
00267 std::vector< size_t> uppers;
00268 for( size_t i=0;i<className.size();i++) {
00269 if(::isupper(className[i]) || ::isdigit(className[i]) ) uppers.push_back(i);
00270 }
00271 std::stringstream shName;
00272 size_t usize = uppers.size();
00273 if( usize < maxL ){
00274 size_t start = 0;
00275 size_t cut = maxL-usize;
00276 if( usize && (cut > uppers[0]) ) cut = uppers[0];
00277 shName << className.substr( start, cut );
00278 size_t left = maxL-cut-usize;
00279 if( usize > 1) left = 0;
00280 size_t curs = 0;
00281 for( size_t i=0; i<usize;i++){
00282 size_t st = uppers[i];
00283 curs = st+left+1;
00284 shName << className.substr(st,left+1);
00285 left = 0;
00286 }
00287 size_t maxIndex = className.size();
00288 if( shName.str().size()<maxL && curs < maxIndex ){
00289 size_t more = maxL - shName.str().size();
00290 size_t max = curs+more;
00291 if(max > className.size()) max = className.size();
00292 for( size_t j=curs;j<max-1;j++ ){
00293 shName << className[j];
00294 }
00295 }
00296
00297
00298 } else {
00299 shName << className[0];
00300 for(size_t i=0 ;i<maxL-1;i++) {
00301 if( uppers[i] != 0 ) shName << className[uppers[i]];
00302 }
00303
00304 }
00306 return shName.str();
00307 }
00308
00309 std::string ora::MappingRules::shortScopedName( const std::string& scopedClassName,
00310 size_t maxLength ){
00311 if( !maxLength ) return "";
00312 std::string cn = scopedClassName;
00313 std::string sn("");
00314 size_t ns = cn.rfind("::");
00315 if( ns!= std::string::npos ){
00316 cn = scopedClassName.substr( ns+2 );
00317 sn = scopedClassName.substr( 0, ns );
00318 }
00319
00320 ns = cn.find(" ");
00321 while( ns != std::string::npos ){
00322 cn = cn.replace( ns, 1, "_");
00323 ns = cn.find(" ");
00324 }
00325
00326 ns = sn.find("::");
00327 if( ns == 0 ){
00328 sn = sn.substr( 2 );
00329 ns = sn.find("::");
00330 }
00331 while( ns != std::string::npos ){
00332 sn = sn.replace( ns, 2, "_");
00333 ns = sn.find("::");
00334 }
00335
00336 if( sn[sn.size()-1]=='_' ) sn = sn.substr(0,sn.size()-1);
00337
00338 if( sn == "std" ) sn = "";
00339
00340 size_t currSize = sn.size()+cn.size()+1;
00341 if( currSize > maxLength+1 ){
00342
00343 size_t maxScopeLen = maxLength/3;
00344 if( maxScopeLen ==0 ) maxScopeLen = 1;
00345 if( maxScopeLen > 1 ) maxScopeLen -= 1;
00346 if( sn.size() > maxScopeLen ){
00347 sn = sn.substr( 0,maxScopeLen );
00348 }
00349 size_t availableSize = maxLength-sn.size();
00350 if( sn.size() ) availableSize -= 1;
00351 cn =shortNameByUpperCase( cn, availableSize );
00352 }
00353 std::string ret = sn;
00354 if(!ret.empty()) ret += "_";
00355 ret += cn;
00356
00357 return ret;
00358 }
00359
00360 std::string ora::MappingRules::nameFromTemplate( const std::string templateClassName,
00361 size_t maxLength ){
00362 if( !maxLength ) return "";
00363 std::string newName("");
00364 size_t ind0 = templateClassName.find('<',0);
00365 if( ind0 != std::string::npos ){
00366 size_t ind1 = templateClassName.rfind('>');
00367 std::string templArg = templateClassName.substr( ind0+1, ind1-ind0-1 );
00368 std::string prefix = shortScopedName( templateClassName.substr( 0, ind0 ), maxLength );
00369 size_t currSize = templArg.size()+prefix.size()+1;
00370 if( currSize > maxLength+1 ){
00371
00372 size_t prefixL = maxLength/3;
00373 if( prefixL == 0 ) prefixL = 1;
00374 if( prefixL >1 ) prefixL -=1;
00375 prefix = shortScopedName( prefix, prefixL );
00376 }
00377 size_t templMaxSize = maxLength-prefix.size()-1;
00378 templArg = nameFromTemplate( templArg, templMaxSize );
00379 newName = prefix+"_"+ templArg;
00380 } else {
00381 newName = shortScopedName( templateClassName, maxLength );
00382 }
00383
00384 return newName;
00385 }
00386
00387 std::string
00388 ora::MappingRules::tableNameForItem( const std::string& itemName )
00389 {
00390 return "ORA_C_"+nameForSchema(formatName( itemName, MaxTableNameLength-5 ));
00391 }
00392
00393 std::string
00394 ora::MappingRules::columnNameForId()
00395 {
00396 return std::string("ID");
00397 }
00398
00399 std::string
00400 ora::MappingRules::columnNameForRefColumn()
00401 {
00402 return std::string("REF_ID");
00403 }
00404
00405 std::string
00406 ora::MappingRules::columnNameForVariable( const std::string& variableName,
00407 const std::string& scopeName,
00408 bool forData )
00409 {
00410 std::ostringstream totalString;
00411 int scopeMaxSize = MaxColumnNameLength/4-1;
00412 int extraSize = MaxColumnNameLength-variableName.size()-2;
00413 if( extraSize>0 && extraSize>scopeMaxSize ) scopeMaxSize = extraSize;
00414 if( !scopeName.empty() ) {
00415 size_t scopeCut = scopeName.size();
00416 if( scopeCut> (size_t)scopeMaxSize ) scopeCut = scopeMaxSize;
00417 totalString << scopeName.substr(0,scopeCut);
00418 totalString << "_";
00419 }
00420 size_t varMaxSize = MaxColumnNameLength-totalString.str().size();
00421
00422 size_t fp = variableName.find('[');
00423 if( fp != std::string::npos ){
00424
00425 std::string arrayVar = variableName.substr(0,fp);
00426 std::string indexVar = variableName.substr(fp);
00427 for( size_t ind = 0; ind!=std::string::npos; ind=indexVar.find('[',ind+1 ) ){
00428 indexVar = indexVar.replace(ind,1,"I");
00429 }
00430 for( size_t ind = indexVar.find(']'); ind!=std::string::npos; ind=indexVar.find(']',ind+1 ) ){
00431 indexVar = indexVar.replace(ind,1,"_");
00432 }
00433 size_t arrayVarCut = 0;
00434 size_t varCut = variableName.size()+1;
00435 if( varCut>varMaxSize ) varCut = varMaxSize;
00436 if( varCut>(indexVar.size()+1) ) arrayVarCut = varCut-indexVar.size()-1;
00437 totalString << arrayVar.substr(0,arrayVarCut);
00438 totalString << "_" << indexVar;
00439 } else {
00440 size_t varCut = variableName.size();
00441 if( varCut>varMaxSize ) varCut = varMaxSize;
00442
00443 totalString << variableName.substr(0,varCut);
00444 }
00445
00446 std::stringstream ret;
00447 if(forData) ret << "D";
00448 ret << nameForSchema(totalString.str());
00449
00450 return formatName(ret.str(),MaxColumnNameLength);
00451 }
00452
00453 std::string
00454 ora::MappingRules::columnNameForOID( const std::string& variableName,
00455 const std::string& scope,
00456 unsigned int index )
00457 {
00458 std::stringstream ret;
00459 ret << "R" << columnNameForVariable( variableName, scope, false )<<"_OID"<<index;
00460 return ret.str();
00461 }
00462
00463 std::string
00464 ora::MappingRules::columnNameForNamedReference( const std::string& variableName,
00465 const std::string& scope )
00466 {
00467 std::stringstream ret;
00468 ret << "R" << columnNameForVariable( variableName, scope, false )<<"_NAME";
00469 return ret.str();
00470 }
00471
00472 std::string
00473 ora::MappingRules::columnNameForRefMetadata( const std::string& variableName,
00474 const std::string& scope )
00475 {
00476 std::stringstream ret;
00477 ret << "M" << columnNameForVariable( variableName, scope, false );
00478 return ret.str();
00479 }
00480
00481 std::string
00482 ora::MappingRules::columnNameForRefId( const std::string& variableName,
00483 const std::string& scope )
00484 {
00485 std::stringstream ret;
00486 ret << "RID_" << columnNameForVariable( variableName, scope, false );
00487 return ret.str();
00488 }
00489
00490 std::string
00491 ora::MappingRules::columnNameForPosition()
00492 {
00493 return std::string("POS");
00494 }
00495
00496 std::string
00497 ora::MappingRules::fkNameForIdentity( const std::string& tableName, int index )
00498 {
00499 std::stringstream ret;
00500 ret << tableName <<"_ID_FK";
00501 if( index ) ret << "_"<<index;
00502 return ret.str();
00503 }
00504
00505 std::string ora::MappingRules::formatName( const std::string& variableName,
00506 size_t maxLength ){
00507 return nameFromTemplate( variableName, maxLength );
00508 }
00509