Skip to content

Commit 44e005b

Browse files
authored
feat(prefs)!: organize modules into preference sections (#41)
Add section metadata to module definitions and render preferences grouped by category. Add shortcut preference support for Clipboard History and remove its default keybinding to comply with GNOME review guidance. Move developer tooling out of the module tree, remove the shell adapter from the extension context, improve Quick Settings attachment reuse, and update tray icon deduplication, translations, tests, and credits. BREAKING CHANGE: ModuleDefinition metadata now requires a section field, and ExtensionContext no longer exposes the shell adapter. Clipboard History no longer ships with a default shortcut; users must assign one in preferences.
1 parent acad1be commit 44e005b

47 files changed

Lines changed: 1596 additions & 595 deletions

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

AGENTS.md

Lines changed: 37 additions & 17 deletions
Original file line numberDiff line numberDiff line change
@@ -52,35 +52,34 @@ Do not leave a task incomplete if either command reports errors or failures.
5252

5353
### Translation commands
5454

55-
- **Regenerate POT template:** `just pot` — builds then scans compiled JS (`dist/`) and rewrites the `.pot` file with all `_()` strings. Run this whenever translatable strings are added or removed.
56-
- **Merge new strings into .po files:** `just update-po` — runs `msgmerge` on every `po/*.po` file against the current `.pot`. Run after `just pot`.
55+
- **Regenerate POT template:** `just pot` — builds then scans compiled JS (`dist/`) and writes the `.pot` into `dist/` (a build artifact, **not** committed — avoids `POT-Creation-Date` churn). Run this whenever translatable strings are added or removed.
56+
- **Merge new strings into .po files:** `just update-po`depends on `pot`; regenerates the template into `dist/` then runs `msgmerge` on every `data/po/*.po` against it. The hand-translated `data/po/*.po` files are the committed source of truth.
5757
- **Compile .mo binaries:** `just compile-mo` — compiles each `po/*.po` into `dist/locale/<lang>/LC_MESSAGES/*.mo`. Called automatically by `just build`.
5858

5959
## Repository Structure
6060

6161
- `src/` — TypeScript source root
6262
- `extension.ts` — entry point; iterates the registry and instantiates modules via each definition's `factory`
63-
- `module.ts` — base `Module` class (accepts `ExtensionContext`)
64-
- `moduleDefinition.ts` — shared `ModuleOption` / `ModuleMetadata` / `ModuleDefinition` types
63+
- `module.ts` — base `Module` class plus the shared `ModuleOption` / `ModuleMetadata` / `ModuleDefinition` types
6564
- `registry.ts` — aggregator; imports each module's `definition` export and returns them in UI order (used by `extension.ts`)
66-
- `prefsMetadata.ts` — pure metadata mirror for the prefs UI; cannot import modules because prefs runs in `gnome-extensions-app` (no `resource:///org/gnome/shell/*` available)
67-
- `prefs.ts` — generic extension preferences UI driven by `prefsMetadata.ts`
65+
- `prefsMetadata.ts` — pure metadata mirror for the prefs UI; cannot import modules because prefs runs in `gnome-extensions-app` (no `resource:///org/gnome/shell/*` available). Also exports `getSections()` (the ordered list of prefs sections)
66+
- `prefs.ts` — generic extension preferences UI driven by `prefsMetadata.ts`; renders one `Adw.PreferencesGroup` per section
6867
- `core/` — Clean Architecture core
6968
- `context.ts``ExtensionContext` interface and implementation
7069
- `logger.ts` — Abstracted logging
7170
- `settings.ts``SettingsManager` abstraction for GSettings
72-
- `adapters/` — Infrastructure adapters (e.g., `ShellEnvironment`)
7371
- `modules/` — one **folder** per feature module, named after the module (e.g., `dock/dock.ts`); the main entry file shares the folder name
74-
- `shared/` — shared utilities used across modules
72+
- `dev/` — developer-only tooling (e.g., `devTool.ts`), gated behind the `AURORA_DEVTOOLS=1` env var. **Not** a feature module: it is not in the registry, prefs, or gschema, and is instantiated directly by `extension.ts`
73+
- `shared/` — shared utilities used across modules (e.g., `quickSettings.ts`)
7574
- `styles/` — SCSS stylesheets (compiled to light + dark CSS)
7675
- `types/` — TypeScript type declarations (`@girs`, GJS, etc.)
7776
- `data/` — resources files
7877
- `schemas/` — GSettings schema XML
7978
- `icons/` — SVG icons used in the project
8079
- `po/` — translation files
8180
- `tests/` — automated tests
82-
- `unit/`vitest unit tests (metadata, registry, schema)
83-
- `shell/` — GNOME Shell integration test scripts (run via `gnome-shell-test-tool`)
81+
- `unit/`Node test-runner unit tests (`node --test` via `tsx`), auto-discovered by the `tests/unit/*.test.ts` glob — just drop a new `*.test.ts` file in here, no `package.json` edit needed. For pure logic that does not import shell internals.
82+
- `shell/` — GNOME Shell integration test scripts (run via `gnome-shell-test-tool`) — exercise modules against a real headless GNOME Shell
8483
- `.github/workflows/ci.yml` — CI pipeline (lint + type-check → unit tests + build → integration tests)
8584
- `scripts/` — helper shell scripts (`create-toolbox.sh`, `run-gnome-shell.sh`, `run-vagrant-gnome-shell.sh`)
8685
- `esbuild.ts` — esbuild bundler configuration
@@ -91,9 +90,9 @@ Do not leave a task incomplete if either command reports errors or failures.
9190

9291
## Architecture
9392

94-
1. **Dependency Injection:** Modules **must not** access global variables (like `Main` or `Gio.Settings`) directly. Instead, they receive an `ExtensionContext` in their constructor.
95-
2. **Abstractions:** Use `this.context.settings` for configuration and `this.context.shell` for GNOME Shell environment interactions.
96-
3. **Layering:** Keep UI logic (Clutter/St) separated from pure domain logic. Complex algorithms should be extracted into pure TypeScript files (e.g., `src/modules/dock/monitorTopology.ts`).
93+
1. **Settings via context:** Modules receive an `ExtensionContext` in their constructor and read configuration through `this.context.settings` (the `SettingsManager` abstraction) rather than touching `Gio.Settings` directly.
94+
2. **`Main` is fair game:** Importing `Main` (`resource:///org/gnome/shell/ui/main.js`) directly is the idiomatic GNOME-extension way and is expected — there is no shell adapter. Confidence in shell interactions comes from the `tests/shell/` integration suite running a real headless GNOME Shell, not from mocking `Main`.
95+
3. **Layering & testability:** Keep UI logic (Clutter/St) separated from pure domain logic. Extract complex algorithms into pure TypeScript files with no shell imports (e.g., `src/modules/dock/monitorTopology.ts`, `src/modules/trayIcons/trayState.ts`) so they can be unit-tested with `node --test`. UI/shell glue is covered by integration tests instead.
9796
4. **Metadata-Driven UI:** The preferences window is generated dynamically from `src/prefsMetadata.ts` (a hand-maintained mirror of each module's metadata, kept in parity by `tests/unit/registry.test.ts`). If a module needs options, define them in the `options` array of its `ModuleDefinition` and mirror them into `prefsMetadata.ts`.
9897
5. **Self-Registering Modules:** Each module file exports a `definition: ModuleDefinition` co-located with its class. The factory that constructs the module lives on the definition itself — `src/registry.ts` is a pure aggregator and never references module classes directly.
9998

@@ -105,7 +104,7 @@ Do not leave a task incomplete if either command reports errors or failures.
105104
import { gettext as _ } from 'gettext';
106105

107106
import type { ExtensionContext } from '~/core/context.ts';
108-
import type { ModuleDefinition } from '~/moduleDefinition.ts';
107+
import type { ModuleDefinition } from '~/module.ts';
109108
import { Module } from '~/module.ts';
110109

111110
export class MyModule extends Module {
@@ -119,6 +118,7 @@ export class MyModule extends Module {
119118
export const definition: ModuleDefinition = {
120119
key: 'my-module',
121120
settingsKey: 'module-my-module',
121+
section: 'behavior', // must match an id from getSections() in prefsMetadata.ts
122122
title: _('My Module'),
123123
subtitle: _('Description'),
124124
options: [
@@ -136,12 +136,13 @@ import { definition as myModule } from '~/modules/myModule/myModule.ts';
136136
return [/* …, */ myModule];
137137
```
138138

139-
3. Mirror the metadata into `src/prefsMetadata.ts` (prefs cannot import modules — see the file header):
139+
3. Mirror the metadata into `src/prefsMetadata.ts` (prefs cannot import modules — see the file header). Include the same `section`:
140140

141141
```typescript
142142
{
143143
key: 'my-module',
144144
settingsKey: 'module-my-module',
145+
section: 'behavior',
145146
title: _('My Module'),
146147
subtitle: _('Description'),
147148
options: [
@@ -160,7 +161,26 @@ return [/* …, */ myModule];
160161
</key>
161162
```
162163

163-
`tests/unit/registry.test.ts` enforces that step 2, step 3, and step 4 stay in parity — a half-finished addition will fail CI.
164+
`tests/unit/registry.test.ts` enforces that step 2, step 3, and step 4 stay in parity — including that every module's `section` is a known section id and matches between the registry and `prefsMetadata.ts`. A half-finished addition will fail CI.
165+
166+
### Prefs sections
167+
168+
The prefs window groups modules by `section`. The ordered section list lives in `getSections()` in `src/prefsMetadata.ts`:
169+
170+
```typescript
171+
export function getSections(): ModuleSection[] {
172+
return [
173+
{ id: 'dock-panel', title: _('Dock & Panel') },
174+
//
175+
];
176+
}
177+
```
178+
179+
To add a new section, append a `{ id, title }` entry here (the array order is the on-screen group order), then reference its `id` from a module's `section`. A module whose `section` matches no known id falls into a defensive "Other" group at the bottom.
180+
181+
### Clipboard shortcuts
182+
183+
Per the GNOME review guidelines, clipboard-related keyboard shortcuts must not ship with a default. The Clipboard History `clipboard-history-shortcut` key defaults to `[]`; users assign it via the `type: 'shortcut'` row in prefs. Keep any future clipboard shortcuts unset by default.
164184

165185
## Coding Standards
166186

@@ -169,7 +189,7 @@ return [/* …, */ myModule];
169189
- Private members: `_prefixed`
170190
- Constants: `UPPER_CASE`
171191
- Keep `enable()` and `disable()` symmetric.
172-
- **Strictly follow Dependency Injection.** No direct imports of `gi://Shell`, `Main`, etc., inside module domain logic.
192+
- Read settings through `this.context.settings`. Importing `Main`/`Shell`/`St` directly is fine — keep heavy algorithms in shell-free pure files so they stay unit-testable.
173193

174194
## Logging Style
175195

CONTRIBUTING.md

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -133,7 +133,9 @@ Maintenance branches are created automatically when the first tag for a new majo
133133

134134
### New features
135135

136-
New features land on `main` and are released alongside a new major GNOME Shell version. **Do not add new features to maintenance branches** — they are strictly for bug fixes.
136+
Each major Aurora Shell release targets a single GNOME Shell version. New features land on `main` and are released alongside a new major GNOME Shell version.
137+
138+
Branches targeting already-released GNOME Shell versions are in maintenance mode. **Do not add new features to maintenance branches** — they are strictly for bug fixes and compatibility updates.
137139

138140
### Bug fixes
139141

CREDITS.md

Lines changed: 28 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
# Credits & Acknowledgements
2+
3+
Aurora Shell stands on the work of the wider GNOME community. This file records the projects and people whose work made parts of this extension possible.
4+
5+
## Bluetooth-Battery-Meter
6+
7+
The animated Bluetooth icons used by the **Bluetooth Menu** module come from
8+
[**maniacx/Bluetooth-Battery-Meter**](https://github.com/maniacx/Bluetooth-Battery-Meter).
9+
Huge thanks to [@maniacx](https://github.com/maniacx) for the great work.
10+
11+
Icons (`data/icons/hicolor/scalable/actions/`):
12+
13+
- `bbm-bluetooth-symbolic.svg`
14+
- `bbm-bluetooth-connected-symbolic.svg`
15+
- `bbm-bluetooth-connecting-animated-symbolic.svg`
16+
- `bbm-bluetooth-connecting-1-symbolic.svg``bbm-bluetooth-connecting-4-symbolic.svg`
17+
- `bbm-bluetooth-disconnecting-animated-symbolic.svg`
18+
- `bbm-bluetooth-disconnecting-1-symbolic.svg``bbm-bluetooth-disconnecting-4-symbolic.svg`
19+
20+
These icons remain the work of their original author and are used under the terms of the
21+
Bluetooth-Battery-Meter project's license.
22+
23+
## XWayland Indicator
24+
25+
The **XWayland Indicator** module is inspired by
26+
[**swsnr/gnome-shell-extension-xwayland-indicator**](https://codeberg.org/swsnr/gnome-shell-extension-xwayland-indicator/).
27+
Thanks to [@swsnr](https://codeberg.org/swsnr) for the original idea of surfacing which
28+
windows run under XWayland.

README.md

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,10 @@
66

77
A modular GNOME Shell extension that adds quality-of-life features missing in vanilla GNOME.
88

9+
> **Project goal:** Aurora Shell is a proving ground. Over time, the aim is for some of its
10+
> features to mature and make their way upstream into GNOME Shell itself. Modules here are
11+
> meant to be useful on their own today, and good candidates for upstream tomorrow.
12+
913
## Modules
1014

1115
Aurora is split into independent modules, so you can enable only what you want.
@@ -63,3 +67,12 @@ just toolbox-run
6367
## Contributing
6468

6569
We welcome contributions! Please see [CONTRIBUTING.md](CONTRIBUTING.md) for information on project architecture, code style, and step-by-step instructions on how to add a new module.
70+
71+
## Credits & Acknowledgements
72+
73+
Aurora Shell builds on the work of the wider GNOME community. Special thanks to:
74+
75+
- [**maniacx/Bluetooth-Battery-Meter**](https://github.com/maniacx/Bluetooth-Battery-Meter) the animated Bluetooth icons used by the Bluetooth Menu module come from this project.
76+
- [**swsnr/gnome-shell-extension-xwayland-indicator**](https://codeberg.org/swsnr/gnome-shell-extension-xwayland-indicator/) the inspiration behind the XWayland Indicator module.
77+
78+
See [CREDITS.md](CREDITS.md) for the full list of attributed work.

data/po/aurora-shell@luminusos.github.io.pot

Lines changed: 0 additions & 71 deletions
This file was deleted.

data/po/en.po

Lines changed: 0 additions & 69 deletions
This file was deleted.

0 commit comments

Comments
 (0)