mirror of
https://github.com/mCaptcha/mCaptcha.git
synced 2026-02-14 11:34:02 +00:00
mv add form into advance
This commit is contained in:
34
templates/panel/sitekey/add/advance/add-level.html
Normal file
34
templates/panel/sitekey/add/advance/add-level.html
Normal file
@@ -0,0 +1,34 @@
|
||||
<fieldset class="sitekey__level-container" id="level-group-<.= level .>">
|
||||
<legend class="sitekey__level-title">
|
||||
Level <.= level .>
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor<.= level .>"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor<.= level .>"
|
||||
id="visitor<.= level .>"
|
||||
/>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty<.= level .>">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty<.= level .>"
|
||||
class="sitekey-form__level-input"
|
||||
id="difficulty<.= level .>"
|
||||
/>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
<span class="sitekey-form__add-level-btn-spacer">Add level</span>
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
/>
|
||||
</label>
|
||||
</fieldset>
|
||||
119
templates/panel/sitekey/add/advance/css/main.scss
Normal file
119
templates/panel/sitekey/add/advance/css/main.scss
Normal file
@@ -0,0 +1,119 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
@import '../../../../../reset';
|
||||
@import '../../../../../vars';
|
||||
@import '../../../../../components/button';
|
||||
@import '../../../../../components/forms';
|
||||
|
||||
.sitekey-form {
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 90%;
|
||||
justify-content: center;
|
||||
align-items: center;
|
||||
// box-sizing: content-box;
|
||||
background-color: $white;
|
||||
margin: auto;
|
||||
padding-bottom: 30px;
|
||||
}
|
||||
|
||||
.form__title-flex-container {
|
||||
display: flex;
|
||||
width: 100%;
|
||||
border-bottom: 0.1px solid $light-grey;
|
||||
}
|
||||
|
||||
.form__title {
|
||||
padding-left: 10px;
|
||||
font-size: 1rem;
|
||||
padding: 0.75rem 1.25rem;
|
||||
box-sizing: border-box;
|
||||
text-align: left;
|
||||
width: 100%;
|
||||
border-bottom: 0.1px solid $light-grey;
|
||||
}
|
||||
|
||||
.sitekey-form__label {
|
||||
@include form-label;
|
||||
}
|
||||
|
||||
.sitekey-form__input {
|
||||
@include form-input;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
// level styling
|
||||
.sitekey__level-container {
|
||||
width: $form-content-width;
|
||||
box-sizing: border-box;
|
||||
display: flex;
|
||||
border: none;
|
||||
}
|
||||
|
||||
.sitekey__level-title {
|
||||
margin-bottom: 10px;
|
||||
margin-top: 5px;
|
||||
}
|
||||
|
||||
.sitekey-form__level-label {
|
||||
@include form-label;
|
||||
font-size: 0.9rem;
|
||||
}
|
||||
|
||||
.sitekey-form__level-name {
|
||||
@include form-label;
|
||||
display: block;
|
||||
}
|
||||
|
||||
.sitekey-form__level-input {
|
||||
@include form-input;
|
||||
flex: 2;
|
||||
}
|
||||
|
||||
|
||||
.sitekey-form__add-level-btn-spacer {
|
||||
color: $white;
|
||||
}
|
||||
|
||||
.sitekey-form__level-add-level-button {
|
||||
@include violet-button;
|
||||
}
|
||||
|
||||
.sitekey-form__level-add-level-button:hover {
|
||||
@include violet-button-hover;
|
||||
}
|
||||
|
||||
.sitekey-form__level-label--hidden {
|
||||
@include form-label;
|
||||
color: $white;
|
||||
flex: 1;
|
||||
}
|
||||
|
||||
// level styling ends
|
||||
|
||||
.sitekey-form__submit {
|
||||
@include violet-button;
|
||||
display: block;
|
||||
margin-top: 50px;
|
||||
width: $form-content-width;
|
||||
width: 90%;
|
||||
}
|
||||
|
||||
.sitekey-form__submit:hover {
|
||||
@include violet-button-hover;
|
||||
}
|
||||
40
templates/panel/sitekey/add/advance/css/mobile.scss
Normal file
40
templates/panel/sitekey/add/advance/css/mobile.scss
Normal file
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
.sitekey__level-container {
|
||||
flex-direction: column;
|
||||
}
|
||||
|
||||
.sitekey-form__level-input {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.sitekey-form__level-label--hidden {
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
.sitekey-form__level-add-level-button {
|
||||
margin: auto;
|
||||
}
|
||||
|
||||
.sitekey-form__add-level-btn-spacer {
|
||||
display: none;
|
||||
}
|
||||
|
||||
.sitekey-form__level-label {
|
||||
width: 100%;
|
||||
}
|
||||
35
templates/panel/sitekey/add/advance/existing-level.html
Normal file
35
templates/panel/sitekey/add/advance/existing-level.html
Normal file
@@ -0,0 +1,35 @@
|
||||
<fieldset class="sitekey__level-container" id="level-group-<.= level .>">
|
||||
<legend class="sitekey__level-title">
|
||||
Level <.= level .>
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor<.= level .>"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor<.= level .>"
|
||||
value=""
|
||||
id="visitor<.= level .>"
|
||||
/>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label" for="difficulty<.= level .>">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
id="difficulty<.= level .>"
|
||||
class="sitekey-form__level-input"
|
||||
value=""
|
||||
id="difficulty<.= level .>"
|
||||
/>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove<.= level .>">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="remove"
|
||||
id="remove<.= level .>"
|
||||
value="Remove"
|
||||
/>
|
||||
</label>
|
||||
</fieldset>
|
||||
42
templates/panel/sitekey/add/advance/form.html
Normal file
42
templates/panel/sitekey/add/advance/form.html
Normal file
@@ -0,0 +1,42 @@
|
||||
<form class="sitekey-form" action="<.= crate::V1_API_ROUTES.levels.add .>" method="post">
|
||||
<h1 class="form__title">
|
||||
<.= form_title .>
|
||||
</h1>
|
||||
<label class="sitekey-form__label" for="description">
|
||||
Description
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="text"
|
||||
name="description"
|
||||
id="description"
|
||||
required
|
||||
<. if !form_description.trim().is_empty() { .>
|
||||
value="<.= form_description .>"
|
||||
<. } .>
|
||||
/>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__label" for="duration">
|
||||
Cooldown Duratoin(in seconds)
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="number"
|
||||
name="duration"
|
||||
id="duration"
|
||||
min=0
|
||||
required
|
||||
value="<.= form_duration .>"
|
||||
/>
|
||||
</label>
|
||||
|
||||
|
||||
<. for level in 1..=levels { .>
|
||||
<. if level == levels { .>
|
||||
<. include!("./add-level.html"); .>
|
||||
<. } else { .>
|
||||
<. include!("./existing-level.html"); .>
|
||||
<. } .>
|
||||
<. } .>
|
||||
|
||||
<button class="sitekey-form__submit" type="submit">Submit</button>
|
||||
</form>
|
||||
15
templates/panel/sitekey/add/advance/index.html
Normal file
15
templates/panel/sitekey/add/advance/index.html
Normal file
@@ -0,0 +1,15 @@
|
||||
<. include!("../../../../components/headers/index.html"); .>
|
||||
<. include!("../../../navbar/index.html"); .>
|
||||
<div class="tmp-layout">
|
||||
<. include!("../../../header/index.html"); .>
|
||||
|
||||
<main class="panel-main">
|
||||
<. include!("../../../help-banner/index.html"); .>
|
||||
<!-- Main content container -->
|
||||
<div class="inner-container">
|
||||
<!-- Main menu/ important actions roaster -->
|
||||
|
||||
<. include!("./form.html"); .>
|
||||
</div>
|
||||
<!-- end of container -->
|
||||
<. include!("../../../../components/footers.html"); .>
|
||||
198
templates/panel/sitekey/add/advance/ts/addLevelButton.test.ts
Normal file
198
templates/panel/sitekey/add/advance/ts/addLevelButton.test.ts
Normal file
@@ -0,0 +1,198 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import getNumLevels from "./levels/getNumLevels";
|
||||
import {getAddForm, trim, addLevel} from "./setupTests";
|
||||
import setup from "../../../../../components/error/setUpTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
document.body.appendChild(setup());
|
||||
|
||||
jest.useFakeTimers();
|
||||
|
||||
it("addLevelButton works", () => {
|
||||
expect(getNumLevels()).toBe(1);
|
||||
// add a level
|
||||
addLevel(2, 4);
|
||||
expect(getNumLevels()).toBe(2);
|
||||
|
||||
|
||||
|
||||
// add second level
|
||||
addLevel(4, 9);
|
||||
expect(getNumLevels()).toBe(3);
|
||||
|
||||
const a = document.body.innerHTML;
|
||||
|
||||
|
||||
expect(trim(a)).toBe(trim(finalHtml()));
|
||||
|
||||
// try to add duplicate level
|
||||
addLevel(2, 4);
|
||||
expect(getNumLevels()).toBe(3);
|
||||
|
||||
// try to add negative parameters
|
||||
addLevel(-4, -9);
|
||||
expect(getNumLevels()).toBe(3);
|
||||
});
|
||||
|
||||
const finalHtml = () => {
|
||||
return `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<h1 class="form__title">
|
||||
Add Sitekey
|
||||
</h1>
|
||||
<label class="sitekey-form__label" for="description">
|
||||
Description
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="text"
|
||||
name="description"
|
||||
id="description"
|
||||
required=""
|
||||
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__label" for="duration">
|
||||
Cooldown Duratoin(in seconds)
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="number"
|
||||
name="duration"
|
||||
id="duration"
|
||||
min="0"
|
||||
required=""
|
||||
value="30"
|
||||
>
|
||||
</label>
|
||||
|
||||
<fieldset class="sitekey__level-container" id="level-group-1">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 1
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor1"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor1"
|
||||
|
||||
id="visitor1"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty1">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty1"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty1"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level1">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level1"
|
||||
id="remove-level1"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
<fieldset class="sitekey__level-container" id="level-group-2">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 2
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor2"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor2"
|
||||
|
||||
id="visitor2"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty2">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty2"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty2"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level2">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level2"
|
||||
id="remove-level2"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
<fieldset class="sitekey__level-container" id="level-group-3">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 3
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor3"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor3"
|
||||
|
||||
id="visitor3"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty3">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty3"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty3"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
|
||||
<button class="sitekey-form__submit" type="submit">Submit</button>
|
||||
</form>
|
||||
<div id="err__container">
|
||||
</div>
|
||||
`;
|
||||
};
|
||||
135
templates/panel/sitekey/add/advance/ts/addLevelButton.ts
Normal file
135
templates/panel/sitekey/add/advance/ts/addLevelButton.ts
Normal file
@@ -0,0 +1,135 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import validateLevel from "./levels/validateLevel";
|
||||
import getNumLevels from "./levels/getNumLevels";
|
||||
import * as UpdateLevel from "./levels/updateLevel";
|
||||
import {
|
||||
getRemoveButtonHTML,
|
||||
addRemoveLevelButtonEventListener,
|
||||
} from "./removeLevelButton";
|
||||
import CONST from "./const";
|
||||
|
||||
import log from "../../../../../logger";
|
||||
|
||||
/**
|
||||
* Gets executed when 'Add' Button is clicked to add levels
|
||||
* Used to validate levels per m_captcha::defense::Defense's
|
||||
* specifications
|
||||
*/
|
||||
const addLevel = (e: Event) => {
|
||||
const eventTarget = <HTMLElement>e.target;
|
||||
const PARENT = <HTMLLabelElement>eventTarget.parentElement;
|
||||
const FIELDSET = <HTMLElement>PARENT.parentElement;
|
||||
const onScreenLevel = getNumLevels();
|
||||
|
||||
const isValid = validateLevel(onScreenLevel);
|
||||
log.debug(`[addLevelButton] isValid: ${isValid}`);
|
||||
if (!isValid) {
|
||||
const error = `Aborting level ${onScreenLevel} addition`;
|
||||
return log.error(error);
|
||||
}
|
||||
|
||||
FIELDSET.replaceChild(getRemoveButtonHTML(onScreenLevel), PARENT);
|
||||
|
||||
const newLevelElement = getHtml(onScreenLevel + 1);
|
||||
FIELDSET.insertAdjacentElement("afterend", newLevelElement);
|
||||
UpdateLevel.register(onScreenLevel);
|
||||
|
||||
addRemoveLevelButtonEventListener(onScreenLevel);
|
||||
addLevelButtonAddEventListener();
|
||||
const main = document.querySelector("body");
|
||||
const style = main.style.display;
|
||||
main.style.display = "none";
|
||||
main.style.display = style;
|
||||
};
|
||||
|
||||
/** adds onclick event listener */
|
||||
const addLevelButtonAddEventListener = (): void => {
|
||||
const addLevelButton = <HTMLElement>(
|
||||
document.querySelector(`.${CONST.ADD_LEVEL_BUTTON}`)
|
||||
);
|
||||
addLevelButton.addEventListener("click", addLevel);
|
||||
};
|
||||
|
||||
/**
|
||||
* Generate HTML to be added when 'Add Level' button is clicked
|
||||
* Check if './add-level.html` to see if this is up to date
|
||||
*/
|
||||
const getHtml = (level: number) => {
|
||||
log.debug(`[generating HTML getHtml]level: ${level}`);
|
||||
|
||||
const fieldset = document.createElement("fieldset"); // new HTMLFieldSetElement();
|
||||
fieldset.className = CONST.LEVEL_CONTAINER_CLASS;
|
||||
fieldset.id = `${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${level}`;
|
||||
|
||||
const legend = document.createElement("legend"); // new HTMLLegendElement();
|
||||
legend.className = CONST.LEGEND_CLASS;
|
||||
const legendText = document.createTextNode(`Level ${level}`);
|
||||
legend.appendChild(legendText);
|
||||
|
||||
fieldset.appendChild(legend);
|
||||
|
||||
const vistitorLabel = document.createElement("label"); //document.createElement('label');
|
||||
vistitorLabel.className = CONST.LABEL_CLASS;
|
||||
const visitorText = document.createTextNode("Visitor");
|
||||
vistitorLabel.appendChild(visitorText);
|
||||
const visitor = document.createElement("input"); //document.createElement('input');
|
||||
const visitorId = `${CONST.VISITOR_WITHOUT_LEVEL}${level}`;
|
||||
visitor.className = CONST.LEVEL_INPUT_CLASS;
|
||||
visitor.type = "number";
|
||||
visitor.name = visitorId;
|
||||
visitor.id = visitorId;
|
||||
vistitorLabel.htmlFor = visitorId;
|
||||
vistitorLabel.appendChild(visitor);
|
||||
|
||||
fieldset.appendChild(vistitorLabel);
|
||||
|
||||
const difficultyLabel = document.createElement("label");
|
||||
difficultyLabel.className = CONST.LABEL_CLASS;
|
||||
const difficultyText = document.createTextNode("Difficulty");
|
||||
difficultyLabel.appendChild(difficultyText);
|
||||
const difficulty = document.createElement("input");
|
||||
const difficultyID = `${CONST.DIFFICULTY_WITHOUT_LEVEL}${level}`;
|
||||
difficulty.type = "number";
|
||||
difficulty.name = difficultyID;
|
||||
difficulty.className = CONST.LEVEL_INPUT_CLASS;
|
||||
difficulty.id = difficultyID;
|
||||
difficultyLabel.htmlFor = difficultyID;
|
||||
difficultyLabel.appendChild(difficulty);
|
||||
|
||||
fieldset.appendChild(difficultyLabel);
|
||||
|
||||
const addLevelLabel = document.createElement("label");
|
||||
addLevelLabel.className = CONST.REMOVE_LEVEL_LABEL_CLASS;
|
||||
const addLevel = document.createElement("input");
|
||||
addLevel.className = CONST.ADD_LEVEL_BUTTON;
|
||||
addLevel.type = "button";
|
||||
const addLevelButtonID = "add";
|
||||
addLevel.name = addLevelButtonID;
|
||||
addLevel.id = addLevelButtonID;
|
||||
addLevelLabel.htmlFor = addLevelButtonID;
|
||||
const addText = document.createTextNode("Add level");
|
||||
addLevelLabel.appendChild(addText);
|
||||
addLevel.value = "Add";
|
||||
addLevelLabel.appendChild(addLevel);
|
||||
|
||||
fieldset.appendChild(addLevelLabel);
|
||||
|
||||
return fieldset;
|
||||
};
|
||||
|
||||
export default addLevelButtonAddEventListener;
|
||||
55
templates/panel/sitekey/add/advance/ts/const.ts
Normal file
55
templates/panel/sitekey/add/advance/ts/const.ts
Normal file
@@ -0,0 +1,55 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
const LABEL_INNER_TEXT_WITHOUT_LEVEL = "Level ";
|
||||
const LABEL_CLASS = "sitekey-form__level-label";
|
||||
|
||||
const INPUT_ID_WITHOUT_LEVEL = "level";
|
||||
const LEVEL_INPUT_CLASS = "sitekey-form__level-input";
|
||||
|
||||
const VISITOR_WITHOUT_LEVEL = "visitor";
|
||||
const DIFFICULTY_WITHOUT_LEVEL = "difficulty";
|
||||
|
||||
const LEVEL_CONTAINER_CLASS = "sitekey__level-container";
|
||||
const LEVEL_FIELDSET_ID_WITHOUT_LEVEL = "level-group-";
|
||||
const LEGEND_CLASS = "sitekey__level-title";
|
||||
|
||||
const REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL = "remove-level";
|
||||
const REMOVE_LEVEL_BUTTON_CLASS = "sitekey-form__level-remove-level-button";
|
||||
const REMOVE_LEVEL_LABEL_TEXT = "Remove Level";
|
||||
const REMOVE_LEVEL_LABEL_CLASS = "sitekey-form__level-label--hidden";
|
||||
|
||||
const ADD_LEVEL_BUTTON = "sitekey-form__level-add-level-button";
|
||||
|
||||
const CONST = {
|
||||
LABEL_CLASS,
|
||||
INPUT_ID_WITHOUT_LEVEL,
|
||||
LEVEL_INPUT_CLASS,
|
||||
LABEL_INNER_TEXT_WITHOUT_LEVEL,
|
||||
VISITOR_WITHOUT_LEVEL,
|
||||
DIFFICULTY_WITHOUT_LEVEL,
|
||||
LEVEL_CONTAINER_CLASS,
|
||||
LEVEL_FIELDSET_ID_WITHOUT_LEVEL,
|
||||
LEGEND_CLASS,
|
||||
ADD_LEVEL_BUTTON,
|
||||
REMOVE_LEVEL_LABEL_CLASS,
|
||||
REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL,
|
||||
REMOVE_LEVEL_LABEL_TEXT,
|
||||
REMOVE_LEVEL_BUTTON_CLASS,
|
||||
};
|
||||
|
||||
export default CONST;
|
||||
67
templates/panel/sitekey/add/advance/ts/form/index.ts
Normal file
67
templates/panel/sitekey/add/advance/ts/form/index.ts
Normal file
@@ -0,0 +1,67 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { LEVELS } from "../levels";
|
||||
|
||||
import getFormUrl from "../../../../../../utils/getFormUrl";
|
||||
import genJsonPayload from "../../../../../../utils/genJsonPayload";
|
||||
|
||||
import VIEWS from "../../../../../../views/v1/routes";
|
||||
|
||||
import validateDescription from "./validateDescription";
|
||||
import validateDuration from "./validateDuration";
|
||||
|
||||
import createError from "../../../../../../components/error";
|
||||
|
||||
export const SITE_KEY_FORM_CLASS = "sitekey-form";
|
||||
export const FORM = <HTMLFormElement>(
|
||||
document.querySelector(`.${SITE_KEY_FORM_CLASS}`)
|
||||
);
|
||||
|
||||
export const addSubmitEventListener = (): void =>
|
||||
FORM.addEventListener("submit", submit, true);
|
||||
|
||||
const submit = async (e: Event) => {
|
||||
e.preventDefault();
|
||||
|
||||
const description = validateDescription(e);
|
||||
const duration = validateDuration();
|
||||
|
||||
const formUrl = getFormUrl(FORM);
|
||||
|
||||
const levels = LEVELS.getLevels();
|
||||
console.debug(`[form submition]: levels: ${levels}`);
|
||||
|
||||
const payload = {
|
||||
levels: levels,
|
||||
duration,
|
||||
description,
|
||||
};
|
||||
|
||||
console.debug(`[form submition] json payload: ${JSON.stringify(payload)}`);
|
||||
|
||||
const res = await fetch(formUrl, genJsonPayload(payload));
|
||||
if (res.ok) {
|
||||
const data = await res.json();
|
||||
window.location.assign(VIEWS.viewSitekey(data.key));
|
||||
} else {
|
||||
const err = await res.json();
|
||||
createError(err.error);
|
||||
}
|
||||
};
|
||||
|
||||
export default addSubmitEventListener;
|
||||
@@ -0,0 +1,43 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import validateDescription from "./validateDescription";
|
||||
import {getAddForm, fillDescription} from "../setupTests";
|
||||
import {mockAlert} from "../../../../../../setUpTests";
|
||||
|
||||
import setup from "../../../../../../components/error/setUpTests";
|
||||
|
||||
mockAlert();
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
const emptyErr = "can't be empty";
|
||||
|
||||
it("validateDescription workds", () => {
|
||||
document.querySelector("body").appendChild(setup());
|
||||
try {
|
||||
const event = new Event("submit");
|
||||
validateDescription(event);
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(emptyErr);
|
||||
}
|
||||
|
||||
// fill and validate
|
||||
fillDescription("testing");
|
||||
const event = new Event("submit");
|
||||
validateDescription(event);
|
||||
});
|
||||
@@ -0,0 +1,28 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import isBlankString from "../../../../../../utils/isBlankString";
|
||||
|
||||
const validateDescription = (e: Event): string => {
|
||||
const inputElement = <HTMLInputElement>document.getElementById("description");
|
||||
const val = inputElement.value;
|
||||
const filed = "Description";
|
||||
isBlankString(val, filed, e);
|
||||
return val;
|
||||
};
|
||||
|
||||
export default validateDescription;
|
||||
@@ -0,0 +1,68 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
//const validateDuration = (e: Event) => {
|
||||
// const duartionElement = <HTMLInputElement>document.getElementById('duration');
|
||||
// const duration = parseInt(duartionElement.value);
|
||||
// if (!isNumber(duration) || Number.isNaN(duration)) {
|
||||
// throw new Error('duration can contain nubers only');
|
||||
// }
|
||||
//
|
||||
// if (duration <= 0) {
|
||||
// throw new Error('duration must be greater than zero');
|
||||
// }
|
||||
// return duration;
|
||||
//};
|
||||
//
|
||||
//export default validateDuration;
|
||||
|
||||
import validateDuration from "./validateDuration";
|
||||
import {getAddForm, fillDuration} from "../setupTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
const emptyErr = "can't be empty";
|
||||
const NaNErr = "duration can contain nubers only";
|
||||
const zeroErr = "duration must be greater than zero";
|
||||
|
||||
const duration = 30;
|
||||
|
||||
it("validateDuration workds", () => {
|
||||
try {
|
||||
validateDuration();
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(emptyErr);
|
||||
}
|
||||
|
||||
// fill string error
|
||||
try {
|
||||
fillDuration("testing");
|
||||
validateDuration();
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(NaNErr);
|
||||
}
|
||||
|
||||
// zero err
|
||||
try {
|
||||
fillDuration(0);
|
||||
validateDuration();
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(zeroErr);
|
||||
}
|
||||
|
||||
fillDuration(duration);
|
||||
expect(validateDuration()).toBe(duration);
|
||||
});
|
||||
@@ -0,0 +1,32 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import isNumber from "../../../../../../utils/isNumber";
|
||||
|
||||
const validateDuration = (): number => {
|
||||
const duartionElement = <HTMLInputElement>document.getElementById("duration");
|
||||
const duration = parseInt(duartionElement.value);
|
||||
if (!isNumber(duration) || Number.isNaN(duration)) {
|
||||
throw new Error("duration can contain nubers only");
|
||||
}
|
||||
|
||||
if (duration <= 0) {
|
||||
throw new Error("duration must be greater than zero");
|
||||
}
|
||||
return duration;
|
||||
};
|
||||
|
||||
export default validateDuration;
|
||||
24
templates/panel/sitekey/add/advance/ts/index.ts
Normal file
24
templates/panel/sitekey/add/advance/ts/index.ts
Normal file
@@ -0,0 +1,24 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import addLevelButtonAddEventListener from "./addLevelButton";
|
||||
import addSubmitEventListener from "./form";
|
||||
|
||||
export const index = (): void => {
|
||||
addLevelButtonAddEventListener();
|
||||
addSubmitEventListener();
|
||||
};
|
||||
@@ -0,0 +1,54 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import getLevelFields from "./getLevelFields";
|
||||
import {
|
||||
getAddForm,
|
||||
level1,
|
||||
level2,
|
||||
fillAddLevel,
|
||||
addLevel,
|
||||
} from "../setupTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
const visNumErr = "visitor can contain nubers only";
|
||||
const diffNumErr = "difficulty can contain nubers only";
|
||||
|
||||
it("get levels fields works", () => {
|
||||
addLevel(level1.visitor_threshold, level1.difficulty_factor);
|
||||
expect(getLevelFields(1)).toEqual(level1);
|
||||
|
||||
// NaN visitor
|
||||
try {
|
||||
fillAddLevel("test", level2.difficulty_factor);
|
||||
getLevelFields(2);
|
||||
} catch (e) {
|
||||
expect(e.message).toBe(visNumErr);
|
||||
}
|
||||
|
||||
// Nan difficulty_factor
|
||||
try {
|
||||
fillAddLevel(level2.visitor_threshold, "fooasdads");
|
||||
getLevelFields(2);
|
||||
} catch (e) {
|
||||
expect(e.message).toBe(diffNumErr);
|
||||
}
|
||||
|
||||
addLevel(level2.visitor_threshold, level2.difficulty_factor);
|
||||
expect(getLevelFields(2)).toEqual(level2);
|
||||
});
|
||||
@@ -0,0 +1,57 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { Level } from "./index";
|
||||
import CONST from "../const";
|
||||
|
||||
import log from "../../../../../../logger";
|
||||
|
||||
/** Fetches level from DOM using the ID passesd and validates */
|
||||
const getLevelFields = (id: number): Level => {
|
||||
log.debug(`[getLevelFields]: id: ${id}`);
|
||||
const visitorID = CONST.VISITOR_WITHOUT_LEVEL + id.toString();
|
||||
const difficultyID = CONST.DIFFICULTY_WITHOUT_LEVEL + id.toString();
|
||||
|
||||
const visitorElement = <HTMLInputElement>document.getElementById(visitorID);
|
||||
const difficultyElement = <HTMLInputElement>(
|
||||
document.getElementById(difficultyID)
|
||||
);
|
||||
|
||||
const visitor_threshold = parseInt(visitorElement.value);
|
||||
const difficulty_factor = parseInt(difficultyElement.value);
|
||||
|
||||
if (Number.isNaN(visitor_threshold)) {
|
||||
throw new Error("visitor can contain nubers only");
|
||||
}
|
||||
|
||||
if (Number.isNaN(difficulty_factor)) {
|
||||
throw new Error("difficulty can contain nubers only");
|
||||
}
|
||||
|
||||
const level: Level = {
|
||||
difficulty_factor,
|
||||
visitor_threshold,
|
||||
};
|
||||
|
||||
log.debug(
|
||||
`[getLevelFields.ts] visitor: ${visitor_threshold} difficulty: ${difficulty_factor}`
|
||||
);
|
||||
|
||||
return level;
|
||||
};
|
||||
|
||||
export default getLevelFields;
|
||||
@@ -0,0 +1,29 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import getNumLevels from "./getNumLevels";
|
||||
import {getAddForm, addLevel} from "../setupTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
it("get num levels works", () => {
|
||||
expect(getNumLevels()).toBe(1);
|
||||
addLevel(2, 4);
|
||||
expect(getNumLevels()).toBe(2);
|
||||
addLevel(4, 9);
|
||||
expect(getNumLevels()).toBe(3);
|
||||
});
|
||||
@@ -0,0 +1,32 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import CONST from "../const";
|
||||
|
||||
import log from "../../../../../../logger";
|
||||
|
||||
/** returns number of level input fields currently in DOM */
|
||||
const getNumLevels = (): number => {
|
||||
let numLevels = 0;
|
||||
document
|
||||
.querySelectorAll(`.${CONST.LEVEL_CONTAINER_CLASS}`)
|
||||
.forEach(() => numLevels++);
|
||||
log.debug(`[getNumLevels]: numLevels: ${numLevels}`);
|
||||
return numLevels;
|
||||
};
|
||||
|
||||
export default getNumLevels;
|
||||
145
templates/panel/sitekey/add/advance/ts/levels/index.ts
Normal file
145
templates/panel/sitekey/add/advance/ts/levels/index.ts
Normal file
@@ -0,0 +1,145 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import log from "../../../../../../logger";
|
||||
|
||||
/** Datatype represenging an mCaptcha level */
|
||||
export type Level = {
|
||||
difficulty_factor: number;
|
||||
visitor_threshold: number;
|
||||
};
|
||||
|
||||
/** Datatype representing a collection of mCaptcha levels */
|
||||
class Levels {
|
||||
levels: Array<Level>;
|
||||
|
||||
constructor() {
|
||||
this.levels = [];
|
||||
}
|
||||
|
||||
add = (newLevel: Level) => {
|
||||
log.debug(`[levels/index.ts] levels lenght: ${this.levels.length}`);
|
||||
if (newLevel.difficulty_factor <= 0) {
|
||||
throw new Error(
|
||||
`Level ${this.levels.length}'s difficulty must be greater than zero`,
|
||||
);
|
||||
}
|
||||
|
||||
if (newLevel.visitor_threshold <= 0) {
|
||||
throw new Error(
|
||||
`Level ${this.levels.length}'s visitors must be greater than zero`,
|
||||
);
|
||||
}
|
||||
|
||||
if (this.levels.length == 0) {
|
||||
this.levels.push(newLevel);
|
||||
return true;
|
||||
}
|
||||
|
||||
let count = 1;
|
||||
|
||||
this.levels.forEach(level => {
|
||||
if (level.visitor_threshold >= newLevel.visitor_threshold) {
|
||||
const msg = `Level ${this.levels.length}'s visitor count should be greater than previous levels(Level ${count} is greater)`;
|
||||
throw new Error(msg);
|
||||
} else if (level.difficulty_factor >= newLevel.difficulty_factor) {
|
||||
const msg = `Level ${this.levels.length} difficulty should be greater than previous levels(Level ${count} is greater)`;
|
||||
throw new Error(msg);
|
||||
} else {
|
||||
count++;
|
||||
}
|
||||
});
|
||||
|
||||
this.levels.push(newLevel);
|
||||
};
|
||||
|
||||
get = () => this.levels;
|
||||
}
|
||||
|
||||
/** Singleton that does manipulations on Levels object */
|
||||
export const LEVELS = (function() {
|
||||
const levels = new Levels();
|
||||
|
||||
return {
|
||||
/** get levels */
|
||||
getLevels: () => levels.get(),
|
||||
|
||||
/** add new level */
|
||||
add: (newLevel: Level) => levels.add(newLevel),
|
||||
|
||||
/** update levels */
|
||||
update: (updateLevel: Level, id: number) => {
|
||||
const tmpLevel = new Levels();
|
||||
|
||||
id -= 1;
|
||||
try {
|
||||
for (let i = 0; i < levels.levels.length; i++) {
|
||||
if (id == i) {
|
||||
tmpLevel.add(updateLevel);
|
||||
} else {
|
||||
tmpLevel.add(levels.levels[i]);
|
||||
}
|
||||
}
|
||||
levels.levels = tmpLevel.levels;
|
||||
log.debug("post update:");
|
||||
LEVELS.print();
|
||||
return true;
|
||||
} catch (e) {
|
||||
log.debug(e);
|
||||
return false;
|
||||
}
|
||||
},
|
||||
|
||||
print: () =>
|
||||
levels.levels.forEach(level =>
|
||||
log.debug(
|
||||
`difficulty_factor: ${level.difficulty_factor} visitor ${level.visitor_threshold}`,
|
||||
),
|
||||
),
|
||||
|
||||
/** remove level */
|
||||
remove: (id: number) => {
|
||||
log.debug(`[LEVELS] received order to remove ${id} element`);
|
||||
|
||||
const tmpLevel = new Levels();
|
||||
|
||||
id -= 1;
|
||||
try {
|
||||
for (let i = 0; i < levels.levels.length; i++) {
|
||||
if (id != i) {
|
||||
tmpLevel.add(levels.levels[i]);
|
||||
} else {
|
||||
log.debug(`[LEVELS] removing ${i} element`);
|
||||
const rmElement = levels.levels[i];
|
||||
log.debug(
|
||||
`[LEVELS] removing element:
|
||||
difficulty_factor: ${rmElement.difficulty_factor}
|
||||
visitor_threshold: ${rmElement.visitor_threshold}`,
|
||||
);
|
||||
}
|
||||
}
|
||||
levels.levels = tmpLevel.levels;
|
||||
log.debug("Post remove:");
|
||||
LEVELS.print();
|
||||
return true;
|
||||
} catch (e) {
|
||||
log.debug(e);
|
||||
return false;
|
||||
}
|
||||
},
|
||||
};
|
||||
})();
|
||||
82
templates/panel/sitekey/add/advance/ts/levels/levels.test.ts
Normal file
82
templates/panel/sitekey/add/advance/ts/levels/levels.test.ts
Normal file
@@ -0,0 +1,82 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import {LEVELS, Level} from "./index";
|
||||
import {level1, level1visErr, level1diffErr, level2} from "../setupTests";
|
||||
|
||||
const visitorErr = "visitor count should be greater than previous levels";
|
||||
const difficultyErr = "difficulty should be greater than previous levels";
|
||||
|
||||
const zeroVisError = "visitors must be greater than zero";
|
||||
const zeroDiffError = "difficulty must be greater than zero";
|
||||
|
||||
const zeroVis: Level = {
|
||||
difficulty_factor: 10,
|
||||
visitor_threshold: 0,
|
||||
};
|
||||
|
||||
const zeroDiff: Level = {
|
||||
difficulty_factor: 0,
|
||||
visitor_threshold: 10,
|
||||
};
|
||||
|
||||
it("LEVELS works", () => {
|
||||
// add level
|
||||
LEVELS.add(level1);
|
||||
expect(LEVELS.getLevels()).toEqual([level1]);
|
||||
|
||||
// add visitor count < prev level
|
||||
try {
|
||||
LEVELS.add(level1visErr);
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(visitorErr);
|
||||
}
|
||||
|
||||
// add difficulty < prev level
|
||||
try {
|
||||
LEVELS.add(level1diffErr);
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(difficultyErr);
|
||||
}
|
||||
|
||||
// add second level
|
||||
LEVELS.add(level2);
|
||||
expect(LEVELS.getLevels()).toEqual([level1, level2]);
|
||||
|
||||
// update level
|
||||
const newLevel2 = level2;
|
||||
newLevel2.difficulty_factor = 8000;
|
||||
LEVELS.update(newLevel2, 2);
|
||||
expect(LEVELS.getLevels()).toEqual([level1, newLevel2]);
|
||||
|
||||
// update second level
|
||||
LEVELS.remove(1);
|
||||
expect(LEVELS.getLevels()).toEqual([newLevel2]);
|
||||
|
||||
// visitor is 0
|
||||
try {
|
||||
LEVELS.add(zeroVis);
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(zeroVisError);
|
||||
}
|
||||
// difficulty is 0
|
||||
try {
|
||||
LEVELS.add(zeroDiff);
|
||||
} catch (e) {
|
||||
expect(e.message).toContain(zeroDiffError);
|
||||
}
|
||||
});
|
||||
62
templates/panel/sitekey/add/advance/ts/levels/updateLevel.ts
Normal file
62
templates/panel/sitekey/add/advance/ts/levels/updateLevel.ts
Normal file
@@ -0,0 +1,62 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import CONST from "../const";
|
||||
import getLevelFields from "./getLevelFields";
|
||||
import { LEVELS } from "./index";
|
||||
|
||||
import createError from "../../../../../../components/error";
|
||||
|
||||
/** on-change event handler to update level */
|
||||
const updateLevel = (e: Event): void => {
|
||||
const target = <HTMLInputElement>e.target;
|
||||
|
||||
const id = target.id;
|
||||
|
||||
let level;
|
||||
if (id.includes(CONST.VISITOR_WITHOUT_LEVEL)) {
|
||||
level = parseInt(id.slice(CONST.VISITOR_WITHOUT_LEVEL.length));
|
||||
}
|
||||
if (id.includes(CONST.DIFFICULTY_WITHOUT_LEVEL)) {
|
||||
level = parseInt(id.slice(CONST.DIFFICULTY_WITHOUT_LEVEL.length));
|
||||
}
|
||||
|
||||
if (Number.isNaN(level)) {
|
||||
console.error("[updateLevel.ts] level # computed is not correct, got NaN");
|
||||
}
|
||||
|
||||
try {
|
||||
const updatedLevel = getLevelFields(level);
|
||||
LEVELS.update(updatedLevel, level);
|
||||
} catch (e) {
|
||||
createError(e.message);
|
||||
}
|
||||
};
|
||||
|
||||
/** registers on-change event handlers to update levels */
|
||||
export const register = (id: number): void => {
|
||||
const visitorID = CONST.VISITOR_WITHOUT_LEVEL + id.toString();
|
||||
const difficultyID = CONST.DIFFICULTY_WITHOUT_LEVEL + id.toString();
|
||||
|
||||
const visitorElement = <HTMLInputElement>document.getElementById(visitorID);
|
||||
const difficultyElement = <HTMLInputElement>(
|
||||
document.getElementById(difficultyID)
|
||||
);
|
||||
|
||||
visitorElement.addEventListener("input", updateLevel, false);
|
||||
difficultyElement.addEventListener("input", updateLevel, false);
|
||||
};
|
||||
@@ -0,0 +1,40 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import validateLevel from "./validateLevel";
|
||||
import {getAddForm, level1, fillAddLevel} from "../setupTests";
|
||||
import setup from "../../../../../../components/error/setUpTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
document.body.appendChild(setup());
|
||||
|
||||
it("validate levels fields works", () => {
|
||||
// null error
|
||||
expect(validateLevel(1)).toEqual(false);
|
||||
|
||||
fillAddLevel(level1.visitor_threshold, level1.difficulty_factor);
|
||||
expect(validateLevel(1)).toEqual(true);
|
||||
|
||||
// zero visitor error
|
||||
fillAddLevel(0, level1.difficulty_factor);
|
||||
expect(validateLevel(1)).toEqual(false);
|
||||
|
||||
// zero difficulty error
|
||||
fillAddLevel(level1.visitor_threshold, 0);
|
||||
expect(validateLevel(1)).toEqual(false);
|
||||
});
|
||||
@@ -0,0 +1,37 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import {LEVELS} from "./index";
|
||||
import getLevelFields from "./getLevelFields";
|
||||
import createError from "../../../../../../components/error/";
|
||||
|
||||
/**
|
||||
* Fetches level from DOM using the ID passesd and validates
|
||||
* its contents
|
||||
* */
|
||||
const validateLevel = (id: number): boolean => {
|
||||
try {
|
||||
const level = getLevelFields(id);
|
||||
LEVELS.add(level);
|
||||
return true;
|
||||
} catch (e) {
|
||||
createError(e.message);
|
||||
return false;
|
||||
}
|
||||
};
|
||||
|
||||
export default validateLevel;
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import { LEVELS } from "../levels/index";
|
||||
import updateLevelNumbersOnDOM from "./updateDom";
|
||||
import CONST from "../const";
|
||||
|
||||
import log from "../../../../../../logger";
|
||||
|
||||
const REMOVE_LEVEL_BUTTON = "sitekey-form__level-remove-level-button";
|
||||
|
||||
/**
|
||||
* Gets executed when 'Remove' Button is clicked to remove levels
|
||||
*/
|
||||
const removeLevel = (e: Event) => {
|
||||
const eventTarget = <HTMLElement>e.target;
|
||||
const PARENT = <HTMLElement>eventTarget.parentElement;
|
||||
const FIELDSET = <HTMLElement>PARENT.parentElement;
|
||||
|
||||
const levelNum = parseInt(
|
||||
eventTarget.id.slice(CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL.length)
|
||||
);
|
||||
|
||||
if (Number.isNaN(levelNum)) {
|
||||
const msg =
|
||||
"[removeLevelButton.ts] error in parsing level number from remove button ID";
|
||||
//log.error(msg);
|
||||
throw new Error(msg);
|
||||
}
|
||||
updateLevelNumbersOnDOM(levelNum);
|
||||
|
||||
LEVELS.remove(levelNum);
|
||||
FIELDSET.remove();
|
||||
};
|
||||
|
||||
/** adds onclick event listener */
|
||||
export const addRemoveLevelButtonEventListener = (level: number): void => {
|
||||
const removeButton = document.getElementById(
|
||||
`${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${level}`
|
||||
);
|
||||
|
||||
removeButton.addEventListener("click", removeLevel);
|
||||
};
|
||||
|
||||
/** adds onclick event listener to all remove buttons */
|
||||
export const addRemoveLevelButtonEventListenerAll = (): void => {
|
||||
const removeButtons = document.querySelectorAll(`.${REMOVE_LEVEL_BUTTON}`);
|
||||
removeButtons.forEach((button) =>
|
||||
button.addEventListener("click", removeLevel)
|
||||
);
|
||||
};
|
||||
|
||||
/**
|
||||
* Generate Remove button HTML. On-click handler should be added
|
||||
* seprately
|
||||
*/
|
||||
export const getRemoveButtonHTML = (level: number): HTMLLabelElement => {
|
||||
log.log(`[generating HTML getHtml]level: ${level}`);
|
||||
|
||||
const btn = document.createElement("input");
|
||||
btn.className = CONST.REMOVE_LEVEL_BUTTON_CLASS;
|
||||
btn.type = "button";
|
||||
const id = `${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${level}`;
|
||||
btn.name = id;
|
||||
btn.id = id;
|
||||
btn.value = "x";
|
||||
|
||||
const removeLabel = document.createElement("label");
|
||||
removeLabel.className = CONST.REMOVE_LEVEL_LABEL_CLASS;
|
||||
const removeLabelText = document.createTextNode("RemoveLevel");
|
||||
removeLabel.appendChild(removeLabelText);
|
||||
removeLabel.appendChild(btn);
|
||||
removeLabel.htmlFor = id;
|
||||
|
||||
return removeLabel;
|
||||
};
|
||||
@@ -0,0 +1,60 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import getNumLevels from "../levels/getNumLevels";
|
||||
import { getAddForm, addLevel } from "../setupTests";
|
||||
import CONST from "../const";
|
||||
|
||||
import log from "../../../../../../logger";
|
||||
import { MODE } from "../../../../../../logger";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
const setUp = () => {
|
||||
expect(getNumLevels()).toBe(1);
|
||||
// add a level
|
||||
addLevel(2, 2);
|
||||
expect(getNumLevels()).toBe(2);
|
||||
|
||||
// add second level
|
||||
addLevel(4, 4);
|
||||
expect(getNumLevels()).toBe(3);
|
||||
|
||||
// add thrid level
|
||||
addLevel(5, 5);
|
||||
expect(getNumLevels()).toBe(4);
|
||||
};
|
||||
|
||||
log.setMode(MODE.none);
|
||||
|
||||
it("removeLevelButton works", () => {
|
||||
setUp();
|
||||
|
||||
for (let i = 1; i < 4; i++) {
|
||||
const l1 = <HTMLButtonElement>(
|
||||
document.getElementById(
|
||||
`${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${1}`
|
||||
)
|
||||
);
|
||||
|
||||
const expecting = 4 - i;
|
||||
|
||||
l1.click();
|
||||
const currentLevels = getNumLevels();
|
||||
expect(currentLevels).toBe(expecting);
|
||||
}
|
||||
});
|
||||
@@ -0,0 +1,89 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import getNumLevels from "../../levels/getNumLevels";
|
||||
import CONST from "../../const";
|
||||
import log from "../../../../../../../logger";
|
||||
|
||||
import updateLabels from "./updateLabel";
|
||||
import updateInputs from "./updateInputs";
|
||||
import updateRemoveButton from "./updateRemoveButton";
|
||||
import updateLevelGroup from "./updateLevelGroup";
|
||||
|
||||
/**
|
||||
* update level number on fieldset legends and their ids too
|
||||
* @param {number} id - level number that was ordered to remove.
|
||||
* All updates are made relative to id
|
||||
* */
|
||||
const updateLevelNumbersOnDOM = (id: number): void => {
|
||||
const numLevels = getNumLevels();
|
||||
if (id == numLevels) {
|
||||
throw new Error(
|
||||
"Can't remove the very fist element, it has to be first added to DOM"
|
||||
);
|
||||
}
|
||||
|
||||
// since I'm doing id+1, I have to remove id after I'm done
|
||||
// with inclreasing level numbers
|
||||
for (let i = id + 1; i <= numLevels; i++) {
|
||||
const newLevel = i - 1;
|
||||
|
||||
const levelGroup = document.querySelector(
|
||||
`#${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${i}`
|
||||
);
|
||||
|
||||
if (levelGroup === null) {
|
||||
const msg = `[removeLevelButton.ts]:
|
||||
error when trying to fetch level group field set ${i}. got null`;
|
||||
log.error(msg);
|
||||
throw new Error(msg);
|
||||
}
|
||||
|
||||
// rename legend
|
||||
const legend = levelGroup.getElementsByTagName("legend")[0];
|
||||
const legendText = document.createTextNode(`Level ${newLevel}`);
|
||||
const newLegend = document.createElement("legend");
|
||||
newLegend.className = legend.className;
|
||||
newLegend.appendChild(legendText);
|
||||
legend.replaceWith(newLegend);
|
||||
|
||||
// rename labels
|
||||
updateLabels(levelGroup, newLevel);
|
||||
|
||||
// rename inputs
|
||||
updateInputs(levelGroup, newLevel);
|
||||
|
||||
if (i != numLevels) {
|
||||
// update remove button
|
||||
updateRemoveButton(levelGroup, newLevel);
|
||||
}
|
||||
|
||||
// update levelGroup's ID
|
||||
updateLevelGroup(levelGroup, newLevel);
|
||||
// TODO change remove button ID as well
|
||||
|
||||
/* TODO
|
||||
* change field set ID
|
||||
* change legend inner Text
|
||||
* change visitor lable for value
|
||||
* change visitor input id
|
||||
* change difficulty for value
|
||||
* change difficulty input id
|
||||
*/
|
||||
}
|
||||
};
|
||||
|
||||
export default updateLevelNumbersOnDOM;
|
||||
@@ -0,0 +1,36 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import getNumLevels from "../../levels/getNumLevels";
|
||||
import { getAddForm, addLevel } from "../../setupTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
export const setupAddlevels = (): void => {
|
||||
expect(getNumLevels()).toBe(1);
|
||||
// add a level
|
||||
addLevel(2, 2);
|
||||
expect(getNumLevels()).toBe(2);
|
||||
|
||||
// add second level
|
||||
addLevel(4, 4);
|
||||
expect(getNumLevels()).toBe(3);
|
||||
|
||||
// add thrid level
|
||||
addLevel(5, 5);
|
||||
expect(getNumLevels()).toBe(4);
|
||||
};
|
||||
@@ -0,0 +1,241 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import {getAddForm, trim} from "../../setupTests";
|
||||
import updateInputs from "./updateInputs";
|
||||
import CONST from "../../const";
|
||||
|
||||
import log from "../../../../../../../logger";
|
||||
import {MODE} from "../../../../../../../logger";
|
||||
|
||||
import {setupAddlevels} from "./setupTests";
|
||||
|
||||
document.body.innerHTML = getAddForm();
|
||||
|
||||
log.setMode(MODE.none);
|
||||
|
||||
it("updateInputs works", () => {
|
||||
setupAddlevels();
|
||||
// removing level 2
|
||||
const level = 2;
|
||||
const levelGroup = document.querySelector(
|
||||
`#${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${level}`,
|
||||
);
|
||||
|
||||
const newLevel = 20;
|
||||
|
||||
updateInputs(levelGroup, newLevel);
|
||||
|
||||
const inputs = <NodeListOf<HTMLInputElement>>(
|
||||
levelGroup.querySelectorAll(`.${CONST.LEVEL_INPUT_CLASS}`)
|
||||
);
|
||||
inputs.forEach(input => {
|
||||
if (input.id.includes(CONST.VISITOR_WITHOUT_LEVEL)) {
|
||||
expect(input.id).toBe(`${CONST.VISITOR_WITHOUT_LEVEL}${newLevel}`);
|
||||
console.log("checking visitor");
|
||||
} else {
|
||||
// if (input.id.includes(CONST.DIFFICULTY_WITHOUT_LEVEL)) {
|
||||
console.log("checking difficulty");
|
||||
expect(input.id).toBe(`${CONST.DIFFICULTY_WITHOUT_LEVEL}${newLevel}`);
|
||||
}
|
||||
});
|
||||
|
||||
expect(trim(document.body.innerHTML)).toBe(trim(update()));
|
||||
});
|
||||
|
||||
/** get initial form to test remove button functionality */
|
||||
export const update = (): string => {
|
||||
return `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<h1 class="form__title">
|
||||
Add Sitekey
|
||||
</h1>
|
||||
<label class="sitekey-form__label" for="description">
|
||||
Description
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="text"
|
||||
name="description"
|
||||
id="description"
|
||||
required=""
|
||||
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__label" for="duration">
|
||||
Cooldown Duratoin(in seconds)
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="number"
|
||||
name="duration"
|
||||
id="duration"
|
||||
min="0"
|
||||
required=""
|
||||
value="30"
|
||||
>
|
||||
</label>
|
||||
|
||||
<fieldset class="sitekey__level-container" id="level-group-1">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 1
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor1"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor1"
|
||||
|
||||
id="visitor1"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty1">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty1"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty1"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level1">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level1"
|
||||
id="remove-level1"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
<fieldset class="sitekey__level-container" id="level-group-2">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 2
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor2"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor20"
|
||||
|
||||
id="visitor20"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty2">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty20"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty20"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level2">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level2"
|
||||
id="remove-level2"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
<fieldset class="sitekey__level-container" id="level-group-3">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 3
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor3"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor3"
|
||||
|
||||
id="visitor3"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty3">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty3"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty3"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level3">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level3"
|
||||
id="remove-level3"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
|
||||
<fieldset class="sitekey__level-container" id="level-group-4">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 4
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor4"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor4"
|
||||
|
||||
id="visitor4"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty4">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty4"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty4"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
|
||||
<button class="sitekey-form__submit" type="submit">Submit</button>
|
||||
</form>
|
||||
`;
|
||||
};
|
||||
@@ -0,0 +1,46 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import CONST from "../../const";
|
||||
import log from "../../../../../../../logger";
|
||||
|
||||
/** update input IDs with new level */
|
||||
const updateInput = (levelGroup: Element, newLevel: number): void => {
|
||||
const inputs = <NodeListOf<HTMLInputElement>>(
|
||||
levelGroup.querySelectorAll(`.${CONST.LEVEL_INPUT_CLASS}`)
|
||||
);
|
||||
log.log(inputs);
|
||||
inputs.forEach(input => {
|
||||
if (input.id.includes(CONST.VISITOR_WITHOUT_LEVEL)) {
|
||||
log.log(`${input.id}`);
|
||||
log.log("changing visitor_threshold input");
|
||||
const id = `${CONST.VISITOR_WITHOUT_LEVEL}${newLevel}`;
|
||||
input.id = id;
|
||||
input.name = id;
|
||||
} else if (input.id.includes(CONST.DIFFICULTY_WITHOUT_LEVEL)) {
|
||||
log.log("changing difficulty input");
|
||||
const id = `${CONST.DIFFICULTY_WITHOUT_LEVEL}${newLevel}`;
|
||||
input.id = id;
|
||||
input.name = id;
|
||||
} else {
|
||||
if (input.id != "add") {
|
||||
throw new Error(`Did you add an extra input to DOM? ${input.id} ${input.className} ${input.name}`);
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
export default updateInput;
|
||||
@@ -0,0 +1,120 @@
|
||||
/*
|
||||
* Copyright (C) 221 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { trim } from "../../setupTests";
|
||||
import updateLabels from "./updateLabel";
|
||||
import CONST from "../../const";
|
||||
|
||||
import log from "../../../../../../../logger";
|
||||
import { MODE } from "../../../../../../../logger";
|
||||
|
||||
/** get initial form to test remove button functionality */
|
||||
export const labelLevel = (level: number): string => {
|
||||
return `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<fieldset class="sitekey__level-container" id="level-group-2">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 2
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor${level}"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor2"
|
||||
|
||||
id="visitor2"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty${level}">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty2"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty2"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level${level}">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level2"
|
||||
id="remove-level2"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
>
|
||||
</label>
|
||||
|
||||
</fieldset>
|
||||
</form>
|
||||
`;
|
||||
};
|
||||
|
||||
document.body.innerHTML = labelLevel(2);
|
||||
|
||||
log.setMode(MODE.none);
|
||||
|
||||
it("addLevelButton works", () => {
|
||||
// removing level 2
|
||||
const level = 2;
|
||||
const levelGroup = document.querySelector(
|
||||
`#${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${level}`
|
||||
);
|
||||
|
||||
const newLevel = 20;
|
||||
|
||||
updateLabels(levelGroup, newLevel);
|
||||
|
||||
const labels = <NodeListOf<HTMLLabelElement>>(
|
||||
levelGroup.querySelectorAll(`.${CONST.LABEL_CLASS}`)
|
||||
);
|
||||
log.log(labels);
|
||||
labels.forEach((label) => {
|
||||
log.log(`${label.htmlFor}`);
|
||||
if (label.htmlFor.includes(CONST.VISITOR_WITHOUT_LEVEL)) {
|
||||
expect(label.htmlFor).toBe(`${CONST.VISITOR_WITHOUT_LEVEL}${newLevel}`);
|
||||
} else if (label.htmlFor.includes(CONST.DIFFICULTY_WITHOUT_LEVEL)) {
|
||||
expect(label.htmlFor).toBe(
|
||||
`${CONST.DIFFICULTY_WITHOUT_LEVEL}${newLevel}`
|
||||
);
|
||||
} else if (
|
||||
label.htmlFor.includes(CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL)
|
||||
) {
|
||||
expect(label.htmlFor).toBe(
|
||||
`${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${newLevel}`
|
||||
);
|
||||
} else {
|
||||
throw new Error("Did you add an extra label to DOM?");
|
||||
}
|
||||
});
|
||||
|
||||
expect(trim(document.body.innerHTML)).toBe(trim(labelLevel(newLevel)));
|
||||
});
|
||||
@@ -0,0 +1,48 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import CONST from "../../const";
|
||||
import log from "../../../../../../../logger";
|
||||
|
||||
/** update level lables to match new level */
|
||||
const updateLabels = (levelGroup: Element, newLevel: number): void => {
|
||||
// rename labels
|
||||
const labels = <NodeListOf<HTMLLabelElement>>(
|
||||
levelGroup.querySelectorAll("label")
|
||||
);
|
||||
log.log(labels);
|
||||
labels.forEach((label) => {
|
||||
log.log(`${label.htmlFor}`);
|
||||
const currentFor = label.htmlFor;
|
||||
if (currentFor.includes(CONST.VISITOR_WITHOUT_LEVEL)) {
|
||||
label.htmlFor = `${CONST.VISITOR_WITHOUT_LEVEL}${newLevel}`;
|
||||
} else if (currentFor.includes(CONST.DIFFICULTY_WITHOUT_LEVEL)) {
|
||||
label.htmlFor = `${CONST.DIFFICULTY_WITHOUT_LEVEL}${newLevel}`;
|
||||
} else if (
|
||||
currentFor.includes(CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL)
|
||||
) {
|
||||
label.htmlFor = `${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${newLevel}`;
|
||||
} else {
|
||||
if (currentFor != "add") {
|
||||
throw new Error(
|
||||
`Did you add an extra label to DOM? Found label with for: ${currentFor}`
|
||||
);
|
||||
}
|
||||
}
|
||||
});
|
||||
};
|
||||
|
||||
export default updateLabels;
|
||||
@@ -0,0 +1,101 @@
|
||||
/*
|
||||
* Copyright (C) 221 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { trim} from "../../setupTests";
|
||||
import updateLevelGroup from "./updateLevelGroup";
|
||||
import CONST from "../../const";
|
||||
|
||||
import log from "../../../../../../../logger";
|
||||
import {MODE} from "../../../../../../../logger";
|
||||
|
||||
|
||||
/** get initial form to test remove button functionality */
|
||||
export const labelLevel = (level: number): string => {
|
||||
return `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<fieldset class="sitekey__level-container" id="level-group-${level}">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 2
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor2"
|
||||
|
||||
id="visitor2"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty2"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty2"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level2"
|
||||
id="remove-level2"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
>
|
||||
</label>
|
||||
|
||||
</fieldset>
|
||||
</form>
|
||||
`;
|
||||
};
|
||||
|
||||
document.body.innerHTML = labelLevel(2);
|
||||
|
||||
log.setMode(MODE.none);
|
||||
|
||||
it("update levelGroup works", () => {
|
||||
// removing level 2
|
||||
const level = 2;
|
||||
const levelGroup = document.querySelector(
|
||||
`#${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${level}`,
|
||||
);
|
||||
|
||||
const newLevel = 20;
|
||||
|
||||
updateLevelGroup(levelGroup, newLevel);
|
||||
expect(levelGroup.id).toBe(
|
||||
`${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${newLevel}`,
|
||||
);
|
||||
|
||||
expect(trim(document.body.innerHTML)).toBe(trim(labelLevel(newLevel)));
|
||||
});
|
||||
@@ -0,0 +1,23 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import CONST from "../../const";
|
||||
|
||||
/** update level grup to match new level */
|
||||
const updateLevelGroup = (levelGroup: Element, newLevel: number): string =>
|
||||
(levelGroup.id = `${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}${newLevel}`);
|
||||
|
||||
export default updateLevelGroup;
|
||||
@@ -0,0 +1,107 @@
|
||||
/*
|
||||
* Copyright (C) 221 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import {trim} from "../../setupTests";
|
||||
import updateRemoveButton from "./updateRemoveButton";
|
||||
import CONST from "../../const";
|
||||
|
||||
import log from "../../../../../../../logger";
|
||||
import {MODE} from "../../../../../../../logger";
|
||||
|
||||
/** get initial form to test remove button functionality */
|
||||
export const labelLevel = (level: number): string => {
|
||||
return `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<fieldset class="sitekey__level-container" id="level-group-">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 2
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor2"
|
||||
|
||||
id="visitor2"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty2"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty2"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level${level}"
|
||||
id="remove-level${level}"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
>
|
||||
</label>
|
||||
|
||||
</fieldset>
|
||||
</form>
|
||||
`;
|
||||
};
|
||||
|
||||
const level = 2;
|
||||
document.body.innerHTML = labelLevel(level);
|
||||
|
||||
log.setMode(MODE.none);
|
||||
|
||||
it("update remove button works", () => {
|
||||
// removing level 2
|
||||
|
||||
const levelGroup = document.getElementById(
|
||||
`${CONST.LEVEL_FIELDSET_ID_WITHOUT_LEVEL}`,
|
||||
);
|
||||
|
||||
const newLevel = 20;
|
||||
updateRemoveButton(levelGroup, newLevel);
|
||||
|
||||
const button = <HTMLInputElement>(
|
||||
levelGroup.querySelector(`.${CONST.REMOVE_LEVEL_BUTTON_CLASS}`)
|
||||
);
|
||||
expect(button.id).toBe(
|
||||
`${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${newLevel}`,
|
||||
);
|
||||
expect(button.name).toBe(
|
||||
`${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${newLevel}`,
|
||||
);
|
||||
|
||||
expect(trim(document.body.innerHTML)).toBe(trim(labelLevel(newLevel)));
|
||||
});
|
||||
@@ -0,0 +1,30 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import CONST from "../../const";
|
||||
|
||||
/** update remove level button's ID */
|
||||
const updateRemoveButton = (levelGroup: Element, newLevel: number): void => {
|
||||
// rename button
|
||||
const button = <HTMLInputElement>(
|
||||
levelGroup.querySelector(`.${CONST.REMOVE_LEVEL_BUTTON_CLASS}`)
|
||||
);
|
||||
const id = `${CONST.REMOVE_LEVEL_BUTTON_ID_WITHOUT_LEVEL}${newLevel}`;
|
||||
button.id = id;
|
||||
button.name = id;
|
||||
};
|
||||
|
||||
export default updateRemoveButton;
|
||||
358
templates/panel/sitekey/add/advance/ts/setupTests.ts
Normal file
358
templates/panel/sitekey/add/advance/ts/setupTests.ts
Normal file
@@ -0,0 +1,358 @@
|
||||
/*
|
||||
* Copyright (C) 2021 Aravinth Manivannan <realaravinth@batsense.net>
|
||||
*
|
||||
* This program is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU Affero General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <https://www.gnu.org/licenses/>.
|
||||
*/
|
||||
import getNumLevels from "./levels/getNumLevels";
|
||||
import { Level } from "./levels/index";
|
||||
import CONST from "./const";
|
||||
import addLevelButtonAddEventListener from "./addLevelButton";
|
||||
|
||||
/** get rid of all whitespaces, useful when comparing DOM states */
|
||||
export const trim = (s: string): string => s.replace(/\s/g, "");
|
||||
|
||||
export const level1: Level = {
|
||||
difficulty_factor: 200,
|
||||
visitor_threshold: 500,
|
||||
};
|
||||
|
||||
export const level1diffErr: Level = {
|
||||
difficulty_factor: 100,
|
||||
visitor_threshold: 600,
|
||||
};
|
||||
|
||||
export const level1visErr: Level = {
|
||||
difficulty_factor: 600,
|
||||
visitor_threshold: 400,
|
||||
};
|
||||
|
||||
export const level2: Level = {
|
||||
difficulty_factor: 400,
|
||||
visitor_threshold: 700,
|
||||
};
|
||||
|
||||
/** add level to DOM by filling add level form and clicking "Add" button */
|
||||
export const addLevel = (visitor: number, diff: number): void => {
|
||||
fillAddLevel(visitor, diff);
|
||||
const addLevelButton = <HTMLElement>(
|
||||
document.querySelector(`.${CONST.ADD_LEVEL_BUTTON}`)
|
||||
);
|
||||
addLevelButton.click();
|
||||
};
|
||||
|
||||
/** Fill add level form without clicking add button */
|
||||
export const fillAddLevel = (
|
||||
visitor: number | string,
|
||||
diff: number | string
|
||||
): void => {
|
||||
addLevelButtonAddEventListener();
|
||||
|
||||
const level = getNumLevels();
|
||||
const visitorField = <HTMLInputElement>(
|
||||
document.getElementById(`${CONST.VISITOR_WITHOUT_LEVEL}${level}`)
|
||||
);
|
||||
visitorField.value = visitor.toString();
|
||||
|
||||
const diffField = <HTMLInputElement>(
|
||||
document.getElementById(`${CONST.DIFFICULTY_WITHOUT_LEVEL}${level}`)
|
||||
);
|
||||
diffField.value = diff.toString();
|
||||
};
|
||||
|
||||
/** Fill add level form without clicking add button */
|
||||
export const editLevel = (
|
||||
level: number,
|
||||
visitor?: number,
|
||||
diff?: number
|
||||
): void => {
|
||||
if (visitor !== undefined) {
|
||||
const visitorField = <HTMLInputElement>(
|
||||
document.getElementById(`${CONST.VISITOR_WITHOUT_LEVEL}${level}`)
|
||||
);
|
||||
visitorField.value = visitor.toString();
|
||||
}
|
||||
|
||||
if (diff !== undefined) {
|
||||
const diffField = <HTMLInputElement>(
|
||||
document.getElementById(`${CONST.DIFFICULTY_WITHOUT_LEVEL}${level}`)
|
||||
);
|
||||
diffField.value = diff.toString();
|
||||
}
|
||||
};
|
||||
|
||||
/** Fill description in add level form */
|
||||
export const fillDescription = (description: string): void => {
|
||||
const inputElement = <HTMLInputElement>document.getElementById("description");
|
||||
inputElement.value = description;
|
||||
};
|
||||
|
||||
/** Fill duration in add level form */
|
||||
export const fillDuration = (duration: number | string): void => {
|
||||
const inputElement = <HTMLInputElement>document.getElementById("duration");
|
||||
inputElement.value = duration.toString();
|
||||
};
|
||||
|
||||
export const getAddForm = (): string => `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<h1 class="form__title">
|
||||
Add Sitekey
|
||||
</h1>
|
||||
<label class="sitekey-form__label" for="description">
|
||||
Description
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="text"
|
||||
name="description"
|
||||
id="description"
|
||||
required=""
|
||||
|
||||
/>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__label" for="duration">
|
||||
Cooldown Duratoin(in seconds)
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="number"
|
||||
name="duration"
|
||||
id="duration"
|
||||
min="0"
|
||||
required=""
|
||||
value="30"
|
||||
/>
|
||||
</label>
|
||||
|
||||
<fieldset class="sitekey__level-container" id="level-group-1">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 1
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor1"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor1"
|
||||
|
||||
id="visitor1"
|
||||
/>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty1">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty1"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty1"
|
||||
/>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
/>
|
||||
</label>
|
||||
</fieldset>
|
||||
|
||||
<button class="sitekey-form__submit" type="submit">Submit</button>
|
||||
</form>
|
||||
`;
|
||||
|
||||
/** get initial form to test remove button functionality */
|
||||
export const getRemoveButtonHTMLForm = (): string => {
|
||||
return `
|
||||
<form class="sitekey-form" action="/api/v1/mcaptcha/levels/add" method="post">
|
||||
<h1 class="form__title">
|
||||
Add Sitekey
|
||||
</h1>
|
||||
<label class="sitekey-form__label" for="description">
|
||||
Description
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="text"
|
||||
name="description"
|
||||
id="description"
|
||||
required=""
|
||||
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__label" for="duration">
|
||||
Cooldown Duratoin(in seconds)
|
||||
<input
|
||||
class="sitekey-form__input"
|
||||
type="number"
|
||||
name="duration"
|
||||
id="duration"
|
||||
min="0"
|
||||
required=""
|
||||
value="30"
|
||||
>
|
||||
</label>
|
||||
|
||||
<fieldset class="sitekey__level-container" id="level-group-1">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 1
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor1"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor1"
|
||||
|
||||
id="visitor1"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty1">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty1"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty1"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level1">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level1"
|
||||
id="remove-level1"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
<fieldset class="sitekey__level-container" id="level-group-2">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 2
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor2"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor2"
|
||||
|
||||
id="visitor2"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty2">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty2"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty2"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level2">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level2"
|
||||
id="remove-level2"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
<fieldset class="sitekey__level-container" id="level-group-3">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 3
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor3"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor3"
|
||||
|
||||
id="visitor3"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty3">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty3"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty3"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="remove-level3">
|
||||
Remove Level
|
||||
<input
|
||||
class="sitekey-form__level-remove-level-button"
|
||||
type="button"
|
||||
name="remove-level3"
|
||||
id="remove-level3"
|
||||
value="x"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
|
||||
<fieldset class="sitekey__level-container" id="level-group-4">
|
||||
<legend class="sitekey__level-title">
|
||||
Level 4
|
||||
</legend>
|
||||
<label class="sitekey-form__level-label" for="visitor4"
|
||||
>Visitor
|
||||
<input
|
||||
class="sitekey-form__level-input"
|
||||
type="number"
|
||||
name="visitor4"
|
||||
|
||||
id="visitor4"
|
||||
>
|
||||
</label>
|
||||
|
||||
<label class="sitekey-form__level-label" for="difficulty4">
|
||||
Difficulty
|
||||
<input
|
||||
type="number"
|
||||
name="difficulty4"
|
||||
class="sitekey-form__level-input"
|
||||
|
||||
id="difficulty4"
|
||||
>
|
||||
</label>
|
||||
<label class="sitekey-form__level-label--hidden" for="add">
|
||||
Add level
|
||||
<input
|
||||
class="sitekey-form__level-add-level-button"
|
||||
type="button"
|
||||
name="add"
|
||||
id="add"
|
||||
value="Add"
|
||||
>
|
||||
</label>
|
||||
</fieldset>
|
||||
|
||||
<button class="sitekey-form__submit" type="submit">Submit</button>
|
||||
</form>
|
||||
`;
|
||||
};
|
||||
Reference in New Issue
Block a user