2020-08-01 03:43:15 +02:00
|
|
|
"use strict";
|
|
|
|
|
2024-10-09 00:25:41 +02:00
|
|
|
const assert = require("node:assert/strict");
|
2020-11-30 23:46:45 +01:00
|
|
|
|
2020-07-25 02:02:35 +02:00
|
|
|
const _ = require("lodash");
|
|
|
|
|
2023-09-11 11:59:27 +02:00
|
|
|
const {zrequire, set_global} = require("./lib/namespace");
|
2023-02-22 23:04:10 +01:00
|
|
|
const {run_test} = require("./lib/test");
|
2020-12-01 00:02:16 +01:00
|
|
|
|
2022-03-25 14:47:51 +01:00
|
|
|
const emoji = zrequire("emoji");
|
2021-02-10 04:53:22 +01:00
|
|
|
const emoji_picker = zrequire("emoji_picker");
|
2017-08-19 01:15:18 +02:00
|
|
|
|
2023-02-22 23:03:47 +01:00
|
|
|
const emoji_codes = zrequire("../../static/generated/emoji/emoji_codes.json");
|
2020-07-25 23:59:49 +02:00
|
|
|
|
2023-09-11 11:59:27 +02:00
|
|
|
set_global("document", "document-stub");
|
|
|
|
|
2020-07-15 01:29:15 +02:00
|
|
|
run_test("initialize", () => {
|
2020-07-25 23:59:49 +02:00
|
|
|
emoji.initialize({
|
|
|
|
realm_emoji: {},
|
|
|
|
emoji_codes,
|
|
|
|
});
|
2017-08-19 01:15:18 +02:00
|
|
|
emoji_picker.initialize();
|
|
|
|
|
2020-07-15 01:29:15 +02:00
|
|
|
const complete_emoji_catalog = _.sortBy(emoji_picker.complete_emoji_catalog, "name");
|
2020-06-14 09:01:53 +02:00
|
|
|
assert.equal(complete_emoji_catalog.length, 11);
|
2024-07-18 03:13:54 +02:00
|
|
|
assert.equal(emoji.emojis_by_name.size, 1876);
|
2017-08-19 01:15:18 +02:00
|
|
|
|
2020-06-14 19:40:33 +02:00
|
|
|
let total_emoji_in_categories = 0;
|
|
|
|
|
2017-08-19 01:15:18 +02:00
|
|
|
function assert_emoji_category(ele, icon, num) {
|
|
|
|
assert.equal(ele.icon, icon);
|
|
|
|
assert.equal(ele.emojis.length, num);
|
|
|
|
function check_emojis(val) {
|
2020-06-14 19:40:33 +02:00
|
|
|
for (const this_emoji of ele.emojis) {
|
|
|
|
assert.equal(this_emoji.is_realm_emoji, val);
|
js: Automatically convert _.each to for…of.
This commit was automatically generated by the following script,
followed by lint --fix and a few small manual lint-related cleanups.
import * as babelParser from "recast/parsers/babel";
import * as recast from "recast";
import * as tsParser from "recast/parsers/typescript";
import { builders as b, namedTypes as n } from "ast-types";
import { Context } from "ast-types/lib/path-visitor";
import K from "ast-types/gen/kinds";
import { NodePath } from "ast-types/lib/node-path";
import assert from "assert";
import fs from "fs";
import path from "path";
import process from "process";
const checkExpression = (node: n.Node): node is K.ExpressionKind =>
n.Expression.check(node);
const checkStatement = (node: n.Node): node is K.StatementKind =>
n.Statement.check(node);
for (const file of process.argv.slice(2)) {
console.log("Parsing", file);
const ast = recast.parse(fs.readFileSync(file, { encoding: "utf8" }), {
parser: path.extname(file) === ".ts" ? tsParser : babelParser,
});
let changed = false;
let inLoop = false;
let replaceReturn = false;
const visitLoop = (...args: string[]) =>
function(this: Context, path: NodePath) {
for (const arg of args) {
this.visit(path.get(arg));
}
const old = { inLoop };
inLoop = true;
this.visit(path.get("body"));
inLoop = old.inLoop;
return false;
};
recast.visit(ast, {
visitDoWhileStatement: visitLoop("test"),
visitExpressionStatement(path) {
const { expression, comments } = path.node;
let valueOnly;
if (
n.CallExpression.check(expression) &&
n.MemberExpression.check(expression.callee) &&
!expression.callee.computed &&
n.Identifier.check(expression.callee.object) &&
expression.callee.object.name === "_" &&
n.Identifier.check(expression.callee.property) &&
["each", "forEach"].includes(expression.callee.property.name) &&
[2, 3].includes(expression.arguments.length) &&
checkExpression(expression.arguments[0]) &&
(n.FunctionExpression.check(expression.arguments[1]) ||
n.ArrowFunctionExpression.check(expression.arguments[1])) &&
[1, 2].includes(expression.arguments[1].params.length) &&
n.Identifier.check(expression.arguments[1].params[0]) &&
((valueOnly = expression.arguments[1].params[1] === undefined) ||
n.Identifier.check(expression.arguments[1].params[1])) &&
(expression.arguments[2] === undefined ||
n.ThisExpression.check(expression.arguments[2]))
) {
const old = { inLoop, replaceReturn };
inLoop = false;
replaceReturn = true;
this.visit(
path
.get("expression")
.get("arguments")
.get(1)
.get("body")
);
inLoop = old.inLoop;
replaceReturn = old.replaceReturn;
const [right, { body, params }] = expression.arguments;
const loop = b.forOfStatement(
b.variableDeclaration("let", [
b.variableDeclarator(
valueOnly ? params[0] : b.arrayPattern([params[1], params[0]])
),
]),
valueOnly
? right
: b.callExpression(
b.memberExpression(right, b.identifier("entries")),
[]
),
checkStatement(body) ? body : b.expressionStatement(body)
);
loop.comments = comments;
path.replace(loop);
changed = true;
}
this.traverse(path);
},
visitForStatement: visitLoop("init", "test", "update"),
visitForInStatement: visitLoop("left", "right"),
visitForOfStatement: visitLoop("left", "right"),
visitFunction(path) {
this.visit(path.get("params"));
const old = { replaceReturn };
replaceReturn = false;
this.visit(path.get("body"));
replaceReturn = old.replaceReturn;
return false;
},
visitReturnStatement(path) {
if (replaceReturn) {
assert(!inLoop); // could use labeled continue if this ever fires
const { argument, comments } = path.node;
if (argument === null) {
const s = b.continueStatement();
s.comments = comments;
path.replace(s);
} else {
const s = b.expressionStatement(argument);
s.comments = comments;
path.replace(s, b.continueStatement());
}
return false;
}
this.traverse(path);
},
visitWhileStatement: visitLoop("test"),
});
if (changed) {
console.log("Writing", file);
fs.writeFileSync(file, recast.print(ast).code, { encoding: "utf8" });
}
}
Signed-off-by: Anders Kaseorg <anders@zulipchat.com>
2020-02-06 06:19:47 +01:00
|
|
|
}
|
2017-08-19 01:15:18 +02:00
|
|
|
}
|
2020-07-15 01:29:15 +02:00
|
|
|
if (ele.name === "Custom") {
|
2017-08-19 01:15:18 +02:00
|
|
|
check_emojis(true);
|
|
|
|
} else {
|
|
|
|
check_emojis(false);
|
2020-06-14 19:40:33 +02:00
|
|
|
total_emoji_in_categories += ele.emojis.length;
|
2017-08-19 01:15:18 +02:00
|
|
|
}
|
|
|
|
}
|
2020-06-14 19:40:33 +02:00
|
|
|
const popular_emoji_count = 6;
|
|
|
|
const zulip_emoji_count = 1;
|
2022-06-10 22:40:31 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-car", 195);
|
2023-11-29 06:47:59 +01:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-hashtag", 223);
|
2024-07-18 03:13:54 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-smile-o", 168);
|
2020-07-15 01:29:15 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-star-o", popular_emoji_count);
|
2024-07-18 03:13:54 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-thumbs-o-up", 385);
|
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-lightbulb-o", 262);
|
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-cutlery", 135);
|
2022-11-23 01:14:20 +01:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-flag", 269);
|
2020-07-15 01:29:15 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-cog", 1);
|
2024-07-18 03:13:54 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-leaf", 153);
|
2023-06-06 01:17:15 +02:00
|
|
|
assert_emoji_category(complete_emoji_catalog.pop(), "fa-soccer-ball-o", 85);
|
2020-06-14 19:40:33 +02:00
|
|
|
|
|
|
|
// The popular emoji appear twice in the picker, and the zulip emoji is special
|
2020-07-15 00:34:28 +02:00
|
|
|
assert.equal(
|
|
|
|
emoji.emojis_by_name.size,
|
|
|
|
total_emoji_in_categories - popular_emoji_count + zulip_emoji_count,
|
|
|
|
);
|
2018-05-15 12:40:07 +02:00
|
|
|
});
|
2022-04-30 19:52:53 +02:00
|
|
|
|
|
|
|
run_test("is_emoji_present_in_text", () => {
|
|
|
|
const thermometer_emoji = {
|
|
|
|
name: "thermometer",
|
|
|
|
emoji_code: "1f321",
|
|
|
|
reaction_type: "unicode_emoji",
|
|
|
|
};
|
|
|
|
const headphones_emoji = {
|
|
|
|
name: "headphones",
|
|
|
|
emoji_code: "1f3a7",
|
|
|
|
reaction_type: "unicode_emoji",
|
|
|
|
};
|
|
|
|
assert.equal(emoji_picker.is_emoji_present_in_text("🌡", thermometer_emoji), true);
|
|
|
|
assert.equal(
|
|
|
|
emoji_picker.is_emoji_present_in_text("no emojis at all", thermometer_emoji),
|
|
|
|
false,
|
|
|
|
);
|
|
|
|
assert.equal(emoji_picker.is_emoji_present_in_text("😎", thermometer_emoji), false);
|
|
|
|
assert.equal(emoji_picker.is_emoji_present_in_text("😎🌡🎧", thermometer_emoji), true);
|
|
|
|
assert.equal(emoji_picker.is_emoji_present_in_text("😎🎧", thermometer_emoji), false);
|
|
|
|
assert.equal(emoji_picker.is_emoji_present_in_text("😎🌡🎧", headphones_emoji), true);
|
|
|
|
assert.equal(
|
|
|
|
emoji_picker.is_emoji_present_in_text("emojis with text 😎🌡🎧", thermometer_emoji),
|
|
|
|
true,
|
|
|
|
);
|
|
|
|
assert.equal(
|
|
|
|
emoji_picker.is_emoji_present_in_text("emojis with text no space😎🌡🎧", headphones_emoji),
|
|
|
|
true,
|
|
|
|
);
|
|
|
|
});
|