---
title: SJS Reference
---

# SJS Reference

`Safe/Subset Javascript (SJS)` is a custom scripting language applicable to MiniApps. You can apply SJS to build a page structure on top of `Tuya Markup Language (TYML)`.

## Things to note

1. The running environment of `SJS` is isolated from other `JavaScript` programs. In `SJS`, you cannot call functions defined in other `JavaScript` files or `APIs` provided by Smart MiniApp.
2. `SJS` is a subset of `JavaScript` and different from `JavaScript`.

- [SJS module](#sjs-module)
- [Variable](#variable)
- [Comment](#comment)
- [Operator](#operator)
- [Statement](#statement)
- [Data type](#data-type)
- [Base class library](#base-class-library)
- [Event system](#event-system)

## SJS module

`SJS` can be programmed in the `<sjs>` tags of `tyml`, or in the files with the extension `.sjs`. Each `.sjs` file and each `<sjs>` tag is an independent module. Each module works in a private scope. By default, the variables and functions that are defined as private in a module are invisible to other modules.

#### Export module

To expose variables and functions of a module, you can export the module based on the modular syntax `module.exports`, `export default`, and `exports`.

```js
export const message = 'hello tuya';
export const getMsg = (x) => x;

// export default
export default {
  message,
  getMsg,
};

// module.exports
module.exports = {
  message,
  getMsg,
};
```

#### `require` function

In a `.sjs` module, you can use the `require` function to reference other `.sjs` file modules.

The following things must be noted:

- Only `.sjs` file modules can be referenced and a relative path must be used.
- Each `.sjs` module is a singleton. When referenced for the first time, a `.sjs` module is automatically initialized into a singleton. The same `.sjs` module object is referenced several times in multiple places for different pages.
- If a `.sjs` module is not referenced after it is defined, this module will not be parsed and run.

**Example**

```js
// /a.sjs
export const message = 'hello tuya';
```

```js
// /b.sjs
var a = require('./a.sjs');
console.log(a.message);
```

```xml
<!-- /page/index/index.tyml -->
<sjs src="./b.sjs" module="b" />
```

Page output:

```
hello tuya
```

#### `<sjs>` tag

| Property | Type | Default value | Description |
| ------ | ------ | ------ | -------------------------------------------------------------------------- |
| module | string |        | The module name of the current `<sjs>` tag. Required |
| src | string |        | The relative path of the referenced `.sjs` file. This applies only to a self-closing tag or empty tag. |

#### `module` property

The `module` property is the module name of the current `<sjs>` tag. The property value is recommended to be unique in the same `tyml` file. A module that is created later overwrites the one created earlier when they use the same module name. However, the `sjs` modules with the same name in different `tyml` files do not overwrite each other.

The `module` property is assigned values based on the following naming rules:

The initial character must be a letter or underscore (`A-Z`, `a-z`, or `_`)
The remaining characters can be alphanumeric characters or underscores (`A-Z`, `a-z`, `0-9`, or `_`).

**Examples**:

```xml
<!--tyml-->

<sjs module="foo">
var some_msg = "hello world";
module.exports = {
  msg : some_msg,
}
</sjs>
<view> {{foo.msg}} </view>
```

Page output:

```
hello world
```

In this example, a module named `foo` is declared, and the variable `some_msg` is exposed to be used by the current page.

#### `src` property

In a `.sjs` file module, you can use the `src` property to reference other `.sjs` file modules.

The following things must be noted:

- Only `.sjs` file modules can be referenced and a relative path must be used.
- Each `.sjs` module is a singleton. When referenced for the first time, a `.sjs` module is automatically initialized into a singleton. The same `.sjs` module object is referenced several times in multiple places for different pages.
- If a `.sjs` module is not referenced after it is defined, this module will not be parsed and run.

**Examples**:

```js
// /pages/index/index.js

Page({
  data: {
    msg: "'hello world' from js",
  },
});
```

```xml
<!-- /pages/index/index.tyml -->

<sjs src="./../comm.sjs" module="some_comms"></sjs>
<! -- A self-closed tag is allowed.
<sjs src="./../comm.sjs" module="some_comms" />
-->

<! -- Calls the `bar` function in the module `some_comms` and sets the parameter to `foo` of `some_comms`. -->
<view> {{some_comms.bar(some_comms.foo)}} </view>
<! -- Calls the `bar` function in the module `some_comms` and sets the parameter to `msg` of `page/index/index.js`. -->
<view> {{some_comms.bar(msg)}} </view>
```

Page output:

```
'hello world' from comm.sjs
'hello world' from js
```

In this example, the `<sjs>` tag is used to reference the module `/page/comm.sjs` in `/page/index/index.tyml`.

#### Things to note

The `<sjs>` module can only be accessed in the `tyml` file of the defined module. In the use of `<include>` or `<import>`, the `<sjs>` module is not referenced in the respective `tyml` file.
In the `<template>` tag, you can only use the `<sjs>` module that is defined in the `tyml` file that defines the `<template>` tag.

## Variable

All variables in SJS are references to values.

#### Syntax rules

- The `var` behaves in the same way as in JavaScript. Variable hoisting might happen.
- The `const` and `let` variables are supported, and they behave in the same way as in JavaScript.
- A variable that is declared but not used has the default value `undefined`.

```js
var num = 1;
var str = 'hello tuya';
var undef; // undef === undefined
const n = 2;
let s = 'string';
```

#### Variable name

##### Naming rules

A variable is named based on the following naming rules:

- The initial character must be a letter or underscore (A-Z, `a-z`, or `_`)
- The remaining characters can be alphanumeric characters or underscores (`A-Z`, `a-z`, `0-9`, or `_`).

##### Reserved identifier

Reserved identifiers are handled based on similar syntax rules to `Javascript`.

## Comment

Just like the syntax rules of `Javascript`, SJS code blocks can be commented out in the following way:

```js
// page.sjs
// Method 1: This is the comment for a single line.
/*
Method 2: This is the comment for several lines.
All content in between is annotated.
*/
let h = 'hello';
const w = ' tuya';
```

## Operator

#### Arithmetic operator

```js
var a = 10,
  b = 20;
// An addition operation.
console.log(30 === a + b); //true
// A subtraction operation.
console.log(-10 === a - b); //true
// A multiplication operation.
console.log(200 === a * b); //true
// A division operation.
console.log(0.5 === a / b); //true
// A complementation operation.
console.log(10 === a % b); //true
```

The addition (`+`) operator can be used for string concatenation.

```js
var a = 'hello',
  b = ' tuya';
// Concatenates strings.
console.log('hello tuya' === a + b); //true
```

#### Comparison operator

```js
var a = 10,
  b = 20;
// Less than
console.log(true === a < b); //true
// Greater than
console.log(false === a > b); //true
// Less than or equal to
console.log(true === a <= b); //true
// Greater than or equal to
console.log(false === a >= b); //true
// Equal to
console.log(false === (a == b)); //true
// Unequal to
console.log(true === (a != b)); //true
// All equal to
console.log(false === (a === b)); //true
// Not all equal to
console.log(true === (a !== b)); //true
```

#### Binary logic operator

```js
var a = 10,
  b = 20;
// The logical AND operator.
console.log(20 === (a && b)); //true
// The logical OR operator.
console.log(10 === (a || b)); //true
// Logical NOT, an inverse operation.
console.log(false === !a); //true
```

#### Bit operator

```js
var a = 10,
  b = 20;
// An left-shift operation.
console.log(80 === a << 3); //true
// An unsigned right-shift operation.
console.log(2 === a >> 2); //true
// A signed right-shift operation.
console.log(2 === a >>> 2); //true
// An AND operation.
console.log(2 === (a & 3)); //true
// An XOR operation.
console.log(9 === (a ^ 3)); //true
// An OR operation.
console.log(11 === (a | 3)); //true
```

#### Assignment operator

```js
var a = 10;
a = 10;
a *= 10;
console.log(100 === a); //true
a = 10;
a /= 5;
console.log(2 === a); //true
a = 10;
a %= 7;
console.log(3 === a); //true
a = 10;
a += 5;
console.log(15 === a); //true
a = 10;
a -= 11;
console.log(-1 === a); //true
a = 10;
a <<= 10;
console.log(10240 === a); //true
a = 10;
a >>= 2;
console.log(2 === a); //true
a = 10;
a >>>= 2;
console.log(2 === a); //true
a = 10;
a &= 3;
console.log(2 === a); //true
a = 10;
a ^= 3;
console.log(9 === a); //true
a = 10;
a |= 3;
console.log(11 === a); //true
```

#### Unary operator

```js
var a = 10,
  b = 20;
// An increment operation.
console.log(10 === a++); //true
console.log(12 === ++a); //true
// An decrement operation.
console.log(12 === a--); //true
console.log(10 === --a); //true
// A positive operation.
console.log(10 === +a); //true
// A negative operation.
console.log(0 - 10 === -a); //true
// A NOT operation.
console.log(-11 === ~a); //true
// An inverse operation.
console.log(false === !a); //true
// A delete operation.
console.log(true === delete a.fake); //true
// A void operation.
console.log(undefined === void a); //true
// A `typeof` operation.
console.log('number' === typeof a); //true
```

#### Ternary operator

```js
var a = 10,
  b = 20;
// The condition operator.
console.log(20 === (a >= 10 ? a + 10 : b + 10)); //true
```

#### Comma operator

```js
var a = 10,
  b = 20;
// The comma operator.
console.log(20 === (a, b)); //true
```

#### Operator priority

The priority of SJS operators is the same as that in JavaScript.

## Statement

#### `if` Statement

In the `.sjs` file, the `if` statement can be used in the following formats:

- `if (expression) statement`: When `expression` is `true`, execute `statement`.
- `if (expression) statement1 else statement2`: When `expression` is `true`, execute `statement1`. Otherwise, execute `statement2`.
- `if ... else if ... else statementN`: This statement allows you to select one of `statement1` to `statementN` and execute the statement.

**Example:**

```javascript
// if ...
if (expression) statement;
if (expression) statement;
if (expression) {
  Code block;
}
// if ... else
if (expression) statement;
else statement;
if (expression) statement;
else statement;
if (expression) {
  Code block;
} else {
  Code block;
}
// if ... else if ... else ...
if (expression) {
  Code block;
} else if (expression) {
  Code block;
} else if (expression) {
  Code block;
} else {
  Code block;
}
```

#### `switch` statement

**Example:**

```javascript
switch (expression) {
  case variable:
    statement;
  case number:
    statement;
    break;
  case string:
    statement;
  default:
    statement;
}
```

- `default` branches can be omitted.
- Following the `case` keyword, use only a `variable`, `number`, or `string`.

**Examples**:

```javascript
var exp = 10;
switch (exp) {
  case '10':
    console.log('string 10');
    break;
  case 10:
    console.log('number 10');
    break;
  case exp:
    console.log('var exp');
    break;
  default:
    console.log('default');
}
```

**Output:**

```
number 10
```

#### `for` statement

**Example:**

```javascript
for (statement; statement; statement) statement;
for (statement; statement; statement) {
  Code block;
}
```

- The keywords `break` and `continue` are supported.

**Examples**:

```javascript
for (var i = 0; i < 3; ++i) {
  console.log(i);
  if (i >= 1) break;
}
```

**Output:**

```
0
1
```

#### `while` statement

**Example:**

```javascript
while (expression) statement;
while (expression) {
  Code block;
}
do {
  Code block;
} while (expression);
```

- When `expression` is `true`, do loop execution of `statement` or `code block`.
- The keywords `break` and `continue` are supported.

## Data type

`SJS` currently supports the following data types, similar to those of `JavaScript`.

- Value types (basic types): `string`, `number`, `Boolean`, `null`, `undefined`, and `symbol`.
- Reference data types: `object`, `array`, and `function`.

## Base class library

Currently, `SJS` supports the same base library as that of `JavaScript`.
