Escape-символ Laravel в построителе запросов

Кодирую запрос:

$result = \DB::table('order_items as oi')
        ->selectRaw(
            'order_item_type as item_type,
            order_item_id as item_id,
            if(order_item_type = "App\\\Models\\\Book", oi.price, invoices.price) as price
              )

просто обратите внимание на инструкцию if, мне нужно использовать два escape-символа, или запрос не соответствует App\Models\Book. когда я проверяю выходной запрос отладчиком laravel, он:

select order_item_type as item_type,
order_item_id as item_id,
if(order_item_type = "App\\Models\\Book", oi.price, invoices.price) as price,...

что здесь происходит? Удаляет ли построитель запросов laravel одну косую черту, а затем движок mysql удаляет вторую косую черту во время выполнения?

РЕДАКТИРОВАТЬ:
Но где-то еще в том же запросе у меня есть предложение where, в котором я использовал один escape-символ, и он отлично работает:

 ->leftjoin('books', function ($q) {
            $q->on('q3.order_item_id', '=', 'books.id')
                ->where('q3.order_item_type', '=', 'App\\Models\\Book');
        })

и часть выходного запроса отладчиком laravel:

left join `books` on `q3`.`order_item_id` = `books`.`id` and 
`q3`.`order_item_type` = 'App\Models\Book'

Может ли кто-нибудь объяснить, почему в if я должен использовать два escape-символа, а в join нужен только один escape-символ?
на самом деле не было бы проблем, если бы Я даже не использую escape-символы в where методе построения запросов и пишу код как:

  ->leftjoin('books', function ($q) {
            $q->on('q3.order_item_id', '=', 'books.id')
                ->where('q3.order_item_type', '=', 'App\Models\Book');
        })

person alex    schedule 28.06.2016    source источник
comment
Вы пробовали использовать 4 или 2 обратных слеша? 3 обратные косые черты мне кажутся некорректными.   -  person Ivan Yarych    schedule 28.06.2016
comment
@IvanYarych, это поведение не всегда одно и то же, взгляните на РЕДАКТИРОВАТЬ.   -  person alex    schedule 28.06.2016


Ответы (1)


И PHP 1, и MySQL 2 избегает косой черты. С другой стороны, MySQL требует их экранирования, если только NO_BACKSLASH_ESCAPES 3 Режим SQL включен - по умолчанию он отключен. В MySQL escape-последовательность либо интерпретируется, либо игнорируется - \n будет переведено в новую строку, \m игнорируется и преобразуется в m.

Итак, сначала PHP преобразует \\\ в \\ - два экранируются в один. Тогда MySQL также превратится из \\ в \, понимая, что вам нужен буквальный слеш. :)

Что касается вашего редактирования, selectRaw() отправляет необработанные запросы в MySQL, так что вам нужно избегать данных самостоятельно. Все другие необработанные методы делают это внутри Laravel Query Builder, поэтому вам не нужно возиться с этими вещами.

PHP, в отличие от MySQL, не игнорирует косые черты. При использовании строк в одинарных кавычках любая нескончаемая косая черта в любом случае будет распознаваться как буквальная, поэтому вам не нужно их экранировать - если ваша строка заканчивается косой чертой, тогда вы обязательны. В строках с двойными кавычками есть escape-последовательности, которые переводятся - ваш пример по-прежнему будет работать с ними, но есть случаи, которые могут пойти не так.

person Paulo Freitas    schedule 28.06.2016
comment
спасибо, я добавил правку. не могли бы вы проверить вопрос еще раз - person alex; 28.06.2016
comment
Я обновил свой ответ, чтобы также ответить на ваш новый вопрос. ;) - person Paulo Freitas; 28.06.2016
comment
Я не использовал escape-символы во внутреннем методе построения запросов where, и он отлично работает. Означает ли это, что метод where будет считать, что все символы, написанные пользователем (разработчиком), буквальны? - person alex; 28.06.2016
comment
PHP, в отличие от MySQL, не игнорирует косые черты. При использовании строк в одинарных кавычках любая нескончаемая косая черта в любом случае будет распознаваться как буквальная, поэтому вам не нужно их экранировать - если ваша строка заканчивается косой чертой, тогда вы обязательны. В строках с двойными кавычками есть escape-последовательности, которые переводятся - ваш пример по-прежнему будет работать с ними, но есть случаи, которые могут пойти не так. ;) - person Paulo Freitas; 28.06.2016