0

I use sed to customize LXC container configuration files from the LXC host. That works well so far. When adjusting comment headers (hostname and date), there are aesthetic problems with the width of the headers, since when the hostname with different lengths are replaced, the total width of the heather is not automatically compensated for at the end.

in my example the string SERVER should be replaced.

############################
# RSYSLOG Konfiguration    #
# SERVER:/etc/rsyslog.conf #
# t12@RMS 2020-03-23       #
############################
############################
# RSYSLOG Konfiguration    #
# gersrv:/etc/rsyslog.conf   #
# t12@RMS 2020-04-23       #
############################
############################
# RSYSLOG Konfiguration    #
# sv4:/etc/rsyslog.conf   #
# t12@RMS 2020-06-23       #
############################

How can I get this with sed? Or do I need awk?

sed -i "s/SERVER/${servername}/g" /path to container/etc/rsyslog.conf
questor
  • 1
  • 2

1 Answers1

1

Here you are a solution:

I use the length of the first dashes line as a length reference.

#! /bin/bash

RSYSLOG_FILENAME="/etc/rsyslog.conf"

awk -v servername="$1" '
/^#+$/ {
    ndash = length($0)
    print
    next
}
/^# SERVER:/ {
    str = "# " servername ":/etc/rsyslog.conf"
    nspace = ndash - length(str) - 1
    if (nspace < 1) { nspace = 1 }
    printf("%s%*.*s#\n", str, nspace, nspace, "")
    next
}
{
    print
}
' "${RSYSLOG_FILENAME}" > "${RSYSLOG_FILENAME}.tmp"

mv "${RSYSLOG_FILENAME}.tmp" "${RSYSLOG_FILENAME}"

UPDATE

For multiple files.

File: ./sysconf.sh

#! /bin/bash

declare -r SERVER_NAME="$1"
shift

for CONF_FILENAME in "${@}"; do
    awk -v servername="${SERVER_NAME}" '
    /^#+$/ {
        ndash = length($0)
        print
        next
    }
    /^# SERVER:/ {
        match($0, /[: ][^: #]*[ #]/, arr)
        fn = arr[0]
        gsub(/[: #]/, "", fn)
        str = "# " servername ":" fn
        nspace = ndash - length(str) - 1
        if (nspace < 1) { nspace = 1 }
        printf("%s%*.*s#\n", str, nspace, nspace, "")
        next
    }
    {
        print
    }
    ' "${CONF_FILENAME}" > "${CONF_FILENAME}.tmp"
    mv "${CONF_FILENAME}.tmp" "${CONF_FILENAME}"
done

Used like that:

./sysconf.sh sv4 /etc/rsyslog.conf /etc/mysql/mariadb.cnf
  • thanks, works fine. But one point is open. My script should change the header of config files for various services in multiple Containers, not only rsyslog. means /etc/rsyslog.conf is only and example and can not used as static string # SERVER:/etc/rsyslog.conf # # SERVER:/etc/mysql/mariadb.cnf # # SERVER:/etc/ldap/ldap.conf # in sed there are \1 \2 statements to keep a string if matched with a filter. not sure if similar is needed in awk. – questor Nov 21 '21 at 15:47
  • I have updated my solution for any filenames – Arnaud Valmary Nov 21 '21 at 20:15