sql >> Base de Datos >  >> RDS >> Mysql

Uso de enumeración de MyBatis

He trabajado en esta pregunta desde un par de ángulos y aquí están mis hallazgos. Advertencia:hice todas estas investigaciones usando MyBatis-3.1.1, por lo que las cosas podrían haberse comportado de manera diferente en versiones anteriores.

Primero, MyBatis tiene un EnumTypeHandler incorporado . De forma predeterminada, cada vez que especifique una enumeración de Java como tipo de resultado o tipo de parámetro, esto es lo que manejará ese tipo. Para las consultas, al intentar convertir un registro de base de datos en una enumeración de Java, EnumTypeHandler solo toma un argumento e intenta buscar el valor de enumeración de Java que corresponde a ese valor.

Un ejemplo ilustrará mejor. Supongamos que su consulta anterior devuelve 2 y "Ready" cuando paso "Listo" como argumento. En ese caso, recibo el mensaje de error No enum constant com.foo.Status.2 . Si invierto el orden de su instrucción SELECT para que sea

SELECT ls.name, ls.id

entonces el mensaje de error es No enum constant com.foo.Status.Ready . Supongo que puedes inferir lo que está haciendo MyBatis. Tenga en cuenta que EnumTypeHandler ignora el segundo valor devuelto por la consulta.

Cambiando su consulta a

SELECT UPPER(ls.name)

hace que funcione:se devuelve la enumeración Status.READY.

Entonces, a continuación, traté de definir mi propio TypeHandler para la enumeración de estado. Desafortunadamente, al igual que con el EnumTypeHandler predeterminado , solo pude obtener uno de los valores (id o nombre) para hacer referencia al Enum correcto, no a ambos. Entonces, si la identificación de la base de datos no coincide con el valor que codificaste anteriormente, entonces tendrás una discrepancia. Si se asegura de que la identificación de la base de datos siempre coincida con la identificación que especifica en la enumeración, entonces todo lo que necesita de la base de datos es el nombre (convertido a mayúsculas).

Entonces pensé que sería inteligente e implementaría MyBatis ObjectFactory, tomaría tanto el id de int como el nombre de la cadena y me aseguraría de que coincidieran en la enumeración de Java que devuelvo, pero eso no funcionó porque MyBatis no llama a ObjectFactory para un Tipo de enumeración de Java (al menos no pude hacerlo funcionar).

Así que mi conclusión es que las enumeraciones de Java en MyBatis son fáciles siempre que solo necesite hacer coincidir el nombre de la base de datos con el nombre de la constante de enumeración; use el EnumTypeHandler incorporado o defina el suyo propio si hace UPPER (nombre) en el SQL no es suficiente para hacer coincidir los nombres de enumeración de Java. En muchos casos, esto es suficiente, ya que el valor enumerado puede ser solo una restricción de verificación en una columna y solo tiene un valor único, no una identificación también. Si también necesita hacer coincidir una identificación int así como un nombre, haga que las identificaciones coincidan manualmente al configurar la enumeración de Java y/o las entradas de la base de datos.

Finalmente, si desea ver un ejemplo práctico de esto, vea el koan 23 de mis koans de MyBatis aquí:https://github.com/midpeter444/mybatis-koans . Si solo quiere ver mi solución, busque en el directorio complete-koans/koan23. También tengo un ejemplo de cómo insertar un registro en la base de datos a través de una enumeración de Java.