2014-11-18 8 views
11

Nel mio file di migrazione, ho dato il mio tavolo pages a enum con 2 possibili valori (come visto di seguito). La mia domanda è, se è possibile selezionare questi valori con Laravels Eloquent?Ottieni opzioni enum in laravels eloquente

$table->enum('status', array('draft','published')); 

Ci sono diverse soluzioni che ho trovato, ma ci deve essere un modo "eloquenti-native" per gestire questa situazione. La mia uscita prevista sarebbe questa (sarebbe perfetta!):

array('draft','published') 

Grazie in anticipo!

risposta

12

Sfortunatamente, Laravel non offre una soluzione per questo. Dovrai farlo da solo. Ho fatto qualche ricerca e ho trovato this answer

È possibile utilizzare questa funzione e di trasformarlo in un metodo nella classe del modello ...

class Page extends Eloquent { 

    public static function getPossibleStatuses(){ 
     $type = DB::select(DB::raw('SHOW COLUMNS FROM pages WHERE Field = "type"'))[0]->Type; 
     preg_match('/^enum\((.*)\)$/', $type, $matches); 
     $values = array(); 
     foreach(explode(',', $matches[1]) as $value){ 
      $values[] = trim($value, "'"); 
     } 
     return $values; 
    } 
} 

e si utilizza in questo modo

$options = Page::getPossibleStatuses(); 

Se vuoi che tu possa renderlo un po 'più universalmente accessibile e generico.

Innanzitutto, creare un BaseModel. Tutti i modelli dovrebbero quindi estendere da questa classe

class BaseModel extends Eloquent {} 

Dopo di che, mettere questa funzione in là

public static function getPossibleEnumValues($name){ 
    $instance = new static; // create an instance of the model to be able to get the table name 
    $type = DB::select(DB::raw('SHOW COLUMNS FROM '.$instance->getTable().' WHERE Field = "'.$name.'"'))[0]->Type; 
    preg_match('/^enum\((.*)\)$/', $type, $matches); 
    $enum = array(); 
    foreach(explode(',', $matches[1]) as $value){ 
     $v = trim($value, "'"); 
     $enum[] = $v; 
    } 
    return $enum; 
} 

Si chiama questo genere

$options = Page::getPossibleEnumValues('status'); 
+2

Perché non utilizzare un tratto dedicato per questo? – ozanmuyes

+0

Certo, puoi usare un tratto se vuoi che – lukasgeiter

+0

Laravel lo aggiunga ad ogni Classe Eloquent come Tratto –

0

A partire dal L5.17 Eloquente fa non includere questa funzionalità, ma è necessario tornare al QL nativo. Ecco un esempio che funzionerà con SQL e in una riga, restituendo un array come richiesto.

Nello spirito di una complessità di linea;)

ho gettato questo in una delle mie vista autori - recupera la colonna dalla tabella, esplode e assembla i valori in un array.

I iterare su quello nelle mie visualizzazioni utilizzando un foreach.

explode (
    "','", 
    substr (
     DB::select(" SHOW COLUMNS 
        FROM ".(new \Namespace\Model)->getTable()." 
        LIKE 'colName'" 
    )[0]->Type, 
     6, 
     -2 
    ) 
); 
1

Ha apportato un piccolo miglioramento alla funzione di lukasgeiter. Il ciclo di foreach nella sua risposta sta analizzando la stringa. È possibile aggiornare la regex per farlo per voi.

/** 
* Retrieves the acceptable enum fields for a column 
* 
* @param string $column Column name 
* 
* @return array 
*/ 
public static function getPossibleEnumValues ($column) { 
    // Create an instance of the model to be able to get the table name 
    $instance = new static; 

    // Pulls column string from DB 
    $enumStr = DB::select(DB::raw('SHOW COLUMNS FROM '.$instance->getTable().' WHERE Field = "'.$column.'"'))[0]->Type; 

    // Parse string 
    preg_match_all("/'([^']+)'/", $enumStr, $matches); 

    // Return matches 
    return isset($matches[1]) ? $matches[1] : []; 
}