js-gnome-apps
SKILL.md
GNOME JavaScript (GJS) Application Development
Technology Stack
| Component | Purpose |
|---|---|
| GJS | JavaScript runtime (SpiderMonkey) with GObject Introspection bindings |
| GTK 4 | UI toolkit |
| Libadwaita (Adw) 1.x | GNOME-specific widgets, adaptive layouts, styling |
| GLib / GIO | Core utilities, async I/O, settings, D-Bus, file operations |
| Meson | Build system |
| Flatpak | App packaging and distribution |
| Blueprint (optional) | Declarative UI markup that compiles to GTK XML |
Imports (ES Modules — required for new code)
// Built-in GJS modules
import Cairo from "cairo";
import Gettext from "gettext";
import System from "system";
// Platform libraries via gi:// URI
import GLib from "gi://GLib";
import GObject from "gi://GObject";
import Gio from "gi://Gio";
// Versioned imports (required when multiple API versions exist)
import Gtk from "gi://Gtk?version=4.0";
import Adw from "gi://Adw?version=1";
// Relative user modules (include .js extension)
import * as Utils from "./lib/utils.js";
Keep imports grouped: built-in → platform (gi://) → local, separated by blank lines. Use PascalCase for imported modules.
GObject Subclassing
Register every GObject subclass with GObject.registerClass(). Use constructor() (not _init(), which is legacy pre-GNOME 42).
const MyWidget = GObject.registerClass(
{
GTypeName: "MyWidget",
Template: "resource:///com/example/MyApp/my-widget.ui",
InternalChildren: ["title_label", "action_button"],
Properties: {
"example-prop": GObject.ParamSpec.string(
"example-prop",
"",
"",
GObject.ParamFlags.READWRITE,
null,
),
},
Signals: {
"item-selected": {
param_types: [GObject.TYPE_STRING],
},
},
},
class MyWidget extends Gtk.Box {
constructor(params = {}) {
super(params);
// Template children: this._title_label, this._action_button
}
get example_prop() {
return this._example_prop ?? null;
}
set example_prop(value) {
if (this.example_prop === value) return;
this._example_prop = value;
this.notify("example-prop");
}
},
);
Key rules:
- Property names:
kebab-casein GObject declarations,snake_casein JS accessors - Always call
this.notify('prop-name')in setters to emit change notifications GTypeNameis optional unless the type is referenced in UI XML<template class="...">InternalChildrenmapsidattrs in UI XML →this._childId;Children→this.childId
Application Entry Point
import GLib from "gi://GLib";
import GObject from "gi://GObject";
import Gio from "gi://Gio";
import Gtk from "gi://Gtk?version=4.0";
import Adw from "gi://Adw?version=1";
import { MyAppWindow } from "./window.js";
const MyApp = GObject.registerClass(
class MyApp extends Adw.Application {
constructor() {
super({
application_id: "com.example.MyApp",
flags: Gio.ApplicationFlags.DEFAULT_FLAGS,
});
const quitAction = new Gio.SimpleAction({ name: "quit" });
quitAction.connect("activate", () => this.quit());
this.add_action(quitAction);
this.set_accels_for_action("app.quit", ["<Primary>q"]);
}
vfunc_activate() {
let win = this.active_window;
if (!win) win = new MyAppWindow(this);
win.present();
}
},
);
const app = new MyApp();
app.run([System.programInvocationName, ...ARGV]);
Async with Gio._promisify
Wrap *_async/*_finish pairs once at module level for async/await usage:
Gio._promisify(
Gio.File.prototype,
"load_contents_async",
"load_contents_finish",
);
const file = Gio.File.new_for_path("/tmp/example.txt");
try {
const [contents] = await file.load_contents_async(null);
const text = new TextDecoder().decode(contents);
} catch (e) {
logError(e, "Failed to load file");
}
Code Style (GJS conventions)
- 4-space indentation, single quotes, semicolons
constby default,letwhen mutation needed, nevervar- File names:
lowerCamelCase.js; directories:lowercase - Arrow functions for inline callbacks;
.bind(this)for method references exportfor public API, nevervar
Reference Files
Consult these based on the task at hand:
- Project setup & packaging: references/project-setup.md — Meson build, Flatpak manifests, GResource, application ID, desktop files, GSettings schemas, directory layout
- UI design (GTK4 + Libadwaita): references/ui-patterns.md — Widget templates (UI XML), adaptive layouts (breakpoints, split views, view switcher), boxed lists, style classes, header bars, GNOME HIG patterns
- GIO & platform patterns: references/gio-patterns.md — File I/O, GSettings, actions & menus, D-Bus, subprocesses, list models, GVariant
Weekly Installs
6
Repository
padparadscho/skillsFirst Seen
Feb 7, 2026
Security Audits
Installed on
amp6
opencode6
kimi-cli6
codex6
github-copilot6
gemini-cli6