Mysql
 sql >> Baza danych >  >> RDS >> Mysql

ColdFusion Parametryzacja zapytania

Ignorowanie właściwego podejścia przez chwilę powodem tego jest to, że używasz nieprawidłowego cfsqltype dla parametrów. Tak więc w rzeczywistości wysyłasz do bazy danych różne wartości (i w konsekwencji dokonujesz innego porównania) niż myślisz. W rezultacie zapytanie nie może znaleźć żadnych pasujących rekordów. Dlatego Twój wykres jest pusty.

Używając cf_sql_timestamp konwertujesz „wartość” na pełny obiekt daty/godziny. Jednak ROK() zwraca tylko czterocyfrową liczbę. Więc porównujesz jabłka i pomarańcze. Koncepcyjnie Twoje zapytanie faktycznie działa tak:

  WHERE  2014 = {ts '2009-02-13 23:31:30'}

Powodem, dla którego nie zgłasza błędu, jest to, że wartości daty/godziny są wewnętrznie przechowywane jako liczby. Tak więc w rzeczywistości porównujesz małą liczbę (tj. rok) z naprawdę dużą liczbą (tj. data/godzina). Oczywiście wartość daty będzie znacznie większa, więc prawie nigdy nie będzie pasować do numeru roku. Ponownie, koncepcyjnie Twoje zapytanie robi to:

 WHERE 2014 = 1234567890

Ponieważ cfsqltype jest opcjonalny, wiele osób uważa, że ​​nie jest to bardzo ważne - ale tak jest.

  • Weryfikacja: Oprócz innych korzyści, cfqueryparam sprawdza podaną "wartość" na podstawie cfsqltype (data, data i godzina, numer itp.). Dzieje się to przed sql jest zawsze wysyłane do bazy danych. Więc jeśli dane wejściowe są nieprawidłowe, nie marnujesz wywołania bazy danych. Jeśli pominiesz cfsqltype lub po prostu użyjesz domyślnego, tj. ciągu, stracisz tę dodatkową walidację.

  • Dokładność Wybranie odpowiedniego cfsqltype zapewnia przesłanie prawidłowej wartości do bazy danych. Jak pokazano powyżej, użycie niewłaściwego typu może spowodować, że CF wyśle ​​niewłaściwą wartość do bazy danych.

    cfsqltype zapewnia również, że wartości są przesyłane do bazy danych w jednoznacznym formacie, baza danych będzie interpretować w oczekiwany sposób. Technicznie rzecz biorąc, możesz wysłać wszystko do bazy danych jako ciąg znaków. Jednak zmusza to bazę danych do wykonania niejawnej konwersji (zwykle niepożądane).

    W przypadku konwersji niejawnej interpretacja ciągów jest całkowicie pozostawiona bazie danych — i może ona nie zawsze dać oczekiwaną odpowiedź. Przesyłanie dat jako ciągów, a nie obiektów dat, jest tego najlepszym przykładem. Jak bieżąca baza danych zinterpretuje ciąg daty, taki jak „05/04/2014”? Jak 5 kwietnia czy 4 maja? To zależy. Zmień bazę danych lub ustawienia bazy danych, a wynik może być zupełnie inny.

Jedynym sposobem na zapewnienie spójnych wyników jest określenie odpowiedniego cfsqltype. Powinien być zgodny z typem danych kolumny/funkcji porównania lub przynajmniej z równoważnym typem. W przypadku YEAR() , zwraca czterocyfrową liczbę. Powinieneś więc użyć cf_sql_integer , ponieważ Adrian wspomniał o komentarzach . To samo dotyczy Twojego MONTH() porównanie.

 WHERE Year(ColumnName) = <cfqueryparam value="2014" cfsqltye="CF_SQL_INTEGER">
 AND   Month(ColumnName) = <cfqueryparam value="11" cfsqltye="CF_SQL_INTEGER"> 

Powiedziawszy to wszystko, sugestia Dana to lepszy sposób na porównanie dat. Ten paradygmat jest bardziej przyjazny dla indeksów i działa niezależnie od tego, czy kolumna docelowa zawiera datę (tylko) czy datę i godzinę. Zwróć uwagę na użycie cf_sql_date w jego przykładzie.

  • cf_sql_timestamp - wysyła zarówno datę, jak i godzinę
  • cf_sql_date - wysyła tylko datę. wartość czasu jest obcinana


  1. Database
  2.   
  3. Mysql
  4.   
  5. Oracle
  6.   
  7. Sqlserver
  8.   
  9. PostgreSQL
  10.   
  11. Access
  12.   
  13. SQLite
  14.   
  15. MariaDB
  1. Sklonuj bazę danych MySQL

  2. Czy dynamiczne zapytania mysql z kodem ucieczki sql są tak samo bezpieczne, jak przygotowane instrukcje?

  3. Pobieranie PDO w PHP ma wartość null

  4. Yii2 – lewe dołączenie pod warunkiem wielokrotnym

  5. alternatywa levenshteina