在 Java(或其他語言)中使用 MySQL 的 ENUM 類型時,實體類的映射方式取決於你使用的 ORM 框架(如 MyBatis、Hibernate/JPA 等)。以下是幾種常見做法:


一、使用 JPA/Hibernate(推薦)

1. 定義枚舉類

public enum Gender {
    MALE, FEMALE, OTHER
}

2. 實體類中使用

@Entity
@Table(name = "user")
public class User {
    @Id
    private Long id;

    @Enumerated(EnumType.STRING) // 存儲為字符串 'MALE', 'FEMALE' 等
    private Gender gender;

    // getter/setter...
}
  • @Enumerated(EnumType.STRING):將枚舉存儲為字符串(對應 MySQL ENUM 的值)
  • @Enumerated(EnumType.ORDINAL):按序號存儲(0,1,2...),不推薦,因為 MySQL 的 ENUM 是基於字符串的,且序號變更易出錯。

⚠️ 注意:MySQL 的 ENUM 類型本質上是字符串集合,底層用數字索引優化存儲,但對外表現為字符串。所以建議用 STRING 方式映射。


二、使用 MyBatis

MyBatis 默認支持 Java 枚舉與數據庫字符串/整數的映射。

1. 枚舉定義(可選實現接口以增強控制)

public enum Status {
    ACTIVE("active"),
    INACTIVE("inactive");

    private final String value;

    Status(String value) {
        this.value = value;
    }

    public String getValue() {
        return value;
    }

    // 可選:根據數據庫值反向查找枚舉
    public static Status fromValue(String value) {
        for (Status s : values()) {
            if (s.value.equals(value)) {
                return s;
            }
        }
        throw new IllegalArgumentException("Unknown status: " + value);
    }
}

2. 實體類

public class User {
    private Long id;
    private Status status;
    // getter/setter
}

3. MyBatis TypeHandler(可選但推薦)

如果你的枚舉使用自定義字符串值(如上面的 "active"),需要寫一個 TypeHandler

@MappedTypes(Status.class)
public class StatusTypeHandler extends BaseTypeHandler<Status> {

    @Override
    public void setNonNullParameter(PreparedStatement ps, int i, Status parameter, JdbcType jdbcType) throws SQLException {
        ps.setString(i, parameter.getValue());
    }

    @Override
    public Status getNullableResult(ResultSet rs, String columnName) throws SQLException {
        String value = rs.getString(columnName);
        return value == null ? null : Status.fromValue(value);
    }

    // 其他重載方法...
}

然後在 MyBatis 配置中註冊,或在字段上使用 @Results / resultMap 指定 typeHandler。

如果枚舉名和數據庫值一致(如 ACTIVE'ACTIVE'),MyBatis 默認能自動轉換,無需 TypeHandler。


三、注意事項

  1. MySQL ENUM 的限制
  • 值必須預先定義,不能動態擴展。
  • 修改 ENUM 列(增刪值)可能鎖表,影響性能。
  • 排序按定義順序,不是字母序。
  1. 替代方案建議: 很多團隊避免使用 MySQL 的 ENUM,而改用:
  • VARCHAR + 應用層枚舉校驗
  • 單獨的字典表(更靈活,支持國際化等)

這樣實體類直接用枚舉即可,數據庫無耦合。


總結

場景

實體類處理方式

JPA/Hibernate

@Enumerated(EnumType.STRING) + Java enum

MyBatis(簡單)

Java enum 名 = DB 值,自動映射

MyBatis(複雜值)

自定義 TypeHandler

最佳實踐

考慮不用 MySQL ENUM,改用 VARCHAR + 枚舉

mysql enum 類型_MySQL