none
Suche Hilfe zur Lösung dieses Problems: "Subquery returned more than 1 value. This is not permitted when the subquery follows =, !=, <, <= , >, >= or when the subquery is used as an expression" RRS feed

  • Frage

  • Hallo zusammen,

    hoffentlich kann mir jemand dabei helfen. Es geht um eine Stored Procedure, die nicht nur die Anzahl von Opportunities mit Status "Pending" oder "Accepted" sondern auch die Namen der Opportunities mit diesen Stati ausgeben sollte. Folgende Probleme:

    1. Der SELECT, der mir die Namen der Opportunities ausgibt, kann mir aber in manchen Faellen mehr als einen Wert ausgeben. Ich kann aber den SELECT nicht einer Variable zuweisen, z.B. mi SET, wie kann ich das in dem Code anders zuweisen oder wie kann man den Code abändern in dem Fall?

    2. Der Code müsste auch die Namen der Opportunities ausgeben, naemlich nach "Die Opportunities sind:" und diese dem Empfaenger einer Email zugeschickt werden. Wie kann ich aber das so darstellen, so dass diese Opportunities Zeile fuer Zeile ausgegeben werden und nicht alles in einer Zeile, damit diese Ergebnisse dann per Email zugeschickt werden können?

    Es wuerde mich sehr freuen, wenn mir ein Specialist in Stored Procedures mit SQL Server dabei hilft, da ich schon längst versuche, diese Probleme zu lösen. Folgendes ist der Code:

    CREATE PROCEDURE [dbo].[Pending_Opportunities] 
    AS 
    
    
    BEGIN  
    
    declare @V_USER VARCHAR(20),    
    	@V_NAME VARCHAR(100),
        @V_OPP_NAME VARCHAR(100),    
    	@V_ANZAHL INT,    
    	@V_EMAIL VARCHAR(60),       
    	@V_BODY VARCHAR(MAX),    
    	@V_ANZAHL_AKTIV int
    
    DECLARE CUR CURSOR FOR  
    SELECT USER, COMPLETEDNAME, EMAILDIRECTION  FROM USER_SIEBEL  WHERE STATE = 'G'   
    
    OPEN CUR  FETCH NEXT FROM CUR INTO @V_USER, @V_NAME, @V_EMAIL   
    WHILE @@FETCH_STATUS = 0  
    
    BEGIN    
    
       
    SET @V_OPP_NAME = (	SELECT  T1.NAME FROM dbo.S_OPTY T1         
    			INNER JOIN dbo.S_OPTY_POSTN T2 ON T1.PR_POSTN_ID = T2.POSITION_ID AND T1.ROW_ID = T2.OPTY_ID        
    			INNER JOIN dbo.S_OPTY_BU T3 ON T3.BU_ID = '1-O5H' AND T1.ROW_ID = T3.OPTY_ID        
    			INNER JOIN dbo.S_PARTY T4 ON T2.POSITION_ID = T4.ROW_ID        
    			INNER JOIN dbo.S_PARTY T5 ON T3.BU_ID = T5.ROW_ID        
    			LEFT OUTER JOIN dbo.S_USER T6 ON T1.CREATED_BY = T6.PAR_ROW_ID    
           		LEFT OUTER JOIN dbo.S_SYS_KEYMAP T7 ON T1.ROW_ID = T7.SIEBEL_SYS_KEY        
    			LEFT OUTER JOIN dbo.S_OPTY T8 ON T1.PAR_OPTY_ID = T8.ROW_ID        
    			LEFT OUTER JOIN dbo.S_ADDR_ORG T9 ON T1.PR_OU_ADDR_ID = T9.ROW_ID        
    			LEFT OUTER JOIN dbo.S_ORG_EXT T10 ON T1.PR_DEPT_OU_ID = T10.PAR_ROW_ID        
    			LEFT OUTER JOIN dbo.S_POSTN T11 ON T1.PR_POSTN_ID = T11.PAR_ROW_ID        
    			LEFT OUTER JOIN dbo.S_PRI_LST T12 ON T10.CURR_PRI_LST_ID = T12.ROW_ID        
    			LEFT OUTER JOIN dbo.S_USER T13 ON T11.PR_EMP_ID = T13.PAR_ROW_ID       
    			WHERE  T1.STATUS_CD in ( 'Pending' , 'Accepted')     
    			--AND T13.LOGIN = @V_USER     
    			AND (T13.LOGIN in (@V_USER) )
                --OR (T6.LOGIN in (@V_USER)) )
    			AND T1.SUM_EFFECTIVE_DT <= GETDATE()      
    			AND T1.SUM_EFFECTIVE_DT >= '20100601' )
    
    
    SET @V_ANZAHL = 0   
    SET @V_ANZAHL_AKTIV = 0   
    SET @V_ANZAHL = (	SELECT  COUNT(*) FROM dbo.S_OPTY T1         
    			INNER JOIN dbo.S_OPTY_POSTN T2 ON T1.PR_POSTN_ID = T2.POSITION_ID AND T1.ROW_ID = T2.OPTY_ID        
    			INNER JOIN dbo.S_OPTY_BU T3 ON T3.BU_ID = '1-O7F' AND T1.ROW_ID = T3.OPTY_ID        
    			INNER JOIN dbo.S_PARTY T4 ON T2.POSITION_ID = T4.ROW_ID        
    			INNER JOIN dbo.S_PARTY T5 ON T3.BU_ID = T5.ROW_ID        
    			LEFT OUTER JOIN dbo.S_USER T6 ON T1.CREATED_BY = T6.PAR_ROW_ID    
           		LEFT OUTER JOIN dbo.S_SYS_KEYMAP T7 ON T1.ROW_ID = T7.SIEBEL_SYS_KEY        
    			LEFT OUTER JOIN dbo.S_OPTY T8 ON T1.PAR_OPTY_ID = T8.ROW_ID        
    			LEFT OUTER JOIN dbo.S_ADDR_ORG T9 ON T1.PR_OU_ADDR_ID = T9.ROW_ID        
    			LEFT OUTER JOIN dbo.S_ORG_EXT T10 ON T1.PR_DEPT_OU_ID = T10.PAR_ROW_ID        
    			LEFT OUTER JOIN dbo.S_POSTN T11 ON T1.PR_POSTN_ID = T11.PAR_ROW_ID        
    			LEFT OUTER JOIN dbo.S_PRI_LST T12 ON T10.CURR_PRI_LST_ID = T12.ROW_ID        
    			LEFT OUTER JOIN dbo.S_USER T13 ON T11.PR_EMP_ID = T13.PAR_ROW_ID       
    			WHERE  T1.STATUS_CD in ( 'Pending' , 'Accepted')     
    			--AND T13.LOGIN = @V_USER     
    			AND (T13.LOGIN in (@V_USER) )
                --OR (T6.LOGIN in (@V_USER)) )
    			AND T1.SUM_EFFECTIVE_DT <= GETDATE()      
    			AND T1.SUM_EFFECTIVE_DT >= '20100601' )    
    
    			
    SET @V_ANZAHL_AKTIV = ( 	SELECT COUNT(*)            
    				FROM dbo.S_EVT_ACT T1          
    				WHERE (		(T1.APPT_REPT_REPL_CD IS NULL)          
    						AND (T1.TEMPLATE_FLG != 'Y' AND T1.TEMPLATE_FLG != 'P' OR T1.TEMPLATE_FLG IS NULL)          
    						AND (T1.PRIV_FLG = 'N' OR T1.PRIV_FLG IS NULL OR T1.OWNER_PER_ID = '1-ONG')
    				      )          
    				AND T1.TODO_PLAN_START_DT <=  getdate()  
    				AND T1.TODO_PLAN_START_DT >=  '20100601'  
            			AND T1.EVT_STAT_CD IN ('Pending','Programmed')          
    				AND T1.TODO_CD != 'Erinnerung'          
    				AND T1.TODO_CD != 'Task'         
    				AND T1.OPTY_ID is not null        
    				AND T1.NAME NOT LIKE '%hat Ihnen zu einer Opportunity eingeladen:%'         
    				AND T1.OWNER_LOGIN = @V_USER )    
    
    
    if @V_ANZAHL + @V_ANZAHL_AKTIV > 0   
    begin    
    
    	SET @V_BODY = '<BODY style="color:navy; font-size:10pt; font-family:verdana">'    
    	SET @V_BODY = @V_BODY + 'Sehr geehrte(r) ' + @V_USER + ',<br>'
    	SET @V_BODY = @V_BODY + 'Sie haben '     IF @V_ANZAHL > 0  
    
    	BEGIN     SET @V_BODY = @V_BODY + cast(@V_ANZAHL as varchar) + ' Opportunities mit Status Pending'         
    	SET @V_BODY = @V_BODY + '<br>Die Opportunities sind:<br>'
        SET @V_BODY = @V_BODY + '<BR>'	
    	SET @V_BODY = @V_BODY + @V_OPP_NAME
    
    	IF @V_ANZAHL_AKTIV > 0      
    		SET @V_BODY = @V_BODY + ' und '    
    	END    
    
    IF @V_ANZAHL_AKTIV > 0    
    BEGIN     
    	SET @V_BODY = @V_BODY + cast(@V_ANZAHL_AKTIV as varchar) + ' Activities mit Status Pending/Programmed' END  
    	SET @V_BODY = @V_BODY + '<BR>'    
    
    </BODY>'     
    
    exec msdb..sp_send_dbmail @profile_name = 'Siebel Administrator',
         @recipients = @V_EMAIL,  
         @subject = 'SIEBEL Email zur Verfolgung der Opportunities / Activities',  
         @body = @V_BODY,  
         @body_format = 'HTML',  
         @exclude_query_output = 1 
    end 
    
    
    FETCH NEXT FROM CUR INTO @V_USER, @V_NAME, @V_EMAIL  
    END   
    CLOSE CUR  
    DEALLOCATE CUR  END

    Mittwoch, 19. November 2014 03:52

Alle Antworten

  • Hallo,

    wenn der Ausdruck mehrere Werte liefern kann, kannst Du eine Liste mit XML PATH erzeugen, siehe dazu u. a.:

    How to assign the result of 'FOR XML PATH' to a variable? Impossible?

    Die Beispiele verwenden ein Komma, damit Du in HTML einen Zeilenumbruch bekommst, verwende anstatt dessen '<br>'.

    Das Ermitteln der V_ANZAHL über die identische Abfrage könnte entfallen; es sollte schneller sein, die Rückgabe auszuwerten.

    Gruß Elmar

    Mittwoch, 19. November 2014 05:21
  • Danke für die Antwort. V_ANZAHL müsste auch dabei sein, weil das Ergebnis, das aus dieser Variable rauskommt, sollte Teil der Ausgabe in @body sein und dieses auch dem Kunden / User zugeschickt werden.
    Donnerstag, 20. November 2014 02:29