- Introduction
- Step 1: Creating a Database
- Step 2: Adding a MongoDB Collection and Data
- Step 3 : Using Spring Initializr to Create a Project
- Step 4 : Import project into Eclipse
- Step 5 : Adding Model to Spring Boot Project
- Step 6 : Adding Repository to Spring Boot Project
- Step 7 : Adding the MongoDB Connection Info
- Step 8 : Creating REST Controller
- Step 9 : Adding the REST Endpoints
- Step 10 : Creating Service
Introduction
This document walks you through the process of using Spring Boot and MongoDB to build a Rest API that stores data in and retrieves it from MongoDB, a document-based database.
Tools Used in this Tutorial
- Java
- Spring Boot
- Maven
- MongoDB
- Postman
- Eclipse
Step 1: Creating a Database
It is assumed that you already have an accessible instance of MongoDB that you can connect to.
Let us start by creating a test database. I will call mine "rest_pets" using the following command in the MongoDB shell, or through a database manager like Robo 3T 1.1.1.
use rest_pets; |
---|
This will create a new database in MongoDB that we can use for our tutorial.
Step 2: Adding a MongoDB Collection and Data
In MongoDB, collections are analogous to tables in a relational database — they hold the data that we will be querying using our REST API. I will be creating a sample collection that will hold data about different types of pets. Let's create the collection with the following command:
db.createCollection("pets"); |
Once the collection is created, we need to add some data! This collection will hold the names, breeds, and species of various pets.
We can add data to the collection with the following command:
db.pets.insertMany([ { "name" : "Spot", "species" : "dog", "breed" : "pitbull" }, { "name" : "Daisy", "species" : "cat", "breed" : "calico" }, { "name" : "Bella", "species" : "dog", "breed" : "australian shepard" } ]); |
Querying the collection with
db.pets.find({});
reveals that MongoDB automatically assigns a unique _id
field to each document to make it easier to find and edit documentsStep 3 : Using Spring Initializr to Create a Project
Spring offers a tool called the Spring Initializr to help jump-start your Spring Boot project. Access the Initializr at start.spring.io and enter the following information:
- Group: This is the package name
- Example: com.esb.demo
- Artifact: This is the project name
- Example: SpringBootMongoDB
- Dependencies: These are the features that will be added to your project (remember, you can always add these later)
- Our tutorial will use the "Web" and "MongoDB" dependencies
Then click Generate Project to download a .zip file with the basic project structure.
Step 4 : Import project into Eclipse
With the project downloaded from the Spring Initializer, you can now open it in your favorite IDE to begin editing the project. In my case i am using eclipse
Step 5 : Adding Model to Spring Boot Project
First, we will want to add a pets model, so that Spring will know what kind of data the database will return. We can do this by creating a new folder in
src/main/java/[package name]/
called "models". In the new "models" folder, we can create a file called Pets.java
. This Java class will hold the basic structure of a document in the "pets" collection, so the class looks as follows:package com.esb.demo.SpringBootMongoDB.models; import org.bson.types.ObjectId; import org.springframework.data.annotation.Id; public class Pets { @Id public ObjectId _id; public String name; public String species; public String breed; // Constructors public Pets() { } public Pets(ObjectId _id, String name, String species, String breed) { this._id = _id; this.name = name; this.species = species; this.breed = breed; } // ObjectId needs to be converted to string public String get_id() { return _id.toHexString(); } public void set_id(ObjectId _id) { this._id = _id; } public String getName() { return name; } public void setName(String name) { this.name = name; } public String getSpecies() { return species; } public void setSpecies(String species) { this.species = species; } public String getBreed() { return breed; } public void setBreed(String breed) { this.breed = breed; } } |
Step 6 : Adding Repository to Spring Boot Project
Now that we have a model that identifies the data structure stored in the database to Spring Boot, we can create the connector between the model and MongoDB. This is done through a Repository interface. We can create this first by making a new folder called "repositories" in
src/main/java/[package name]/
.
In the new "repositories" folder, we can create a file called
PetsRepository.java
. The name of this repository is extremely important because it tells MongoDB the collection that it will be querying (in this case, the pets collection). This interface will extend the MongoRepository class, which already contains generic methods like save
(for creating/updating documents) and delete
(for removing documents), but we will need to specify additional methods ourselves.
Luckily, we do not need to manually implement these queries, we can simply use Spring Boot's repository naming conventions, and the MongoRepository will intelligently construct the queries at runtime. This means that our interface will be extremely simple, as follows:
package com.esb.demo.SpringBootMongoDB.repositories; import org.bson.types.ObjectId; import org.springframework.data.mongodb.repository.MongoRepository; import com.esb.demo.SpringBootMongoDB.models.Pets; public interface PetsRepository extends MongoRepository<Pets, String> { Pets findBy_id(ObjectId _id); } |
Step 7 : Adding the MongoDB Connection Info
To tell Spring the connection information for our MongoDB, we will need to add connection details to the
application.properties
file, located in the "src/main/resources" folder. Add the following lines to the file, replacing the information in brackets with the information specific to your MongoDB instance:spring.data.mongodb.host=localhost spring.data.mongodb.port=27017 spring.data.mongodb.authentication-database=admin spring.data.mongodb.username=dev spring.data.mongodb.password=dev spring.data.mongodb.database=rest_pets |
This is all the information that Spring will need to connect to the database.
Step 8 : Creating REST Controller
Spring should now be able to connect to MongoDB, so now we can establish the enpoints that we can contact to interact with the database. This will be done in a Spring Rest Controller, which uses Request Mappings to map requests with functions. We can create a Rest Controller by adding a file called
PetsController.java
to the src/main/java/[package name]/
folder. The basic file structure will look as follows:package com.esb.demo.SpringBootMongoDB.controller; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RestController; import com.esb.demo.SpringBootMongoDB.service.PetsService; @RestController @RequestMapping(value = "/pets") public class PetsController { @Autowired private PetsService petsService; } |
The
@RestController
annotation tells Spring that this class will requested by URL and will return data to the requester. The @RequestMapping
annotation specifies the base URL that the controller will be handling, so any request to the host starting with "/pets" will be directed to this controller. The @Autowired
annotation creates an instance of the PetsRepository object that will allow us to access and modify the pets database.Step 9 : Adding the REST Endpoints
All of the following enpoints will be added directly into the PetsController class.
GET
@RequestMapping(value = "/all", method = RequestMethod.GET) public List<Pets> getAllPets() { return petsService.getAllPets(); } @RequestMapping(value = "{id}", method = RequestMethod.GET) public Pets getPetById(@PathVariable("id") ObjectId id) { return petsService.getPetbyId(id); } |
The first mapping takes any
GET
requests to the host with a URL of /pets/all
and maps them to the getAllPets()
method, which requests all documents from the pets
collection.
The second mapping takes and
GET
requests to the host with a URL of /pets/
followed by an ObjectId and maps them to the getPetById()
method, which searches the pets
collection for the document with an _id
field equal to the ObjectId in the URL.
PUT
@RequestMapping(value = "{id}", method = RequestMethod.PUT) public void modifyPetById(@PathVariable("id") ObjectId id, @RequestBody Pets pets) { pets.set_id(id); petsService.updatePetById(pets); } |
This mapping expects a request body (in JSON format) with each of the fields that a Pets object contains (
name
, species
, and breed
). The id in the request URL is the _id
of the document to be modified.
POST
@RequestMapping(value = "/create", method = RequestMethod.POST) public Pets createPet(@RequestBody Pets pets) { pets.set_id(ObjectId.get()); return petsService.save(pets); } |
This mapping expects a request body (in JSON format) with each of the fields that a Pets object contains (
name
, species
, and breed
), and assigns it a new ObjectId. This object is then inserted into the pets
collection, and the new Pets object is returned.
DELETE
@RequestMapping(value = "{id}", method = RequestMethod.DELETE) public void deletePet(@PathVariable ObjectId id) { petsService.deletePet(id); } |
Completed Controller
package com.esb.demo.SpringBootMongoDB.controller; import java.util.List; import org.bson.types.ObjectId; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.web.bind.annotation.PathVariable; import org.springframework.web.bind.annotation.RequestBody; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RestController; import com.esb.demo.SpringBootMongoDB.models.Pets; import com.esb.demo.SpringBootMongoDB.service.PetsService; @RestController @RequestMapping(value = "/pets") public class PetsController { @Autowired private PetsService petsService; @RequestMapping(value = "/all", method = RequestMethod.GET) public List<Pets> getAllPets() { return petsService.getAllPets(); } @RequestMapping(value = "{id}", method = RequestMethod.GET) public Pets getPetById(@PathVariable("id") ObjectId id) { return petsService.getPetbyId(id); } @RequestMapping(value = "{id}", method = RequestMethod.PUT) public void modifyPetById(@PathVariable("id") ObjectId id, @RequestBody Pets pets) { pets.set_id(id); petsService.updatePetById(pets); } @RequestMapping(value = "/create", method = RequestMethod.POST) public Pets createPet(@RequestBody Pets pets) { pets.set_id(ObjectId.get()); return petsService.save(pets); } @RequestMapping(value = "{id}", method = RequestMethod.DELETE) public void deletePet(@PathVariable ObjectId id) { petsService.deletePet(id); } } |
Step 10 : Creating Service
Now We will create a Service class by adding a file called
PetsService.java
to the src/main/java/[package name]/
folder.package com.esb.demo.SpringBootMongoDB.service; import java.util.List; import org.bson.types.ObjectId; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.stereotype.Service; import com.esb.demo.SpringBootMongoDB.models.Pets; import com.esb.demo.SpringBootMongoDB.repositories.PetsRepository; @Service public class PetsService { @Autowired private PetsRepository repository; public List<Pets> getAllPets() { return repository.findAll(); } public Pets getPetbyId(ObjectId id) { return repository.findBy_id(id); } public void updatePetById(Pets pets) { repository.save(pets); } public Pets save(Pets pets) { return repository.save(pets); } public void deletePet(ObjectId id) { repository.delete(repository.findBy_id(id)); } } |
Step 10 : Testing Your API
Now that the controller has all of our endpoints, we can begin testing our API! From the command line, in the project root, run the
mvn spring-boot:run
command to compile the code and start the Spring server with the default port 8080.
Once the server starts, you are free to test your API however you choose.
With body :
and header : 'Content-Type: application/json'
{"name" : "Liam", "species" : "cat", "breed" : "tabby"}
and header : 'Content-Type: application/json'
Returns:
{ "_id": "5aecef5b6d55754834124df3", "name": "Liam", "species": "cat", "breed": "tabby" } |
With body :
and header :
{"name" : "Liam", "species" : "cat", "breed" : "siamese"}
and header :
Content-Type : application/json
empty response |
---|
Returns:
{ "_id": "5aecef5b6d55754834124df3", "name": "Liam", "species": "cat", "breed": "siamese" } |
Returns:
|
---|
Returns:
[ { "_id": "5aeccb0a18365ba07414356c", "name": "Spot", "species": "dog", "breed": "pitbull" }, { "_id": "5aeccb0a18365ba07414356d", "name": "Daisy", "species": "cat", "breed": "calico" }, { "_id": "5aeccb0a18365ba07414356e", "name": "Bella", "species": "dog", "breed": "australian shepard" } ] |
No comments:
Post a Comment