Os arquivos do Microsoft Word e Excel não são arquivos de texto nos quais você pode simplesmente substituir o texto e isso definitivamente não funcionará com um
BLOB
. docx e xlsx os arquivos são na verdade arquivos zip (tente alterar a extensão do arquivo e descompactar para ver por si mesmo) que contêm uma definição XML do documento. Então você vai precisar:- Descompacte o arquivo
- Converter o arquivo que precisa ser alterado de um
BLOB
para umCLOB
- Modifique o conteúdo do arquivo XML adequado
- Converter o arquivo novamente em um
BLOB
de umCLOB
- Adicione o arquivo modificado de volta ao arquivo zip
Eu escrevi o código abaixo como um exemplo de como substituir um docx Arquivo. Para xlsx arquivos, cada planilha do Excel está contida em um arquivo XML diferente, portanto, você precisará modificar um pouco o código para que funcione com os dois tipos de arquivo.
O código usa o APEX_ZIP pacote que simplifica muito o trabalho com arquivos zip e também torna o código de exemplo um pouco mais claro sobre o que está acontecendo. Se você não tiver o APEX instalado, precisará descobrir como descompactar/rezipar os arquivos usando os pacotes Oracle que você possui.
DECLARE
l_old_file BLOB;
l_new_file BLOB;
l_files apex_zip.t_files;
l_document BLOB;
l_clob CLOB;
l_dest_offsset INTEGER;
l_src_offsset INTEGER;
l_lang_context INTEGER := DBMS_LOB.default_lang_ctx;
l_warning INTEGER;
BEGIN
-- Get the blob you want to "correct"
SELECT blob_content
INTO l_old_file
FROM apex_application_temp_files
WHERE ROWNUM = 1;
-- Get a list of all the file names contained within the zip
l_files := apex_zip.get_files (l_old_file);
-- Loop through all the files adding each one to the new zip
FOR i IN l_files.FIRST .. l_files.LAST
LOOP
l_document := apex_zip.get_file_content (l_old_file, l_files (i));
IF l_files (i) = 'word/document.xml'
THEN
-- if the file name is word/document.xml then make the changes to it
DBMS_LOB.createTemporary (lob_loc => l_clob, cache => FALSE);
l_dest_offsset := 1;
l_src_offsset := 1;
DBMS_LOB.converttoclob (dest_lob => l_clob,
src_blob => l_document,
amount => DBMS_LOB.lobmaxsize,
dest_offset => l_dest_offsset,
src_offset => l_src_offsset,
blob_csid => DBMS_LOB.default_csid,
lang_context => l_lang_context,
warning => l_warning);
--------------------
-- This is where you would do any replacements
--------------------
l_clob := REPLACE (l_clob, 'www.google.co.uk', 'www.google.com');
--------------------
l_dest_offsset := 1;
l_src_offsset := 1;
DBMS_LOB.CONVERTTOBLOB (dest_lob => l_document,
src_clob => l_clob,
amount => DBMS_LOB.lobmaxsize,
dest_offset => l_dest_offsset,
src_offset => l_src_offsset,
blob_csid => DBMS_LOB.default_csid,
lang_context => l_lang_context,
warning => l_warning);
END IF;
apex_zip.add_file (l_new_file, l_files (i), l_document);
END LOOP;
apex_zip.finish (l_new_file);
--Do whatever you want with the "new" file here
END;