Reading PDF into a blob then sending as an attachment - pdf

I am trying to read a PDF into a blob object then do an INSERT into my oracle database so that it can be sent off as an attachment. Now the email portion is working, and it adds an attachment but the attachment is always corrupt and I can't open it. Below is the code where I create my blob pdf, can someone help me figure out why this isn't creating the proper attachment?
ls_pdf_name = ls_pdf_path + "\" + "invnum_" + ls_invoice + ".pdf"
ls_pdf_filename = "invoice_" + ls_invoice + ".pdf"
ls_rc = wf_check_pdf_status(ll_invoice_number, ls_sub_type, ll_user_supp_id)
If ls_rc = "Y" Then
li_fnum = FileOpen(ls_pdf_name, StreamMode!)
li_bytes = FileRead(li_fnum, bPDF)
FileClose(li_fnum)
ll_rc = wf_update_pdf_tables(bPDF, ls_pdf_filename, ls_sub_type, ll_user_supp_id, ll_invoice_number, ls_month, ls_year)
EDIT
So I took Calvin's advice and switched my insert to the following:
Here is the INSERT statement that puts the blob into the table
INSERT INTO ATTACH_DOCUMENT
(id, filename, mime_type, date_time_created)
VALUES
(ATTACH_DOCUMENT_SEQ.NEXTVAL, :pdf_filename, 'application/pdf', CURRENT_TIMESTAMP);
UPDATEblob ATTACH_DOCUMENT
SET data = :pdf
WHERE id = ATTACH_DOCUMENT_SEQ.CURRENTVAL;
But when I go to open the PDF email attachment from my email, Adobe opens up with this error - Could not open because it is either not a supported file type or because it has been damaged (for example it was sent as an email attachment and wasn't decoded correctly)
Thanks

How big is the PDF file?
You may not be getting all the contents with a simple FileRead() - try using FileReadEx()

The first thing to do is to check if the pdf is correctly saved in the database :
don't remove the pdf file after it is inserted in the db.
using a sql interpreter calculate the size of the blob column you have inserted the file into and verify that it matches the file size.
You didn't mention the database you are using, for example in ms sql server you could use the datalength() function to do this. Depending on the database you may check if the pdf is corrupted by calculating its md5 hash.
if you use a capable query tool (eg TOAD for Oracle) you could save the blob as a pdf file and verify that is readable.

Related

How to avoid empty xml file

Apologizing in advance if i am posting this in the wrong place. I have a windows batch script that calls a sql query to produce an xml file which gets transferred to a 3rd party. It is scheduled to run every 15 min. My issue is that there are times when there are no records and it creates an empty file. This causes issues when it reaches the 3rd party.
This is the section that is in my .sql file (which runs fine) but I cant figure out how to only produce the xml if there are records in it.
select #cmd = ' bcp "select * from dbo.WelcomeEmail CustomerDetail for xml auto, root(''CustomerDetails''), elements" ' + 'queryout "d:\sample.xml"
I tried this but it gave me an error bcp failed:
select #cmd = ' bcp "select * from dbo.WelcomeEmail where email is not null CustomerDetail for xml auto, root(''CustomerDetails''), elements" ' + 'queryout "d:\sample.xml"
if you need me to provide additional info, please let me know. Thanks!
See this answer: How can I check the size of a file in a Windows batch script?
You could check to see if the file contains zero bytes (or is whatever the size of the file is when there's no data) and then just delete the file.

Exporting image data with bcp in sql2000

Hi I have a a sql 2000 database with a large number of scanned documents stored as pdfs and word documents stored in an image data type.
I need to export them to files.
I have written code to to do this using xp_cmdshell and bcp. Looking at other questions I have created a fmt file as below:
8.0
1
1 SQLIMAGE 0 0 "" 1 FILEDATA ""
the command is
bcp "select filedata FROM attacheddocuments where pkey = '+ convert (varchar, #imageid) + '" queryout "c:\scans\' + #imagefilename + '" -T -f c:\scans\attached.fmt
however when I run the query it creates all the files but they cannot be opened in either word or acrobat. both report that the file is corrupt.
If instead I run the command
bcp "select filedata FROM attacheddocuments where pkey = '+ convert (varchar, #imageid) + '" queryout "c:\scans\' + #imagefilename + '" -T -N
The pdf files now open ok but the word documents are still corrupt.
Does anyone have any ideas where I am going wrong?
I know this is a really old post, I am having this issue with all files except PDF's.
I have tried without the -N and with. Using a format file and not using a format file. Strange thing is I used to use my script often, had not used it for a while. During that period some SQL updates have came out. Not the scripts only exports PDF documents not being corrupt.
Zip files and just about any file I can run through a repair tool and they are fixed. But that is not a doable option due to volume.
format file
Plus My format file had a 4 instead of 0. That alone made all files but PDF's documents corrupt with corrupt headers.

DotNetZip zipping files with Arabic names

When creating a zip file out of many Arabic named files, I have as prompted in DotNetZip's FAQ changed the code page to the following:
Using zip As New ZipFile()
zip.AddDirectoryByName("Files")
zip.AlternateEncoding = Encoding.UTF8
zip.AlternateEncodingUsage = Ionic.Zip.ZipOption.Always
Dim row As Integer
For row = 0 To ds.Tables("d").Rows.Count - 1
fileToDownload = Server.MapPath("~/.../Resources/Attachments/" + ds.Tables("d").Rows(row).Item(1).ToString)
zip.AddFile(fileToDownload, "Files")
Next
Response.Clear()
Response.BufferOutput = False
Dim zipName As String = [String].Format(gvRow.Cells(8).Text.Trim + ".zip")
Response.ContentType = "application/zip"
Response.AddHeader("content-disposition", "attachment; filename=" + zipName)
zip.Save(Response.OutputStream)
Response.[End]()
End Using
I have used several listed Arabic encoding codes, but most of them produce '???' whereas this one produces names as the following: '¦ßs-¦ µ+++ ¦ß+pß.docx'
What is the correct code to be used? Or am I missing something?
Use UTF8 Encoding and pass it as parameter to the constructor:
IO.File.Delete("D:/testZip.zip")
Using zip As New Ionic.Zip.ZipFile(Encoding.UTF8)
zip.AddDirectory("d:/out")
zip.Save("D:/testZip.zip")
End Using
this code works with me with Arabic file names (windows 7).
EDIT #1 : you must force DotNetZip to use the specified encoding by using Always option instead of AsNesseary :
IO.File.Delete("D:/testZip.zip")
Using zip As New Ionic.Zip.ZipFile()
zip.AlternateEncoding = Encoding.UTF8
zip.AlternateEncodingUsage = Ionic.Zip.ZipOption.Always
zip.AddDirectory("d:/out")
zip.Save("D:/testZip.zip")
End Using
EDIT #2 : based on your comment, I think your operating system does not support Arabic UI,for windows 7 professional 32 bit, go to Control Panel -> Region and Language -> Administrative [tab] -> click "change System locale" button -> choose "Arabic Egypt" for Example -> OK -> OK (restart computer is needed) , Don't worry, the language of windows 7 still English.
EDIT #3 : As I mentioned in EDIT #2, your system must support Arabic UI, for example, create a file called (ملف جديد) then add it to archive using WinZip or Winrar, then open the generated archive, if you can read file names correctly , then try to use one of the following encodings in your code :
Encoding.Unicode
Encoding.UTF7
Encoding.UTF8
Encoding.UTF32
If you are unable to read Arabic file names inside the generated archive, you must configure your system to support Arabic UI.
Also, please use the following order for these lines, put the Encoding, then add files or folders :
zip.AlternateEncoding = Encoding.UTF8
zip.AlternateEncodingUsage = Ionic.Zip.ZipOption.Always
zip.AddDirectoryByName("Files")
After using what seemed like a myriad of trials using code pages, simply replacing this:
zip.AlternateEncoding = Encoding.UTF8
with this:
zip.AlternateEncoding = Encoding.GetEncoding(720)
worked.

How to run same syntax on multiple spss files

I have 24 spss files in .sav format in a single folder. All these files have the same structure. I want to run the same syntax on all these files. Is it possible to write a code in spss for this?
You can use the SPSSINC PROCESS FILES user submitted command to do this or write your own macro. So first lets create some very simple fake data to work with.
*FILE HANDLE save /NAME = "Your Handle Here!".
*Creating some fake data.
DATA LIST FREE / X Y.
BEGIN DATA
1 2
3 4
END DATA.
DATASET NAME Test.
SAVE OUTFILE = "save\X1.sav".
SAVE OUTFILE = "save\X2.sav".
SAVE OUTFILE = "save\X3.sav".
EXECUTE.
*Creating a syntax file to call.
DO IF $casenum = 1.
PRINT OUTFILE = "save\TestProcess_SHOWN.sps" /"FREQ X Y.".
END IF.
EXECUTE.
Now we can use the SPSSINC PROCESS FILES command to specify the sav files in the folder and apply the TestProcess_SHOWN.sps syntax to each of those files.
*Now example calling the syntax.
SPSSINC PROCESS FILES INPUTDATA="save\X*.sav"
SYNTAX="save\TestProcess_SHOWN.sps"
OUTPUTDATADIR="save" CONTINUEONERROR=YES
VIEWERFILE= "save\Results.spv" CLOSEDATA=NO
MACRONAME="!JOB"
/MACRODEFS ITEMS.
Another (less advanced) way is to use the command INSERT. To do so, repeatedly GET each sav-file, run the syntax with INSERT, and sav the file. Probably something like this:
get 'file1.sav'.
insert file='syntax.sps'.
save outf='file1_v2.sav'.
dataset close all.
get 'file2.sav'.
insert file='syntax.sps'.
save outf='file2_v2.sav'.
etc etc.
Good luck!
If the Syntax you need to run is completely independent of the files then you can either use: INSERT FILE = 'Syntax.sps' or put the code in a macro e.g.
Define !Syntax ()
* Put Syntax here
!EndDefine.
You can then run either of these 'manually';
get file = 'file1.sav'.
insert file='syntax.sps'.
save outfile ='file1_v2.sav'.
Or
get file = 'file1.sav'.
!Syntax.
save outfile ='file1_v2.sav'.
Or if the files follow a reasonably strict naming structure you can embed either of the above in a simple bit of python;
Begin Program.
imports spss
for i in range(0, 24 + 1):
syntax = "get file = 'file" + str(i) + ".sav.\n"
syntax += "insert file='syntax.sps'.\n"
syntax += "save outfile ='file1_v2.sav'.\n"
print syntax
spss.Submit(syntax)
End Program.

Issue with bulk insert

I am trying to insert the data from this link to my SQL server
https://www.ian.com/affiliatecenter/include/V2/CityCoordinatesList.zip
I created the table
CREATE TABLE [dbo].[tblCityCoordinatesList](
[RegionID] [int] NOT NULL,
[RegionName] [nvarchar](255) NULL,
[Coordinates] [nvarchar](4000) NULL
) ON [PRIMARY]
And I am running the following script to do the bulk insert
BULK INSERT tblCityCoordinatesList
FROM 'C:\data\CityCoordinatesList.txt'
WITH
(
FIRSTROW = 2,
MAXERRORS = 0,
FIELDTERMINATOR = '|',
ROWTERMINATOR = '\n'
)
But the bulk insert fails with following error
Cannot obtain the required interface ("IID_IColumnsInfo") from OLE DB provider "BULK" for linked server "(null)".
When I google, I found several articles which says the issue may be with RowTerminator, but I tried everything like \n\r, \n etc, but nothing is working.
Could anyone please help me to insert this data into my database?
Try ROWTERMINATOR = '0x0a'.
it should work.
This can also happen if the number of columns mismatch between the table and the imported file
I got the same error message, and as you had mention, it was related to unexpected line ending.
In my case the line ending was specified in a fmt file as a Windows Line ending (CRLF), written as \r\n, and the data file to process has a Mac classic one (CR).
I solved it with an editor that can show the current line ending and change it. I used EditPad Lite wich shows the opened file line ending in the bottom bar and pressing it allow to replace with the expected one.
I had this on SQL2019 when the FORMAT='CSV' option was used, and there was a comma on the end of each line in the source file. So the table your BULK inserting into needed to have an extra dummy field to cater for the fact each record has essentially a blank field in the source file.
!
I get the same error, probably from the file encoding problem. I fixed it by opening the problem CSV file using Notepad++, select everything and copy to clipboard. Next, create a new text file (making sure it has the CSV file extension), open it using Notepad++, then paste the text to the new file. Save and close all files. You should be able to successfully load the new CSV file into the SQL server.
you need run BULK INSERT - command from windows login (not from SQL). Now I don't have any examples