JavaScript is a powerful programming language and I will use it to create a powerful API feature. I already have my Web API built in ASP.NET Core, and it has various function like providing flight reservations data to clients in JSON, searching the reservations with their ids, updating and deleting reservations and so on.
This tutorial is a part of the ASP.NET Core API series which contains 4 tutorials to master this area:
I will now use only Pure JavaScript to call these methods of this Web API to perform tasks like Creating, Reading, Updating and Deleting reservations. In the end I will show you how to upload files with API using JavaScript, so make sure you go through the entire tutorial and download the source code from the link given at the end.
Page Contents
The ASP.NET Core Web API has a method that returns all the flight reservations in JSON. It’s signature is shown below:
[HttpGet]
public IEnumerable<Reservation> Get()
{
//… return all the reservations
}
To call this method of the Web API with JavaScript, first create an HTML page and call it AllReservation.html or anything you want. In this page all the reservations will be shown in an HTML table as given below.
<table id="apiTable">
<thead>
<tr>
<th>ID</th>
<th>Name</th>
<th>Start Location</th>
<th>End Location</th>
</tr>
</thead>
<tbody>
</tbody>
</table>
I have kept the tbody element as empty as I will show all the reservations inside it once I receive all the reservations in JSON from the API.
Next, add the following JavaScript code to this page inside the script tag:
<script type="text/javascript">
ShowAllReservation();
function ShowAllReservation() {
var xhttp = new XMLHttpRequest();
xhttp.open("GET", "https://localhost:44324/api/Reservation", true);
xhttp.send();
xhttp.onreadystatechange = function () {
var tbody = document.getElementById("apiTable").querySelector("tbody");
tbody.innerHTML = "";
if (this.readyState == 4 && this.status == 200) {
JSON.parse(this.responseText).forEach(function (data, index) {
tbody.innerHTML += "<tr><td>" + data.id + "</td>" + "<td>" + data.name + "</td>" + "<td>" + data.startLocation + "</td>" + "<td>" + data.endLocation + "</td></tr>";
});
}
};
}
</script>
When the page the JS function named ShowAllReservation() is called. In this function I am making an AJAX call to my API. So first I create an XMLHttpRequest object like this:
var xhttp = new XMLHttpRequest();
Then I make an HTTP GET type request to the URL of my API’s method that has the task to return all these reservations. In my case this URL is:
https://localhost:44324/api/Reservation
The API returns the reservations in JSON as shown below:
[
{
"id": 1,
"name": "Ankit",
"startLocation": "New York",
"endLocation": "Beijing"
},
{
"id": 2,
"name": "Bobby",
"startLocation": "New Jersey",
"endLocation": "Boston"
},
{
"id": 3,
"name": "Jacky",
"startLocation": "London",
"endLocation": "Paris"
}
]
Finally, the onreadystatechange handler is called as soon as the JSON is received. In this handler I am showing the reservations inside the html table.
See the below image which shows all the reservations (returned by the API) inside the HTML table:
My ASP.NET Core API has a method that allows for searching a reservation by it’s Id. It’s definition is given below:
[HttpGet("{id}")]
public ActionResult<Reservation> Get(int id)
{
if (id == 0)
return BadRequest("Value must be passed in the request body.");
return Ok(repository[id]);
}
To call this method from JavaScript I will create a new page and call it GetReservation.html. This page has 3 things:
The code for this page is shown below:
<input type="text" class="form-control" id="Id" />
<button id="GetButton" onclick="GetReservation()">Get Reservation</button>
<table id="apiTable">
<thead>
<tr>
<th>ID</th>
<th>Name</th>
<th>Start Location</th>
<th>End Location</th>
</tr>
</thead>
<tbody>
</tbody>
</table>
Next, add the JavaScript code which does the API calling part. The below code is the one that you need to add to this page:
<script type="text/javascript">
function GetReservation() {
var xhttp = new XMLHttpRequest();
xhttp.open("GET", "https://localhost:44324/api/Reservation/" + document.getElementById("Id").value, true);
xhttp.send();
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
var response = JSON.parse(this.responseText);
var tbody = document.getElementById("apiTable").querySelector("tbody");
tbody.innerHTML = "<tr><td>" + response.id + "</td><td>" + response.name + "</td><td>" + response.startLocation + "</td><td>" + response.endLocation + "</td></tr>";
}
};
}
</script>
This JavaScript code is quite similar to the one which I made earlier. All you have to see is that the API’s method URL is added with the reservation ‘id’ and then HTTP GET type of AJAX request is made to the API.
var xhttp = new XMLHttpRequest();
xhttp.open("GET", "https://localhost:44324/api/Reservation/" + document.getElementById("Id").value, true);
At the end, the API response, which is the searched reservation data in JSON, is shown inside the HTML table by appending it to the tbody element:
tbody.innerHTML = "<tr><td>" + response.id + "</td><td>" + response.name + "</td><td>" + response.startLocation + "</td><td>" + response.endLocation + "</td></tr>";
I have created a small video which shows the working of this search feature:
Did you know that we can upload files to remote servers using API to? Here I will create this feature in JavaScript with very less code.
My API has a method that accepts files sent by clients from a submitted Form tag. It has a IFormFile type of parameter to accept these files. You can see it’s code is shown below:
[HttpPost("UploadFile")]
public async Task<string> UploadFile([FromForm] IFormFile file)
{
string path = Path.Combine(hostingEnvironment.WebRootPath, "Images/" + file.FileName);
using (var stream = new FileStream(path, FileMode.Create))
{
await file.CopyToAsync(stream);
}
return "https://localhost:44324/Images/" + file.FileName;
}
This means if I make a call to this method with my JavaScript code and attach the file to the Form data then I will be making the file upload to work.
So create a new page and call it AddFile.html. Add 2 html tags to this page:
<input type="file" id="File" />
<button id="AddButton" onclick="UploadFile()" type="submit">Add</button>
Next, add the JavaScript code which is given below:
<script type="text/javascript">
function UploadFile() {
var xhttp = new XMLHttpRequest();
xhttp.open("POST", "https://localhost:44324/api/Reservation/UploadFile", true);
data = new FormData();
data.append("file", document.getElementById("File").files[0]);
xhttp.send(data);
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
alert(this.response);
}
};
}
</script>
I am making an HTTP Post type of AJAX request to the API method. It’s URL is:
https://localhost:44324/api/Reservation/UploadFile
Then I am adding the file to the FormData:
data = new FormData();
data.append("file", document.getElementById("File").files[0]);
And then finally making the call using send() method and adding the ‘FormData’ to it:
xhttp.send(data);
Check this video for understanding the working of this feature:
Note: In this video I am uploading an image file and also showing the image in an ‘img’ tag once it gets uploaded. You can use it to upload any type of files.
Adding a reservation with the help of API is also very simple. The API has a method that adds a new reservation. It accepts reservation data from the body of the HTTP request which is made to the API.
The code of this method is given below:
[HttpPost]
public IActionResult Post([FromBody] Reservation res)
{
//… add reservation to the database
}
First create a new html page called AddReservation.html. Add to it the following code:
<input type="text" id="Name" />
<input type="text" id="StartLocation" />
<input type="text" id="EndLocation" />
<button type="submit" onclick="AddReservation()">Add</button>
<table id="apiTable">
<thead>
<tr>
<th>ID</th>
<th>Name</th>
<th>Start Location</th>
<th>End Location</th>
</tr>
</thead>
<tbody>
</tbody>
</table>
There are 3 text boxes are for accepting the Name, Start Location and End Location of a new reservation. The button has a click event so that when it is clicked the API call is made through JavaScript.
The html table work is to show the newly added reservation.
Next, to this page add the following JavaScript code which makes the call to the API:
<script type="text/javascript">
function AddReservation() {
var xhttp = new XMLHttpRequest();
xhttp.open("POST", "https://localhost:44324/api/Reservation", true);
xhttp.setRequestHeader("Content-type", "application/json");
xhttp.setRequestHeader("Key", "[email protected]");
var obj = { Id: 0, Name: document.getElementById("Name").value, StartLocation: document.getElementById("StartLocation").value, EndLocation: document.getElementById("EndLocation").value };
xhttp.send(JSON.stringify(obj));
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
var response = JSON.parse(this.responseText);
var tbody = document.getElementById("apiTable").querySelector("tbody");
tbody.innerHTML = "<tr><td>" + response.id + "</td><td>" + response.name + "</td><td>" + response.startLocation + "</td><td>" + response.endLocation + "</td></tr>";
}
};
}
</script>
On API call is made to the URL – https://localhost:44324/api/Reservation.
My ASP.NET Core API has a security feature that needs credentials for adding a new reservation, therefore notice that I am adding these credentials to the header of the XMLHttpRequest object as shown below:
xhttp.setRequestHeader("Content-type", "application/json");
xhttp.setRequestHeader("Key", "[email protected]");
Next, the new reservation data is grabbed from the text boxes and added to the XMLHttpRequest object as shown below:
var obj = { Id: 0, Name: document.getElementById("Name").value, StartLocation: document.getElementById("StartLocation").value, EndLocation: document.getElementById("EndLocation").value };
xhttp.send(JSON.stringify(obj));
Once the reservation data is added and I get the response by the API, I show the new reservation inside an HTML table given on the page.
I have created a small video which shows the working of this feature. See below:
The HTTP PUT type of API method does the updating task of the reservations. It’s definition is given below:
[HttpPut]
public Reservation Put([FromForm] Reservation res)
{
//…
}
Start by creating a new HTML page called UpdateReservation.html. Then add the following HTML to this page:
<input type="text" id="Id" readonly />
<input type="text" id="Name" />
<input type="text" id="StartLocation" />
<input type="text" id="EndLocation" />
<button type="submit" onclick="UpdateReservation()">Update</button>
<table id="apiTable">
<thead>
<tr>
<th>ID</th>
<th>Name</th>
<th>Start Location</th>
<th>End Location</th>
</tr>
</thead>
<tbody>
</tbody>
</table>
There are some input text boxes to provide the new reservation values. This means the user will update the reservation by entering the new values on these input controls, and then clicking the button to update them.
The updated reservation is shown on the html table.
Now add the following JavaScript code to your page:
<script type="text/javascript">
GetReservation();
function UpdateReservation() {
var xhttp = new XMLHttpRequest();
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
var response = JSON.parse(this.responseText);
var tbody = document.getElementById("apiTable").querySelector("tbody");
tbody.innerHTML = "<tr><td>" + response.id + "</td><td>" + response.name + "</td><td>" + response.startLocation + "</td><td>" + response.endLocation + "</td></tr>";
}
};
xhttp.open("PUT", "https://localhost:44324/api/Reservation", true);
data = new FormData();
data.append("Id", document.getElementById("Id").value);
data.append("Name", document.getElementById("Name").value);
data.append("StartLocation", document.getElementById("StartLocation").value);
data.append("EndLocation", document.getElementById("EndLocation").value);
xhttp.send(data);
}
function GetReservation() {
let params = (new URL(document.location)).searchParams;
let id = params.get("id");
var xhttp = new XMLHttpRequest();
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
var response = JSON.parse(this.responseText);
document.getElementById("Id").value = response.id;
document.getElementById("Name").value = response.name;
document.getElementById("StartLocation").value = response.startLocation;
document.getElementById("EndLocation").value = response.endLocation;
}
};
xhttp.open("GET", "https://localhost:44324/api/Reservation/" + id, true);
xhttp.send();
}
</script>
Once the page loads the GetReservation() function is called whose work is to fetch the reservation data from the API. It does this by sending the ‘id’ of the reservation to the API.
Note that reservation id is send to this page in the URL itself i.e. in the query string. To get this reservation ‘id’ the following 2 lines of codes are used:
let params = (new URL(document.location)).searchParams;
let id = params.get("id");
On receiving the response the reservation is shown in the html table given on the page.
The UpdateReservation() function is called on the click of the button. Inside this function I make the API call to the update reservation method whose URL is https://localhost:44324/api/Reservation.
I have to add the updated reservation values to FormFata which is done as:
data = new FormData();
data.append("Id", document.getElementById("Id").value);
data.append("Name", document.getElementById("Name").value);
data.append("StartLocation", document.getElementById("StartLocation").value);
data.append("EndLocation", document.getElementById("EndLocation").value);
And then I add the ‘FormData’ object to the XMLHttpRequest as given below:
xhttp.send(data);
I have created a small video that shows it’s working:
Note: You can link this page from the AllReservation.html page by creating an update reservation td element in the table. The changes which you need to do are:
1. Add update ‘th’ on the ‘thead’ area:
<table id="apiTable">
<thead>
<tr>
//…
<th>Update</th>
</tr>
</thead>
<tbody></tbody>
</table>
2. Add a new ‘td’ element to the ‘tbody’ element and create a link that contains the ‘id’ of the reservation in query string.
tbody.innerHTML += "<tr><td>" + data.id + "</td>" + "<td>" + data.name + "</td>" + "<td>" + data.startLocation + "</td>" + "<td>" + data.endLocation + "</td>" + "<td><a href=\"UpdateReservation.html?id=" + data.id + "\">Update</a></td></tr>";
Now let me do the updation of reservations by calling the HTTP PATCH based API method. This method of the API looks like:
[HttpPatch("{id}")]
public StatusCodeResult Patch(int id, [FromBody]JsonPatchDocument<Reservation> patch)
{
//…
}
It has 2 parameters – ‘id’ of the reservation that needs to be updated and JsonPatchDocument object that will contain the new reservation values.
So create a new html page called UpdateReservationPatch.html and add 3 text boxes for taking new values for the reservation, and a button.
<input type="text" id="Id" readonly />
<input type="text" id="Name" />
<input type="text" id="StartLocation" />
<input type="text" id="EndLocation" />
<button type="submit" onclick="UpdateReservation()">Update</button>
Next, add the following JavaScript code which will update the reservation by calling the HTTP PATCH based API method.
<script type="text/javascript">
GetReservation();
function GetReservation() {
let params = (new URL(document.location)).searchParams;
let id = params.get("id");
var xhttp = new XMLHttpRequest();
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
var response = JSON.parse(this.responseText);
document.getElementById("Id").value = response.id;
document.getElementById("Name").value = response.name;
document.getElementById("StartLocation").value = response.startLocation;
document.getElementById("EndLocation").value = response.endLocation;
}
};
xhttp.open("GET", "https://localhost:44324/api/Reservation/" + id, true);
xhttp.send();
}
function UpdateReservation() {
var xhttp = new XMLHttpRequest();
xhttp.onreadystatechange = function () {
if (this.readyState == 4 && this.status == 200) {
window.location.href = "AllReservation.html";
}
};
let params = (new URL(document.location)).searchParams;
let id = params.get("id");
var data = JSON.stringify([
{
op: "replace",
path: "Name",
value: document.getElementById("Name").value
},
{
op: "replace",
path: "StartLocation",
value: document.getElementById("StartLocation").value
},
{
op: "replace",
path: "EndLocation",
value: document.getElementById("EndLocation").value
}
]);
xhttp.open("PATCH", "https://localhost:44324/api/Reservation/" + id, true);
xhttp.setRequestHeader("Content-type", "application/json");
xhttp.send(data);
}
</script>
On the button click the UpdateReservation() JS function is called. In this function I grab the ‘id’ of the reservation from the query string by using the below code:
let params = (new URL(document.location)).searchParams;
let id = params.get("id");
I then convert the new reservation values entered in the 3 text boxes to JSON by using the JSON.stringify method of JS as shown below:
var data = JSON.stringify([
{
op: "replace",
path: "Name",
value: document.getElementById("Name").value
},
{
op: "replace",
path: "StartLocation",
value: document.getElementById("StartLocation").value
},
{
op: "replace",
path: "EndLocation",
value: document.getElementById("EndLocation").value
}
]);
And then finally making the AJAX calls as given below:
xhttp.open("PATCH", "https://localhost:44324/api/Reservation/" + id, true);
xhttp.setRequestHeader("Content-type", "application/json");
xhttp.send(data);
Then check the functionality which is shown by the below video:
The API has a method that deletes a reservation. The method accepts the reservation id in it’s parameter:
[HttpDelete("{id}")]
public void Delete(int id){
//… delete the reservation
}
The delete record feature will be added to the AllReservation.html page which I have already build before. So perform the following things on the html table control given on the ‘AllReservation.html’ page:
1. Add delete ‘th’ on the ‘thead’ area:
<table id="apiTable">
<thead>
<tr>
//…
<th>Delete</th>
</tr>
</thead>
<tbody></tbody>
</table>
2. Add a new ‘td’ element to the ‘tbody’ element that contains a ‘cross’ image. When this image is clicked the delete operation is preformed.
tbody.innerHTML += "<tr><td>" + data.id + "</td>" + "<td>" + data.name + "</td>" + "<td>" + data.startLocation + "</td>" + "<td>" + data.endLocation + "</td>" + "<td><a href=\"UpdateReservation.html?id=" + data.id + "\"><img src=\"icon/edit.png\" /></a></td>" + "<td><img class=\"delete\" src=\"icon/close.png\" /></td></tr>";
Next, add the following JS function called ‘CreateClickEvent()’ in your page:
function CreateClickEvent() {
var dimg = document.getElementsByClassName("delete");
for (let i = 0; i < dimg.length; i++) {
dimg[i].addEventListener("click", function (e) {
var xhttp = new XMLHttpRequest();
xhttp.onreadystatechange = function () {
ShowAllReservation();
};
var resId = e.target.closest("tr").childNodes[0].innerHTML;
xhttp.open("DELETE", "https://localhost:44324/api/Reservation/" + resId, true);
xhttp.send();
})
}
}
Also make sure you update the ShowAllReservation() function so that you call the CreateClickEvent() function from inside the xhttp.onreadystatechange handler. I have shown this below:
function ShowAllReservation() {
//…
xhttp.onreadystatechange = function () {
//…
if (this.readyState == 4 && this.status == 200) {
//…
CreateClickEvent();
}
};
}
Once the reservations are fetched from the API, I am creating click event on all the delete images i.e. the cross image. So I am calling the CreateClickEvent() function from inside the http.onreadystatechange handler.
I am grabbing all the click images by their CSS class as:
var dimg = document.getElementsByClassName("delete");
I am then looping through each of them and adding a click event to them by using the addEventListener function of JS:
for (let i = 0; i < dimg.length; i++) {
dimg[i].addEventListener("click", function (e) {
//…
})
}
Before making the API call to delete a reservation I should get it’s id from the first td of the row which is done by using the below like:
var resId = e.target.closest("tr").childNodes[0].innerHTML;
And finally making the API call by passing the reservation id as shown below:
xhttp.open("DELETE", "https://localhost:44324/api/Reservation/" + resId, true);
Test this feature by clicking the cross icon against any reservation object and the API will delete it. Check the below video which shows the delete process:
The link to download the full source code of this tutorial is given below:
This API tutorial gives you all the working knowledge of calling any API with pure JavaScript. Download the source codes and use it freely in your website. Do check my other tutorials to.
Share this article -