2013-07-21 4 views
6

Это связано с предыдущим вопросом, здесь: Converting a \u escaped Unicode string to ASCIIсанобработке строки в R

Я предложил решение с участием eval(parse(text=x)), что для не-R пользователей, означает, что он говорит: разбор строки текста, а затем оценить его. Целью было не, чтобы разрешить выполнение произвольного кода, но только для того, чтобы избежать escape-кода из текста Unicode. Поэтому решение:

eval(parse(text=paste0("'", x, "'"))) 

Хотя это должно быть достаточно безопасным, учитывая ограниченный цель, я бы интересно узнать: сколько санитарной обработки требуется, чтобы держать вещи в безопасности?

Как минимум, я предполагаю, что любые встроенные одиночные и двойные кавычки должны быть экранированы. Например, предположим, что мы имеем

x <- "this is a '; print(dir()); 'string" 

Тогда eval «ИНГ это за фрагмент кода выше, будет выполнять код в середине. Поэтому нам нужно избегать котировок:

eval(parse(text=paste0("'", 
         gsub("'", "\\\\'", x), 
         "'"))) 

И аналогично для двойных кавычек. Я не думаю, что unescaped Юникод-эквиваленты \u0022 и \u0027 являются проблемой, так как для анализатора они будут идентичны равным " и '.

Есть ли какие-либо отверстия в этом подходе, которые я пропустил?

+0

Было бы хорошо, если бы был способ для разбора уцелевших строк без машин (и риски) 'eval'! – seancarmody

+0

Я придумал альтернативу без 'eval': http://stackoverflow.com/a/17771985/1543437 – seancarmody

ответ

4
this is a \'; print(dir()); 'string 

спасшемся в:

'this is a \\'; print(dir()); 'string' 

двойной обратный слэш evaled в буквальном обратную косую черту, цитата активна, код выполняется.

Также я не знаю о R, но, возможно, вы могли бы как минимум вызвать сбой с использованием необработанных управляющих символов, таких как символ новой строки или недействительные экраны.

eval - игра в кружку в целом. Обычная обработка строк (строка поиска для нужной вам последовательности, ее замена) - лучший подход, и лучше всего использовать существующую библиотеку для конкретного правильно заданного формата. Например, если у вас JSON, используйте парсер JSON. Существует много возможных форматов строковых литералов, которые используют \u экранов, все со слегка отличающимися правилами, поэтому вы захотите правильно выбрать точный формат.

+0

Фактически, синтаксический анализатор выдаст ошибку на этом входе, поэтому все выражение (включая встроенный код) будет никогда не оцениваться. Но это тоже не очень хорошо. –

0

Существует shQuote функции, которая могла бы работать для вас:

eval(parse(text=shQuote(x))) 
# [1] "this is a '; print(dir()); 'string" 
Смежные вопросы