sqlsql-serverhistorian

SQL Historian Query not returning all results


I am using an historian to search for certain values of a specific tag. The historian has certain rules, such as, I cannot create or drop tables, queries need tagnames etc.

I want to search a TagName 'Tank1' for example and return its DateTime and Value results, then search further Tags using these results to match those tags that have the same Values at that DateTime.

I search 'Tank1' between a given date and time and receive 4 results as below

2021-11-02 08:00:54.9870000 1
2021-11-02 10:22:27.9850000 1
2021-11-02 11:47:31.3360000 2
2021-11-02 23:11:57.8120000 2

So, I need to search four other Tags and return results that match the dateTime and value.

The below code is what I have produced (I should now tell you that I am a virtual novice)

DECLARE @AT1Value INT,
        @AT1DateTime DateTime
SELECT  @AT1Value = Value,                              --GETS THE VALUES OF AT1 STERILISER
        @AT1DateTime = DateTime                         --GETS THE DATETIME OF AT1 STERILISER VALUES
From Runtime.dbo.v_History
Where 
    Runtime.dbo.v_History.Tagname = 'AT1_Select_ster'
AND Runtime.dbo.v_History.DateTime >= '2021-11-02 08:00'
AND Runtime.dbo.v_History.DateTime <= '2021-11-03 08:01'
AND Runtime.dbo.v_History.Value > 0


Select  a.DateTime,
        a.TagName,
        a.Value
From Runtime.dbo.v_History AS a        --GETS  THE VALUES OF THE FM TAGS AT THE DATETIME OF AT1 STERILISER VALUES
Where  
    ((a.TagName = 'FM_S1_Batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime)
OR  (a.Tagname = 'FM_S2_batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime)
OR  (a.Tagname = 'FM_S3_batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime)
OR  (a.Tagname = 'FM_S4_batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime))
AND a.Value > 0

This works fine, albeit it only produces the last dateTime and Value result below,

2021-11-02 23:11:57.8120000 FM_S2_batch 2

Am I right in assuming this is because the Variable is being overwritten each time and only holding the last values?

The results that should be returned should look something like the results below

2021-11-02 08:00:54.9870000 FM_S1_batch 1
2021-11-02 10:22:27.9850000 FM_S1_batch 1
2021-11-02 11:47:31.3360000 FM_S2_batch 2
2021-11-02 23:11:57.8120000 FM_S2_batch 2

Is there anyway I can do several scans and save each result until I have all the results needed? or is there an easier more suitable method (which I am guessing there is).

TIA


Solution

  • Thanks to everyone who took the time to reply to my problem. I finally got it working using a cursor thanks to @EdmCoff for suggesting trying a for-loop or a cursor.

    The for-loop returned the last value 4 times so I tried the cursor and it worked for me.

    I have posted the code that works for me below

    DECLARE @AT1Value INT,
            @AT1DateTime DateTime
            
    DECLARE cursor_result CURSOR                                
    
    FOR SELECT  Runtime.dbo.v_History.Value,                    
            Runtime.dbo.v_History.DateTime                      
    From Runtime.dbo.v_History
    Where 
        Runtime.dbo.v_History.Tagname = 'AT1_Select_ster'
    AND Runtime.dbo.v_History.DateTime >= '2021-11-02 08:00'
    AND Runtime.dbo.v_History.DateTime <= '2021-11-04 08:01'
    AND Runtime.dbo.v_History.Value > 0
    
    OPEN cursor_result                                          
    FETCH NEXT FROM cursor_result INTO                          
        @AT1Value,
        @AT1DateTime
    
    WHILE @@FETCH_STATUS = 0                                    
    Select  a.DateTime,
            a.TagName,
            a.Value
    From Runtime.dbo.v_History AS a                             
    Where  
        ((a.TagName = 'FM_S1_Batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime)
    OR  (a.Tagname = 'FM_S2_batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime)
    OR  (a.Tagname = 'FM_S3_batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime)
    OR  (a.Tagname = 'FM_S4_batch' AND a.Value = @AT1Value AND a.DateTime = @AT1DateTime))
    AND a.Value > 0
    FETCH NEXT FROM cursor_result INTO                                      
    @AT1Value,
    @AT1DateTime
    END
    CLOSE cursor_result                                         
    DEALLOCATE cursor_result