3

dropwizard プロジェクトをセットアップしようとしていますが、行き詰っています。@GetGeneratedKeys で自動生成された id フィールドを取得しようとすると、次の例外が発生します。

org.postgresql.util.PSQLException: Bad value for type long : foo.

リクエストは単純な JSON リクエストです

{"name":"foo"}

データベースへの INSERT は成功しますが、ステートメントは生成された ID ではなく名前の値を返すようです。どうすればこれを解決できますか?

私は postgresql を使用しています。テーブル プロジェクトには、nextval('project_id_seq'::regclass) を持つ主キー フィールド「id」が含まれています。私が使用するPOJO、DAO、およびリソースクラスは次のとおりです。

public class Project {
    private long id;
    private String name;

    public Project() { // Jackson deserialization }
    public Project(long id, String name) {
        this.id = id;
        this.name = name;
    }
    ...
}

@RegisterMapper(ProjectMapper.class)
public interface ProjectDAO {
    @SqlUpdate("insert into project (name) values (:name)")
    @GetGeneratedKeys
    public long insert(@Bind("name") String name);
}

@Path("/project")
@Consumes({MediaType.APPLICATION_JSON})
@Produces({MediaType.APPLICATION_JSON})
public class ProjectResource {
    ProjectDAO projectDAO;

    public ProjectResource(ProjectDAO personDAO) {
        this.projectDAO = personDAO;
    }

    @POST
    @Timed
    public Response add(@Valid Project project) {
        long newId = projectDAO.insert(project.getName());
        project.setId(newId);
        return Response.status(Response.Status.CREATED)
                       .entity(project).build();
    }
}

===============

アップデート

これは、id 列がテーブルの最初の列ではないという事実に関連していることがわかりました。列名は。この問題は、 @GetGeneratedKeysが org.skife.jdbi.v2.util.LongMapper.FIRST を返す org.skife.jdbi.v2.PrimitivesMapperFactory を使用している org.skife.jdbi.v2.sqlobject.FigureItOutResultSetMapper を使用しているために発生します。このマッパーは 、メソッド extractByIndex(...) を介してjava.sql.ResultSet.getLong(1)を呼び出して、生成された ID を取得していますが、これは私の場合は ID ではありません...

データベースの列を再編成することで問題を解決しますが、可能であれば堅牢な実装が必要です: @GetGeneratedKeys アノテーションを使用するときに id 列の列名を指定する方法はありますか? (org.skife.jdbi.v2.util.LongMapper クラスには、extractByName(...) というメソッドも含まれています)

4

1 に答える 1