Quantcast
Channel: ASP.Net Web API – Bit of Technology
Viewing all articles
Browse latest Browse all 37

Building ASP.Net Web API RESTful Service – Part 6

$
0
0

This is the sixth part of Building ASP.Net Web API RESTful Service Series. The topics we’ll cover are:

Implement Resources Association

In this post we’ll be covering the relationship between resources which is called “Resources Association”, for example there is a relation between each “Course” and “Students” i.e. each course has multiple students enrolled in it. So we can build an absolute URI in the form:”api/courses/courseid/students/{userName}”, so if we want to list all students enrolled in course id 5 our GET request will be as: “api/courses/5/students/”. If we want to enroll student his username is “TaiseerJoudeh” in course id 5 we’ll issue POST request to the URI: ”api/courses/5/students/TaiseerJoudeh” and so on.

To implement this we need add new route in “WebApiConfig” class named “Enrollments” as the code below:


     config.Routes.MapHttpRoute(
         name: "Enrollments",
         routeTemplate: "api/courses/{courseId}/students/{userName}",
         defaults: new { controller = "Enrollments", userName = RouteParameter.Optional }
     );

Notice how is “courseId” parameter is not optional and “userName” parameter is optional.

Now we’ve to add new controller named “EnrollmentsController”, we’ll support two HTTP verbs, GET to list all students in specific class, and POST to enroll student in specific calls, you’ll notice that we’ve implemented pagination for GET method, we’ll cover this topic in the next post. The controller code listed as the below:


    public class EnrollmentsController : BaseApiController
    {
        public EnrollmentsController(ILearningRepository repo)
            : base(repo)
        {
        }

        public IEnumerable<StudentBaseModel> Get(int courseId, int page = 0, int pageSize = 10)
        {
            IQueryable<Student> query;

            query = TheRepository.GetEnrolledStudentsInCourse(courseId).OrderBy(s => s.LastName);

            var totalCount = query.Count();

            System.Web.HttpContext.Current.Response.Headers.Add("X-InlineCount", totalCount.ToString());

            var results = query
                        .Skip(pageSize * page)
                        .Take(pageSize)
                        .ToList()
                        .Select(s => TheModelFactory.CreateSummary(s));

            return results;

        }

        public HttpResponseMessage Post(int courseId, [FromUri]string userName, [FromBody]Enrollment enrollment)
        {
            try
            {

                if (!TheRepository.CourseExists(courseId)) return Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Could not find Course");

                var student = TheRepository.GetStudent(userName);
                if (student == null) return Request.CreateErrorResponse(HttpStatusCode.BadRequest, "Could not find Student");

                var result = TheRepository.EnrollStudentInCourse(student.Id, courseId, enrollment);

                if (result == 1)
                {
                    return Request.CreateResponse(HttpStatusCode.Created);
                }
                else if (result == 2)
                {
                    return Request.CreateResponse(HttpStatusCode.NotModified, "Student already enrolled in this course");
                }

                return Request.CreateResponse(HttpStatusCode.BadRequest);

            }
            catch (Exception ex)
            {
                return Request.CreateErrorResponse(HttpStatusCode.BadRequest, ex);
            }
        }
    }

In the POST method notice how we’re using FromUri and FromBody attribute to indicate from where we’re getting the values of the request, we’ll get the “userName” from the URI and the “enrollment” object from Request Body. The “enrollment” object will contain the enrollment data only, we could send the “CourseID” and “StudentID” as well, but it makes more sense to get both values from the URI.

To test the POST request we’ll use fiddler to issue a POST request, we want to enroll student “TaiseerJoudeh” in course with ID=5, the request will be as the image below:

FiddlerPostRequest-Enrollments

As we’ve learned before, we will return HTTP status code as a result for this POST operation, if the request is successful we will return 201 (Resource Created), if the student already enrolled in this class we’ll return status code 304 (Not modified).

In the next post we’ll talk about pagination for large results, using manual pagination, and how we return pagination meta-data.

Source code is available on GitHub.



Viewing all articles
Browse latest Browse all 37

Trending Articles