Comply with noImplicitAny (#9940)
* Stash noImplicitAny work * Stash * Fix imports * Iterate * Fix tests * Delint * Fix tests
This commit is contained in:
parent
ac7f69216e
commit
61a63e47f4
359 changed files with 1621 additions and 1353 deletions
|
@ -15,8 +15,9 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import React, { ReactNode } from "react";
|
||||
import { AutoDiscovery } from "matrix-js-sdk/src/autodiscovery";
|
||||
import { AutoDiscovery, ClientConfig } from "matrix-js-sdk/src/autodiscovery";
|
||||
import { logger } from "matrix-js-sdk/src/logger";
|
||||
import { IClientWellKnown } from "matrix-js-sdk/src/matrix";
|
||||
|
||||
import { _t, _td, newTranslatableError } from "../languageHandler";
|
||||
import { makeType } from "./TypeUtils";
|
||||
|
@ -149,7 +150,7 @@ export default class AutoDiscoveryUtils {
|
|||
throw newTranslatableError(_td("No homeserver URL provided"));
|
||||
}
|
||||
|
||||
const wellknownConfig = {
|
||||
const wellknownConfig: IClientWellKnown = {
|
||||
"m.homeserver": {
|
||||
base_url: homeserverUrl,
|
||||
},
|
||||
|
@ -190,7 +191,7 @@ export default class AutoDiscoveryUtils {
|
|||
*/
|
||||
public static buildValidatedConfigFromDiscovery(
|
||||
serverName: string,
|
||||
discoveryResult,
|
||||
discoveryResult: ClientConfig,
|
||||
syntaxOnly = false,
|
||||
isSynthetic = false,
|
||||
): ValidatedServerConfig {
|
||||
|
@ -219,8 +220,8 @@ export default class AutoDiscoveryUtils {
|
|||
} else if (isResult && isResult.state !== AutoDiscovery.PROMPT) {
|
||||
logger.error("Error determining preferred identity server URL:", isResult);
|
||||
if (isResult.state === AutoDiscovery.FAIL_ERROR) {
|
||||
if (AutoDiscovery.ALL_ERRORS.indexOf(isResult.error) !== -1) {
|
||||
throw newTranslatableError(isResult.error);
|
||||
if (AutoDiscovery.ALL_ERRORS.indexOf(isResult.error as string) !== -1) {
|
||||
throw newTranslatableError(isResult.error as string);
|
||||
}
|
||||
throw newTranslatableError(_td("Unexpected error resolving identity server configuration"));
|
||||
} // else the error is not related to syntax - continue anyways.
|
||||
|
@ -235,8 +236,8 @@ export default class AutoDiscoveryUtils {
|
|||
if (hsResult.state !== AutoDiscovery.SUCCESS) {
|
||||
logger.error("Error processing homeserver config:", hsResult);
|
||||
if (!syntaxOnly || !AutoDiscoveryUtils.isLivelinessError(hsResult.error)) {
|
||||
if (AutoDiscovery.ALL_ERRORS.indexOf(hsResult.error) !== -1) {
|
||||
throw newTranslatableError(hsResult.error);
|
||||
if (AutoDiscovery.ALL_ERRORS.indexOf(hsResult.error as string) !== -1) {
|
||||
throw newTranslatableError(hsResult.error as string);
|
||||
}
|
||||
throw newTranslatableError(_td("Unexpected error resolving homeserver configuration"));
|
||||
} // else the error is not related to syntax - continue anyways.
|
||||
|
|
|
@ -189,7 +189,7 @@ export default class DMRoomMap {
|
|||
return Object.keys(this.roomToUser)
|
||||
.map((r) => ({ userId: this.getUserIdForRoomId(r), room: this.matrixClient.getRoom(r) }))
|
||||
.filter((r) => r.userId && r.room && r.room.getInvitedAndJoinedMemberCount() === 2)
|
||||
.reduce((obj, r) => (obj[r.userId] = r.room) && obj, {});
|
||||
.reduce((obj, r) => (obj[r.userId] = r.room) && obj, {} as Record<string, Room>);
|
||||
}
|
||||
|
||||
/**
|
||||
|
|
|
@ -23,7 +23,7 @@ import { IEncryptedFile, IMediaEventInfo } from "../customisations/models/IMedia
|
|||
import { getBlobSafeMimeType } from "./blobs";
|
||||
|
||||
export class DownloadError extends Error {
|
||||
public constructor(e) {
|
||||
public constructor(e: Error) {
|
||||
super(e.message);
|
||||
this.name = "DownloadError";
|
||||
this.stack = e.stack;
|
||||
|
@ -31,7 +31,7 @@ export class DownloadError extends Error {
|
|||
}
|
||||
|
||||
export class DecryptError extends Error {
|
||||
public constructor(e) {
|
||||
public constructor(e: Error) {
|
||||
super(e.message);
|
||||
this.name = "DecryptError";
|
||||
this.stack = e.stack;
|
||||
|
|
|
@ -18,7 +18,7 @@ export type getIframeFn = () => HTMLIFrameElement; // eslint-disable-line @types
|
|||
|
||||
export const DEFAULT_STYLES = {
|
||||
imgSrc: "",
|
||||
imgStyle: null, // css props
|
||||
imgStyle: null as string | null, // css props
|
||||
style: "",
|
||||
textContent: "",
|
||||
};
|
||||
|
|
|
@ -15,6 +15,8 @@ See the License for the specific language governing permissions and
|
|||
limitations under the License.
|
||||
*/
|
||||
|
||||
import { ReactElement, ReactNode } from "react";
|
||||
|
||||
import { _t } from "../languageHandler";
|
||||
import { jsxJoin } from "./ReactUtils";
|
||||
|
||||
|
@ -105,9 +107,9 @@ export function getUserNameColorClass(userId: string): string {
|
|||
* between each item, but with the last item appended as " and [lastItem]".
|
||||
*/
|
||||
export function formatCommaSeparatedList(items: string[], itemLimit?: number): string;
|
||||
export function formatCommaSeparatedList(items: JSX.Element[], itemLimit?: number): JSX.Element;
|
||||
export function formatCommaSeparatedList(items: Array<JSX.Element | string>, itemLimit?: number): JSX.Element | string;
|
||||
export function formatCommaSeparatedList(items: Array<JSX.Element | string>, itemLimit?: number): JSX.Element | string {
|
||||
export function formatCommaSeparatedList(items: ReactElement[], itemLimit?: number): ReactElement;
|
||||
export function formatCommaSeparatedList(items: ReactNode[], itemLimit?: number): ReactNode;
|
||||
export function formatCommaSeparatedList(items: ReactNode[], itemLimit?: number): ReactNode {
|
||||
const remaining = itemLimit === undefined ? 0 : Math.max(items.length - itemLimit, 0);
|
||||
if (items.length === 0) {
|
||||
return "";
|
||||
|
|
|
@ -81,7 +81,7 @@ export default class MultiInviter {
|
|||
* @param {boolean} sendSharedHistoryKeys whether to share e2ee keys with the invitees if applicable.
|
||||
* @returns {Promise} Resolved when all invitations in the queue are complete
|
||||
*/
|
||||
public invite(addresses, reason?: string, sendSharedHistoryKeys = false): Promise<CompletionStates> {
|
||||
public invite(addresses: string[], reason?: string, sendSharedHistoryKeys = false): Promise<CompletionStates> {
|
||||
if (this.addresses.length > 0) {
|
||||
throw new Error("Already inviting/invited");
|
||||
}
|
||||
|
|
|
@ -14,7 +14,7 @@ See the License for the specific language governing permissions and
|
|||
limitations under the License.
|
||||
*/
|
||||
|
||||
import React from "react";
|
||||
import React, { ReactNode } from "react";
|
||||
|
||||
/**
|
||||
* Joins an array into one value with a joiner. E.g. join(["hello", "world"], " ") -> <span>hello world</span>
|
||||
|
@ -22,8 +22,8 @@ import React from "react";
|
|||
* @param joiner the string/JSX.Element to join with
|
||||
* @returns the joined array
|
||||
*/
|
||||
export function jsxJoin(array: Array<string | JSX.Element>, joiner?: string | JSX.Element): JSX.Element {
|
||||
const newArray = [];
|
||||
export function jsxJoin(array: ReactNode[], joiner?: string | JSX.Element): JSX.Element {
|
||||
const newArray: ReactNode[] = [];
|
||||
array.forEach((element, index) => {
|
||||
newArray.push(element, index === array.length - 1 ? null : joiner);
|
||||
});
|
||||
|
|
|
@ -69,7 +69,15 @@ export function getNestedReplyText(
|
|||
): { body: string; html: string } | null {
|
||||
if (!ev) return null;
|
||||
|
||||
let { body, formatted_body: html, msgtype } = ev.getContent();
|
||||
let {
|
||||
body,
|
||||
formatted_body: html,
|
||||
msgtype,
|
||||
} = ev.getContent<{
|
||||
body: string;
|
||||
msgtype?: string;
|
||||
formatted_body?: string;
|
||||
}>();
|
||||
if (getParentEventId(ev)) {
|
||||
if (body) body = stripPlainReply(body);
|
||||
}
|
||||
|
|
|
@ -25,7 +25,7 @@ export class SnakedObject<T = Record<string, any>> {
|
|||
const val = this.obj[key];
|
||||
if (val !== undefined) return val;
|
||||
|
||||
return this.obj[altCaseName ?? snakeToCamel(key)];
|
||||
return this.obj[<K>(altCaseName ?? snakeToCamel(key))];
|
||||
}
|
||||
|
||||
// Make JSON.stringify() pretend that everything is fine
|
||||
|
|
|
@ -30,7 +30,7 @@ export default class Timer {
|
|||
private startTs?: number;
|
||||
private promise: Promise<void>;
|
||||
private resolve: () => void;
|
||||
private reject: (Error) => void;
|
||||
private reject: (err: Error) => void;
|
||||
|
||||
public constructor(private timeout: number) {
|
||||
this.setNotStarted();
|
||||
|
|
|
@ -40,7 +40,7 @@ export function wrapRequestWithDialog<R, A = any>(
|
|||
Modal.createDialog(InteractiveAuthDialog, {
|
||||
...opts,
|
||||
authData: error.data,
|
||||
makeRequest: (authData) => boundFunction(authData, ...args),
|
||||
makeRequest: (authData?: IAuthData) => boundFunction(authData, ...args),
|
||||
onFinished: (success, result) => {
|
||||
if (success) {
|
||||
resolve(result);
|
||||
|
|
|
@ -25,5 +25,5 @@ export class ValidatedServerConfig {
|
|||
// when the server config is based on static URLs the hsName is not resolvable and things may wish to use hsUrl
|
||||
public isNameResolvable: boolean;
|
||||
|
||||
public warning: string;
|
||||
public warning: string | Error;
|
||||
}
|
||||
|
|
|
@ -143,7 +143,7 @@ export default class WidgetUtils {
|
|||
return new Promise((resolve, reject) => {
|
||||
// Tests an account data event, returning true if it's in the state
|
||||
// we're waiting for it to be in
|
||||
function eventInIntendedState(ev): boolean {
|
||||
function eventInIntendedState(ev: MatrixEvent): boolean {
|
||||
if (!ev || !ev.getContent()) return false;
|
||||
if (add) {
|
||||
return ev.getContent()[widgetId] !== undefined;
|
||||
|
@ -158,7 +158,7 @@ export default class WidgetUtils {
|
|||
return;
|
||||
}
|
||||
|
||||
function onAccountData(ev): void {
|
||||
function onAccountData(ev: MatrixEvent): void {
|
||||
const currentAccountDataEvent = MatrixClientPeg.get().getAccountData("m.widgets");
|
||||
if (eventInIntendedState(currentAccountDataEvent)) {
|
||||
MatrixClientPeg.get().removeListener(ClientEvent.AccountData, onAccountData);
|
||||
|
|
|
@ -37,7 +37,7 @@ const GeolocationOptions = {
|
|||
};
|
||||
|
||||
const isGeolocationPositionError = (error: unknown): error is GeolocationPositionError =>
|
||||
typeof error === "object" && !!error["PERMISSION_DENIED"];
|
||||
typeof error === "object" && !!(error as GeolocationPositionError)["PERMISSION_DENIED"];
|
||||
/**
|
||||
* Maps GeolocationPositionError to our GeolocationError enum
|
||||
*/
|
||||
|
@ -132,7 +132,7 @@ export const watchPosition = (
|
|||
onWatchPositionError: (error: GeolocationError) => void,
|
||||
): ClearWatchCallback => {
|
||||
try {
|
||||
const onError = (error): void => onWatchPositionError(mapGeolocationError(error));
|
||||
const onError = (error: GeolocationPositionError): void => onWatchPositionError(mapGeolocationError(error));
|
||||
const watchId = getGeolocation().watchPosition(onWatchPosition, onError, GeolocationOptions);
|
||||
const clearWatch = (): void => {
|
||||
getGeolocation().clearWatch(watchId);
|
||||
|
|
|
@ -31,7 +31,7 @@ const localStorage = window.localStorage;
|
|||
|
||||
// just *accessing* indexedDB throws an exception in firefox with
|
||||
// indexeddb disabled.
|
||||
let indexedDB;
|
||||
let indexedDB: IDBFactory;
|
||||
try {
|
||||
indexedDB = window.indexedDB;
|
||||
} catch (e) {}
|
||||
|
|
|
@ -22,6 +22,8 @@ export enum ExportFormat {
|
|||
Json = "Json",
|
||||
}
|
||||
|
||||
export type ExportFormatKey = "Html" | "PlainText" | "Json";
|
||||
|
||||
export enum ExportType {
|
||||
Timeline = "Timeline",
|
||||
Beginning = "Beginning",
|
||||
|
@ -29,6 +31,8 @@ export enum ExportType {
|
|||
// START_DATE = "START_DATE",
|
||||
}
|
||||
|
||||
export type ExportTypeKey = "Timeline" | "Beginning" | "LastNMessages";
|
||||
|
||||
export const textForFormat = (format: ExportFormat): string => {
|
||||
switch (format) {
|
||||
case ExportFormat.Html:
|
||||
|
|
|
@ -15,13 +15,13 @@ limitations under the License.
|
|||
*/
|
||||
|
||||
import { BlurhashEncoder } from "../BlurhashEncoder";
|
||||
import { IEncryptedFile } from "../customisations/models/IMediaEventContent";
|
||||
|
||||
type ThumbnailableElement = HTMLImageElement | HTMLVideoElement;
|
||||
|
||||
interface IThumbnail {
|
||||
info: {
|
||||
// eslint-disable-next-line camelcase
|
||||
thumbnail_info: {
|
||||
thumbnail_info?: {
|
||||
w: number;
|
||||
h: number;
|
||||
mimetype: string;
|
||||
|
@ -30,6 +30,8 @@ interface IThumbnail {
|
|||
w: number;
|
||||
h: number;
|
||||
[BLURHASH_FIELD]: string;
|
||||
thumbnail_url?: string;
|
||||
thumbnail_file?: IEncryptedFile;
|
||||
};
|
||||
thumbnail: Blob;
|
||||
}
|
||||
|
|
|
@ -83,7 +83,7 @@ export const makeMapSiteLink = (coords: GeolocationCoordinates): string => {
|
|||
};
|
||||
|
||||
export const createMapSiteLinkFromEvent = (event: MatrixEvent): string => {
|
||||
const content: Object = event.getContent();
|
||||
const content = event.getContent();
|
||||
const mLocation = content[M_LOCATION.name];
|
||||
if (mLocation !== undefined) {
|
||||
const uri = mLocation["uri"];
|
||||
|
|
|
@ -44,10 +44,9 @@ export enum EffectiveMembership {
|
|||
Leave = "LEAVE",
|
||||
}
|
||||
|
||||
export interface MembershipSplit {
|
||||
// @ts-ignore - TS wants this to be a string key, but we know better.
|
||||
[state: EffectiveMembership]: Room[];
|
||||
}
|
||||
export type MembershipSplit = Partial<{
|
||||
[state in EffectiveMembership]: Room[];
|
||||
}>;
|
||||
|
||||
export function splitRoomsByMembership(rooms: Room[]): MembershipSplit {
|
||||
const split: MembershipSplit = {
|
||||
|
|
|
@ -90,7 +90,7 @@ export function objectHasDiff<O extends {}>(a: O, b: O): boolean {
|
|||
const aKeys = Object.keys(a);
|
||||
const bKeys = Object.keys(b);
|
||||
if (aKeys.length !== bKeys.length) return true;
|
||||
const possibleChanges = arrayIntersection(aKeys, bKeys);
|
||||
const possibleChanges = arrayIntersection(aKeys, bKeys) as Array<keyof O>;
|
||||
// if the amalgamation of both sets of keys has the a different length to the inputs then there must be a change
|
||||
if (possibleChanges.length !== aKeys.length) return true;
|
||||
|
||||
|
|
|
@ -208,7 +208,7 @@ export class RoomPermalinkCreator {
|
|||
}
|
||||
|
||||
private updateAllowedServers(): void {
|
||||
const bannedHostsRegexps = [];
|
||||
const bannedHostsRegexps: RegExp[] = [];
|
||||
let allowedHostsRegexps = [ANY_REGEX]; // default allow everyone
|
||||
if (this.room.currentState) {
|
||||
const aclEvent = this.room.currentState.getStateEvents(EventType.RoomServerAcl, "");
|
||||
|
@ -216,10 +216,10 @@ export class RoomPermalinkCreator {
|
|||
const getRegex = (hostname: string): RegExp =>
|
||||
new RegExp("^" + utils.globToRegexp(hostname, false) + "$");
|
||||
|
||||
const denied = aclEvent.getContent().deny || [];
|
||||
const denied = aclEvent.getContent<{ deny: string[] }>().deny || [];
|
||||
denied.forEach((h) => bannedHostsRegexps.push(getRegex(h)));
|
||||
|
||||
const allowed = aclEvent.getContent().allow || [];
|
||||
const allowed = aclEvent.getContent<{ allow: string[] }>().allow || [];
|
||||
allowedHostsRegexps = []; // we don't want to use the default rule here
|
||||
allowed.forEach((h) => allowedHostsRegexps.push(getRegex(h)));
|
||||
}
|
||||
|
|
|
@ -106,7 +106,7 @@ export function pillifyLinks(nodes: ArrayLike<Element>, mxEvent: MatrixEvent, pi
|
|||
// we're adding now, since we've just inserted nodes into the structure
|
||||
// we're iterating over.
|
||||
// Note we've checked roomNotifTextNodes.length > 0 so we'll do this at least once
|
||||
node = roomNotifTextNode.nextSibling;
|
||||
node = roomNotifTextNode.nextSibling as Element;
|
||||
|
||||
const pillContainer = document.createElement("span");
|
||||
const pill = (
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue