eslint: Fix @typescript-eslint/prefer-nullish-coalescing.

Signed-off-by: Anders Kaseorg <anders@zulip.com>
This commit is contained in:
Anders Kaseorg
2025-04-09 14:07:24 -07:00
committed by Tim Abbott
parent 819504a0e9
commit ff4337eee5
22 changed files with 57 additions and 122 deletions

View File

@@ -66,8 +66,7 @@ export const window_size = {
}; };
export async function ensure_browser(): Promise<Browser> { export async function ensure_browser(): Promise<Browser> {
if (browser === null) { browser ??= await puppeteer.launch({
browser = await puppeteer.launch({
args: [ args: [
`--window-size=${window_size.width},${window_size.height}`, `--window-size=${window_size.width},${window_size.height}`,
"--no-sandbox", "--no-sandbox",
@@ -78,7 +77,6 @@ export async function ensure_browser(): Promise<Browser> {
defaultViewport: null, defaultViewport: null,
headless: true, headless: true,
}); });
}
return browser; return browser;
} }
@@ -256,14 +254,11 @@ export async function get_internal_email_from_name(
export async function log_in( export async function log_in(
page: Page, page: Page,
credentials: {username: string; password: string} | null = null, credentials: {username: string; password: string} = test_credentials.default_user,
): Promise<void> { ): Promise<void> {
console.log("Logging in"); console.log("Logging in");
await page.goto(realm_url + "login/"); await page.goto(realm_url + "login/");
assert.equal(realm_url + "login/", page.url()); assert.equal(realm_url + "login/", page.url());
if (credentials === null) {
credentials = test_credentials.default_user;
}
// fill login form // fill login form
const params = { const params = {
username: credentials.username, username: credentials.username,

View File

@@ -175,13 +175,10 @@ export function current_scroll_offset(): number | undefined {
export function update_current_history_state_data( export function update_current_history_state_data(
new_data: StateData, new_data: StateData,
url: string | undefined = undefined, url: string = window.location.href,
): void { ): void {
// The optional url parameter is for those rare situations where // The optional url parameter is for those rare situations where
// we want to adjust the URL without adding a new history entry. // we want to adjust the URL without adding a new history entry.
if (url === undefined) {
url = window.location.href;
}
const current_state = state_data_schema.nullable().parse(window.history.state); const current_state = state_data_schema.nullable().parse(window.history.state);
const current_state_data = { const current_state_data = {
narrow_pointer: current_state?.narrow_pointer, narrow_pointer: current_state?.narrow_pointer,

View File

@@ -344,13 +344,7 @@ export function update_topic_inputbox_on_mandatory_topics_change(): void {
update_topic_displayed_text(compose_state.topic()); update_topic_displayed_text(compose_state.topic());
} }
export function update_topic_displayed_text( export function update_topic_displayed_text(topic_name = "", has_topic_focus = false): void {
topic_name: string | undefined,
has_topic_focus = false,
): void {
if (topic_name === undefined) {
topic_name = "";
}
compose_state.topic(topic_name); compose_state.topic(topic_name);
// When topics are mandatory, no additional adjustments are needed. // When topics are mandatory, no additional adjustments are needed.

View File

@@ -285,11 +285,9 @@ export function analyze_selection(selection: Selection): {
// Skip any selection sections that don't intersect a message. // Skip any selection sections that don't intersect a message.
continue; continue;
} }
if (start_id === undefined) {
// start_id is the Zulip message ID of the first message // start_id is the Zulip message ID of the first message
// touched by the selection. // touched by the selection.
start_id = start_data[0]; start_id ??= start_data[0];
}
$endc = $(range.endContainer); $endc = $(range.endContainer);
$initial_end_tr = get_end_tr_from_endc($endc); $initial_end_tr = get_end_tr_from_endc($endc);

View File

@@ -37,14 +37,14 @@ export function append_custom_profile_fields(element_id: string, user_id: number
]); ]);
for (const field of all_custom_fields) { for (const field of all_custom_fields) {
let field_value = people.get_custom_profile_data(user_id, field.id); const field_value = people.get_custom_profile_data(user_id, field.id) ?? {
value: "",
rendered_value: "",
};
const editable_by_user = current_user.is_admin || field.editable_by_user; const editable_by_user = current_user.is_admin || field.editable_by_user;
const is_select_field = field.type === all_field_types.SELECT.id; const is_select_field = field.type === all_field_types.SELECT.id;
const field_choices = []; const field_choices = [];
if (field_value === undefined || field_value === null) {
field_value = {value: "", rendered_value: ""};
}
if (is_select_field) { if (is_select_field) {
const field_choice_dict = settings_components.select_field_data_schema.parse( const field_choice_dict = settings_components.select_field_data_schema.parse(
JSON.parse(field.field_data), JSON.parse(field.field_data),

View File

@@ -145,9 +145,7 @@ export const draft_model = (function () {
// since we expect bugged drafts will have either been run // since we expect bugged drafts will have either been run
// through this code or been deleted by the previous // through this code or been deleted by the previous
// behavior of deleting them after 30 days. // behavior of deleting them after 30 days.
if (draft.topic === undefined) { draft.topic ??= "";
draft.topic = "";
}
valid_drafts[draft_id] = { valid_drafts[draft_id] = {
...draft, ...draft,

View File

@@ -1008,9 +1008,7 @@ export class Filter {
} }
predicate(): (message: Message) => boolean { predicate(): (message: Message) => boolean {
if (this._predicate === undefined) { this._predicate ??= this._build_predicate();
this._predicate = this._build_predicate();
}
return this._predicate; return this._predicate;
} }
@@ -1154,9 +1152,7 @@ export class Filter {
} }
can_mark_messages_read(): boolean { can_mark_messages_read(): boolean {
if (this._can_mark_messages_read === undefined) { this._can_mark_messages_read ??= this.calc_can_mark_messages_read();
this._can_mark_messages_read = this.calc_can_mark_messages_read();
}
return this._can_mark_messages_read; return this._can_mark_messages_read;
} }

View File

@@ -61,9 +61,7 @@ async function renderGIPHYGrid(targetEl: HTMLElement): Promise<{remove: () => vo
const {renderGrid} = await import(/* webpackChunkName: "giphy-sdk" */ "@giphy/js-components"); const {renderGrid} = await import(/* webpackChunkName: "giphy-sdk" */ "@giphy/js-components");
const {GiphyFetch} = await import(/* webpackChunkName: "giphy-sdk" */ "@giphy/js-fetch-api"); const {GiphyFetch} = await import(/* webpackChunkName: "giphy-sdk" */ "@giphy/js-fetch-api");
if (giphy_fetch === undefined) { giphy_fetch ??= new GiphyFetch(realm.giphy_api_key);
giphy_fetch = new GiphyFetch(realm.giphy_api_key);
}
async function fetchGifs(offset: number): Promise<GifsResult> { async function fetchGifs(offset: number): Promise<GifsResult> {
assert(giphy_fetch !== undefined); assert(giphy_fetch !== undefined);

View File

@@ -291,12 +291,8 @@ export function update_information_density_settings(
$elem: JQuery, $elem: JQuery,
changed_property: "web_font_size_px" | "web_line_height_percent", changed_property: "web_font_size_px" | "web_line_height_percent",
for_settings_ui = false, for_settings_ui = false,
new_value?: number, new_value: number = get_new_value_for_information_density_settings($elem, changed_property),
): number { ): number {
if (new_value === undefined) {
new_value = get_new_value_for_information_density_settings($elem, changed_property);
}
user_settings[changed_property] = new_value; user_settings[changed_property] = new_value;
$elem.closest(".button-group").find(".current-value").val(new_value); $elem.closest(".button-group").find(".current-value").val(new_value);
if (for_settings_ui) { if (for_settings_ui) {

View File

@@ -432,12 +432,11 @@ function open_invite_user_modal(e: JQuery.ClickEvent<Document, undefined>): void
$(e.target).parent().remove(); $(e.target).parent().remove();
}); });
function toggle_invite_submit_button(selected_tab?: string): void { function toggle_invite_submit_button(
if (selected_tab === undefined) { selected_tab: string | undefined = $(".invite_users_option_tabs")
selected_tab = $(".invite_users_option_tabs")
.find(".selected") .find(".selected")
.attr("data-tab-key"); .attr("data-tab-key"),
} ): void {
const valid_custom_time = util.validate_custom_time_input( const valid_custom_time = util.validate_custom_time_input(
custom_expiration_time_input, custom_expiration_time_input,
false, false,

View File

@@ -373,17 +373,13 @@ function display_video(payload: Media): void {
} }
export function build_open_media_function( export function build_open_media_function(
on_close: (() => void) | undefined, on_close = (): void => {
): ($media: JQuery<HTMLMediaElement | HTMLImageElement>) => void {
if (on_close === undefined) {
on_close = function () {
remove_video_players(); remove_video_players();
is_open = false; is_open = false;
assert(document.activeElement instanceof HTMLElement); assert(document.activeElement instanceof HTMLElement);
document.activeElement.blur(); document.activeElement.blur();
}; },
} ): ($media: JQuery<HTMLMediaElement | HTMLImageElement>) => void {
return function ($media: JQuery<HTMLMediaElement | HTMLImageElement>): void { return function ($media: JQuery<HTMLMediaElement | HTMLImageElement>): void {
// This is used both for clicking on media in the messagelist, as well as clicking on images // This is used both for clicking on media in the messagelist, as well as clicking on images
// in the media list under the lightbox when it is open. // in the media list under the lightbox when it is open.

View File

@@ -449,12 +449,9 @@ export function update_messages(events: UpdateMessageEvent[]): void {
// Add message's edit_history in message dict // Add message's edit_history in message dict
// For messages that are edited, edit_history needs to // For messages that are edited, edit_history needs to
// be added to message in frontend. // be added to message in frontend.
if (anchor_message.edit_history === undefined) {
anchor_message.edit_history = [];
}
anchor_message.edit_history = [ anchor_message.edit_history = [
edit_history_entry, edit_history_entry,
...anchor_message.edit_history, ...(anchor_message.edit_history ?? []),
]; ];
} }
any_message_content_edited = true; any_message_content_edited = true;
@@ -587,12 +584,9 @@ export function update_messages(events: UpdateMessageEvent[]): void {
edit_history_entry.topic = new_topic; edit_history_entry.topic = new_topic;
edit_history_entry.prev_topic = orig_topic; edit_history_entry.prev_topic = orig_topic;
} }
if (moved_message.edit_history === undefined) {
moved_message.edit_history = [];
}
moved_message.edit_history = [ moved_message.edit_history = [
edit_history_entry, edit_history_entry,
...moved_message.edit_history, ...(moved_message.edit_history ?? []),
]; ];
} }

View File

@@ -56,10 +56,7 @@ export function process_new_message(raw_message: RawMessage, deliver_locally = f
let message: Message; let message: Message;
if (message_with_booleans.type === "stream") { if (message_with_booleans.type === "stream") {
let topic = message_with_booleans.topic; const topic = message_with_booleans.topic ?? message_with_booleans.subject;
if (topic === undefined) {
topic = message_with_booleans.subject;
}
assert(topic !== undefined); assert(topic !== undefined);
// We add fully delivered messages to stream_topic_history, // We add fully delivered messages to stream_topic_history,

View File

@@ -206,9 +206,7 @@ export class MessageListData {
} }
_get_predicate(): (message: Message) => boolean { _get_predicate(): (message: Message) => boolean {
// We cache this. // We cache this.
if (!this.predicate) { this.predicate ??= this.filter.predicate();
this.predicate = this.filter.predicate();
}
return this.predicate; return this.predicate;
} }

View File

@@ -1202,10 +1202,7 @@ export function render_message_list_with_selected_message(opts: {
const id_info = opts.id_info; const id_info = opts.id_info;
const select_offset = opts.select_offset; const select_offset = opts.select_offset;
let msg_id = id_info.final_select_id; const msg_id = id_info.final_select_id ?? message_lists.current.first_unread_message_id();
if (msg_id === undefined) {
msg_id = message_lists.current.first_unread_message_id();
}
// There should be something since it's not visibly empty. // There should be something since it's not visibly empty.
assert(msg_id !== undefined); assert(msg_id !== undefined);

View File

@@ -1237,9 +1237,7 @@ export function build_termlet_matcher(termlet: string): (user: User) => boolean
let full_name = user.full_name; let full_name = user.full_name;
// Only ignore diacritics if the query is plain ascii // Only ignore diacritics if the query is plain ascii
if (is_ascii) { if (is_ascii) {
if (user.name_with_diacritics_removed === undefined) { user.name_with_diacritics_removed ??= typeahead.remove_diacritics(full_name);
user.name_with_diacritics_removed = typeahead.remove_diacritics(full_name);
}
full_name = user.name_with_diacritics_removed; full_name = user.name_with_diacritics_removed;
} }
const names = full_name.toLowerCase().split(" "); const names = full_name.toLowerCase().split(" ");
@@ -1576,11 +1574,7 @@ export function get_user_by_id_assert_valid(
return get_by_user_id(user_id); return get_by_user_id(user_id);
} }
let person = maybe_get_user_by_id(user_id, true); return maybe_get_user_by_id(user_id, true) ?? add_inaccessible_user(user_id);
if (person === undefined) {
person = add_inaccessible_user(user_id);
}
return person;
} }
function get_involved_people(message: MessageWithBooleans): DisplayRecipientUser[] { function get_involved_people(message: MessageWithBooleans): DisplayRecipientUser[] {

View File

@@ -1,5 +1,6 @@
import Handlebars from "handlebars/runtime.js"; import Handlebars from "handlebars/runtime.js";
import $ from "jquery"; import $ from "jquery";
import assert from "minimalistic-assert";
import render_banner from "../../templates/components/banner.hbs"; import render_banner from "../../templates/components/banner.hbs";
import {$t, $t_html} from "../i18n.ts"; import {$t, $t_html} from "../i18n.ts";
@@ -404,7 +405,8 @@ $(window).on("load", () => {
return; return;
} }
let label = $<HTMLInputElement>("input#primary_button_text").val(); let label = $<HTMLInputElement>("input#primary_button_text").val();
if (!label) { assert(label !== undefined);
if (label === "") {
label = "Primary Button"; label = "Primary Button";
} }
const is_icon_enabled = $("#enable_primary_button_icon").prop("checked") === true; const is_icon_enabled = $("#enable_primary_button_icon").prop("checked") === true;
@@ -498,7 +500,8 @@ $(window).on("load", () => {
return; return;
} }
let label = $<HTMLInputElement>("input#quiet_button_text").val(); let label = $<HTMLInputElement>("input#quiet_button_text").val();
if (!label) { assert(label !== undefined);
if (label === "") {
label = "Quiet Button"; label = "Quiet Button";
} }
const is_icon_enabled = $("#enable_quiet_button_icon").prop("checked") === true; const is_icon_enabled = $("#enable_quiet_button_icon").prop("checked") === true;
@@ -587,7 +590,8 @@ $(window).on("load", () => {
return; return;
} }
let label = $<HTMLInputElement>("input#borderless_button_text").val(); let label = $<HTMLInputElement>("input#borderless_button_text").val();
if (!label) { assert(label !== undefined);
if (label === "") {
label = "Borderless Button"; label = "Borderless Button";
} }
const is_icon_enabled = $("#enable_borderless_button_icon").prop("checked") === true; const is_icon_enabled = $("#enable_borderless_button_icon").prop("checked") === true;

View File

@@ -8,9 +8,7 @@ import * as util from "./util.ts";
let inertDocument: Document | undefined; let inertDocument: Document | undefined;
export function postprocess_content(html: string): string { export function postprocess_content(html: string): string {
if (inertDocument === undefined) { inertDocument ??= new DOMParser().parseFromString("", "text/html");
inertDocument = new DOMParser().parseFromString("", "text/html");
}
const template = inertDocument.createElement("template"); const template = inertDocument.createElement("template");
template.innerHTML = html; template.innerHTML = html;

View File

@@ -31,9 +31,7 @@ export class IdTracker {
} }
max_id(): number { max_id(): number {
if (this._cached_max_id === undefined) { this._cached_max_id ??= _.max([...this.ids]);
this._cached_max_id = _.max([...this.ids]);
}
return this._cached_max_id ?? -1; return this._cached_max_id ?? -1;
} }

View File

@@ -160,10 +160,7 @@ function stream_notification_setting_changed(target: HTMLInputElement): void {
const $status_element = $(target).closest(".subsection-parent").find(".alert-notification"); const $status_element = $(target).closest(".subsection-parent").find(".alert-notification");
const setting = stream_specific_notification_settings_schema.keyof().parse(target.name); const setting = stream_specific_notification_settings_schema.keyof().parse(target.name);
if (sub[setting] === null) { sub[setting] ??= user_settings[settings_config.generalize_stream_notification_setting[setting]];
sub[setting] =
user_settings[settings_config.generalize_stream_notification_setting[setting]];
}
stream_settings_api.set_stream_property( stream_settings_api.set_stream_property(
sub, sub,
{property: setting, value: target.checked}, {property: setting, value: target.checked},

View File

@@ -209,11 +209,7 @@ export function get_stream_id(name: string): number | undefined {
// Note: Only use this function for situations where // Note: Only use this function for situations where
// you are comfortable with a user dealing with an // you are comfortable with a user dealing with an
// old name of a stream (from prior to a rename). // old name of a stream (from prior to a rename).
let stream_id = stream_ids_by_name.get(name); return stream_ids_by_name.get(name) ?? stream_ids_by_old_names.get(name);
if (!stream_id) {
stream_id = stream_ids_by_old_names.get(name);
}
return stream_id;
} }
export function get_stream_name_from_id(stream_id: number): string { export function get_stream_name_from_id(stream_id: number): string {
@@ -224,10 +220,7 @@ export let get_sub_by_name = (name: string): StreamSubscription | undefined => {
// Note: Only use this function for situations where // Note: Only use this function for situations where
// you are comfortable with a user dealing with an // you are comfortable with a user dealing with an
// old name of a stream (from prior to a rename). // old name of a stream (from prior to a rename).
let stream_id = stream_ids_by_name.get(name); const stream_id = stream_ids_by_name.get(name) ?? stream_ids_by_old_names.get(name);
if (!stream_id) {
stream_id = stream_ids_by_old_names.get(name);
}
if (!stream_id) { if (!stream_id) {
return undefined; return undefined;
} }

View File

@@ -165,9 +165,7 @@ export function update_message(submsg: Submessage): void {
return; return;
} }
if (message.submessages === undefined) { message.submessages ??= [];
message.submessages = [];
}
const existing = message.submessages.find((sm) => sm.id === submsg.id); const existing = message.submessages.find((sm) => sm.id === submsg.id);