Spring Data MongoDB:实体布尔属性持久化为可读可搜索值方案咨询
Hey Thorben, let's work through how to handle your boolean-to-readable-string requirement for MongoDB while supporting that regex-based "contains" search you're building for your prototype. Here are two practical approaches tailored to your needs:
This approach gives you the best of both worlds: you retain efficient native boolean queries for exact matches, plus a human-readable description field perfect for regex-based "contains" searches.
How to Implement It
Add a description field to your Foo class, then populate it based on the values of superPowers and evil before persisting the entity (use ORM lifecycle hooks like JPA's @PrePersist or a simple utility method in your DAO/service layer):
public class Foo { protected Boolean superPowers; protected Boolean evil; protected String description; // New field for search/readability // Call this before saving to MongoDB public void populateDescription() { if (superPowers == null || evil == null) { this.description = "Unknown Entity"; return; } if (superPowers && !evil) { this.description = "Super Hero"; } else if (superPowers && evil) { this.description = "Villain"; } else { this.description = "Regular Person"; // Adjust based on your needs } } }
MongoDB Storage Result
You'll get exactly the format you wanted:
{ "superPowers": true, "evil": false, "description": "Super Hero" }
Search Example
Use regex on the description field for your "contains" search:
// Case-insensitive search for hero-related entities db.foo.find({ description: /hero/i })
If you don't need native boolean querying and prefer to store the boolean state as searchable strings (as your "temporary acceptable" format mentions), you can map the boolean values directly to string equivalents.
How to Implement It
Change the field types from Boolean to String, and add setter logic to convert boolean inputs to your desired string values:
public class Foo { protected String superPowers; protected String evil; public void setSuperPowers(Boolean hasPowers) { this.superPowers = (hasPowers != null && hasPowers) ? "super powers" : ""; } public void setEvil(Boolean isEvil) { this.evil = (isEvil != null && isEvil) ? "evil" : ""; } }
MongoDB Storage Result
You'll get the format you referenced:
{ "superPowers": "super powers", "evil": "" }
Search Example
Query using regex on the string fields:
// Find entities with super powers db.foo.find({ superPowers: /super/i }) // Find non-evil entities db.foo.find({ evil: "" })
- The first approach is more flexible: it lets you do fast exact boolean queries (e.g.,
db.foo.find({ evil: true })) while still supporting regex searches on thedescriptionfield. - Since you're working with a small dataset, regex performance won't be an issue. If you scale later, consider MongoDB's native text indexes for more efficient full-text search.
- For the second approach, be consistent with empty strings vs.
null—stick to one to avoid confusion in queries.
内容的提问来源于stack exchange,提问作者thorben.heins

