SQL lekérdezés hiba

Wathfea képe

Sziasztok!

Van egy D6-os modul amiben van egy ilyen lekérdezés:

$header = array(
     array('data' => t('Symbol'), 'field' => 'symbol'),
     array('data' => t('Bid'), 'field' => 'bid', 'class' => 'rightcell'),
     array('data' => t('Ask'), 'field' => 'ask', 'class' => 'rightcell'),
      );
 
$result = db_query('SELECT * FROM {gft_cache} WHERE forexid IN (%s)'.tablesort_sql($header),variable_get('gft_api_forexids', '1,2,3,4'));

Ami egy ilyen query-t generál:

SELECT * FROM gft_cache WHERE forexid IN (47,116,4,34,3,35,1,54908,67054) ORDER BY symbol ASC

Megpróbáltam a lekérdezést átírni D7-re:

$header = array(
    array(
      'data' => t('Symbol'),
      'field' => 'symbol',
    ),
    array(
      'data' => t('Bid'),
      'field' => 'bid',
      'class' => 'rightcell',
    ),
    array(
      'data' => t('Ask'),
      'field' => 'ask',
      'class' => 'rightcell',
    ),
  );
 
  $select = db_select('gft_cache','gc')->extend('TableSort');
  $result = $select->fields()->condition('forexid', array(variable_get('gft_api_forexids', '1,2,3,4')),'in')->orderByHeader($header)->execute();

Ami egy ilyen kimenetet generál:

SELECT .* FROM {gft_cache} gc {} WHERE (forexid IN (:db_condition_placeholder_0)) ORDER BY symbol ASC

Hogyan kéne ezt a lekérdezést helyrehozni? Én már nem találok hozzá több leírást amiből kibogozhatnám. :S

Drupal verzió: 
szantog képe

Így kávé előtt nekem előtt elsőre teljesen jónak tűnik a kimenet. Vagy az a bajod vele, hogy nem konkrét eredményt kapsz? Mert ahhoz még kell egy $result->fetchCol(), talán táblázathoz ez passzol leginkább, vagy $result ->fetchAllAssoc(). Ekkor már a result tömb lesz, amit fel lehet dolgozni.

0
0

----
Rájöttem, miért kérdezek olyan ritkán a drupal.hu-n. Amíg szedem össze az infokat a kérdéshez, mindig rájövök a megoldásra.

Wathfea képe

    Warning: Missing argument 1 for SelectQueryExtender::fields(), called in D:\MUNKA\DEV\goldforex\sites\all\themes\goldforex\page.tpl.php on line 119 and defined in SelectQueryExtender->fields() (line 735 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined variable: table_alias in SelectQueryExtender->fields() (line 736 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->preExecute() (line 1244 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->compile() (line 1078 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->compiled() (line 1096 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: arguments in SelectQuery->arguments() (line 1023 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->arguments() (line 1027 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->compiled() (line 1096 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->__toString() (line 1528 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: table in SelectQuery->__toString() (line 1535 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    Notice: Undefined index: alias in SelectQuery->__toString() (line 1540 of D:\MUNKA\DEV\goldforex\includes\database\select.inc).
    PDOException: SQLSTATE[42000]: Syntax error or access violation: 1064 You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near '* FROM gft_cache gft_cache WHERE (forexid IN ('47,116,4,34,3,35,1,54908,670' at line 1: SELECT .* FROM {gft_cache} gft_cache {} WHERE (forexid IN (:db_condition_placeholder_0)) ORDER BY symbol ASC; Array ( [:db_condition_placeholder_0] => 47,116,4,34,3,35,1,54908,67054 ) in include() (line 119 of D:\MUNKA\DEV\goldforex\sites\all\themes\goldforex\page.tpl.php).

Ezt kapom errorba.
0
0
pp képe

Ettől jobb lesz?

  1. $header = array(
  2. 'data' => t('Symbol'),
  3. 'field' => 'symbol',
  4. ),
  5. 'data' => t('Bid'),
  6. 'field' => 'bid',
  7. 'class' => 'rightcell',
  8. ),
  9. 'data' => t('Ask'),
  10. 'field' => 'ask',
  11. 'class' => 'rightcell',
  12. ),
  13. );
  14.  
  15. $select = db_select('gft_cache','gc')->extend('TableSort')->orderByHeader($header);
  16. $result = $select->fields('gc')->condition('forexid', explode(',', variable_get('gft_api_forexids', '1,2,3,4')),'in')->execute();
4
0
Wathfea képe

Igen ezzel már lefut. Azt szeretném kérdezni, hogy az orderBy-t miért nem a condition után kell rakni? Mmint eddig minden lekérdezés amit láttam neten ott mindig a legvégén volt. Szóval annyi, hogy a megoldás tök jó csak szeretném megtanulni, hogy miért így kell. Megírnád nekem azt is, ha lesz rá időd? Köszönöm szépen.

1
0
Sk8erPeter képe

  1. Ez volt az első hiba:

    Warning: Missing argument 1 for SelectQueryExtender::fields()

    Ez jelzi, hogy a fields() függvény használatánál hiányzott egy kötelező - default értékkel nem rendelkező! - argumentum, mégpedig a $table_alias, ahogy az a következő hibaüzenetből ki is derül:
    Notice: Undefined variable: table_alias in SelectQueryExtender->fields()

    Érdemes megnézned a hivatalos doksit:
    SelectQueryExtender::fields, itt látszik, hogy a függvény várna legalább 1 paramétert.

    pp pedig helyesen át is adta a megfelelő $table_alias-t, lásd a kódjában ezt a részt:

    $select->fields('gc')

  2. Volt még a kódjában egy explode() is, amivel a vessző mentén "szétrobbantotta" a stringet egy tömbbé, ami stringek tömbje. Jelen esetben valami ilyesmi lesz az eredménye:

    array( 0=>'1', 1=>'2', 2=>'3', 3=>'4' );

    Ez pedig egy érvényes bemenet a condition() metódushoz, lásd a következőt:
    QueryConditionInterface::condition
    "This method can take a variable number of parameters. If called with two parameters, they are taken as $field and $value with $operator having a value of IN if $value is an array and = otherwise."

    Tehát ez a metódus egy tömböt is elfogad második paramétereként, ha az $operator opció egyenlő az 'in'-nel, ami esetedben így is van.

  3. Az is látszik a hibaüzenetből, hogy nem lesz jó, ha a variable_get()-tel default értékként sima stringet adsz meg, ami nálad az '1,2,3,4' volt.

    Idézet a hibaüzenetből:
    "WHERE (forexid IN ('47,116,4,34,3,35,1,54908,670'"
    Itt nem jó, hogy ömlesztett string lesz belőle!

    pp tehát ahogy korábban is említettem, szétbontotta először egy tömbre:
    explode(',', variable_get('gft_api_forexids', '1,2,3,4')

    Esélyes, hogy egyébként így is jó lett volna:
    variable_get('gft_api_forexids', array(1,2,3,4))
    Persze ebben az esetben figyelni kell rá, hogy amennyiben van a variable táblában gft_api_forexids bejegyzés, akkor oda is tömb legyen feltöltve (természetesen megfelelően serializálva, vagyis a variable_set()-tel feltöltve egy tömböt).

  4. A sorrendre vonatkozó rész itt van a doksiból:
    TableSort::orderByHeader

    Tulajdonképpen itt az orderByHeader-nek a TableSort extender mellé pakolása logikus is, bár elvileg kerülhetne máshova is "sorrendileg", lásd itt a felhasználását: [link].
    Itt viszont láthatsz egy kis magyarázatot is a query-khez, és a TableSort extender felhasználásához, na meg itt úgy használja az orderByHeader-t, ahogy pp: [link].
    Ahogy a hivatalos oldalon lévő doksiban is szerepel:
    Dynamic queries
    Az utóbbi cikket egyébként mindenképp érdemes lehet áttanulmányozni, ha szeretnéd megérteni a dinamikus query-ket Drupalban.

Huhh, a végére jó terjengős magyarázat lett, bocsánat, hogy kicsit áttekinthetetlen lett - ettől függetlenül remélem segített valamennyit a megértésben.

7
0
Wathfea képe

Ugyan már, ez messzemenőleg áttekinthető és nagyon is segített! :) Köszönöm szépen a részletes leírást, így már érthető, hogy mit miért. :)Még egyszer köszönöm pp-nek is és Neked is.

1
0