Я писал небольшую оболочку для nullmailer, когда заметил, imho, нежелательное поведение в grep.В частности, я заметил кое-что странное с @ s.
. Он разрывает строки, содержащие @, и дает неправильный вывод.
TL; DR
E-адреса электронной почты имеют некоторые правила (EG RFC 2822 ), поэтому я буду использовать заведомо неправильное регулярное выражение для них, просто чтобы сделать его немного короче.Обратите внимание, что это не изменит проблему, о которой я спрашиваю.
Я использую адреса электронной почты в этом сообщении, но проблема очевидно для каждой строки с хотя бы @ в ней.
Я написал небольшой скрипт, чтобы помочь мне объяснить, что я «нашел»:
#!/bin/bash
funct1() {
arr=(local1@domain.tld local2@domain.tld)
regex="[[:alnum:]]*@[[:alpha:]]*\.[[:alpha:]]\{2,\}"
for dest in ${arr[@]}; do
printf "%s\n" "$dest" | grep -o -e "$regex"
done
}
funct2() {
arr=(local1@domain.tld local2@domain.tld)
regex="[[:alpha:]]*@[[:alpha:]]*\.[[:alpha:]]\{2,\}"
for dest in ${arr[@]}; do
printf "%s\n" "$dest" | grep -o -e "$regex"
done
}
funct3(){
arr=(local1@dom1@ain.tld local2@dom2@ain.tld)
regex="[[:alpha:]]*@[[:alpha:]]*@[[:alpha:]]*\.[[:alpha:]]\{2,\}"
for dest in ${arr[@]}; do
printf "%s\n" "$dest" | grep -o -e "$regex"
done
}
funct4(){
arr=(local1@dom1@ain.tld local2@dom2@ain.tld)
regex="[[:alpha:]]*@[[:alnum:]]*@[[:alpha:]]*\.[[:alpha:]]\{2,\}"
for dest in ${arr[@]}; do
printf "%s\n" "$dest" | grep -o -e "$regex"
done
}
printf "One @, all parts of regex right:\n"
funct1
printf "One @, first part of regex wrong:\n"
funct2
printf "Two @, first and second part of regex wrong:\n"
funct3
printf "Two @, first part of regex wrong:\n"
funct4
exit 0
Чтобы лучше понять проблему, я использовал два типа строк: local1@domain.tld
и local1@dom1@ain.tld
, и кажется,мне, что grep не ведет себя должным образом со строками, содержащими по крайней мере @.
Вывод:
One @, all parts of regex right:
local1@domain.tld
local2@domain.tld
One @, first part of regex wrong:
@domain.tld
@domain.tld
Two @, first and second part of regex wrong:
Two @, first part of regex wrong:
@dom1@ain.tld
@dom2@ain.tld
funct1
имеет регулярное выражение, которое решает все строкитак что нет проблем, все они печатаются.
funct2
имеет регулярное выражение, которое решает только строки от @ до конца, так что я должен ожидать, что нет вывода, из-за неправильного выражения;вместо этого у меня есть вторая часть строк ...
Именно поэтому я решил добавить второй @ в строку и выполнить несколько тестов.
funct3
решает толькостроки от второго @ до конца, так что я должен ожидать вообще никакого вывода из-за ошибки в регулярном выражении;Хорошо, ничего не выводится.
funct4
вместо этого имеет регулярное выражение, которое решает только строки от первого @ до конца, поэтому я должен ожидать, что он не может ничего мне показать;вместо этого, то, что у меня есть, это выход первого @, как funct2
.
За исключением funct1
У меня вообще не должно быть никакого вывода, я прав?
Почемуgrep прерывает результат при первом @?
Я считаю это нежелательным поведением, потому что таким образом результат будет состоять из строк, которые не полностью соответствуют моему выражению.
Я что-то упустил?
РЕДАКТИРОВАТЬ: тег удаления undefined-behavior