Sunday, 5 March 2017

Oracle Attachments in EBS


Attaching Tax PDFs to respective Parties using DB Object

Below steps include bulk attachment of files from a location to the respective parties,

Step 1 - Create a staging table with file details,

DROP TABLE Stag_w9_party_det CASCADE CONSTRAINTS;

CREATE TABLE Stag_w9_party_det
(
  PDF_NAME        VARCHAR2(200 BYTE),
  TAX_PAYER_NAME  VARCHAR2(200 BYTE),
  TAX_PAYER_ID    VARCHAR2(20 BYTE),
  HAND_WRTN_NO    VARCHAR2(15 BYTE),
  STATUS          VARCHAR2(15 BYTE),
  STATUS_MSG      VARCHAR2(400 BYTE),
  PARTY_NAME      VARCHAR2(360 BYTE)            NOT NULL,
  PARTY_NUMBER    VARCHAR2(30 BYTE)             NOT NULL
);

Step 2 - Load excel data to above staging table using SQL*Loader,

OPTIONS (SKIP=1, BINDSIZE=50000, DIRECT=FALSE, ERRORS=99999, ROWS=100000, READSIZE=65536)
load data
TRUNCATE
into table Stag_w9_party_det
fields terminated by ',' optionally enclosed by '"'
trailing nullcols (
PDF_NAME "trim(:PDF_NAME)",
TAX_PAYER_NAME "trim(:TAX_PAYER_NAME)",
TAX_PAYER_ID "trim(:TAX_PAYER_ID)",
HAND_WRTN_NO "regexp_replace( trim(:HAND_WRTN_NO), '[[:space:]]+', NULL)",
PARTY_NAME "trim(:PARTY_NAME)",
PARTY_NUMBER "regexp_replace( trim(:PARTY_NUMBER), '[[:space:]]+', NULL)"
)

Step 3 - Create a concurrent program upon the below procedure, and capture all the invalid parties and process all valid parties by attaching the Tax PDF Files to the respective parties 

CREATE OR REPLACE PROCEDURE apps.w9fileattach (
   p_errbuff         OUT      VARCHAR2,
   p_retcode         OUT      NUMBER,
   v_user_name       IN       VARCHAR2,
   v_resp_name       IN       VARCHAR2,
   v_category_name   IN       VARCHAR2,
   v_entity_name     IN       VARCHAR2
)
AS
/*###################################################################
File Name :  apps.w9FileAttach
Description : Attaches the Tax pdf file to the corresponding Parties
/*################################################################### */
   l_rowid                   ROWID;
   l_attached_document_id    NUMBER;
   l_document_id             NUMBER;
   l_document_tl_id          NUMBER;
   l_media_id                NUMBER;
   l_category_id             NUMBER;
   l_pk1_value               fnd_attached_documents.pk1_value%TYPE;
   l_description             fnd_documents_tl.description%TYPE;
   l_title                   fnd_documents_tl.title%TYPE;
   l_filename                fnd_documents_tl.file_name%TYPE;
   l_seq_num                 NUMBER                                  := NULL;
   l_appl_id                 NUMBER;
   l_resp_id                 NUMBER;
   l_fnd_user_id             NUMBER;
   l_instance                VARCHAR2 (20);
   v_conc_req_id             NUMBER;
   l_dir_name                VARCHAR2 (20);
   l_short_datatype_id       NUMBER;
   x_blob                    BLOB;
   fils                      BFILE;
   blob_length               INTEGER;
   l_entity_name             VARCHAR2 (100);
   l_format                  VARCHAR2 (100);
   l_concurrent_program_id   VARCHAR2 (100);
   l_application_id          VARCHAR2 (100);
   l_last_update_date        VARCHAR2 (100);
   l_file_content_type       VARCHAR2 (100);
   v_pty_id                  VARCHAR2 (100);
   v_pty_no                  VARCHAR2 (100);
   v_pty_nme                 VARCHAR2 (100);
   v_tax_code                VARCHAR2 (100);
   v_pk2_val                 VARCHAR2 (20)                       DEFAULT NULL;
   v_pk3_val                 VARCHAR2 (20)                       DEFAULT NULL;
   v_pk4_val                 VARCHAR2 (20)                       DEFAULT NULL;
   v_pk5_val                 VARCHAR2 (20)                       DEFAULT NULL;
   v_doc_id                  NUMBER;
   v_att_doc_id              NUMBER;
   l_pdf_name                VARCHAR2 (100);
   file_exists               BOOLEAN                                 := FALSE;
   v_file_name_cnt           NUMBER                                  := NULL;
   v_dir_cnt                 NUMBER                                  := NULL;
   v_pty_val                 NUMBER;
   v_flag                    VARCHAR2 (1);
   v_status                  VARCHAR2 (50)                           := NULL;
   v_status_msg              VARCHAR2 (400)                          := NULL;

   CURSOR c1
   IS
      SELECT   *
          FROM Stag_w9_party_det
         WHERE status IS NULL
      ORDER BY pdf_name DESC;
BEGIN
   BEGIN
      SELECT instance_name
        INTO l_instance
        FROM v$instance;
   EXCEPTION
      WHEN OTHERS
      THEN
         apps.fnd_file.put_line (fnd_file.LOG,
                                    'Error in Instance select statment - '
                                 || SQLERRM
                                );
   END;

   IF l_instance IN ('DEV', 'TEST', 'PREPROD')
   THEN
      SELECT COUNT (1)
        INTO v_dir_cnt
        FROM all_directories
       WHERE directory_name = 'FILES_ATTACH_DIR'
         AND directory_path =
                  '/interface_j/' || l_instance || '/incoming/W9_PARTIES';
   ELSE
      SELECT COUNT (1)
        INTO v_dir_cnt
        FROM all_directories
       WHERE directory_name = 'FILES_ATTACH_DIR'
         AND directory_path =
                  '/interface_i/' || l_instance || '/incoming/W9_PARTIES';
   END IF;

   IF v_dir_cnt = 0
   THEN
      fnd_file.put_line (fnd_file.LOG,
                         '==========Directory Creation....==========='
                        );

      -- Directory Creation
      IF l_instance IN ('DEV', 'TEST', 'PREPROD')
      THEN
         EXECUTE IMMEDIATE    'create or replace directory FILES_ATTACH_DIR AS
                             ''/interface_j/'
                           || l_instance
                           || '/incoming/W9_PARTIES''';
      ELSE
         EXECUTE IMMEDIATE    'create or replace directory FILES_ATTACH_DIR AS
                             ''/interface_i/'
                           || l_instance
                           || '/incoming/W9_PARTIES''';
      END IF;
   ELSE
      fnd_file.put_line (fnd_file.LOG, 'Directory already created');
   END IF;

   fnd_file.put_line (fnd_file.LOG,
                      '==========User/Responsibility Details....==========='
                     );

   -- User Details
   SELECT user_id
     INTO l_fnd_user_id
     FROM apps.fnd_user
    WHERE UPPER (user_name) = UPPER (v_user_name);

   SELECT application_id, responsibility_id
     INTO l_appl_id, l_resp_id
     FROM apps.fnd_responsibility_vl
    WHERE UPPER (responsibility_name) = UPPER (v_resp_name);

   -- Category_id
   SELECT category_id
     INTO l_category_id
     FROM fnd_document_categories_vl
    WHERE user_name LIKE v_category_name;

   fnd_file.put_line (fnd_file.LOG,
                      'Processing with Category Name - ' || v_category_name
                     );
   fnd_file.put_line (fnd_file.output,
                      'Processing with Category Name - ' || v_category_name
                     );

-- Fetching and processing staging table data
   FOR i IN c1
   LOOP
      fnd_file.put_line
                  (fnd_file.output,
                   '########################################################'
                  );
      fnd_file.put_line (fnd_file.LOG,
                            'Processing party from staging table - '
                         || i.party_name
                        );
      v_flag := 'Y';
      v_pty_val := NULL;

      -- Validation Parties
      IF v_flag = 'Y'
      THEN
         BEGIN
            SELECT COUNT (1)
              INTO v_pty_val
              FROM hz_parties
             WHERE UPPER (party_name) LIKE UPPER (i.party_name);
         EXCEPTION
            WHEN OTHERS
            THEN
               v_flag := 'N';
               v_status := 'INVALID';
               v_status_msg := 'Invalid Party Name';
         END;
      END IF;

      v_pty_val := NULL;

      IF v_flag = 'Y'
      THEN
         -- Validation
         BEGIN
            SELECT COUNT (1)
              INTO v_pty_val
              FROM hz_parties
             WHERE (    UPPER (party_name) LIKE UPPER (i.party_name)
                    AND jgzz_fiscal_code IN (i.tax_payer_id)
                   );
         EXCEPTION
            WHEN OTHERS
            THEN
               v_flag := 'N';
               v_status := 'INVALID';
               v_status_msg := 'Invalid Party Name';
         END;
      END IF;

      v_pty_val := NULL;

      IF v_flag = 'Y'
      THEN
         -- Validation
         BEGIN
            SELECT COUNT (1)
              INTO v_pty_val
              FROM hz_parties
             WHERE (    UPPER (party_name) LIKE UPPER (i.party_name)
                    AND jgzz_fiscal_code IN (i.tax_payer_id)
                   )
               AND TRIM (REGEXP_REPLACE (party_number, '[[:space:]]+', NULL)) IN
                                                                                --(i.party_number)
                                                                                TRIM
                                                                                   (REGEXP_REPLACE
                                                                                       (i.party_number,
                                                                                        '[[:space:]]+',
                                                                                        NULL
                                                                                       )
                                                                                   );
         EXCEPTION
            WHEN OTHERS
            THEN
               v_flag := 'N';
               v_status := 'INVALID';
               v_status_msg := 'Invalid Party Name';
         END;
      END IF;

      IF v_pty_val IS NULL
      THEN
         UPDATE Stag_w9_party_det
            SET status = v_status,
                status_msg = v_status_msg
          WHERE party_name = i.party_name
            AND party_number = i.party_number
            AND tax_payer_id = i.tax_payer_id
            AND pdf_name = i.pdf_name;

         fnd_file.put_line
                        (fnd_file.LOG,
                            'Error through validation of parties for party - '
                         || i.party_name
                        );
         COMMIT;
      ELSE
-- Fetching and processing Party Information from DB
         FOR rec_mpty IN
         
            --c2(i.party_name,i.tax_payer_id, i.party_number)
            (SELECT party_id, party_number, party_name, jgzz_fiscal_code
               FROM hz_parties
              WHERE (    UPPER (party_name) LIKE UPPER (i.party_name)
                     AND jgzz_fiscal_code IN (i.tax_payer_id)
                    )
                AND TRIM (REGEXP_REPLACE (party_number, '[[:space:]]+', NULL)) IN
                                                                                 --(i.party_number)
                                                                                 TRIM
                                                                                    (REGEXP_REPLACE
                                                                                        (i.party_number,
                                                                                         '[[:space:]]+',
                                                                                         NULL
                                                                                        )
                                                                                    ))
         LOOP
            --v_cnt := 1;
            v_pty_id := rec_mpty.party_id;
            v_pty_no := rec_mpty.party_number;
            v_pty_nme := rec_mpty.party_name;
            v_tax_code := rec_mpty.jgzz_fiscal_code;
            fnd_file.put_line (fnd_file.LOG,
                                  'DB Processing Party Name - '
                               || v_pty_nme
                               || ' and Party Id - '
                               || v_pty_id
                              );
            fnd_file.put_line (fnd_file.output,
                                  'DB Processing Party Name - '
                               || v_pty_nme
                               || ' and Party Id - '
                               || v_pty_id
                              );

            SELECT SUBSTR (i.pdf_name, 1, LENGTH (i.pdf_name) - 4)
              --INSTR (i.pdf_name, '.', 1) - 1)
            INTO   l_pdf_name
              FROM DUAL;

-- Fetching and processing PDF files as per table data
            FOR k IN (SELECT   l_pdf_name || '.pdf' l_pdf_name
                          FROM DUAL
                      UNION
                      SELECT   l_pdf_name || ' (2).pdf' l_pdf_name
                          FROM DUAL
                      ORDER BY 1 DESC)
            LOOP
               l_filename := k.l_pdf_name;
               fnd_file.put_line (fnd_file.output,
                                  'Processing PDF Name - ' || l_filename
                                 );
               v_doc_id := NULL;
               v_att_doc_id := NULL;

               -- Validation to verify file name attachment
               BEGIN
                  SELECT COUNT (DISTINCT file_name)
                    INTO v_file_name_cnt
                    FROM fnd_documents
                   WHERE document_id IN (
                            SELECT document_id
                              FROM fnd_attached_documents
                             WHERE pk1_value = v_pty_id
                               AND entity_name = v_entity_name
                               AND category_id = l_category_id)
                     AND category_id = l_category_id
                     AND file_name = l_filename;
               EXCEPTION
                  WHEN OTHERS
                  THEN
                     v_file_name_cnt := 0;
               END;

               IF v_file_name_cnt >= 1
               THEN
                  fnd_file.put_line (fnd_file.LOG,
                                        'There exists "'
                                     || l_filename
                                     || '" already attached to the party - '
                                     || v_pty_nme
                                    );
               ELSE
                  fnd_file.put_line
                                (fnd_file.LOG,
                                    'Attaching PDF to the Party with Name - '
                                 || l_filename
                                );
                  fnd_file.put_line (fnd_file.LOG,
                                     'Attachment Process Started '
                                    );

-- Creating Document Ids
                  SELECT fnd_documents_s.NEXTVAL
                    INTO l_document_id
                    FROM DUAL;

                  SELECT fnd_documents_s.CURRVAL
                    INTO l_document_tl_id
                    FROM DUAL;

                  SELECT fnd_attached_documents_s.NEXTVAL
                    INTO l_attached_document_id
                    FROM DUAL;

-- Seq Num
                  SELECT NVL (MAX (seq_num), 0) + 10
                    INTO l_seq_num
                    FROM fnd_attached_documents
                   WHERE pk1_value = v_pty_id AND entity_name = v_entity_name;

-- Get Data type id for Short Text types of attachments
                  SELECT datatype_id
                    INTO l_short_datatype_id
                    FROM apps.fnd_document_datatypes
                   WHERE NAME = 'FILE';

                  SELECT MAX (file_id) + 1
                    INTO l_media_id
                    FROM fnd_lobs;

                  SELECT SUBSTR (i.pdf_name, LENGTH (i.pdf_name) - 2)
                    INTO l_format
                    FROM DUAL;

                  -- Condition to get file_content_type
                  IF UPPER (l_format) = 'PDF'
                  THEN
                     l_file_content_type := 'application/pdf';
                  ELSIF UPPER (l_format) = 'XLS'
                  THEN
                     l_file_content_type := 'application/vnd.ms-excel';
                  ELSE
                     l_file_content_type := 'application/pdf';
                  END IF;

                  fnd_file.put_line (fnd_file.LOG,
                                        'File Content Type - '
                                     || l_file_content_type
                                    );

                  -- Fetching the concurrent program details
                  SELECT   MAX (request_id), concurrent_program_id
                      INTO v_conc_req_id, l_concurrent_program_id
                      FROM fnd_concurrent_requests
                     WHERE concurrent_program_id =
                              (SELECT concurrent_program_id
                                 FROM fnd_concurrent_programs_vl
                                WHERE user_concurrent_program_name LIKE
                                         'W9 Party Pdf Attachment Program')
                  GROUP BY concurrent_program_id;

                  SELECT SUBSTR (user_concurrent_program_name, 1, 75),
                         application_id, last_update_date
                    INTO l_description,
                         l_application_id, l_last_update_date
                    FROM fnd_concurrent_programs_vl
                   WHERE concurrent_program_id = l_concurrent_program_id;

                  l_description := 'W9 - ' || v_pty_nme;
                  l_title := 'W9 - ' || v_pty_nme;
                  fnd_file.put_line (fnd_file.LOG,
                                     'Description - ' || l_description
                                    );
                  fnd_file.put_line (fnd_file.LOG, 'Title - ' || l_title);
                  l_dir_name := 'FILES_ATTACH_DIR';  -- Directory from which files to be read and attached
                  fnd_file.put_line (fnd_file.LOG,
                                     '==========File...==========='
                                    );
-- Reading and verifying the file across directory
--   fils := BFILENAME (l_dir_name, l_filename);
                  fils := BFILENAME (l_dir_name, l_filename);
                  file_exists := DBMS_LOB.fileexists (fils) = 1;

                  IF file_exists
                  THEN
-- Obtain the size of the blob file
                     DBMS_LOB.fileopen (fils, DBMS_LOB.file_readonly);
                     blob_length := DBMS_LOB.getlength (fils);
                     DBMS_LOB.fileclose (fils);
                     fnd_file.put_line
                               (fnd_file.LOG,
                                '=========File read completed....==========='
                               );

-- Insert a new record into the table containing the
-- filename you have specified and a LOB LOCATOR.
-- Return the LOB LOCATOR and assign it to x_blob.
                     INSERT INTO fnd_lobs
                                 (file_id, file_name,
                                  file_content_type, upload_date,
                                  expiration_date, program_name, program_tag,
                                  file_data, LANGUAGE, oracle_charset,
                                  file_format
                                 )
                          VALUES (l_media_id, l_filename,
                                  l_file_content_type, SYSDATE,
                                  NULL, 'FNDATTCH', NULL,
                                  EMPTY_BLOB (), 'US', 'UTF8',
                                  'binary'
                                 )
                       RETURNING file_data
                            INTO x_blob;

                     fnd_file.put_line
                        (fnd_file.LOG,
                         '==========Record inserted in fnd_lob table....==========='
                        );
-- Load the file into the database as a BLOB
                     DBMS_LOB.OPEN (fils, DBMS_LOB.lob_readonly);
                     DBMS_LOB.OPEN (x_blob, DBMS_LOB.lob_readwrite);
                     DBMS_LOB.loadfromfile (x_blob, fils, blob_length);
-- Close handles to blob and file
                     DBMS_LOB.CLOSE (x_blob);
                     DBMS_LOB.CLOSE (fils);
                     --fnd_file.put_line(fnd_file.LOG,'FND_LOBS Created with media_id - ' || l_media_id);
                     COMMIT;

-- This package allows user to share file across multiple orgs or restrict to single org
                     BEGIN
                        fnd_documents_pkg.insert_row
                           (x_rowid                       => l_rowid,
                            x_document_id                 => l_document_id,
                            x_creation_date               => SYSDATE,
                            x_created_by                  => l_fnd_user_id,
                            x_last_update_date            => SYSDATE,
                            x_last_updated_by             => l_fnd_user_id,
                            x_last_update_login           => fnd_profile.VALUE
                                                                   ('LOGIN_ID'),
                            x_datatype_id                 => l_short_datatype_id,
                            x_security_id                 => NULL,
                            x_publish_flag                => 'Y',
                            --This flag allow the file to share across multiple organization
                            x_category_id                 => l_category_id,
                            x_security_type               => 4,
                            x_usage_type                  => 'O',
                            x_language                    => 'US',
                            x_request_id                  => v_conc_req_id,
                            x_program_application_id      => l_application_id,
                            x_program_id                  => l_concurrent_program_id,
                            x_program_update_date         => l_last_update_date,
                            x_description                 => l_description,
                            x_file_name                   => l_filename,
                            x_media_id                    => l_media_id,
                            x_title                       => l_title
                           );
                        COMMIT;
                     EXCEPTION
                        WHEN OTHERS
                        THEN
                           fnd_file.put_line
                              (fnd_file.LOG,
                                  'Error while inserting in fnd_documents table and fnd_documents_tl table - '
                               || SQLERRM
                              );
                     END;

                     fnd_file.put_line
                        (fnd_file.LOG,
                         '==========Record inserted in fnd_documents table and fnd_documents_tl table....==========='
                        );

                     BEGIN
                        fnd_attached_documents_pkg.insert_row
                           (x_rowid                         => l_rowid,
                            x_attached_document_id          => l_attached_document_id,
                            x_document_id                   => l_document_id,
                            x_creation_date                 => SYSDATE,
                            x_created_by                    => l_fnd_user_id,
                            x_last_update_date              => SYSDATE,
                            x_last_updated_by               => l_fnd_user_id,
                            x_last_update_login             => fnd_profile.VALUE
                                                                   ('LOGIN_ID'),
                            x_seq_num                       => l_seq_num,
                            x_entity_name                   => v_entity_name,
                            x_column1                       => NULL,
                            x_pk1_value                     => v_pty_id,
                            x_pk2_value                     => v_pk2_val,
                            x_pk3_value                     => v_pk3_val,
                            x_pk4_value                     => v_pk4_val,
                            x_pk5_value                     => v_pk5_val,
                            x_automatically_added_flag      => 'Y',
                            x_datatype_id                   => l_short_datatype_id,
                            x_category_id                   => l_category_id,
                            x_security_type                 => 4,
                            x_security_id                   => NULL,
                            x_publish_flag                  => 'Y',
                            x_language                      => 'US',
                            x_request_id                    => v_conc_req_id,
                            x_program_application_id        => l_application_id,
                            x_program_id                    => l_concurrent_program_id,
                            x_program_update_date           => l_last_update_date,
                            x_description                   => l_description,
                            x_file_name                     => l_filename,
                            x_media_id                      => l_media_id,
                            x_title                         => l_title
                           );
                        COMMIT;
                     EXCEPTION
                        WHEN OTHERS
                        THEN
                           fnd_file.put_line
                              (fnd_file.LOG,
                                  'Error while inserting in fnd_attached_documents table, fnd_documents table and fnd_documents_tl table - '
                               || SQLERRM
                              );
                     END;

                     fnd_file.put_line
                        (fnd_file.LOG,
                         '==========Record inserted in fnd_attached_documents table, fnd_documents table and fnd_documents_tl table....==========='
                        );

-- Updating status as PDF attachment is completed
                     UPDATE Stag_w9_party_det
                        SET status = 'COMPLETED',
                            status_msg = 'PDFs Attached successfully'
                      WHERE party_name = i.party_name
                        AND party_number = i.party_number
                        AND tax_payer_id = i.tax_payer_id
                        AND pdf_name = l_filename;

                     fnd_file.put_line
                                   (fnd_file.output,
                                       'PDF Successfully attached to party - '
                                    || i.party_name
                                   );
                     COMMIT;
                  ELSE
                     UPDATE Stag_w9_party_det
                        SET status = 'ERROR',
                            status_msg = 'PDF doesn''t exist in directory'
                      WHERE party_name = i.party_name
                        AND party_number = i.party_number
                        AND tax_payer_id = i.tax_payer_id
                        AND pdf_name = l_filename;

                     fnd_file.put_line (fnd_file.LOG,
                                           l_filename
                                        || ' does not exist in directory'
                                       );
                     COMMIT;
                  END IF;
               END IF;
            END LOOP;
         END LOOP;
      END IF;
   END LOOP;
EXCEPTION
   WHEN OTHERS
   THEN
      fnd_file.put_line
                   (fnd_file.LOG,
                       'Error while processing the attachment process - Main'
                    || SQLERRM
                   );
END;
/

No comments:

Post a Comment