O MongoDB veio com todos os recursos sofisticados de geração de ObjectId, mas muitas vezes você simplesmente pulou o navio do banco de dados relacional e ainda deseja um campo identificador numérico fácil de ler/comunicar que é incrementado automaticamente toda vez que um novo registro é inserido.
Uma sugestão interessante do tutorial do MongoDB é usar uma coleção de contadores com um 'nome do contador' como seu id e um campo 'seq' para armazenar o último número usado.
Ao desenvolver usando Spring Data MongoDB, esse truque legal pode ser escrito como um serviço simples. Aqui eu usei o nome da coleção como o nome do contador, então é fácil adivinhar/lembrar.
import static org.springframework.data.mongodb.core.FindAndModifyOptions.options;
import static org.springframework.data.mongodb.core.query.Criteria.where;
import static org.springframework.data.mongodb.core.query.Query.query;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.mongodb.core.MongoOperations;
import org.springframework.data.mongodb.core.query.Update;
import org.springframework.stereotype.Service;
import com.model.CustomSequences;
@Service
public class NextSequenceService {
@Autowired private MongoOperations mongo;
public int getNextSequence(String seqName)
{
CustomSequences counter = mongo.findAndModify(
query(where("_id").is(seqName)),
new Update().inc("seq",1),
options().returnNew(true).upsert(true),
CustomSequences.class);
return counter.getSeq();
}
}
CustomSequences é apenas uma classe simples que representa a coleção. Por favor, tenha cuidado com o uso do tipo de dados int, isso limitará a 2^31 entradas no máximo.
import org.springframework.data.annotation.Id;
import org.springframework.data.mongodb.core.mapping.Document;
@Document(collection = "customSequences")
public class CustomSequences {
@Id
private String id;
private int seq;
// getters and setters
}
Então, ao inserir uma nova entrada (com a ajuda do suporte ao Spring MongoDB Repository), basta definir o campo id assim antes de salvá-lo
BaseQuestion baseQuestion = new BaseQuestion();
baseQuestion.setQuestionId(nextSequenceService.getNextSequence("customSequences"));
/* Rest all values */
baseQuestionRepository.save(baseQuestion);
Se você não gostar dessa maneira, precisará usar MongoDBEvents e usar onBeforeConvert para gerar valor automatizado usando a mesma abordagem acima.
Também a abordagem acima é threadsafe, pois findAndModify() é um método atômico seguro para thread