|
1 | 1 | import {listFiles} from "../util"; |
2 | 2 | import path from "path"; |
| 3 | +import {ConfigLang} from "../../../../../../config/lang"; |
| 4 | +import {getIcon} from "./icon"; |
| 5 | +import {getAppTitle} from "./title"; |
| 6 | +import fs from "node:fs"; |
3 | 7 |
|
4 | 8 | export const ManagerAppLinux = { |
5 | 9 | list: async () => { |
6 | 10 | return lists() |
7 | 11 | } |
8 | 12 | } |
9 | 13 |
|
| 14 | +const appSet = new Set<string>(); |
| 15 | + |
10 | 16 | const lists = async () => { |
| 17 | + appSet.clear() |
11 | 18 | const files = await listFiles([ |
12 | 19 | "/usr/share/applications", |
13 | 20 | "/var/lib/snapd/desktop/applications", |
14 | 21 | `${process.env.HOME}/.local/share/applications`, |
15 | 22 | ]) |
16 | | - for (const file of files) { |
17 | | - if (path.extname(file.pathname) !== ".desktop") { |
| 23 | + const apps = [] |
| 24 | + const locale = ConfigLang.getLocale() |
| 25 | + for (const f of files) { |
| 26 | + if (appSet.has(f.pathname)) { |
| 27 | + // console.log('appSet.has', f.pathname) |
| 28 | + continue |
| 29 | + } |
| 30 | + const extname = path.extname(f.pathname); |
| 31 | + if (extname !== '.desktop') { |
| 32 | + continue |
| 33 | + } |
| 34 | + const app = { |
| 35 | + name: f.name.replace(/\.(desktop)$/, ''), |
| 36 | + title: f.name, |
| 37 | + pathname: f.pathname, |
| 38 | + icon: null, |
| 39 | + command: null, |
| 40 | + } |
| 41 | + const desktopInfo = await parseDesktopFile(app.pathname) |
| 42 | + app.icon = await getIcon(desktopInfo, app.pathname, app.name) |
| 43 | + app.title = await getAppTitle(desktopInfo, locale, app.pathname, app.name); |
| 44 | + if (!app.icon) { |
| 45 | + continue |
| 46 | + } |
| 47 | + if (!desktopInfo.Exec) { |
18 | 48 | continue |
19 | 49 | } |
20 | | - //TODO |
| 50 | + let command = desktopInfo.Exec |
| 51 | + .replace(/ %[A-Za-z]/g, "") |
| 52 | + .replace(/"/g, "") |
| 53 | + .trim(); |
| 54 | + if (desktopInfo.Terminal === 'true') { |
| 55 | + command = `gnome-terminal -x ${command}` |
| 56 | + } |
| 57 | + app.command = command |
| 58 | + appSet.add(app.pathname) |
| 59 | + apps.push(app) |
| 60 | + } |
| 61 | + return apps |
| 62 | +} |
| 63 | + |
| 64 | +const parseDesktopFile = async (pathname: string): Promise<Record<string, string>> => { |
| 65 | + const content = fs.readFileSync(pathname, 'utf-8'); |
| 66 | + const desktop = {}; |
| 67 | + for (const line of content.split('\n')) { |
| 68 | + if (line.startsWith('[')) { |
| 69 | + continue; |
| 70 | + } |
| 71 | + const [key, value] = line.split('='); |
| 72 | + if (!key || !value) { |
| 73 | + continue; |
| 74 | + } |
| 75 | + desktop[key] = value; |
21 | 76 | } |
22 | | - return [] |
| 77 | + return desktop |
23 | 78 | } |
0 commit comments