Search code examples
vbscriptparameter-passingevalqtpexecute

Pass a string as a variable name QTP


I have a function that does the same operation for all of my scripts, but only the variable in which the Pass-Fail value is stored, would change. For example, in one script -> the status is stored in Envrionment.Value("Current_Status") in another script -> the status is stored in DataTable.Value("Status",1) in another script -> the status is stored in objRS("AddCriteria_Status").Value

So i am trying to make a function in which i pass on these parameters as strings and then later use them as variable names. Here is the sample code:

Envrionment.Value("Current_Status") = "none"
Environment.Value("Fail_text") = "none"
Call AddCriteria("Environment.Value(""Current_Status"")","Environment.Value(""Fail_text"")")

Pubic Function AddCriteria(varStatus,varActual)

varTemp = ""

Execute(varStatus+ "=InProgress")    'change status to InProgress by the time execution is done
Execute(varActual + "=not_defined")   'this will have the reason the case failed

....code

If varTemp = "FAIL" Then
 Execute(varStatus+ "=PASS")
 Execute(varActual + "=PASS")
Else
 Execute(varStatus+ "=FAIL")
 Execute(varActual + "=Criteria did not get added")
End If

End Function

On calling the sub-routine i want the value of Environment.Value("Current_Status") to change from "none" to "InProgress" and then to "PASS" But after the "Execute" command is executed, the Environment variable become empty.

Since CVar is not supported in VBScript, i cannot use it.

I tried Eval, but it doesn't work in the other direction i.e.: If you change the value of Environment.Value("Current_Status"), then the value Eval(varStatus) changes, but I could not find a way to change the value of Eval(varStatus) so that the value of Environment.Value("Current_Status") changes.

Please help out. I am stuck at this for a week.

!!!What I'm trying to accomplish!!!

In a .vbs file, pass on any string to a function as a parameter; and convert it into a variable name in that function. Simple example: pass a string "abc" as a parameter to a function -> and within that function, convert the string to a variable name to store value [say, abc = "PASS"]

!!!How I attempt to do it!!!

I tried using Execute command as that is a solution that I got from a previous post [vbscript Eval a string to a Variable in a loop?

Using "CVar" is a way but that is not supported in VBScript. So I ran out of ideas

!!!Problems that I faced!!!

Honestly, I didn't understand the logic of using "Execute", but i tried it nevertheless. Sadly, it didn't work out. When using execute command (as mentioned in the code), the environment variables become empty.


Solution

  • Ideas:

    • Use ExecuteGlobal to execute the assignment you want to execute -- if that´s what you want. Eval and especially Execute have subtle limitations regarding the scope they live in.

    • The target variable (i.e. the variable that receives a value in the assignment that is evaluated by ExecuteGlobal) must be a global variable.

    • If the ExecuteGlobal call happens on an Action's global scope, the target variable must be declared there, too. (I think.)

    • If the ExecuteGlobal call happens in a routine in a function library, the target variable must be declared there, too. (I know that for sure. But read on.)

    To further help you, I'd need an update on your question because it is not clear what you want to accomplish, and what problems you see. Because -- Eval does not change values, it just evaluates an expression supplied as a string, and returns its value. If the expression has side-effects, like setting a global variable, then you might be out of luck because...well...it depends on where that global variable is declared, and initialized (if at all), and where the ExecuteGlobal call happens. Actions and libraries do NOT share one global scope, even if it looks like they do, and that can create a lot of strange behavior.

    But as I said, if you clarify what you are trying to accomplish (got 90% of that), how you attempt to do it (got 40% of it), and what problems you face (got 10% of it), I´m sure I can update this answer so it approaches a solution.

    ** Update **

    I use this library code for all runtime expression evaluation, be it from within a library or Action:

    ' Interpret (execute) a piece of VSH source code consisting of statements -- success?
    '   Code: String containing VBS source code. Passed by reference for performance reasons only
    Public Function ExecCode (ByRef Code)
        Dim ErrNumber
        Dim ErrDescription
    
        On error resume next ' Avoid getting kicked out by errors in the code contained in Code
        ExecuteGlobal Code
        ErrNumber=Err.Number
        ErrDescription=Err.Description
        On error goto 0 ' Re-enable RTE handling
    
        If ErrNumber <> 0 Then
            ExecCode=false
    
            Print "Code execution failed ('" & ErrDescription & "'), code:" & vbNewline & Code & "<eof>"
        else
            ExecCode=true
        End If
    End Function
    
    Dim GlobalVar
    
    ' Interpret (execute) a piece of VSH source code consisting of a single expression -- success?
    '   Expr; String containing a VBS expression. Passed by reference for performance reasons only.
    '   Target: Variable receiving the value to which the expression evaluates
    Public Function EvalCodeAndAssign (ByRef Expr, ByRef Target)
    
        ' In order to force "Option explicit", we don´t use Eval, but ExecCode (and thus ExecuteGlobal):
        Dim Code: Code="Option Explicit: GlobalVar=(" & Expr & ")"
        Dim Result: Result=ExecCode (Code)
        If Result Then
            Target=GlobalVar
        End If
        EvalCodeAndAssign=Result
    
    End Function
    

    Update 2: if the statement that you pass to ExecuteGlobal contains quotes (which I think are missing in your code), the must be quoted, I.e. you must use double-quotes, like in

    ExecuteGlobal "x=""This is a string"""
    

    Because what ExecuteGlobal/Execute/Eval do is: take a string and interpret it as VBScript code. The code you are trying to use is not valid due to missing quotes.