Skip to content

Instantly share code, notes, and snippets.

@buzztaiki
Last active July 20, 2023 06:13
Show Gist options
  • Save buzztaiki/1492431 to your computer and use it in GitHub Desktop.
Save buzztaiki/1492431 to your computer and use it in GitHub Desktop.
Using shell object in gjs
#!/usr/bin/gjs
// SPDX-License-Identifier: MIT
// usage: gjs shell_object_sample.js
const { GIRepository, GLib, Gio } = imports.gi;
function findLib(path, prefix) {
const libdir = Gio.File.new_for_path(path);
const files = libdir.enumerate_children('', Gio.FileQueryInfoFlags.NONE, null);
for (; ;) {
const finfo = files.next_file(null);
if (!finfo) break;
if (finfo.get_file_type() == Gio.FileType.DIRECTORY && finfo.get_name().startsWith(prefix)) {
return GLib.build_filenamev([path, finfo.get_name()]);
}
}
return null;
}
GIRepository.Repository.prepend_library_path('/usr/lib64/gnome-shell')
GIRepository.Repository.prepend_search_path('/usr/lib64/gnome-shell');
GIRepository.Repository.prepend_library_path(findLib('/usr/lib64', 'mutter-'));
GIRepository.Repository.prepend_search_path(findLib('/usr/lib64', 'mutter-'));
const { Shell } = imports.gi;
const appSys = Shell.AppSystem.get_default();
print(appSys.get_installed().map(x => x.get_name()).join('\n'));
@buzztaiki
Copy link
Author

I rewrite this example.

> uname -a
Linux echo 5.4.5-arch1-1 #1 SMP PREEMPT Wed, 18 Dec 2019 19:48:51 +0000 x86_64 GNU/Linux

> gnome-shell --version
GNOME Shell 3.34.2

> gjs --version
gjs 1.58.3

> LD_LIBRARY_PATH=/usr/lib64/gnome-shell/ gjs shell_object_sample.js | head
Pingus
Slack
絵文字の選択
OpenJDK Java 10 Shell
Widget Factory
サウンド
テキストエディター
Banner Designer
Qt4 Designer
画像ビューアー

@nlpsuge
Copy link

nlpsuge commented Nov 12, 2021

Not work for me.

  • gnome-shell --version

GNOME Shell 41.1

  • LD_LIBRARY_PATH=/usr/lib64/gnome-shell/ gjs shell_object_sample.js | head

(gjs:27581): Gjs-CRITICAL **: 10:56:04.899: JS ERROR: Error: Requiring Shell, version none: Typelib file for namespace 'Meta', version '9' not found
@test.js:6:15

(gjs:27581): Gjs-CRITICAL **: 10:56:04.899: Script test.js threw an exception

@buzztaiki
Copy link
Author

I think you should add /usr/lib64/mutter-9 to search path instead of /usr/lib64/mutter-5 for your environment.

@buzztaiki
Copy link
Author

Update to a generic version.

@nlpsuge
Copy link

nlpsuge commented Nov 21, 2021

Thanks for the update.

@yilozt
Copy link

yilozt commented Jul 11, 2022

We can load librarys directly by GIRepository.Repository.prepend_library_path() instead of LD_LIBRARY_PATH enviroment variable. There is a example, works with gnome-shell 42.3

#!/usr/bin/gjs

// chmod +x ./shell_object_sample.js && ./shell_object_sample.js

const res = imports.gi.GIRepository.Repository

// load library of Mutter project 
res.prepend_search_path('/usr/lib/mutter-10')
res.prepend_library_path('/usr/lib/mutter-10')

// load library of gnome-shell project
res.prepend_search_path('/usr/lib/gnome-shell')
res.prepend_library_path('/usr/lib/gnome-shell')

const Shell = imports.gi.Shell;
const appSys = Shell.AppSystem.get_default();
print(appSys.get_installed().map(x => x.get_name()).join('\n'));

@buzztaiki
Copy link
Author

Looks really good. Updated.

@nlpsuge
Copy link

nlpsuge commented Jul 16, 2022

@yilozt

Just tried your code.
Errors throw on my machine:

Gjs-CRITICAL **: JS ERROR: Error: Requiring Shell, version none: Typelib file for namespace 'Shell' (any version) not found
getApps.js:15:15

Gjs-CRITICAL **: Script getApps.js threw an exception

The line 15 is const Shell = imports.gi.Shell; and I use gnome-shell 42.2.

@yilozt
Copy link

yilozt commented Jul 16, 2022

@nlpsuge , It should works if you replace /usr/lib with /usr/lib64. I just test it in Fedora36 with gnome-shell 42.2.

@nlpsuge
Copy link

nlpsuge commented Jul 17, 2022

@yilozt

Just tested, it works if I replace /usr/lib with /usr/lib64.

Thank your very much. :)

@blueray453
Copy link

Debian 12:

#!/usr/bin/gjs

// chmod +x ./shell_object_sample.js && ./shell_object_sample.js

const res = imports.gi.GIRepository.Repository

// load library of Mutter project
res.prepend_search_path('/usr/lib/x86_64-linux-gnu/mutter-11')
res.prepend_library_path('/usr/lib/x86_64-linux-gnu/mutter-11')

// load library of gnome-shell project
res.prepend_search_path('/usr/lib/gnome-shell')
res.prepend_library_path('/usr/lib/gnome-shell')

const Shell = imports.gi.Shell;
const appSys = Shell.AppSystem.get_default();
print(appSys.get_installed().map(x => x.get_name()).join('\n'));

Thank you very much.

@blueray453
Copy link

If I replace get_installed with get_running then there are not output. why?

@nlpsuge
Copy link

nlpsuge commented Jul 15, 2023

If I replace get_installed with get_running then there are not output. why?

Do you have any apps with at least one window running while you run your script?

@blueray453
Copy link

Yes. I opened many apps including gnome specific apps. Nothing.

@nlpsuge
Copy link

nlpsuge commented Jul 19, 2023

Running Shell.AppSystem.get_default().get_running().map(x => x.get_name()).join('\n') in lg (alt+F2 then type lg), is there output?

@blueray453
Copy link

The output is r(0) = Firefox Alacritty ..... I mean the command works if i run this way.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment