javascript-obfuscator 5.4.1 → 5.4.2

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/CHANGELOG.md CHANGED
@@ -1,5 +1,9 @@
1
1
  Change Log
2
2
 
3
+ v5.4.2
4
+ ---
5
+ * Fixed obfuscated code hanging in Bun when `selfDefending` is enabled. Fixes https://github.com/javascript-obfuscator/javascript-obfuscator/issues/1404
6
+
3
7
  v5.4.1
4
8
  ---
5
9
  * Fixed `Utils.nodeRequire` causing `ReferenceError: require is not defined` in browser build by making it lazy-evaluated
package/README.md CHANGED
@@ -15,13 +15,25 @@ Huge thanks to all supporters!
15
15
 
16
16
  ---
17
17
 
18
- ### :rocket: Obfuscator.io with VM Obfuscation is out!
18
+ ### :rocket: Obfuscator.io with VM Obfuscation
19
19
 
20
- **Obfuscator.io** features **VM-based bytecode obfuscation** the most advanced code protection available. Your JavaScript functions are transformed into custom bytecode running on an embedded virtual machine, making reverse engineering extremely difficult.
20
+ **Obfuscator.io** adds **VM-based bytecode obfuscation** to this package - your JavaScript functions are compiled to custom bytecode that runs on an embedded virtual machine. Each build produces unique opcodes and VM structure, making reverse engineering and automated deobfuscation dramatically harder.
21
21
 
22
- [Try it at obfuscator.io](https://obfuscator.io)
22
+ | Protection goal | Free (this package) | [obfuscator.io](https://obfuscator.io) |
23
+ | --- |-----------------------------------------------------------------------------------|---------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------|
24
+ | Rename identifiers | ✅ variable/function renaming | ✅ + VM-local symbols never exposed as JavaScript |
25
+ | Obscure strings | ✅ string array + base64/rc4 | ✅ + strings embedded in bytecode constants |
26
+ | Obscure control flow | ✅ control flow flattening | ✅ full bytecode virtualization, [`vmJumpsEncoding`](#vmjumpsencoding) (runtime-computed jump targets), [`vmDeadCodeInjection`](#vmdeadcodeinjection) (fake bytecode sequences) |
27
+ | Resist decompilation | ⚠️ output is still JavaScript | ✅ custom opcodes, [`vmStatefulOpcodes`](#vmstatefulopcodes) (position-dependent opcode mapping), [`vmMacroOps`](#vmmacroops) (fused instructions), [`vmDecoyOpcodes`](#vmdecoyopcodes) (fake opcode handlers) |
28
+ | Resist automated LLM-based analysis | ❌ fully vulnerable (no LLM-specific defenses) | ✅ bytecode encryption + anti-LLM defenses in [`vmSelfDefending`](#vmselfdefending) and [`vmDebugProtection`](#vmdebugProtection) |
29
+ | Encryption | ✅ [`stringArrayEncoding`](#stringarrayencoding) (base64/rc4 on extracted strings) | ✅ [`vmBytecodeEncoding`](#vmbytecodeencoding) (per-instruction encoding), [`vmBytecodeArrayEncoding`](#vmbytecodeArrayEncoding) (whole bytecode array as single block) |
30
+ | Anti-debugging | ✅ `debugProtection` (freezes browser DevTools) | ✅ [`vmDebugProtection`](#vmdebugProtection) (multi-layered anti-debugging and anti-analysis defenses) |
31
+ | Tamper detection | ✅ `selfDefending` (breaks if beautified) | ✅ [`vmSelfDefending`](#vmselfdefending) (multi-layered tamper detection, anti-hooking, anti-reverse-engineering protection) |
32
+ | Runs offline, no network | ✅ | ❌ uses obfuscator.io API (requires token) |
23
33
 
24
- This package provides access to Obfuscator.io Pro API via CLI and Node.js API.
34
+ [Visit Obfuscator.io](https://obfuscator.io) · [Pro API methods](#shield-pro-api-methods-vm-obfuscation)
35
+
36
+ This package provides access to Obfuscator.io API via CLI and Node.js API.
25
37
 
26
38
  ---
27
39
 
@@ -51,6 +63,7 @@ The example of obfuscated code: [github.com](https://github.com/javascript-obfus
51
63
  * Malta: [malta-js-obfuscator](https://github.com/fedeghe/malta-js-obfuscator)
52
64
  * Netlify plugin: [netlify-plugin-js-obfuscator](https://www.npmjs.com/package/netlify-plugin-js-obfuscator)
53
65
  * Snowpack plugin: [snowpack-javascript-obfuscator](https://www.npmjs.com/package/snowpack-javascript-obfuscator)
66
+ * Vite plugin: [vite-plugin-bundle-obfuscator](https://github.com/z0ffy/vite-plugin-bundle-obfuscator)
54
67
 
55
68
  [![npm version](https://badge.fury.io/js/javascript-obfuscator.svg)](https://badge.fury.io/js/javascript-obfuscator)
56
69
  [![FOSSA Status](https://app.fossa.io/api/projects/git%2Bgithub.com%2Fjavascript-obfuscator%2Fjavascript-obfuscator.svg?type=shield)](https://app.fossa.io/projects/git%2Bgithub.com%2Fjavascript-obfuscator%2Fjavascript-obfuscator?ref=badge_shield)
@@ -513,6 +526,8 @@ When using CLI this prefix will be added automatically.
513
526
 
514
527
  ## JavaScript Obfuscator Options
515
528
 
529
+ > :shield: **Looking for VM obfuscation?** Options like `vmObfuscation`, `parseHtml`, and every `vm*` option are Pro-only and require an API token from [obfuscator.io](https://obfuscator.io). Use them via the [`obfuscatePro()`](#shield-pro-api-methods-vm-obfuscation) method, or the `--pro-api-token` CLI flag — see [Pro API Methods](#shield-pro-api-methods-vm-obfuscation).
530
+
516
531
  Following options are available for the JS Obfuscator:
517
532
 
518
533
  #### options:
@@ -1870,8 +1885,8 @@ Specify exactly which root-level functions should get VM protection by name.
1870
1885
  **Example:**
1871
1886
  ```javascript
1872
1887
  {
1873
- vmObfuscation: true,
1874
- vmTargetFunctions: ['someFunctionName']
1888
+ vmObfuscation: true,
1889
+ vmTargetFunctions: ['someFunctionName']
1875
1890
  }
1876
1891
  ```
1877
1892
 
@@ -1885,8 +1900,8 @@ Specify root-level functions that should never get VM protection. Takes preceden
1885
1900
  **Example:**
1886
1901
  ```javascript
1887
1902
  {
1888
- vmObfuscation: true,
1889
- vmExcludeFunctions: ['someFunctionName']
1903
+ vmObfuscation: true,
1904
+ vmExcludeFunctions: ['someFunctionName']
1890
1905
  }
1891
1906
  ```
1892
1907
 
@@ -1906,28 +1921,28 @@ Controls how functions/methods are selected for VM obfuscation.
1906
1921
  ```javascript
1907
1922
  // Source code
1908
1923
  function regularFunction() {
1909
- return 'not virtualized';
1924
+ return 'not virtualized';
1910
1925
  }
1911
1926
 
1912
1927
  /* javascript-obfuscator:vm */
1913
1928
  function sensitiveFunction() {
1914
- return 'this will be VM-protected';
1929
+ return 'this will be VM-protected';
1915
1930
  }
1916
1931
 
1917
1932
  function outer() {
1918
- /* javascript-obfuscator:vm */
1919
- function nestedSensitive() {
1920
- return 'nested but still VM-protected';
1921
- }
1922
- return nestedSensitive();
1933
+ /* javascript-obfuscator:vm */
1934
+ function nestedSensitive() {
1935
+ return 'nested but still VM-protected';
1936
+ }
1937
+ return nestedSensitive();
1923
1938
  }
1924
1939
  ```
1925
1940
 
1926
1941
  ```javascript
1927
1942
  // Obfuscator options
1928
1943
  {
1929
- vmObfuscation: true,
1930
- vmTargetFunctionsMode: 'comment'
1944
+ vmObfuscation: true,
1945
+ vmTargetFunctionsMode: 'comment'
1931
1946
  }
1932
1947
  ```
1933
1948
 
@@ -2020,10 +2035,10 @@ vmBytecodeArrayEncodingKeyGetter: "window.config.encryption.key"
2020
2035
  ```ts
2021
2036
  // Build time
2022
2037
  JavaScriptObfuscator.obfuscate(code, {
2023
- vmObfuscation: true,
2024
- vmBytecodeArrayEncoding: true,
2025
- vmBytecodeArrayEncodingKey: 'mySecretKey123',
2026
- vmBytecodeArrayEncodingKeyGetter: 'window.__VM_KEY__'
2038
+ vmObfuscation: true,
2039
+ vmBytecodeArrayEncoding: true,
2040
+ vmBytecodeArrayEncodingKey: 'mySecretKey123',
2041
+ vmBytecodeArrayEncodingKeyGetter: 'window.__VM_KEY__'
2027
2042
  });
2028
2043
 
2029
2044
  // Runtime - key must be set before obfuscated code runs
@@ -2045,26 +2060,24 @@ Type: `boolean` Default: `false`
2045
2060
 
2046
2061
  Injects fake bytecode sequences that are never executed. These look like real instructions but are skipped during runtime, confusing analysis tools that process them.
2047
2062
 
2048
- ### `vmCompactDispatcher`
2063
+ ### `vmMacroOps`
2049
2064
  Type: `boolean` Default: `false`
2050
2065
 
2051
- Uses a single unified dispatcher (generator-based) for both sync and async/generator code execution. By default (`false`), the VM generates two separate dispatchers: a non-generator version for sync code (faster) and a generator version for async/generator code. When enabled, only the generator-based dispatcher is used for all execution.
2066
+ Combines common instruction sequences into single "macro" opcodes. For example, `LOAD + ADD + STORE` might become a single `MACRO_ADD_TO_VAR` instruction. This breaks pattern recognition and can improve performance.
2052
2067
 
2053
- **Trade-offs:**
2054
- - `false` (default): Larger code size due to dual dispatchers, but faster sync execution (no generator overhead)
2055
- - `true`: Smaller code size with single dispatcher, but sync code has generator protocol overhead
2068
+ ### `vmDebugProtection`
2069
+ Type: `boolean` Default: `false`
2056
2070
 
2057
- Use this when code size is more important than sync execution speed.
2071
+ Adds multi-layered anti-debugging, anti-analysis, and anti-LLM defenses to the VM runtime. For best results, allow `unsafe-eval` in your Content Security Policy. Works best with `browser`/`browser-no-eval` targets.
2058
2072
 
2059
- ### `vmMacroOps`
2073
+ ### `vmSelfDefending`
2060
2074
  Type: `boolean` Default: `false`
2061
2075
 
2062
- Combines common instruction sequences into single "macro" opcodes. For example, `LOAD + ADD + STORE` might become a single `MACRO_ADD_TO_VAR` instruction. This breaks pattern recognition and can improve performance.
2076
+ Adds multi-layered tamper detection, anti-hooking, and anti-reverse-engineering protection to the VM runtime.
2063
2077
 
2064
- ### `vmDebugProtection`
2065
- Type: `boolean` Default: `false`
2078
+ > :warning: This option force-enables [`vmBytecodeArrayEncoding`](#vmbytecodeArrayEncoding).
2066
2079
 
2067
- Adds anti-debugging measures to the VM runtime. Detects debugger presence and alters behavior when debugging is detected.
2080
+ Strongly recommended to use together with [`vmDebugProtection`](#vmDebugProtection), [`vmBytecodeArrayEncodingKey`](#vmbytecodeArrayEncodingKey), and [`vmBytecodeArrayEncodingKeyGetter`](#vmbytecodeArrayEncodingKeyGetter).
2068
2081
 
2069
2082
  ### `vmStatefulOpcodes`
2070
2083
  Type: `boolean` Default: `false`
@@ -2078,6 +2091,26 @@ Encrypts values on the VM stack during execution. Values are encoded when pushed
2078
2091
 
2079
2092
  This option heavily affects performance.
2080
2093
 
2094
+ ### `vmCompactDispatcher`
2095
+ Type: `boolean` Default: `false`
2096
+
2097
+ Uses a single VM executor instead of dual executors (sync + generator). Reduces obfuscated code size but adds ~20% performance overhead on recursion-heavy code.
2098
+
2099
+ - `false` (default): dual executors — optimal performance, larger output
2100
+ - `true`: single executor — smaller output, slightly slower
2101
+
2102
+ ### `vmStringArrayBytecodeOnly`
2103
+ Type: `boolean` Default: `false`
2104
+
2105
+ When enabled, the string array will **only** extract strings from bytecode data — no other strings in the code are transformed. This force-enables `stringArray` even if it's not explicitly set.
2106
+
2107
+ **Why use this:** Extracting all VM runtime strings to a string array is slow. This option targets only bytecode content for string array extraction, improving performance while still protecting bytecode constants.
2108
+
2109
+ - When `vmBytecodeArrayEncoding: false` — strings inside bytecode constant pools (`c` arrays) are extracted
2110
+ - When `vmBytecodeArrayEncoding: true` — top-level base64 encoded bytecode strings are extracted
2111
+ - `stringArrayThreshold` still controls what percentage of those bytecode strings are extracted
2112
+
2113
+
2081
2114
  ### `strictMode`
2082
2115
  Type: `boolean | null` Default: `null`
2083
2116