Converting Scripts From One Scripting Language To Another

Applies to TestComplete 14.61, last modified on April 22, 2021

TestComplete supports multiple scripting languages: JavaScript, Python, VBScript, DelphiScript, and others. In some case, you may need to convert script code from one language to another. Typically, this is not the code samples from TestComplete documentation, as it includes examples in all the supported languages. Usually, this happens when you find some third-party code that does what you need, but is written in a scripting language other than the one that your test project uses.

Modern programming and testing tools (including TestComplete) don’t convert scripts automatically, you have to do this manually.

Different scripting languages have similar code structures, but declare and implement them in slightly different manners. Below are equivalents of code structures used in the scripting languages that TestComplete supports. Use this list as a hint to convert scripts faster.

Tip: C#Script, C++Script and JScript (not JavaScript), use the same scripting engine, so there is no need to convert script code from one of these languages to another. You can use JScript code with no changes in C#Script and C++Script projects, and vice versa.

Brief overview

The table below lists sample scripting statements that demonstrate syntactic differences between the scripting languages.

Case sensitivity

Sensitive

Sensitive

Procedure declaration

function MyProcedure()
{
  …
}

def MyProcedure():
  ...

Function declaration

function MyFunction()
{
  …
  return 0;
}

def MyFunction():
  ...
  return 0

Variable declaration

let x, y;
var x, y;

 

Constant declaration

const c = 45;

x = 0
y = 0

Boolean values

true false

True False

String literal

"String"
'String'

"String"
'String'
"""String"""

String concatenation

"Abra" + "cadabra"

"Abra" + "cadabra"

Comments

/* Multi-line
comment */

// Single-line comment

# Single-line comment

Assignment

x = 10;

x = 10

Object assignment

x = MyObject;

x = MyObject

Getting object property

x = obj.MyProperty;
x = obj.$get("MyProperty");

x = obj.MyProperty

Calling object method

x.MyMethod(Param1, Param2);
x.$call("MyMethod", Param1, Param2);

x.MyMethod(Param1, Param2)

Arithmetic operations

Addition

x + 5

x + 5

Subtraction

y - 9

y - 9

Multiplication

x * y

x * y

Division

x / 2

x / 2

Modulus arithmetic

x % 2

x % 2

Integer division

 

x // 3

Increment

i++
i = i+1

i += 1
i = i+1

Decrement

i- -
i = i-1

i -= 1
i = i-1

Exponentiation

Math.pow(x,3)

x ** 3

Comparison operators

Equality

x == 10

x == 10

Inequality

x != 0

x != 0

Less than

x < 17

x < 17

Greater than

x > 0

x > 0

Less than or equal to

x <= 5

x <= 5

Greater than or equal to

x >= 10

x >= 10

Test object equivalence

Obj1 == Obj2
equal(Obj1, Obj2)

Obj1 == Obj2

Logical operators

Logical negation

! x

not x

Logical conjunction

x && y

x and y

Logical disjunction

x || y

x or y

Logical exclusion

x ^ y

 

Bitwise operators

Bitwise negation

~ x

~ x

Bitwise conjunction

x & y

x & y

Bitwise disjunction

x | y

x | y

Bitwise exclusion

x ^ y

x ^ y

Bitwise left shift

x << y

x << y

Bitwise right shift

x >> y

x >> y

Conditionals

If statement

if (x == 10)
  Test1();
else
  Test2();

if x == 10:
  Test1()
else:
  Test2()

Switch/Select statement

switch (someChar)
{
  case "a": TestOnA(); break;
  case "z": TestOnZ(); break;
  default: TestOnElse();
}

if someChar == 'a':
  TestOnA()
elif someChar == 'z':
  TestOnZ()
else:
  TestOnElse()

Loops

For loop

for (let i = 0; i < 10; i++)
  Test1();

for i in range (0, 9):
  Test1()

While loop

while (i < 10)
  Test1();

while i < 10:
  Test1()

Do-While loop

do Test1(); while (i < 10)

while True:
  Test1()
  if i == 9:
    break

Enumerator loops

for i of object
— or —
Enumerator object
— or —
Utils.Enumerator() method

Utils.Enumerator method

Early exit from loop

break;

break

Arrays

Declare an array

let myArr = new Array(3);

myArr = []

Declare and initialize an array

let Arr = [10, 15, 25, 44];
let Arr = new Array(10, 15, 25, 44);

Arr = [10, 15, 25, 44]

Array length

len(myArr)
VarArrayHighBound(myArr,1)+1

Access array element

myArr[1] = 15;

myArr[1] = 15

Blanks

Verify if data is unassigned

strictEqual(x, undefined)
equal(x, aqObject.EmptyVariant)

x == aqObject.EmptyVariant

Test against empty object

strictEqual(myObj, null)

myObj == None
— or —
myObj == aqObject.EmptyObject

Check against blank value

strictEqual(myObj, null);

x == None

Handling exceptions

Handling exceptions

try
{
  Test1();
}
catch (e)
  Log.Error(e.description);

try:
  Test1
except:
  Log.Error(ExceptionMessage)

Sensitive

Sensitive

Sensitive

Insensitive

Insensitive

function MyProcedure()
{
  …
}

function MyProcedure()
{
  …
}

def MyProcedure():
  ...

Sub MyProcedure
  …
End Sub

procedure MyProcedure;
begin
  …
end;

function MyFunction()
{
  …
  return 0;
}

function MyFunction()
{
  …
  return 0;
}

def MyFunction():
  ...
  return 0

Function MyFunction
  …
  MyFunction = 0
End Function

function MyFunction;
begin
  …
  Result := 0;
end;

let x, y;
var x, y;

var x, y;

 

Dim x, y

var x, y;

const c = 45;

var c = 45;

x = 0
y = 0

Const c = 45

const c = 45;

true false

true false

True False

True False

true false

"String"
'String'

"String"
'String'

"String"
'String'
"""String"""

"String"

'String'

"Abra" + "cadabra"

"Abra" + "cadabra"

"Abra" + "cadabra"

"Abra" & "cadabra"
"Abra" + "cadabra"

'Abra' + 'cadabra'

/* Multi-line
comment */

// Single-line comment

/* Multi-line
comment */

// Single-line comment

# Single-line comment

Rem Single-line comment 1
' Single-line comment 2

{ Multi-line
comment }
// Single-line comment

x = 10;

x = 10;

x = 10

x = 10

x := 10;

x = MyObject;

x = MyObject;

x = MyObject

Set x = MyObject

x := MyObject;

x = obj.MyProperty;
x = obj.$get("MyProperty");

x = obj.MyProperty;
x = obj["MyProperty"];

x = obj.MyProperty

x = obj.MyProperty

x := obj.MyProperty;

x.MyMethod(Param1, Param2);
x.$call("MyMethod", Param1, Param2);

x.MyMethod(Param1, Param2);
x["MyMethod"](Param1, Param2);

x.MyMethod(Param1, Param2)

Call x.MyMethod(Param1, Param2)

x.MyMethod(Param1, Param2);

x + 5

x + 5

x + 5

x + 5

x + 5

y - 9

y - 9

y - 9

y - 9

y - 9

x * y

x * y

x * y

x * y

x * y

x / 2

x / 2

x / 2

x / 2

x / 2

x % 2

x % 2

x % 2

x Mod 2

x mod 2

 

 

x // 3

x \ 3

x div 3

i++
i = i+1

i++
i = i+1

i += 1
i = i+1

i = i+1

Inc(i)
i := i+1

i- -
i = i-1

i- -
i = i-1

i -= 1
i = i-1

i = i-1

Dec(i)
i := i-1

Math.pow(x,3)

Math.pow(x,3)

x ** 3

x ^ 3

 

x == 10

x == 10

x == 10

x = 10

x = 10

x != 0

x != 0

x != 0

x <> 0

x <> 0

x < 17

x < 17

x < 17

x < 17

x < 17

x > 0

x > 0

x > 0

x > 0

x > 0

x <= 5

x <= 5

x <= 5

x <= 5

x <= 5

x >= 10

x >= 10

x >= 10

x >= 10

x >= 10

Obj1 == Obj2
equal(Obj1, Obj2)

Obj1 == Obj2

Obj1 == Obj2

Obj1 Is Obj2

Obj1 = Obj2

! x

! x

not x

Not x

not x

x && y

x && y

x and y

x And y

x and y

x || y

x || y

x or y

x Or y

x or y

x ^ y

x ^ y

 

x Xor y

x xor y

~ x

~ x

~ x

Not x

not x

x & y

x & y

x & y

x And y

x and y

x | y

x | y

x | y

x Or y

x or y

x ^ y

x ^ y

x ^ y

x Xor y

x xor y

x << y

x << y

x << y

 

x shl y

x >> y

x >> y

x >> y

 

x shr y

if (x == 10)
  Test1();
else
  Test2();

if (x == 10)
  Test1()
else
  Test2();

if x == 10:
  Test1()
else:
  Test2()

If x = 10 Then
  Test1
Else
 Test2
End If

if x = 10 then
  Test1
else
  Test2;

switch (someChar)
{
  case "a": TestOnA(); break;
  case "z": TestOnZ(); break;
  default: TestOnElse();
}

switch (someChar)
{
  case "a": TestOnA(); break;
  case "z": TestOnZ(); break;
  default: TestOnElse();
}

if someChar == 'a':
  TestOnA()
elif someChar == 'z':
  TestOnZ()
else:
  TestOnElse()

Select Case someChar
  Case "a" TestOnA
  Case "z" TestOnZ
  Case Else TestOnElse
End Select

case someChar of
  'a': TestOnA();
  'z': TestOnZ();
  else TestOnElse();
end;

for (let i = 0; i < 10; i++)
  Test1();

for (i = 0; i < 10; i++)
  Test1();

for i in range (0, 9):
  Test1()

For i = 0 To 9
  Test1
Next

for i := 0 to 9 do
  Test1

while (i < 10)
  Test1();

while (i < 10)
  Test1();

while i < 10:
  Test1()

Do While i < 10
  Test1
Loop

while (i < 10) do
  Test1();

do Test1(); while (i < 10)

do Test1(); while (i < 10)

while True:
  Test1()
  if i == 9:
    break

Do
  Test1
Loop While i < 10

repeat Test1(); until (i = 10);

for i of object
— or —
Enumerator object
— or —
Utils.Enumerator() method

Enumerator object
— or —
Utils.Enumerator() method

Utils.Enumerator method

For Each
— or —
Utils.Enumerator() method

Utils.Enumerator() method

break;

break;

break

Exit For
Exit Do

break;

let myArr = new Array(3);

var myArr = new Array(3);

myArr = []

Dim myArr(3)

var myArr : array[0..2];

let Arr = [10, 15, 25, 44];
let Arr = new Array(10, 15, 25, 44);

var Arr = [10, 15, 25, 44];
var Arr = new Array(10, 15, 25, 44);

Arr = [10, 15, 25, 44]

Dim myArr: myArr = Array(10, 15, 25, 44)

 

myArr.length

myArr.length
myArr["length"]
VarArrayHighBound(myArr,1)+1

len(myArr)
VarArrayHighBound(myArr,1)+1

UBound(myArr)+1
VarArrayHighBound(myArr,1)+1

VarArrayHighBound(myArr,1)+1

myArr[1] = 15;

myArr[1] = 15;

myArr[1] = 15

myArr(1) = 15

myArr[1] := 15;

strictEqual(x, undefined)
equal(x, aqObject.EmptyVariant)

typeof(x) == "undefined"
x == aqObject.EmptyVariant

x == aqObject.EmptyVariant

x = Empty
IsEmpty(x)
x = aqObject.EmptyVariant

x = Unassigned
x = aqObject.EmptyVariant

strictEqual(myObj, null)

myObj == null
— or —
myObj == aqObject.EmptyObject

myObj == None
— or —
myObj == aqObject.EmptyObject

myObj Is Nothing
— or —
myObj Is aqObject.EmptyObject

myObj = nil
— or —
myObj = aqObject.EmptyObject

strictEqual(myObj, null);

x == null

x == None

strictEqual(x, null)

x = nil

try
{
  Test1();
}
catch (e)
  Log.Error(e.description);

try
{
   Test1();
}
catch (e)
  Log.Error(e.description);

try:
  Test1
except:
  Log.Error(ExceptionMessage)

Err.Clear
On Error Resume Next
  Test1
If Err.Number <> 0 Then
  Log.Error Err.Description
End If

try
 Test1;
except
  Log.Error(ExceptionMessage);
end;

Differences in Basic Syntax

JavaScript

JScript, C#Script, C++Script

Python

VBScript

DelphiScript

Variant Data Types

All scripting languages supported by TestComplete use Variant-compatible data types. Variant is a universal type that can be used to store almost any kind of data: numbers, strings, date/time, true/false, references to objects, arrays and so on. All variables and parameters that you create and use in all your test projects are Variant-compatible.

For more information about Variant-compatible data types, see the following topics:

Case Sensitivity

Different scripting languages use different rules for function, variable, constant and parameter names and statements (keywords):

  • JavaScript, JScript, Python, C#Script and C++Script are case-sensitive. That is, they differentiate the letter case in names. For example, they consider Foo() and foo() as different functions.

  • VBScript and DelphiScript are case-insensitive, that is, they do not differentiate upper-case and lower-case characters in names. In these languages, for example, the names Foo() and foo() relate to the same function.

When porting code from a case-insensitive to a case-sensitive language, pay attention to the letter case in function, variable, constant and parameter names and in statements.

Routine Declarations

Routines are divided into two types - procedures and functions. A procedure is a subprogram that performs some actions but does not return any value. Whereas, a function is a subprogram that performs actions and returns the calculated result on exit. The way in which the resulting value is returned depends on the scripting language.

In JavaScript, JScript, C#Script and C++Script, both procedures and functions are declared by using the same function statement. The program instructions are enclosed in curly brackets. The function result is set via the return statement.

JavaScript, JScript

function Func1(A, B)
{
  return A+B;
}

function Test1()
{
  var str;
  Log.Message(Func1(3,4));
  str = "Done.";
  Log.Message(str);
}

C++Script, C#Script

function Func1(A, B)
{
  return A+B;
}

function Test1()
{
  var str;
  Log["Message"](Func1(3,4));
  str = "Done.";
  Log["Message"](str);
}

In Python, procedures and functions are declared by using the def statement. Program instructions are indented. The function result is set by assigning a value to a special return variable. Routine declaration requires a colon (:) after the routine name and arguments.

Python

def Func1(A, B):
  return A+B;

def Test1():
  Log.Message(Func1(3,4))
  str = "Done."
  Log.Message(str)

In VBScript, procedure instructions are enclosed in the Sub and End Sub statements. Function instructions are enclosed in the Function and End Function statements and the function result is defined by assigning a value to the function name.

VBScript

Function Func1(A, B)
  Func1 = A + B
End Function

Sub Test1()
  Dim str
  Log.Message(Func1(3,4))
  str = "Done."
  Log.Message(str)
End Sub

In DelphiScript, procedures and functions are declared via the procedure and function statements. Program instructions are enclosed in the begin and end statements. The function result is set by assigning a value to a special variable named Result. Routine declaration requires a semicolon (;) after the routine name and arguments.

DelphiScript

function Func1(A, B);
begin
  Result := A + B;
end;

procedure Test1();
  var str;
begin
  Log.Message(Func1(3,4));
  str := 'Done.';
  Log.Message(str);
end;

Comments

Comments are used to provide some remarks about the program. Another typical usage of comments is to temporally exclude some code from execution.

See Also

Script Tests
Supported Scripting Languages - Specifics of Usage
Handling Exceptions in Scripts

Highlight search results