実際にはそうではありません。MongoJavaドライバーは、最後のエラーを構築された文字列としてすでに公開しているためです。
writeResult.getLastError().get("err")
次のようなものを返します:
insertDocument :: caused by :: 11000 E11000 duplicate key error index: test.person.$username dup key: { : "joe" }
これはシェルとすべてのドライバーにも当てはまると思います。
合理的な解決策は、カスタム例外を使用してそのような重複キー例外を解析することだと思います:
public class DetailedDuplicateKeyException extends DuplicateKeyException {
public DetailedDuplicateKeyException(String msg) {
// Instead of just calling super parse the message here.
super(msg);
}
}
...カスタム例外トランスレータ:
public class DetailedDuplicateKeyExceptionTransaltor extends MongoExceptionTranslator {
@Override
public DataAccessException translateExceptionIfPossible(RuntimeException ex) {
if (ex instanceof MongoException.DuplicateKey) {
return new DetailedDuplicateKeyException(ex.getMessage());
}
return super.translateExceptionIfPossible(ex);
}
}
...そしてSpring構成を適切に設定する:
@Bean
public MongoFactoryBean mongo() {
MongoFactoryBean mongo = new MongoFactoryBean();
mongo.setExceptionTranslator(new DetailedDuplicateKeyExceptionTransaltor());
mongo.setHost("localhost");
return mongo;
}
編集
MongoTemplate
を検査した後 コード(1.4.1.RELEASE)、内部的にはSimpleMongoDbFactory
のようです デフォルトのMongoExceptionTranslator
を取得するために使用されます 、したがって、MongoFactoryBean
で作成されたもの 影になっています。その部分を逃していた。
解決策は、SimpleMongoDbFactory
をオーバーライドすることです。 (MongoFactoryBean
は忘れてください 、このコンテキストでは役に立たない):
public class MySimpleMongoDbFactory extends SimpleMongoDbFactory {
PersistenceExceptionTranslator translator = new
DetailedDuplicateKeyExceptionTransaltor();
public MySimpleMongoDbFactory(Mongo mongo, String databaseName) {
super(mongo, databaseName);
}
@Override
public PersistenceExceptionTranslator getExceptionTranslator() {
return translator;
}
}
これで、カスタムのMongoDbFactory
を使用してテンプレートを作成できます。 :
template = new MongoTemplate
(new MySimpleMongoDbFactory(new MongoClient(), "test"));
試してみましたが、これでうまくいきます。