[NEWSboard IBMi Forum]
  1. #1
    Registriert seit
    Dec 2009
    Beiträge
    314

    SQL - Verständnisfrage

    Hallo Leute,

    folgendes Phänomen tritt bei mir auf (V7R3):

    update lea/leap1 p1 set (p1.loschkz,
    p1.suchname, p1.name1, p1.name2,)=
    (select 'X',
    (case when p1.suchname is not null then
    TRANSLATE ( CHAR(BIGINT(RAND() * 1000000000000000)),
    'abcdefgHijklmnoPqrstuv', '1234567890' )
    else ' '
    end),
    (case when p1.name1 is not null then
    TRANSLATE ( CHAR(BIGINT(RAND() * 1000000000000000)),
    'abcdefgHijklmnoPqrstuv', '1234567890' )
    else ' '
    end),
    (case when p1.name2 is not null then
    TRANSLATE ( CHAR(BIGINT(RAND() * 1000000000000000)),
    'abcdefgHijklmnoPqrstuv', '1234567890' )
    else ' '
    end)

    where partnernr = 1234567

    Durchgeführt im STRSQL funktioniert es tadellos

    Wenn ich das mit RUNSQLSTM oder als Procedure laufen lasse, bringt mir das System 30 1 Position 1 Nullwerte für Spalte oder Variable P1_SUCHNAME nicht zulässig.


    Ich habe keine Ahnung warum oder übersehe ich schon wieder etwas. Vor allem in einer anderen Procedure funktioniert das tadellos.

    Bitte um Hilfe

    Gruß

    Nico
    Andreas
    Ein AS/400 Dinosaurier since 1989

  2. #2
    Registriert seit
    Feb 2001
    Beiträge
    20.207
    Wie der Fehler schon sagt:
    Der inner Select findet auf Grund der Whereklausel u.U. keine Daten und deine Zielvariablen erlauben kein NULL.
    Nun ist es leider so, dass der Optimizer im Dialog (STRSQL) anders arbeitet als im embedded.
    Zusätzlich ist es wohl auch so, dass eben ein Subselect NULL bringen kann, auch wenn er es nachher dann doch nicht tut, was der Optimizer wohl mal wieder vorher prüft.

    Vervollständige einfach den SQL mit einer Where-Klausel auf dem Update:

    update table
    set ... = (select ... where ...)
    where ...
    Dienstleistungen? Die gibt es hier: http://www.fuerchau.de
    Das Excel-AddIn: https://www.ftsolutions.de/index.php/downloads
    BI? Da war doch noch was: http://www.ftsolutions.de

  3. #3
    Registriert seit
    Dec 2009
    Beiträge
    314
    okay dann mach ich mich mal an den umbau, wobei im Moment ist mir nicht klar warum das nicht funktioniert. aber das ist wieder viel Schreibarbeit

    ich habe bei diesem Projekt aber noch ein 2. Ding was mich zum verzweifeln bringt:


    -- Trigger-Programm für die Löschung lt. DSGVO ruft
    -- DSGVOPROCA auf und führt die Löschung durch
    ------------------------------------------------------------------------------
    --
    CREATE or REPLACE TRIGGER lea/dsgvotrgu
    AFTER UPDATE of DSG1_VERARB_KZ
    on lea/leadsg1
    REFERENCING NEW AS NEW_ROW OLD AS OLD_ROW
    FOR EACH ROW MODE DB2ROW
    SET OPTION DBGVIEW = *SOURCE
    WHEN (NEW_ROW.DSG1_VERARB_KZ = 'L')
    BEGIN Atomic
    ------------------------------------------------------------------------------
    -- Cursor Deklarationen
    ------------------------------------------------------------------------------
    ------------------------------------------------------------------------------
    -- Allgemeine Deklarationen
    ------------------------------------------------------------------------------
    declare leadsg_dsgsatznrc char(9) default ' ';
    declare leadsg_dsgmsg char(5) default ' ';
    declare leadsg_rownumc char(6) default ' ';
    declare cmdline varchar(2000);
    declare cmdline1 varchar(2000);
    declare cmdlinesbm varchar(11);
    declare cmdlinecall varchar(21);
    declare cmdlineparm varchar(48);
    declare cmdlen integer;
    declare cmdlenp decimal(15, 5);
    declare leadsg_found char(1);
    declare leadsg_partnernrc char(9);

    ------------------------------------------------------------------------------
    -- Exception Handler
    ------------------------------------------------------------------------------

    -------------------------------------------------------------------------------
    -- OPEN-Cursor
    -------------------------------------------------------------------------------
    -------------------------------------------------------------------------------
    -- Start des Aufrufs
    -------------------------------------------------------------------------------
    -- Den Schritt würde ich gerne submitten weil sonst ist der Schirm zu lange
    -- blockiert und des macht kan guten Eindruck
    SET leadsg_dsgsatznrc = digits(NEW_ROW.DSG1_SATZ_NR);
    CALL LEA/DSGVOPROCA(leadsg_dsgsatznrc, leadsg_dsgmsg, leadsg_rownumc);
    -- SET leadsg_dsgsatznrc = digits(NEW_ROW.DSG1_SATZ_NR);
    -- SET cmdlinesbm = 'SBMJOB CMD(';
    -- SET cmdlinecall = 'CALL LEA/DSGVOPROCA (';
    -- SET cmdlineparm = 'leadsg_dsgsatznrc leadsg_dsgmsg leadsg_rownumc))';
    -- SET cmdline = cmdlinesbm || cmdlinecall || cmdlineparm;

    -- SET cmdlen = length(cmdline);
    -- SET cmdlenp = cmdlen;
    -- Der Aufruf stürzt mit MCH3601 ab???????
    -- blockiert und des macht kan guten Eindruck
    -- CALL QCMDEXC(cmdline, cmdlenp);
    END;
    --
    --
    -- E n d o f S t a t e m e n t

    Das ruft mir dann die Procedure auf, wo dann oben beschriebener Fehler aufgetreten ist. DSGVO lässt Grüßen
    Andreas
    Ein AS/400 Dinosaurier since 1989

  4. #4
    Registriert seit
    Feb 2001
    Beiträge
    20.207
    Für solche Dinge eignen sich asynchrone Verfahren ganz gut.
    Erstelle eine DTAQ und eine Prestart-Job, der per QRCVDTAQ wartet.
    Im SQL-Trigger rufst du einen Wrapper auf, der ein Kennzeichen (Dateiname, Id, ...) in die DTAQ sendet.
    Der Trigger ist dann bereits fertig.

    Das Batchprogramm reagiert dann auf den QRCVDTAQ und kann nun in aller Ruhe alle Sätze bearbeiten, die fällig sind (DSG1_VERARB_KZ).
    Anschließend legt es sich wieder schlafen bis zur nächsten Anforderung.
    Sollte es in der DTAQ zu einem Überhang kommen (s.o. alle Sätze je RCV), passiert ja nichts da keine Daten zur Verarbeitung mehr vorliegen.

    Vorteil:
    Separat testbar, keine 1000de neuen Jobs die dann ggf. noch warten, ...
    Bei einem anderen Projekt hatten wir einen kleinen Test mit dieser Methode gemacht.
    Die eigentlich Laufzeit je Job betrug knapp 1 Sekunde, allerdings das Submitten/Starten/Beenden der Jobs lag zusätzlich bei 3-5 Sekunden. Bei ca. 100.000 Jobs/Tag eine nicht unerhebliche Einsparung.
    Dienstleistungen? Die gibt es hier: http://www.fuerchau.de
    Das Excel-AddIn: https://www.ftsolutions.de/index.php/downloads
    BI? Da war doch noch was: http://www.ftsolutions.de

  5. #5
    Registriert seit
    Dec 2009
    Beiträge
    314
    Danke, das war mein Fehler wieder einmal. Da hab ich zu kurz gedacht, weil die andere Procedure ja tadellos funktioniert hat. Aber da bekomme ich die Daten nicht über eine Datei sondern mache den Update auf Grund eines Kennzeichens im LEAP1.
    Zitat Zitat von Fuerchau Beitrag anzeigen
    Wie der Fehler schon sagt:
    Der inner Select findet auf Grund der Whereklausel u.U. keine Daten und deine Zielvariablen erlauben kein NULL.
    Nun ist es leider so, dass der Optimizer im Dialog (STRSQL) anders arbeitet als im embedded.
    Zusätzlich ist es wohl auch so, dass eben ein Subselect NULL bringen kann, auch wenn er es nachher dann doch nicht tut, was der Optimizer wohl mal wieder vorher prüft.

    Vervollständige einfach den SQL mit einer Where-Klausel auf dem Update:

    update table
    set ... = (select ... where ...)
    where ...
    Andreas
    Ein AS/400 Dinosaurier since 1989

Berechtigungen

  • Neue Themen erstellen: Nein
  • Themen beantworten: Nein
  • You may not post attachments
  • You may not edit your posts
  •