4
\$\begingroup\$

What I'm trying to do here is first set the first eight variables to the proper default values. That's the first area I'm thinking there might be a way to optimize. Is there anyway to set both variables at once for example I know in PHP I could do $title=$d_title="value"; Is there any way to consolidate that section? (The variables prefixed with d_ will not change, but the same variable without the d_ may be changed.)

Then the rest of the snippet should do the following:

  • If the second argument is NOT "config"

    • Look in the file to see if the a line with the format ${sfile}_variablename="*" exists.
      • If it does, use sed to replace the contents of the quotes with the new variable
      • If it does not, append the line in its entirety
  • If the second argument IS "config"
    • If a line exists that contains ${sfile}_variablename, read in what's between the quotes and assign it to the variablename
    • If not, set the variablename to the default value

Below is how I was achieving that. Is there any way to do this in a more simplified or compact manner?

In this case, sdir is a base path I define elsewhere, and sfile is another prefix. Those are hard-coded into the top of the script, so those will always be correct.

d_finddir=${2:-"${sdir}/music/trine_soundtrack/"}
finddir=${d_finddir}

d_title=${3:-"Random Tangent"}
title=${d_title}

d_desc=${4:-"Random Tangent Playlist"}
desc=${d_desc}

d_rand=${5:-"randomize"}
rand=${d_rand}


if [ ! "${finddir}" = "config" ]; then
    if egrep -q "${sfile}_finddir" "${sdir}/config.cfg"; then
        sed -r -i "s,(${sfile}_finddir=).*,\\1\"${finddir}\"," "${sdir}/config.cfg"
    else
        printf "%s_finddir=\"%s\"\n" "${sfile}" "${finddir}" >>"${sdir}/config.cfg"
    fi

    if egrep -q "${sfile}_title" "${sdir}/config.cfg"; then
        sed -r -i "s,(${sfile}_title=).*,\\1\"${title}\"," "${sdir}/config.cfg"
    else
        printf "%s_title=\"%s\"\n" "${sfile}" "${title}" >>"${sdir}/config.cfg"
    fi

    if egrep -q "${sfile}_desc" "${sdir}/config.cfg"; then
        sed -r -i "s,(${sfile}_desc=).*,\\1\"${desc}\"," "${sdir}/config.cfg"
    else
        echo "${sfile}_desc=\"${desc}\"">>"${sdir}/config.cfg"
        printf "%s_desc=\"%s\"\n" "${sfile}" "${desc}" >>"${sdir}/config.cfg"
    fi

    if egrep -q "${sfile}_mode" "${sdir}/config.cfg"; then
        sed -r -i "s,(${sfile}_mode=).*,\\1\"${rand}\"," "${sdir}/config.cfg"
    else
        printf "%s_mode=\"%s\"" "${sfile}" "${rand}" >>"${sdir}/config.cfg"
    fi
else
    if egrep -q "${sfile}_finddir" "${sdir}/config.cfg"; then
        finddir=$(egrep "${sfile}_finddir" "${sdir}/config.cfg" | egrep -o "\".+\"" | sed 's/\"//g')
    else
        finddir=${d_finddir}
    fi

    if egrep -q "${sfile}_title" "${sdir}/config.cfg"; then
        title=$(egrep "${sfile}_title" "${sdir}/config.cfg" | egrep -o "\".+\"" | sed 's/\"//g')
    else
        title=${d_title}
    fi

    if egrep -q "${sfile}_desc" "${sdir}/config.cfg"; then
        desc=$(egrep "${sfile}_desc" "${sdir}/config.cfg" | egrep -o "\".+\"" | sed 's/\"//g')
    else
        desc=${d_desc}
    fi

    if egrep -q "${sfile}_mode" "${sdir}/config.cfg"; then
        rand=$(egrep "${sfile}_mode" "${sdir}/config.cfg" | egrep -o "\".+\"" | sed 's/\"//g')
    else
        rand=${d_rand}
    fi
fi
\$\endgroup\$
2
\$\begingroup\$
  • Using sed to its fullest

    sed is surprisingly powerful tool. For example:

    finddir=$(sed -n -E /"${sfile}_finddir"'/s/[^"]*\"([^"]*).*/\1/p' "${sdir}/config.cfg")
    [ -z ${finddir} ] && finddir=${d_finddir}
    

    achieves the desired effect without any egrep.

    • Explanation: The last line ([ -z ]) tests whether finddir has zero length (meaning that sed didn't find the line in interest) and if so (&&) assigns it a default value.
  • Editing the config file

    I am not sure I understand the decision to edit the config file via the script. It is much more natural (at least within the context provided) to edit it manually.

\$\endgroup\$
  • \$\begingroup\$ I'll look more at that sed example and what it does tonight, but as for the config file, this is part of a longer start script for a program which if not called with config, expects that you're defining the values to start the program. The config is more of a "This is what you used last time". \$\endgroup\$ – Trel Jan 4 '16 at 21:25
  • \$\begingroup\$ @Trel see the edit \$\endgroup\$ – vnp Jan 4 '16 at 21:37
  • \$\begingroup\$ If I'm reading the sed example, and if I'm understanding it right, I'd want to use this format over your example, unless I'm misunderstanding something sed -n -E "s/${sfile}_finddir=\"([^\"]*).*\".*/\1/p" "${sdir}/config.cfg" would be what I want to use if I'm going to use -z for the test? \$\endgroup\$ – Trel Jan 4 '16 at 22:04
  • \$\begingroup\$ @Trel You may do that, but why run sed twice? It is much easier to save the result (possibly empty) in the variable, and than inspect the it. If it is not empty, you have the desired result; otherwise default it. \$\endgroup\$ – vnp Jan 4 '16 at 22:29
  • \$\begingroup\$ Where am I running sed twice? If I'm understanding yours, it's matching the ${sfile}_finddir part and then if it matches, extracts the part of the line between ". In my example, it just looks for the whole line including the ${sfile}_finddir and extracts the same portion. I'm not seeing where the way I was doing it runs sed twice? \$\endgroup\$ – Trel Jan 4 '16 at 22:46

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.