XRootD
Loading...
Searching...
No Matches
XrdXmlMetaLink Class Reference

#include <XrdXmlMetaLink.hh>

+ Collaboration diagram for XrdXmlMetaLink:

Public Member Functions

 XrdXmlMetaLink (const char *protos="root:xroot:", const char *rdprot="xroot:", const char *rdhost=0, const char *encode=0)
 
 ~XrdXmlMetaLink ()
 Destructor.
 
XrdOucFileInfoConvert (const char *fbuff, int blen=0)
 
XrdOucFileInfo ** ConvertAll (const char *fbuff, int &count, int blen=0)
 
const char * GetStatus (int &ecode)
 

Static Public Member Functions

static void DeleteAll (XrdOucFileInfo **vecp, int vecn)
 

Detailed Description

The XrdXmlMetaLink object provides a uniform interface to convert metalink XML specifications to one or more XrdOucFileInfo objects. This object does not do a rigorous syntactic check of the metalink specification. Specifications that technically violate RFC 5854 (v4 metalinks) or the metalink.org v3 metalinks may be accepted and yield valid information.

Definition at line 46 of file XrdXmlMetaLink.hh.

Constructor & Destructor Documentation

◆ XrdXmlMetaLink()

XrdXmlMetaLink::XrdXmlMetaLink ( const char *  protos = "root:xroot:",
const char *  rdprot = "xroot:",
const char *  rdhost = 0,
const char *  encode = 0 
)
inline

Constructor

Parameters
protosPointer to the list of desired protocols. Each protocol ends with a colon. They are specified without embedded spaces. Only urls using one of the listed protocols is returned. A nil pointer returns all urls regardless of the protocol.
rdprotThe protocol to be used when constructing the global file entry. If nil, the first protocol in protos is used. If nil, a global file is not constructed.
rdhostThe "<host>[<port>]" to use when constructing the global file. A global file entry is constructed only if rdhost is specified and a protocol is available, and a global file element exists in the xml file.
encodeSpecifies the xml encoding. Currently, only UTF-8 is is supported and is signified by a nil pointer.

Definition at line 136 of file XrdXmlMetaLink.hh.

136 :xroot:",
137 const char *rdprot="xroot:",
138 const char *rdhost=0,
139 const char *encode=0
140 ) : reader(0),
141 fileList(0), lastFile(0), currFile(0),
142 prots(protos ? strdup(protos) : 0),
143 encType(encode ? strdup(encode) : 0),
144 rdProt(rdprot), rdHost(rdhost),
145 fileCnt(0), eCode(0),
146 doAll(false), noUrl(true)
147 {*eText = 0; *tmpFn = 0;}

◆ ~XrdXmlMetaLink()

XrdXmlMetaLink::~XrdXmlMetaLink ( )
inline

Destructor.

Definition at line 153 of file XrdXmlMetaLink.hh.

153 {if (prots) free(prots);
154 if (encType) free(encType);
155 }

Member Function Documentation

◆ Convert()

XrdOucFileInfo * XrdXmlMetaLink::Convert ( const char *  fbuff,
int  blen = 0 
)

Convert an XML metalink specification to a file info object. Only the first file entry is converted (see ConvertAll()).

Parameters
fbuffPointer to the filepath that contains the metalink specification when blen is 0. Otherwise, fbuff points to a memory buffer of length blen containing the specification.
blenLength of the buffer. When <=0, the first argument is a file path. Otherwise, it is a memory buffer of length blen whose contents are written into a file in /tmp, converted, and then deleted.
Returns
Pointer to the corresponding file info object upon success. Otherwise, a null pointer is returned indicating that the metalink specification was invalid or had no required protocols. Use the GetStatus() method to obtain the description of the problem.

Definition at line 104 of file XrdXmlMetaLink.cc.

105{
106 static const char *mlV3NS = "http://www.metalinker.org/";
107 static const char *mlV4NS = "urn:ietf:params:xml:ns:metalink";
108 static const char *mlV3[] = {"metalink", "files", 0};
109 static const char *mTag[] = {"", "metalink", 0};
110 static const char *mAtr[] = {"xmlns", 0};
111 const char *scope = "metalink";
112 char *mVal[] = {0};
113 CleanUp onReturn;
114 XrdOucFileInfo *fP;
115 const char *gLFN;
116 char *colon, gHdr[272];
117 bool chkG;
118
119// If we are converting a buffer, then generate the file
120//
121 if (blen > 0)
122 {if (!PutFile(fname, blen)) return 0;
123 onReturn.delTFN = tmpFn;
124 fname = tmpFn;
125 }
126
127// Check if we should add a global file entry
128//
129 if (rdHost && (rdProt || (prots && (colon = index(prots,':')))))
130 {if (!rdProt) {rdProt = prots; *(colon+1) = 0;}
131 else colon = 0;
132 snprintf(gHdr, sizeof(gHdr), "%s//%s/", rdProt, rdHost);
133 if (colon) *(colon+1) = ':';
134 chkG = true;
135 } else chkG = false;
136
137// Get a file reader
138//
139 if (!(reader = XrdXmlReader::GetReader(fname, encType)))
140 {eCode = errno;
141 snprintf(eText, sizeof(eText), "%s trying to read %s",
142 (errno ? XrdSysE2T(errno) : "Unknown error"), fname);
143 return 0;
144 }
145
146// Make sure we delete the reader should we return
147//
148 onReturn.delRDR = &reader;
149
150// We must find the metalink tag
151//
152 if (!reader->GetElement(mTag, true))
153 {GetRdrError("looking for 'metalink' tag");
154 return 0;
155 }
156
157// The input can be in metalink 3 or metalink 4 format. The metalink tag will
158// tell us which one it is. It better be in the document with the xmlns attribute
159//
160 if (!reader->GetAttributes(mAtr, mVal))
161 {strcpy(eText, "Required metalink tag attribute 'xmlns' not found");
162 eCode = ENOMSG;
163 return 0;
164 }
165
166// The namespace tells us what format we are using here. For v3 formt we must
167// alignh ourselves on the "files" tag. There can only be one of those present.
168//
169 if (!strcmp(mVal[0], mlV3NS))
170 {if (!reader->GetElement(mlV3, true))
171 GetRdrError("looking for 'files' tag");
172 scope = "files";
173 }
174 else if ( strcmp((const char *)mVal[0], mlV4NS))
175 {strcpy(eText, "Metalink format not supported");
176 eCode = EPFNOSUPPORT;
177 }
178
179// Check if can continue
180//
181 free(mVal[0]);
182 if (eCode) return 0;
183
184// Get one or more files
185//
186 currFile = 0; fileCnt = 0; noUrl = true;
187 do{if (!GetFile(scope)) break;
188 currFile = new XrdOucFileInfo;
189 if (GetFileInfo("file"))
190 {if (lastFile) lastFile ->nextFile = currFile;
191 else fileList = currFile;
192 lastFile = currFile;
193 if (chkG && (gLFN = currFile->GetLfn()))
194 {char lfnBuff[2048];
195 snprintf(lfnBuff, sizeof(lfnBuff), "%s%s", gHdr, gLFN);
196 currFile->AddUrl(lfnBuff, 0, INT_MAX);
197 currFile->AddProtocol(rdProt);
198 }
199 currFile = 0;
200 fileCnt++; noUrl = true;
201 }
202 } while(doAll);
203
204// The loop ends when we cannot find a file tag. So, the current file is invalid
205//
206 if (currFile) {delete currFile; currFile = 0;}
207
208// Check if we have any files at all
209//
210 if (!fileCnt)
211 {strcpy(eText, "No applicable urls specified for the file entry");
212 eCode = EDESTADDRREQ;
213 }
214
215// If this is an all call then return to execute the postantem
216//
217 fP = fileList; lastFile = fileList = 0;
218 if (doAll) return fP;
219
220// Check if we have clean status. If not, undo all we have and return failure
221//
222 if (!eCode) return fP;
223 if (fP) delete fP;
224 return 0;
225}
const char * XrdSysE2T(int errcode)
Definition XrdSysE2T.cc:104
XrdOucFileInfo * nextFile
Link field to simply miltiple file processing.
const char * GetLfn()
void AddProtocol(const char *protname)
void AddUrl(const char *url, const char *cntry=0, int prty=0, bool fifo=true)
static XrdXmlReader * GetReader(const char *fname, const char *enc=0, const char *impl=0)
virtual int GetElement(const char **ename, bool reqd=false)=0
virtual bool GetAttributes(const char **aname, char **aval)=0

References XrdOucFileInfo::AddProtocol(), XrdOucFileInfo::AddUrl(), XrdXmlReader::GetAttributes(), XrdXmlReader::GetElement(), XrdOucFileInfo::GetLfn(), XrdXmlReader::GetReader(), XrdOucFileInfo::nextFile, and XrdSysE2T().

Referenced by ConvertAll().

+ Here is the call graph for this function:
+ Here is the caller graph for this function:

◆ ConvertAll()

XrdOucFileInfo ** XrdXmlMetaLink::ConvertAll ( const char *  fbuff,
int &  count,
int  blen = 0 
)

Convert an XML metalink specification to a file info object. All file entries are converted.

Parameters
fbuffPointer to the filepath that contains the metalink specification when blen is 0. Otherwise, fbuff points to a memory buffer of length blen containing the specification.
countPlace where the number of array elements is returned.
blenLength of the buffer. When <=0, the first argument is a file path. Otherwise, it is a memory buffer of length blen whose contents are written into a file in /tmp, converted, and then deleted.
Returns
Pointer to the array of corresponding fil info objects upon success. Otherwise, Otherwise, a null pointer is returned indicating that the metalink specification was invalid or had no required protocols. Use the GetStatus() method to obtain the description of the problem. Be aware that you must first delete each file info object before deleting the array. You can do this via DeleteAll().

Definition at line 231 of file XrdXmlMetaLink.cc.

233{
234 CleanUp onReturn;
235 XrdOucFileInfo *fP, **fvP;
236
237// Indicate this is a call from here
238//
239 doAll = true;
240 count = 0;
241
242// If we are converting a buffer, then generate the file
243//
244 if (blen > 0)
245 {if (!PutFile(fname, blen)) return 0;
246 onReturn.delTFN = tmpFn;
247 fname = tmpFn;
248 }
249
250// Perform the conversion
251//
252 if (!(fP = Convert(fname))) return 0;
253
254// Check if we have clean status, if not return nothing
255//
256 if (eCode)
257 {XrdOucFileInfo *fnP = fP->nextFile;
258 while((fP = fnP))
259 {fnP = fP->nextFile;
260 delete fP;
261 }
262 return 0;
263 }
264
265// Return a vector of the file info objects
266//
267 fvP = new XrdOucFileInfo* [fileCnt];
268 for (int i = 0; i < fileCnt; i++) {fvP[i] = fP; fP = fP->nextFile;}
269 count = fileCnt;
270 return fvP;
271}

References Convert(), and XrdOucFileInfo::nextFile.

+ Here is the call graph for this function:

◆ DeleteAll()

void XrdXmlMetaLink::DeleteAll ( XrdOucFileInfo **  vecp,
int  vecn 
)
static

Delete a vector of file info objects and the vector itself as well.

Parameters
vecpPointer to the array.
vecnNumber of elements in the vector.

Definition at line 277 of file XrdXmlMetaLink.cc.

278{
279// Delete each object in the vector
280//
281 for (int i = 0; i < vecn; i++)
282 delete vecp[i];
283
284// Now delete the vector
285//
286 delete []vecp;
287}

◆ GetStatus()

const char * XrdXmlMetaLink::GetStatus ( int &  ecode)
inline

Obtain ending status of previous conversion.

Parameters
ecodePlace to return the error code, if any.
Returns
Pointer to the error text describing the error. The string becomes invalid if Convert() is called or the object is deleted. If no error was encountered, a null string is returned with ecode == 0.

Definition at line 115 of file XrdXmlMetaLink.hh.

115{ecode = eCode; return eText;}

The documentation for this class was generated from the following files: