2016-06-23 15 views
7

Używam DBUnit dla testu integracji, a przed wykonaniem kodu testu używam do tego błędu:DBUnit PostgresqlDataTypeFactory nie rozpoznaje listy enum

badges.track_types data type (2003, '_text') not recognized and will be ignored. See FAQ for more information. 

org.dbunit.dataset.NoSuchColumnException: badges.TRACK_TYPES - (Non-uppercase input column: track_types) in ColumnNameToIndexes cache map. Note that the map's column names are NOT case sensitive. 

kolumna, która jest ignorowana jest lista wylicza. W zbiorze jest napisane tak:

<?xml version='1.0' encoding='UTF-8'?> 
<dataset> 
    // More info ... 
    <badges name="30&apos;000" description="30k a day" image_name="30000.png" threshold_val="30000.00000000" has_many="true" id="45" track_types="{TRACK_GENERIC}" "/> 
</dataset> 

spojrzałem w DBUnit FAQ i zobaczyłem this issue, który mówi, że muszę zastąpić metodę isEnumType(), aby wspierać mój enum jest PostgreSQL, więc zrobiłem to:

/** 
* Override method to set custom properties/features 
*/ 
protected void setUpDatabaseConfig(DatabaseConfig config) { 

    config.setProperty(DatabaseConfig.PROPERTY_DATATYPE_FACTORY, new PostgresqlDataTypeFactory(){ 
     public boolean isEnumType(String sqlTypeName) { 
      if(sqlTypeName.equalsIgnoreCase("track_types")){ 
       return true; 
      } 
      return false; 
     } 
    }); 
    config.setProperty(DatabaseConfig.PROPERTY_METADATA_HANDLER, new DefaultMetadataHandler()); 
} 

Ale nadal mam ten sam błąd i nie wiem dlaczego. Może nie przesadzam z tą metodą? Może to nie jest nawet przyczyną mojego problemu? Jeśli potrzebujesz innego kodu, po prostu zapytaj, dzięki!

+0

Czy w zbiorze danych 'odznaki' znajduje się kolumna' TRACK_TYPES'? –

+0

Czy możesz wysłać mi swój kod źródłowy? Spróbuję się w to zagłębić. –

+0

@KevinWallis Właśnie zaktualizowałem pytanie, aby zobaczyć wiersz zestawu danych. Tak, zawiera tę kolumnę, ale jest ignorowana, jak stwierdza błąd. – alfizqu

Odpowiedz

1

Cóż ... nie był w stanie rozwiązać tego dokładnie, ale udało się go rozwiązać przez obejście.

Ten błąd pojawia się z powodu adnotacji @DatabaseSetup. Jeśli zrobiłem ten proces bez użycia go, to nadal generuje błąd "nie rozpoznano kolumny", ponieważ nie rozpoznaje on tablic postgresów (to była podstawowa przyczyna, którą mam), ale mogłem go rozwiązać, tworząc nowy DataTypeFactory, który rozszerza z domyślnego:

public class PsqlArrayDataTypeFactory extends DefaultDataTypeFactory { 
     public DataType createDataType(int sqlType, String sqlTypeName) throws DataTypeException { 
      if (sqlType == Types.ARRAY) 
      { 
       return DataType.VARCHAR; 
      } 

      return super.createDataType(sqlType, sqlTypeName); 
     } 
    } 
2

Staraj się utrzymywać enum z jego wartością

enum.values(); 

zwróci tablicę niż zapisać ten element

+0

gdzie powinienem przechowywać wyliczenie? W metodzie setUpDatabaseConfig? – alfizqu

+0

Spróbuj użyć 'EntityManager' ma metody' persist (obj) ' – Irazza

1

jest ograniczone wsparcie dla PostgreSQL teksty stałe bo tylko czytania i pisania ciągi jest obsługiwany od dbunit 2.4.6. Aby to zrobić trzeba zastąpić metodę „isEnumType” w PostgresqlDataTypeFactory jak ten:

PostgresqlDataTypeFactory factory = new PostgresqlDataTypeFactory(){ 
    public boolean isEnumType(String sqlTypeName) { 
    if(sqlTypeName.equalsIgnoreCase("abc_enum")){ 
     return true; 
    } 
    return false; 
    } 
}; 
0

miałem następny błąd:

Caused by: org.postgresql.util.PSQLException: ERROR: column "status" is of type topic_status but expression is of type character varying 
    Hint: You will need to rewrite or cast the expression. 

DbUnit żąda meta na stole i odbiera typ VARCHAR za teksty stałe z PostgreSQL. Ale PostgreSQL nie zaakceptuje tego typu z powrotem.

I overrode metody z PostgresqlDataTypeFactory w następny sposób:

config.setProperty(DatabaseConfig.PROPERTY_DATATYPE_FACTORY, 
    new PostgresqlDataTypeFactory() { 
     @Override 
     public boolean isEnumType(String sqlTypeName) { 
      return "topic_status".equalsIgnoreCase(sqlTypeName); 
     } 

     @Override 
     public DataType createDataType(int sqlType, String sqlTypeName) throws DataTypeException { 
      if (isEnumType(sqlTypeName)) { 
       sqlType = Types.OTHER; 
      } 
      return super.createDataType(sqlType, sqlTypeName); 
     } 
    }); 
); 

Ustawia typ dla wyliczenia jako OTHER i sposobu dominującej super.createDataType(sqlType, sqlTypeName) tworzy DataType w odpowiedni sposób.

wersja PostgreSQL: wersja 9.6.5
DBUnit: 2.5.4

Więcej informacji można znaleźć na discussion.

Powiązane problemy