[VXCMD] Offset not being applied in Binary_ReadData?

Rodney Tamblyn rodneytamblyn at paradise.net.nz
Thu Feb 13 16:12:40 CST 2003


Ruslan,

Yes Valentina Binary_Read works fine now with large binary objects.

Some notes:

1) It's imperative to read from offset 0 otherwise you'll miss the  
first char of the data.   Metacard read/write commands are normally 1  
relative (eg in Metacard: read from file myFile at 0 ... will return a  
seek error)
2) You must check the size first and only read the right amount of  
data.  Valentina will return data if you read more (junk) ... ie it  
won't just evaluate to empty.

Here's an example script.  I use wrappers around the various Valentina  
calls to ensure they are appropriately formatted (eg  DB_GetDataSize)  
etc...

Rodney

--Example MC function which given a cursor and a field name and an  
(optional) file , will write a large binary file from Blob to file or  
new temporary file.

#saves a blob file to an external file
function DB_ExportFile pCurs,pFldNm,pFile
   local tData,tFldRef,tRead,tLength
#chk Valentina version is greater than 1.9.7b10
   if not DB_SupportRead() then
     answer "ExportFile - Sorry, only supported in 1.9.6b10 and later..."
     exit DB_ExportFile
   end if
#chk file to write to
   if pFile is empty then put tempName() into pFile
#open file
   open file pFile for binary write
   get the result
   if it <> empty then
     devErr the params && it	
     exit DB_ExportFile
   end if
#Note - read is 0 relative, unlike MC which is 1 relative
   put 0 into tOffset
   #get field ref
   put DB_CursGetFldRef(pCurs,pFldNm) into tFldRef
   if tFldRef is not a number then
     breakpoint
   end if
   #read data from db and write to file.
   #Make sure doesn't go wild and eat hard disk...
   put DB_GetDataSize(tFldRef) into tLength
   put false into tExit
   #I use a constant for default read size, but this can't be written  
to, so...
put kRead into tRead
   #val read is 0 relative.  You must read precisely the right amount of  
data
#otherwise any extra read will include junk you don't want (ie won't  
just return empty)
   repeat until tExit
     #read 1/2Mb
     #if file is less than read chunk, ie 500k by default...
     if kRead > tLength then put tLength into tRead
     #last chunk?
     if tOffset + kRead >= tLength then
       put tLength- tOffset into tRead
       put true into tExit
     end if
#assertion in case something went wrong...
     if tOffset >= tLength then
       #already got it all
       breakpoint
        exit repeat
     end if
     get  
DBChk("Binary_ReadData",Valentina("Binary_ReadData",tFldRef,"tData",tRea 
d,tOffset))
     write tData to file pFile at end
     add tRead to tOffset
   end repeat
   put tOffset
   close file pFile
end DB_ExportFile



More information about the Valentina mailing list