refactor: move formatting related code into separate file (#4568)

Co-authored-by: Alexandr <qwerty541zxc@gmail.com>
This commit is contained in:
Ophelia Goldstein
2025-10-25 18:58:57 +02:00
committed by martin-mfg
co-authored by Alexandr
parent f5916427f1
commit e29ac4b338
8 changed files with 57 additions and 58 deletions
+1 -1
View File
@@ -4,7 +4,6 @@ import {
parseEmojis,
wrapTextMultiline,
encodeHTML,
kFormatter,
measureText,
flexLayout,
iconWithLabel,
@@ -12,6 +11,7 @@ import {
} from "../common/utils.js";
import Card from "../common/Card.js";
import { getCardColors } from "../common/color.js";
import { kFormatter } from "../common/fmt.js";
import { icons } from "../common/icons.js";
import languageColors from "../common/languageColors.json" with { type: "json" };
+1 -1
View File
@@ -2,12 +2,12 @@
import { Card } from "../common/Card.js";
import { getCardColors } from "../common/color.js";
import { kFormatter } from "../common/fmt.js";
import { I18n } from "../common/I18n.js";
import { icons } from "../common/icons.js";
import {
encodeHTML,
flexLayout,
kFormatter,
measureText,
parseEmojis,
wrapTextMultiline,
+1 -1
View File
@@ -3,12 +3,12 @@
import { Card } from "../common/Card.js";
import { getCardColors } from "../common/color.js";
import { CustomError } from "../common/error.js";
import { kFormatter } from "../common/fmt.js";
import { I18n } from "../common/I18n.js";
import { icons, rankIcon } from "../common/icons.js";
import {
clampValue,
flexLayout,
kFormatter,
measureText,
buildSearchFilter,
} from "../common/utils.js";
+1 -1
View File
@@ -3,6 +3,7 @@
import { Card } from "../common/Card.js";
import { getCardColors } from "../common/color.js";
import { createProgressNode } from "../common/createProgressNode.js";
import { formatBytes } from "../common/fmt.js";
import { I18n } from "../common/I18n.js";
import {
chunkArray,
@@ -10,7 +11,6 @@ import {
flexLayout,
lowercaseTrim,
measureText,
formatBytes,
} from "../common/utils.js";
import { langCardLocales } from "../translations.js";
+50
View File
@@ -0,0 +1,50 @@
/**
* Retrieves num with suffix k(thousands) precise to given decimal places.
*
* @param {number} num The number to format.
* @param {number=} precision The number of decimal places to include.
* @returns {string|number} The formatted number.
*/
const kFormatter = (num, precision) => {
const abs = Math.abs(num);
const sign = Math.sign(num);
if (typeof precision === "number" && !isNaN(precision)) {
return (sign * (abs / 1000)).toFixed(precision) + "k";
}
if (abs < 1000) {
return sign * abs;
}
return sign * parseFloat((abs / 1000).toFixed(1)) + "k";
};
/**
* Convert bytes to a human-readable string representation.
*
* @param {number} bytes The number of bytes to convert.
* @returns {string} The human-readable representation of bytes.
* @throws {Error} If bytes is negative or too large.
*/
const formatBytes = (bytes) => {
if (bytes < 0) {
throw new Error("Bytes must be a non-negative number");
}
if (bytes === 0) {
return "0 B";
}
const sizes = ["B", "KB", "MB", "GB", "TB", "PB", "EB"];
const base = 1024;
const i = Math.floor(Math.log(bytes) / Math.log(base));
if (i >= sizes.length) {
throw new Error("Bytes is too large to convert to a human-readable string");
}
return `${(bytes / Math.pow(base, i)).toFixed(1)} ${sizes[i]}`;
};
export { kFormatter, formatBytes };
-1
View File
@@ -10,7 +10,6 @@ export {
ERROR_CARD_LENGTH,
renderError,
encodeHTML,
kFormatter,
parseBoolean,
parseArray,
clampValue,
-51
View File
@@ -78,28 +78,6 @@ const iconWithLabel = (icon, label, testid, iconSize) => {
return flexLayout({ items: [iconSvg, text], gap: 20 }).join("");
};
/**
* Retrieves num with suffix k(thousands) precise to given decimal places.
*
* @param {number} num The number to format.
* @param {number=} precision The number of decimal places to include.
* @returns {string|number} The formatted number.
*/
const kFormatter = (num, precision) => {
const abs = Math.abs(num);
const sign = Math.sign(num);
if (typeof precision === "number" && !isNaN(precision)) {
return (sign * (abs / 1000)).toFixed(precision) + "k";
}
if (abs < 1000) {
return sign * abs;
}
return sign * parseFloat((abs / 1000).toFixed(1)) + "k";
};
/**
* Returns boolean if value is either "true" or "false" else the value as it is.
*
@@ -443,40 +421,12 @@ const dateDiff = (d1, d2) => {
return Math.round(diff / (1000 * 60));
};
/**
* Convert bytes to a human-readable string representation.
*
* @param {number} bytes The number of bytes to convert.
* @returns {string} The human-readable representation of bytes.
* @throws {Error} If bytes is negative or too large.
*/
const formatBytes = (bytes) => {
if (bytes < 0) {
throw new Error("Bytes must be a non-negative number");
}
if (bytes === 0) {
return "0 B";
}
const sizes = ["B", "KB", "MB", "GB", "TB", "PB", "EB"];
const base = 1024;
const i = Math.floor(Math.log(bytes) / Math.log(base));
if (i >= sizes.length) {
throw new Error("Bytes is too large to convert to a human-readable string");
}
return `${(bytes / Math.pow(base, i)).toFixed(1)} ${sizes[i]}`;
};
export {
ERROR_CARD_LENGTH,
renderError,
createLanguageNode,
iconWithLabel,
encodeHTML,
kFormatter,
parseBoolean,
parseArray,
clampValue,
@@ -492,5 +442,4 @@ export {
parseEmojis,
parseOwnerAffiliations,
dateDiff,
formatBytes,
};
+3 -2
View File
@@ -1,14 +1,15 @@
// @ts-check
import { describe, expect, it } from "@jest/globals";
import { queryByTestId } from "@testing-library/dom";
import "@testing-library/jest-dom";
import {
encodeHTML,
formatBytes,
kFormatter,
parseBoolean,
renderError,
wrapTextMultiline,
} from "../src/common/utils.js";
import { formatBytes, kFormatter } from "../src/common/fmt.js";
describe("Test utils.js", () => {
it("should test kFormatter default behavior", () => {