context: // ReSharper disable All
  using System.Collections.Generic;
  using System.Net;
  using System.Net.Http;
  using System.Web.Http;
  using MixERP.Net.Api.Framework;
  using MixERP.Net.ApplicationState.Cache;
  using MixERP.Net.Common.Extensions;
  using MixERP.Net.EntityParser;
  using MixERP.Net.Framework;
  using Newtonsoft.Json;
  using Newtonsoft.Json.Linq;
  using PetaPoco;
  
  namespace MixERP.Net.Api.HRM
  {
      /// <summary>
      ///     Provides a direct HTTP access to perform various tasks such as adding, editing, and removing Employees.
      /// </summary>
      [RoutePrefix("api/v1.5/hrm/employee")]
      public class EmployeeController : ApiController
      {
          /// <summary>
          ///     The Employee data context.
          /// </summary>
          private readonly MixERP.Net.Core.Modules.HRM.Data.Employee EmployeeContext;
  
          public EmployeeController()
          {
              this._LoginId = AppUsers.GetCurrent().View.LoginId.ToLong();
              this._UserId = AppUsers.GetCurrent().View.UserId.ToInt();
              this._OfficeId = AppUsers.GetCurrent().View.OfficeId.ToInt();
              this._Catalog = AppUsers.GetCurrentUserDB();
  
              this.EmployeeContext = new MixERP.Net.Core.Modules.HRM.Data.Employee
              {
                  _Catalog = this._Catalog,
                  _LoginId = this._LoginId,
                  _UserId = this._UserId
              };
          }
  
          public long _LoginId { get; }
          public int _UserId { get; private set; }
          public int _OfficeId { get; private set; }
          public string _Catalog { get; }
  
          /// <summary>
          ///     Creates meta information of "employee" entity.
          /// </summary>
          /// <returns>Returns the "employee" meta information to perform CRUD operation.</returns>
          [AcceptVerbs("GET", "HEAD")]
          [Route("meta")]
          [Route("~/api/hrm/employee/meta")]
          public EntityView GetEntityView()
          {
              return new EntityView
              {
                  PrimaryKey = "employee_id",
                  Columns = new List<EntityColumn>()
                                  {
                                          new EntityColumn { ColumnName = "employee_id",  PropertyName = "EmployeeId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = true,  IsSerial = true,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "employee_code",  PropertyName = "EmployeeCode",  DataType = "string",  DbDataType = "varchar",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 12 },
                                          new EntityColumn { ColumnName = "first_name",  PropertyName = "FirstName",  DataType = "string",  DbDataType = "varchar",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 50 },
                                          new EntityColumn { ColumnName = "middle_name",  PropertyName = "MiddleName",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 50 },
                                          new EntityColumn { ColumnName = "last_name",  PropertyName = "LastName",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 50 },
                                          new EntityColumn { ColumnName = "employee_name",  PropertyName = "EmployeeName",  DataType = "string",  DbDataType = "varchar",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 160 },
                                          new EntityColumn { ColumnName = "gender_code",  PropertyName = "GenderCode",  DataType = "string",  DbDataType = "varchar",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 4 },
                                          new EntityColumn { ColumnName = "marital_status_id",  PropertyName = "MaritalStatusId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "joined_on",  PropertyName = "JoinedOn",  DataType = "DateTime",  DbDataType = "date",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "office_id",  PropertyName = "OfficeId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "user_id",  PropertyName = "UserId",  DataType = "int",  DbDataType = "int4",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "employee_type_id",  PropertyName = "EmployeeTypeId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "current_department_id",  PropertyName = "CurrentDepartmentId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "current_role_id",  PropertyName = "CurrentRoleId",  DataType = "int",  DbDataType = "int4",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "current_employment_status_id",  PropertyName = "CurrentEmploymentStatusId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "current_job_title_id",  PropertyName = "CurrentJobTitleId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "current_pay_grade_id",  PropertyName = "CurrentPayGradeId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "current_shift_id",  PropertyName = "CurrentShiftId",  DataType = "int",  DbDataType = "int4",  IsNullable = false,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "nationality_code",  PropertyName = "NationalityCode",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 12 },
                                          new EntityColumn { ColumnName = "date_of_birth",  PropertyName = "DateOfBirth",  DataType = "DateTime",  DbDataType = "date",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "photo",  PropertyName = "Photo",  DataType = "string",  DbDataType = "image",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "zip_code",  PropertyName = "ZipCode",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "address_line_1",  PropertyName = "AddressLine1",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "address_line_2",  PropertyName = "AddressLine2",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "street",  PropertyName = "Street",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "city",  PropertyName = "City",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "state",  PropertyName = "State",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "country_id",  PropertyName = "CountryId",  DataType = "int",  DbDataType = "int4",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "phone_home",  PropertyName = "PhoneHome",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "phone_cell",  PropertyName = "PhoneCell",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "phone_office_extension",  PropertyName = "PhoneOfficeExtension",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "phone_emergency",  PropertyName = "PhoneEmergency",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "phone_emergency2",  PropertyName = "PhoneEmergency2",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "email_address",  PropertyName = "EmailAddress",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "website",  PropertyName = "Website",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "blog",  PropertyName = "Blog",  DataType = "string",  DbDataType = "varchar",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 128 },
                                          new EntityColumn { ColumnName = "is_smoker",  PropertyName = "IsSmoker",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "is_alcoholic",  PropertyName = "IsAlcoholic",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "with_disabilities",  PropertyName = "WithDisabilities",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "low_vision",  PropertyName = "LowVision",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "uses_wheelchair",  PropertyName = "UsesWheelchair",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "hard_of_hearing",  PropertyName = "HardOfHearing",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "is_aphonic",  PropertyName = "IsAphonic",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "is_cognitively_disabled",  PropertyName = "IsCognitivelyDisabled",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "is_autistic",  PropertyName = "IsAutistic",  DataType = "bool",  DbDataType = "bool",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "service_ended_on",  PropertyName = "ServiceEndedOn",  DataType = "DateTime",  DbDataType = "date",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "audit_user_id",  PropertyName = "AuditUserId",  DataType = "int",  DbDataType = "int4",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 },
                                          new EntityColumn { ColumnName = "audit_ts",  PropertyName = "AuditTs",  DataType = "DateTime",  DbDataType = "timestamptz",  IsNullable = true,  IsPrimaryKey = false,  IsSerial = false,  Value = "",  MaxLength = 0 }
                                  }
              };
          }
  
          /// <summary>
          ///     Counts the number of employees.
          /// </summary>
          /// <returns>Returns the count of the employees.</returns>
          [AcceptVerbs("GET", "HEAD")]
          [Route("count")]
          [Route("~/api/hrm/employee/count")]
          public long Count()
          {
              try
              {
                  return this.EmployeeContext.Count();
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          /// <summary>
          ///     Returns collection of employee for export.
          /// </summary>
          /// <returns></returns>
          [AcceptVerbs("GET", "HEAD")]
          [Route("export")]
          [Route("all")]
          [Route("~/api/hrm/employee/export")]
          [Route("~/api/hrm/employee/all")]
          public IEnumerable<MixERP.Net.Entities.HRM.Employee> Get()
          {
              try
              {
                  return this.EmployeeContext.Get();
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          /// <summary>
          ///     Returns an instance of employee.
          /// </summary>
          /// <param name="employeeId">Enter EmployeeId to search for.</param>
          /// <returns></returns>
          [AcceptVerbs("GET", "HEAD")]
          [Route("{employeeId}")]
          [Route("~/api/hrm/employee/{employeeId}")]
          public MixERP.Net.Entities.HRM.Employee Get(int employeeId)
          {
              try
              {
                  return this.EmployeeContext.Get(employeeId);
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          [AcceptVerbs("GET", "HEAD")]
          [Route("get")]
          [Route("~/api/hrm/employee/get")]
          public IEnumerable<MixERP.Net.Entities.HRM.Employee> Get([FromUri] int[] employeeIds)
          {
              try
              {
                  return this.EmployeeContext.Get(employeeIds);
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          /// <summary>
          ///     Creates a paginated collection containing 10 employees on each page, sorted by the property EmployeeId.
          /// </summary>
          /// <returns>Returns the first page from the collection.</returns>
          [AcceptVerbs("GET", "HEAD")]
          [Route("")]
          [Route("~/api/hrm/employee")]
          public IEnumerable<MixERP.Net.Entities.HRM.Employee> GetPaginatedResult()
          {
              try
              {
                  return this.EmployeeContext.GetPaginatedResult();
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          /// <summary>
          ///     Creates a paginated collection containing 10 employees on each page, sorted by the property EmployeeId.
          /// </summary>
          /// <param name="pageNumber">Enter the page number to produce the resultset.</param>
          /// <returns>Returns the requested page from the collection.</returns>
          [AcceptVerbs("GET", "HEAD")]
          [Route("page/{pageNumber}")]
          [Route("~/api/hrm/employee/page/{pageNumber}")]
          public IEnumerable<MixERP.Net.Entities.HRM.Employee> GetPaginatedResult(long pageNumber)
          {
              try
              {
                  return this.EmployeeContext.GetPaginatedResult(pageNumber);
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          /// <summary>
          ///     Counts the number of employees using the supplied filter(s).
          /// </summary>
          /// <param name="filters">The list of filter conditions.</param>
          /// <returns>Returns the count of filtered employees.</returns>
          [AcceptVerbs("POST")]
          [Route("count-where")]
          [Route("~/api/hrm/employee/count-where")]
          public long CountWhere([FromBody]JArray filters)
          {
              try
              {
                  List<EntityParser.Filter> f = filters.ToObject<List<EntityParser.Filter>>(JsonHelper.GetJsonSerializer());
                  return this.EmployeeContext.CountWhere(f);
              }
              catch (UnauthorizedException)
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.Forbidden));
              }
              catch (MixERPException ex)
              {
                  throw new HttpResponseException(new HttpResponseMessage
                  {
                      Content = new StringContent(ex.Message),
                      StatusCode = HttpStatusCode.InternalServerError
                  });
              }
              catch
              {
                  throw new HttpResponseException(new HttpResponseMessage(HttpStatusCode.InternalServerError));
              }
          }
  
          /// <summary>
          ///     Creates a filtered and paginated collection containing 10 employees on each page, sorted by the property EmployeeId.
          /// </summary>
          /// <param name="pageNumber">Enter the page number to produce the resultset. If you provide a negative number, the result will not be paginated.</param>
          /// <param name="filters">The list of filter conditions.</param>
          /// <returns>Returns the requested page from the collection using the supplied filters.</returns>
          [AcceptVerbs("POST")]
          [Route("get-where/{pageNumber}")]
          [Route("~/api/hrm/employee/get-where/{pageNumber}")]
          public IEnumerable<MixERP.Net.Entities.HRM.Employee> GetWhere(long pageNumber, [FromBody]JArray filters)
          {
              try
              {
                  List<EntityParser.Filter> f = filters.ToObject<List<EntityParser.Filter>>(JsonHelper.GetJsonSerializer());
  
gt:                 return this.EmployeeContext.GetWhere(pageNumber, f);