Ar trebui să folosesc wpdb prepare?

11 mai 2011, 10:16:11
Vizualizări: 58.6K
Voturi: 38

Sunt începător în SQL și mă întreb dacă trebuie să folosesc wpdb->prepare pentru următoarea interogare către un tabel pe care l-am creat

global $wpdb;
$tablename = $wpdb->prefix . "my_custom_table";
$sql = "SELECT * FROM " . $tablename . " ORDER BY date_created DESC";
$resulst = $wpdb->get_results( $sql , ARRAY_A );

Trebuie să folosesc prepare aici? Cum aș putea face asta?

Mulțumesc

0
Toate răspunsurile la întrebare 3
7
47

Este o practică recomandată să folosești întotdeauna prepare, dar scopul principal al acesteia este prevenirea atacurilor de tip SQL injection. În cazul tău, deoarece nu există nicio intrare de la utilizatori sau vizitatori care să poată afecta interogarea, aceasta nu este o problemă.

Dar, așa cum am menționat anterior, este o practică bună să o folosești și odată ce începi să o folosești, nu mai renunți. Deci, în exemplul tău, poți să o folosești astfel:

global $wpdb;
$tablename = $wpdb->prefix . "my_custom_table";
$sql = $wpdb->prepare( "SELECT * FROM %s ORDER BY date_created DESC",$tablename );
$results = $wpdb->get_results( $sql , ARRAY_A );

Pentru a afla mai multe despre cum să o folosești, vizitează codex

11 mai 2011 10:43:00
Comentarii

Salut @Bainternet, mulțumesc pentru explicația atât de clară - din nu știu ce motiv, când încerc codul tău, returnează un array gol. Am verificat și dublu verificat dacă am greșeli de scriere. Dacă fac query-ul nepreparat, primesc array-ul. Nu înțeleg de ce nu funcționează..!

Richard Sweeney Richard Sweeney
11 mai 2011 11:03:09

Ciudat. Am încercat să folosesc același cod cu un alt query: `$tablename = $wpdb->prefix . "my_custom_table"; $concert_id = 1;

$sql = "SELECT * FROM " . $tablename . " WHERE concert_id = %d LIMIT 1;";

$prep_sql = $wpdb->prepare( $sql, $concert_id );

$get_concerts = $wpdb->get_results( $prep_sql , ARRAY_A );`

Și funcționează perfect! Nu sunt sigur de ce ar fi așa. Dar în orice caz, acum am înțeles!

Richard Sweeney Richard Sweeney
11 mai 2011 11:36:02

Includerea numele de tabel între ghilimele simple nu va funcționa. Escaparea normală se face cu backticks, deci query-ul tău ar trebui să arate astfel: SELECT * FROM \wp_my_custom_table`. Poți activa suportul pentru ghilimele duble, dar atunci ar trebui să arate așa:SELECT * FROM "wp_my_custom_table"`.

Jan Fabry Jan Fabry
11 mai 2011 11:52:17

Nu sunt de acord cu acest răspuns. De ce ar trebui să folosești escaping când funcția deja face escaping la tot? Crezi că WordPress va decide să elimine escaping-ul din nucleu? De asemenea, nu are rost să folosești escaping pentru numele tabelei :) pentru că este hardcodat și știi că este ok. Știu că acesta este doar un exemplu, dar oricum nu folosi escaping pentru numele tabelelor, am probleme când folosesc prepare cu nume de tabele, adaugă backticks și SQL aruncă eroare.

Tommixoft Tommixoft
4 nov. 2014 14:41:44

@Tommixoft Dacă citești din nou răspunsul, vei vedea că de fapt spui același lucru ca mine, și că numele tabelei este doar un exemplu.

Bainternet Bainternet
5 nov. 2014 09:07:36

Poți să susții afirmația că este cea mai bună practică? Pare ciudat (ca în nu cea mai bună practică) să folosești o funcție care este inutilă și așteaptă 2+ parametri în acest caz....

random_user_name random_user_name
14 oct. 2016 17:23:32

Ahhh, răspunsul este din 2011!!! Dacă acceptați input de la utilizator în interogare, atunci da, este întotdeauna cea mai bună practică.

Bainternet Bainternet
20 oct. 2016 17:27:15
Arată celelalte 2 comentarii
2

Când utilizați prepare(), acesta protejează codul împotriva vulnerabilităților de injecție SQL.

Iată codul pe care trebuie să-l modificați pentru a utiliza prepare():

global $wpdb;
$tablename = $wpdb->prefix . "my_custom_table";
$sql = $wpdb->prepare( "SELECT * FROM {$tablename} ORDER BY date_created DESC");
$resulst = $wpdb->get_results( $sql , ARRAY_A );
12 oct. 2015 18:34:35
Comentarii

Doar pentru că folosești prepare() codul nu este automat protejat împotriva injecțiilor SQL. Codul tău ar putea sugera că $tablename este protejat împotriva injecțiilor SQL pentru că este folosit în prepare, ceea ce nu este cazul, deoarece nu este furnizat prin argumente. În acest caz, aceasta nu este o problemă, deoarece conținutul lui $tablename este sigur, dar cred că ar fi bine să clarificăm acest aspect.

Constantin Constantin
28 dec. 2020 17:04:58

Da. Acest răspuns este greșit și potențial periculos, aș spune. Ai apelat prepare într-un mod care de fapt nu protejează împotriva injecției SQL.

Harry Wood Harry Wood
11 nov. 2021 13:30:10
0

În cazul tău nu este posibil un atac prin injecție SQL. Codul tău nu are nevoie de protecție suplimentară deoarece nu utilizează date introduse de utilizator precum: post, get, request, cookie.

Nu utiliza funcții complicate atunci când nu sunt necesare pentru a economisi resursele serverului.

17 iul. 2015 11:51:54