20 May 2026
Planet GNOME
Christian Hergert: Asynchronous Varlink with varlink-glib
I've been putting together varlink-glib, which is a library for writing Varlink clients and services in C. The basic idea is to keep the transport policy out of the library. You get a connected GIOStream however you want, whether that is GLib networking, socket activation, or something more specialized, and then wrap it in a VarlinkClientProtocol or VarlinkServerProtocol.
The API is built around DexFuture, which makes the async parts feel a lot nicer in C than the usual callback layering. Client calls return a future, server replies return a future, and internally the protocol can use fibers for the work that wants to look sequential while still integrating with the GLib main context. This is very much the style of API I want for system services: explicit enough that you can debug it, but not so painfully manual that every call site becomes a state machine.
future = example_calc_add_call_invoke (proxy,
call,
VARLINK_METHOD_CALL_DEFAULT,
add_reply_cb,
NULL,
NULL);
There is also a varlink-codegen tool which takes a .varlink interface and generates typed C wrappers for it. That gives you proxy objects, server skeletons, call objects, reply objects, and error constants instead of making every application hand-roll JSON. You can still drop down to VarlinkMessage, VarlinkMessageBuilder, and VarlinkMessageReader for forwarding or weird infrastructure cases, but most code should get to stay typed.
File descriptor passing works when the transport is a Unix socket connection. This follows the same general model as systemd's Varlink support: the JSON payload contains an integer index, while the actual descriptors are sent out-of-band with SCM_RIGHTS and attached to the containing message as a GUnixFDList. Generated code can continue to treat the field as an integer, while the actual descriptor list stays attached to the underlying VarlinkMessage.
fd_list = g_unix_fd_list_new (); fd_index = g_unix_fd_list_append (fd_list, fd, &error); varlink_message_set_unix_fd_list (parameters, fd_list);
Protocol upgrades are supported too. A method call can ask to upgrade the connection, and once the final successful reply is sent, Varlink stops being valid on that connection. The VarlinkProtocol is still a GIOStream, so the next protocol can continue reading and writing through the same object. That keeps the handoff explicit without requiring a separate transport abstraction.
I also wired in optional Sysprof capture support. When enabled, client and server RPCs can show up as Sysprof marks with useful bits like method name, result, reply count, one-way, multi-reply, upgrade, Varlink error, and GError details. That matters because once you have concurrent calls, generated dispatch through VarlinkServerRegistry, and services doing real work, "it got slow somewhere" is not enough information.
There is still more polish to do, but the shape is there: typed generated APIs for normal users, low-level message APIs for infrastructure, DexFuture for async flow, Unix FD passing for the system service cases, protocol upgrades for handoff cases, and profiler hooks so it can be debugged when the happy path stops being happy.
A small personal note: as I wrote in my recent update from France, I am no longer employed by Red Hat. Work like this is currently self-funded, out of pocket, while my family and I settle into a new chapter. If you find it useful, a note of encouragement or a contribution means a lot right now. It helps make it possible to keep improving the free software infrastructure many of us rely on.
20 May 2026 8:55am GMT
Richard Hughes: LVFS Sponsorship Announcement: HP
Some more great news: I'm pleased to announce that HP has also agreed to be premier sponsor for the Linux Vendor Firmware Service (LVFS) as part of our sustainability effort.
With the industry support from HP (and our existing sponsors of Lenovo, Dell, Framework, OSFF and of course Linux Foundation and Red Hat) we can turbo-charge the growth of the LVFS even more. Thanks!
20 May 2026 8:09am GMT
18 May 2026
Planet GNOME
Martin Pitt: Leaving Red Hat
In December 2016 I left Canonical with one sad and one happy eye, with lots of good memories. Now it's time to revisit some more! Starting at Red Hat back then was quite a cultural shock, of course. I got used to the new headwear fashion quickly: But never really to the rest of the formal dress attire: The drinking habits I was familiar with, and I quickly learned enough Czech to get "dvě piva prosím":
18 May 2026 12:00am GMT
16 May 2026
Planet GNOME
Andy Wingo: soot, solar, sedimentation, sin, & 'centers
Good evening, friends. Tonight I have a few loosely-knit stories.
soot
A couple years ago, my house was heated by a condensing gas boiler. It was awful from both an environmental and a geopolitical perspective: environmental, as I would emit somewhere around 2.5 tons of CO2 equivalent per year to heat my home, which compares poorly to the target total CO2e emissions of 2 tons per year per person; and geopolitical, because although France gets 40% of its gas from Norway, with whom we have no beef, all the rest is a problem in some way. (Algeria, 10%, is the least of my worries; the 20% for Russia and the US respectively are the most, followed by 10% for the Gulf states.)
Still, natural gas is better than fuel oil, which we had at my former rental house. It is a lamentably visceral experience to call up the fuel provider and say, yes, s'il vous plaît, can you drive a diesel-powered tanker truck out to my house, unroll the hose, and pour out 1500 liters of toxic fuel oil into a tank under my garden. Yes, I will just burn it all. Sure, see you again next year.
Some friends of mine recently had their fuel boiler die, which is itself an experience: one of them came over to visit, completely covered in soot, saying that the chimneysweep (whom he also has to call every year) said that his boiler is on its way out, that the chimney is completely clogged, and now because of the cleaning his basement is also covered in soot; awful. What to replace it with? Apparently despite the prohibition on new fuel-oil boiler installs, it might be possible to just install a new one; or they could hook up to natural gas from the street; or they could install a heat pump. Which to do?
To all these questions there is a moral answer, which we can phrase in terms in CO2 emissions and localized PM2.5 pollution, and it is always and everywhere to stop burning things. But fortunately we don't need to rely only on moralism: electrification is just better, in essentially all ways. Owning and operating an electric car is a better experience than a petrol car. Induction stoves are better than gas; I know, I did not believe this for the longest time, but I was wrong. The experience of using a heat pump is pretty much equivalent to gas, so it's a harder sell, but it is a relief to no longer have a pressurized methane tube connected to my house.
In the end, I think my neighbors are going to go for the heat pump, despite the 20k€ price tag, labor included. (Oddly, I think the deciding factor was that my neighbor confessed to having had a long chat with an AI chatbot, after which she felt she had a good understanding of the proposed solution and its tradeoffs; make of that what you will!)
solar
In late November I got some brave lads to install nineteen solar panels on my roof. Each of these magic rectangles can make up to 500W of power in optimal conditions, but my house faces south, with the roof inclined east and west, so it's unlikely that I will ever hit the full 9.5 kW of potential power.
December was... very dark. The panels produced a total of 145 kWh over the month, but I used 1250 kWh of electricity, essentially all to run the heat pump. I live in a basin that is mostly covered by low clouds from November to February, and slanty photons couldn't make much headway through the fog. The house is well-insulated (20-25 cm of wood-fiber exterior insulation on sides, 40 under the roof, though it is an old house with a few less-insulated bits), so it's not that I am leaking lots of heat, and I have a combination of low-temperature floor heating and low-temperature radiators, so it's not that I'm running the heat pump inefficiently to generate a too-high output temperature; it's just, you know, cold in winter. A typical day would be between 1 and 5 degrees C. Cold; cold and dark.
Things got a little better in January: 285 kWh produced, though the heating needs are higher than in December, with 1450 kWh total consumed. In February we grew to 419 kWh produced, for 850 kWh consumed. In March we equalized, with about 850 kWh produced and consumed, but although the bulk of my consumption in this month is for heating, the "need" to heat overnight meant that I consume from the grid overnight, but feed in to the grid during the day. I have a small battery (7 kWh), but it's not enough to store the "excess" electricity generated in a day; I should probably arrange to have the system heat only during the day in these months, to avoid taking from the grid.
With practically no heating needs now, as you can imagine, I am just feeding a lot of excess to the grid. We're halfway through May, just coming through a cold snap (the peasant lore is that we just passed the saints de glace, the date you need to wait for to plant crops that aren't frost-hardy), but still we've produced more than twice as much as we've consumed (550 kWh vs 220 kWh), and essentially all the excess goes to the grid. The 7 kWh battery is quite enough to cover night-time electricity needs.
I didn't know before, but often a solar panel installation doesn't work when the grid is down. This is because the inverters that convert the DC from the panels to AC for the house need to match phase with the grid, and if the grid's phase signal is down, they stop. It's also for safety, so that line workers can repair downed lines without worrying that every house is a live wire. I spent a little extra to install a cutout that allows the house to run in "island mode" if the grid is down. We almost never have that situation here, though, but it seemed prudent that if we were going all-in on electricity, that perhaps we should take precautions.
When you buy a solar installation, you can either have little DC/AC inverters attached to the back of each panel (microinverters), or feed DC from all panels wired in series (they call them strings; there may be 2 or 3 of them in a home setup) to a central inverter. I have the latter. The panels happen to be assembled locally by MaviWatt, though surely the cells themselves are from China. My panels are installed on top of the ceramic roof tiles with little clips and an aluminum structure. (It used to be that sometimes panels would replace tiles and become the roof. That's not done so much any more here.) Installation is, like, 60% of the price of solar. Often you need scaffolding, though my installers just used ladders; perhaps living in the mountains where I am, there are more people used to doing ropes and rock-climbing and such. I don't think they took as much care of themselves as they should, though.
My inverter is made by Huawei (SUN2000), as is my battery and the cutout ("backup") box. Some batteries have their own microinverter, allowing them to consume and produce AC, but this one is DC, hence the need to have the same brand as the inverter. It sends all my electricity usage data to China or something, so that it can send it to the app on my phone. It's not ideal from an geopolitical perspective but it is good kit.
sedimentation
Although we haven't hit the height of summer yet, I would like to offer a few observations that have precipitated out of solution.
Firstly, at least in my house, the baseline load without heating is pretty low: 200 or 300 watts or so. (I didn't know this before looking at Huawei's app.) We have a recently renovated, not tiny, but otherwise normal sort of house with, you know, the usual lot of modern conveniences, idle chargers plugged in here and there, and also my work computers and such, and it all runs on less than a handful of the old 60W bulbs. That's interesting.
As far as actual load, there are only a few things that count: heating, when it's cold; it can easily average 2 kW on a cold day. Plug in the electric car (I don't have a wall box yet, just with the mains plug), that's another kilowatt. I hardly drive, though, so it's not a huge load. Using hot water is perhaps the most surprising thing: it can cause a spike up to 6 kW, over a short time, despite the heat coming from the heat pump; probably there is some tuning to do there. The oven and stove are little tiny blips. There's the kettle, but it's also a little blip. Nothing else matters: not the dishwasher, not the washing machine, nothing. You can leave the lights on all day and it just doesn't matter.
Call me naïve, but I had hoped that solar would help my electricity usage in winter. This is simply not the case. Though the heat pump is efficient, there does not appear to be a magical energy solution for December, which is the bulk of my energy usage. My electricity bill is fixed-rate: 20 cents per kWh used. Using 4000 kWh or so from the grid over winter costs me 800€; annoying. I don't have a natural before-and-after experiment as we added on to the house as we were renovating, but for context, in my previous poorly-insulated rental house that was half the size of this one, we'd pay 2000€ or so per year for heating oil. Perhaps I can lower the 800€ via variable-rate metering, to let the battery do some arbitrage, but there are some fundamental constraints that can't be finagled away.
When I got my solar panels, I was resigned to never getting peak power, as they are on two different sections of the roof. It turns out that doesn't matter: firstly, because 9.5 kW is a lot of power, as you can appreciate from the numbers above. I could never do anything with 9 kW. But secondly, because power isn't equally valuable at different times of the day: by having east and west roof pitches, I can start producing earlier and continue producing later than if I had, say, a flat roof with panels tilted to the south. And the morning and the evening are the peak hours both for my house and for the grid, so that lets me consume more of my local production both when I need it and when the grid is under higher stress.
I was interested to hear that Alec Watson of Technology Connections had reservations about residential rooftop solar. I found a video in which he explains his perspective, which has a delightfully socialist character. His beef is partly due to the net metering scheme in some parts of the US, in which each kWh fed to the grid makes your meter run backwards; Watson finds it unfair, because it lets those wealthy households who have the capital to install solar to opt out of paying for the grid, which is a social good. In some cases, these households actually capture a part of what consumers pay for the grid, unlike industrial producers who are paid wholesale rates that don't include transmission. Also, he finds it less efficient overall to install solar panels on houses rather than in bigger solar parks; each euro that society allocates to solar would go farther if we pooled them together.
Both points are interesting, but I would offer a couple responses. Firstly, at least in Europe, net metering is not really a thing; we have smart meters and I hear from friends in Portugal that there can even be a charge for grid injection at some times, if the grid is overloaded. France's case is a bit weirder; I wouldn't have gotten as large a system as I did, but there was a government program to offer a fixed buyback rate of 7 cents per kWh, stable for 20 years, if you installed more than 9 kW of panels. But given the lack of solar in December, I still pay the grid when I need energy the most.
Putting solar panels on roofs is indeed less efficient than putting them on a field. But, we are not in a situation of scarce solar panels: China could make another 350 GW of panels this year if there were demand. An incentive like the 7-cent buyback rate encourages capital allocation to solar, effectively calling these panels into existence. The bank loans me 20k€ at 4%, and the elimination of 3000 kWh that I would have bought from the grid in a year plus the 9000 kWh that I sell to the grid covers the cost entirely, and I get a life insurance policy on the remaining principal. It's not a great investment financially but it doesn't cost me anything either.
sin
As a person with a conscience, I have always experienced questions of energy as questions of sin; to leave a light on is not simply inefficient but a moral failing. Each kilometer a car travels on fossil fuel carries with it a quantum of guilt and must be justified in some way, otherwise a moral stain attaches.
Solar panels and electrification changes all this. 8 or 9 months out of the year, I live in a world of abundance: the electrical generation capacity that I have called into existence is free, clean, and much, much more than I need. Owning and operating a car still has externalities, but the emissions and cost aspects are entirely gone. It's a funny feeling, and disorienting.
I grew up in the south of the US, where everyone has air conditioning. I came to see it as sinful, too; burning things and making emissions just so you could be a bit more comfortable. I haven't lived in air conditioning since then, but it does get hot in summer, and I would be more comfortable if I could pump heat out of my house. Now I can. I have excess power available right when air conditioning (or, in my case, floor cooling) is needed. On a societal level, solar plus air conditioning is going to be a key part keeping our cities liveable while we ride out higher temperatures.
'centers
It is with a sense of dissonance, then, that I have been experiencing Datacenter Discourse™: there is a lingering language of sin proceeding from an environmentalism born in penury, in a world in which every kilowatt-hour is precious and scarce. If China has unallocated capacity for another 350 GW of panels this year, why stress about a few GW of datacenters?
Of course, there are many aspects to these AI datacenters, but today I am just thinking about energy. Given that each GW of datacenter places extra demand on a grid, equivalent to 3 million times my home's baseline load, or maybe 300 thousand of its winter load, if society wants this kind of datacenter to be a thing, it needs to add that amount of clean energy to the grid, with adequate battery storage to even out supply. We should, as a society, require this via legislation, because the market seems only too happy to use natural gas or even coal if it is marginally cheaper. At least if the datacenter boom busts, we'd be left with more clean energy production.
Conversely... and I don't think I'm going too far here, but causing new fossil generation to come online in 2026, or even prolonging the life of existing generation, should result in the state confiscating all property of those responsible. (I have moderated my previous position, which was hanging.) Such people are not fit to live in society, so society should not allow them to own things.
Anyway. I think that those of us that wish "AI" were not a thing are losing the battle, and that we should prepare to fall back to more defensible positions; otherwise we risk a rout. A requirement to bring additional clean capacity online in sufficient amounts should be a baseline ask when it comes to datacenters. We have the productive capacity in the form of solar panels, at an affordable price, more than enough space in terms of the existing cropland that is inefficiently turned into ethanol to burn, batteries are a thing, and we just lack the political will to turn what could be into what is.
And as for AI datacenters themselves: there are enough aspects to argue about as it is. We do ourselves a disservice by weighing down the Discourse with outdated ideas of what is and isn't possible.
16 May 2026 7:29pm GMT
15 May 2026
Planet GNOME
This Week in GNOME: #249 Quality Over Quantity
Update on what happened across the GNOME project in the week from May 8 to May 15.
GNOME Circle Apps and Libraries
Graphs ↗
Plot and manipulate data
Sjoerd Stendahl says
This week we released Graphs 2.0.
It's been about two years since the last major feature-update, and this is by far our biggest update yet. On a technical level, the code base has known a major overhaul. Importing logic is written in a more modular way, making it possible to add parsers for new data types, and we rewrote a large part of the code-base from Python to Vala, which now stands for the majority of the code.
For the people who follow TWIG, some of this might sound familiar from the announcement of the beta, but we finally added support for some major long-requested changes. Most significantly, we finally have proper symbolic equation-support. Meaning equations now span over an infinite range, and can be manipulated analytically (e.g. doing a derivative of 6x² will change the equation to 12x, and the line will be re-rendered accordingly). Item and figure settings, such as when changing the scaling or limits, no longer block the view of the main canvas. The style editor editor has been redesigned with a live preview of the changes, we revamped the import dialog, and imported data now supports error bars. Equations with infinite values in them such as y=tan(x) now also render properly with values being drawn all the way to infinity and without having a line going from plus to minus infinity. We've also added support for spreadsheet and SQLite database files, drag-and-drop importing, improved curve fitting with residuals and better confidence bands, and now have proper mobile support. Since the beta-release we managed to squeeze in some improvements in the code-base, and labels are now concatinated in a smart way based on the screen size, making Graphs more usuable on mobile interfaces.
This release took a long time to get right, but we're happy to get the new features to the public. Graphs is handcrafted by human hands, which takes more time than LLM-based slop. But the longer manual process does allow us to think through changes, and make intentional decisions with human care. I am very proud to say we are able to deliver something intentional where we can deliver the polish that both Graphs, as well as the users deserve. As always, thanks to anyone involved which includes everyone who has been providing feedback, reported issues, contributed with code, or helped in any other possible way. And of course especially to Christoph Matthias Kohnen who has been maintaining Graphs with me and is responsible for a large part of the architectural changes that made this release possible.
See a more complete list of changes here: https://blogs.gnome.org/sstendahl/2026/05/15/graphs-2-0-is-out/ And get the latest release on Flathub!
Third Party Projects
Anil reports
Codd is now available on Flathub!
Codd is a lightweight PostgreSQL client for GNOME, built with Rust, GTK4, libadwaita, Relm4, GtkSourceView, and sqlx. It focuses on a clean, native, and lightweight interface for working with PostgreSQL databases.
The initial release includes saved connections, SQL execution with syntax highlighting, result tables, query history, table browsing with pagination, filters and editable table cells.
More features are planned, and feedback from real-world PostgreSQL workflows would be very welcome.
Flathub: https://flathub.org/apps/io.github.anil_e.Codd Source: https://github.com/anil-e/codd
Haydn Trowell says
The latest version of Typesetter, the minimalist Typst editor, brings a bunch of improvements for package and template usage, most notably:
- a GUI package manager for installing and removing custom Typst packages and templates;
- a template selection popover in the header bar for creating new documents from built-in and user-installed templates;
- and an initial set of built-in templates.
Flathub: https://flathub.org/apps/net.trowell.typesetter Source: https://codeberg.org/haydn/typesetter/
Alain says
Planify 4.19.2 is out! 🎉
This release brings several new features and fixes across the board.
On the backup side, Planify now supports automatic daily backups - backups trigger at midnight and can be copied to additional folders of your choice, including cloud-mounted directories.
CalDAV keeps getting better: sections are now fully supported via VTODO List prefix, syncing bidirectionally with Nextcloud Tasks, Thunderbird, and other clients. Horde server compatibility is also improved. Past dates can now be selected in the date picker, with dimmed styling and a handy Today pill button to jump back to the current month.
On the UI side, Planify now follows your GNOME system accent color, the Board view inbox section auto-hides when empty, and the multi-select label picker now correctly tracks only the changes you explicitly make.
Several bug fixes land too: calendar events now update correctly when kept open past midnight, task counts in Board view are accurate after drag and drop, and moving tasks between different sources (e.g. CalDAV → Local) now works correctly.
Get it on Flathub! 🚀
New to Planify? It's a beautiful, open source task manager for Linux with Todoist and Nextcloud sync, built with GTK4 and libadwaita. Never worry about forgetting things again - give it a try!
Christian reports
🎉 Gitte 0.3.0 released!
Gitte 0.3.0 has been released, bringing full merge support, accessibility improvements, a new compact UI mode, and official macOS support.
The new merge workflow allows initiating, resolving, and completing merges directly from within the application. This release also adds a new compact UI mode, multi-selection support in the changed files list, and a release notes dialog with update notifications.
The diff viewer received major improvements as well: diffs in the log viewer can now be selected and copied and large diffs are handled more gracefully.
On the platform side, Gitte now supports macOS thanks to work by René de Hesselle. The app also received new GNOME-style icons by Jakub Steiner, expanded test coverage, CI integration, translation updates, and many internal refactorings and bug fixes.
Get it on Flathub, for macOS or check the source code
That's all for this week!
See you next week, and be sure to stop by #thisweek:gnome.org with updates on your own projects!
15 May 2026 8:27pm GMT
Sjoerd Stendahl: Graphs 2.0 is out!
After two years of development, Graphs 2.0 is finally out!
This will be a shorter blog, as the changelist of the new features have been discussed in the previous post in more detail, you can check this out here in more detail if you're interested: https://blogs.gnome.org/sstendahl/2026/04/14/announcing-the-upcoming-graphs-2-0/
For a quick overview, a quick reprise of the most interesting features can be found here in bullet-point format:
- New Data Types with proper equations: In this new release, we finally have proper support for equations, where equations are manipulated analytically (e.g. a derivative on y = 12x² will result in y = 24x, and be rendered accordingly), limits are rendered infinitely, and equations can be changed after importing them. To accomodate this change, we now have three different data types. Equations, Imported Data, and Generated Data. Imported Data is regular data that you import from file. Generated Data behaves the same as Imported Data, but you generate the dataset using an equation. For generate data you can also change the equation after the fact, and rerender, or change limits or amount of generated datapoints.
- New Style Editor: We revamped the style editor. One major change is that you can now easily import new styles based on matplotlib-style themes, and you can also export your style and share it with others. If you have a nice style you want to share with us, open an issue on the GitLab page and let us know. We're looking to expand the default choice of styles :). Furthermore, when editing a style, you finally see a preview of how this affects the canvas. This way you don't need to guess, or go back and forth when finetuning a style.
- UX-changes: Whilst the general look-and-feel of Graphs is still mostly the same, we did make some UX-changes with how we handle settings. Mainly, instead of showing a modal popup dialog, settings that affect the canvas itself (i.e. item and figure settings) are now shown in the sidebar instead. The reason for this, is that the popup dialog hid the figure that you're editing, making it difficult to see how your changes actually affect your canvas.
- Improved data import. We revamped the data import completely. First of all, we have made the codebase here much more modular, making it easier to write new parsers for other filetypes. We now added support for SQLite Database Files, Microsoft Excel Sheets and .ods files from LibreOffice Calc. It's also now possible to import multiple files at once, and finetuning the settings for each file individually. Another nice feature here is that you can now import multiple datasets from the same file without having to reimport them. Finally, we added proper-support also for single-column imports where x-data can be generated using your own equation
- Error bar support: Graphs now has proper support for error bars. The error bar style can be set globally in the new style editor, or individually for each item.
- Reworked Curve Fitting: The curve fitting logic has almost been completely rewritten. Whilst it mostly still works the same, the confidence band that is shown is now calculated properly using the Delta-method, instead of using a naive way using the limits of the standard deviations. We also added support to show the residuals to verify your fits, and added more useful error messages when things go wrong. The results in the curve fitting dialog now also show the root mean squared error as a second goodness-of-fit figure. The parameter values themselves in the curve fitting dialog are no longer rounded (e.g. 421302 used to be rounded to 421000) and finally custom equations in the curve fitting dialog now have an apply button, greatly improving the smoothness when entering new equations
- Proper Mobile Support: With this release, we now officially feel confident in stating proper mobile support. The entire UI is tested on real mobile phones using PostMarketOS, and everything works properly. Labels are now also ellipsized earlier on narrow displays, so that the UI remains useable.
- Reworked Figure Exports: Figure exports are reworked. Instead of simply taking a snapshot of the current canvas, you can set the actual size in pixels when exporting a figure. This is vital when trying to create reproducable figures for e.g. publications. Of course, you can also easily still use the same canvas that you see in the application.
- Quality of life changes: We haven't even gone through each individual change we made in the blog, but here's a quick fire-round of more quality-of-life changes:
- It is now possible to have multiple instances of Graphs open at the same time
- The style editor now also has the option to draw tick labels (so the numeric values) on all axes containing ticks, this is not supported by default in Matplotlib, so we had to add our own parameter here
- Graphs now inhibits the session when unsaved data is still open, so you get a warning if you close your computer with unsaved data.
- Added support for base-2 logarithmic scaling
- Graphical fixes for the drag-drop animations, which used to look somewhat glitchy
- Panning and zooming are now done consistently on all axes when using multiple axes
- Data can now be imported by drag-and-drop into Graphs
- The subtitle now also shows the full file path for Flatpaks
- Limits can now easily be clicking on the numbers near the axes
- The custom transformation has gained the following extra variables: x_mean, y_mean, x_median, y_median, x_std, y_std and counts
- Warnings are now displayed when trying to open a project from a beta version
- The many code refactors and reimplementations from Python to Vala makes the application more robust, and significantly more performance. Especially when working with larger datasets.
This release took a long time to get right, but we're happy to get the new features to the public. Graphs is handcrafted by human hands, which takes more time than LLM-based slop. But the longer manual process does allow us to think through changes, and make intentional decisions with human care. I am very proud to say we are able to deliver something intentional where we can deliver the polish that both Graphs, as well as the users deserve. As always, thanks to anyone involved which includes everyone who has been providing feedback, reported issues, contributed with code, or helped in any other possible way. And of course especially to Christoph who has been maintaining Graphs with me and is responsible for a large part of the architectural changes that made this release possible.
Go get the new release from Flathub here!
p.s. On a more personal note with a shameless plug, I will be speaking at GUADEC 2026 about my journey into app development, and how to get into this world as an outsider without a CS degree. Be sure to check that out if you are interested in starting with applications, and want to know how it is to join a project in the GNOME ecosystem, it's a lot less scary than it may sounds
I'll be joining on-site, so say hi to me there if you have any questions or are up for a chat :). Otherwise the whole event will be livestreamed as well, and you can always reach me at sstendahl@gnome.org.
15 May 2026 7:00pm GMT
Allan Day: GNOME Foundation Update, 2026-05-15
Welcome to another GNOME Foundation update post! Today's installment covers highlights from what's happened over the past two weeks.
LAS 2026
Linux Apps Summit 2026 starts tomorrow! The organizing team, which includes members from both GNOME and KDE, has been hard at work and is on the ground in Berlin making final preparations. The schedule looks great, and it promises to be a well-attended event.
The talks are being streamed this year, so make sure to watch our social media for details, and tune in live to hear the talks.
GUADEC 2026
Preparations are continuing for July's GUADEC. The call for Birds of a Feather sessions is currently open. If you want to hold an informal discussion or working session, please fill out the form before 5th June.
Applications are still open for travel funding for GUADEC. The deadline for submissions is 24th May - that's just over one week.
Board meeting
This week the Board of Directors had its regular meeting for May. A summary:
- The Board authorized the closure of a bank account which we are no longer using.
- I gave an update on operations over the past month, and got feedback from the Board
- Felipe Borges from the Internship Committee joined, to give a report. The Board discussed how we can best support the committee.
- Deepa gave a finance report, which included numbers from January and February. The main news here was that our finances are running close to what was projected for this year's budget.
- The Board discussed the draft of the report from the audit we recently underwent, as well as the draft of our latest annual tax filing. This is a routine part of the Board's work, as it is required to perform a review before these documents are finalized.
Office transitions
Our long-running effort to enhance our internal accounting processes has continued over the past two weeks. A notable development has been the retirement of several finance platforms, which have been effectively replaced by the new payments platform that we adopted in January. This platform reduction will reduce operational complexity, as well as workloads. It is still ongoing - we have an additional two more platforms that are currently in the process of being retired.
Another highlight has been the launch of a search for a new member to join our finance and operations team. This is a part-time, contract-based role, which has been shaped in close consultation with Dawn Matlak, who is supporting our finance and accounting operations on a temporary basis, and has already been factored into our budget projections.
We are looking for someone at director level who brings substantial nonprofit finance experience - including audit preparation and compliance experience - which reflects how much the Foundation's operational and regulatory requirements have grown, particularly in the run up to and following our audit last March, and will provide in-house expertise which will reduce our reliance on external consultants. You can read the full posting here.
Thanks for reading, and see you in two week's time!
15 May 2026 4:41pm GMT
Bart Piotrowski: How does Flathub even work? The CDN and caching layer
There is one specific way in which the non-corporate open source projects typically document how their infrastructure work: not at all, and Flathub is no different. The full picture likely lives only in my brain, and while it could be sorted out by anyone (especially in this LLM age, yay or nay), why should it only be me thinking at night about all the single points of failure?
Like any system that evolved naturally, it's all over the place. It's tempting to tell its history chronologically, but even then, it's difficult to find a good entry point. Instead, this post focuses on what happens when users call flatpak install; later entries will cover the website and, finally, the build infrastructure. Buckle up!
CDN, caching proxies, the master server
The secret of making computers work well is to have them not do anything at all, and that's the story behind serving Flathub's OSTree repository. Content-addressed objects are extremely cacheable as they are immutable, offloading the effort to the CDN provider.
When the client connects to dl.flathub.org, you can be certain it hits some layer of cache. Almost all the heavy-lifting is done by Fastly. At the peak, when both EMEA and North America are awake and at computers, 50 million requests per hour are cache hits served by Fastly's infrastructure, with a modest 20 million being misses passed down to our servers. There would be no Flathub without Fastly; Fastly does it completely for free, not even for fake Internet points as we are incredibly bad at highlighting what our sponsors do for us.


You can't do enough cache, and so various Fastly servers talk to Fastly-managed shield server which caches the most requested objects to avoid spilling over too much to us. For legit cache misses, the request will be served by one of 8 caching proxies we are running at different VPS providers. We use a consistent hashing director at Fastly which will pick the backend based on the path being requested. In the past, we used a dumb round-robin but as a result, each caching proxy had its own independent copy of the working set, wasting disk space and producing a higher miss rate against the master server. Hashing by URL behaves like one big cache instead of N copies.
These days, the caching proxy fleet consists of 3 servers at Mythic Beasts, 2 servers at AWS, another 2 at NetCup and a single server at DigitalOcean. We don't collect overly detailed metrics, but on average, each proxy serves around 1 TB/month back to Fastly and pulls roughly 5 TB/month from origin. With only 100 GB of disk space per proxy against a multi-TB working set, we're not so much caching the long tail as smoothing it. In the ideal world, we would be retaining much more data at this layer, but it's not the world we live in.
Each of these servers is running the latest stable Debian release. The requests are served by the usual nginx setup with proxy_cache enabled. There is some custom Lua code for invalidating certain paths after publishing new builds finishes (spoilers!). Vanilla nginx doesn't support the PURGE method, and third-party modules like ngx_cache_purge have not seen any maintenance for over 10 years. In the end, it was more maintainable to write Lua code to calculate the caching key of a URL and then run os.remove to "purge" it from the cache.
There's also a systemd timer for refreshing the Fastly IP allowlist. We used to expose these servers publicly, but a vision of everything crumbling down due to a DDoS attack kept me awake at night so this had to change.
On the far end of this setup sits a lonely physical server living in one of the Mythic Beasts' datacenters. This is The Server holding the entire Flathub repo on an equivalent of RAID10 in ZFS world: two 2-disk mirror vdevs on which ZFS stripes data across. There is more nuance to this setup, but the ultimate advantage is that we can tolerate a disk failure in each of the mirrors, while being less taxing to resilver after a swap. The entire reachable data set is around 4TB of data, with the remaining 6TB unused. There will be more about the repository maintenance later on!
Ironically, it's the only server running Ubuntu. At the time, it was the easiest way to have support for ZFS readily available. We could re-provision it to Debian, but on the other hand, what for? It works fine that way. It has survived at least 2 major upgrades between LTS-es; if it ain't broke, don't fix it.
The master server itself has to be partially public as it's where new builds are being uploaded. It no longer exposes the raw Flathub repository for the same reason caching proxies don't. This is accomplished with Tailscale and a lightweight ACL config ensuring caching proxies can talk only to the HTTP server running on the main repo server and vice versa (for issuing PURGE requests). Yes, all involved parties have public IP addresses assigned so this could technically be pure WireGuard setup but I prefer to make this someone else's concern, especially given how generous Tailscale's free plan is.

It's not much, but it's honest work. For how little we have, the file-serving half of Flathub's infrastructure works unreasonably well. Stay tuned for part 2!
15 May 2026 10:25am GMT
Christian Hergert: Translating French
I have been spending more time learning French lately, and as often happens, that turned into a small side project. liblingua is not intended to be a big mainstream translation platform. It is a fun GLib/GObject library for experimenting with local machine translation from applications.
The library uses Bergamot from Mozilla for the translation backend. Instead of sending text to a web service, liblingua resolves the language pair you ask for, downloads the required language model into the local user cache, and then performs translation locally.
The high-level API is built around a few small objects: LinguaRegistry discovers available translation profiles, LinguaProfile represents a model that can be loaded or downloaded, LinguaProgress reports download progress, and LinguaTranslator performs the translation.
All potentially blocking work is exposed as DexFuture, so it fits naturally into libdex based applications. If you are already using fibers, the code can stay linear and easy to read with dex_await_object().
A Small Example
Here is the basic shape of translating French into English:
#include <liblingua.h>
static void
translate_example (void)
{
g_autoptr(LinguaProgress) progress = lingua_progress_new ();
g_autoptr(LinguaRegistry) registry = NULL;
g_autoptr(LinguaProfile) profile = NULL;
g_autoptr(LinguaTranslator) translator = NULL;
g_autoptr(LinguaTranslation) result = NULL;
g_autoptr(GListModel) profiles = NULL;
g_autoptr(GError) error = NULL;
if ((registry = dex_await_object (lingua_registry_new (), &error)) &&
(profiles = lingua_registry_resolve (registry, "fr", "en")) &&
(profile = g_list_model_get_item (profiles, 0)) &&
(translator = dex_await_object (lingua_profile_load (profile, progress), &error)) &&
(result = dex_await_object (lingua_translator_translate (translator, "Bonjour"), &error)))
g_print ("%s\n", lingua_translation_get_translation (result));
else
g_printerr ("Error: %s\n", error->message);
}
The first time a model is needed, loading the profile may download it. After that, the model is reused from the local cache. That makes liblingua useful for little tools, demos, and desktop experiments where local translation is preferable to wiring everything through a remote service.
In the future this is probably the type of thing we would want as a desktop service to avoid duplicating caches amongst Flatpak applications. It would also be extremely useful to do live translation in Camera and Image Preview apps. I played a bit with that using Tesseract for OCR and it worked better than expected.
15 May 2026 9:50am GMT
14 May 2026
Planet GNOME
Nirbheek Chauhan: An Esoteric Type of Memory "Leak"
A little while ago, my colleague Sebastian started complaining about OOMs caused by Evolution taking up tens of gigabytes of memory. We discussed using sysprof to debug it, but it was too busy a time for Sebastian to set aside a few hours to do that.
Funnily enough, the most efficient fix at the time was to buy more RAM, since rust-analyzer was also causing OOM issues.
A few weeks went by. Restarting Evolution had become a daily ritual for Sebastian.
Then, on a whim, I decided investigating this might be a good test for an LLM.
I updated my Evolution git repo, built it, and started up Claude Code in the source root. This was the only prompt I supplied:
Find memory leaks in Evolution, current sourcedir. Particularly leaks that could accumulate over several hours. A colleague has a leak that slowly accumulates memory usage to several GB over the course of a day, requiring a restart of Evolution. That is the main focus, but we can fix other leaks in the process.
I wish I was lying, but that was all Claude Code needed to find the problem: Evolution just needed to call malloc_trim(0) from time to time.
I refused to believe it at first. I was only convinced when we saw the memory drop after running gdb -p $(pidof evolution) -batch -ex "call malloc_trim(0)" -ex detach
This seems absurd! Doesn't glibc reclaim freed memory from time to time?
Yes, it does. It calls sbrk() to do that. However, sbrk() can only reclaim free memory at the top of the heap, since it simply moves the program break downward to do so. malloc_trim(0) calls sbrk() and then also calls madvise(..., MADV_DONTNEED) on the free pages, which allows the kernel to reclaim them.
So if you have 10GB of unused memory followed by 4 bytes allocated at the top of the heap, your RSS is >10GB, even if you're using a few hundred megs. Till you call malloc_trim(0).
Note that you can only get into this situation if you have hundreds of thousands of small allocs/deallocs happening repeatedly. If your alloc is >128KB, mmap() is used for the allocation, and none of this applies.
Coincidentally, GLib's use of GSlice for GObject allocations was masking this issue in the past, but GSlice has been a no-op for some time now (for good reasons). Ideally, Evolution should not be using GObject for such ephemeral objects.
Lesson learned: if you have memory usage issues and you suspect fragmentation, try malloc_trim(0) before you go thinking about fancy allocators.
14 May 2026 9:52pm GMT
13 May 2026
Planet GNOME
Toluwaleke Ogundipe: Hello GNOME and GSoC, Again!
I am delighted to announce that I am returning for Google Summer of Code 2026 to contribute to GNOME once again. Following my work on Crosswords last year, I will be shifting focus to the core of the desktop: Mutter. For what it's worth, I never left; I've been working with Jonathan to improve things and add shiny new features in Crosswords.
Mutter serves as the Wayland display server and compositor library for GNOME Shell. Currently, a GPU reset invalidates the EGL context and causes the loss of all allocated GPU memory, resulting in the entire desktop crashing or freezing.
My project aims to implement a robust recovery mechanism for GPU resets to prevent these session-ending freezes, under the mentorship of Jonas Ådahl, Robert Mader, and Carlos Garnacho. Leveraging the GL_EXT_robustness extension, I will implement reset detection, context re-creation, and re-upload of essential GPU resources, such as client textures, glyph caches, and background images. This will allow the compositor to resume rendering seamlessly after hardware-level failures.
Over the course of the project, I will share updates on the progress of these recovery mechanisms and the challenges of managing state restoration within the compositor.
I am very grateful to my mentors, Jonas, Robert, and Carlos, for the opportunity to work on this critical part of the GNOME ecosystem. Also, a big shout-out to Federico, Hans Petter, and Jonathan for their continuous support. I look forward to another productive summer with the community. 

13 May 2026 6:17pm GMT
11 May 2026
Planet GNOME
Nick Richards: Agile Rates After Launch
Last summer I wrote up Octopus Agile Prices For Linux, a small GTK app to show the current Octopus Agile electricity price and the next day of half-hourly rates. It did one thing, which is a good number of things for a desktop utility to do.
Since then the app has become a bit less narrow. But it now does enough more that the launch post undersells it, and in a couple of places sends people looking for the wrong name.
The app is now called Agile Rates. The application ID is still com.nedrichards.octopusagile, because changing stable app IDs is not exciting for anyone, but the name changed because Agile is no longer the whole story. Thanks to code from Andy Piper, it can also work with Octopus Go and Intelligent Go tariffs. Intelligent Go needs an API key because those prices are account-specific, but plain Agile and Go can still be set up manually.
That was the first larger change: setup had to become a thing.
The original app assumed you knew your tariff and region, or at least were willing to rummage in preferences until the graph stopped being wrong. That is fine for a scratch-your-own-itch project and a bit rude for an app on Flathub. The current version opens with a setup assistant. You can connect an Octopus account with an API key and account number, in which case the app tries to detect the active electricity tariff. Or you can keep it simple and choose the tariff and region manually.
The second change is the one I actually use most: finding the cheapest slot.
The launch version showed a graph and left the planning to the human. That works for quick glances, but most of my real questions are more specific:
When should the dishwasher run?
When should the washing machine run?
Is there a cheap three-hour block before tomorrow afternoon?
So there is now a "find cheapest time" tool. Pick a duration and it searches the available forecast window for the cheapest continuous block. The chart now scrolls to the chosen time instead of making you squint along the bars like you are reading a very dull railway timetable.
The graph itself has had a lot of tweaks. It has grid lines, clearer day boundaries, better current-price highlighting, less terrible dark-mode contrast, and layout rules that behave on narrower screens. The preferences window and main window are adaptive now too. Handy if you split your screen or have a Linux phone.
The biggest recent addition is usage history. If you connect an account, the app can fetch recent smart meter consumption data, cache it locally, and show a Usage view. That includes kWh history, a seven-day trend, an estimated monthly usage figure, and charts. It also tries to estimate spend by matching historical usage to tariff rates and standing charges.
Underneath that, the project has become more like a real small application. There are unit tests for pricing, tariff selection, adaptive layout, usage insights, and historical cost calculation. The development Flatpak manifest runs the Meson tests inside the GNOME SDK, which catches the class of bugs where the host Python environment was accidentally being too kind. Ruff is in the loop for linting. The app moved to the GNOME 50 runtime. Screenshots, AppStream metadata, branding colours, and icons have all been tidied up.
So the current description is: Agile Rates is a small GNOME app for UK Octopus Energy customers who want current and upcoming smart tariff rates, a cheap-time finder, and, if they connect their account, recent usage and estimated spend history. It is independent and is not affiliated with, endorsed by, or sponsored by Octopus Energy. I hope you find it useful.
11 May 2026 7:53pm GMT
Michael Catanzaro: Flatpak Sandbox Escape via Yelp
Yelp 49.1 fixes a significant Flatpak sandbox escape related to last year's CVE-2025-3155. CVE assignment for this new issue is currently pending.
This is not a bug in Flatpak. Flatpak allows sandboxed applications to open URIs or files, meaning the sandboxed application may use a URI or file path to launch another application to open the URI or file. This is brokered via the OpenURI portal. The portal or the app may decide to require user interaction to decide which app to launch, but user interaction is generally not required. This is necessary: you would get pretty frustrated if you were prompted to select which app to use every time you click on a link or try to open something! Accordingly, unsandboxed applications that are installed on the host system are somewhat risky: any malicious sandboxed app may launch an unsandboxed app using a malicious file, generally with no user interaction required. Unsandboxed applications installed on the host OS are inherently part of the attack surface of the Flatpak sandbox.
In this case, a sandboxed application may launch Yelp to open a malicious help file. The help file can then exfiltrate arbitrary files from your host OS to a web server by using a CSS stylesheet embedded in an SVG. Suffice to say the attack is pretty clever, and certainly more impactful than the typical boring memory safety bugs I more commonly see.
This bug was discovered by Codean Labs, which performed a security audit of Flatpak and several GNOME projects thanks to generous sponsorship by the Sovereign Tech Resilience program of Germany's Sovereign Tech Agency.
11 May 2026 2:12pm GMT
10 May 2026
Planet GNOME
Laura Kramolis: Computers Are Terrible
A slightly more collected version of originally 18 Signal messages. This is a simplification. I am evidently no expert in Unicode specifically or text encoding in general.
I, for a long time, believed that while many modern standards are a mess of legacy compatibility built on legacy compatibility, Unicode was an exception. That the only compromise it made was ASCII-compatibility, but even that wasn't such a big one given that its character set is the most common one in computing even to this day. I was wrong.
I got a US keyboard so now I have 2 different ways of typing accented characters. I can either hold the A key until I get an option of à, á, â, ä, ǎ, etc., or I can press ⌥ E and then A to get to á, combining ´ and a regular a. I started wondering… when typing it one way or the other, the results must be different, right? I looked for a website that showed me what code points I was typing, and… they were the same?
Most systems (the OS/browser in this case) normalize all text either one way or the other. In this case, to a single code point. Unicode does have deprecation, so you would think that when they introduced combining characters, they would have deprecated the precomposed versions of characters that can be written using them, right? Nope!
It's arbitrary which way each system normalizes text. Some do it composed (á) and some decomposed (a + ◌́). Both are part of the standard. And of course, you need to treat them as equivalent when not normalized so you might as well do it when you can anyway.
Precomposed characters are the legacy solution for representing many special letters in various character sets. In Unicode, they were included for compatibility with early encoding systems […].
Oh well, my day is ruined. My new life goal is advocacy for the deprecation of all precomposed characters… or maybe I should just accept that all computing will be plagued by backwards compatibility headaches 'til the end of time.
10 May 2026 12:00am GMT
09 May 2026
Planet GNOME
Jakub Steiner: USS/FMS Carrier
I'm a sucker for pixel art and very constrained music grooveboxes. While I'm not into chiptunes, they sure are a cultural phenomenon.
You heard me boast about the Dirtywave M8 numerous times, even in person, because it's my tool of choice for producing and performing music. Its genius lies in high sound quality and a workflow that grew out of the tiny screen and button constraints on the Nintendo Gameboy, the platform of choice for an app called LSDJ, which the M8 is modelled after. That, and the sheer amount of sound engines living in your pocket. Building on the shoulders of giants and all.
The small M8 community has a few 'celebrities', such as Ess Mattisson. I first heard of Ess when I ran into an amazing single channel track called Wertstoffe. Ess has a great pedigree as the creator of the original Digitone FM synthesizer while working at Elektron. FM remains his forte, and after creating numerous plugins through Fors, he has now released a little 2-operator FM synth and sequencer for the platform of the future, Nintendo Gameboy Advance.
What makes FMS a bit crazy is what it's doing under the hood. The Gameboy Advance has no FM synthesis hardware at all. Its audio gives you two Direct Sound DMA channels of 8-bit signed PCM - that's 256 amplitude levels, roughly 48 dB of dynamic range. For comparison, a CD has 96 dB, in much finer fidelity. The CPU is an ARM7TDMI running at 16.78 MHz with 256 KB of RAM, and that's where all the FM math happens. Sine waves, modulation, mixing four channels, all in real time, in software, on a chip from 2001 that was designed to shuffle sprites around. The hiss you hear is just part of the deal: quantization noise from that 8-bit DAC. So few amplitude steps means everything that comes out has this fuzzy, slightly crushed quality. You can't get rid of it. It is the sound. And somehow there are four channels of 2-operator FM synthesis in there, each with envelopes and ratio control. On a Gameboy Advance.
Picking GBA as a platform of choice in 2026 may be strange. Surprisingly, it can be used on a very large array of hardware. Not only can you plug a memory card into the original hardware or new fancy clones like the Analogue Pocket, you have an exponentially larger choice of dozens if not hundreds of Chinese emulator handhelds from Anbernic, Powkiddy, Miyoo or Retroid. You can also use the Steam Deck or any PC running one of the many emulators, RetroArch being the most popular one.
FMS really touched me. Partly because I have a soft spot for the Nordic demo scene, but mainly for its novel approach to composition. Just like with the M8, creating basic building blocks and then applying transposition to break the looping monotony is my favorite workflow. This little thing has that in the form of pattern and trig transposition but also a novel take on "effects". Yes, you heard me right. There's a sorta-kinda-delay. Even does stereo field ping-pong.
I will keep on trying to create something that … sounds good. The process has been amazing. I truly love some of the sequencing tricks and workflows. The sequencer is, however, so good it would be worth seeing it run on top of a higher quality sound engine too.
09 May 2026 12:00am GMT
08 May 2026
Planet GNOME
This Week in GNOME: #248 Tracking Performance
Update on what happened across the GNOME project in the week from May 01 to May 08.
GNOME Core Apps and Libraries
Glycin ↗
Sandboxed and extendable image loading and editing.
Sophie (she/her) says
Automatically running tests on GitLab has now been a standard for a while. But tracking performance metrics is much less common. Glycin now started running basic performance tests on bencher.dev's bare metal runners, which will hopefully provide comparable results.
As of now, the benchmarks are only covering the overhead of the loader stack, by loading a 1px PNG, and the binary file sizes for glycin loaders and the thumbnailer. But the tests should be easy to expand. The benchmarks are always run for commits in the main branch, and can be manually started for merge requests. This way it will be possible to track performance improvements and catch regressions early.
Third Party Projects
Christian says
🎉 Gitte 0.2.0 is out!
This week, Gitte 0.2.0 was released with a big focus on interactive rebasing and polishing everyday Git workflows.
The biggest addition is interactive rebasing directly from the commit log. Commits can now be reordered via drag & drop, dropped, reworded, edited during a paused rebase, or squashed and fixuped without leaving the GUI.
Remote operations like push, pull, fetch and clone now use the Git CLI internally, improving credential handling and protocol support. The diff view font is now configurable, and repositories can be opened directly from the terminal using commands like
gitte ~/Code/projects/Gitte.This release also adds a unified stash dialog for workflows that require stashing changes, ahead/behind indicators for the current branch, double-click checkout for local branches, and improved merge commit information in the log viewer. There are also a few small easter eggs hidden throughout the app.
On the translation side, Gitte now includes a German translation and a Ukrainian translation by Dymko. The release also includes AUR packaging documentation contributed by Kainoa Kanter, alongside many bug fixes and smaller refinements across the application.
Get it on Flathub or check the source code.
Bilal Elmoussaoui reports
I have released the first version of gobject-linter, previously known as goblint.
This release brings a lot of new functionality: Meson integration for accurate dead code detection (functions, enum variants, structs, struct fields and more) via the new dead_code rule, mis-exported public types detection, inconsistent function signatures checking, and a type_style rule to enforce consistent use of either GLib type aliases (
gint,gfloat,gdouble) or their C equivalents across your codebase. Two new GObject introspection rules for verifying missing since annotations and the exported public APIs are bindings friendly.It also supports diff-scoped linting via
--diff -so you can incrementally integrate it into large existing projects.The release is also available on crates.io
Jeffry Samuel announces
Nocturne 1.0.0 has been released!
Nocturne is a modern music player that can play songs from your OpenSubsonic, Jellyfin and local libraries.
It includes features such as audio visualizers, equalizers and automatic lyric fetching.
Some of the new features in 1.0.0 are:
- Support for changing max bitrate
- Support for replay gain
- Added option to show sidebar player
- Compatibility with word for word lyrics
- Faster and more stable interface
- Gapless playback
- Grouping of songs in albums by their disc
- Added option to show dynamic background in the main window
- Much more
mas says
Hi, finally released my first app, Press! With has a very straight-forward interface to compress huge music libraries with ease.
You might like it because:
- Compresses multiple files simultaneously
- Never takes destructive actions on the source (but it can replace files on the destination if you want)
- Avoids re-compressing a file (if you just want to add a new album, it compresses just that one, not your entire library)
- Import basically any format GStreamer can take!
- Export to mp3, m4a, or ogg
- Move other non-auto files with you
- You can add custom formats with a bit of GStreamer know-how
It really is a one-stop solution to compress music to portable devices.
I'd love to hear feedback and suggestions.
Get it on Flathub or check the source code. Oh and, it uses libadwaita, vala, and GStreamer.
JumpLink announces
The type-definitions generator ts-for-gir produces the typings used to write GNOME applications in TypeScript. It can now experimentally run directly on GJS, without Node.js.
This is made possible by the new experimental GJSify framework, which provides Node.js and Web APIs on top of GJS. Its long-term goal is to make as much of the JavaScript / TypeScript ecosystem as possible available to GJS applications.
bhack announces
I'd like to introduce Mini EQ, a new small GTK/Libadwaita app for PipeWire desktops.
Mini EQ is a system-wide parametric equalizer. It creates a PipeWire filter-chain sink with builtin biquad filters, routes desktop playback through it with WirePlumber, and provides a compact 10-band fader workflow. It also supports Equalizer APO/AutoEq preset import and an optional spectrum analyzer through the PipeWire JACK compatibility layer.
The project is now available on Flathub, with source and packaging published on GitHub.
Flathub: https://flathub.org/apps/io.github.bhack.mini-eq GNOME Shell extension: https://extensions.gnome.org/extension/9803/mini-eq-controls/
Source: https://github.com/bhack/mini-eq
Anton Isaiev announces
RustConn is a GTK4/libadwaita connection manager for SSH, RDP, VNC, SPICE, Telnet, MOSH, and more.
Versions 0.12.8-0.13.7 were shaped heavily by user feedback. What started as a personal tool is now used daily by sysadmins and DevOps teams - and their reports drive the roadmap.
Key additions:
Local Shell in Flatpak - fully working host shell via flatpak-spawn with real PTY and job control. RDP dynamic resize - in-place resolution change via Display Control Channel, no reconnect needed; automatic fallback for legacy servers. RDP Autotype - type text as keystrokes into remote sessions, bypassing clipboard restrictions. Drag & Drop - file paths into terminals, files to RDP clipboard. Smart Folders & Dynamic Folders - filter connections by tag/protocol/pattern, or generate them from external scripts. Virt-viewer .vv file support - open SPICE/VNC files from Proxmox, oVirt, libvirt directly. CLI -format json|csv|table - machine-readable output for scripting and AI agents. GNOME HIG audit - restructured menus, unified dialogs, accessible labels across all windows. Flatpak CLI auto-versioning - 7 bundled CLI tools now resolve latest versions from upstream automatically.
Homepage: https://github.com/totoshko88/RustConn Flathub: https://flathub.org/en/apps/io.github.totoshko88.RustConn
Shell Extensions
Miklós Zsitva says
Matrix Status Monitor v7 improves room handling, notifications, and profile actions in GNOME Shell.
Matrix Status Monitor v7 is now available on GNOME Extensions, bringing a noticeably smoother experience for Matrix users running GNOME Shell. This release focuses on making the extension feel more responsive and more native to the desktop, while keeping the panel UI lightweight and fast.
The biggest change is the new weight-based room sorting system, which replaces the old timestamp-only approach. Rooms are now ranked by highlights, unread counts, direct messages, favourites, visit frequency, and recency, so the most relevant conversations surface first.
v7 also adds a clear idle/active separator in the room list, plus async menu rebuilds via GLib.idle_add to avoid blocking the UI during updates. On top of that, the extension now sends GNOME desktop notifications through MessageTray, with event ID deduplication so the same message does not trigger repeated alerts.
The profile header has been expanded as well: it now shows the user avatar, display name, user ID, plus one-click copy and QR toggle actions. The avatar loading path was also extended to handle a larger profile icon size, which helps the header feel more polished and distinct from room rows.
Overall, v7 is a refinement release that makes the extension feel more reliable, more readable, and more useful in daily GNOME use.
https://extensions.gnome.org/extension/9328/matrix-status-monitor/
That's all for this week!
See you next week, and be sure to stop by #thisweek:gnome.org with updates on your own projects!
08 May 2026 12:00am GMT























