tiny ‘n’ smart
database layer

Odkazy: dibi | API reference

Oznámení

Omlouváme se, provoz fóra byl ukončen

Dibi a Oracle

před 10 lety

LeonardoCA
Člen | 297

Začal jsem testovat použití dibi s Oracle databází a napíšu tady pár poznámek, kdyby jste měl někdo více zkušenosti ozvěte se prosím. Zkouším zatím oživit standartní DataGrid.

1. DibiProfiler – vyhazuje vyjímku díky tomu, že oracle driver nemá implementovanou metodu getRowCount() – chtělo by to ošetřit /pro unbuffered dotazy nezobrazovat příslušné info/

2. applyLimit se dá implementovat takto

public function applyLimit(&$sql, $limit, $offset)
{
    if ($limit < 0 && $offset < 1) return;
    // rownum is 1 and up vs mysql line numbering 0 and up - that's why rnum > '. (int) $offset
    $sql = 'SELECT * FROM (SELECT a.*, rownum rnum FROM (' . $sql . ') a WHERE rownum <= '.((int) $offset + (int) $limit).') WHERE rnum > '. (int) $offset;
}

Trochu teorie k tomu: http://www.oracle.com/…6asktom.html

3. Ve funkci escape jsem se pokusil nahradit FIELD_BOOL – problém vznikl při použití datasource, kdy bez stanovení podmínky Oracle nespolkne podmínku „WHERE 1“, ale už akceptuje „1=1“. Tohle je sice nesmyslné, ale v tomto případě funkční řešení.

case dibi::FIELD_BOOL:
    return $value ? '1=1' : 0; //originally return $value ? 1 : 0; LXO

4. Další problém je např. v konstruktoru DibiDatasource „AS t

$this->sql = '(' . $sql . ') AS t';

Oracle vyhodí chybu „ORA-00933: SQL command not properly ended“ – je to „AS t“ nutné? zatím jsem se nedopátral k jeho významu

5. getTables() – by mohlo fungovat nějak takto

public function getTables()
{
    $this->query("SELECT * FROM cat");
    $res = array();
    while ($row = $this->fetch(FALSE)) {
      if (($row[1] === 'TABLE')||($row[1] === 'VIEW')){
          $res[] = array(
             'name' => $row[0],
             'view' => isset($row[1]) && $row[1] === 'VIEW',
          );
      };
    }
    $this->free();
    return $res;
    //throw new NotImplementedException;
}

to je první nástřel, nemám vyzkoušené všechny možnosti …

Editoval LeonardoCA (25. 4. 2009 18:21)

před 10 lety

David Grudl
Nette Core | 6806

Díky moc za cenné připomínky, aplikoval jsem je do poslední revize.

1. DibiProfiler – vyhazuje vyjímku díky tomu, že oracle driver nemá implementovanou metodu getRowCount() – chtělo by to ošetřit /pro unbuffered dotazy nezobrazovat příslušné info/

opraveno

2. applyLimit se dá implementovat takto

Doplněno. Můžeš to prosím vyzkoušet, i pro případ, že bude nastaven jen limit nebo jen offset? (tj. limit je třeba –1)

3. Ve funkci escape jsem se pokusil nahradit FIELD_BOOL – problém vznikl při použití datasource, kdy bez stanovení podmínky Oracle nespolkne podmínku „WHERE 1“, ale už akceptuje „1=1“. Tohle je sice nesmyslné, ale v tomto případě funkční řešení.

opraveno

4. Další problém je např. v konstruktoru DibiDatasource „AS t

Je to kvůli MySQL http://dev.mysql.com/…d-views.html. Pokud je problém čistě v tom „AS“, to lze vyhodit. Použití aliasu by snad nemělo způsobovat problém, v tom „FROM ($sql) a“ je taky.

5. getTables() – by mohlo fungovat nějak takto

Je to tam.

před 10 lety

LeonardoCA
Člen | 297

Paráda, všechno funguje, až na:

2. applyLimit

__rownum musí být v uvozovkách – pokud je na začátku podtržítko

$sql = 'SELECT * FROM (SELECT t.*, ROWNUM AS "__rnum" FROM (' . $sql . ') t ' . ($limit >= 0 ? 'WHERE ROWNUM <= ' . ((int) $offset + (int) $limit) : '') . ') WHERE "__rnum" > '. (int) $offset;

takhle to funguje

pro zajimavost citace z oracle reference:

Nonquoted identifiers must begin with an alphabetic character from your database character set. Quoted identifiers can begin with any character.

Nonquoted identifiers can contain only alphanumeric characters from your database character set and the underscore (_), dollar sign ($), and pound sign (#). Database links can also contain periods (.) and „at“ signs (@). Oracle strongly discourages you from using $ and # in nonquoted identifiers.

Quoted identifiers can contain any characters and punctuations marks as well as spaces. However, neither quoted nor nonquoted identifiers can contain double quotation marks or the null character (\0).

otestoval jsem varianty, když bude nastaven jen limit nebo jen offset, to je ok.

Editoval LeonardoCA (26. 4. 2009 21:29)

před 10 lety

David Grudl
Nette Core | 6806

tak super. uvozovky fixnu.