2

Can someone help me out with this. I have 2 files

First one contains IDs of employees that left a company

employeeid.txt

5678D956 
45S87954
56898K78
4D856898
556987F8
23657D87

Second file is a config file for an application that stores users settings

App.conf (only part of the file)

/export/home/conf[naa.5678D956]/displayName = "John Paul (naa.5678D956)"
/export/home/conf[naa.5678D956]/Scripts = "true"
/export/home/conf[naa.5678D956]/FTP = "true"
/export/home/conf[naa.5678D956]/HomeDirs = "true" 
/export/home/conf[naa.4487984D]/displayName = "Cara Jones (naa.4487984D)"  
/export/home/conf[naa.4487984D]/Scripts = "false"
/export/home/conf[naa.4487984D]/FTP = "true"
/export/home/conf[naa.4487984D]/HomeDirs = "true" 
/export/home/conf[naa.45S87954]/displayName = "Eimer Fenton (naa.45S87954)"
/export/home/conf[naa.45S87954]/Scripts = "true"
/export/home/conf[naa.45S87954]/FTP
/export/home/conf[naa.45S87954]/HomeDirs = "true"
/export/home/conf[naa.56898K78]/displayName = "Edd Waters (naa.56898K78)"
/export/home/conf[naa.56898K78]/Scripts = "true"
/export/home/conf[naa.56898K78]/FTP = "true"
/export/home/conf[naa.56898K78]/HomeDirs = "true"
/export/home/conf[naa.909878S4]/displayName = "Phil Mooney (naa.909878S4)"  
/export/home/conf[naa.909878S4]/Scripts
/export/home/conf[naa.909878S4]/FTP = "true"
/export/home/conf[naa.909878S4]/HomeDirs  = "true"

I would like to have it so that if a employee ID exists in employeeid.txt, it comments out their configuration setting in App.conf and saves as new file

#/export/home/conf[naa.5678D956]/displayName = "John Paul (naa.5678D956)"
#/export/home/conf[naa.5678D956]/Scripts = "true"
#/export/home/conf[naa.5678D956]/FTP = "true"
#/export/home/conf[naa.5678D956]/HomeDirs = "true" 
/export/home/conf[naa.4487984D]/displayName = "Cara Jones (naa.4487984D)"  
/export/home/conf[naa.4487984D]/Scripts = "false"
/export/home/conf[naa.4487984D]/FTP = "true"
/export/home/conf[naa.4487984D]/HomeDirs = "true" 
#/export/home/conf[naa.45S87954]/displayName = "Eimer Fenton (naa.45S87954)"
#/export/home/conf[naa.45S87954]/Scripts = "true"
#/export/home/conf[naa.45S87954]/FTP
#/export/home/conf[naa.45S87954]/HomeDirs = "true"
#/export/home/conf[naa.56898K78]/displayName = "Edd Waters (naa.56898K78)"
#/export/home/conf[naa.56898K78]/Scripts = "true"
#/export/home/conf[naa.56898K78]/FTP = "true"
#/export/home/conf[naa.56898K78]/HomeDirs = "true"
/export/home/conf[naa.909878S4]/displayName = "Phil Mooney (naa.909878S4)"  
/export/home/conf[naa.909878S4]/Scripts
/export/home/conf[naa.909878S4]/FTP = "true"
/export/home/conf[naa.909878S4]/HomeDirs  = "true"

I have been trying to get it to work with sed, but have not been getting anywhere

3 Answers 3

1

Assuming there aren't any employer IDs with which might be interpreted as valid regular expression characters by sed, e.g. *, ? or \:

sed 's:^/export/home/conf\[naa.\('"$(paste -sd '|' employeeid.txt)"'\)\]:#&:' App.conf

If you have a lot of employer IDs so that the resulting line becomes too long and your sed support -f- (otherwise you got to redirect it to a file first and then let sed read the script):

{
  printf '%s' 's:^/export/home/conf\[naa.\(';
  paste -sd '|' employeeid.txt;
  printf '%s' '\)\]:#&:';
} | tr -d '\n' | sed -f- App.conf

To make the changes in-place (modifying the file right away instead of showing you the results) add -i for GNU sed or -i '' for FreeBSD sed.

1
  • 1
    Errh... ok, I had something completely different in mind: turn each line into a regex (instead of concatenating them into a single regex) and escape any special chars in the process e.g. sed 's|[[\.*^$/]|\\&|g;s|.*|/\\.&\\]/s/^/#/|' employeeid.txt | sed -f- App.conf... never mind :)... Commented Apr 25, 2017 at 20:07
1
while read employeeid; do
    sed --in-place "/$employeeid/s/^/#/" /path/to/App.conf
done < employeeid.txt
1
  • 1
    It's worth noting that this would get quite slow with a lot of employer IDs (read performance + sed runs over the whole file for every employer ID).
    – phk
    Commented Apr 25, 2017 at 19:40
1

gawk(GNU awk) approach:

awk 'NR==FNR{a[$1]; next}{match($4, /\[naa\.([0-9A-Z]+)\]/, b); 
     if(b[1] in a) $1="#"$1;}1' OFS="/" employeeid.txt FS="/" App.conf > newfile

Now, newfile contains the needed lines


a[$1] - accumulating an array of employee ids(as indices) while the first file employeeid.txt get processed

FS="/" - field separator for the second file App.conf

match($4, /\[naa\.([0-9A-Z]+)\]/, b) - captures an employee id within the 4th field of a second file's line

if(b[1] in a) $1="#"$1 - checks if the captured employee id is in the crucial array. If so, adds # to the first field(i.e. at the beginning of the line)

1
  • @ICRealTime, you're welcome Commented Apr 25, 2017 at 19:54

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .