| Both sides previous revision Previous revision Next revision | Previous revision Next revisionBoth sides next revision |
| docs:guide-user:advanced:opkg_extras [2022/02/20 09:23] – Mention Attended sysUpgrade as an alternative vpelletier | docs:guide-user:advanced:opkg_extras [2023/10/03 18:19] – [Instructions] delay for networking to become ready vgaetera |
|---|
| ====== Opkg extras ====== | ====== Opkg extras ====== |
| {{section>meta:infobox:howto_links#cli_skills&noheader&nofooter&noeditbutton}} | {{section>meta:infobox:howto_links#basic_skills&noheader&nofooter&noeditbutton}} |
| |
| ===== Introduction ===== | ===== Introduction ===== |
| * Restore automatically after firmware upgrade. | * Restore automatically after firmware upgrade. |
| * Upgrade all upgradable packages. | * Upgrade all upgradable packages. |
| * Find new configurations. | * Fix symbolic links for installed alternatives. |
| | * Find new configurations for upgraded packages. |
| |
| ===== Implementation ===== | ===== Implementation ===== |
| * Rely on [[docs:guide-user:base-system:uci|UCI]] and [[https://github.com/openwrt/openwrt/blob/master/package/base-files/Makefile#L47|backup defaults]] to store and manage profiles. | * Rely on [[docs:guide-user:base-system:uci|UCI]] and [[https://github.com/openwrt/openwrt/blob/master/package/base-files/Makefile#L47|backup defaults]] to store and manage profiles. |
| * Identify package types with [[man>grep(1)|grep]] and [[man>find(1)|find]], and RWM with [[man>mount(8)|mount]]. | * Identify package types with [[man>grep(1)|grep]] and [[man>find(1)|find]], and RWM with [[man>mount(8)|mount]]. |
| * Support importing [[https://github.com/openwrt/openwrt/blob/master/package/base-files/files/sbin/sysupgrade#L245-L251|user-installed]] packages from [[docs:techref:sysupgrade|Sysupgrade]]. | * Support importing [[https://github.com/openwrt/openwrt/blob/master/package/base-files/files/sbin/sysupgrade#L249-L255|user-installed]] packages from [[docs:techref:sysupgrade|Sysupgrade]]. |
| * Use [[docs:guide-user:base-system:hotplug|Hotplug]] to detect WAN connectivity and trigger profile restore. | * Use [[docs:guide-user:advanced:hotplug_extras|Hotplug extras]] to detect WAN connectivity and trigger profile restore. |
| * Utilize lockfiles with [[https://github.com/openwrt/openwrt/blob/master/package/utils/busybox/patches/220-add_lock_util.patch|lock]] to avoid race conditions and loops. | * Utilize lockfiles with [[https://github.com/openwrt/openwrt/blob/master/package/utils/busybox/patches/220-add_lock_util.patch|lock]] to avoid race conditions and loops. |
| * Perform [[man>reboot(8)|reboot]] to apply changes after automatic profile restore. | * Perform [[man>reboot(8)|reboot]] to apply changes after automatic profile restore. |
| * Write and read non-interactive logs with [[docs:guide-user:base-system:log.essentials|Syslog]] for troubleshooting. | |
| * Fetch the default profile to restore and roll back from UCI, unless specified manually. | * Fetch the default profile to restore and roll back from UCI, unless specified manually. |
| * Take precedence for remove over install to avoid package conflicts while restoring profile. | * Take precedence for remove over install to avoid package conflicts while restoring profile. |
| | ''**uci** [<prof>] < <uciprof>'' | Import Opkg profile from stdin or file to UCI. | | | ''**uci** [<prof>] < <uciprof>'' | Import Opkg profile from stdin or file to UCI. | |
| | ''**import** [<bakprof>]'' | Import Opkg profile from Sysupgrade backup to UCI. | | | ''**import** [<bakprof>]'' | Import Opkg profile from Sysupgrade backup to UCI. | |
| | ''**save** [<prof>]'' | Save the current Opkg profile to UCI. | | | ''**save**'' | Save the current Opkg profile to UCI. | |
| | ''**restore** [<prof>]'' | Restore Opkg profile:\\ ''auto'' or none - default profile,\\ ''rwm'' - RWM profile,\\ ''custom'' - custom profile. | | | ''**restore** [<prof>]'' | Restore Opkg profile:\\ ''main'' or none - default profile,\\ ''init'' - RWM/minimal profile,\\ ''custom'' - custom profile. | |
| | ''**rollback** [<prof>]'' | Roll back Opkg profile:\\ remove user-installed packages,\\ install user-removed packages,\\ skip upgraded packages. | | | ''**rollback** [<prof>]'' | Roll back Opkg profile:\\ remove user-installed packages,\\ install user-removed packages,\\ skip upgraded packages. | |
| | ''**upgr** [<pkgtype>]'' | Upgrade packages by type:\\ ''ai'' or none - all installed,\\ ''oi'' - overlay-installed. | | | ''**upgr** [<pkgtype>]'' | Upgrade packages by type:\\ ''ai'' or none - all installed,\\ ''oi'' - overlay-installed. | |
| | ''**proc** <cmd> < <pkgs>'' | Process packages from stdin with the given sub-command. | | | ''**proc** <cmd> < <pkgs>'' | Process packages from stdin with the given sub-command. | |
| | ''**reinstall** <pkgs>'' | Reinstall specific packages. | | | ''**reinstall** <pkgs>'' | Reinstall specific packages. | |
| | ''**newconf** [<path>]'' | Find new configurations. | | | ''**altlink**'' | Fix symbolic links for installed alternatives. | |
| | | ''**newconf** [<path>]'' | Find new configurations for upgraded packages. | |
| |
| ===== Instructions ===== | ===== Instructions ===== |
| local OPKG_UCI="$(uci -q get opkg.defaults."${OPKG_CMD}")" | local OPKG_UCI="$(uci -q get opkg.defaults."${OPKG_CMD}")" |
| case "${OPKG_CMD}" in | case "${OPKG_CMD}" in |
| (init|uci|import|save|restore|rollback\ | (init|uci|import|save|restore|rollback|upgr\ |
| |upgr|export|newconf|proc|reinstall) opkg_"${@}" ;; | |export|proc|reinstall|altlink|newconf) opkg_"${@}" ;; |
| (*) command opkg "${@}" ;; | (*) command opkg "${@}" ;; |
| esac | esac |
| set opkg.defaults='opkg' | set opkg.defaults='opkg' |
| set opkg.defaults.import='/etc/backup/installed_packages.txt' | set opkg.defaults.import='/etc/backup/installed_packages.txt' |
| set opkg.defaults.save='auto' | set opkg.defaults.restore='init main' |
| set opkg.defaults.restore='auto' | set opkg.defaults.rollback='main' |
| set opkg.defaults.rollback='auto' | |
| set opkg.defaults.upgr='ai' | set opkg.defaults.upgr='ai' |
| set opkg.defaults.export='ai' | set opkg.defaults.export='ai' |
| opkg_uci() { | opkg_uci() { |
| local OPKG_OPT="${1:-${OPKG_UCI}}" | local OPKG_OPT="${1:-${OPKG_UCI}}" |
| local OPKG_OPT="${OPKG_OPT:-auto}" | local OPKG_OPT="${OPKG_OPT:-main}" |
| if ! uci -q get opkg > /dev/null | if ! uci -q get opkg > /dev/null |
| then opkg init | then opkg init |
| then sed -n -r -e "s/\s(overlay|unknown)$/\ | then sed -n -r -e "s/\s(overlay|unknown)$/\ |
| \tipkg/p" "${OPKG_OPT}" \ | \tipkg/p" "${OPKG_OPT}" \ |
| | opkg uci auto | | opkg uci main |
| fi | fi |
| } | } |
| |
| opkg_save() { | opkg_save() { |
| local OPKG_OPT="${1:-${OPKG_UCI}}" | |
| local OPKG_WR="$(opkg export wr)" | local OPKG_WR="$(opkg export wr)" |
| local OPKG_WI="$(opkg export wi)" | local OPKG_WI="$(opkg export wi)" |
| sed -e "s/$/\trpkg/" "${OPKG_UR}" | sed -e "s/$/\trpkg/" "${OPKG_UR}" |
| sed -e "s/$/\tipkg/" "${OPKG_UI}" | sed -e "s/$/\tipkg/" "${OPKG_UI}" |
| } | opkg uci "${OPKG_OPT}" | } | opkg uci main |
| rm -f "${OPKG_WR}" "${OPKG_WI}" "${OPKG_UR}" "${OPKG_UI}" | rm -f "${OPKG_WR}" "${OPKG_WI}" "${OPKG_UR}" "${OPKG_UI}" |
| } | } |
| local OPKG_OPT="${1:-${OPKG_UCI}}" | local OPKG_OPT="${1:-${OPKG_UCI}}" |
| local OPKG_CONF="${OPKG_OPT}" | local OPKG_CONF="${OPKG_OPT}" |
| | for OPKG_CONF in ${OPKG_CONF} |
| | do |
| local OPKG_AI="$(opkg export ai)" | local OPKG_AI="$(opkg export ai)" |
| local OPKG_PR="$(opkg export pr)" | local OPKG_PR="$(opkg export pr)" |
| | opkg proc install | | opkg proc install |
| rm -f "${OPKG_AI}" "${OPKG_PR}" "${OPKG_PI}" | rm -f "${OPKG_AI}" "${OPKG_PR}" "${OPKG_PI}" |
| | done |
| } | } |
| |
| local OPKG_OPT="${OPKG_UCI}" | local OPKG_OPT="${OPKG_UCI}" |
| opkg install "${@}" ${OPKG_OPT} | opkg install "${@}" ${OPKG_OPT} |
| | } |
| | |
| | opkg_altlink() { |
| | sed -n -e "/^Alternatives:/\ |
| | {s/^\S*\s*//;s/,\s/\n/gp}" /usr/lib/opkg/status \ |
| | | sort -n -t ":" \ |
| | | while IFS=":" read -r OPKG_PRIO OPKG_LINK OPKG_ALT |
| | do ln -f -s "${OPKG_ALT}" "${OPKG_LINK}" |
| | done |
| } | } |
| |
| mkdir -p /etc/hotplug.d/online | mkdir -p /etc/hotplug.d/online |
| cat << "EOF" > /etc/hotplug.d/online/50-opkg-restore | cat << "EOF" > /etc/hotplug.d/online/50-opkg-restore |
| OPKG_CONF="init main" | OPKG_CONF="$(uci -q get opkg.defaults.restore)" |
| for OPKG_CONF in ${OPKG_CONF} | for OPKG_CONF in ${OPKG_CONF} |
| do if [ ! -e /etc/opkg-restore-"${OPKG_CONF}" ] \ | do if [ ! -e /etc/opkg-restore-"${OPKG_CONF}" ] \ |
| && lock -n /var/lock/opkg-restore \ | && lock -n /var/lock/opkg-restore \ |
| | && sleep 10 \ |
| && opkg update | && opkg update |
| then . /etc/profile.d/opkg.sh | then . /etc/profile.d/opkg.sh |
| opkg restore "${OPKG_CONF/main}" 2>&1 \ | opkg restore "${OPKG_CONF}" &> \ |
| | logger -t opkg | /var/log/opkg-restore-"${OPKG_CONF}" |
| touch /etc/opkg-restore-"${OPKG_CONF}" | touch /etc/opkg-restore-"${OPKG_CONF}" |
| lock -u /var/lock/opkg-restore | lock -u /var/lock/opkg-restore |
| opkg rollback | opkg rollback |
| |
| # Set up a custom Opkg profile | # Set up Opkg profiles |
| uci set opkg.defaults.restore="custom" | uci set opkg.defaults.restore="init custom" |
| | uci set opkg.init="opkg" |
| | uci add_list opkg.init.ipkg="losetup" |
| | uci add_list opkg.init.ipkg="parted" |
| | uci add_list opkg.init.ipkg="resize2fs" |
| uci set opkg.custom="opkg" | uci set opkg.custom="opkg" |
| uci add_list opkg.custom.rpkg="dnsmasq" | uci add_list opkg.custom.rpkg="dnsmasq" |
| |
| # Check Opkg log | # Check Opkg log |
| logread -e opkg | tail -f /var/log/opkg-* |
| |
| # Upgrade packages | # Upgrade packages |
| opkg update | opkg update |
| opkg upgr | opkg upgr |
| | |
| | # Maintenance |
| | opkg altlink |
| | opkg newconf |
| </code> | </code> |
| |
| ===== Automated ===== | ===== Automated ===== |
| <code bash> | <code bash> |
| uclient-fetch -O opkg-extras.sh "https://openwrt.org/_export/code/docs/guide-user/advanced/opkg_extras?codeblock=0" | wget -U "" -O opkg-extras.sh "https://openwrt.org/_export/code/docs/guide-user/advanced/opkg_extras?codeblock=0" |
| . ./opkg-extras.sh | . ./opkg-extras.sh |
| </code> | </code> |
| |
| ===== See also ===== | |
| |
| Attended sysUpgrade: ''luci-app-attended-sysupgrades'' or ''auc'' | |