Neuigkeiten:

Privates MODX und LINUX BLOG, User Registrierung ist deaktiviert! Fragen oder Tipps? Bitte per Matrix: @jolichter:tchncs.de

Hauptmenü

Neueste Beiträge

#31
LINUX / Thermal Monitor liest nicht au...
Letzter Beitrag von Jo - 2020-04-05 | 10:01:18
Ich benutze unter KDE das Widget "Thermal Monitor" in meiner Taskleiste um z.B. die CPU, Mainboard und SSD-Temperatur anzuzeigen. Leider scheint das Projekt nicht mehr gepflegt zu werden. Während es im Allgemeinen funktioniert, muss ich immer per Kontextmenü einmal auf "Reload Temperature Sources" klicken, um das Widget dazu zu bringen die Temperaturen abzufragen.

Workaround (Quelle):
kate ~/.local/share/plasma/plasmoids/org.kde.thermalMonitor/contents/ui/main.qml
In der Datei alles ausklammern, was mit der Variable SystemmonitorAvailableSources zu tun hat.

Meine main.qml Datei mit ausgeklammerten Zeilen ist gepackt im Anhang, wie immer ohne Gewähr!


getestet mit KDE 5.18.3 | Kernel 5.4.28 | Plasmoid Version 1.2.8


Noch ein Bug: System (journalctl) log is filled with repeated messages
Workaround: Habe die Qt-Debug-Protokollierung wie im Link steht im bash_profile des Benutzers deaktiviert.
kate ~/.bash_profilediese 2 Zeilen hinzufügen:
  QT_LOGGING_RULES='*.debug=false'
  export QT_LOGGING_RULES


#32
LINUX / fritz-nas mit Samba 4.11 oder ...
Letzter Beitrag von Jo - 2020-04-03 | 22:21:21
Fritz-NAS USB-Festplatte als Netzlaufwerk

Samba 4.11 (smbclient 4.11.x) deaktiviert SMB1 und unterstützt SMB2/3.
Das ist eine gute Nachricht, leider scheint AVM noch nicht so weit zu sein.

Soweit mir bekannt ist, verwenden die derzeitigen FritzBox-Modelle das alte und unsicheren Protokoll SMB1.
AVM scheint an der SMB2/3-Unterstützung zu arbeiten, z.B. für das 7490 Modell: Link

Solltet ihr seit Samba 4.11 nicht mehr auf euren fritz-nas per smb zugreifen können (Fehlermeldung: Verbindung zu Rechner fritz-nas ist unterbrochen), ist es möglich die SMB1 Unterstützung wie folgt zu aktivieren:
kate /etc/samba/smb.confund fügt dort diese Zeile ein:

client min protocol = NT1

siehe auch: AVM - Hinweis zur Umstellung des Zugriffs auf FritzNAS Inhalte über das SMB-Protokoll


Nachtrag: Seit Fritz!OS 7.2 nutze ich nur noch SMB3, auf meinem NAS-Server schon länger!
In meiner smb.conf steht nun wieder "client min protocol = SMB2".



#33
LINUX / Videochat Jitsi Meet
Letzter Beitrag von Jo - 2020-03-21 | 12:34:28
Plattformunabhängige Alternative für Skype, WebEx oder Hangouts: Jitsi Meet
Getestet mit Linux Manajro KDE (AppImage), iOS, Mozilla Firefox und Pale Moon

Es ist kein Konto notwendig, nur ein aktueller Webbrowser mit WebRTC Unterstützung oder einer App.
Da bei WebRTC keine Plug-Ins geladen werden müssen, ist die Wahrscheinlichkeit sich Malware einzufangen sehr unwahrscheinlich.
Hinweis WebRTC mit VPN Verbindung: Hier könnte jemand die wirkliche IP-Adresse herausfinden.

Jitsi Meet ist quelloffen (https://github.com/jitsi), sicher und kostenlos. Mit Jitsi Meet könnt ihr folgendes tun:
  • Video oder nur Audio mit einem oder mehreren Benutzern
  • Einfach nur Chatten
  • Desktop oder ein bestimmtes Fenster freigeben
  • Benutzer über eine einfache URL* einladen

*die URL setzt sich aus Hostnamen und Konferenznamen zusammen und kann daher sehr einfach mit anderen geteilt werden

Es gibt auch eine App für iOS (App Store), Android (Google Play), f-droid.org (F-Droid-Store) und Linux (AppImage).

Die Bedienung ist einfach und selbsterklärend. Ich nutze nur deutsche Jitsi Meet Instanzen die im Gegensatz zu https://meet.jit.si auf Google Analytics verzichten, z.B. von der Technischen Universität Ilmenau oder Linus Neumann, Link mit Liste.


Das Jitsi Meet kann auf mehrere Arten genutzt werden:
  • Im Browser z.B. https://jitsi.fem.tu-ilmenau.de, https://meet.linus-neumann.de oder teamjoin.de öffnen, es muss immer die gleiche Instanz mit dem Teilnehmer genutzt werden und wäre bei einer App so als Server URL einzutragen
  • Einen freien Namen ohne Umlaute oder Leerstellen für die Konferenz wählen, z.B. "blablabla42" und euren Chat-Partner den Link mit angehangen Namen mitteilen (https://jitsi.fem.tu-ilmenau.de/blablabla42)
  • In der App wird nur der Konferenzname zum Verbinden angegeben, die Instanz (Standard Server URL ist https://meet.jit.si) wird in den Einstellungen eingetragen
  • Optional kann auch ein Passwort vergeben werden, indem ihr unten auf das Info Symbol klickt (Share link / Add password)


Unter Linux lässt sich Jitsi Meet im Browser oder per AppImage ohne Installation und Root-Rechte ausführen, Download Link: Jitsi Meet AppImage. Diese Datei z.B. in euer Home Ordner ~/bin speichern und ausführbar machen. Beim ersten Start solltet ihr danach gefragt werden, ansonsten:
chmod +x ./*.AppImage
PrintScreen AppImage Jitsi Meet mit Einstellungen:


Mit Firejail härte ich meine Internetprogramme und lasse auch Jitsi Meet in einem sicheren Sandkasten laufen. Dazu passe ich manuell im KDE Anwendungsstarter (Kontextmenü -> Menüeinträge bearbeiten...) unter Internet das Element Jitsi Meet an, Befehl: firejail --appimage ~/bin/jitsi-meet-x86_64.AppImage %U
Beim ersten Start sollte dieser Eintrag automatisch ohne Firejail im KDE Menü eingetragen sein, hier meine Einstellungen als PrintScreen:


Die Einstellungsdateien liegen im Versteckten Ordner ~/.config/Jitsi Meet/ und kann für ein Reset einfach gelöscht werden:
rm -rf ~/.config/'Jitsi Meet'

Hinweis: Bisher können über WebRTC nur 1:1-Anrufe wirklich Ende-zu-Ende-verschlüsselt werden. Bei Gruppen-Calls entschlüsselt der Server die Datenströme aller Teilnehmer und bündelt sie aus Effizienzgründen in einen einzigen Strom. Sowohl Signaling als auch die eigentlichen Sprach- und Videodaten sind in diesem Fall also maximal per TLS bis zum Server gesichert (z.B. bis zur TU Ilmenau, wenn ihr diese Instanz nutzt). Quelle: Golem - Ende-zu-Ende-Verschlüsselung.

Unternehmen die für Videokonferenzen einen erhöhten Datenschutz benötigen, sollten sich eine eigene Jitsi-Meet Instanz hosten.
Eine simple Möglichkeit wäre das via Docker Compose zu tun.

#34
LINUX / Drucker für Airprint fähig mac...
Letzter Beitrag von Jo - 2020-03-06 | 22:02:27
Vom iPad oder iPhone via Airprint und Cups drucken
Apple ist ziemlich Linux freundlich  :smilie:
(getestet mit HP-Drucker und Manjaro KDE 2020-03-06)

Quelle: wiki.archlinux.org - AirPrint from Mobile Devices

Bei einer neuen Manjaro Installation mit Kernel 6.1.9 musste ich nur den Resolved-Service deaktivieren und den Avahi-Service aktivieren:
sudo systemctl disable systemd-resolved.service
sudo systemctl stop systemd-resolved.service
sudo systemctl enable avahi-daemon.service
sudo systemctl start avahi-daemon.service


Wenn das nicht funktioniert:

Erst alles aktualisieren, z.B.:
yay -Syyuu && sudo paccache -rk2 && sudo pacman -Qdtq
Eine Avahi-Service-Datei kann manuell oder alternativ wie im Wiki-Link beschrieben per Script erzeugt werden.
Dafür werden die Pakete python und python-pycups benötigt:
sudo pacman -S python  python-pycups

1. Drucker im Netzwerk freigeben (system-config-printer oder per localhost:631/admin), sonst gibt dieses Python-Skript keine Datei nach /etc/avahi/services aus:


2. Script vom github (tjfontaine) laden und ausführen, für jeden Drucker wird eine Avahi-Service-Datei erstellt:
wget https://raw.githubusercontent.com/tjfontaine/airprint-generate/master/airprint-generate.py
sudo python airprint-generate.py -d /etc/avahi/services



Bei mir sieht die Drucker Avahi-Service-Datei so aus:

<?xml version="1.0" ?>
<!DOCTYPE service-group  SYSTEM 'avahi-service.dtd'>
<service-group>
    <name replace-wildcards="yes">AirPrint Hewlett-Packard-HP-Color-LaserJet-CP2025dn @ %h</name>
    <service>
        <type>_ipp._tcp</type>
        <subtype>_universal._sub._ipp._tcp</subtype>
        <port>631</port>
        <txt-record>txtvers=1</txt-record>
        <txt-record>qtotal=1</txt-record>
        <txt-record>Transparent=T</txt-record>
        <txt-record>URF=none</txt-record>
        <txt-record>rp=printers/Hewlett-Packard-HP-Color-LaserJet-CP2025dn</txt-record>
        <txt-record>note=Hewlett-Packard-HP-Color-LaserJet-CP2025dn</txt-record>
        <txt-record>product=(GPL Ghostscript)</txt-record>
        <txt-record>printer-state=3</txt-record>
        <txt-record>printer-type=0x82905c</txt-record>
        <txt-record>pdl=application/octet-stream,application/pdf,application/postscript,application/vnd.cups-raster,image/gif,image/jpeg,image/png,image/tiff,image/urf,text/html,text/plain,application/vnd.adobe-reader-postscript,application/vnd.cups-command</txt-record>
    </service>
</service-group>

Hinweis wenn ihr die Avahi-Service-Datei manuell ohne Script erstellt:
  • _ipp._tcp = LPD/LPR-Protokoll wird verwendet
  • 631 = Portnummer auf der LPD lauscht
  • rp=printers/Hewlett-Packard-HP-Color-LaserJet-CP2025dn = Name der Cups Warteschlange (siehe /etc/printcap)

Danach kann das Script entfernt werden:
rm airprint-generate.py
Beim Drucken muss nur der PC eingeschaltet sein und ein Login ist nicht notwendig. FAX versenden funktioniert nur mit Login und
gestarteten Roger-Router, da die Eingabe der Zielfaxnummer am Linux PC und nicht auf dem Apple Gerät erfolgt.

Screenshot vom iPhone:




#35
LINUX / Master PDF Editor
Letzter Beitrag von Jo - 2020-03-01 | 08:35:01
getestet mit Linux Manjaro KDE 2020-02 und 2021-04

Master PDF Editor 4 ist eine kostenlose proprietäre Anwendung zur Bearbeitung von PDF-Dokumenten unter Linux, Windows und MacOS. Er kann PDF-Dokumente erstellen, bearbeiten, Text oder Bilder einfügen, lesen und ausfüllen von XFA-Formularen, kommentieren, anzeigen, verschlüsseln und signieren.

Mit der Version Master PDF Editor 5 wurden einige Funktionen aus seiner kostenlosen Version 4 entfernt, wie z.B. das Bearbeiten oder Hinzufügen von Text, das Einfügen von Bildern und vieles mehr - bei der Verwendung solcher Werkzeuge fügt die Anwendung ein großes Wasserzeichen in das PDF-Dokument ein, es sei denn, der Benutzer kauft die Vollversion (ca. 70€).

Leider ist die 5er Vollversion das einzigste PDF-Programm das ich kenne, welches es voll mit dem Adobe Acrobat DC für Linux, macOS oder Windows  aufnehmen kann und z.B. PDF Formulare ausfüllen und entsprechende Felder berechnen kann.

Der Master PDF Editor 4, ist für die nicht-kommerzielle Nutzung mit wenigen Einschränkungen kostenlos (zumindest unter Linux) und kann immer noch heruntergeladen werden, auch wenn er nicht auf der offiziellen Website der Anwendung verlinkt ist.

Download Version 4.3.89: master-pdf-editor-4.3.89_qt5.amd64.tar.gz (Qt 5.4.1, 64-Bit)

Nach dem Download entpacken und den Ordner in euer ~/bin (/home/[USER]/bin) verschieben. Dafür sind keine Root-Rechte notwendig! Die Datei masterpdfeditor4 ist ausführbar und habe diese in masterpdfeditor4.sh umbenannt (alle meine ausführbaren Shell Scripts bekommen bei mir die Extension sh). Dann manuell ein Menüeintrag mit passendem Icon masterpdfeditor4.png) erstellen, Befehl: "~/bin/master-pdf-editor/masterpdfeditor4.sh", dananch die Dateizuordnung anpassen und alle PDF's starten mit dem Master PDF Editor.

PrintScreen KDE Menü:


Beim ersten Start erscheint die Meldung "Neue Version verfügbar! Jetzt herunterladen?". Dieses abbrechen und im Menü -> Werkzeuge -> Einstellungen -> Aktualisieren -> Updates auf "nie" setzen.

Wenn etwas nicht funktioniert, startet das Programm per Terminal um Fehlermeldungen zu sehen (evtl. euren Pfad anpassen):
./bin/master-pdf-editor/masterpdfeditor4.sh

Quelle und Abhängigkeiten siehe: aur.archlinux.org/packages/masterpdfeditor-free
(Master PDF Editor 4 und 5 sind im AUR Repository enthalten, jedoch bevorzuge ich die manuelle Installation unter /home ohne Root-Rechte)

#36
LINUX / TuTo: Manjaro (KDE)
Letzter Beitrag von Jo - 2020-01-26 | 11:42:38
letzte Anpassung 2024-Mai (Qt6 und VirtualBox 7.0.18)

LINUX MANJARO
Stabil mit immer aktueller Software
Basiert auf die leichtgewichtige Distribution Arch Linux
Viele aktuelle Desktops KDE, XFCE, GNOME, CINNAMON u.v.m.


VORWORT    direkt zum TUTORIAL

Sorry, das ist keine Anleitung für Anfänger, eher ein Nachschlagewerk für mich, andere können evtl. auch was damit anfangen und ein paar "Krümel" davon gebrauchen  :rolleyes:

Kurz (meine Meinung): Für alle Neueinsteiger oder wer einfach nur Anwender bleiben will und ein sehr stabiles Linux bevorzugt, sollte Linux Mint nutzen. Wer mehr Erfahrung mit Linux hat und ein stabiles Rolling-Release-Modell bevorzugt, kann sich Manjaro anschauen welches ich nutze aber Einsteiger nicht empfehlen würde.

Dank Knoppix, Ubuntu und Mint ist LINUX erfolgreich geworden. Eine Live-DVD oder USB-Stick zum testen und installieren ist mit der simplen Bedienoberfläche auch für Einsteiger geeignet. Mit solch einem LINUX Live-System habt ihr immer eine Rettungs DVD oder Stick zur Hand um z.B. eure Daten zu retten oder ins Internet zu gehen! Ich nutze seit vielen Jahren die Debian Distributionen, Ubuntu, Mint oder KDE neon und habe dabei verschiedene Desktops getestet. KDE, XFCE, GNOME, CINNAMON oder MATE - ist alles Geschmackssache und jeder kann sich sein Lieblings-Desktop installieren.

Ubuntu ist für mich heute nicht mehr was es zu Beginn war. Schlecht gepflegte Universe, versuch ein eigenes Init-System einzuführen, Amazon-Anbindung, schwieriges Verhältnis zur Open Source-Community und dann noch die Katastrophe mit dem UNITY-Desktop, was viele Ressourcen gekostet hat. Daher kann Ubuntu mich am Arch lecken. Wenn es denn Ubuntu sein soll, dann nehmt Mint, denn das ist inzwischen das bessere Ubuntu, leider aber auch davon abhängig.

Auf der Suche nach einer Alternative, die auch meinen Lieblings-Desktop KDE voll unterstützt, habe ich mich für Manjaro entschieden.

WARUM NUTZE ICH NUN MANJARO?
Erst mal möchte ich ein immer aktuelles und stabiles System haben. Manjaro lief selbst in meiner virtuellen Maschine schneller als mein damaliges KDE neon. Bootzeit meines PCs wie hier beschrieben dauert mit open-iscsi, Apache Web Server und MySQL ca. 10 Sekunden bis zur Anmeldung, weitere 3 Sekunden bis zum KDE Desktop, welcher sofort voll verfügbar ist. Das Laden von Anwendungen, wechseln zwischen den Anwendungen und booten des Computer ist einfach schneller. Wie kann ich die Geschwindigkeitsvorteile erklären? Evtl. liegt das an der Anzahl der Dienste und Daemons. Mit cups, samba, httpd, mariadb services und fstrim.timer sind das bei mir nur 22 Dienste, bei Ubuntu waren das 94 Dienste! OK ein paar kann ich deaktivieren, dennoch sind es viel mehr. Prüft es selbst:
systemctl list-unit-files --state=enabled --no-pager
Manjaro ist eine auf Arch Linux basierende Linux-Distribution, die in Deutschland, Frankreich und Österreich entwickelt wird. Es ist in erster Linie ein freies Betriebssystem für Personal Computer, welches auf Benutzerfreundlichkeit ausgerichtet ist. Wie seine Basis, Arch Linux, nutzt es ein Rolling-Release-Modell. Jedoch nimmt Manjaro das meiste Risiko aus dem Rolling-Release-Modell heraus, indem es die Veröffentlichung neuer Anwendungen und Funktionen um mehrere Wochen verzögert. Sobald diese getestet und als sicher erwiesen wurden, werden sie zur Verfügung gestellt.

HAUPTMERKMALE
Manjaro teilt viele Eigenschaften mit Arch. Hierzu gehören insbesondere:
  • Geschwindigkeit, Stärke und Effizienz
  • Zugang zu neuer und neuester Software, oftmals bevor die Pakete für andere Distributionen erhältlich sind
  • Manjaro ist ebenfalls ein Rolling Release, so dass jeweils die neueste Software installiert werden kann ohne dass die Notwendigkeit bestünde, auch ein neues System zu installieren
  • Zugang zu von Arch-Nutzern bereit gestellten Paketen (AUR) -> ist per Default deaktiviert, lässt sich leicht aktivieren, Anfänger sollten sich mit AUR erst vetraut machen

Allerdings besitzt Manjaro auch einige Eigenschaften, die es von Arch deutlich unterscheiden, insbesondere:
  • Eine einfachere und benutzerfreundlichere Installationsroutine
  • Automatische Hardwarerkennung, bspw. der Grafikkarte
  • Automatische Installation der Software, die für das Funktionieren des Computers benötigt werden, etwa von Grafiktreibern
  • Manjaro hat ein eigenes Software-Archiv (stable-Repository), um sicherzustellen, dass die Benutzer Zugang zu vollständig getesteter und stabiler Software erhalten, nimmt also in Bezug auf Aktualität der Pakete etwas mehr Abstand von Arch
  • Unterstützung bei der Installation und Benutzung mehrerer Kernel (ich nutze nur LTS-Kernel)

Quelle: wiki.manjaro.org

Mit Manjaro bekommt ihr neueste Technologie, die fertig entwickelt und umfassend getestet wurde (Cutting Edge). Beispiel: Manjaro hatte KDE Plasma 5.18 / 5.19 nicht sofort zur Verfügung gestellt, sondern erst mit dem drittes Release (5.18.3 / 5.19.3), welches die meisten der gemeldeten Probleme behebt. Dieses Rolling-Release-Modell bleibt immer aktuell und stabil. Bedeutet daher auch öfters größere Updates, was eine schnelle Internetverbindung voraussetzt. Ebenso sollte mindestens einmal im Monat Manjaro upgedatet werden, sonst kann es zu Problemen kommen.

Nicht jeder möchte immer das Neuste haben, selbst wenn umfassend getestet könnte das manche Anwender irritieren? Privat sollte das kein Problem sein, aber im Geschäftsbetrieb könnten die vielen Updates stören. Mitarbeiter die gerne kritisieren, weil sie der Meinung sind das Windows besser ist, fühlen sich dann bestätigt. Wobei bei Windows 10/11 die Datensammlungswut und die Mega-Updates nur noch nervig sind. Das ist echte Arbeitsverhinderung die es so bei Linux nicht gibt! Egal ob Windows, Linux oder MAC, viele Anwender sind froh wenn sie die benötigen Programme einigermaßen beherrschen. Wenn dann mal etwas auf englisch erscheint oder ein Programm eine andere Oberfläche hat, wird gemault und stört den Büroalltag. In dem Fall würde ich ein Linux LTS wie z.B. Linux MINT nehmen, welches 5 Jahre Langzeitsupport bietet.

Als fast-nicht-Gamer benutze ich vorrangig Intel Onboard Grafikprozessoren (GPU), z.B. UHD 630 welche an meinem 4K-Monitor out-of-the-box problemlos läuft. Ein Sache zu den Nvidia- und AMD-Treiber: Die Nvidia free-Variante installiert als Open-Source-Treiber das sogenannte Nouveau-Paket. Dieses ist ein Produkt aus Reverse Engineering vieler Freiwilliger, bei dem jedoch die Spiele-Performance fehlt. Die non-free-Variante ist schneller aber leider auch anfällig für Fehler. Als Gamer würde ich daher bevorzugt eine AMD Grafikkarten zulegen. AMD stellt im Gegensatz zu Nvidia das schnelle und stabile AMDGPU (opensource) Treibermodul für den Linuxkernel zur Verfügung. Dieser ist fester Bestandteil des Kernels und somit auf dem System ebenfalls out-of-the-box vorhanden.




TUTORIAL
Hier mein TuTo um Manjaro mit KDE auf einer leeren Festplatte (kann auch während der Einrichtung gelöscht werden) mit /home auf eine extra Partition zu installieren. Die Installation auf einer SSD Festplatte hat keine 5 Minuten gedauert! Die Bilder aus meiner VM zeigt die Testinstallation von Manjaro auf einer virtuellen 30GB Festplatte.

INHALT
Manjaro installieren
Tipps damit Manjaro lange läuft
Optimieren und pflegen
Paketverwaltungsbefehle
Programme deinstallieren & installieren
Kernel Crash?
SSD optimieren
VirtualBox installieren
Webserver installieren und einrichten (lokal)
Paketliste und System wiederherstellen (oder nur die Chronik anzeigen)
KWalletManager: Passwörter aus Backup wiederherstellen
Anhang: Neuinstallation auf bestehendes LINUX ohne die /home Partition zu formatieren


1 ) Download Manjaro KDE Plasma 64 bit Version (Live Image), testen und installieren
Ich wähle die minimal Basis-Desktop-Umgebung mit LTS-Kernel ohne vorinstallierte zusätzliche Softwarepakete aus (Minimal Long Term Support Kernel with no additional software packages pre-installed), Download Link.


(z.B.: manjaro-kde-21.2.0-minimal-211220-linux510.iso | Stand 2021-12-20)

Wichtig: Erstellt vor der Installation ein Backup!

Das Live-Image habe ich mit dd (disk dump) auf einen USB-Stick kopiert. Unetbootin funktioniert anscheinend mit Efi nicht (komme beim booten immer nur in grub rescue). Unter Windows soll das mit Rufus und dem DD-Modus funktionieren (ungetestet). Ich habe das per Terminal wie folgt getan.

ACHTUNG! Beschreibt das richtige Laufwerk und listet dafür die Partitionen auf, um den Pfad für das USB-Laufwerk zu ermitteln:
sudo fdisk -l(bei mir ist das "/dev/sde1")

Sicherstellen das dieses USB-Gerät ausgehängt ist:
sudo umount /dev/sde1
ISO-Datei auf USB-Gerät schreiben. Den Pfad zur ISO-Datei (bei mir "Downloads") und Dateiname anpassen.
Als USB-Gerät nicht die Partitionsnummer "/dev/sde1" angeben, sondern "/dev/sde" (also ohne Zahl).
Beispiel Manjaro KDE 21.2.0 minimal (wenn die Version neuer ist, muss natürlich der Dateinamen angepasst werden):
sudo dd bs=4M if=~/Downloads/manjaro-kde-21.2.0-minimal-211220-linux510.iso of=/dev/sde status=progress oflag=sync
Hinweis: In Manjaro selbst könnt ihr dafür den Suse Studio Imagewriter nutzen (sudo pacman -S imagewriter) oder Mintstick von Linuxmint (sudo pacman -S mintstick).
Link: Dual Boot mit Windows nutzen (brauche ich nicht, benötige Win10 sehr selten und wenn dann via VM).

Beim Starten vom Live-Image per VM hatte ich ca. 2 Minuten einen schwarzen Bildschirm, also etwas Geduld und ihr könnt Manjaro testen, im echten System ist das viel schneller.


Wenn das Netzwerk, Soundkarte usw. funktioniert, einfach auf das Icon "Install Manjaro Linux" klicken.





Zwei btrfs-Partitionen manuell anlegen. Swap-Partition in Testumgebung nicht notwendig (seit Kernel 5 kann eine swap-Datei nachträglich erstellt werden):
  • / (root - flagged as boot) sollte ca. 40GB groß sein, der Rest ist dann für /home (hier nur 10GB, da das eine Testumgebung ist)
  • /home verschlüsselt mit LUKS

Habe zum Testen die Home-Partition mit LUKS (dm-crypt) verschlüsselt, Nachteil: Nach der Installation erscheint die Passwortabfrage für die Home-Partition während des Boot-Prozesses, bei einem One-User System melde ich mich daher automatisch an um nicht 2x ein Passwort angeben zu müssen. Mit PAM lässt sich das automatisch einbinden, setzt jedoch gute Linux-Kenntnisse voraus.

Diese Verschlüsselung verhindert das jemand eure Festplatte ausbaut oder mit einem Live System auf eure Daten zugreifen kann. Wenn das System gebootet ist, ist daher alles entschlüsselt! Siehe auch Härten.

Möchtet ihr wichtige Daten sicher auch nach dem Anmelden verstecken, könnt ihr unter KDE mit Plasma Vault Ordner per CryFS oder GocryptFS nachträglich sicher verschlüsseln. Auch cool, z.B. kann beim Öffnen eines Vault-Ordner das Netzwerk und Bluetooth automatisch deaktiviert werden. GocryptFS wurde von EncFS inspiriert und hat den Anspruch, Schwachstellen von EncFS zu beheben.



Hinweis: Bei einem Lenovo Flex 2-15 Notebook mit 500GB Festplatte und 4GB RAM habe ich das wie folgt getan.
  • Im Bios Setup (Fn & F2 beim Booten halten), "Boot Mode: Legacy Support" und "Boot Priority: Legacy First" setzen, "SATA: AHCI" dürfte klar sein und "Intel Virtual Technology: Enabled" wenn eine VM installiert werden soll.
  • Manjaro wurde mit GPT-Partitionierung (anstatt MBR) installiert. Ohne EFI wird eine 8MB (8MiB) unformatierte Partition mit der Markierung bios_grub (flag) benötigt und muss die allererste Partition auf der Festplatte sein! Dann eine 8GB (8096MiB) Swap Partition, 50GB (50000MiB) root (ext4) und den Rest für /home (ext4) angelegt.

Nachtrag: Partitionen meiner NVMe SSD die kein Legacy-BIOS-Modus unterstützt. Sicherstellen, dass Secure Boot und Windows Fast Boot im UEFI-Firmware-Setup deaktiviert sind und das UEFI so eingestellt ist, dass nur im UEFI-Modus gebootet wird, während CSM (Legacy-BIOS-Modus) deaktiviert ist. Mit UEFI BOOT via GPT anstatt MBR befindet sich der zugehörige Boot Loader auf der EFI System Partition (ESP): 100MB/FAT32 /boot/efi (Flag: "boot" und "esp") | root | /home | ohne swap
Da die manuelle Partitionierung mit dem Calamares-Installer grauenhaft ist, nutze ich inzwischen dafür GParted (sudo pacman -S gparted) und partitioniere meine Festplatte vor dem Installieren.

Siehe auch meinen Kenko Mini H155S PC von Silentmaxx.







2 ) PAMAC
Nach dem Start kann mit Pamac alles aktualisiert werden und mit dem Einstellungsmanager z.B. zusätzliche Sprachpakete installiert werden. Im Kontextmenü Optionen (Manjaro Notifier KDE Settings) können die Kernel-Benachrichtigungen angepasst werden, ich lasse nur bei LTS-Kernel benachrichtigen.


Bei einer Installation fehlte bei mir der Einstellungsmanager und das Icon in der Taskleiste (siehe Problem with background service manager kded5), dann das Tray-Icon und den fehlenden Daemon nachinstallieren:
sudo pacman -S kded pamac-tray-icon-plasma
Pamac ist ein grafischer Paketmanager von Manjaro und als Unterbau dient Pacman, welches ich per Kommandozeile im Terminal nutze. Dieser beherrscht auch die Installation von Paketen über das AUR (Arch User Repositories), welches von einer Gemeinschaft verwaltet wird und kann in den Einstellungen aktiviert werden. AUR Benutzer sollten mit dem Build-Prozess vertraut sein. Tatsächlich ist die AUR-Unterstützung deaktiviert (Standardeinstellung) und muss manuell aktiviert werden. Im Prinzip ist AUR das Pendant zu Ubuntus PPA's. Linux Anfänger und normale Benutzer empfehle ich Pakete nur aus den Manjaro Software Repositories zu installieren und wenn möglich nie aus dem AUR Pakete zu installieren.

Aktualisiere alle installierten Pakete, die aus den Repos oder dem AUR kommen per Pamac CLI:
pamac upgrade -aSicherer Weg um alte Paket-Cache-Dateien zu entfernen, mit Ausnahme der letzten zwei Paketversionen:
pamac clean --keep 2in einer Zeile:
pamac upgrade -a && sudo pamac clean --keep 2
Wenn eine Fehlermeldung wie z.B. "Kann Datenbank nicht sperren" erscheint:
Vorbereitung...
Synchronisiere Paketdatenbanken...
Kann Datenbank nicht sperren
Fehler beim Synchronisieren der Datenbanken
Es gibt nichts zu tun.
Vorgang erfolgreich abgeschlossen.
Lösung:
sudo rm /var/tmp/pamac/dbs/db.lck
Pacman verwaltet Binärpakete die aus den Repositorys stammen und hält das System aktuell, indem die Paketlisten mit einem Server synchronisiert werden. Durch dieses Server/Client-Modell ist es möglich, Pakete mit allen Abhängigkeiten herunterzuladen, zu installieren bzw. zu aktualisieren.
Diese Seite kann bei einem Problem hilfreich sein: archlinux.de/news oder manjaro.org/c/announcements


3 ) Grub anpassen, z.B.:
kate /etc/default/grubGRUB_DEFAULT=0
GRUB_TIMEOUT=2
GRUB_TIMEOUT_STYLE=menu
GRUB_DISTRIBUTOR="Manjaro"
GRUB_CMDLINE_LINUX_DEFAULT="noplymouth resume=UUID=xxxxxxxxxxxxxxx udev.log_priority=3"
GRUB_CMDLINE_LINUX=""
GRUB_SAVEDEFAULT="false"

Wichtig: "resume=UUID=xxxxx bla bla bla" stehen lassen - wichtig wenn Hibernate genutzt wird!
(ich bevorzuge die Anzeige der Kernel-Meldungen während des Bootvorgangs, daher  das "noplymouth" anstatt "quiet")

Dann Grub aktualisieren und den PC neu starten:
sudo update-grub
Ich möchte die Kernelmeldungen beim Ladeprozess mitverfolgen und 2 Sekunden das Grub Menü sehen, um notfalls einen älteren Kernel zu starten (wenn unterdrückt, beim Booten die linke Shift oder Esc Taste festhalten).

Wenn btrfs genutzt wird und beim starten die Fehlermeldung sparse file not allowed erscheint, muss "GRUB_SAVEDEFAULT" deaktiviert werden. Das Abspeichern funktioniert aus Sicherheitsgründen nicht auf einem RAID-Verbund, einem LVM-Dateisystem, einem btrfs-Dateisystem oder einem ZFS-Dateisystem (Quelle: GNU GRUB MANUAL).

4 ) SWAP-DATEI
Anstelle einer dedizierten swap-Partition kann seit dem Kernel 5 im btrfs-Filesystem eine Auslagerungsdatei nachträglich erstellt werden. Quelle: Swapfiles on BTRFS

z.B. eine 8GB swap-Datei anlegen (gleiche Größe wie RAM verfügbar ist, ab 8GB erhöhe ich das nicht mehr), die Reihenfolge ist wichtig:
sudo truncate -s 0 /swapfile
sudo chattr +C /swapfile
sudo btrfs property set /swapfile compression none
sudo fallocate -l 8G /swapfile
sudo mkswap /swapfile
sudo chmod 600 /swapfile
sudo swapon /swapfile
sudo bash -c "echo /swapfile none swap defaults 0 0 >> /etc/fstab"
Eintrag in der fstab kontrollieren:
kate /etc/fstabPC neu starten und prüfen:
swapon -sTipp: Das KDE-Infozentrum zeigt die Speicherbelegung und viele andere Information zum System grafisch an.

Eine swap-Datei kann so entfernt werden:
sudo swapoff /swapfile
sudo rm -f /swapfile
Eintrag aus der fstab entfernen oder ausklammern:
kate /etc/fstabPC neu starten.

Tipps damit Manjaro lange läuft (ohne Gewähr, mehrere Manjaro KDE Installationen rennen so bei mir seit über 4 Jahren fast problemlos):
Härtet euren PC und verzichtet nach Möglichkeit auf AUR Pakete. Third-Party Software aus unbekannten Quellen sind ein No-Go, also Tabu!
Updatet wenigstens einmal im Monat per Terminal oder Skript KDEtweaksManjaro.sh im Anhang (siehe auch Paketverwaltungsbefehle):
sudo pacman-mirrors --country Germany,France,Austria && sudo pacman -Syyuu && sudo paccache -rk2(das synchronisiert die Spiegelserver aus 3 Ländern, Update und aufräumen in nur einer Zeile)

Wer ganz sicher gehen will nutzt die Shell per ALT+STRG+F2 ohne Desktop dafür, dann einloggen und
sudo pacman -Syyuu && sudo paccache -rk2wenn alles fertig ist wieder raus aus der Shell mit ALT+STRG+F7 oder besser den PC neu starten, besonders nach einem Kernel Update:
sudo reboot
Bei grösseren Updates lese ich erst die Manjaro Announcements Seite und prüfe ob evtl. mit Problemen zu rechnen ist - hier werden dann auch Lösungen gezeigt.

Sollte der Pamac Paketmanager Probleme bei Updates machen, kann das helfen:
sudo pacman -Scc(alle Pakete im Pacman Cache werden vollständig entfernt - die 2 Fragen mit "j" bestätigen)

Ich nutze nur LTS Kernel, einen aktuellen und den vorherigen um eventuell einem Kernel Crash vorzubeugen!

Root-Rechte?! Für viele Einsteiger ist es verwirrend, dass Dateien in Systemordnern nicht ohne weiteres z.B. mit einem grafischen Dateimanager wie z.B. Dolphin bearbeitet oder kopiert werden können. Diese Einschränkung ist ein essentieller Baustein des Sicherheitskonzepts von Linux. Hierbei würde die Grafikanwendung (GUI) auch Konfigurationsdateien mit Root-Rechten im Basisordner /home speichern, was unweigerlich zu Problemen führen wird. Merke: Für Anwendungen mit einer GUI, nie sudo benutzen!

So das war es eigentlich, mit dem GUI Pamac könnt ihr noch fehlende Software installieren oder deinstallieren. Viel Freude mit Manjaro!

:bounce:  :bounce:  :bounce:






Infos und Details zu Manjaro KDE
So wie ich KDE mit Manjaro nutze, evtl. ist was für euch dabei?

Version prüfen per Terminal:
lsb_release -aoder
neofetch

Ausgabe Basisinformationen:
inxi -Fz(der Schalter -z blendet persönliche Infos wie z.B. MAC oder IP aus, also Forum geeignet)
Ausgabe vollständiger Systeminformationen:
inxi -v8per KDE-Infozentrum


5 ) KDE Systemeinstellungen nach eigenen Bedarf und Wünschen anpassen, z.B.
  • Manjaro -> Hardwarekonfiguration, Kernel und Sprachpakete prüfen
  • Erscheinungsbild -> Globales Design und Stile  -> Breath
  • Erscheinungsbild -> Schriftarten  -> Wer einen 2K (QHD) oder 4K (UHD) Monitor benutzt kann hier die DPI für Schriften anpassen, z.B. hat ein 4K Monitor Dell U3219Q laut Techn. Datenblatt 140 DPI (wer keine Daten hat kann das leicht ausrechnen, Link DPI-Rechner)
  • Erscheinungsbild -> Symbole  -> Ab einem 4K (UHD) Monitor setze ich die Symbolgröße für jedes Icon eine Stufe höher
  • Hinweis: Einfacher ist das dem Schieberegler unter Hardware -> Anzeige und Monitor -> Anzeige-Einrichtung -> Globale Skalierung (das passt auch die DPI für Schriften an)
  • Arbeitsbereich -> Verhalten des Arbeitsbereichs -> Allgemeines Verhalten -> Klick-Verhalten: Doppelklick zum Öffnen der Dateien/Ordner
  • Arbeitsbereich -> Verhalten des Arbeitsbereichs -> Bildschirmsperre -> Aktivierung: 5 Min. | 300 Sek. | Meta+L | Erscheinungsbild: Diaschau, Virtuelle Arbeitsflächen 2
  • Arbeitsbereich ->Verhalten des Arbeitsbereichs -> Aktivitäten: Privatsphäre Verlauf für 1 Monat behalten oder "Nicht merken"
  • Arbeitsbereich -> Fensterverwaltung -> Fensterverhalten, im TAB "Fensteraktionen" Sondertaste: "Meta" (wichtig wenn ihr z.B. VirtualBox mit Windows benutzt)
  • Arbeitsbereich -> Starten und Beenden -> Anmeldeschirm (SDDM) -> Breath
  • Arbeitsbereich -> Starten und Beenden -> Arbeitsflächen-Sitzung: Abmeldung bestätigen aus, Rechner ausschalten, Mit leerer Sitzung starten
  • Arbeitsbereich -> Starten und Beenden -> Startbildschirm -> Breath
  • Arbeitsbereich -> Suchen -> Dateisuche: habe hier alles deaktiviert (beendet den baloo_file_extractor Prozess und die Suche nach Dateinamen funktioniert weiterhin; Indexinformationen löschen: rm -rf ~/.local/share/baloo)
  • Persönliche Informationen -> Benutzerkontodetails -> KDE-Passwortspeicher: Bei Nichtgebrauch schließen nach: 180 Min.
  • Persönliche Informationen -> Regionaleinstellungen -> Sprache: Deutsch, Rechtschreibprüfung: Deutsch (Deutschland)
  • Persönliche Informationen -> Regionaleinstellungen -> Datum & Zeit: Datum und Uhrzeit automatisch einstellen
  • Persönliche Informationen -> Anwendungen -> Standard-Anwendungen: Webbrowser: firefox (evtl. chrome oder palemoon?) / E-Mail-Programm (11/12): kmail (evtl. evolution oder thunderbird?)
  • Persönliche Informationen -> Anwendungen -> Dateizuordnungen: hier die gewünschte Standardprogramme anpassen z.B. für audio, image und video
  • Netzwerk -> Verbindungen: Hier könnt ihr LAN, WLAN oder z.B. VPN mit OpenConnect einrichten (Clientseitig getestet mit einem VASCO Token)
  • Netzwerk -> Bluetooth -> Erweiterte Einstellungen: Bluetooth-Integration aktivieren oder deaktivieren
  • Hardware -> Eingabegeräte -> Tastatur: Zahlenblock beim Plasma Start, Maus: Zeigebeschleunigung anpassen
  • Hardware -> Anzeige und Monitor -> Compositor: Hier nutze ich anstatt OpenGL 2.0 die Version OpenGL 3.1
  • Hardware -> Energieverwaltung -> Bildschirm-Energieverwaltung -> Ausschalten nach: 240 Min. / Wenn der Ausschalt-Knopf betätigt wird: Herunterfahren
  • Hardware -> Wechselmedien -> Automatisches Einhängen von Wechselmedien aktivieren

Optional die KDE Benachrichtigungen einrichten (Sound bei bestimmten Ereignissen):
Persönliche Informationen -> Benachrichtigungen -> Anwendungen: Einrichten .., dann Systemdienste -> KDE-Plasma-Arbeitsbereich: Ereignisse einrichten ...

Tipps: Alte Hardware oder lahme Grafikkarte? Dann schaltet die Desktop Effekte aus: Hardware -> Anzeige und Monitor -> Compositor. Die Diaschau ist eine schöne Alternative zum alten Bildschirmschoner / Screensaver welche es zu Röhrenbildschirm-Zeiten gab (CRT).

6 ) Paketverwaltungsbefehle
KDEtweaksManjaro.sh als ZIP-Datei im Anhang (seit V21.06.011 nutze ich dafür pamac upgrade)
Link einer Tabelle mit Paketverwaltungsbefehle einiger Linux-Distributionen, z.B.:
Komplette System-Aktualisierung:
sudo pacman -Syyuuwenn Pakete aus dem AUR installiert wurden (benötigt yay, siehe Punkt 10 ):
yay -SyyuuManjaro sauber halten (lässt zwei Versionen der Pakete für den Fall, dass ein Downgrade durchgeführt werden muss):
sudo paccache -rk2(siehe auch Automatische Cache-Wartung)

ALLES in einer Zeile und nicht mehr benötigte Abhängigkeiten anzeigen[ (verwaiste Pakete):
sudo pacman -Syyuu && sudo paccache -rk2 && sudo pacman -Qdtq
oder ALLES in einer Zeile wenn ihr zusätzlich AUR-Upgrade nutzten wollt:
yay -Syyuu && sudo paccache -rk2 && sudo pacman -Qdtq("Failed to parse JSON" erscheint wenn kein AUR genutzt wird)

Verwaiste Pakete entfernen:
sudo pacman -Rsn $(pacman -Qdtq)
Sollte der Pamac Paketmanager Probleme bei Updates machen, kann das helfen:
sudo pacman -Scc(alle Pakete im Pacman Cache werden vollständig entfernt - die 2 Fragen mit "j" bestätigen)

dann aktuelle Spiegelserver aus diesen 3 Ländern speichern und alles synchronisieren (nutze ich so da schneller, siehe auch Pacman-mirrors)
sudo pacman-mirrors --country Germany,France,Austria && sudo pacman -Syyuu(Mirrorliste wrd hier gespeichert: /etc/pacman.d/mirrorlist)

Automatische Cache-Wartung:
Der Pacman Cache (/var/cache/pacman/pkg/) wird standardmäßig per pamac-cleancache.timer einmal im Monat entfernt, ansonsten wird die Partition irgendwann voll. Details siehe /usr/lib/systemd/system/pamac-cleancache.timer (Timer einmal im Monat in Kombination mit Persistent=true). Prüfen ob dieser Timer aktiv ist:
systemctl list-timers(oder Systemeinstellungen -> Systemverwaltung -> Systemd -> Timers)
wenn dieser Timer fehlt:
sudo systemctl enable pamac-cleancache.timer
sudo systemctl start pamac-cleancache.timer

Pkgfile:
Mit pkgfile können die Pakete der offiziellen Repositorien nach Dateien durchsucht werden. Eine ähnliche Funktionalität ist auch in pacman (Option -F und Folgeoptionen) eingebaut, aber alternativ kann weiterhin pkgfile verwendet werden. Irgendwann ist mir ein sporadische Fehler (failed to start pkgfile database update) aufgefallen. Bei einer Installation hatte ich eine KDE-Edition mit git-Paketen erwischt bei dem der Systemd Service pkgfile-update.timer aktiviert war (welcher eigentlich deaktiviert ist). Da ich das nicht benötige habe ich diesen Service wieder deaktiviert (also wie 'default'). Vorgehensweise:
Wird pkgfile verwendet?
systemctl | grep pkgfileWenn ja, können wir nach allem suchen, was sich auf pkgfile verlässt:
pacman -Qi pkgfile | grep RequiredWenn niemand die pkgfile Datenbank benötigt, kann Systemd Service pkgfile-update.timer deaktiviert werden (oder nutzt diesen Workaround):
sudo systemctl disable pkgfile-update.timer(wieder aktivieren: sudo systemctl enable pkgfile-update.timer)

7 ) Deinstallieren, z.B. Yakuake (drop-down Terminal):
sudo pacman -Rns yakuake
8 ) Mozilla Firefox Add-ons und härten
  • DNS-over-HTTPS (DoH). Inzwischen laufen fast alle Webseiten über HTTPS (SSL) und Provider können nicht sehen welche Daten wir übermitteln, besonders Benutzername und Passwort. Jedoch sind die Verbindung zum DNS-Server immer noch unverschlüsselt und der Provider kann diese in Klarschrift mitlesen. Lösung: DoH aktivieren, im Menü unter Einstellungen -> Verbindungs-Einstellungen, hier die Checkbox "DNS über HTTPS aktivieren" einschalten und als Anbieter z.B. Cloudflare wählen oder benutzerdefiniert "https://dnsforge.de/dns-query" von dnsforge.de eintragen (deutscher Server mit Werbefiter). Mit der FritzBox ab V7.2 könnt ihr euer Heimnetz global per DoT die DNS Abfragen verschlüsseln (Link).
  • Werbeblocker uBlock Origin (Werbung blocken, schneller laden und Seiten sicherer machen!)
  • Cookies Info löschen (EU-Cookie-Irrsinn blocken!) oder per uBlock Origin in der Filterliste »Belästigungen« die Liste "EasyList Cookie" aktivieren
  • Privacy Badger unterdrückt Werbe-Tracker
  • Nutze VPN ohne WebRTC, jemand könnte damit die wirkliche IP herausfinden. Deaktivieren: about:config -> media.peerconnection.enabled = false
  • Canvas Fingerprinting blockieren (siehe Wiki Canvas_Fingerprinting und zum Testen browserleaks.com)
  • Web Developer (Entwickler Tools für Internetseiten)
  • Foxy Gestures (z.b. Klickgesten zurück/vor: Enable chord gestures)
  • JScript Toggle On and Off (JavaScript ein- und ausschalten)
  • Firefox härten mit firejail (Profil ist vorhanden), Anwendung starten mit: firejail firefox %u

Hinweis: Es ist nahezu unmöglich, die User-Agent Kennung plausibel in allen Punkten zu faken und ein unvollständiger Fake-Versuch kann ein gutes Identifizierungsmerkmal für Trackingdienste sein, da man sich von der großen Masse der Surfer stärker unterscheidet.

Nachtrag zu Firejail mit dem Mozilla Firefox. Folgende Zeilen habe ich in meiner firefox.local eingegeben, um den Zugriff auf gemeinsame Programme/Addons/Plugins und plasma-browser-integration zu ermöglichen. Wenn diese config noch nicht vorhanden ist:
mkdir ~/.config/firejail/dann mit einem Editor öffnen:
kate ~/.config/firejail/firefox.localund folgendes Eintragen:
# Quellen:
# /etc/firejail/firefox.profile
# /etc/firejail/firefox-common.profile
#
# ~/.config/firejail/firefox.local
#
#
# Add the next lines to your firefox.local for plasma-browser-integration.
dbus-user.own org.mpris.MediaPlayer2.plasma-browser-integration
dbus-user.talk org.kde.JobViewServer
dbus-user.talk org.kde.kuiserver
#
# Add the next line to your firefox-common.local to allow access to common programs/addons/plugins.
include firefox-common-addons.profile

9a ) Evtl. Pale Moon Browser als Firefox Alternative
sudo pacman -S palemoon
  • deutsches Sprachpaket, beachte die Infos dort (about:config -> general.useragent.locale von "en-US" auf "de" setzen)
  • in den Pale Moon Einstellungen (Erweitert), die Updates deaktivieren, das übernimmt das Linuxsystem
  • Pale Moon unterstützt keine WebExtensions, daher funktioniert nur das ältere deutsche Wörterbuch Version 2.0.6 (german_dictionary-2.0.6-an+fx+sm+tb.xpi im Anhang)
  • uBlock Origin (direkt von github, sucht Latest release: uBlock0.firefox-legacy.xpi)
  • uBlock Origin Updater (damit wird uBlock Origin automatisch aktualisiert)
  • Canvas Fingerprinting verhindern: about:config -> canvas.poisondata auf "true" setzen, es gibt auch eine Erweiterung dazu: canvasblocker-legacy (meine Block Mode Einstellung: fake readout API)
  • Toggle JavaScript (Enabled/Disabled)
  • i-dont-care-about-cookies (entfernt lästige Cookie-Warnungen) oder per uBlock Origin in der Filterliste »Belästigungen« die Liste "EasyList Cookie" aktivieren
  • Pale Moon härten mit firejail (Profil ist vorhanden), Anwendung starten mit: firejail palemoon %u

Hinweis: Pale Moon ist ein alternativer Web-Browser und nutze den gerne fürs Banking. Einige Websites halten diesen manchmal für veraltet und senden tatsächlich eine Seite mit der Meldung: "Ihr Browser ist veraltet. Bitte aktualisieren Sie auf einen modernen Browser, um diese Seite nutzen zu können". Das ist natürlich Unsinn und ich bin mit dieser Einschätzung nicht einverstanden. Pale Moon hat die Möglichkeit den User-Agent für bestimmte Domains zu ändern. Einfach einen neuen Eintrag auf der about:config Seite machen. Sucht nach "general.useragent.override", dann seht ihr eine Liste vorhandener Einstellungen und könnt einen neuen Eintrag mit gleicher Syntax einfügen, z.B.:
"general.useragent.override.MEINE-HAUS-BANK.de" mit dem String: "Mozilla/5.0 (X11; Linux x86_64; rv:97.0) Gecko/20100101 Firefox/97.0" (evtl. die Version anpassen, hier habe ich Firefox 97 eingetragen).

Nachtrag:
  • Ich nutze die Erweiterung "i-dont-care-about-cookies" nicht, funktioniert ist aber langsam. Dafür nutze ich die Filterliste »Belästigungen -> EasyList Cookie« in der uBlock Origin Erweiterung. Details siehe hier.
  • Meine Standardsuchmaschine ist startpage.com


Noch was zum Firejail, dieser kann in den gesamten Desktop integriert werden und jede Anwendung verwendet dann die Firejail-Sandbox, wenn sie standardmäßig unterstützt wird (nutze ich nicht!):
sudo firecfgRückgängig machen:
sudo firecfg --clean
Damit DRM z.B. mit Amazon Prime Video oder Apple Music funktioniert, muss die /etc/firejail/firejail.config Datei angepasst werden (Quelle). Sonst kommen Fehlermeldungen wie "content_equivalent" oder "Das Plugin "WidevineCdm" ist abgestürzt". Einfach per Terminal die Linie in der Config Datei aktivieren:
sudo sed -i 's/# browser-allow-drm no/browser-allow-drm yes/' /etc/firejail/firejail.config
9b ) Nutze seit Ende 2022 den Brave Browser als Firefox Alternative
pamac install brave-browserMehr ist nicht notwendig, Brave Shields und Tor ist enthalten. Ich nutze dazu nur die Erweiterung Tabs to the Front v2 um neue Tabs sofort und nicht mehr im Hintergrund zu öffnen.

Der Brave Browser ist ein kostenloser, quelloffener Webbrowser, der auf Chromium basiert und viele Vorteile bietet, wie schnelle Leistung, hohe Kompatibilität mit Websites und Erweiterungen sowie Funktionen zur Verbesserung der Privatsphäre und Sicherheit der Benutzer, einschließlich der Blockierung von Werbung, Trackern und Cookies von Drittanbietern. Der Browser bietet auch einen automatischen Tracking-Schutz namens Brave Shields, der ähnlich wie Firefox und der neue Edge funktioniert und Werbung blockiert. Lesezeichen können einfach zwischen verschiedenen Geräten zu synchronisieren. Dies bedeutet, dass Benutzer ihre Lesezeichen auf ihrem Computer, Smartphone oder Tablet synchronisieren können, um auf ihre bevorzugten Websites von überall aus zugreifen zu können. Die Synchronisation erfolgt über ein verschlüsseltes Netzwerk, um die Privatsphäre und Sicherheit der Benutzer zu gewährleisten.

10 ) Installiere diese Pakete (die ich benutze) auf deinem System, sofern sie noch nicht vorhanden sind:
sudo pacman -S --needed yay base-devel hunspell-de manjaro-printer system-config-printer cups-pdf libimobiledevice backintime-qt kolourpaint lame fdkaac audacity easytag mencoder frei0r-plugins devede vlc elisa gimp kfind kdf kwave mediainfo handbrake gthumb firejail pingus kmahjongg aisleriot libreoffice zip unzip unrar doublecmd plasma-vault cryfs encfs gocryptfs imagemagick dconf-editor geany htop meld kdialog imagewriter mintstick kompare ncdu gparted net-tools arp-scan dnsutils cifs-utils sqlite
Umstellung auf Qt6 (2024-Mai). Um sicherzustellen, dass die Qt6-Anwendungen gut aussehen und sich nahtlos in deine Desktop-Umgebung einfügen, solltest du folgende Pakete installieren (falls noch nicht geschehen):
sudo pacman -S --needed qt6ct qt6-wayland qt6-translationsNachdem du die notwendigen Pakete installiert hast, kannst du die Qt6-Einstellungen (qt6ct) anpassen. Achte darauf, die passende Konfigurationsvariable für Qt6 festzulegen, und füge diese Zeile ans Ende deiner ".bashrc" oder ".zshrc" Datei hinzu (je nachdem, welche du verwendest), damit sie bei jedem Start deiner Shell automatisch geladen wird:
# Set the Qt6 platform theme
export QT_QPA_PLATFORMTHEME=qt6ct
Lade anschließend die ".bashrc" oder ".zshrc" Datei neu, damit die Änderungen wirksam werden. Das kannst du tun, indem du den folgenden Befehl in deinem Terminal eingibst:
source ~/.zshrcoder
source ~/.bashrcNun sollte `qt6ct` korrekt konfiguriert sein und das Erscheinungsbild von Qt6-Anwendungen anpassen. Überprüfe, ob die Umgebungsvariable korrekt gesetzt ist:
echo $QT_QPA_PLATFORMTHEME
Timeshift, falls nicht installiert:
sudo pacman -S timeshift timeshift-autosnap-manjaro grub-btrfs
sudo update-grub
timeshift deinstallieren:
sudo pacman -Rsn timeshift timeshift-autosnap-manjaro grub-btrfs
sudo update-grub

Hinweis: Das btrfs Dateisystem unterstützt im Gegensatz zu ext4 Snapshots und wenn Manjaro mit btrfs installiert wird, ist automatisch Pacman gepatcht. Das gepatchte Pacman erstellt dann vor jedem Update automatisch Snapshots und trägt diese in grub-btrfs ein. Das bedeutet, wenn irgendetwas beim Update schief gegangen ist, dann wählt ihr in GRUB einfach "Manjaro mit erweiterten Optionen" -> "Snapshots" aus und ihr könnt in das vorherige (noch funktionierende) System booten. Vorteil: Zum Reparieren wird keine LiveCD/USB benötigt, allerdings setzt btrfs ein paar Grundkenntnisse im Umgang damit voraus, siehe z.B.: Was ist BtrFS. Wichtig ist zu beachten, dass Snapshots zusätzlichen Platz auf der Partition benötigen und keine Sicherungskopien im Sinne von Backups sind, siehe z.B. BackInTime. Daher hilft das gegen fehlerhafte Updates oder gelöschte Dateien, jedoch nicht gegen Festplattenschäden!

Solaar ist ein Linux-Manager für viele Logitech Eingabegeräte die sich direkt über ein USB-Kabel oder kabellos verbinden, z.B. Logitech Mouse MX Anywhere 3. Damit lässt sich das Gefühl des Scrollrads beim scrollen anpassen (Ratschenmodus / scroll force):
sudo pacman -S solaar
Steam ist ein Online-Store für Games und rennt nativ unter Manjaro:
sudo pacman -S steamCool, der Weltraumsimulator Universe Sandbox rennt damit unter Manjaro, hat jedoch eine hohe Systemanforderungen! Demos z.B. auf YouTube.
(Steam härten mit firejail (Profil ist vorhanden), Anwendung starten mit: firejail /usr/bin/steam-runtime %U)

Hinweis:
  • sollte nach einem KDE (qt5 oder qt6) oder Gnome (gtk2) Zweig bzw. Provider zum Auswählen gefragt werden, wählt KDE (qt5 oder qt6)
  • "LibreOffice Fresh" ist die stabile Version mit den neuesten Funktionen und "LibreOffice Still" ist die stabile Version, die (über einen längeren Zeitraum) mehr Tests unterzogen wurde
  • ich bevorzuge libimobiledevice und ifuse, damit können iOS-Gerät wie z.B. das iPhone als USB-Laufwerk eingebunden werden, sh Beispiele als ZIP-Datei unten im Anhang
  • KDEConnect gibt es inzwischen auch für iPhone/iPad und ist ziemlich gut geworden

sudo pacman -S ifuse
Wer Samba benötigt (Zugriff auf Dateifreigaben in gemischten Netzwerken, z.B. NAS):
sudo pacman -S samba smbclient kdenetwork-filesharing manjaro-settings-samba kio-fuseEin Samba-Passwort für euer Benutzerkonto erstellen: 'sudo smbpasswd -a $USER' (-a = add user | -x = delete user)
(Benutzter wird der user-group 'sambashare' hinzugefügt | Nachträglich möglich per 'sudo gpasswd -a $USER sambashare' | Kontrolle per 'groups' oder 'id')
Samba wieder entfernen:
sudo pacman -Rsn samba smbclient kdenetwork-filesharing manjaro-settings-samba kio-fuse
testparm prüft die Samba Konfigurationsdatei (smb.conf) auf interne Korrektheit:
$ testparm
Load smb config files from /etc/samba/smb.conf
Loaded services file OK.
Weak crypto is allowed
Server role: ROLE_STANDALONE

Press enter to see a dump of your service definitions

Das ttf-ms-fonts Paket für Windows-basierte Schriftarten (ich benötige keine dieser Schriftarten) ist in den Arch Repositorys enthalten und kann aus dem AUR installiert werden:
yay -S ttf-ms-fonts(von Microsoft freigegebenen Kern-Schriftarten für Windows)
Wenn die Fehlermeldung "cannot find the fakeroot binary" erscheint, müsst ihr das erst installieren (ist im base-devel Paket enthalten):
sudo pacman -S base-devel
Der LibreOffice Writer nervt seit V 6.2 und wird trotz löschen immer wieder in die Favoritenliste angelegt. Workaround:
rm -r ~/.local/share/kactivitymanagerd
kactivitymanagerd stop; killall plasmashell; kactivitymanagerd start; plasmashell &
Das löscht alle Aktivitäten und Favoriten! Dann die Favoriten neu anlegen.

Plugin Content Aware Healing für GIMP (Filter -> Verbessern -> Heal Selection...), enthalten in gimp-plugin-registry:
yay -S babl-git gegl-git gimp-plugin-registry
Brennprogramm und optionale Abhängigkeiten installieren:
sudo pacman -S k3b dvd+rw-tools emovix cdrdao transcode cdparanoia soxBenutzer der Gruppe optical hinzufügen:
sudo gpasswd -a $USER opticalPC neu starten, im K3b Programm die Einstellungen prüfen (K3b einrichten...), z.B. Temporärer Ordner habe ich auf "/tmp" festgelegt.

Videoeditor:
Avidemux ist für einfache Schneide- Filter- und Kodierungsaufgaben geeignet.
sudo pacman -S avidemux-qt
Mit Kdenlive ist es möglich, mehrere Bild- und Tonspuren zu bearbeiten und verwendet die MLT Video Rendering Engine.
sudo pacman -S kdenlive(Sollte es noch nicht geschehen sein, installiere auch qt6ct. Da Kdenlive nun auf Qt6 basiert, wird dies benötigt, damit z.B. der Color Picker funktioniert)


11 ) Druckfunktion aktivieren (benötigt manjaro-printer):
sudo systemctl enable --now cups.servicePC neu starten oder manuell die Druckfunktion starten:
sudo systemctl start cups.service(cups deaktivieren mit disable)
CUPS Web Interface: http://localhost:631

Standard Papierformat in der Datei /etc/papersize auf A4 setzen:
sudo sh -c "echo 'A4' > /etc/papersize"
CUPS entfernen (z.b. für ein Reset):
sudo systemctl disable --now cups.service
sudo pacman -Rsn manjaro-printer
pacman -Qi cups
sudo pacman -Rsn cups cups-pdf

Wenn nach einem CUPS-Update der Drucker oder die Seite http://localhost:631 nicht erreichbar ist, aktualisiert ihr die  Systemdienste wie folgt (Quelle):
sudo systemctl disable --now org.cups.cupsd.socket
sudo systemctl disable --now org.cups.cupsd.service
sudo systemctl disable --now org.cups.cupsd.path
sudo systemctl enable --now cups.service
sudo systemctl enable --now cups.socket
sudo systemctl enable --now cups.path
(der Dienst wurde vor einiger Zeit in nur cups umgemannt)

Prüfen ob CUPS läuft:
sudo systemctl status cups.service
E-Mail Programme Kontact oder Evolution ist Geschmackssache, finde beide gut da diese Programme Aliase, IMAP, CardDav, CalDav und openPGP nativ unterstützen:

12 ) Kontact ist ein Paket das die Programme KMail, KOrganizer und KAddressBook usw unter einem Hut vereint:
sudo pacman -S yay kontact kmail kaddressbook korganizer knotes akregator aspell-de kgpg
13 ) Evolution ist eine gute alternative das ich seit vielen Jahren nutze, Evolution ist ein Gnome E-Mail und -Kalender Programm welches auch sehr gut unter KDE läuft:
sudo pacman -S evolution gnome-keyring seahorse gnupg kgpg(anstatt kgpg könnt ihr auch gpa installieren)

KGpg ist ein grafisches KDE-Frontend für das Verschlüsselungsprogramm GnuPG. Damit lassen sich einfach neue Schlüssel erstellen, exportieren, importieren oder signieren. Z.B. eigenen Schlüssel mit öffentlichen und geheimen Teil, als auch nur öffentliche Schlüssel von Freunden, Kunden usw. Meinen öffentlichen Schlüssel könnt ihr von der Kontaktseite laden und mit dem Tool importieren. PGP erspart einem den Geheimtransport von Schlüsseln und besteht immer aus zwei Teilen. Einem öffentlichen, mit dem man nur verschlüsseln kann (public-key) und einem geheimen um diese Daten zu entschlüsseln (private-key). Siehe auch PGP Mail Verschlüsselung.
Wenn in der Konsole beim Start der Schlüsselverwaltung
kgpg -kdie Warnung "unsafe permissions on homedir ~/.gnupg" oder ähnlich erscheint, die Zugriffsrechte der Ordner auf 700 setzen:
sudo find ~/.gnupg \( -type d -exec chmod 700 {} + \);
GNOME Schlüsselbund automatisch mit SDDM Login entsperren, dass Passwort muss gleich mit dem KDE Login kwallet sein (Quelle):
kate /etc/pam.d/sddmHabe diese 2 Zeilen ans Ende der jeweiligen Sektion eingefügt:
auth      optional    pam_gnome_keyring.so
session    optional    pam_gnome_keyring.so auto_start

Reset Evolution und deinstallieren:
evolution --force-shutdown
rm -rf ~/.local/share/evolution
rm -rf ~/.cache/evolution
rm -rf ~/.config/evolution
dconf reset -f /org/gnome/evolution/
dconf reset -f /org/gnome/evolution-data-server
sudo pacman -Rns evolution

Fehler beim Drucken? Siehe WebKit Bug 202363, dafür gibt es ein workaround: Ändert im KDE-Menü-Edior den Befehl "evolution %U" in "WEBKIT_FORCE_SANDBOX=0 evolution". Scheint gelöst zu sein.

14) bauh (optional, nutze ich nicht), ist eine GUI für AppImage, Flatpak, Snap, AUR und Web:
sudo pacman -S bauh flatpak
15 ) Roger Router benötigt die Pakete libcapi und librm aus den AUR Repos und sollte mit installiert werden (ich nutze derzeit die Flatpak Version):
sudo pacman -S yay pulseaudio pulseaudio-alsa
yay -S librm libcapi
yay -S roger-router
Start mit
roger
Installation des Fax-Druckers (cups muss dafür aktiviert sein):
lpadmin -p Roger-Router-Fax -m drv:///sample.drv/generic.ppd -v socket://localhost:9100/ -E -o PageSize=A4
Telefonliste löschen: Erst Liste im Fritz-Router löschen, dann die csv-Datei.
rm ~/.local/share/rm/[deinProfilname]/journal.csv
Einstellungen können per dconf angepasst werden. Roger Router Reset:
dconf reset -f /org/tabos/

Alternative: Roger Router per Flatpak installieren
sudo pacman -S flatpakRoger-Router über flathub installieren:
flatpak install flathub org.tabos.roger
Wenn die Warnung "org.freedesktop.Platform.openh264 ist nicht installiert" kommt, versucht folgendes:
flatpak install flathub org.freedesktop.Platform/x86_64/19.08
flatpak update

Roger-Router starten (evtl. muss der PC erst neu gestartet werden):
flatpak run org.tabos.roger
Telefonliste löschen: Erst Liste im Fritz-Router löschen, dann die csv-Datei.
rm ~/.var/app/org.tabos.roger/data/rm/[deinProfilname]/journal.csv
Settings bearbeiten:
kate ~/.var/app/org.tabos.roger/config/glib-2.0/settings/keyfile
Flatpak Updates:
flatpak update
Faltpak Liste:
flatpak list
Roger Router deinstallieren:
flatpak uninstall org.tabos.roger
flatpak uninstall --unused
rm -r ~/.var/app/org.tabos.roger/

Einstellungen werden in der Flatpak Version im "keyfile" gespeichert und ist im Ordner:
~/.var/app/org.tabos.roger/config/glib-2.0/settings/
Telefonliste "journal.csv" im Ordner:
~/.var/app/org.tabos.roger/data/rm/[deinProfilName]/
16a ) Gambas IDE installieren (optional)
In der Gruppe base-devel sind z.B. benötigte pakete wie autoconf, automake, fakeroot, make und gcc enthalten:
sudo pacman -S gambas3 rpm-tools base-develdebhelper installieren (nur nötig wenn Debian Installationspakete erstellt werden sollen):
yay -S debhelperWenn ein Gambas Programm unter Arch installiert wird, werden benötigte Pakete wie z.B. der Runtime-Interpreter (gambas3-runtime) automatisch mit installiert (IDE nicht notwendig).

Wenn die IDE eine Warnung "Please set $EDITOR enviroment variable with your favorite graphical text editor" meldet, wie folgt einen Editor setzen, z.B. Kate:
kate /etc/profile.d/editor.shund diese 2 Zeilen eintragen:
export EDITOR=/usr/bin/kate
export VISUAL=/usr/bin/kate
(test mit:  echo $EDITOR)

Gambas3 IDE


16b ) Python IDE installieren (optional)
PyCharm Community ist eine IDE für reine Python-Entwicklung und entwickelt auf Basis von Open Source:
sudo pacman -S python python-pip tk pycharm-community-edition
Aktuelle Umgebung überprüfen:
pip checkDadurch wird festgestellt, ob es irgendwelche Inkonsistenzen in installierten Paketen gibt.

Zeigt installierte Pakete an:
pip list
Zeigt nur Pakete an, die mit "pip install --user" installiert wurden:
pip list --user
Was mir als Python Anfänger nicht klar war:

  • Module aus dem Python Package werden via pip an der Paketverwaltung vorbei installiert. Das kann zu unvorhergesehen Problemen mit Python-Scripts führen, besonders wenn das gleiche Python Modul auch über die Paketverwaltung installiert wird. Daher installiere ich diese per Paketverwaltung systemweit (wenn vorhanden) und optionale Pakete per "pip install --user" ohne sudo! In der IDE installiere ich Module im entsprechenden "Virtual Environment" (venv), das ist der sicherste Weg.
  • pip installiert standardmäßig Python-Pakete ins Systemverzeichnis (/usr/local/lib/pythonY.X/). Dies erfordert Root-Zugriff. Optionale Pakete sollten mit "'pip install --user" (ohne sudo!) installiert werden, diese gehen in "~/.local/lib/pythonX.Y/site-packages/".
  • Für die selbe Python-Version lassen sich standardmäßig Module nicht parallel lokal für einen Nutzer installieren, es ist nur eine von beiden Installationen möglich.
  • Wer verschiedene Versionen des gleichen Moduls braucht, muss ein "Virtual Environment" (venv) benutzen.

Python IDE mit venv:


Python-pyqt5 is newer than extra
Obwohl ihr den stabilen Zweig (stable branch) nicht gewechselt habt, erscheint eine Warnung wie z.B. "python-pyqt5: local (5.15.6-7.1) is newer than extra (5.15.6-7)".
Dann kann es sein, dass die Paketbetreuer (Maintainer) das Paket in den Repositories auf eine höhere Version gesetzt haben. Dies geschieht manchmal, wenn ein größeres Problem gefunden wird, um die Verbreitung dieses Problems für die Benutzer zu begrenzen.
Wenn die neuere Version funktioniert, braucht ihr nichts zu tun. Die Meldung verschwindet von selbst, wenn das Paket in den Repositories aktualisiert wird.
Wenn die neuere Version nicht funktioniert, ihr mit den Repositories im Einklang bleiben wollt oder einfach nicht wollt das diese Warnung erscheint, könnt ihr das Paket herabstufen, indem ihr den Paketmanager zwingt, die Version aus den Repositories zu installieren:
sudo pacman -Syyuu
Überprüfe die PyQt5 Installation:
python -c "from PyQt5.QtCore import QT_VERSION_STR; print(QT_VERSION_STR)"
Dieses Paket kann zusätzlich für Anwendungen, die PyQt6 benötigen, installiert werden:
sudo pacman -S python-pyqt6Überprüfe die PyQt6 Installation:
python -c "from PyQt6.QtCore import PYQT_VERSION_STR; print(PYQT_VERSION_STR)"
Durch die Installation in der systemweiten Python-Umgebung stehen sowohl die PyQt5- als auch die PyQt6-Module allen Python-Anwendungen zur Verfügung, die diese Umgebung nutzen.

17 ) SSD optimieren
a) In der /etc/fstab dürfen die Optionen "space_cache" und "autodefrag" bei SSD's mit dem Filesystem btrfs nicht verwendet werden, jedoch noatime (Dateizugriffszeiten nicht speichern) und ssd.
(Der Kernel erkennt eine SSD automatisch wenn in der Datei /sys/block/<device>/queue/rotational eine "0" steht, setze die Option ssd sicherheitshalber dennoch)

Beispiel:
UUID=xxxx-xxxx /boot/efi        vfat    umask=0077 0 2
UUID=xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx /              btrfs  subvol=/@,defaults,noatime,ssd 0 1
UUID=xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx /home          btrfs  defaults,noatime,ssd 0 2

Prüfen ob die SSD TRIM (discard) unterstützt:
lsblk --discardDISC-GRAN und DISC-MAX Werte ungleich Null zeigen die TRIM-Unterstützung an. Manuelles trimmen:
sudo fstrim -a -v
Es ist besser manuelles TRIM zu verwenden, daher verwende ich die Option "discard" in der fstab nicht und habe den fstrim.timer systemd Service aktiviert (Standard wöchentlich):
sudo systemctl enable fstrim.timer(kann mit 'disable' wieder deaktiviert werden)

Timer prüfen (oder Systemeinstellungen -> Systemverwaltung -> Systemd -> Timers):
systemctl cat fstrim.timerLogdatei einsehen:
journalctl | grep fstrim
b) Der LINUX-Kernel stellt tmpfs bereit. Tmpfs unterscheidet sich von einer LINUX Ramdisk insofern, als Speicher dynamisch alloziert wird und weniger genutzte Seiten in einen Swap-Bereich ausgelagert werden können. Seit systemd ist kein Eintrag in der fstab nötig (Link) und benutzt tmpfs bis zur Hälfte des RAM. Prüfen ob Unit tmp.mount geladen ist:
sudo systemctl status tmp.mount
In der Regel ist hier keine Anpassung notwendig!

Habe bei 32 GB RAM etwas Feintunig per fstab gemacht:
kate /etc/fstab# dynamic RAMDisk
tmpfs /tmp tmpfs defaults,noatime,size=50%,mode=1777 0 0
tmpfs /var/tmp tmpfs defaults,noatime,size=5%,mode=0777 0 0
(noatime = Dateizugriffszeiten nicht speichern und die /tmp Verzeichnisse benutzen ein Sticky Bit, daher das "mode=1777")

Der /tmp Eintrag wird nach einem PC Neustart durch einen systemd-generator generisch erstellt (ansonsten gibt es diese Datei nicht), prüfen:
cat /run/systemd/generator/tmp.mount
Im Verzeichnis /var/tmp werden temporäre Dateien abgelgt die zwischen Systemneustarts erhalten bleiben (z.B. systemd). Da ich das nicht benötige lege ich diese Daten auch im RAM ab. Logs lege ich nicht ins RAM, da sonst mein Apache den Start verweigert. Grund: /var/log/httpd fehlt nach dem Startup. Also entweder das Startscript patchen oder es sein lassen. Davon abgesehen würde ich diese Logfiles ungern auf eine Ramdisk legen, da diese beim Neustart gelöscht werden.

Einstellung nach Neustart prüfen, z.B.:
df -htmpfs          794M  1,2M  792M  1% /tmp
tmpfs          199M    0  199M  0% /var/tmp
(ohne SWAP-Speicher könnte es trotz genug Arbeitsspeicher zu Problemen kommen)

c) Firefox Cache ins RAM verlegen und Sitzungswiederherstellung anpassen (gilt auch für auch Firefox-ESR und Pale Moon)

Browser starten und in der Adressleiste about:config eingeben.
Dann irgendwo auf dem leeren Bildschirm im Browser, unter about:config,
einen Rechtsklick ausführen und auf "Neu" klicken. Hier einen neuen String mit dem Namen browser.cache.disk.parent_directory und dem Wert /tmp erstellen.
Auch solltet ihr das Backup für die Sitzungswiederherstellung von 15 Sekunden auf 5 Minuten setzen. Sucht nach browser.sessionstore.interval und setzt den Wert von 15000ms auf 300000ms.
Das muss für jeden User wiederholt werden.

d) SMART Werte von NVMe SSD auslesen (z.B. Samsung 970 PRO):
sudo pacman -S nvme-clilisten:
sudo nvme listInfos lesen:
sudo nvme --smart-log /dev/nvme0n1
e) Eine "~/.xsession-errors" Datei wie unter Debian gibt es hier nicht mehr und ist nun systemd Sache, Log siehe ksystemlog.

f) Schneller Booten:
Das Linux-System rennt unter dem Hintergrundprogramm (Daemon) Systemd und systemd-analyze gibt eine Liste aller laufenden Units von systemd aus, sortiert nach der Zeit, die diese für die Initialisierung benötigt haben:
systemd-analyze blame(mit Q beenden)

Manche service Dienste werden sehr selten benötigt, z.B. ModemManager.service (Analog/UMTS Modem) oder der NetworkManager-wait-online.service (teilt Anwendungen mit ob eine Online-Verbindung besteht). Wer das nicht benötigt kann diese deaktivieren:
systemctl disable ModemManager.service
systemctl disable NetworkManager-wait-online.service
Sollte dann etwas nicht mehr funktionieren, lässt sich ein service mit enable einfach wieder aktivieren.

18 ) Kernel Crash?
Tipp zum Vorbeugen


Beispiel Manjaro-Einstellungsmanager mit LTS-Kernel 5.4.x und 4.19.x, nächste LTS-Kernel Version war 5.10, 5.15 und nun 6.1 (2023)
  • einen älteren LTS-Kernel als Fallback Kernel installieren!
  • bei einem Kernel Update Crash (z.B. Stromausfall), kann damit gebootet und eine komplette System-Aktualisierung gestartet werden, z.B.:

sudo pacman -Syyuu
sudo mkinitcpio -P
(mkinitcpio ist ein Programm zur initramfs-Erstellung)

wenn das nicht hilft oder ihr habt keinen anderen Kernel (Restore_the_GRUB_Bootloader):
  • starte PC mit dem USB-Stick, das Skript manjaro-chroot ist im Manjaro Live System verfügbar (Paket manjaro-tools-base)
  • bei btrfs Dateisystem werden"subvolumes" einghängt (siehe Link oben!), ansonsten:

su
manjaro-chroot -a
pacman-mirrors --country Germany,France,Austria && pacman -Syu grub
update-grub
exit
dann den PC ohne USB-Stick neu starten.


Tipps Logeinträge prüfen (Systemd)
Prüfen ob irgendwelche systemd-Dienste fehlgeschlagen sind:
systemctl --failed
Protokoll der letzten Updates:
grep -i upgraded /var/log/pacman.log
Fehler Protokoll seit gestern:
journalctl -p err --since yesterday(kernel: proc: Bad value for 'hidepid', kann ignoriert werden, siehe github systemd 16896)

Shutdown/Reboot-Protokoll vom letzten Bootvorgang:
journalctl -b -1 | grep -A999 "System is rebooting.\|System is powering down."
Journal Protokoll von - bis:
journalctl --since "20:00:40" --until "20:01:00"
Löschen aller Protokolldaten:
sudo journalctl --rotate
sudo journalctl --vacuum-time=1s
Der erste Befehl dreht die Protokoll-Dateien und erstellt neue. Der zweite Befehl löscht alle Protokolldaten, die älter als eine Sekunde sind. Du kannst die Zeitspanne nach Bedarf anpassen.

Ncdu Festplattenbelegung:
ncdu


19 ) VIRTUALBOX installieren (Update 2024-Mai, V7.0.18)
Bei der Installation von VirtualBox wird die Version des aktuellen Kernels benötigt, Ausgabe mit:
uname -r(Ausgabe z.B. "6.6.30-2-MANJARO")

VB installieren:
sudo pacman -S virtualboxund wählt den eben entsprechenden Kernel aus, in dem Fall "linux66-virtualbox-host-modules"

Nach der Installation muss das VirtualBox-Modul dem Kernel hinzugefügt werden. Entweder den PC neu booten oder das Kernel Modul manuell hinzuzufügen:
sudo modprobe vboxdrv
Wird später ein neue Kernel installiert, muss das VirtualBox Modul nicht neu angepasst werden. Das Manjaro-Hardware-Erkennungs-Tool (mwhd-kernel) updated automatisch neue Kernel mit den entsprechenden Modulen.

Benutzer der Gruppe vboxusers hinzufügen, sonst ist kein USB verfügbar:
sudo gpasswd -a $USER vboxusers(entfernen mit: sudo gpasswd -d $USER vboxusers)

Passende "Oracle VirtualBox Extension Pack-x.x.x" (Nutzung von USB 2.0 und 3.0) könnt ihr hier laden und installieren:
Oracle_VM_VirtualBox_Extension_Pack-x.x.x.vbox-extpack


Funktioniert auch per Konsole. Namen der Erweiterungspakete anzeigen, die derzeit installiert sind:
VBoxManage list extpackswenn vorhanden altes Erweiterungspaket löschen, z.B. (Name evtl. anpassen, siehe "Pack no."):
sudo VBoxManage extpack uninstall "Oracle VM VirtualBox Extension Pack"dann das neue Erweiterungspaket installieren, z.B.:
sudo VBoxManage extpack install Oracle_VM_VirtualBox_Extension_Pack-7.0.18.vbox-extpackoder in einem Befehl wenn die Datei im Ordner Downloads ist:
sudo VBoxManage extpack install --replace ~/Downloads/Oracle_VM_VirtualBox_Extension_Pack-7.0.18.vbox-extpack
Einfrieren beim Starten einer virtuellen Maschine mit einer Intel-CPU Generation 12/13
Bei einer Intel Alder Lake und neuem Raptor Lake CPU konnte ich die VM nicht starten (Starting Virtual Machine 20%), habe dazu nur diesen workaround gefunden und in Grub diesen Kernel Parameter eingetragen:
GRUB_CMDLINE_LINUX="ibt=off"
Im Linux-Kernel wurde von Intel-Ingenieuren und anderen viel an der Unterstützung von ITB (Indirect Branch Tracking) gearbeitet und anscheinend in Linux 6.1 integriert. Bei CPUs, die nicht über die Hardware-Fähigkeit für IBT als Teil der Control-flow Enforcement Technology verfügen, sollen keine Verhaltensänderung bemerken, aber bei neueren CPUs ist dies eine gute Voreinstellung als eine weitere Ebene des hardwarenahen Sicherheitsschutzes. Anscheinden kommt die derzeitge VirtualBox damit nicht klar :-\



20 ) WEBSERVER (Apache, PHP 8 und MariaDb) installieren
Benutze ich nur um CMS-Seiten LOKAL zu testen. Mein online Server rennt natürlich nur im FastCGI-Mode ohne Desktop Umgebung und die CMS ist entsprechend 'gehärtet' und immer aktuell!

Pakete für Webserver installieren:
sudo pacman -S mariadb php php-apache phpmyadmin php-gd php-imagick
WICHTIG!
Wenn sich die Datenbank (/var/lib/mysql) in einem btrfs-Dateisystem befindet, sollte das Copy-on-Write für dieses Verzeichnis deaktiviert werden, bevor eine Datenbank erstellt wird (Quelle). So wird das copy-on-write für das Verzeichnis und Dateien deaktiviert (no-COW).
Prüfe ob Ordner leer ist:
sudo ls -all /var/lib/mysql/dann:
sudo chattr +C /var/lib/mysql
Wenn nicht leer, hilft dieser Trick um das nachträglich zu tun (als su):
sudo systemctl stop mysqld
mv /var/lib/mysql /var/lib/mysql_old
mkdir /var/lib/mysql
chattr +C /var/lib/mysql
cp -a /var/lib/mysql_old/* /var/lib/mysql
chown -R mysql:mysql /var/lib/mysql
sudo systemctl restart mysqld
wenn das funktioniert hat:
rm -rf /var/lib/mysql_old
MariaDB (MySQL) initialisieren:
sudo mysql_install_db --user=mysql --basedir=/usr --datadir=/var/lib/mysql
MariaDB starten und beim Booten starten:
sudo systemctl start mysqld
sudo systemctl enable mysqld
MariaDB Status prüfen:
systemctl status mysqld(Abbruch mit Strg & C )

Eigentlich sollte es mit dem Script "mysql_secure_installation" ohne MySQL-Passwort weiter gehen, jedoch hat das bei mir seit MariaDB noch nie funktioniert. Also erst das MySQL Passwort setzen (MariaDB 10.1.20 und neuer):
sudo mysql
MariaDB [(none)]> USE mysql;
MariaDB [(none)]> ALTER USER 'root'@'localhost' IDENTIFIED BY 'MeinPASSWORT';
MariaDB [(none)]> FLUSH PRIVILEGES;
MariaDB [(none)]> exit

und die MySQL Installation mit diesem Script abschließen (wichtig!):
mysql_secure_installation(Abbruch mit Strg & C )

Hinweis: Sollte das Script euer MySQL Passwort nicht annehmen, hilft eine Reset (sonst überspringen):
sudo mysqld_safe --skip-grant-tables &
sudo mysql -u root
dann:
MariaDB [(none)]> use mysql;
MariaDB [(none)]> FLUSH PRIVILEGES;
MariaDB [(none)]> ALTER USER 'root'@'localhost' IDENTIFIED BY 'MeinPASSWORT';
MariaDB [(none)]> exit
Prüfen, reparieren und optimieren der Tabellen:
sudo killall -9 mysqld
sudo mysqlcheck -A --auto-repair -u root -p
sudo mysqlcheck -A --auto-repair -f -o -u root -p

Installation mit diesem Script abschließen (wichtig!):
mysql_secure_installationAls erstes werdet ihr nach den MySQL root Passwort gefragt.
Dann bei der Frage "Switch to unix_socket authentication" per 'n' weiter und bei "You already have your root account protected" auch mit 'n' weiter. Als nächstes sollte auf jeden Fall der Anonymous User entfernt werden wenn der Server produktiv eingesetzt wird. Im nächsten Schritt sollte dem root User das Recht genommen werden sich über das Netzwerk anzumelden (ich arbeite nur lokal). Zusätzlich zum Anonymous User gibt es eine Testdatenbank die entfernt werden sollte. Am Ende werden die Berechtigungen neu geladen.

Wenn nachträglich Anpassungen vorgenommen werden müssen, MariaDB aktualisieren:
sudo su
systemctl restart mariadb.service && mariadb-upgrade -u root -p
exit
(Wichtig, obigen Befehl als root ausführen, sonst gibt es diesen Fehler: Could not create the upgrade info file '/var/lib/mysql/mysql_upgrade_info' in the MariaDB Servers)

Die Apache Datei httpd.conf konfigurieren:
kate /etc/httpd/conf/httpd.conf
Wenn Server nur lokal erreichbar sein soll:
Listen 127.0.0.1:80
Diese Zeilen mit einer Raute (#) auskommentieren:
#LoadModule unique_id_module modules/mod_unique_id.so
#LoadModule authn_file_module modules/mod_authn_file.so
#LoadModule mpm_event_module modules/mod_mpm_event.so
Diese Zeile aktivieren (Raute entfernen):
LoadModule mpm_prefork_module modules/mod_mpm_prefork.so
Diese Zeilen am Ende hinzufügen:
LoadModule php_module modules/libphp.so
AddHandler php-script .php
Include conf/extra/php_module.conf
Include conf/extra/phpmyadmin.conf
und prüfen ob diese Module aktiviert sind:
LoadModule userdir_module modules/mod_userdir.so
LoadModule rewrite_module modules/mod_rewrite.so

dann phpmyadmin.conf anlegen:
kate /etc/httpd/conf/extra/phpmyadmin.confAlias /phpmyadmin "/usr/share/webapps/phpMyAdmin"
<Directory "/usr/share/webapps/phpMyAdmin">
    DirectoryIndex index.php
    AllowOverride All
    Options FollowSymlinks
    Require local
</Directory>
Info "Require all granted" nur wenn nicht Lokal!

php.ini konfigurieren:
kate /etc/php/php.iniDiese Zeilen prüfen/anpassen/aktivieren:
date.timezone = Europe/Berlin
extension=gd
extension=exif
extension=iconv
extension=pdo_mysql
extension=mysqli
open_basedir = /srv/http/:/var/www/:/home/:/tmp/:/var/tmp/:/var/cache/:/usr/share/pear/:/usr/share/webapps/:/etc/webapps/
session.gc_probability = 1
upload_max_filesize = 20M
max_file_uploads = 40

config.inc.php konfigurieren:
kate /etc/webapps/phpmyadmin/config.inc.phpHier ein 32 stelliges Passwort zur Cookie-Authentifizierung setzen, z.B.:
$cfg['blowfish_secret'] = 'seit_phpMyAdmin504istdasPflicht'; /* This is needed for cookie based authentication to encrypt password in cookie. Needs to be 32 chars long. */
Apache starten und beim Booten starten:
sudo systemctl restart httpd
sudo systemctl enable httpd

Apache Status prüfen:
systemctl status httpd(Abbruch mit Strg & C )

Listet PHP Module:
php -m
Apache/PHP Error Log:
kate /var/log/httpd/error_log
PHP Info Datei erstellen und speichern:
kate /srv/http/phpinfo.php<?php
phpinfo
();
?>
dann im Browser http://localhost/phpinfo.php öffnen, PHP Version und Konfiguration sollte angezeigt werden.

phpMyAdmin ist eine freie Webanwendung zur Administration von MySQL-Datenbanken und MariaDB, im Browser http://localhost/phpmyadmin/ öffen.



Wenn die Fehlermeldung "Auf das $cfg['TempDir'] (/usr/share/webapps/phpMyAdmin/tmp/) kann nicht zugegriffen werden. PhpMyAdmin kann keine Templates zwischenspeichern und ist daher langsam." kommt, den Temp Ordner anlegen und "http" als Besitzer und Gruppe setzen (chmod 777 is dann nicht notwendig):
sudo mkdir /usr/share/webapps/phpMyAdmin/tmp/
sudo chown -R http:http /usr/share/webapps/phpMyAdmin/tmp/

Sollte die Meldung "Der phpMyAdmin-Konfigurationsspeicher ist nicht vollständig konfiguriert, einige erweiterte Funktionen wurden deaktiviert..." kommen, fehlt wahrscheinlich die Datenbank ,,phpmyadmin". Dann einfach mit diesem Link die Datenbank ,,phpmyadmin" anlegen und die Konfigurationsspeicher-Tabellen einrichten: http://localhost/phpmyadmin/index.php?route=/check-relations.

Eine andere mögliche Lösung für dieses Problem ist, eine neue Datenbank manuell in phpMyAdmin zu erstellen und dann die Konfigurationsspeicher-Tabellen darin einzurichten: Öffne phpMyAdmin und klicke auf Registerkarte "Datenbanken" oben auf dem Bildschirm. Gebe als Name "phpmyadmin" für die neue Datenbank ein und stelle die Codierung auf "utf8mb4_general_ci". Klicke auf "Erstellen", um die neue Datenbank zu erstellen. Wechsel zur Registerkarte "Importieren" oben auf dem Bildschirm und wähle die Datei "create_tables.sql" im phpMyAdmin-Installationsverzeichnis aus (/usr/share/webapps/phpMyAdmin/sql/), klicke auf "OK", um die Konfigurationsspeicher-Tabellen in der neuen Datenbank zu erstellen.




"User directories" aktivieren ~/public_html
(möchte mein CMS nicht im Ordner /var/www/ testen, sondern in meinem /home)
kate /etc/httpd/conf/extra/httpd-userdir.confDieser Bereich sollte so aussehen:
UserDir public_html
#
# Control access to UserDir directories. The following is an example
# for a site where these directories are restricted to read-only.
#
<Directory "/home/*/public_html">
    DirectoryIndex index.php index.html
    AllowOverride All
    Options MultiViews SymLinksIfOwnerMatch IncludesNoExec
    Require method GET POST OPTIONS
</Directory>
Habe das "Directory Listing" des Apache-Webservers deaktiviert, also "Indexes" entfernt (Zugriff auf alle Unterverzeichnisse werden verwehrt).

Ordner public_html erstellen und Berechtigungen anpassen:
mkdir ~/public_html
chmod 775 ~/public_html
chmod 755 ~
Apache neustarten:
sudo systemctl restart httpd
PHP Info Datei erstellen und speichern:
kate ~/public_html/phpinfo.php<?php
phpinfo
();
?>
dann im Browser "http://localhost/~BENUTZERNAME/phpinfo.php" öffnen, PHP Version und Konfiguration sollte angezeigt werden.



Dateien die der Webserver erzeugt oder ändert (z.B. ein CMS) sind nur für Mitglieder der Gruppe 'http' (bei Debian 'www-data') schreibbar. Um diese Dateien zu beschreiben, den Benutzer zu dieser Gruppe hinzufügen (Neustart notwendig):
sudo gpasswd -a $USER http(entfernen mit: sudo gpasswd -d $USER http)

Berechtigungen für home und public_html anpassen/prüfen, die Reihenfolge ist wichtig:
sudo chown -R $USER:$USER ~/
find ~/ \( -type d -exec chmod 755 {} + \) -or \( -type f -exec chmod 644 {} + \)
find ~/public_html/ \( -type d -exec chmod 775 {} + \) -or \( -type f -exec chmod 664 {} + \)
sudo chown -R http:http ~/public_html
AppImage und ShellScript ausführbar machen:
chmod +x ./*.AppImage
chmod +x ./*.sh
prüfen:
find ~ ! -user $USER -lsdas sollte nur Dateien aus dem Ordner public_html auflisten.


21 ) Paketliste und System wiederherstellen
Kontrollieren ob/wann/was über dem Packetmanager de-/installiert wurde findet ihr in der pacman.log (Chronik):
less /var/log/pacman.logoder mit einem Filter, z.B.:
grep "ALPM] installed" /var/log/pacman.logoder per pamac-gui im Menü -> "Chronik anzeigen", zeigt dann die Pamac Historie in einem Fenster.

Paketliste erstellen (Quelle)
Erstellt eine Liste von Paketen ohne (q) Versionsnummer aus, die ausdrücklich installiert wurden und nicht von anderen als Abhängigkeit benötigt werden:
pacman -Qeqt > paketliste.txt
System wiederherstellen. Man sollte diese Wiederherstellung möglichst in einem "frischen" System vornehmen (direkt nach der Basisinstallation).
pacman -S $(cat paketliste.txt)

22 ) KWalletManager: Passwörter aus Backup wiederherstellen
Die Wallet-Dateien, kdewallet.kwl und kdewallet.salt, befinden sich im Ordner ~/.local/share/kwalletd/ und können aus einem Backup wieder hergestellt werden.



ANHANG: Neuinstallation auf bestehendes LINUX ohne die /home Partition zu formatieren

Vorteil: Alle Dateien und Einstellungen bleiben erhalten - ohne Gewähr!
Gründe: Entweder weil eine Neuinstallation ratsam ist, ihr euer Linux zerschossen habt oder zu Linux Manjaro wechseln wollt, oder...

Voraussetzungen:
  • ihr kennt die Rechteverwaltung im Linux-Dateisystem (chown & chmod) - viele Probleme entstehen wenn Dateien im /home Ordner z.B. root gehören
  • Einstellungsdateien auf Standard setzen (reset) oder aus einem Backup wiederherstellen ist kein Problem für euch
  • nutzt die gleiche Desktop-Umgebung und Version - kein muss wenn nur kompatible Einstellungsdateien wiederhergestellt werden
  • /home ist auf einer eigenen Partition
  • Backup ist vorhanden und ihr wisst wie ein Restore funktioniert (wenn was schief läuft)

Prüfen ob die /home Dateien euch gehören, ausser ihr nutzt z.B. einen lokalen Webserver (siehe oben):
find ~ ! -user $USER -ls(Ausgabe sollte leer sein)
ansonsten:
sudo chown -R $USER:$USER ~/(Alle Dateien in /home/[Benutzer] gehören dann euch)
chmod anpassen, alle Ordner 755 und Dateien 644:
find ~/ \( -type d -exec chmod 755 {} + \) -or \( -type f -exec chmod 644 {} + \)AppImage und ShellScript ausführbar machen:
chmod +x ./*.AppImage
chmod +x ./*.sh

Backups von allen meinen Dokumenten und Einstellungen erstelle ich auf einer externen Festplatte oder NAS (verschlüsselt) mit BackInTime und von root reicht mir ein Snapshot pro Woche per Timeshift (Backup Ort: /run/timeshift/). Snapshots sind keine Sicherungskopien im Sinne von Backups! Halte diese Snapshots oder ein Root Backup auf einer anderen Festplatte oder NAS für nicht wichtig, da das mit einem Live System notfalls schnell wieder hergestellt ist, besonders wenn /home auf einer extra Partition ist. Wer kein Backup hat oder zusätzlich ganz sicher gehen will und ein zusätzliches Backup auf einer externen Festplatte erstellen will, kann das wie hier beschrieben per Terminal vor der Neuinstallation tun. Ansonsten könnt ihr die "Vorbereitung" überspringen.

VORBEREITUNG

a) Mit der KDE-Partitionsverwaltung eine externe USB-Festplatte formatieren, wenn noch nicht getan: Dateiformat ext4 und als Bezeichnung z.B. "Backup_ext4". Wenn ihr das Backup behalten wollt sollte die Festplatte mit LUKS verschlüsselt werden. Jedoch wäre dieses Backup schnell zu alt, daher würde ich solch eine verschlüsselte Festplatte nur mit einem Backup-Werkzeug wie z.B. BackInTime oder Timeshift nutzen.

Nach dem die Festplatte formatiert ist, die Zugriffsrechte per Terminal setzen (damit kein sudo notwendig ist). Pfad und Benutzername anpassen, bei mir ist der Benutzername jo:
sudo chown $USER:$USER /run/media/jo/Backup_ext4
sudo chmod 755 /run/media/jo/Backup_ext4

b) alle Dateien auf Backup Festplatte kopieren:
cp -arv ~/* /run/media/jo/Backup_ext4Hinweis: Wenn ihr Plasma Vault nutzt und diese(n) Ordner geöffnet habt, werden Dateien unverschlüsselt auf die Backup Festplatte geschrieben. Verschlüsselte Dateien liegen im versteckten Ordner "~/.local/share/plasma-vault/". Daher halte ich Plasma Vault beim Backup erstellen geschlossen (Settings: ~/.config/plasmavaultrc).

c) alle versteckte Dateien (Einstellungen) auf Backup Festplatte kopieren (ich lösche erst die Cache Dateien):
sudo rm -r ~/.cache/cp -arv ~/.[!.]* /run/media/jo/Backup_ext4/Dann die Backup Festplatte aushängen und sicher verwahren bis nach der Neuinstallation.

NEUINSTALLTION BEGINNEN

d) PC mit einem aktuellen Live-Image starten und Manjaro installieren. Beim installieren darf "/home" nur eingebunden und nicht formatiert werden! WICHTIG: Benutzername und Passwort muß identisch mit der alten Version sein!

e) Bei einem Kubuntu System hatte ich so Manjaro KDE installiert, in dem Fall findet ihr die alten Daten unter "/home/@home/[Benutzername]"
Diese Daten solltet ihr z.B. mit Dolphin ohne Root-Rechte in euren neuen Ordner "/home/[Benutzername]" kopieren oder verschieben.
Wenn die neue Desktop-Umgebung nicht zum alten Desktop passt oder zu alt ist, kopiere ich mit dem Dolphin oder Double Commander (doublecmd) nur versteckte Dateien zurück die Sinn machen (evtl. Schlüsselbund, Browser, E-Mail oder FileZilla Einstellungen).

Nach einem Ab- und Anmelden sollten alle Einstellungen wie vor der Neuinstallation konfiguriert sein.
Dann den alten Ordner "@home" löschen, fehlende Pakete nach installieren und Grub und SWAP konrollieren bzw. anpassen (siehe oben).

Bei dem Kubuntu zu Manjaro KDE Umzug wollte kwallet das WiFi Passwort nicht speichern, hier hatte ein kwallet-Reset geholfen:
rm -r ~/.local/share/kwalletd/
f) Wenn was schief gelaufen ist:
Stellt alle Daten aus dem Backup per Dolphin oder Terminal wieder her. Alle Dateien per Terminal zurück kopieren:
yes | cp -rv /run/media/jo/Backup_ext4/* ~/Daten werden ohne Rückfrage überschrieben!

Alle versteckte Ordner und Dateien wieder herstellen:
yes | cp -rv /run/media/jo/Backup_ext4/.[!.]* ~/Daten werden ohne Rückfrage überschrieben!
Wenn die neue Desktop-Umgebung nicht zum alten Desktop passt oder zu alt ist, kopiere ich mit dem Dolphin oder Double Commander (doublecmd) nur versteckte Dateien zurück die Sinn machen (evtl. Schlüsselbund, Browser, E-Mail oder FileZilla Einstellungen).

:dance:



mehr Tipps:

Schneller Konsolenstart per "Strg" & "Alt" & "T"

Eine erneute Synchronisation mit den Manjaro-Repository-Servern durchführen
Manjaro- und Arch-Benutzer verfügen über einen Sicherheitsschlüsselring auf ihrem Rechner, um sicher Pakete aus den Manjaro- und Arch-Repositories herunterzuladen, ohne dass diese Pakete durch einen Man-in-the-Middle-Angriff manipuliert werden können. Wenn ein Benutzer sein System lange Zeit nicht aktualisiert, kann dieser Schlüsselring manchmal ablaufen. Der Schlüsselbund kann auch aus irgendeinem Grund beschädigt werden. Um grundlegende Probleme mit dem Schlüsselbund zu lösen, gehen ihr wie folgt vor (dauert etwas):
sudo pacman -Syyuu
sudo pacman-key --refresh-keys
sudo pacman-key --populate archlinux manjaro
Vergewissert euch, dass die Systemzeit richtig eingestellt ist! Die drei Befehle sollten die meisten Probleme mit dem Schlüsselbund lösen, mehr siehe wiki.manjaro.org.

Cache leeren, um Upgrade-Probleme zu beheben
Diese Lösung kann auch Probleme mit KDE- und Qt-Anwendungen beheben, die nach einem Update nicht korrekt aussehen.
rm ~/.config/Trolltech.conf
kbuildsycoca5 --noincremental

Qt speichert Konfigurationsinformationen in "~/.config/Trolltech.conf" und legt diese nach dem löschen wieder neu an, "kbuildsycoca5 --noincremental" erstellt den Zwischenspeicher vollständig neu für die Systemeinstellungen der KService-Desktop-Dateien. Mehr dazu siehe: KDE - ArchWiki - Configuration related (eng)

KDE-Kontrollleiste oder Miniprogramme aus versehen gelöscht? Einfach aus einem Backup wiederherstellen, Ort:
~/.config/plasma-org.kde.plasma.desktop-appletsrc
Der Plasma Haftnotiz Text wird hier gespeichert:
~/.local/share/plasma_notes/
Oder Originalzustand des KDE-Desktop wiederherstellen:
kquitapp5 plasmashell
rm ~/.config/plasma-org.kde.plasma.desktop-appletsrc
rm ~/.config/plasmashellrc
rm ~/.config/plasmarc
plasmashell & disown
Der KDE-Desktop startet mit den Standardeinstellungen und die gelöschten Dateien werden neu angelegt.

Kompletten Ordner ~/.config aus einem Backup (z.B. BackInTime) wiederherstellen.
Erst BackInTime GUI starten und den .config Ordner, aus dem letzen Backup, zum Wiederherstellen vorbereiten (markieren). Dann euren KDE-Desktop beenden und den Ordner .config löschen:
backintime-qt
kquitapp5 plasmashell
rm -r ~/.config
Danach den .config Ordner aus dem Backup per BackInTime wieder herstellen und den KDE-Desktop wieder starten:
plasmashell & disown
VLC Autostart deaktivieren. Beim Einhängen einer externen Festplatte startete VLC und wollte alle Dateien öffnen und verursachte daher jede Menge Fehlermeldungen. Irgendwie hatte ich mein VLC verhext und auch ein Reset (vlc –reset-config) half nicht. Die Datei ~/.config/mimeapps.list gibt an, welche Anwendung per Vorgabe zum Öffnen spezifischer MIME-Typen registriert ist und lässt sich bei Bedarf mit einem Editor bearbeiten. Per Kate hatte ich die VLC Linien bis auf "audio/mpeg=vlc.desktop;" gelöscht und es herrscht wieder Ruhe:
kate ~/.config/mimeapps.listWenn das nicht hilft, kann man diese aus einem Backup wieder herstellen oder einfach löschen. Standard-Anwendungen müssen dann evtl. wieder angepasst werden.

Problem mit SDDM, bei einer Neuinstallation mit vorhandener /home Partition erschien diese Fehlermeldung:
Configuration file "var/lib/sddm/.config/sddm-greeterrc" not writeableGrund: Nicht alle Dateien hatten dem User sddm gehört, Lösung:
sudo chown -R sddm:sddm /var/lib/sddm/
AUR Pamac Update Problem, z.B. wenn "https://aur.manjaro.org/packages-meta-ext-v1.json.gz: Nicht akzeptables TLS-Zertifikat":
Versuche die Datei packages-meta-ext-v1.json.gz in /var/tmp/pamac-build-[UserName] zu löschen, dann solte es gehen, z.B.:

sudo rm -R /var/tmp/pamac-build-jo/packages-meta-ext-v1.json.gz
pamac update --force-refresh
pamac upgrade -a

Wayland
Das KDE-Team hat kontinuierlich daran gearbeitet, Plasma unter Wayland voll funktionsfähig zu machen, und sie haben bedeutende Fortschritte gemacht. Es gibt viele Verbesserungen und neue Funktionen, die speziell für Wayland entwickelt wurden, einschließlich besserer Unterstützung für Touchscreens und Verbesserungen bei der Leistung und Stabilität. Falls Wayland noch nicht auf deinem System installiert ist, kannst du es problemlos nachinstallieren. Bei der nächsten Anmeldung hast du dann die Möglichkeit, zwischen X11 und Wayland zu wählen.
sudo pacman -S plasma-wayland-session


Feiertage Deutschland könnt ihr auf feiertage-deutschland.de/kalender-download als iCalendar-Datei (.ics) downloaden und in alle gängigen Kalenderprogramme einbinden. Der Kalender umfasst alle bundes- und landesweiten Feiertage bis 2035. Wichtig: Beim Importieren der ICS-Datei erst einen neuen Kalender anlegen, damit sich die Daten später einfacher löschen lassen.

#37
LINUX / AnyDesk (PC-Fernwartung)
Letzter Beitrag von Jo - 2019-12-31 | 14:11:56
getestet mit KDE Plasma 5.18.5 und AnyDesk 5.5.6

TeamViewer wurde im Stillen 2014 von der englischen Datenkrake Permira übernommen und einige ehemalige TeamViewer-Mitarbeiter hatten danach die neue Remote-Desktop-Software AnyDesk als Alternative entwickelt. AnyDesk läuft überall, ist schlanker, hat eine bessere Performance und ist "Made in Germany" mit Sitz in Stuttgart und frei für Privatnutzer.

Seit langem nutze ich die Generic 64 Bit Version (anydesk-latest-amd64.tar.gz). Der große Vorteil ist, dass diese einfach im Home-Ordner (z.B.: ~/bin/anydesk/) entpackt und ohne Root-Rechte ausgeführt werden kann.

Unter Ubuntu oder Mint muss der Ordner zwingend "bin" heißen, welcher sich direkt im Home-Ordner befindet (siehe Bild Anhang). Das Verzeichnis $HOME/bin wird, sofern es existiert, nach der Anmeldung automatisch in der PATH-Umgebungsvariable eingetragen. Daher kann es sein, das ihr euch erst ab- und wieder anmelden müsst, um dem System die Möglichkeit zu geben, den Ordner richtig einzubinden. Kontrolle per Terminal:
echo $PATH
Nach dem entpacken benenne ich die Shell Script Datei "anydesk" in "anydesk.sh" um. Dadurch ist diese Datei leicht als ausführbar erkennbar. Das ist wichtig wenn Zugriffsrechte manuell oder per KDEtweaks aktualisiert werden, z.B.:
chmod +x ./*.AppImage
chmod +x ./*.sh

Bei einem Update könnt ihr die bestehenden Dateien einfach überschreiben, danach alte anydesk.sh löschen und neue anydesk in anydesk.sh umbenennen.

Bei Manjaro fehlen eventuell noch die Pakete:
sudo pacman -S gtkglextwenn in der Konsole der Fehler "error while loading shared libraries: libpangox-1.0.so.0" kommt, Paket pangox-compat aus dem AUR installieren:
yay -S pangox-compat(siehe auch Missing Libraries)

Für Ubuntu und Mint muss dieses Paket installiert sein:
sudo apt install libgtkglext1
Wenn etwas nicht funktioniert, startet das Programm per Konsole um evtl. Fehlermeldungen zu sehen:
./bin/anydesk/anydesk.sh(obligatorische Bibliotheken die evtl. fehlen, siehe README)

Dann AnyDesk manuell im Startmenü anlegen (KDE PrintScreen):


Tipp:
Für AnyDesk gibt es ein Firejail anydesk.profile (Sandkasten). Dieses Profil funktioniert bei einer manuellen Installation unter Home nicht. Lösung: Ihr könnt die Datei anydesk.profile in euer ~/bin/anydesk/ speichern und fügt hinter

whitelist ${HOME}/.anydesk  diese Zeile ein
whitelist ${HOME}/bin/anydesk
danach kann AnyDesk mit Firejail wie folgt gestartet werden (Befehl):
firejail --profile=~/bin/anydesk/anydesk.profile ~/bin/anydesk/anydesk.sh(modifiziertes anydesk.profile im Anhang)


Optional:
(nutze ich nicht!)

Für Manjaro gibt es eine AUR-Version (anydesk-bin oder anydesk-debian), diese kann per manuellen Build-Prozess installiert werden.

Es gibt auch eine Debian/Ubuntu *.deb Datei zum installieren (Root-Rechte notwendig) oder eine *.exe Datei zum direkten Ausführen für Windows Systeme. Standardmäßig zeigt Windows bei einer *.exe Datei eine Sicherheitswarnung an. Bei beiden Dateien (deb oder exe), solltet ihr sicher sein woher die Dateien stammen und selbst von der offiziellen Homepage laden.

oder

Wer unter Debian/Ubuntu immer eine aktuelle Version möchte, kann das per DEB repository einbinden und installieren. Leider funktioniert das nur mit Root-Rechte:
sudo -i
wget -qO - https://keys.anydesk.com/repos/DEB-GPG-KEY | apt-key add -
echo "deb http://deb.anydesk.com/ all main" > /etc/apt/sources.list.d/anydesk-stable.list
apt update; sudo apt upgrade; sudo apt full-upgrade
apt install anydesk

Solltet ihr AnyDesk und die Repository wieder entfernen wollen:
sudo apt --purge remove anydesk
sudo rm /etc/apt/sources.list.d/anydesk-stable.list
dann mit "apt-key list" den Key suchen und auch entfernen, z.B. "sudo apt-key del 47A11ABC"




#38
CMS / modxComment
Letzter Beitrag von Jo - 2019-04-14 | 15:57:00
Einfache Kommentarkomponente
getestet mit MODX Revolution 2.7.2-pl und Bootstrap 2.3.2

Leider gibt es keine ordentliche Open Source Kommentarfunktion für MODX die DSGVO konform ist. Daher habe ich mir das mit MODX "Standard Snippets und Chunks" zusammengebaut. Das ist die Stärke von MODX: Flexibel hoch 3.

Nenne das ganze modxComment V19.04.002 und die Features sind:
+ eMail Benachrichtigung
+ eMail Syntax-Überprüfung
+ eMail Veröffentlichen ja/nein
+ eMail Maskierung
+ Spamschutz ohne nervigen Captcha (Danke an Jako!)
+ Icon Set und BBCode
+ Bewertung des Berichtes
+ Kommentare im Frontend ändern und de- bzw. aktivieren*
+ deaktivierte Kommentare endgültig löschen*
+ IP kann aus Sicherheitsgründen gespeichert werden (sollte dann einmal pro Woche via cronjob gelöscht werden)

* darf nur User mit ID1 - wenn mehr User diese Berechtigung haben sollen - einfach die Output Filter !+modx.user.id:eq=`1` durch ein !+modx.user.id:memberof=`Administrator` ersetzen (oder einer anderen Gruppe).

Vorwort:
QUIP und modxTalks werden seit sehr langer Zeit nicht mehr gepflegt und sind mir zu Fehlerhaft.
Besonders bei modxTalks finde ich das sehr Schade! Das Design ist Topp! Nur was nützt es, wenn das MODX Error Log voll läuft und es keinen Support per github gibt? Sottwell und ich hatten vergeblich versucht per github das Tool ordentlich ans laufen zu bringen  :confused:
OK, also Plan B mit FormIt & Co:

#### Vorbereitungen ####

Folgende 4 Packages werden für modxComment benötigt:
(in Klammer stehen meine Versionen)
  • FormIt (4.2.2-pl) - Form Eingabefeld
  • rowboat (1.1.0-pl) - DB lesen
  • getPage (1.2.4-pl) - Paginierung
  • StupidQuestion (0.7.2-pl) - Spamschutz


1) eine custom SQL-Tabelle für formit2db anlegen
(z.B. mit phpMyAdmin importieren)
CREATE TABLE `modx_custom_comment`(
  `id` int(10) NOT NULL auto_increment,
  `ctResource` int(10) NOT NULL default '0',
  `ctIp` varchar(50) NOT NULL default '0:0:0:0:0:0:0:0',
  `ctName` varchar(50) NOT NULL default '',
  `ctEmail` varchar(60) NOT NULL default '',
  `ctEmailshow` tinyint(1) NOT NULL default '0',
  `ctHome` varchar(50) NOT NULL default '',
  `ctVote` int(1) NOT NULL default '0',
  `ctText` text NOT NULL,
  `ctDate` timestamp NOT NULL default CURRENT_TIMESTAMP,
  `ctActive` tinyint(1) NOT NULL default '1',
PRIMARY KEY (`id`)
);
Hinweis: Der PREFIX 'modx_' ist Standard, wenn nicht muss das angepasst werden.


#### snippets erstellen ####

2) Zwei snippets db2formit und formit2db erstellen (Quelle: formit2db with autocreate schema&classes).

db2formit
<?php
# e.g.: <a href="[[~42? &resId=`[[+id]]`]]">Edit resource</a>

$prefix=$scriptProperties['prefix'];
$packageName $scriptProperties['packageName'];
$tablename $scriptProperties['tablename'];

$restrictPrefix true;

$packagepath $modx->getOption('core_path') . 'components/'.$packageName.'/';
$modelpath $packagepath.'model/';
$schemapath $modelpath.'schema/';
$schemafile $schemapath.$packageName.'.mysql.schema.xml';
$manager$modx->getManager();
$generator$manager->getGenerator();
if (!
file_exists($schemafile)){

    if (!
is_dir($packagepath)) {
        
mkdir($packagepath0755);
    }
    if (!
is_dir($modelpath)) {
        
mkdir($modelpath0755);
    }
    if (!
is_dir($schemapath)) {
        
mkdir($schemapath0755);
    }
    
//Use this to create a schema from an existing database
    
$xml$generator->writeSchema($schemafile$packageName'xPDOObject'$prefix$restrictPrefix);

    
//Use this to generate classes and maps from your schema
    //NOTE: by default, only maps are overwritten; delete class files if you want to regenerate classes
    
$generator->parseSchema($schemafile$modelpath);    


$modx->addPackage($packageName,$modelpath,$prefix);
$classname $generator->getClassName($tablename);

if (isset(
$_GET['resId'])){
    if (
$dataobject=$modx->getObject($classname,array('id'=>$_GET['resId']))){
        if (!
is_object($dataobject) || !($dataobject instanceof xPDOObject)) {
            
$errorMsg='Failed to create object of type: ' $classname;
            
$hook->addError('error_message',$errorMsg);
            return 
false;
        }
        
# only if
        
if ($modx->user->isMember(array('Administrator'))){
        
# or
        # if ($modx->user->get('id') == '1'){
        
$hook->setValues($dataobject->toArray());
        }
    }
}

return 
true;

formit2db
<?php
$prefix
=$scriptProperties['prefix'];
$packageName $scriptProperties['packageName'];
$tablename $scriptProperties['tablename'];

$packagepath $modx->getOption('core_path') . 'components/'.$packageName.'/';
$modelpath $packagepath.'model/';

$modx->addPackage($packageName,$modelpath,$prefix);
$manager$modx->getManager();
$generator$manager->getGenerator();
$classname $generator->getClassName($tablename);

$dataobject=$modx->getObject($classname,array('id'=>$hook->getValue('resource_id')));

if (empty(
$dataobject)){
  
$dataobject $modx->newObject($classname);
}
else{
// kein neuen DS anlegen (also update)
}

if (!
is_object($dataobject) || !($dataobject instanceof xPDOObject)) {
  
$errorMsg='Failed to create object of type: ' $classname;
  
$hook->addError('error_message',$errorMsg);
  return 
false;
}

$allFormFields $hook->getValues();
foreach (
$allFormFields as $field=>$value){
if (
$field !== 'spam' && $field !== 'resource_id'){
  
$dataobject->set($field,$value);
}
}

$dataobject->save();
return 
true;

3) commentEntryDel
<?php
# löscht alle deaktivierte Kommentare
$table 'modx_custom_comment';
$where 'ctActive=0';

$count $modx->exec("DELETE FROM $table WHERE $where");
return 
$count' Kommentar(e) wurde(n) gelöscht!';

4) commentQty
<?php
# zähle aktivierte Einträge der aktuellen Ressource [[!commentQty?active=`1`]]
# Anzahl Platzhalter [[+ctQTY]]

$id $modx->resource->get('id');
$stmt $modx->query('SELECT * FROM `modx_custom_comment` WHERE `ctActive`='.$active.' AND `ctResource`='.$id);

  
$count=0;
  
$count $stmt->rowCount();
  
$modx->setPlaceholder('ctQTY'$count);

return 
$count;

5) emailMask
<?php
# email-Adressen vor bots durch Maskierung verbergen

$hiddenEmail '';
$length strlen($input);

for(
$i 0;$i<$length;$i++){
  
$hiddenEmail .= '&#'.ord($input[$i]).';';
}

return 
$hiddenEmail;

6) getGravatar
<?php
//Example
//[[!getGravatar? &email=`[[+gbemail:htmlent]]` &size=`40` &default=`[[++site_url]]/assets/content/images/Gravatar_40x40.jpg`]]
//or
//[[!getGravatar? &email=`[[+gbemail:htmlent]]` &size=`40` &default=``]]

$grav_url="https://www.gravatar.com/avatar/".md5(strtolower(trim($email)))."?d=".urlencode($default)."&amp;s=".$size;

return 
'<img src="'.$grav_url.'" class="img-polaroid" alt="" title="Gravatar" />';

7) smilies
<?php
# Output-Filter zur Darstellung der Smilies in den Kommentaren
# Z.B.:
# [[$smilieChunk:smilies]]
# oder
# [[+ctText:nl2br:smilies]]

// Path where the smilies are stored
$basepath $modx->config['site_url'].'assets/content/images/';
// Mapping of text to imagename
$smilies = array(':biggrin:' => 'biggrin.gif',':-)' => 'smile.gif',':-(' => 'mad.gif',':eek:' => 'bigeek.gif',':-P' => 'razz.gif',':oops:' => 'upset.gif',':cry:' => 'cry.gif',':evil:' => 'sigh.gif',':dead:' => 'dead.gif',':roll:' => 'rolleyes.gif',';-)' => 'wink.gif','8-)' => 'cool.gif',':-?' => 'confused.gif',':sleep:' => 'sleep.gif');

// Convert imagenames to html tags here, just to keep the structure above
// easy to maintain, especially when I want to change the generated HTML.
foreach ($smilies as $key => $value)
{
$smilies[$key] = "<img src='".$basepath.$value."' class='smilie' alt='$key' />";
}
return 
str_replace(array_keys($smilies), array_values($smilies), $input);

8 ) vote
<?php
# Output-Filter zur Darstellung der Vote-Icons in den Kommentaren
# Z.B.:
# [[+ctVote:vote]]

$vote '';
for (
$i 1$i <= $input$i++) {
$vote .= '<img src="assets/content/images/vote-16x18.png" class="vote" alt="Bewertung" />';
}
return 
$vote;

9) bbcode
<?php
# Output-Filter zur Darstellung von BBCode in den Kommentaren
# Z.B.: [[+ctText:bbcode]]
# erlaubt ist:
# [b]fett[/b] [i]kursiv[/i] [u]unterstrichen[/u] [center]zentriert[/center]
# [link]https://jolichter.de[/link] oder [url]jolichter.de[/url]
#
$string preg_replace("/&amp;(#[0-9]+|[a-z]+);/i""&$1;"htmlspecialchars($input));
$string preg_replace('~\[b\](.+?)\[/b\]~is''<b>\1</b>'$string);
$string preg_replace('~\[i\](.+?)\[/i\]~is''<i>\1</i>'$string);
$string preg_replace('~\[u\](.+?)\[/u\]~is''<span style="text-decoration: underline;">\1</span>'$string);
$string preg_replace('~\[center\](.+?)\[/center\]~is''<div style="text-align:center;">\1</div>'$string);
$string preg_replace('~\[link\]www.(.+?)\[/link\]~is''<a href="https://www.\1" target="_blank">www.\1</a>'$string);
$string preg_replace('~\[link\](.+?)\[/link\]~is''<a href="\1" target="_blank">\1</a>'$string);
$string preg_replace('~\[link=(.+?)\](.+?)\[/link\]~is''<a href="\1" target="_blank">\2</a>'$string);
$string preg_replace('~\[url\]www.(.+?)\[/url\]~is''<a href="https://www.\1" target="_blank">www.\1</a>'$string);
$string preg_replace('~\[url\](.+?)\[/url\]~is''<a href="\1" target="_blank">\1</a>'$string);
$string preg_replace('~\[url=(.+?)\](.+?)\[/url\]~is''<a href="\1" target="_blank">\2</a>'$string);
$string str_replace(array("[","]","`"),array("[","&#93;","&#96;"),$string);
 
return 
$string;


#### chunks erstellen ####

10) modxComment
<hr>
<div class="span10">
<div class="comment">
Die eMail Adresse wird nur auf Wunsch angezeigt und Avatar Bilder werden verschlüsselt über <a href="https://de.gravatar.com/" target="_blank">Gravatar</a> bezogen.
</div>
<p>[[!$commentForm]]</p>


[[+ctQTY:gt=`0`:then=`<h3>[[!commentQty?active=`1`]] [[+ctQTY:eq=`1`:then=`Kommentar`:else=`Kommentare`]]</h3>`:else=``]]

[[!$commentEntry]]
</div>
diesen Chunk z.B. im Seitentemplate hinter [[*content]] per TV uncached einbinden
......
......
  [[*content]]
  [[*tvComment:is=`ja`:then=`[[!$modxComment]]`:else=``]]
......
......

11) commentSmilies
<div class="smilies">
  <div class="smilieSelect"><img src="assets/content/icons/biggrin.gif" alt="biggrin" onclick="AddSmile(':biggrin:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/smile.gif" alt=":-)" onclick="AddSmile(':-)')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/mad.gif" alt=":-(" onclick="AddSmile(':-(')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/smilies2/bigeek.gif" alt=":eek:" onclick="AddSmile(':eek:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/razz.gif" alt=":-P" onclick="AddSmile(':-P')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/upset.gif" alt=":oops:" onclick="AddSmile(':oops:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/cry.gif" alt=":cry:" onclick="AddSmile(':cry:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/sigh.gif" alt=":evil:" onclick="AddSmile(':evil:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/dead.gif" alt="dead" onclick="AddSmile(':dead:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/rolleyes.gif" alt=":roll:" onclick="AddSmile(':roll:')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/wink.gif" alt=";-)" onclick="AddSmile(';-)')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/cool.gif" alt="8-)" onclick="AddSmile('8-)')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/confused.gif" alt=":-?" onclick="AddSmile(':-?')" /></div>
  <div class="smilieSelect"><img src="assets/content/icons/sleep.gif" alt=":sleep:" onclick="AddSmile(':sleep:')" /></div>
</div>

12) commentAddSmile
<script>
function AddSmile(x,D,F){D=document;F=D.getElementById('ctText');D.selection?(F.focus(),D.selection.createRange().text=x):(F.selectionStart||F.selectionStart===0)?F.value=F.value.substring(0,F.selectionStart)+x+F.value.substring(F.selectionEnd,F.value.length):F.value+=x}
</script>

13) commentEmail
Neuer Kommentar gesendet von [[++site_url]] <br />

<br />[[+ctName:htmlent]] ([[+ctEmail:htmlent]]) hat als Kommentar geschrieben: <br /><br />
[[+ctText:htmlent:nl2br]]

<br /><br />

Bewertung: [[+ctVote]]<br />
Ort: [[+ctHome:htmlent]]<br />
Datenschutzerklärung akzeptiert: [[+datenschutz:is=`1`:then=`Ja`:else=`Nein`]]<br />

14) commentEntry
<div class="row"><div class="span12">
<span class="label">Seite [[+page]] von [[+pageCount]]</span>
</div></div>

[[!getPage:default=`Noch kein Eintrag vorhanden`?
   &element=`Rowboat`
   &table=`modx_custom_comment`
   &sortBy=`id`
   &sortDir=`DESC`
   &where=`[[!+modx.user.id:eq=`1`:then=`{"ctResource:=":"[[*id]]","ctActive:>=":"0"}`:else=`{"ctResource:=":"[[*id]]","ctActive:=":"1"}`]]`
   &totalVar=`rowboat.total`
   &cacheResults=`0`
   &tpl=`tplCommentEntry`
   &limit=`5`
   &pageFirstTpl=`<li class="control"><a[[+classes]][[+title]] href="[[+href]]">Erste</a></li>`
   &pageLastTpl=`<li class="control"><a[[+classes]][[+title]] href="[[+href]]">Letzte</a></li>`
]]

[[!+page.nav:notempty=`
    <div class="pagination">
        <ul>
        [[!+page.nav]]
        </ul>
    </div>
`]]
<hr>

15) commentForm
-> redirectTo Res.-Id anpassen (hier 4711)
-> Link zur Res.-Id Datenschutz anpassen (hier 666)
[[!FormIt?
  &preHooks=`StupidQuestion,db2formit`
  &hooks=`StupidQuestion,spam,email,formit2db,redirect`
  &prefix=`modx_custom_`
  &tablename=`comment`
  &packageName=`comment`
  &emailTpl=`commentEmail`
  &emailFrom=`deine-e-mail@server.tld`
  &emailTo=`deine-e-mail@server.tld`
  &redirectTo=`4711`
  &emailUseFieldForSubject=`1`
  &emailSubject=`Neuer Kommentar`
  &validationErrorMessage=`<p class="text-error">Die eingegebenen Daten waren nicht richtig: [[+errors]]</p>`
  &validate=`ctName:required:maxLength=`50`,
    ctEmail:email:required:maxLength=`60`,
    ctHome:required:maxLength=`50`,
    ctText:required:stripTags:maxLength=`1000`,
    ctVote:required,
    datenschutz:required,
    name2:blank`
]]

[[$commentAddSmile]]

<script>
     $(function(){
        function runEffect() {
    var options = {};
    $("#effect").toggle("blind", options, 500);
    };
     $('#ctEinblenden').click(function() {
     $('#ctAusblenden').slideToggle("slow");
    $(this).toggleClass("ct");
    if($(this).hasClass("ct")){
                    $(this).html("<i class='icon-comment'></i> Eintrag ausblenden");
                }else{
                    $(this).html("<i class='icon-comment icon-white'></i> Eintrag hinzufügen");
                }
            runEffect();
        return false;
    });
        });
</script>

<div class="row"><div class="span4">
<button id="ctEinblenden" class="btn btn-primary" type="button"><i class="icon-comment icon-white"></i> Eintrag hinzufügen</button>
<div id="ctAusblenden" style="display:none;"> 

<h2>Kommentar Eintrag</h2>

[[!+fi.error.error_message:notempty=`<p>[[!+fi.error.error_message]]</p>`]]
<form action="[[~[[*id]]]]" method="post" class="form">
<input type="hidden" name="name2" value="" />
<input name="resource_id" type="hidden" value="[[+fi.id]]" />
[[- IP aktiviere ich nur kurzeitig bei Bedarf, z.B. bei DDoS-Attacken um diese dann zu sperren]]
[[- !+modx.user.id:eq=`1`:then=``:else=`<input type="hidden" name="ctIp" value="[[!myIP?]]" />`]]
<input type="hidden" name="ctResource" value="[[*id]]" />

<table class="table table-hover table-condensed">

  [[!+modx.user.id:eq=`1`:then=`
    <tr><th>Aktiv:</th>
    <th>
    <input type="hidden" name="ctActive[]" value="0" />
    <input type="checkbox" name="ctActive[]" id="ctActive" value="1" [[!+fi.ctActive:FormItIsChecked=`1`]] />
    Kommentar veröffentlichen? <br /><br />
    </th></tr>
  `:else=``]]

  <tr><th><label for="ctName">Name:</label></th>
  <th><input required type="text" name="ctName" id="ctName" maxlength="50" value="[[!+fi.ctName:htmlent]]" />
  <img src="assets/content/images/text-x-vcard.png" alt="icon" width="16" height="16" />
  <span class="text-error">[[+fi.error.ctName]]</span>
  </th></tr>

  <tr><th><label for="ctHome">Wohnort:</label></th>
  <th><input required type="text" name="ctHome" id="ctHome" maxlength="50" value="[[!+fi.ctHome:htmlent]]" />
  <img src="assets/content/images/user-home.png" alt="icon" width="16" height="16" />
  <span class="text-error">[[+fi.error.ctHome]]</span>
  </th></tr>

  <tr><th><label for="ctEmail">eMail:</label></th>
  <th><input required type="email" name="ctEmail" id="ctEmail" maxlength="50" value="[[!+fi.ctEmail:htmlent]]" />
  <img src="assets/content/images/mail-message.png" alt="icon" width="16" height="16" />
  <span class="text-error">[[+fi.error.ctEmail]]</span><div class="smallfont">
  <input type="hidden" name="ctEmailshow[]" value="0" />
  <input type="checkbox" name="ctEmailshow[]" id="ctEmailshow" value="1" [[!+fi.ctEmailshow:FormItIsChecked=`1`]] /> eMail wird  veröffentlicht!<br /><br /></div>
  </th></tr>

  <tr><th><label for="ctVote">Bericht Bewertung:</label></th>
  <th>
    <select required tabindex="0" name="ctVote" id="ctVote">
    <option value="[[+fi.ctVote]]">Bitte bewerten</option>
    <option value="5">5 Sterne</option>
    <option value="4">4 Sterne</option>
    <option value="3">3 Sterne</option>
    <option value="2">2 Sterne</option>
    <option value="1">1 Sterne</option>
    </select>
  <img src="assets/content/images/vote-16x18.png" alt="vote" width="16" height="16" />
  <span class="text-error">[[+fi.error.ctVote]]</span>
  </th></tr>

  <tr><th></th>
  <th class="smallfont"><br/>Mit <a href="[[~[[*id]]]]#" data-rel="popover-top" class="btn-min btn-success" data-content="
    erlaubt ist:<br />
    [b]fett[/b]<br />
    [i]kursiv[/i]<br />
    [u]unterstrichen[/u]<br />
    [center]zentriert[/center]" data-original-title="BBCode">BBCode</a> könnt ihr euren Text strukturieren<br />
  </th></tr>

  <tr><th><label for="ctText">Kommentar:<br />
  <span class="smallfont">(max. 1000 Zeichen)</span></label>
  <img src="assets/content/images/text-x-generic.png" alt="icon" width="24" height="24" /></th>
  <th><textarea required class="span5" name="ctText" id="ctText" cols="50" rows="6">[[!+fi.ctText:htmlent]]</textarea>
  <span class="text-error">[[+fi.error.ctText]]</span>
  </th></tr>

  <tr><th></th>
  <th>[[$commentSmilies]]
  </th></tr>

  <tr><th><label for="datenschutz">Datenschutz:</label></th>
  <th><input type="hidden" name="datenschutz[]" value="0" />
  <input required type="checkbox" name="datenschutz[]" id="datenschutz" value="1" [[!+fi.datenschutz:FormItIsChecked=`1`]] /> Ich bin damit einverstanden, dass mein Kommentar veröffentlicht wird und habe die Datenschutzerklärung im <a href="[[~666]]" target="_blank">Datenschutz</a> gelesen und akzeptiert.
  <span class="text-error">[[+fi.error.datenschutz]]</span>
  </th></tr>

  <tr><th></th>
  <th>[[!+formit.stupidquestion_html]]
  </th></tr>

  <tr><th></th>
  <th>
  [[!+modx.user.id:eq=`1`:then=`
  <button type="submit" class="btn btn-large btn-success">
  <i class="icon-play icon-white"></i> Eintrag hinzufügen ([[+fi.id]])</button>
  `:else=`
  <button type="submit" class="btn btn-large btn-success">
  <i class="icon-play icon-white"></i> Eintrag hinzufügen</button>
  ` ]]
  </th></tr>

  </table>
</form>

</div>
</div></div>

redirectTo Ressource
-> Hide From Menus and Published!
<h3 style="text-align: center;">Vielen Dank für deinen Kommentar</h3>
<br />
Solltest du deinen Beitrag löschen oder korrigieren wollen, melde dich bitte per Kontaktformular und wir werden das schnellstmöglich korrigieren.
<br /><br />
<script>
    document.write('<a href="' + document.referrer + '"><div class="back">Zurück zum Bericht</div></a>');
</script>

16) tplCommentEntry
-> im Chunk die Ressource "delete Comment" durch eure Res.-Id ersetzen (hier 815)
<div class="comment_top">
    <span class="comment_big">
      [[+ctName:htmlent]]
    </span>
    <span class="comment_small">
      am [[+ctDate:strtotime:date=`%d-%m-%Y, %H:%M Uhr`]] aus [[+ctHome:htmlent]]
    </span>
    <span class="comment_vote">
          [[+ctVote:vote]]
    </span>
</div>

<div [[+_alt:is=`0`:then=`class="comment_content"`:else=`class="comment_content_b"`]]>
        <span class="ctEmail">
        [[+ctEmailshow:eq=`1`:then=`<a href="[[emailMask? &input=`mailto:[[+ctEmail:htmlent]]`]]"><i class="icon-envelope" title="eMail"></i></a>`:else=``]]
        [[!+modx.user.id:eq=`1`:then=`<br />[[+ctEmail:htmlent:emailMask]]`:else=``]]
        </span>
        <p class="gbavatar">[[!getGravatar? &email=`[[+ctEmail:htmlent]]` &size=`40` &default=``]]</p>
        [[+ctText:htmlent:bbcode:nl2br:smilies]]
        [[!+modx.user.id:eq=`1`:then=`
        <br /><a href="[[~[[*id]]? &resId=`[[+id]]`]] ">Eintrag ändern</a><br />
         [[+ctActive:eq=`1`:then=``:else=`<font color=#990000>Kommentar ist deaktiviert || <a href="[[~815]]">alle deaktivierte löschen!</a></font>`]]
        `:else=``]]
</div>

Ressource "delete Comment"
-> im Chunk die Ressource "delete all disabled comments" durch eure Res.-Id ersetzen (hier 4711)
-> Hide From Menus and not Published!
<h2 style="text-align: center;">Warnung!</h2>
<p style="text-align: center;">Hier werden alle deaktivierte Kommentare gelöscht!</p>
[[!+modx.user.id:memberof=`Administrator`:then=`
<div class="back"><a href="[[~4711]]"><font color=#990000>Achtung! Jetzt diese Kommentare löschen?</font></a></div>
`:else=`Sorry, du bist kein Admin!`]]
<div class="back"><a href="[[~[[++site_start]]]]">Abrechen!</a></div>

[[!getPage:default=`Es ist kein deaktivierter Eintrag vorhanden!`?
  &element=`Rowboat`
  &table=`modx_custom_comment`
  &sortBy=`id`
  &sortDir=`DESC`
  &where=`[[!+modx.user.id:memberof=`Administrator`:then=`{"ctActive":"0"}`:else=`{"ctActive":"9"}`]]`
  &totalVar=`rowboat.total`
  &cacheResults=`0`
  &tpl=`tplCommentEntryDel`
  &limit=`10`
  &pageFirstTpl=`<li class="control"><a[[+classes]][[+title]] href="[[+href]]">Erste</a></li>`
  &pageLastTpl=`<li class="control"><a[[+classes]][[+title]] href="[[+href]]">Letzte</a></li>`
]]

[[!+page.nav:notempty=`
    <div class="pagination">
        <ul>
        [[!+page.nav]]
        </ul>
    </div>
`]]

Ressource "delete all disabled comments"
-> Hide From Menus and not Published!
[[!+modx.user.id:memberof=`Administrator`:then=`[[!commentEntryDel]]`:else=`keine Berechtigung!`]]
<div class="back"><a href="[[~[[++site_start]]]]">Zur Startseite</a></div>

17) CSS Zeilen für das Seitentemplate (Beispiel)
/* Comments */
#ctText, #ctName, #ctHome, #ctEmail {padding: 2px; clear: right}
#ctEinblenden, #ctAusblenden {text-align: center; font-size: 14px; font-weight: bold; margin: 0; padding: 2px 5px 2px 5px}
#ctAusblenden label {margin-right: 50px}
.smilie {vertical-align: sub}
.smilies {margin: 5px 2px 40px 0px}
.smilieSelect {float: left; margin-right: 5px}
.comment_top {background-color: #123; height: 26px; color: #fff; margin-right: 10px; padding: 2px 5px 2px 5px}
.comment_big {float: left; font-size: 16px; font-weight: bold; margin-right: 10px; padding-top: 4px}
.comment_small {float: left; font-size: 10px; font-weight: bold; padding: 6px 0 0 0}
.ctAvatar {float:left; padding-right: 5px; margin-left: -60px}
.comment_content {min-height: 80px; margin: 0 10px 20px 0; padding: 5px 30px 0 40px; clear: right; background: #fff;  border-width: 1px; border-style: solid; border-color: #123}
.comment_content_b {min-height: 80px; margin: 0 10px 20px 0; padding: 5px 30px 0 40px; clear: right; background: #f4f4f4;  border-width: 1px; border-style: solid; border-color: #123}
.comment_content .ctEmail, .comment_content_b .ctEmail {float: right; margin: 0 -20px 0 20px; color: green; font-size: 10px}
.comment_vote  {float: right; padding: 3px 5px 3px 0; width: 100px}
.comment_vote .vote {float: right; padding: 0px 1px 0; width: 16px; height: 16px}
#39
CMS / Antw:MODX Wetter
Letzter Beitrag von Jo - 2019-01-08 | 00:24:41
Freie Wettervorhersage für MODX Revolution vom deutschen Wetterdienst (DWD)

Getestet mit MODX 2.8.4 (PHP 7.4.16) und MODX 3.0.1 (PHP 8.1.5)

DEMO: Wettervorhersage für Bitburg und im Kalender

Info Links zu opendata und dwd:

Update 2022: Leider ist der DWD nicht in der Lage, alte Links auf neue oder richtige Links umzuleiten und daher gibt es 2 tote Links (mit RIP markiert)  :undecided:


Der MOSMIX-Vorhersagedatensatz "MOSMIX_L" enthält ca. 115 Wettervariablen pro Vorhersage und die maximale Vorhersagezeit beträgt +240 Stunden. Die Vorhersage wird 4 mal täglich um 03, 09, 15 und 21 Uhr UTC aktualisiert. Das Snippet holt 19 dieser Wettervariablen stündlich per cURL (nur wenn Seite geladen wird) und setzt diese in Platzhalter, bzw. in ein Chunk Template für Wetterelemente (10 Tage Trend).

Hinweis: Der "MOSMIX_S" Vorhersagedatensatz enthält 40 Parameter und wird 24x für den ersten Tag und 4 mal täglich für nachfolgende Tage aktualisiert (bis +240h). Leider sind diese Daten sehr groß, da alle Stationen in eine Datei geschrieben werden (ca. 37MB). Diese müssten dann stündlich geladen werden - also täglich ca. 900MB!

Snippet dwdWeather
<?php
#
# DWD Wettervorhersage MODX Snippet | MODX Weather Forecast V 22.10.045
#
# Entgeltfreie Versorgung mit DWD-Geodaten über dem Serverdienst https://opendata.dwd.de
# https://opendata.dwd.de/README.txt
#
# MOSMIX-Dateien werden in dem xml-ähnlichen kml-Format ausgeliefert, die Dateien sind als kmz-Dateien komprimiert
# DWD Stationskatalog (oder besser Vorhersagepunkte!): https://www.dwd.de/DE/leistungen/met_verfahren_mosmix/mosmix_stationskatalog.cfg?view=nasPublication&nn=16102
# z.B.: ID 10609 = Trier, ID 10513 = Koeln/Bonn, ID K428 = Bitburg, usw.
#
# Beispiele für Snippet-Aufrufe
# ohne Uhrzeit:
# [[!dwdWeather? &STATION=`K428` &TPL=`dwdWetterTPL`]]
# [[+dwdWeather]]
# (als Standard wird 12:00 Uhr genommen)
#
# alle Vorhersagen stündlich:
# [[!dwdWeather? &STATION=`K428` &fcAll=`true` &TPL=`dwdWetterTPL`]]
# [[+dwdWeather]]
#
# mit 4 Uhrzeiten pro Tag (T1 -T4) bei 12 Vorhersagen (QTY), also Vorhersage 3 Tage:
# [[!dwdWeather?
#   &STATION=`K428`
#   &TPL=`dwdWetterTPL`
#   &QTY=`12`
#   &T1=`06:00`
#   &T2=`12:00`
#   &T3=`18:00`
#   &T4=`00:00`
# ]]
# [[+dwdWeather]]
#
# eine definierte Zeit pro Tag:
# [[!dwdWeather?
#   &STATION=`K428`
#   &TPL=`dwdWetterTPL`
#   &T1=`18:00`
# ]]
# [[+dwdWeather]]
#
# oder
#
# im Dokument ein Chunk "chunkWeather" aufrufen: [[$chunkWeather? &STATION=`K428` &TPL=`dwdWetterTPL` &QTY=`QTY` &T1=`06:00` &T2=`12:00` &T3=`18:00` &T4=`00:00`]] [[+dwdWeather]]
# dann in dem Chunk das Snippet aufrufen: [[!dwdWeather? &STATION=`[[+STATION]]` &TPL=`[[+TPL]]` &QTY=`16` &T1=`[[+T1]]` &T2=`[[+T2]]` &T3=`[[+T3]]` &T4=`[[+T4]]`]]
# und ein eigenes HTML-Gerüst mit den Platzhalter erstellen
#
# Platzhalter für Chunks:
#   -> Ort und Vorhersagedatum: [[+location]] [[+pubDate]] [[+pubDateDay]]
#   -> Sonnenaufgang: [[+sunrise]], Sonnenuntergang: [[+sunset]], Tageslänge: [[+dayduration]], Luftdrucktendenz: [[+pTendenz]] [[+pDelta]]
#
# Beispiel für ein Chunk Template (z.B. dwdWetterTPL) welches per Platzhalter [[+dwdWeather]] dann platziert wird:
#  <div>
#    <div>
#    <h4>[[+fc0]] [[+fc2]] [[+fc1]]</h4>
#    <img src='[[+fc17]]' title='[[+fc16]]' alt='' >
#    </div>
#    [[+fc5:gte=`0.1`:then=`<span class="label blue">[[+fc5]]</span>`:else=`<span class="label red">[[+fc5]]</span>`]]
#    <br />
#    <small>Sonnenschein: [[+fc14]]</small><br />
#     <small>Wolkendecke: [[+fc10]]</small><br />
#      <small>Niederschlag: [[+fc13]]</small><br />
#       <small>Wind (Richtung): [[+fc8]] ([[+fc7]])</small><br />
#        <small>Max. Windböe: [[+fc9]]</small><br />
#         <small>Luftdruck: [[+fc11]]</small><br />
#          <small>Luftfeuchte: [[+fc18]]</small><br />
#           <small>Sichtweite: [[+fc15]]</small><br />
#  </div>
#
#   Vorhersage Platzhalter z.B. für Kalender
#   -> 20 Vorhersagen (10 Tage): [[+fc_V_E]]  (V = Vorhersage Nr (0-19) | E = Elemente (0-18), z.B. [[+fc_0_5]]
#
#   19 Elemente: 0 Date | 1 Time | 2 Day | 3 minT | 4 maxT | 5 2mT | 6 dewPoint | 7 windDir | 8 windSpeed | 9 windGust | 10 cloud |
#   11 hPa | 12 rainKg24h | 13 rainKg6h | 14 sun | 15 vis | 16 sigW | 17 picName | 18 hu |
#
#
#
# Variablen -Start------------------->
   # Chunk Template(default ist ohne)
   
$strTPL $modx->getOption('TPL',$scriptProperties,'');
   
# Anzahl der Vorhersagen (default ist 40, bei 4 pro Tag sind das dann 10 Tage)
   
$intQTY $modx->getOption('QTY',$scriptProperties40);
   
$strTMP MODX_ASSETS_PATH.'dwd_temp/';
   
$strURL 'https://opendata.dwd.de/weather/local_forecasts/mos/MOSMIX_L/single_stations/';
   
$strStation $modx->getOption('STATION',$scriptProperties,'10609'); # Trier (älteste Stadt Deutschlands)
   
$strURL .= $strStation '/kml/MOSMIX_L_LATEST_' $strStation '.kmz';
   
# Icons Bilder Pfad
   
$strURLIcon $modx->config['base_url'].'assets/dwd_img/';     # Wetter-Icons
   # z.B. Forecast 10 Tage = 24*10
   
$MAX_COUNT 24*10;
   
# Forecast
   
$fcAll $modx->getOption('fcAll',$scriptProperties,'false'); # default all-Forecast false
   
$time1 $modx->getOption('T1',$scriptProperties,'12:00'); # default 12:00
   
$time2 $modx->getOption('T2',$scriptProperties,'');
   
$time3 $modx->getOption('T3',$scriptProperties,'');
   
$time4 $modx->getOption('T4',$scriptProperties,'');
   
# Luftdruck gilt als stabil, wenn hPa Delta nicht grösser als
   
$intPStable 4;
   
# Wetter Icons mit oder ohne Sonne (SunD3) anzeigen, ab x %
   
$intSun 30;
   
# Hitzewelle gilt ab wie viel Grad? Wetter Icon Sonne 0h.png (TX)
   
$valMaxT 35.0;        # ab x Grad Celsius (z.B. 35.0)
   # wenn Winter-Sommerzeit angepasst werden muss
   
$bolTimeOffset false;
   
$timeOffset '0';
# Variablen -Ende-------------------<

   
if ($bolTimeOffset) {
      
# Sommerzeit/Winterzeit
      # daylight timeOffset to UTC)
      # 1 bei Sommerzeit, ansonsten 0
         
if(date('I') == 1) {
            
$timeOffset '7200';
         }
         else{
            
$timeOffset '3600';
         }
   }

   
# Ordner anlegen, wenn fehlt
   
if(!file_exists($strTMP)) {
      
mkdir($strTMP0755true);
   }


# relative Luftfeuchtigkeit berechnen
# calculate relative humidity (TTT(K), Td(K))
if (!function_exists('getHumidity')) {
function 
getHumidity($T$TD) {
  if (
is_numeric($T) && is_numeric($TD)) {
    
$T round($T 273.151);
    
$TD round($TD 273.151);
    
$RH=round(100*(exp((17.625*$TD)/(243.04+$TD)) / exp((17.625*$T)/(243.04+$T))));
  } else {
    
$RH '---';
  }
  return 
$RH;
}
}

if (!
function_exists('xml2array')) {
function 
xml2array $xmlObject$out = array () ) {
  foreach ( (array) 
$xmlObject as $index => $node )
  
$out[$index] = ( is_object $node ) ) ? xml2array $node ) : $node;
  return 
$out;
}
}

if (!
function_exists('getParamArray')) {
function 
getParamArray($rootObj$id) {
  foreach (
$rootObj as $param) {
    if ((string) 
$param['elementName'] == $id) {
      
$output preg_replace('!\s+!'';', (string) $param->value);
      
$output explode(';'$output);
      
array_shift($output);
      return 
$output;
    }
  }
}
}

# function direction in N/E/S/W instead of Grad (Windrichtung)
if (!function_exists('getWindDirection')) {
   function 
getWindDirection($degree 0) {
     
$direction = array('N''NNO''NO''ONO''O''OSO''SO''SSO''S''SSW''SW''WSW''W''WNW''NW''NNW');
     
$step 360 / (count($direction));
     
$b floor(($degree + ($step/2)) / $step);
   return 
$direction[$b count($direction)];
   }
}


# ww-Code - Hashs mit deutschen Konditionen (Code/Description), Quellen:
# https://wetterkanal.kachelmannwetter.com/was-ist-der-ww-code-in-der-meteorologie/
# https://www.dwd.de/DE/leistungen/opendata/help/schluessel_datenformate/kml/mosmix_element_weather_xls.html
# es werden nicht alle benötigt, aber wer weiss... ;-)
$strConditions_de = array(
// Bewölkung
 
'0'  => 'Effektive Wolkendecke weniger als 2/8',
 
'1'  => 'Effektive Wolkendecke zwischen 2/8 und 5/8',
 
'2'  => 'Effektive Wolkendecke zwischen 5/8 und 6/8',
 
'3'  => 'Effektive Wolkendecke mindestens 6/8',
// Dunst, Rauch, Staub oder Sand
 
'4'  => 'Sicht durch Rauch oder Asche vermindert',
 
'5'  => 'trockener Dunst (relative Feuchte < 80 %)',
 
'6'  => 'verbreiteter Schwebstaub, nicht vom Wind herangeführt',
 
'7'  => 'Staub oder Sand bzw. Gischt, vom Wind herangeführt',
 
'8'  => 'gut entwickelte Staub- oder Sandwirbel',
 
'9'  => 'Staub- oder Sandsturm im Gesichtskreis, aber nicht an der Station',
// Trockenereignisse
 
'10' => 'feuchter Dunst (relative Feuchte > 80 %)',
 
'11' => 'Schwaden von Bodennebel',
 
'12' => 'durchgehender Bodennebel',
 
'13' => 'Wetterleuchten sichtbar, kein Donner gehört',
 
'14' => 'Niederschlag im Gesichtskreis, nicht den Boden erreichend',
 
'15' => 'Niederschlag in der Ferne (> 5 km), aber nicht an der Station',
 
'16' => 'Niederschlag in der Nähe (< 5 km), aber nicht an der Station',
 
'17' => 'Gewitter (Donner hörbar), aber kein Niederschlag an der Station',
 
'18' => 'Markante Böen im Gesichtskreis, aber kein Niederschlag an der Station',
 
'19' => 'Tromben (trichterförmige Wolkenschläuche) im Gesichtskreis',
// Ereignisse der letzten Stunde, aber nicht zur Beobachtungszeit
 
'20' => 'nach Sprühregen oder Schneegriesel',
 
'21' => 'nach Regen',
 
'22' => 'nach Schneefall',
 
'23' => 'nach Schneeregen oder Eiskörnern',
 
'24' => 'nach gefrierendem Regen',
 
'25' => 'nach Regenschauer',
 
'26' => 'nach Schneeschauer',
 
'27' => 'nach Graupel- oder Hagelschauer',
 
'28' => 'nach Nebel',
 
'29' => 'nach Gewitter',
// Staubsturm, Sandsturm, Schneefegen oder -treiben
 
'30' => 'leichter oder mäßiger Sandsturm, an Intensität abnehmend',
 
'31' => 'leichter oder mäßiger Sandsturm, unveränderte Intensität',
 
'32' => 'leichter oder mäßiger Sandsturm, an Intensität zunehmend',
 
'33' => 'schwerer Sandsturm, an Intensität abnehmen',
 
'34' => 'schwerer Sandsturm, unveränderte Intensität',
 
'35' => 'schwerer Sandsturm, an Intensität zunehmend',
 
'36' => 'leichtes oder mäßiges Schneefegen, unter Augenhöhe',
 
'37' => 'starkes Schneefegen, unter Augenhöhe',
 
'38' => 'leichtes oder mäßiges Schneetreiben, über Augenhöhe',
 
'39' => 'starkes Schneetreiben, über Augenhöhe',
// Nebel oder Eisnebel
 
'40' => 'Nebel in einiger Entfernung',
 
'41' => 'Nebel in Schwaden oder Bänken',
 
'42' => 'Nebel, Himmel erkennbar, dünner werdend',
 
'43' => 'Nebel, Himmel nicht erkennbar, dünner werdend',
 
'44' => 'Nebel, Himmel erkennbar, unverändert',
 
'45' => 'Nebel, Himmel nicht erkennbar, unverändert',
 
'46' => 'Nebel, Himmel erkennbar, dichter werdend',
 
'47' => 'Nebel, Himmel nicht erkennbar, dichter werdend',
 
'48' => 'Nebel mit Reifansatz, Himmel erkennbar',
 
'49' => 'Nebel mit Reifansatz, Himmel nicht erkennbar',
// Sprühregen
 
'50' => 'unterbrochener leichter Sprühregen',
 
'51' => 'durchgehend leichter Sprühregen',
 
'52' => 'unterbrochener mäßiger Sprühregen',
 
'53' => 'durchgehend mäßiger Sprühregen',
 
'54' => 'unterbrochener starker Sprühregen',
 
'55' => 'durchgehend starker Sprühregen',
 
'56' => 'leichter gefrierender Sprühregen',
 
'57' => 'mäßiger oder starker gefrierender Sprühregen',
 
'58' => 'leichter Sprühregen mit Regen',
 
'59' => 'mäßiger oder starker Sprühregen mit Regen',
// Regen
 
'60' => 'unterbrochener leichter Regen oder einzelne Regentropfen',
 
'61' => 'durchgehend leichter Regen',
 
'62' => 'unterbrochener mäßiger Regen',
 
'63' => 'durchgehend mäßiger Regen',
 
'64' => 'unterbrochener starker Regen',
 
'65' => 'durchgehend starker Regen',
 
'66' => 'leichter gefrierender Regen',
 
'67' => 'mäßiger oder starker gefrierender Regen',
 
'68' => 'leichter Schneeregen',
 
'69' => 'mäßiger oder starker Schneeregen',
// Schnee
 
'70' => 'unterbrochener leichter Schneefall oder einzelne Schneeflocken',
 
'71' => 'durchgehend leichter Schneefall',
 
'72' => 'unterbrochener mäßiger Schneefall',
 
'73' => 'durchgehend mäßiger Schneefall',
 
'74' => 'unterbrochener starker Schneefall',
 
'75' => 'durchgehend starker Schneefall',
 
'76' => 'Eisnadeln (Polarschnee)',
 
'77' => 'Schneegriesel',
 
'78' => 'Schneekristalle',
 
'79' => 'Eiskörner (gefrorene Regentropfen)',
// Schauer
 
'80' => 'leichter Regenschauer',
 
'81' => 'mäßiger oder starker Regenschauer',
 
'82' => 'äußerst heftiger Regenschauer',
 
'83' => 'leichter Schneeregenschauer',
 
'84' => 'mäßiger oder starker Schneeregenschauer',
 
'85' => 'leichter Schneeschauer',
 
'86' => 'mäßiger oder starker Schneeschauer',
 
'87' => 'leichter Graupelschauer',
 
'88' => 'mäßiger oder starker Graupelschauer',
 
'89' => 'leichter Hagelschauer',
 
'90' => 'mäßiger oder starker Hagelschauer',
// Gewitter
 
'91' => 'Gewitter in der letzten Stunde, zurzeit leichter Regen',
 
'92' => 'Gewitter in der letzten Stunde, zurzeit mäßiger oder starker Regen',
 
'93' => 'Gewitter in der letzten Stunde, zurzeit leichter Schneefall/Schneeregen/Graupel/Hagel',
 
'94' => 'Gewitter in der letzten Stunde, zurzeit mäßiger oder starker Schneefall/Schneeregen/Graupel/Hagel',
 
'95' => 'leichtes oder mäßiges Gewitter mit Regen oder Schnee',
 
'96' => 'leichtes oder mäßiges Gewitter mit Graupel oder Hagel',
 
'97' => 'starkes Gewitter mit Regen oder Schnee',
 
'98' => 'starkes Gewitter mit Sandsturm',
 
'99' => 'starkes Gewitter mit Graupel oder Hagel',
 
'100' => 'not available'
);



# Wetter Icons
if (!function_exists('wwPic')) {
   function 
wwPic($Code$bolSun$intTagBeginn$intTagEnde$WT$bolMaxT) {
     
# $intHour = date('H');
     
$intHour $WT;
     
$bolDay  = ($intHour $intTagBeginn && $intHour $intTagEnde);

      switch (
$Code) {
case 0:
# wenn Tag und heiss: 0h | wenn Tag: 0d | wenn Nacht: 0n
            
if ($bolDay == true and $bolMaxT == true) {
                
$icon '0h';
            } elseif (
$bolDay == true) {
                
$icon '0d';
            } else {
                
$icon '0n';
            }
break;
case 1:
# wenn sonniger Tag: 1s | wenn Tag: 1d | wenn Nacht: 1n
            
if ($bolDay == true and $bolSun == true) {
                
$icon '1s';
            } elseif (
$bolDay == true) {
                
$icon '1d';
            } else {
                
$icon '1n';
            }
break;
case 2:
# wenn sonniger Tag: 2s | wenn Tag: 2d | wenn Nacht: 2n
            
if ($bolDay == true and $bolSun == true) {
                
$icon '2s';
            } elseif (
$bolDay == true) {
                
$icon '2d';
            } else {
                
$icon '2n';
            }
break;
case 3:
                
# wenn Tag: 3d | wenn Nacht: 3n
$icon = ($bolDay) ? '3d' '3n';
break;
case 4:
case 5:
case 6:
case 7:
case 8:
case 9:
$icon '4-9';
break;
case 10:
case 11:
case 12:
case 13:
case 14:
case 15:
case 16:
$icon '10-16';
break;
case 17:
$icon '17';
break;
case 18:
$icon '18';
break;
case 19:
$icon '19';
break;
case 20:
$icon '20';
break;
case 21:
$icon '21';
break;
case 22:
$icon '22';
break;
case 23:
case 24:
$icon '23-24';
break;
case 25:
$icon '25';
break;
case 26:
$icon '26';
break;
case 27:
$icon '27';
break;
case 28:
$icon '28';
break;
case 29:
$icon '29';
break;
case 30:
case 31:
case 32:
$icon '30-32';
break;
case 33:
case 34:
case 35:
$icon '33-35';
break;
case 36:
case 37:
case 38:
case 39:
$icon '36-39';
break;
case 40:
case 41:
case 42:
case 43:
case 44:
case 45:
case 46:
case 47:
case 48:
case 49:
$icon '40-49';
break;
case 50:
case 51:
case 52:
case 53:
$icon '50-53';
break;
case 54:
case 55:
case 56:
case 57:
case 58:
case 59:
$icon '55-59';
break;
case 60:
case 61:
case 62:
case 63:
case 64:
case 65:
$icon '60-65';
break;
case 66:
case 67:
$icon '66-67';
break;
case 68:
case 69:
$icon '68-69';
break;
case 70:
case 71:
case 72:
case 73:
case 74:
case 75:
case 76:
case 77:
case 78:
case 79:
$icon '70-79';
break;
case 80:
# wenn sonniger Tag: 80s | wenn Tag: 80d | wenn Nacht: 80n
            
if ($bolDay == true and $bolSun == true) {
                
$icon '80s';
            } elseif (
$bolDay == true) {
                
$icon '80d';
            } else {
                
$icon '80n';
            }
break;
case 81:
$icon '81';
break;
case 82:
$icon '82';
break;
case 83:
case 84:
$icon '83-84';
break;
case 85:
case 86:
    case 
87:
    case 
88:
$icon '85-88';
break;
case 89:
case 90:
$icon '89-90';
break;
case 91:
case 92:
case 93:
case 94:
case 95:
case 96:
case 97:
case 98:
case 99:
$icon '91-99';
break;
// default
         
default:
$icon 'unknown';
break;
      }
   return 
$icon.'.png';
   }
}



   
# max. stündlich eine neue Datei ([Station]_[ISO-Datum]_[h]_dwdWeather.kmz) erstellen und alle alte [Station].* löschen
   # Start------------------->
   
$strDatumStunde date('Y-m-d_G');
   
$strZieldatei $strTMP.$strStation.'_'.$strDatumStunde.'_dwdWeather.kmz';

   if(!
file_exists($strZieldatei)) {
      
array_map('unlink'glob($strTMP.$strStation.'*'));
      
# Datei per CURL abholen -Start------------------->
      
if (function_exists('curl_version')) {
         
$ch curl_init($strURL);
         
$zieldatei fopen($strZieldatei'w');
         
# deaktiviere SSL Überprüfung
         # curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, 0);
         # curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, 0);
         
curl_setopt($chCURLOPT_FILE$zieldatei);
         
curl_setopt($chCURLOPT_TIMEOUT3600);
         
curl_exec($ch);
         
$intReturnCode curl_getinfo($chCURLINFO_HTTP_CODE);
         
fclose($zieldatei);
         
# prüfe ob die Seite erreichbar ist!
         
if ($intReturnCode != 200 && $intReturnCode != 302 && $intReturnCode != 304) {return 'ERROR: Page not available!';};
         }
      
# Datei per CURL abholen -Ende--------------------<
   
# max. stündlich -Ende-------------------<


   # lösche Datei wenn die Dateigrösse 0 ist
   
clearstatcache();
   if(
== filesize($strZieldatei)) {
     
array_map('unlink'glob($strTMP.$strStation.'*'));
     return 
'ERROR: File is empty and due that deleted!';
   }


    
# downloaded source data (*.kmz)
    
$fn $strZieldatei;
    
$za = new ZipArchive();
    
$za->open($fn);


    
# Header-Infos
    
$stat $za->statIndex(0);
    
$data file_get_contents('zip://'.$strZieldatei.'#'.$stat['name']);

    
# Ort, Ausgabezeit und Lokation (für Sonnenaufgang und Sonnenuntergang Berechnung)
    
$xml2 simplexml_load_string($data);
    
$xmlDocument $xml2->children('kml'true)->Document;

    
$location = (string) $xmlDocument->Placemark->description;
    
$coordinates = (string) $xmlDocument->Placemark->Point->coordinates;   # Bitburg "6.53,49.98,359.0"
    
$coordinates explode(','$coordinates);

    
$now time();
    
# PHP 8.1: date_sunrise, date_sunset functions are deprecated (in PHP 9.0 will be removed) and replaced with date_sun_info
    # $zenith = 90+50/60;
    # $sunset = date_sunset($now, SUNFUNCS_RET_TIMESTAMP, $coordinates[1], $coordinates[0], $zenith);
    # $sunrise = date_sunrise($now, SUNFUNCS_RET_TIMESTAMP, $coordinates[1], $coordinates[0], $zenith);
    
$suninfo date_sun_info($now$coordinates[1], $coordinates[0]);
    
$sunrise $suninfo['sunrise'];
    
$sunset  $suninfo['sunset'];

    
$mycoordinates $coordinates[1] .', '$coordinates[0];
    
$dayduration $sunset $sunrise;
      
$sunrise date('H:i',$sunrise);
      
$sunset date('H:i',$sunset);
        
$dayduration round($dayduration/60/602);
        
$dayduration str_replace(',''.'$dayduration);

    
# Platzhalter Sonnenaufgang, Sonnenuntergang, Tageslänge und Koordinaten
    
$modx->setPlaceholder('sunrise'$sunrise);
    
$modx->setPlaceholder('sunset'$sunset);
    
$modx->setPlaceholder('dayduration'$dayduration);
    
$modx->setPlaceholder('coordinates'$mycoordinates);

    
$pubDate = (string) $xmlDocument->ExtendedData->children('dwd'true)->ProductDefinition->IssueTime;
      
$pubDate strtotime($pubDate) + $timeOffset;
        
$pubDateDay date('w'$pubDate);
        
$pubDate date('Y-m-d H:i'$pubDate);
        
$wochentag = array('So.''Mo.''Di.''Mi.''Do.''Fr.''Sa.');
        
$pubDateDay $wochentag[$pubDateDay];

    
# Platzhalter Ort, Koordinaten und Veröffentlichungsdatum
    
$modx->setPlaceholder('location'$location);
    
$modx->setPlaceholder('pubDate'$pubDate);
    
$modx->setPlaceholder('pubDateDay'$pubDateDay);


    
# short name / long name (for header)
    # RR6c not available for all hours! 6am, 12am, 6pm and 12pm - if needed for all hours: change all RR6c to RR1c
    # RR6c = better precipitation forecasts
    
$alias = array(
      
'TN' => 'minT',        // Minimum temperature - within the last 12 hours (Kelvin) | nur 06:00 und 18:00 Uhr!
      
'TX' => 'maxT',        // Maximum temperature - within the last 12 hours (Kelvin) | nur 06:00 und 18:00 Uhr!
      
'TTT' => '2mT',        // Temperature 2m above surface (Kelvin)
      
'Td' => 'dewPoint',    // Dewpoint 2m above surface (Kelvin)
      
'DD' => 'windDir',     // 0°..360°, Wind direction
      
'FF' => 'windSpeed',   // Wind speed (m/s) | m/s * 3.6 = km/h
      
'FX3' => 'windGust',   // Wind speed (m/s) | m/s * 3.6 = km/h
      
'Neff' => 'cloud',     // Effective cloud cover (%)
      
'PPPP' => 'hPA',       // Surface pressure, reduced | hPA (mBAR)= Pa/1000
      
'RRdc' => 'rainKG24h'// Total precipitation last 24 hour consistent with significant weather | Niederschlag 1 Ltr pro kg/m2 = 1 mm
      
'RR6c' => 'rainKg6h',  // Total precipitation last 6 hour consistent with significant weather | Niederschlag 1 Ltr pro kg/m2 = 1 mm
      
'SunD3' => 'sun',      // Sunshine duration during the last three hours (s)
      
'VV' => 'vis',         // Visibility (m) | wird in km umgerechnet
      
'ww' => 'sigW'         // Significant Weather (ID)
    
);
    
$ids array_keys($alias);




for(
$i=0$i<$za->numFiles$i++) {
    
$stat $za->statIndex($i);
    
$data file_get_contents('zip://'.$strZieldatei.'#'.$stat['name']);

    
$data str_replace(
      array(
"kml:""dwd:"),
      array(
""""),
      
$data
    
);

    
$xml simplexml_load_string($data);
    
$timeSteps xml2array($xml->Document->ExtendedData->ProductDefinition->ForecastTimeSteps->TimeStep);
    
$lines array_fill(0count($timeSteps), array());


# Datum (ISO) | Zeit | Wochentag
    
foreach ($timeSteps as $key => $value) {
        
$date = new DateTime($value);
        
array_push($lines[$key], $date->format('Y-m-d'));
        
array_push($lines[$key], $date->format('H:i'));
array_push($lines[$key], $wochentag[$date->format('w')]);
    } 
// $timeSteps


   
$fnode $xml->Document->Placemark->ExtendedData->Forecast;
    foreach (
$ids as $id) {
        
$param getParamArray($fnode$id);

        if(
is_array($param)){
           if (
count($param) === 0) {
             
$param array_fill(0count($timeSteps), '---');
           }
        } else {
             
# PHP7.2 prevents warning: "Parameter must be an array or an object that implements Countable"
             
$param array_fill(0count($timeSteps), '---');
        }

        foreach (
$param as $key => $value) {
            
# prevents PHP warning "a non-numeric value encountered"
            
if($value !== null && !is_numeric($value)) {
                
$value 0;
            }
            
$v $value;

            if (
in_array($id, array('TN''TX''TTT''Td'))) {
                
$v round(floatval($value) - 273.151);
                
$v str_replace(',''.'$v);
            }
            if (
$id == 'PPPP') {
                
$v round($value 1000);
            }
            if (
in_array($id, array('Neff''Nh''Nm''Nl''ww'))) {
                
$v round($value);
            }
            if (
in_array($id, array('RRhc''RRdc''RR6c'))) {
                
$v round($value1);
                
$v str_replace(',''.'$v);
            }
            if (
$id == 'VV') {
                
$v round(floatval($value) / 10002);
                
$v str_replace(',''.'$v);
            }
            if (
$id == 'ww') {
                
$v $strConditions_de[$v];
            }
            if (
$id == 'DD') {
                
$v getWindDirection(round($value));
            }
            if (
in_array($id, array('FF''FX3'))) {
                
$v round(floatval($value) * 3.6);
            }

            
# Returns an array with units
            
if (in_array($id, array('TN''TX''TTT''Td'))) {
                
$v $v.' °C';
            }
            if (
in_array($id, array('FF''FX3'))) {
                
$v $v.' km/h';
            }
            if (
$id == 'Neff') {
                
$v $v.' % (effektiv)';
            }
            if (
$id == 'SunD3') {
                
# Zeit umrechnen in %/3h
                
$v floatval($v) / 3600;
                
$v round($v 100 3);
                
$v $v.' %';
            }
            if (
$id == 'DRR1') { # 1h
                
$v $v 60;
                
$v $v.' min/h';
            }
            if (
$id == 'RRdc') { # 24h
                
$v $v.' Ltr/24h';
            }
            if (
$id == 'RRhc') { # 12h
                
$v $v.' Ltr/12h';
            }
            if (
$id == 'RR6c') { # 6h
                
$v $v.' Ltr/6h';
            }
            if (
$id == 'PPPP') {
                
$v $v.' hPA';
            }
            if (
$id == 'VV') {
                
$v $v.' km';
            }
            if (
$id == '-') {
                
$v '---';
            }
            
array_push($lines[$key], $v);
        }
    }
// foreach $ids



    // get Picture No (Significant Weather - ww)
    // get Sun (SunD3)
    // get Temp (TTT)
    // get Weather Time ($WT) | Uhrzeit
    
$ww getParamArray($fnode'ww');
    
$rs getParamArray($fnode'SunD3');
    
$ttt getParamArray($fnode'TTT');
    foreach (
$ww as $key => $value) {
       
# $intW = round(floatval($ww[$key]));
       
$valTTT round(floatval($ttt[$key]) - 273.151);
       
$intS round(floatval($rs[$key]));

          
# Zeit umrechnen in %/3h
          
$intS floatval($intS) / 3600;
          
$intS round($intS 100 3);

          if(
$intS >= $intSun) {
             
$bolSun true;
          }
          else{
             
$bolSun false;
          }
          if(
$valTTT >= $valMaxT) {
             
$bolMaxT true;
          }
          else{
             
$bolMaxT false;
          }

      
# für Wetter Icons (Tag oder Nacht)
      
$tr strtotime($sunrise);
      
$tr intval(date('G',$tr));
      
$intTagBeginn $tr 1;

      
$ts strtotime($sunset);
      
$ts intval(date('G',$ts));
      
$intTagEnde $ts 1;

      
$WT strtotime($lines[$key][1]); # Uhrzeit
      
$WT intval(date('G',$WT));

      
array_push($lines[$key], $strURLIcon.wwPic(round(floatval($value)), $bolSun$intTagBeginn$intTagEnde$WT$bolMaxT));
    }

    
// berechnen der Luftfeuchtigkeit
    // calculate humidity (hu %)
    
$t getParamArray($fnode'TTT');  # Temperature 2m above surface
    
$d getParamArray($fnode'Td');   # Dewpoint 2m above surface
    
foreach ($t as $key => $value) {
        
array_push($lines[$key], getHumidity($value$d[$key]).' %');
    }


    
$csvOutput '';

    
// output header
    # $csvOutput = str_replace(
    #  array_keys($alias),
    #  array_values($alias),
    #  'Date|Time|Tag|'.implode('|', $ids).'|pic'.'|hu'.'||'
    # );

    // slice & output content
    
$lines array_slice($lines0$MAX_COUNT);
    foreach (
$lines as $line) {
       if (
$fcAll == 'false'){
           if (
$line[1] == $time1 or $line[1] == $time2 or $line[1] == $time3 or $line[1] == $time4){
               
$csvOutput $csvOutputimplode('|'$line).'||';
           }
       } else {
           
$csvOutput $csvOutputimplode('|'$line).'||';
       }
    }

// END numFiles


# echo $csvOutput;

# mehrdimensionales Array erstellen
$array array_map(function($v){return str_getcsv($v'|');}, explode('||'$csvOutput));
# print_r($array);

$intCA count($array) -1;
unset(
$array[$intCA]); # RIP last array (it is empty)


    # Luftdrucktendenz - Zeitdifferenz in Stunden zwischen den 2 Messungen
    
$tPa1 strtotime($array[0][0].' '.$array[0][1]);
    
$tPa2 strtotime($array[1][0].' '.$array[1][1]);
    
$tPaDelta $tPa2 $tPa1;
    
$intStundenPaDelta round($tPaDelta/60/600);

    
# Luftdrucktendenz (Stabil wenn hPa Delta kleiner als $intPStable)
    
$hPa1 intval($array[0][11]);
    
$hPa2 intval($array[1][11]);

    
$hPaDelta $hPa2 $hPa1;
    
$hPaDeltaABS abs($hPaDelta);
    
# bei positiven hPaDelta ein Pluszeichen für die Ausgabe setzen
      
if ($hPaDelta 0) {
          
$hPaDelta sprintf("%+d",$hPaDelta);
      }

    if (
$hPaDeltaABS $intPStable) {
       if (
$hPa1 $hPa2) {
           
$strPTendenz 'fallend';
       } else {
           
$strPTendenz 'steigend';
       }
       
$modx->setPlaceholder('pDelta''('.$hPaDelta.' hPa/'.$intStundenPaDelta.'h)');

    } else {
         
$strPTendenz 'stabil';
         
$modx->setPlaceholder('pDelta''');
    }
    
$modx->setPlaceholder('pTendenz'$strPTendenz);


  
$output '';
  
$arr '';
  
$arr = array();
  
$arr2 '';
  
$arr2 = array();

  foreach (
$array AS $key => $value) {
  if (
$key >= $intQTY) break;

        foreach (
$value AS $subKey => $subValue) {
            
# echo $key.' | '.$subKey.' | '.$subValue.'<br>';

            # Platzhalter (z.B. für Kalender)
            
$modx->setPlaceholder('fc_'.$key.'_'.$subKey$subValue);

            
# Array für getChunk (kann per Platzhalter [[+dwdWeather]] platziert werden)
            
$arr = ['FC' => $key'fc'.$subKey => $subValue];
            
$arr $arr $arr2;
            
$arr2 $arr;
        }

        if (
$arr) {
            
$output .= $modx->getChunk($strTPL$arr);
        }
  }

$modx->setPlaceholder('dwdWeather'$output);




Optional mit einem extra Snippet getTimeRoundH -> Vorhersage startet mit der nächsten vollen Stunde, z.B:
[[!dwdWeather?
   &STATION=`K428`
   &QTY=`20`
   &TPL=`dwdWetterTPL`
   &T1=`[[!getTimeRoundH]]`
   &T2=`[[!getTimeRoundH? &add=`6`]]`
   &T3=`[[!getTimeRoundH? &add=`12`]]`
   &T4=`[[!getTimeRoundH? &add=`18`]]`
]]

<?php
# get time and round hour
# Uhrzeit für das Wetter auf die volle Stunde aufrunden, aus "10:42" wird dann "11:00"
# z.B. [[!getTimeRoundH]] oder plus 4h [[!getTimeRoundH? &add=`4`]]

$timestamp time();
$timestamp ceil($timestamp/3600)*3600;

if (isset(
$add)) {
   
$timestamp $timestamp + ($add 3600); # 3600 = 1h
}

return 
date('H:i'$timestamp);
#40
LINUX / Raspberry und LibreELEC
Letzter Beitrag von Jo - 2018-02-18 | 11:40:12
Hardware Update

Derzeit nutze ich einen Raspberry Pi 3 Model B mit einer Samsung PRO Plus Micro SDXC 64GB

Eines der beliebtesten Einsatzgebiete ist den Raspberry als Mediacenter zu nutzen.
Auf Kodi (ursprünglichen XBMC) basierend sind die bekanntesten wohl OpenELEC und LibreELEC.

Auf den neueren Raspi-Modellen besitzt das Mediacenter LibreELEC eine äußerst gute Video-Performance. Derzeit nutze ich LibreELEC Version 8.2.3 mit KODI 17 (Krypton).

Selbst für Einsteiger ist die Installation von LibreELEC gegenüber OpenELEC sehr einfach.
Dazu müsst ihr euch nur den LibreELEC SD-Creator für LINUX, MAC oder Windows laden und könnt mit diesem Tool die aktuellste Version von LibreELEC auf euren USB-Stick oder SD-Karte für den Raspberry installieren.

LibreELEC SD-Creator mit LINUX per Terminal laden und starten:

cd ~/Downloads
wget http://releases.libreelec.tv/LibreELEC.USB-SD.Creator.Linux-64bit.bin
chmod +x LibreELEC.USB-SD.Creator.Linux-64bit.bin
sudo ./LibreELEC.USB-SD.Creator.Linux-64bit.bin



Tipps:

  • Vor dem ersten Start am TV die Settings auf Anynet oder HDMI-CEC setzen (Steuerung für HDMI), dann funzt eure TV Fernbedienung mit LibreELEC
  • Ihr könnt auch eine USB Maus und Tastatur anschließen
  • Beim ersten Start werdet ihr nach dem Hostname gefragt, Standard ist "LibreELEC"
  • SSH und Samba Service aktivieren, Resolution 1920×1080p (HD) und alles auf Deutsch umstellen
  • LINUX über SSH mit dem Pi verbinden -> User "root" und das Passwort ist "libreelec"
  • Kodi hat inzwischen auch ein eigenes MediaThekView-Addon :-)


Add-on PVR IPTV Simple Client (PVR = Personal Video Recorder)
Unter Addon -> Benutzer Addons -> PVR Clients solltet ihr den Simple Client finden.
URL Playlist Links (m3u) findet ihr im www. IPTV ist z.B eine Sammlung von frei empfangbaren Streams für TV, meine Liste: http://www.jolichter.de/iptv/livetv.m3u