<commit_before># Settings Reference

This document serves as developer documentation for using "Granular Settings". Granular Settings allow users to specify 
different values for a setting at particular levels of interest. For example, a user may say that in a particular room 
they want URL previews off, but in all other rooms they want them enabled. The `SettingsStore` helps mask the complexity 
of dealing with the different levels and exposes easy to use getters and setters.


## Levels

Granular Settings rely on a series of known levels in order to use the correct value for the scenario. These levels, in 
order of prioirty, are:
* `device` - The current user's device
* `room-device` - The current user's device, but only when in a specific room
* `room-account` - The current user's account, but only when in a specific room
* `account` - The current user's account
* `room` - A specific room (setting for all members of the room)
* `config` - Values are defined by `config.json`
* `default` - The hardcoded default for the settings

Individual settings may control which levels are appropriate for them as part of the defaults. This is often to ensure 
that room administrators cannot force account-only settings upon participants.


## Settings

Settings are the different options a user may set or experience in the application. These are pre-defined in 
`src/settings/Settings.js` under the `SETTINGS` constant and have the following minimum requirements:
```
// The ID is used to reference the setting throughout the application. This must be unique.
"theSettingId": {
  // The levels this setting supports is required. In `src/settings/Settings.js` there are various pre-set arrays
  // for this option - they should be used where possible to avoid copy/pasting arrays across settings.
  supportedLevels: [...],

  // The default for this setting serves two purposes: It provides a value if the setting is not defined at other
  // levels, and it serves to demonstrate the expected type to other developers. The value isn't enforced, but it
  // should be respected throughout the code. The default may be any data type.
  default: false,

  // The display name has two notations: string and object. The object notation allows for different translatable
  // strings to be used for different levels, while the string notation represents the string for all levels.

  displayName: _td("Change something"), // effectively `displayName: { "default": _td("Change something") }`
  displayName: {
    "room": _td("Change something for participants of this room"),

    // Note: the default will be used if the level requested (such as `device`) does not have a string defined here.
    "default": _td("Change something"),
  }
}
```

Settings that support the config level can be set in the config file under the `settingDefaults` key (note that some settings, like the "theme" setting, are special cased in the config file):
```
{
  ...
  settingDefaults: {
    settingName: true
  },
  ...
}
```

### Getting values for a setting

After importing `SettingsStore`, simply make a call to `SettingsStore.getValue`. The `roomId` parameter should always 
be supplied where possible, even if the setting does not have a per-room level value. This is to ensure that the value 
returned is best represented in the room, particularly if the setting ever gets a per-room level in the future.

In settings pages it is often desired to have the value at a particular level instead of getting the calculated value. 
Call `SettingsStore.getValueAt` to get the value of a setting at a particular level, and optionally make it explicitly 
at that level. By default `getValueAt` will traverse the tree starting at the provided level; making it explicit means 
it will not go beyond the provided level. When using `getValueAt`, please be sure to use `SettingLevel` to represent the 
target level.
<commit_msg>Apply suggestions from code review<commit_after># Settings Reference

This document serves as developer documentation for using "Granular Settings". Granular Settings allow users to specify 
different values for a setting at particular levels of interest. For example, a user may say that in a particular room 
they want URL previews off, but in all other rooms they want them enabled. The `SettingsStore` helps mask the complexity 
of dealing with the different levels and exposes easy to use getters and setters.


## Levels

Granular Settings rely on a series of known levels in order to use the correct value for the scenario. These levels, in 
order of prioirty, are:
* `device` - The current user's device
* `room-device` - The current user's device, but only when in a specific room
* `room-account` - The current user's account, but only when in a specific room
* `account` - The current user's account
* `room` - A specific room (setting for all members of the room)
* `config` - Values are defined by `config.json`
* `default` - The hardcoded default for the settings

Individual settings may control which levels are appropriate for them as part of the defaults. This is often to ensure 
that room administrators cannot force account-only settings upon participants.


## Settings

Settings are the different options a user may set or experience in the application. These are pre-defined in 
`src/settings/Settings.js` under the `SETTINGS` constant and have the following minimum requirements:
```
// The ID is used to reference the setting throughout the application. This must be unique.
"theSettingId": {
  // The levels this setting supports is required. In `src/settings/Settings.js` there are various pre-set arrays
  // for this option - they should be used where possible to avoid copy/pasting arrays across settings.
  supportedLevels: [...],

  // The default for this setting serves two purposes: It provides a value if the setting is not defined at other
  // levels, and it serves to demonstrate the expected type to other developers. The value isn't enforced, but it
  // should be respected throughout the code. The default may be any data type.
  default: false,

  // The display name has two notations: string and object. The object notation allows for different translatable
  // strings to be used for different levels, while the string notation represents the string for all levels.

  displayName: _td("Change something"), // effectively `displayName: { "default": _td("Change something") }`
  displayName: {
    "room": _td("Change something for participants of this room"),

    // Note: the default will be used if the level requested (such as `device`) does not have a string defined here.
    "default": _td("Change something"),
  }
}
```

Settings that support the config level can be set in the config file under the `settingDefaults` key (note that some settings, like the "theme" setting, are special cased in the config file):
```json
{
  ...
  "settingDefaults": {
    "settingName": true
  },
  ...
}
```

### Getting values for a setting

After importing `SettingsStore`, simply make a call to `SettingsStore.getValue`. The `roomId` parameter should always 
be supplied where possible, even if the setting does not have a per-room level value. This is to ensure that the value 
returned is best represented in the room, particularly if the setting ever gets a per-room level in the future.

In settings pages it is often desired to have the value at a particular level instead of getting the calculated value. 
Call `SettingsStore.getValueAt` to get the value of a setting at a particular level, and optionally make it explicitly 
at that level. By default `getValueAt` will traverse the tree starting at the provided level; making it explicit means 
it will not go beyond the provided level. When using `getValueAt`, please be sure to use `SettingLevel` to represent the 
target level.

{'fraction_non_alphanumeric': 0.0627791246650504, 'fraction_numerical': 0.0, 'mean_word_length': 4.106188925081433, 'pattern_counts': {'":': 10, '<': 3, '<?xml version=': 0, '>': 3, 'https://': 0, 'lorem ipsum': 0, 'www.': 0, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 0, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '757478', 'n_tokens_mistral': 1914, 'n_tokens_neox': 1855, 'n_words': 1137}