commit 8ace76d4aa8552e32484e5926ba947b7df8a66a1
parent 6319fe1f022af6cfee9ab85a0446b0cb62c32177
Author: iulian moraru <imoraru@mozilla.com>
Date: Mon, 3 Nov 2025 09:10:02 +0200
Revert "Bug 1981970 - Only allow numerical values to be input into the Timer widget. r=home-newtab-reviewers,npypchenko" for causing newtab failures.
This reverts commit dee465c6494f48fe1780f43a6cdd4ed084224ce1.
Diffstat:
3 files changed, 13 insertions(+), 153 deletions(-)
diff --git a/browser/extensions/newtab/content-src/components/Widgets/FocusTimer/FocusTimer.jsx b/browser/extensions/newtab/content-src/components/Widgets/FocusTimer/FocusTimer.jsx
@@ -46,27 +46,6 @@ export const formatTime = seconds => {
};
/**
- * Validates that the inputs in the timer only allow numerical digits (0-9)
- *
- * @param input - The character being input
- * @returns boolean - true if valid numeric input, false otherwise
- */
-export const isNumericValue = input => {
- // Check for null/undefined input or non-numeric characters
- return input && /^\d+$/.test(input);
-};
-
-/**
- * Validates if adding a new digit would exceed the 2-character limit
- *
- * @param currentValue - The current value in the field
- * @returns boolean - true if at 2-character limit, false otherwise
- */
-export const isAtMaxLength = currentValue => {
- return currentValue.length >= 2;
-};
-
-/**
* Converts a polar coordinate (angle on circle) into a percentage-based [x,y] position for clip-path
*
* @param cx
@@ -437,9 +416,13 @@ export const FocusTimer = ({ dispatch, handleUserInteraction }) => {
const values = e.target.innerText.trim();
// only allow numerical digits 0–9 for time input
- if (!isNumericValue(input)) {
+ if (!/^\d+$/.test(input)) {
+ e.preventDefault();
+ }
+
+ // only allow 2 values each for minutes and seconds
+ if (values.length >= 2) {
e.preventDefault();
- return;
}
const selection = window.getSelection();
@@ -458,12 +441,6 @@ export const FocusTimer = ({ dispatch, handleUserInteraction }) => {
const sel = window.getSelection();
sel.removeAllRanges();
sel.addRange(range);
- return;
- }
-
- // only allow 2 values each for minutes and seconds
- if (isAtMaxLength(values)) {
- e.preventDefault();
}
};
diff --git a/browser/extensions/newtab/data/content/activity-stream.bundle.js b/browser/extensions/newtab/data/content/activity-stream.bundle.js
@@ -12958,27 +12958,6 @@ const formatTime = seconds => {
};
/**
- * Validates that input is a numeric digit (0-9)
- *
- * @param input - The character being input
- * @returns boolean - true if valid numeric input, false otherwise
- */
-const isNumericValue = input => {
- // Check for null/undefined input or non-numeric characters
- return input && /^\d+$/.test(input);
-};
-
-/**
- * Validates if adding a new digit would exceed the 2-character limit
- *
- * @param currentValue - The current value in the field
- * @returns boolean - true if at 2-character limit, false otherwise
- */
-const isAtMaxLength = currentValue => {
- return currentValue.length >= 2;
-};
-
-/**
* Converts a polar coordinate (angle on circle) into a percentage-based [x,y] position for clip-path
*
* @param cx
@@ -13285,9 +13264,13 @@ const FocusTimer = ({
const values = e.target.innerText.trim();
// only allow numerical digits 0–9 for time input
- if (!isNumericValue(input)) {
+ if (!/^\d+$/.test(input)) {
+ e.preventDefault();
+ }
+
+ // only allow 2 values each for minutes and seconds
+ if (values.length >= 2) {
e.preventDefault();
- return;
}
const selection = window.getSelection();
const selectedText = selection.toString();
@@ -13305,12 +13288,6 @@ const FocusTimer = ({
const sel = window.getSelection();
sel.removeAllRanges();
sel.addRange(range);
- return;
- }
-
- // only allow 2 values each for minutes and seconds
- if (isAtMaxLength(values)) {
- e.preventDefault();
}
};
const handleFocus = e => {
diff --git a/browser/extensions/newtab/test/unit/content-src/components/Widgets/FocusTimer.test.jsx b/browser/extensions/newtab/test/unit/content-src/components/Widgets/FocusTimer.test.jsx
@@ -4,11 +4,7 @@ import { Provider } from "react-redux";
import { mount } from "enzyme";
import { INITIAL_STATE, reducers } from "common/Reducers.sys.mjs";
import { actionTypes as at } from "common/Actions.mjs";
-import {
- FocusTimer,
- isNumericValue,
- isAtMaxLength,
-} from "content-src/components/Widgets/FocusTimer/FocusTimer";
+import { FocusTimer } from "content-src/components/Widgets/FocusTimer/FocusTimer";
const PREF_WIDGETS_SYSTEM_NOTIFICATIONS_ENABLED =
"widgets.focusTimer.showSystemNotifications";
@@ -568,94 +564,4 @@ describe("<FocusTimer>", () => {
assert.equal(action.type, at.OPEN_LINK);
});
});
-
- // Tests for the focus timer input. It should only allow numbers
- describe("isNumericValue", () => {
- it("should return true for single digit numbers", () => {
- assert.isTrue(isNumericValue("0"));
- assert.isTrue(isNumericValue("1"));
- assert.isTrue(isNumericValue("5"));
- assert.isTrue(isNumericValue("9"));
- });
-
- it("should return true for multi-digit numbers", () => {
- assert.isTrue(isNumericValue("10"));
- assert.isTrue(isNumericValue("25"));
- assert.isTrue(isNumericValue("99"));
- });
-
- it("should return false for non-numeric characters", () => {
- assert.isFalse(isNumericValue("a"));
- assert.isFalse(isNumericValue("Z"));
- assert.isFalse(isNumericValue("!"));
- assert.isFalse(isNumericValue("@"));
- assert.isFalse(isNumericValue(" "));
- });
-
- it("should return false for special characters", () => {
- assert.isFalse(isNumericValue("-"));
- assert.isFalse(isNumericValue("+"));
- assert.isFalse(isNumericValue("."));
- assert.isFalse(isNumericValue(","));
- });
-
- it("should return false for mixed alphanumeric strings", () => {
- assert.isFalse(isNumericValue("1a"));
- assert.isFalse(isNumericValue("a1"));
- assert.isFalse(isNumericValue("5x"));
- });
-
- it("should return false for empty string", () => {
- assert.isFalse(isNumericValue(" "));
- });
- });
-
- // Tests for the 2-character limit (enforces max 99 minutes, 59 seconds)
- describe("isAtMaxLength", () => {
- it("should return false for empty string", () => {
- assert.isFalse(isAtMaxLength(""));
- });
-
- it("should return false for single character", () => {
- assert.isFalse(isAtMaxLength("5"));
- assert.isFalse(isAtMaxLength("9"));
- });
-
- it("should return true for 2 characters", () => {
- assert.isTrue(isAtMaxLength("25"));
- assert.isTrue(isAtMaxLength("99"));
- assert.isTrue(isAtMaxLength("00"));
- });
-
- it("should return true for more than 2 characters", () => {
- assert.isTrue(isAtMaxLength("123"));
- assert.isTrue(isAtMaxLength("999"));
- });
- });
-
- it("should clamp minutes to 99 and seconds to 59 when setting duration", () => {
- // Find the editable fields
- const minutes = wrapper.find(".timer-set-minutes").at(0);
- const seconds = wrapper.find(".timer-set-seconds").at(0);
-
- // Simulate user typing values beyond limits
- minutes.getDOMNode().innerText = "100";
- seconds.getDOMNode().innerText = "85";
-
- // Trigger blur, which calls setTimerDuration()
- seconds.simulate("blur");
-
- // Clamp check
- const clampedMinutes = Math.min(
- parseInt(minutes.getDOMNode().innerText, 10),
- 99
- );
- const clampedSeconds = Math.min(
- parseInt(seconds.getDOMNode().innerText, 10),
- 59
- );
-
- assert.equal(clampedMinutes, 99, "minutes should be clamped to 99");
- assert.equal(clampedSeconds, 59, "seconds should be clamped to 59");
- });
});