mirror of
https://github.com/PrivateCaptcha/PrivateCaptcha.git
synced 2026-05-13 00:08:34 -05:00
@@ -1,10 +1,11 @@
|
||||
name: eslint
|
||||
name: widget
|
||||
on:
|
||||
push:
|
||||
branches:
|
||||
- '**'
|
||||
paths:
|
||||
- 'widget/js/**'
|
||||
- 'widget/test/**'
|
||||
- '.github/workflows/eslint.yml'
|
||||
# - 'web/js/**'
|
||||
- '!node_modules/**'
|
||||
@@ -23,8 +24,7 @@ permissions:
|
||||
# pull-requests: read
|
||||
|
||||
jobs:
|
||||
golangci:
|
||||
name: lint
|
||||
lint-and-test:
|
||||
runs-on: ubuntu-latest
|
||||
steps:
|
||||
- uses: actions/checkout@v4
|
||||
@@ -40,3 +40,7 @@ jobs:
|
||||
- name: Run eslint for widget
|
||||
run: npm run lint
|
||||
working-directory: ./widget
|
||||
|
||||
- name: Run widget tests
|
||||
run: npm run test
|
||||
working-directory: ./widget
|
||||
@@ -27,6 +27,8 @@ web/static/*
|
||||
widget/static/
|
||||
widget/lib/*.js
|
||||
widget/lib/*.js.map
|
||||
widget/test/bundle.test.js
|
||||
widget/test/bundle.test.js.map
|
||||
|
||||
pkg/db/migrations/postgres/000000_sqlc_fix.sql
|
||||
pc.env
|
||||
|
||||
@@ -12,6 +12,9 @@ test-unit:
|
||||
test-unit-cover:
|
||||
@env GOFLAGS="-mod=vendor" CGO_ENABLED=0 go test -short -coverprofile=coverage_unit.cov -coverpkg=$(shell go list ./... | paste -sd, -) ./...
|
||||
|
||||
test-widget-unit:
|
||||
cd widget && env STAGE="$(STAGE)" npm run test
|
||||
|
||||
bench-unit:
|
||||
env GOFLAGS="-mod=vendor" CGO_ENABLED=0 go test -bench=. -benchtime=20s -short ./...
|
||||
|
||||
|
||||
@@ -7,7 +7,7 @@
|
||||
|
||||

|
||||
|
||||
  
|
||||
  
|
||||
|
||||
[](https://sonarcloud.io/dashboard?id=PrivateCaptcha_PrivateCaptcha)
|
||||
[](https://sonarcloud.io/dashboard?id=PrivateCaptcha_PrivateCaptcha)
|
||||
|
||||
@@ -0,0 +1,31 @@
|
||||
import { build, transform } from 'esbuild';
|
||||
import { readFile } from "fs/promises"
|
||||
import inlineWorkerPlugin from 'esbuild-plugin-inline-worker';
|
||||
|
||||
let CSSMinifyPlugin = {
|
||||
name: "CSSMinifyPlugin",
|
||||
setup(build) {
|
||||
build.onLoad({ filter: /\.css$/ }, async (args) => {
|
||||
const f = await readFile(args.path)
|
||||
const css = await transform(f, { loader: "css", minify: false })
|
||||
return { loader: "text", contents: css.code }
|
||||
})
|
||||
}
|
||||
}
|
||||
|
||||
build({
|
||||
entryPoints: ['./test/widget.test.js'],
|
||||
bundle: true,
|
||||
outfile: './test/bundle.test.js',
|
||||
format: 'esm',
|
||||
loader: { '.css': 'text' },
|
||||
external: ['node:test', 'node:assert', 'happy-dom'],
|
||||
plugins: [
|
||||
CSSMinifyPlugin,
|
||||
inlineWorkerPlugin({
|
||||
minify: false
|
||||
}),
|
||||
],
|
||||
minify: false,
|
||||
sourcemap: true,
|
||||
}).catch(() => process.exit(1));
|
||||
+1
-1
@@ -1,7 +1,7 @@
|
||||
'use strict';
|
||||
|
||||
import { ProgressRing } from './progress.js';
|
||||
import { SafeHTMLElement } from "./utils";
|
||||
import { SafeHTMLElement } from "./utils.js";
|
||||
import styles from "./styles.css" with { type: 'css' };
|
||||
import * as i18n from './strings.js';
|
||||
import * as errors from './errors.js';
|
||||
|
||||
@@ -1,6 +1,6 @@
|
||||
'use strict';
|
||||
|
||||
import { SafeHTMLElement } from "./utils";
|
||||
import { SafeHTMLElement } from "./utils.js";
|
||||
|
||||
export class ProgressRing extends SafeHTMLElement {
|
||||
constructor() {
|
||||
|
||||
+7
-2
@@ -90,12 +90,17 @@ export class CaptchaWidget {
|
||||
defaultField = "g-recaptcha-response";
|
||||
}
|
||||
|
||||
let sitekey = "";
|
||||
if (options.hasOwnProperty('sitekey')) {
|
||||
sitekey = options.sitekey;
|
||||
}
|
||||
|
||||
this._options = Object.assign({
|
||||
startMode: this._element.dataset["startMode"] || "auto",
|
||||
debug: this._element.dataset["debug"],
|
||||
fieldName: this._element.dataset["solutionField"] || defaultField,
|
||||
puzzleEndpoint: this._element.dataset["puzzleEndpoint"] || defaultEndpoint,
|
||||
sitekey: this._element.dataset["sitekey"] || "",
|
||||
sitekey: sitekey || this._element.dataset["sitekey"] || "",
|
||||
displayMode: this._element.dataset["displayMode"] || "widget",
|
||||
lang: this._element.dataset["lang"] || "en",
|
||||
theme: this._element.dataset["theme"] || "light",
|
||||
@@ -131,7 +136,7 @@ export class CaptchaWidget {
|
||||
|
||||
try {
|
||||
this.setState(STATE_LOADING);
|
||||
this.trace('fetching puzzle');
|
||||
this.trace(`fetching puzzle. sitekey=${sitekey}`);
|
||||
const puzzleData = await getPuzzle(this._options.puzzleEndpoint, sitekey);
|
||||
this._puzzle = new Puzzle(puzzleData);
|
||||
if (this._puzzle && this._puzzle.isZero()) { this._errorCode = errors.ERROR_ZERO_PUZZLE; }
|
||||
|
||||
Generated
+150
-7
@@ -15,7 +15,8 @@
|
||||
"devDependencies": {
|
||||
"esbuild": "^0.25.0",
|
||||
"esbuild-plugin-inline-worker": "^0.1.1",
|
||||
"eslint": "^9.23.0"
|
||||
"eslint": "^9.23.0",
|
||||
"happy-dom": "^12.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/@esbuild/aix-ppc64": {
|
||||
@@ -730,9 +731,9 @@
|
||||
"integrity": "sha512-QXUSXI3QVc/gJME0dBpXrag1kbzOqCjCX8/b54ntNyW6sjtoqxqRk3LTmXzaJoh71zMsDCjM+47jS7XiwN/+fQ=="
|
||||
},
|
||||
"node_modules/brace-expansion": {
|
||||
"version": "1.1.11",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
|
||||
"integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
|
||||
"version": "1.1.12",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.12.tgz",
|
||||
"integrity": "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"balanced-match": "^1.0.0",
|
||||
@@ -808,6 +809,12 @@
|
||||
"node": ">= 8"
|
||||
}
|
||||
},
|
||||
"node_modules/css.escape": {
|
||||
"version": "1.5.1",
|
||||
"resolved": "https://registry.npmjs.org/css.escape/-/css.escape-1.5.1.tgz",
|
||||
"integrity": "sha512-YUifsXXuknHlUsmlgyY0PKzgPOr7/FjCePfHNt0jxm83wHZi44VDMQ7/fGNkjY3/jV1MC+1CmZbaHzugyeRtpg==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/debug": {
|
||||
"version": "4.4.0",
|
||||
"resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz",
|
||||
@@ -831,6 +838,18 @@
|
||||
"integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/entities": {
|
||||
"version": "4.5.0",
|
||||
"resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz",
|
||||
"integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">=0.12"
|
||||
},
|
||||
"funding": {
|
||||
"url": "https://github.com/fb55/entities?sponsor=1"
|
||||
}
|
||||
},
|
||||
"node_modules/esbuild": {
|
||||
"version": "0.25.10",
|
||||
"resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.10.tgz",
|
||||
@@ -1205,6 +1224,20 @@
|
||||
"url": "https://github.com/sponsors/sindresorhus"
|
||||
}
|
||||
},
|
||||
"node_modules/happy-dom": {
|
||||
"version": "12.10.3",
|
||||
"resolved": "https://registry.npmjs.org/happy-dom/-/happy-dom-12.10.3.tgz",
|
||||
"integrity": "sha512-JzUXOh0wdNGY54oKng5hliuBkq/+aT1V3YpTM+lrN/GoLQTANZsMaIvmHiHe612rauHvPJnDZkZ+5GZR++1Abg==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"css.escape": "^1.5.1",
|
||||
"entities": "^4.5.0",
|
||||
"iconv-lite": "^0.6.3",
|
||||
"webidl-conversions": "^7.0.0",
|
||||
"whatwg-encoding": "^2.0.0",
|
||||
"whatwg-mimetype": "^3.0.0"
|
||||
}
|
||||
},
|
||||
"node_modules/has-flag": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
|
||||
@@ -1214,6 +1247,18 @@
|
||||
"node": ">=8"
|
||||
}
|
||||
},
|
||||
"node_modules/iconv-lite": {
|
||||
"version": "0.6.3",
|
||||
"resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz",
|
||||
"integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"safer-buffer": ">= 2.1.2 < 3.0.0"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=0.10.0"
|
||||
}
|
||||
},
|
||||
"node_modules/ignore": {
|
||||
"version": "5.3.2",
|
||||
"resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz",
|
||||
@@ -1511,6 +1556,12 @@
|
||||
"node": ">=4"
|
||||
}
|
||||
},
|
||||
"node_modules/safer-buffer": {
|
||||
"version": "2.1.2",
|
||||
"resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
|
||||
"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
|
||||
"dev": true
|
||||
},
|
||||
"node_modules/semver": {
|
||||
"version": "6.3.1",
|
||||
"resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
|
||||
@@ -1586,6 +1637,36 @@
|
||||
"punycode": "^2.1.0"
|
||||
}
|
||||
},
|
||||
"node_modules/webidl-conversions": {
|
||||
"version": "7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz",
|
||||
"integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/whatwg-encoding": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-2.0.0.tgz",
|
||||
"integrity": "sha512-p41ogyeMUrw3jWclHWTQg1k05DSVXPLcVxRTYsXUk+ZooOCZLcoYgPZ/HL/D/N+uQPOtcp1me1WhBEaX02mhWg==",
|
||||
"dev": true,
|
||||
"dependencies": {
|
||||
"iconv-lite": "0.6.3"
|
||||
},
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/whatwg-mimetype": {
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-3.0.0.tgz",
|
||||
"integrity": "sha512-nt+N2dzIutVRxARx1nghPKGv1xHikU7HKdfafKkLNLindmPU/ch3U31NOCGGA/dmPcmb1VlofO0vnKAcsm0o/Q==",
|
||||
"dev": true,
|
||||
"engines": {
|
||||
"node": ">=12"
|
||||
}
|
||||
},
|
||||
"node_modules/which": {
|
||||
"version": "2.0.2",
|
||||
"resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz",
|
||||
@@ -2013,9 +2094,9 @@
|
||||
"integrity": "sha512-QXUSXI3QVc/gJME0dBpXrag1kbzOqCjCX8/b54ntNyW6sjtoqxqRk3LTmXzaJoh71zMsDCjM+47jS7XiwN/+fQ=="
|
||||
},
|
||||
"brace-expansion": {
|
||||
"version": "1.1.11",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.11.tgz",
|
||||
"integrity": "sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==",
|
||||
"version": "1.1.12",
|
||||
"resolved": "https://registry.npmjs.org/brace-expansion/-/brace-expansion-1.1.12.tgz",
|
||||
"integrity": "sha512-9T9UjW3r0UW5c1Q7GTwllptXwhvYmEzFhzMfZ9H7FQWt+uZePjZPjBP/W1ZEyZ1twGWom5/56TF4lPcqjnDHcg==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"balanced-match": "^1.0.0",
|
||||
@@ -2076,6 +2157,12 @@
|
||||
"which": "^2.0.1"
|
||||
}
|
||||
},
|
||||
"css.escape": {
|
||||
"version": "1.5.1",
|
||||
"resolved": "https://registry.npmjs.org/css.escape/-/css.escape-1.5.1.tgz",
|
||||
"integrity": "sha512-YUifsXXuknHlUsmlgyY0PKzgPOr7/FjCePfHNt0jxm83wHZi44VDMQ7/fGNkjY3/jV1MC+1CmZbaHzugyeRtpg==",
|
||||
"dev": true
|
||||
},
|
||||
"debug": {
|
||||
"version": "4.4.0",
|
||||
"resolved": "https://registry.npmjs.org/debug/-/debug-4.4.0.tgz",
|
||||
@@ -2091,6 +2178,12 @@
|
||||
"integrity": "sha512-oIPzksmTg4/MriiaYGO+okXDT7ztn/w3Eptv/+gSIdMdKsJo0u4CfYNFJPy+4SKMuCqGw2wxnA+URMg3t8a/bQ==",
|
||||
"dev": true
|
||||
},
|
||||
"entities": {
|
||||
"version": "4.5.0",
|
||||
"resolved": "https://registry.npmjs.org/entities/-/entities-4.5.0.tgz",
|
||||
"integrity": "sha512-V0hjH4dGPh9Ao5p0MoRY6BVqtwCjhz6vI5LT8AJ55H+4g9/4vbHx1I54fS0XuclLhDHArPQCiMjDxjaL8fPxhw==",
|
||||
"dev": true
|
||||
},
|
||||
"esbuild": {
|
||||
"version": "0.25.10",
|
||||
"resolved": "https://registry.npmjs.org/esbuild/-/esbuild-0.25.10.tgz",
|
||||
@@ -2359,12 +2452,35 @@
|
||||
"integrity": "sha512-oahGvuMGQlPw/ivIYBjVSrWAfWLBeku5tpPE2fOPLi+WHffIWbuh2tCjhyQhTBPMf5E9jDEH4FOmTYgYwbKwtQ==",
|
||||
"dev": true
|
||||
},
|
||||
"happy-dom": {
|
||||
"version": "12.10.3",
|
||||
"resolved": "https://registry.npmjs.org/happy-dom/-/happy-dom-12.10.3.tgz",
|
||||
"integrity": "sha512-JzUXOh0wdNGY54oKng5hliuBkq/+aT1V3YpTM+lrN/GoLQTANZsMaIvmHiHe612rauHvPJnDZkZ+5GZR++1Abg==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"css.escape": "^1.5.1",
|
||||
"entities": "^4.5.0",
|
||||
"iconv-lite": "^0.6.3",
|
||||
"webidl-conversions": "^7.0.0",
|
||||
"whatwg-encoding": "^2.0.0",
|
||||
"whatwg-mimetype": "^3.0.0"
|
||||
}
|
||||
},
|
||||
"has-flag": {
|
||||
"version": "4.0.0",
|
||||
"resolved": "https://registry.npmjs.org/has-flag/-/has-flag-4.0.0.tgz",
|
||||
"integrity": "sha512-EykJT/Q1KjTWctppgIAgfSO0tKVuZUjhgMr17kqTumMl6Afv3EISleU7qZUzoXDFTAHTDC4NOoG/ZxU3EvlMPQ==",
|
||||
"dev": true
|
||||
},
|
||||
"iconv-lite": {
|
||||
"version": "0.6.3",
|
||||
"resolved": "https://registry.npmjs.org/iconv-lite/-/iconv-lite-0.6.3.tgz",
|
||||
"integrity": "sha512-4fCk79wshMdzMp2rH06qWrJE4iolqLhCUH+OiuIgU++RB0+94NlDL81atO7GX55uUKueo0txHNtvEyI6D7WdMw==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"safer-buffer": ">= 2.1.2 < 3.0.0"
|
||||
}
|
||||
},
|
||||
"ignore": {
|
||||
"version": "5.3.2",
|
||||
"resolved": "https://registry.npmjs.org/ignore/-/ignore-5.3.2.tgz",
|
||||
@@ -2590,6 +2706,12 @@
|
||||
"integrity": "sha512-pb/MYmXstAkysRFx8piNI1tGFNQIFA3vkE3Gq4EuA1dF6gHp/+vgZqsCGJapvy8N3Q+4o7FwvquPJcnZ7RYy4g==",
|
||||
"dev": true
|
||||
},
|
||||
"safer-buffer": {
|
||||
"version": "2.1.2",
|
||||
"resolved": "https://registry.npmjs.org/safer-buffer/-/safer-buffer-2.1.2.tgz",
|
||||
"integrity": "sha512-YZo3K82SD7Riyi0E1EQPojLz7kpepnSQI9IyPbHHg1XXXevb5dJI7tpyN2ADxGcQbHG7vcyRHk0cbwqcQriUtg==",
|
||||
"dev": true
|
||||
},
|
||||
"semver": {
|
||||
"version": "6.3.1",
|
||||
"resolved": "https://registry.npmjs.org/semver/-/semver-6.3.1.tgz",
|
||||
@@ -2644,6 +2766,27 @@
|
||||
"punycode": "^2.1.0"
|
||||
}
|
||||
},
|
||||
"webidl-conversions": {
|
||||
"version": "7.0.0",
|
||||
"resolved": "https://registry.npmjs.org/webidl-conversions/-/webidl-conversions-7.0.0.tgz",
|
||||
"integrity": "sha512-VwddBukDzu71offAQR975unBIGqfKZpM+8ZX6ySk8nYhVoo5CYaZyzt3YBvYtRtO+aoGlqxPg/B87NGVZ/fu6g==",
|
||||
"dev": true
|
||||
},
|
||||
"whatwg-encoding": {
|
||||
"version": "2.0.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-encoding/-/whatwg-encoding-2.0.0.tgz",
|
||||
"integrity": "sha512-p41ogyeMUrw3jWclHWTQg1k05DSVXPLcVxRTYsXUk+ZooOCZLcoYgPZ/HL/D/N+uQPOtcp1me1WhBEaX02mhWg==",
|
||||
"dev": true,
|
||||
"requires": {
|
||||
"iconv-lite": "0.6.3"
|
||||
}
|
||||
},
|
||||
"whatwg-mimetype": {
|
||||
"version": "3.0.0",
|
||||
"resolved": "https://registry.npmjs.org/whatwg-mimetype/-/whatwg-mimetype-3.0.0.tgz",
|
||||
"integrity": "sha512-nt+N2dzIutVRxARx1nghPKGv1xHikU7HKdfafKkLNLindmPU/ch3U31NOCGGA/dmPcmb1VlofO0vnKAcsm0o/Q==",
|
||||
"dev": true
|
||||
},
|
||||
"which": {
|
||||
"version": "2.0.2",
|
||||
"resolved": "https://registry.npmjs.org/which/-/which-2.0.2.tgz",
|
||||
|
||||
+3
-2
@@ -6,11 +6,12 @@
|
||||
"devDependencies": {
|
||||
"esbuild": "^0.25.0",
|
||||
"esbuild-plugin-inline-worker": "^0.1.1",
|
||||
"eslint": "^9.23.0"
|
||||
"eslint": "^9.23.0",
|
||||
"happy-dom": "^12.0.0"
|
||||
},
|
||||
"scripts": {
|
||||
"build": "node esbuild.config.mjs",
|
||||
"test": "echo \"Error: no test specified\" && exit 1",
|
||||
"test": "node esbuild.test.config.mjs && node --test test/bundle.test.js",
|
||||
"lint": "eslint js/**/*.js"
|
||||
},
|
||||
"dependencies": {
|
||||
|
||||
@@ -0,0 +1,93 @@
|
||||
import test from 'node:test';
|
||||
import assert from 'node:assert';
|
||||
import { Window } from 'happy-dom';
|
||||
|
||||
const window = new Window({
|
||||
url: 'https://localhost:8080'
|
||||
});
|
||||
|
||||
global.window = window;
|
||||
global.document = window.document;
|
||||
global.HTMLElement = window.HTMLElement;
|
||||
global.CustomEvent = window.CustomEvent;
|
||||
global.CSSStyleSheet = window.CSSStyleSheet;
|
||||
|
||||
// we have to mock worker too
|
||||
global.Worker = class Worker {
|
||||
constructor() {
|
||||
this.onmessage = null;
|
||||
this.onerror = null;
|
||||
}
|
||||
|
||||
postMessage(data) {
|
||||
setTimeout(() => {
|
||||
if (data.command === 'init') {
|
||||
this.onmessage?.({ data: { command: 'init' } });
|
||||
} else if (data.command === 'solve') {
|
||||
// Simulate immediate solution for zero puzzle
|
||||
this.onmessage?.({
|
||||
data: {
|
||||
command: 'solve',
|
||||
argument: {
|
||||
id: BigInt(data.argument.id || 0),
|
||||
solution: new Uint8Array(8),
|
||||
wasm: false
|
||||
}
|
||||
}
|
||||
});
|
||||
}
|
||||
}, 10);
|
||||
}
|
||||
|
||||
terminate() { }
|
||||
};
|
||||
|
||||
|
||||
test('CaptchaWidget execute() fires finished event and callback', async (t) => {
|
||||
document.body.innerHTML = `
|
||||
<form>
|
||||
<div class="private-captcha"
|
||||
data-sitekey="test_key"
|
||||
data-finished-callback="testFinishedCallback">
|
||||
</div>
|
||||
</form>
|
||||
`;
|
||||
|
||||
let callbackCalled = false;
|
||||
global.window.testFinishedCallback = (widget) => {
|
||||
callbackCalled = true;
|
||||
};
|
||||
|
||||
const { CaptchaWidget } = await import('../js/widget.js');
|
||||
|
||||
const element = document.querySelector('.private-captcha');
|
||||
assert.ok(element, 'Should find captcha element');
|
||||
|
||||
const widget = new CaptchaWidget(element, {
|
||||
sitekey: 'aaaaaaaabbbbccccddddeeeeeeeeeeee',
|
||||
debug: true
|
||||
});
|
||||
|
||||
// Set up event listener
|
||||
let eventFired = false;
|
||||
element.addEventListener('privatecaptcha:finish', (event) => {
|
||||
eventFired = true;
|
||||
assert.ok(event.detail.widget, 'Event should include widget in detail');
|
||||
assert.strictEqual(event.detail.element, element, 'Event should include element in detail');
|
||||
});
|
||||
|
||||
widget.execute();
|
||||
|
||||
// Wait for async operations to complete (assumes zero puzzle mock above)
|
||||
await new Promise(resolve => setTimeout(resolve, 150));
|
||||
|
||||
assert.strictEqual(eventFired, true, 'privatecaptcha:finish event should be fired');
|
||||
assert.strictEqual(callbackCalled, true, 'Finished callback should be called');
|
||||
|
||||
// Verify solution is available
|
||||
const solution = widget.solution();
|
||||
assert.ok(solution, 'Widget should have a solution');
|
||||
assert.ok(typeof solution === 'string', 'Solution should be a string');
|
||||
|
||||
console.log('✓ Widget execute test passed');
|
||||
});
|
||||
Reference in New Issue
Block a user