Harden Settings using mapped types (#28775)
* Harden Settings using mapped types Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> * Fix issues found during hardening Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> * Iterate Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> * Iterate Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> * Iterate Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> * Remove oidc native flow stale key Signed-off-by: Michael Telatynski <7t3chguy@gmail.com> --------- Signed-off-by: Michael Telatynski <7t3chguy@gmail.com>
This commit is contained in:
committed by
GitHub
parent
4e1bd69e4d
commit
1e42f28a69
@@ -17,7 +17,7 @@ import { filterBoolean } from "../../utils/arrays";
|
||||
export const useRecentSearches = (): [Room[], () => void] => {
|
||||
const [rooms, setRooms] = useState(() => {
|
||||
const cli = MatrixClientPeg.safeGet();
|
||||
const recents = SettingsStore.getValue<string[]>("SpotlightSearch.recentSearches", null);
|
||||
const recents = SettingsStore.getValue("SpotlightSearch.recentSearches", null);
|
||||
return filterBoolean(recents.map((r) => cli.getRoom(r)));
|
||||
});
|
||||
|
||||
|
||||
@@ -55,7 +55,7 @@ export const usePublicRoomDirectory = (): {
|
||||
|
||||
const [updateQuery, updateResult] = useLatestResult<IRoomDirectoryOptions, IPublicRoomsChunkRoom[]>(setPublicRooms);
|
||||
|
||||
const showNsfwPublicRooms = useSettingValue<boolean>("SpotlightSearch.showNsfwPublicRooms");
|
||||
const showNsfwPublicRooms = useSettingValue("SpotlightSearch.showNsfwPublicRooms");
|
||||
|
||||
async function initProtocols(): Promise<void> {
|
||||
if (!MatrixClientPeg.get()) {
|
||||
|
||||
@@ -10,14 +10,39 @@ import { useEffect, useState } from "react";
|
||||
|
||||
import SettingsStore from "../settings/SettingsStore";
|
||||
import { SettingLevel } from "../settings/SettingLevel";
|
||||
import { FeatureSettingKey, SettingKey, Settings } from "../settings/Settings.tsx";
|
||||
|
||||
// Hook to fetch the value of a setting and dynamically update when it changes
|
||||
export const useSettingValue = <T>(settingName: string, roomId: string | null = null, excludeDefault = false): T => {
|
||||
const [value, setValue] = useState(SettingsStore.getValue<T>(settingName, roomId, excludeDefault));
|
||||
export function useSettingValue<S extends SettingKey>(
|
||||
settingName: S,
|
||||
roomId: string | null,
|
||||
excludeDefault: true,
|
||||
): Settings[S]["default"] | undefined;
|
||||
export function useSettingValue<S extends SettingKey>(
|
||||
settingName: S,
|
||||
roomId?: string | null,
|
||||
excludeDefault?: false,
|
||||
): Settings[S]["default"];
|
||||
export function useSettingValue<S extends SettingKey>(
|
||||
settingName: S,
|
||||
roomId: string | null = null,
|
||||
excludeDefault = false,
|
||||
): Settings[S]["default"] | undefined {
|
||||
const [value, setValue] = useState(
|
||||
// XXX: This seems naff but is needed to convince TypeScript that the overload is fine
|
||||
excludeDefault
|
||||
? SettingsStore.getValue(settingName, roomId, excludeDefault)
|
||||
: SettingsStore.getValue(settingName, roomId, excludeDefault),
|
||||
);
|
||||
|
||||
useEffect(() => {
|
||||
const ref = SettingsStore.watchSetting(settingName, roomId, () => {
|
||||
setValue(SettingsStore.getValue<T>(settingName, roomId, excludeDefault));
|
||||
setValue(
|
||||
// XXX: This seems naff but is needed to convince TypeScript that the overload is fine
|
||||
excludeDefault
|
||||
? SettingsStore.getValue(settingName, roomId, excludeDefault)
|
||||
: SettingsStore.getValue(settingName, roomId, excludeDefault),
|
||||
);
|
||||
});
|
||||
// clean-up
|
||||
return () => {
|
||||
@@ -26,7 +51,7 @@ export const useSettingValue = <T>(settingName: string, roomId: string | null =
|
||||
}, [settingName, roomId, excludeDefault]);
|
||||
|
||||
return value;
|
||||
};
|
||||
}
|
||||
|
||||
/**
|
||||
* Hook to fetch the value of a setting at a specific level and dynamically update when it changes
|
||||
@@ -37,20 +62,18 @@ export const useSettingValue = <T>(settingName: string, roomId: string | null =
|
||||
* @param explicit
|
||||
* @param excludeDefault
|
||||
*/
|
||||
export const useSettingValueAt = <T>(
|
||||
export const useSettingValueAt = <S extends SettingKey>(
|
||||
level: SettingLevel,
|
||||
settingName: string,
|
||||
settingName: S,
|
||||
roomId: string | null = null,
|
||||
explicit = false,
|
||||
excludeDefault = false,
|
||||
): T => {
|
||||
const [value, setValue] = useState(
|
||||
SettingsStore.getValueAt<T>(level, settingName, roomId, explicit, excludeDefault),
|
||||
);
|
||||
): Settings[S]["default"] => {
|
||||
const [value, setValue] = useState(SettingsStore.getValueAt(level, settingName, roomId, explicit, excludeDefault));
|
||||
|
||||
useEffect(() => {
|
||||
const ref = SettingsStore.watchSetting(settingName, roomId, () => {
|
||||
setValue(SettingsStore.getValueAt<T>(level, settingName, roomId, explicit, excludeDefault));
|
||||
setValue(SettingsStore.getValueAt(level, settingName, roomId, explicit, excludeDefault));
|
||||
});
|
||||
// clean-up
|
||||
return () => {
|
||||
@@ -62,8 +85,8 @@ export const useSettingValueAt = <T>(
|
||||
};
|
||||
|
||||
// Hook to fetch whether a feature is enabled and dynamically update when that changes
|
||||
export const useFeatureEnabled = (featureName: string, roomId: string | null = null): boolean => {
|
||||
const [enabled, setEnabled] = useState(SettingsStore.getValue<boolean>(featureName, roomId));
|
||||
export const useFeatureEnabled = (featureName: FeatureSettingKey, roomId: string | null = null): boolean => {
|
||||
const [enabled, setEnabled] = useState(SettingsStore.getValue(featureName, roomId));
|
||||
|
||||
useEffect(() => {
|
||||
const ref = SettingsStore.watchSetting(featureName, roomId, () => {
|
||||
|
||||
@@ -16,10 +16,10 @@ export function useTheme(): { theme: string; systemThemeActivated: boolean } {
|
||||
// We have to mirror the logic from ThemeWatcher.getEffectiveTheme so we
|
||||
// show the right values for things.
|
||||
|
||||
const themeChoice = useSettingValue<string>("theme");
|
||||
const systemThemeExplicit = useSettingValueAt<string>(SettingLevel.DEVICE, "use_system_theme", null, false, true);
|
||||
const themeExplicit = useSettingValueAt<string>(SettingLevel.DEVICE, "theme", null, false, true);
|
||||
const systemThemeActivated = useSettingValue<boolean>("use_system_theme");
|
||||
const themeChoice = useSettingValue("theme");
|
||||
const systemThemeExplicit = useSettingValueAt(SettingLevel.DEVICE, "use_system_theme", null, false, true);
|
||||
const themeExplicit = useSettingValueAt(SettingLevel.DEVICE, "theme", null, false, true);
|
||||
const systemThemeActivated = useSettingValue("use_system_theme");
|
||||
|
||||
// If the user has enabled system theme matching, use that.
|
||||
if (systemThemeExplicit) {
|
||||
|
||||
@@ -145,7 +145,7 @@ const tasks: UserOnboardingTask[] = [
|
||||
];
|
||||
|
||||
export function useUserOnboardingTasks(context: UserOnboardingContext): UserOnboardingTaskWithResolvedCompletion[] {
|
||||
const useCase = useSettingValue<UseCase | null>("FTUE.useCaseSelection") ?? UseCase.Skip;
|
||||
const useCase = useSettingValue("FTUE.useCaseSelection") ?? UseCase.Skip;
|
||||
|
||||
return useMemo<UserOnboardingTaskWithResolvedCompletion[]>(() => {
|
||||
return tasks
|
||||
|
||||
Reference in New Issue
Block a user