Results 1 to 3 of 3

Thread: findById returns null

  1. #1
    Join Date
    Nov 2011
    Posts
    5

    Default findById returns null

    1.
    Code:
    PostThread thread = op.findOne(new Query(new Criteria("_id").is(id)), PostThread.class);
    2.
    Code:
    PostThread thread = op.findById(id, PostThread.class);
    statement 1 returns object.
    statement 2 returns null.

    What's the problem ?

    my domain class is

    Code:
    @Document
    public class PostThread {
    
    	@Id
    	private int id;
    
    	private int categoryId;
    }

  2. #2
    Join Date
    Aug 2004
    Location
    New York, NY
    Posts
    74

    Default

    Hi,

    It is probably related to your other question regarding to using int as an @Id value. This section of the docs (How the '_id' field is handled in the mapping layer) goes over the conventions in terms of what is supported with using and Id field an generated values.

    I presume in your case you were expecting the id field to be populated after a save. That will only work if the id field is of the type String, BigInteger or ObjectId. Those are the only types in which the automatically generated Mongo OID can be marshalled into. You can store an int value as the mongo _id value but you would need to assign it in the POJO first before saving.

    So, either change your Id type to be String, BigInteger or ObjectId in the PostThread class or assign the id yourself before saving. We will change the code so than if an @Id field other than String,BigInteger, or ObjectId is passed to MongoTemplate for a save and it has a null value, an exception will be thrown. See this issue.

    Here is some working code

    Code:
    	PostThread pt = new PostThread();
    		pt.setCategoryId(1);
    		template.save(pt);
    		String id = pt.getId();
    		PostThread thread = template.findById(id, PostThread.class);
    		assertNotNull(thread);
    		System.out.println(thread);
    		thread = template.findOne(query(where("id").is(id)), PostThread.class);
    		assertNotNull(thread);
    		System.out.println(thread);
    And PostThread is
    Code:
    public class PostThread {
    	@Override
    	public String toString() {
    		return "PostThread [id=" + id + ", categoryId=" + categoryId + "]";
    	}
    
    	private String id;
    	
    	private int categoryId;
    
    	public String getId() {
    		return id;
    	}
    
    	public void setId(String id) {
    		this.id = id;
    	}
    
    	public int getCategoryId() {
    		return categoryId;
    	}
    
    	public void setCategoryId(int categoryId) {
    		this.categoryId = categoryId;
    	}
    	
    }
    Note that in this case, since it is such a simple class, you don't even need to use the Spring mapping annotations.

    Cheers,
    Mark
    Last edited by Mark Pollack; Nov 17th, 2011 at 11:21 AM.

  3. #3
    Join Date
    Nov 2011
    Posts
    5

    Default

    Thank you for reply.
    But i'm generating int id value manually.

    Code:
    public class Seq {
    
    	@Autowired
    	private MongoOperations op;
    
    	private int threadId;
    	private int postId;
    
    	@PostConstruct
    	private void init() {
    		threadId = getThreadSeed();
    		postId = getPostSeed();
    	}
    
    	private int getThreadSeed() {
    		Query query = new Query();
    		query.sort().on("_id", Order.DESCENDING);
    		query.limit(1);
    		List<PostThread> threadList = op.find(query, PostThread.class);
    		return threadList.isEmpty() ? 0 : threadList.get(0).getId();
    	}
    
    	private int getPostSeed() {
    		Query query = new Query();
    		query.sort().on("_id", Order.DESCENDING);
    		query.limit(1);
    		List<Post> postList = op.find(query, Post.class);
    		return postList.isEmpty() ? 0 : postList.get(0).getId();
    	}
    
    	public synchronized int getNewThreadId() {
    		return ++threadId;
    	}
    
    	public synchronized int getNewPostId() {
    		return ++postId;
    	}
    }
    and assigns id before insert.

    Code:
    	public void insertThread(PostThread thread) {
    		thread.setId(seq.getNewThreadId());
    		op.insert(thread);
    	}
    If int id is set as 10 and saved, it goes as "10" not as 10.
    then
    If I call findById(10), it returns null,
    If I call findOne(new Query(new Criteria("_id").is(10)), PostThread.class), it returns null.

    then I modify "10" to 10 manually,

    and
    If I call findById(10), it returns null,
    If I call findOne(new Query(new Criteria("_id").is(10)), PostThread.class), it returns as normal.

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •