2014-09-05 2 views
0

У меня есть месячные имена в виде столбцов, таких как jan, feb, march и т. Д. В моей таблице.
В моей Форме пользователь должен выбрать месяц из раскрывающегося списка, который я выбираю пользователем как $ month_name.

Я хочу видеть данные в $ month_name, которое не равно 0.00.PHP Mysql - Использовать переменную как имя столбца в операторе Select

Когда эхо $ MONTH_NAME я получаю: джан или фев или т.п.

Я использовал $ MONTH_NAME в моем отборном заявлении, но не работает:

первых попробовать не работает:

$sql = "SELECT * FROM bookoff_monthly WHERE '.$month_name.' <> 0.00 AND year='$year' "; 

2 старайтесь не работать:

$sql = "SELECT * FROM bookoff_monthly WHERE $month_name <> 0.00 AND year='$year' "; 

** но следующие работы, но это не то, что я хочу:

$sql = "SELECT * FROM bookoff_monthly WHERE jan <> 0.00 AND year='$year' "; 

ответ

1

Это то, что я считал бы правильно спасся:

$sql = "SELECT * FROM bookoff_monthly WHERE `".$month_name."` <> 0.00 AND year='".$year."' "; 

Обратите внимание, что вокруг $month_name вы имеете кавычку в заявлении, затем двойные кавычки (как весь запрос окружен ими), затем конкатенация PHP (.). Вам лучше подумать об этом как о string + variable + string ..., а не о переменной в строке. То же самое с переменной $ year.

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

$var = "is a"; 

echo("This ".$var." string 'with quoted text'"); // This is a string 'with quoted text' 

echo("This ".$var." string \"with quoted text\""); // This is a string "with quoted text" 

echo('This '.$var.' string "with quoted text"'); // This is a string "with quoted text" 

echo('This '.$var.' string \'with quoted text\''); // This is a string 'with quoted text' 

Предполагая, что ваши переменные находятся в правильном формате, тогда это должно сработать.

EDIT: Как говорит VMai, потому что вы имеете дело в именах 3 буквенных месяц, вы неизбежно будете использовать «DEC» или «реш» в этом запросе, и это зарезервированное слово в MySQL, так что вы сусло побег имя с обратными вызовами или запрос будут неверно истолкованы.

+1

Вы могли бы добавить, что идентификаторы экранирования в этом случае должны быть, потому что столбец 'DEC' будет разорвать нереализованные запросы. Причина: 'DEC' является [зарезервированным словом] (https://dev.mysql.com/doc/refman/5.6/en/reserved-words.html) в MySQL. $ year может использоваться как есть, но лучше было бы использовать параметризованные подготовленные инструкции. Обратите внимание, что нельзя использовать параметры для идентификаторов. – VMai

+0

Это хороший момент! Я всегда обертываю имена столбцов и таблиц в обратных галочках по этой причине – Luke

+0

Это также верно, но выходит за рамки этого вопроса – Luke

-2

$sql = 'SELECT * FROM bookoff_monthly WHERE '.$month_name.' <> 0.00 AND year="'.$year.'"

+0

Этот ответ, хотя он может работать, является ** крайне ** плохой формой. Ни идентификатор, ни буква, встроенные в запрос, не защищены от инъекции. –

1

Что касается прямой вопрос:

Проблема # 1 является то, что вы пытаетесь смешать одинарные и двойные кавычки. Предполагая, что $ month_name = "jan", это даст вам:

SELECT * FROM bookoff_monthly WHERE '.jan.' <> 0.00 AND year='$year' 

As '.jan.' не равно 0.00, это не будет содержать никаких записей.

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

Но в любом случае, это просто запрос на атаки SQL-инъекций. Например, хакер может подделать вашу входную форму и установить jan = "1 + 1 = 2; удалить с bookoff_monthly где 1.00", а nowit удалит все за данный год.

Плюс любая конструкция, в которой вы создаете имена полей на лету, должна быть поставлена ​​под сомнение сразу с места в карьер.

Правильный способ сделать это состоит в том, чтобы иметь отношения «много к одному» с одной записью за каждый месяц. Подобно create table bookoff_month (bookoff_id int, month char (3), сумма десятичная (7,2)). Тогда ваш запрос станет select * from bookoff_monthly join bookoff_month на bookoff_month.bookoff_id = bookoff_monthly.bookoff_id, где month =? и год =? и заполнить их с помощью подготовленного оператора или, по крайней мере, обернуть параметры в функции, которая выполняет надлежащее экранирование.

Смежные вопросы