Showing posts with label Web Api. Show all posts
Showing posts with label Web Api. Show all posts

Wednesday, 20 November 2024

Refresh Token : JWT Token Authentication WEBAPI

 To implement JWT (JSON Web Token) refresh token logic in a Web API, the general idea is to issue two tokens when a user successfully logs in:

  1. Access Token (short-lived): This token is used for authenticating requests and is typically valid for a short duration (e.g., 15 minutes).
  2. Refresh Token (long-lived): This token is used to get a new access token when the old one expires. It typically has a longer expiry time (e.g., 7 days or more).

Steps to Implement JWT Refresh Token in a Web API

1. Login Endpoint (Generate Access and Refresh Tokens)

When the user successfully logs in, generate both an access token and a refresh token. The access token will be used for authentication, and the refresh token will be stored securely (typically in an HttpOnly cookie or in the database).

public class AuthController : ControllerBase
{
    private readonly IConfiguration _configuration;

    public AuthController(IConfiguration configuration)
    {
        _configuration = configuration;
    }

    [HttpPost("login")]
    public IActionResult Login([FromBody] LoginRequest request)
    {
        // Validate user credentials
        var user = AuthenticateUser(request.Username, request.Password);
        if (user == null) return Unauthorized();

        // Generate JWT Access Token
        var accessToken = GenerateAccessToken(user);

        // Generate Refresh Token
        var refreshToken = GenerateRefreshToken();

        // Save the refresh token in the database or cache associated with the user

        return Ok(new
        {
            AccessToken = accessToken,
            RefreshToken = refreshToken
        });
    }

    private string GenerateAccessToken(User user)
    {
        var claims = new List<Claim>
        {
            new Claim(ClaimTypes.Name, user.Username),
            new Claim(ClaimTypes.NameIdentifier, user.UserId.ToString())
            // Add other claims as necessary
        };

        var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(
_configuration["Jwt:SecretKey"]));
        var creds = new SigningCredentials(key, SecurityAlgorithms.HmacSha256);

        var token = new JwtSecurityToken(
            issuer: _configuration["Jwt:Issuer"],
            audience: _configuration["Jwt:Audience"],
            claims: claims,
            expires: DateTime.Now.AddMinutes(15), // short-lived access token
            signingCredentials: creds
        );

        return new JwtSecurityTokenHandler().WriteToken(token);
    }

    private string GenerateRefreshToken()
    {
        var randomNumber = new byte[32];
        using (var rng = RandomNumberGenerator.Create())
        {
            rng.GetBytes(randomNumber);
        }

        return Convert.ToBase64String(randomNumber);
    }
}

2. Refresh Token Endpoint

When the access token expires, the client sends the refresh token to this endpoint to get a new access token. The refresh token is validated, and if valid, a new access token is issued.

[HttpPost("refresh-token")]
public IActionResult RefreshToken([FromBody] RefreshTokenRequest request)
{
    // Validate the refresh token
    var user = ValidateRefreshToken(request.RefreshToken);
    if (user == null) return Unauthorized();

    // Generate new access token
    var accessToken = GenerateAccessToken(user);

    // Optionally, generate a new refresh token and save it (if you are rotating
// refresh tokens)
    var refreshToken = GenerateRefreshToken();
    SaveRefreshToken(user, refreshToken);

    return Ok(new
    {
        AccessToken = accessToken,
        RefreshToken = refreshToken
    });
}

private User ValidateRefreshToken(string refreshToken)
{
    // Validate the refresh token. Check if it's valid and matches what's stored
// in the database.
    // This could involve checking a database, cache, or other storage for a
// matching refresh token.
    // Implement this logic based on your storage method return GetUserByRefreshToken(refreshToken);
}

3. Refresh Token Storage

Refresh tokens should be securely stored. Options include:

  • HttpOnly Cookies: Secure and less vulnerable to XSS attacks.
  • Database: Store refresh tokens in a table or cache, mapping them to user accounts and ensuring the refresh token is revoked after use.

If you're storing the refresh token in a cookie, set the HttpOnly flag and Secure flag to ensure the token is sent only over HTTPS and cannot be accessed via JavaScript.

Example for setting refresh token in HttpOnly cookie:

Response.Cookies.Append("refresh_token", refreshToken, new CookieOptions
    {
        HttpOnly = true,
        Secure = true,
        SameSite = SameSiteMode.Strict,
        Expires = DateTime.Now.AddDays(7) // Set expiry to match your policy
    });
   

4. Token Expiry and Invalidating Refresh Tokens

Make sure that:

  • Access tokens expire quickly (e.g., in 15 minutes).
  • Refresh tokens can either have a long expiration time (e.g., 7 days) or a single-use (rotating refresh tokens) mechanism to increase security.
  • When a refresh token is used, it’s either revoked or replaced with a new refresh token to avoid token reuse.

5. Middleware for Token Validation

The access token is included in request headers (typically in the Authorization header) as a bearer token. This token is validated with each request to ensure it is still valid.

public class JwtMiddleware
{
    private readonly RequestDelegate _next;
    private readonly IConfiguration _configuration;

    public JwtMiddleware(RequestDelegate next, IConfiguration configuration)
    {
        _next = next;
        _configuration = configuration;
    }

    public async Task InvokeAsync(HttpContext context)
    {
        var token = context.Request.Headers["Authorization"].FirstOrDefault()?
.Split(" ").Last();
        if (token != null)
        {
            AttachUserToContext(context, token);
        }

        await _next(context);
    }

    private void AttachUserToContext(HttpContext context, string token)
    {
        try
        {
            var claimsPrincipal = ValidateToken(token);
            context.User = claimsPrincipal;
        }
        catch
        {
            context.User = null;
        }
    }

    private ClaimsPrincipal ValidateToken(string token)
    {
        var key = new SymmetricSecurityKey(Encoding.UTF8.GetBytes(
_configuration["Jwt:SecretKey"]));
        var tokenHandler = new JwtSecurityTokenHandler();

        var validationParameters = new TokenValidationParameters
        {
            ValidateIssuer = true,
            ValidateAudience = true,
            ValidateLifetime = true,
            IssuerSigningKey = key,
            ClockSkew = TimeSpan.Zero,
            ValidIssuer = _configuration["Jwt:Issuer"],
            ValidAudience = _configuration["Jwt:Audience"]
        };

        return tokenHandler.ValidateToken(token, validationParameters, out _);
    }
}

Key Considerations:

  • Secure Storage: Always ensure that refresh tokens are stored securely, either in a database or HttpOnly cookies.
  • Token Rotation: Optionally, rotate refresh tokens to increase security (i.e., issue a new refresh token each time a new access token is issued).
  • Revocation: Implement a strategy for revoking refresh tokens if necessary (e.g., after logout or password change).

This setup should give you a basic implementation of JWT with access token and refresh token in your Web API.


Continue Reading →

Saturday, 5 October 2024

RESTful API

 RESTful API, or Representational State Transfer API, is a set of rules and conventions for building and interacting with web services.

Key Principles of RESTful APIs:

Statelessness: Each request from a client must contain all the information the server needs to fulfill that request. The server does not store any client context between requests.

HTTP Methods: RESTful APIs use standard HTTP methods to perform operations on resources: GET, PUT, POST, DELETE

Stateless Operations: Each operation on the resource should be independent of others, ensuring scalability and reliability.

Client-Server Separation: The client and server operate independently

Benefits:

Scalability: Stateless interactions can scale more easily.

Flexibility: Clients and servers can evolve independently.

Caching: HTTP protocols allow responses to be cached for performance.

Overall, RESTful APIs are widely used for their simplicity and effectiveness in enabling communication between web services and applications.

RESTful APIs can be secured using HTTPS encryption, authentication mechanisms, and authorization mechanisms.

Continue Reading →

Saturday, 30 September 2023

Web API Versioning

What Is API Versioning?

API versioning is the process of iterating different versions of your API.

Why Is API Versioning Required?

While working on an existing application or creating a new one, we may create multiple APIs that may be consumed by many clients. When the business has started to grow and expand, new requirements arise. Due to this, we may need to provide more functionality in the existing APIs. However, existing Web API can be consumed by many clients so how to implement the new feature without impacting the existing consumers? We can solve this problem by versioning our API.

There are some common ways to version a REST API.

1. Versioning through URI

The most commonly used versioning is in which we can add a version to the API base URL.

Example:

http://api-demo.example.com/api/1/employee

This approach is easy to implement and understand, as clients can simply request the desired version of the API by specifying the corresponding URL. Here are the steps to implement URL-based versioning in ASP.NET Core:

Install the Microsoft.AspNetCore.Mvc.Versioning NuGet package in your ASP.NET Core project. You can do this using the Package Manager Console or the NuGet Package Manager in Visual Studio.

In the ConfigureServices method of your Startup.cs file, configure the API versioning options by adding the following code:

  services.AddApiVersioning(options =>
    {
        options.DefaultApiVersion = new ApiVersion(1, 0);
        options.AssumeDefaultVersionWhenUnspecified = true;
        options.ReportApiVersions = true;
        options.ApiVersionReader = new UrlSegmentApiVersionReader();
    });

This code configures the default API version to be 1.0, assumes the default version when not specified in the URL, reports the API versions in the response headers, and uses the URL segment as the versioning source.

In your controller, add the ApiVersion attribute to specify the supported API versions for each action method. For example:

  [ApiController]
  [Route("api/v{version:apiVersion}/[controller]")]
  [ApiVersion("1.0")]
  public class MyController : ControllerBase
  {
      [HttpGet]
      public IActionResult Get()
      {
          return Ok("Version 1.0");
      }
     
      [HttpGet, MapToApiVersion("2.0")]
      public IActionResult GetV2()
      {
          return Ok("Version 2.0");
      }
  }

This code specifies that the controller supports version 1.0 of the API, and that the GetV2 action method supports version 2.0. The [MapToApiVersion] attribute maps the action method to version 2.0.

Test the API by sending requests to the corresponding URLs. For example:

http://localhost:5000/api/v1.0/my -> returns "Version 1.0"

http://localhost:5000/api/v2.0/my -> returns "Version 2.0"

By using URL-based versioning in ASP.NET Core, you can easily manage different versions of your API and provide backward compatibility to existing clients.

2. Query String

Another option for versioning a REST API is to include the version number as a query parameter.

This is a straightforward way to version an API from an implementation point of view.

Example:

https://api-demo.example.com/api/employee/?api-version=2

Follow the same steps and code as mentioned above. change code for AddApiVersioning method. in this only  ApiVersionReader  property is changed.

  services.AddApiVersioning(options =>
    {
        options.DefaultApiVersion = new ApiVersion(1, 0);
        options.AssumeDefaultVersionWhenUnspecified = true;
        options.ReportApiVersions = true;
        options.ApiVersionReader = new QueryStringApiVersionReader("version");
    });

Test the API by sending requests with the "version" query parameter. For example:

http://localhost:5000/api/my?version=1.0 -> returns "Version 1.0"

http://localhost:5000/api/my?version=2.0 -> returns "Version 2.0"

By using query string-based versioning in ASP.NET Core, you can provide a flexible and convenient way for clients to specify the desired version of your API.

3. Custom headers

Define a new header that contains the version number in the request as part of the request header itself.

Example:

GET https://api-demo.example.com/api/employee
Accept-Version: 3

Follow the same steps and code as mentioned above. change code for AddApiVersioning method. in this only  ApiVersionReader  property is changed.

  services.AddApiVersioning(options =>
    {
        options.DefaultApiVersion = new ApiVersion(1, 0);
        options.AssumeDefaultVersionWhenUnspecified = true;
        options.ReportApiVersions = true;
        options.ApiVersionReader = new HeaderApiVersionReader("X-Version");
    });

This code configures the default API version to be 1.0, assumes the default version when not specified in the header, reports the API versions in the response headers, and uses the "X-Version" header as the versioning source.

Test the API by sending requests with the "X-Version" header. For example:

http://localhost:5000/api/my

X-Version: 1.0 -> returns "Version 1.0"

X-Version: 2.0 -> returns "Version 2.0"

By using header-based versioning in ASP.NET Core, you can provide a flexible and non-intrusive way for clients to specify the desired version of your API.

Learn More: https://codelikeadev.com/https://www.c-sharpcorner.com/
                        https://www.dotnettricks.com/https://blog.devart.com/


Continue Reading →

Monday, 12 October 2020

HTTP Methods

REST APIs enable you to develop any kind of web application having all possible CRUD (create, retrieve, update, delete) operations. REST guidelines suggest using a specific HTTP method on a particular type of call made to the server (though technically it is possible to violate this guideline, yet it is highly discouraged).

Use below-given information to find a suitable HTTP method for the action performed by API.

  1. HTTP GET
  2. HTTP POST
  3. HTTP PUT
  4. HTTP DELETE
  5. HTTP PATCH

GET: GET method is used to retrieve data from a server at the specified resource. For example, say you have an API with a /users endpoint. Making a GET request to that endpoint should return a list of all available users.

For any given HTTP GET API, if the resource is found on the server, then it must return HTTP response code 200 (OK) – along with the response body, which is usually either XML or JSON content (due to their platform-independent nature).

Since a GET request is only requesting data and not modifying any resources, it's considered a safe and idempotent method.

Idempotence means that applying an operation once or applying it multiple times has the same effect. Examples: Multiplication by zero. No matter how many times you do it, the result is still zero.

POST: In web api, POST requests are used to send data to the API server to create or update a resource. The data sent to the server is stored in the request body of the HTTP request.

The simplest example is a contact form on a website. When you fill out the inputs in a form and hit Send, that data is put in the response body of the request and sent to the server. This may be JSON, XML, or query parameters.

Ideally, if a resource has been created on the origin server, the response SHOULD be HTTP response code 201 (Created) and contain an entity which describes the status of the request and refers to the new resource.

It's worth noting that a POST request is non-idempotent. It mutates data on the backend server (by creating or updating a resource), as opposed to a GET request which does not change any data.

PUT: Similar to POST, PUT requests are used to send data to the API to update or create a resource. The difference is that PUT requests are idempotent. So if you send a request multiple times, that should be equivalent to single request modification. In contrast, calling a POST request repeatedly make have side effects of creating the same resource multiple times.

Generally, when a PUT request creates a resource the server will respond with a 201 (Created), and if the request modifies existing resource the server will return a 200 (OK) or 204 (No Content).

The difference between the POST and PUT APIs can be observed in request URIs. POST requests are made on resource collections, whereas PUT requests are made on a single resource.

PATCH: HTTP PATCH requests are to make partial update on a resource. If you see PUT requests also modify a resource entity, so to make more clear – PATCH method is the correct choice for partially updating an existing resource, and PUT should only be used if you’re replacing a resource in its entirety.

DELETE: As the name applies, DELETE APIs are used to delete resources.

A successful response of DELETE requests should be HTTP response code 200 (OK) if the response includes an entity describing the status, 202 (Accepted) if the action has been queued, or 204 (No Content) if the action has been performed but the response does not include an entity.

DELETE operations are idempotent. If you DELETE a resource, it’s removed from the collection of resources. Repeatedly calling DELETE API on that resource will not change the outcome – however, calling DELETE on a resource a second time will return a 404 (NOT FOUND) since it was already removed. Some may argue that it makes the DELETE method non-idempotent. It’s a matter of discussion and personal opinion.

PUT VS PATCH:

When a client needs to replace an existing Resource entirely, they can use PUT. When they’re doing a partial update, they can use HTTP PATCH.

For instance, when updating a single field of the Resource, sending the complete Resource representation can be cumbersome and uses a lot of unnecessary bandwidth. In such cases, the semantics of PATCH make a lot more sense.

Glossary:- 

Safe Methods

As per HTTP specification, the GET and HEAD methods should be used only for retrieval of resource representations – and they do not update/delete the resource on the server. Both methods are said to be considered “safe“.

This allows user agents to represent other methods, such as POST, PUT and DELETE, in a unique way so that the user is made aware of the fact that a possibly unsafe action is being requested – and they can update/delete the resource on server and so should be used carefully.

Idempotent Methods

The term idempotent is used more comprehensively to describe an operation that will produce the same results if executed once or multiple times. Idempotence is a handy property in many situations, as it means that an operation can be repeated or retried as often as necessary without causing unintended effects. With non-idempotent operations, the algorithm may have to keep track of whether the operation was already performed or not.

In HTTP specification, The methods GET, HEAD, PUT and DELETE are declared idempotent methods.

https://restfulapi.net/idempotent-rest-apis/


Continue Reading →

Thursday, 16 July 2020

How to Improve Web API Performance

Web Api: This is a framework for building HTTP services with easy and simple way.
Web API is open source an ideal platform for building REST-ful services over the .NET Framework.
It is light weight architecture and good for devices which have limited bandwidth like smart phones.

In this page, we will discuss about the techniques to improve the Web API performance.

1: JSON serializer over XML:
JSON serializer use JSON Formatter and by default Web API provides media-type formatters for both JSON and XML.A media type formatter is used to read CLR objects from an HTTP message and write the CLR object in HTTP message body.
JSON serializer is highly recommend and it very faster compare to other Serlializer like XML.

2: Asynchronous Task Based WebAPI :
     Async Web API action help to increase the number of concurrent HTTP requests Web API can handle. We can implement asynchronous programming for web api controller by using keywords async, Task, await

public class UserController : ApiController
{       
  public async Task<IHttpActionResultRead()
  {
   var data = await _db.UserMaster.ToListAsync();
   return Ok(data);
  }
 }

3: Cache Data:
Web API  does not provide the output Caching attribute to cache web api response but you can Cache data in memory to process same future request without hitting database and it improve the performance of ASP.NET Web API and Microsoft provides the System.Runtime.Caching library for memory caching. 

4: Multi Result sets or combined results
Web API should return as many objects as you can in one Web API request and combining objects into one aggregate object and It reduce the number of HTTP request to web API

Example : Aggregate Object ‘UserScreenData’

class UserScreenData
{
public List<StateStates { getset; }
public List<CountryCountries { getset; }
}

 Web API Method to return Aggregate object

public async Task<IHttpActionResultGetScreenData()
{
 UserScreenData screen = new Controllers.UserScreenData();
 screen.State = await _db.State.ToListAsync();
 screen.Countries = await _db.Country.ToListAsync();
 return Ok(data);
}

5: Implement compression
You should use compression techniques to compress the data that is transmitted over the wire. You can use GZip or Deflate compression on your Web API to compress data transferred between the server and the client. You can do the compression at the IIS level or by using a custom delegating handler or even using a custom action filter. You can learn more on how you can achieve this from  Click here

Below example you can use in Dotnet Core WebAPI.
public void ConfigureServices(IServiceCollection services)
{
    services.AddResponseCompression();
    services.Configure<GzipCompressionProviderOptions>(options => {
        options.Level = CompressionLevel.Fastest;
    });
}

6: Use classic ADO.NET if possible
Hand coded ADO.NET is still the fastest way to get data from database. If the performance of Web API is really important for you, don’t use ORMs.

The Dapper and the  hand-written fetch code are very fast, as expected, all ORMs are slower than those three.

But if you write your data access logic in optimize ways in EF Core, then definitely it improves the performance of the application. Here, we have some of the techniques which will increase the performance.
  1. Use No Tracking while getting the data which is the only read-only purpose. It improves performance.
  2. Try to filter the data on the database side, don’t fetch the whole data using query and then filter at your end. You can use some function available in EF Core like Where, Select which help you to filter the data on the database side.
  3. Retrieve only the required number of records which is necessary using the help of Take and Skip. You can take one example of paging where you can implement Take and Skip while clicking on the page number.
Let's take one example and try to understand how we can optimize the EF Core query using Select and AsNoTracking.

public async Task < PaginatedList < Post >> GetPagedPendingPosts
     (int pageIndex, int pageSize, List<Category> allowedCategories)
{
  var allowedCatIds = allowedCategories.Select(x => x.Id);
  var query = _context.Post
    .Include(x => x.Topic.Category)
    .Include(x => x.User)
    .Where(x => x.Pending == true && allowedCatIds.Contains(x.Topic.Category.Id))
    .OrderBy(x => x.DateCreated);

  return await PaginatedList<Post>.CreateAsync(query.AsNoTracking(), pageIndex,                                                                 pageSize);
}



Continue Reading →

Friday, 18 January 2019

WebApi CRUD Operation- Step by step

In this tutorial, I am assuming you have basic knowledge of asp.net MVC, Web Api, Entity Framework.

1- Open Visual Studio 2015. Create a new Webapi project.


2- Add a new WebApi Controller named EmployeeController.cs.


3- Add a Repository Folder in the solution. add a IEmployeeRepo.cs interface and EmployeeRepo.cs class in the folder. (See above image)

4- Create Database and table in Sql server. below is the script.

CREATE DATABASE [EmployeeDB]
USE [EmployeeDB]
CREATE TABLE [dbo].[tblEmployee](
 [EmpId] [int] IDENTITY(1,1) NOT NULL,
 [FirstName] [varchar](50) NULL,
 [LastName] [varchar](50) NULL,
 CONSTRAINT [PK_tblEmployee] PRIMARY KEY CLUSTERED 
(
 [EmpId] ASC
)WITH (PAD_INDEX = OFF, STATISTICS_NORECOMPUTE = OFF, IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS = ON, ALLOW_PAGE_LOCKS = ON) ON [PRIMARY]
) ON [PRIMARY]

SET IDENTITY_INSERT [dbo].[tblEmployee] ON 
INSERT [dbo].[tblEmployee] ([EmpId], [FirstName], [LastName]) VALUES (1, N'Suraj', N'Kumar')
INSERT [dbo].[tblEmployee] ([EmpId], [FirstName], [LastName]) VALUES (2, N'Rahul', N'Raj')
INSERT [dbo].[tblEmployee] ([EmpId], [FirstName], [LastName]) VALUES (3, N'Amit', N'Kumar')
SET IDENTITY_INSERT [dbo].[tblEmployee] OFF

5- Add  EmployeeModel.cs class in the Model Folder.



6- Here we are using Database first approach for Entity framework so you need to add Datamodel file (.edmx).


7- Now add the below code in IEmployeeRepo.cs file.

    public interface IEmployeeRepo
    {
        List<EmployeeModel> GetAllEmp();
        void AddEmployee(EmployeeModel entity);
        void DeleteEmployee(int id);
        void UpdateEmployee(int id, EmployeeModel model);
        EmployeeModel FindByEmpId(int Id);
    }

8- Implement this interface in EmployeeRepo.cs class.

using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using EmployeeWeb.Models;

namespace EmployeeWeb.Repository
{
    public class EmployeeRepo : IEmployeeRepo
    {
        EmployeeDBEntities EmpContext;
        List<EmployeeModel> EmpObj = new List<EmployeeModel>();
        public EmployeeRepo()
        {
            EmpContext = new EmployeeDBEntities();
        }

        public List<EmployeeModel> GetAllEmp()
        {
            return MapList(EmpContext.tblEmployees.ToList());
        }

        public List<EmployeeModel> MapList(List<tblEmployee> model)
        {
            List<EmployeeModel> obj = new List<EmployeeModel>();
            foreach (var item in model)
            {
                EmployeeModel emp = new Models.EmployeeModel();
                emp.EmpId = item.EmpId;
                emp.FirstName = item.FirstName;
                emp.LastName = item.LastName;
                
                obj.Add(emp);

            }
            return obj;
        }

        public EmployeeModel FindByEmpId(int Id)
        {
            var result = (from r in EmpContext.tblEmployees where r.EmpId == Id select r).FirstOrDefault();
            return MapEntityToModelModel(result);
        }

        public EmployeeModel MapEntityToModelModel(tblEmployee emp)
        {
            EmployeeModel model = new Models.EmployeeModel();
            model.EmpId = emp.EmpId;
            model.FirstName = emp.FirstName;
            model.LastName = emp.LastName;
            return model;
        }


        public void AddEmployee(EmployeeModel model)
        {
            EmpContext.tblEmployees.Add(MapModelToEntityModel(model));
            EmpContext.SaveChanges();
        }

        public tblEmployee MapModelToEntityModel(EmployeeModel emp)
        {
            tblEmployee model = new Models.tblEmployee();
            //model.EmpId = emp.EmpId;
            model.FirstName = emp.FirstName;
            model.LastName = emp.LastName;
            return model;
        }


        public void DeleteEmployee(int id)
        {
            var emp = EmpContext.tblEmployees
                 .Where(s => s.EmpId == id)
                 .FirstOrDefault();

            EmpContext.Entry(emp).State = System.Data.Entity.EntityState.Deleted;
            EmpContext.SaveChanges();
        }

        public void UpdateEmployee(int id, EmployeeModel model)
        {          
            var existingEmp = EmpContext.tblEmployees.Where(s => s.EmpId == id)
                                                   .FirstOrDefault<tblEmployee>();
            if (existingEmp != null)
            {
                existingEmp.FirstName = model.FirstName;
                existingEmp.LastName = model.LastName;
                EmpContext.Entry(existingEmp).State = System.Data.Entity.EntityState.Modified;
                EmpContext.SaveChanges();
            }
        }
    }
}

9-  Now you need to call your repository functions from Employee api controller.

using System.Net;
using System.Net.Http;
using System.Web.Http;
using EmployeeWeb.Models;
using EmployeeWeb.Repository;
using System.Web.Http.Cors;

namespace EmployeeWeb.Controllers
{
    [EnableCors(origins: "http://localhost:4200", headers: "*", methods: "*")]
    public class EmployeeController : ApiController
    {
        public IEmployeeRepo repository = null;   
        public EmployeeController()
        {
            repository = new EmployeeRepo();
        }

        // GET: api/Employee
        public HttpResponseMessage Get()
        {
            var result = repository.GetAllEmp();
            return Request.CreateResponse(HttpStatusCode.OK, result);
        }

        // GET: api/Employee/5
        public HttpResponseMessage Get(int id)
        {
            var result = repository.FindByEmpId(id);

            return Request.CreateResponse(HttpStatusCode.OK, result);
        }

        // POST: api/Employee
        public HttpResponseMessage Post(EmployeeModel model)
        {
            repository.AddEmployee(model);
            return Request.CreateResponse(HttpStatusCode.Created);
        }

        // PUT: api/Employee/5
        public HttpResponseMessage Put(int id, EmployeeModel model)
        {
            repository.UpdateEmployee(id, model);
            return Request.CreateResponse(HttpStatusCode.OK);
        }

        // DELETE: api/Employee/5
        public HttpResponseMessage Delete(int id)
        {
            repository.DeleteEmployee(id);
            return Request.CreateResponse(HttpStatusCode.OK);
        }
    }
}

10- Add some extraa code in Register function of Webapi config to return api data in json format and to enable CORS.

   public static void Register(HttpConfiguration config)
        {
            config.EnableCors(); // Enables CORS

            // Web API configuration and services
            // Configure Web API to use only bearer token authentication.
            config.SuppressDefaultHostAuthentication();
            config.Filters.Add(new HostAuthenticationFilter(OAuthDefaults.AuthenticationType));

            // Web API routes
            config.MapHttpAttributeRoutes();

            config.Routes.MapHttpRoute(
                name: "DefaultApi",
                routeTemplate: "api/{controller}/{id}",
                defaults: new { id = RouteParameter.Optional }
            );
            config.Formatters.Remove(config.Formatters.XmlFormatter);
        }

11- Change the below property for EmpId column in edmx file.


12- Now build and run your solution. Your Api is ready for functioning. Test the Api with any RestClient.


13- See the result of above request.


14- Below is the request for Post method.


15- Below is the request of update method. Here I'm updating the employee of EmpId= 5.



Let me know if you have any concern in this tutorial. Download the complete project. Click here









Continue Reading →

Monday, 24 December 2018

HTTP - Status Codes

Status codes are issued by a server in response to a client's request made to the server.

S.N.Code and Description
11xx: Informational
It means the request has been received and the process is continuing.
22xx: Success
It means the action was successfully received, understood, and accepted.
33xx: Redirection
It means further action must be taken in order to complete the request.
44xx: Client Error
It means the request contains incorrect syntax or cannot be fulfilled.
55xx: Server Error
It means the server failed to fulfill an apparently valid request.
HTTP status codes are extensible and HTTP applications are not required to understand the meaning of all the registered status codes. Given below is a list of all the status codes.

1xx: Information

MessageDescription
100 ContinueOnly a part of the request has been received by the server, but as long as it has not been rejected, the client should continue with the request.
101 Switching ProtocolsThe server switches protocol.

2xx: Successful

MessageDescription
200 OKThe request is OK.
201 CreatedThe request is complete, and a new resource is created .
202 AcceptedThe request is accepted for processing, but the processing is not complete.
203 Non-authoritative InformationThe information in the entity header is from a local or third-party copy, not from the original server.
204 No ContentA status code and a header are given in the response, but there is no entity-body in the reply.
205 Reset ContentThe browser should clear the form used for this transaction for additional input.
206 Partial ContentThe server is returning partial data of the size requested. Used in response to a request specifying a Range header. The server must specify the range included in the response with the Content-Rangeheader.

3xx: Redirection

MessageDescription
300 Multiple ChoicesA link list. The user can select a link and go to that location. Maximum five addresses  .
301 Moved PermanentlyThe requested page has moved to a new url .
302 FoundThe requested page has moved temporarily to a new url .
303 See OtherThe requested page can be found under a different url .
304 Not ModifiedThis is the response code to an If-Modified-Since or If-None-Matchheader, where the URL has not been modified since the specified date.
305 Use ProxyThe requested URL must be accessed through the proxy mentioned in the Location header.
306 UnusedThis code was used in a previous version. It is no longer used, but the code is reserved.
307 Temporary RedirectThe requested page has moved temporarily to a new url.

4xx: Client Error

MessageDescription
400 Bad RequestThe server did not understand the request.
401 UnauthorizedThe requested page needs a username and a password.
402 Payment RequiredYou can not use this code yet.
403 ForbiddenAccess is forbidden to the requested page.
404 Not FoundThe server can not find the requested page.
405 Method Not AllowedThe method specified in the request is not allowed.
406 Not AcceptableThe server can only generate a response that is not accepted by the client.
407 Proxy Authentication RequiredYou must authenticate with a proxy server before this request can be served.
408 Request TimeoutThe request took longer than the server was prepared to wait.
409 ConflictThe request could not be completed because of a conflict.
410 GoneThe requested page is no longer available .
411 Length RequiredThe "Content-Length" is not defined. The server will not accept the request without it .
412 Precondition FailedThe pre condition given in the request evaluated to false by the server.
413 Request Entity Too LargeThe server will not accept the request, because the request entity is too large.
414 Request-url Too LongThe server will not accept the request, because the url is too long. Occurs when you convert a "post" request to a "get" request with a long query information .
415 Unsupported Media TypeThe server will not accept the request, because the mediatype is not supported .
416 Requested Range Not SatisfiableThe requested byte range is not available and is out of bounds.
417 Expectation FailedThe expectation given in an Expect request-header field could not be met by this server.

5xx: Server Error

MessageDescription
500 Internal Server ErrorThe request was not completed. The server met an unexpected condition.
501 Not ImplementedThe request was not completed. The server did not support the functionality required.
502 Bad GatewayThe request was not completed. The server received an invalid response from the upstream server.
503 Service UnavailableThe request was not completed. The server is temporarily overloading or down.
504 Gateway TimeoutThe gateway has timed out.
505 HTTP Version Not SupportedThe server does not




Continue Reading →

Topics

ADFS (1) ADO .Net (1) Ajax (1) Angular (47) Angular Js (15) ASP .Net (14) Authentication (4) Azure (3) Breeze.js (1) C# (55) CD (1) CI (2) CloudComputing (2) Coding (10) CQRS (1) CSS (2) Design_Pattern (7) DevOps (4) DI (3) Dotnet (10) DotnetCore (20) Entity Framework (5) ExpressJS (4) Html (4) IIS (1) Javascript (17) Jquery (8) jwtToken (4) Lamda (3) Linq (10) microservice (4) Mongodb (1) MVC (46) NodeJS (8) React (10) SDLC (1) Sql Server (32) SSIS (3) SSO (1) TypeScript (3) UI (1) UnitTest (2) WCF (14) Web Api (16) Web Service (1) XMl (1)

Dotnet Guru Archives