using Foresight.Data;
using Foresight.Fleet.Services;
using Foresight.Fleet.Services.Asset;
using Foresight.Fleet.Services.Device;
using Foresight.Fleet.Services.JobSite;
using Foresight.Fleet.Services.User;
using Foresight.ServiceModel;
using IronIntel.Contractor.Contact;
using IronIntel.Contractor.Device;
using IronIntel.Contractor.JobSites;
using IronIntel.Contractor.Machines;
using IronIntel.Contractor.MapView;
using IronIntel.Contractor.Users;
using IronIntel.Services;
using IronIntel.Services.Business.Admin;
using IronIntel.Services.Contractor;
using IronIntel.Services.Contractor.Machine;
using IronIntel.Services.Customers;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Data;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Web;
using FFSDevice = Foresight.Fleet.Services.Device;

namespace IronIntel.Contractor.Site
{
    public class MachineDeviceBasePage : ContractorBasePage
    {
        protected void ProcessRequest(string method)
        {
            object result = null;
            try
            {
                string methodName = Request.Params["MethodName"];
                if (methodName != null)
                {
                    switch (methodName.ToUpper())
                    {
                        case "GETMACHINES":
                            result = GetMachines();
                            break;
                        case "GETGPSDEVICES":
                            result = GetGPSDevices();
                            break;
                        case "SAVEGPSDEVICE":
                            result = SaveGPSDevice();
                            break;
                        case "GETGPSSOURCES":
                            result = GetGPSSources();
                            break;
                        case "CHANGEGPSCONTRACTOR":
                            result = ChangeGPSContractor();
                            break;
                        case "GETDEVICECOMMENTS":
                            result = GetDeviceComments();
                            break;
                        case "ADDDEVICECOMMENT":
                            result = AddDeviceComment();
                            break;
                        case "GETMACHINETYPES":
                            result = GetMachineTypes();
                            break;
                        case "GETCONTRACTORS":
                            result = GetContractors();
                            break;
                        case "GETCONTRACTORSBYUSER":
                            result = GetContractorsByUser();
                            break;
                        case "SAVEMACHINEGROUP":
                            result = SaveMachineGroup();
                            break;
                        case "SAVEASSETGROUP":
                            result = SaveAssetGroup();
                            break;
                        case "DELETEMACHINEGROUP":
                            result = DeleteMachineGroup();
                            break;
                        case "DELETEASSETGROUP":
                            result = DeleteAssetGroup();
                            break;
                        case "GETMACHINEGROUPS":
                            result = GetMachineGroups();
                            break;
                        case "GETASSETGROUPS":
                            result = GetAssetGroups();
                            break;
                        case "GETASSETLIST":
                            result = GetAssetList();
                            break;
                        case "GETJOBSITEASSETLIST":
                            result = GetJobsiteAssetList();
                            break;
                        case "GETMACHINESBYGROUP":
                            result = GetMachinesByGroup();
                            break;
                        case "GETASSETSBYGROUP":
                            result = GetAssetsByGroup();
                            break;
                        case "GETMACHINEGROUPBYUSER":
                            result = GetMachineGroupByUser();
                            break;
                        case "SAVEMACHINEMAKE":
                            result = SaveMachineMake();
                            break;
                        case "SAVEMACHINEMODEL":
                            result = SaveMachineModel();
                            break;
                        case "DELETEMACHINEMAKE":
                            result = DeleteMachineMake();
                            break;
                        case "DELETEMACHINEMODEL":
                            result = DeleteMachineModel();
                            break;
                        case "GETASSETMAKES":
                            result = GetAssetMakes();
                            break;
                        case "GETASSETMODELS":
                            result = GetAssetModels();
                            break;
                        case "GETACTIVEJOBSITES":
                            result = GetActiveJobsites();
                            break;
                        case "GETCONTACTS":
                            result = GetContacts();
                            break;
                        case "CHANGEMACHINEICONFILE":
                            result = ChangeMachineIconFile();
                            break;
                        case "SEARCHRENTALS":
                            result = SearchRentals();
                            break;
                        case "SEARCHRENTALSBYASSET":
                            result = SearchRentalsByAsset();
                            break;
                        case "GETRENTALINFO":
                            result = GetRentalInfo();
                            break;
                        case "SAVERENTAL":
                            result = SaveRental();
                            break;
                        case "DELETERENTAL":
                            result = DeleteRental();
                            break;
                        case "GETSELECTMACHINESBYCOMPANY":
                            result = GetSelectMachinesByCompany();
                            break;
                        case "SEARCHRENTALCHANGEHISTORY":
                            result = SearchRentalChangeHistory();
                            break;
                        case "GETMACHINEDETAILURL":
                            result = GetMachineDetailURL();
                            break;
                        case "GETSELECTMACHINESBYRENTAL":
                            result = GetSelectMachinesByRental();
                            break;
                        case "GETATTACHMENTS":
                            result = GetAttachments();
                            break;
                        case "ADDATTACHMENT":
                            result = AddAttachment();
                            break;
                        case "DELETEATTACHMENT":
                            result = DeleteAttachment();
                            break;
                        case "GETASSETCURRENTODOMETER":
                            result = GetAssetCurrentOdometer();
                            break;
                        case "SAVEADJUSTODOMETER":
                            result = SaveAdjustOdometer();
                            break;
                        case "GETASSETCURRENTENGINEHOURS":
                            result = GetAssetCurrentEngineHours();
                            break;
                        case "SAVEADJUSTENGINEHOURS":
                            result = SaveAdjustEngineHours();
                            break;
                        case "GETASSETCURRENTLOCATION":
                            result = GetAssetCurrentLocation();
                            break;
                        case "GETASSETCURRENTIDLEHOURS":
                            result = GetAssetCurrentIdleHours();
                            break;
                        case "GETASSETCURRENTFUELUSED":
                            result = GetAssetCurrentFuelUsed();
                            break;
                        case "CHANGEPRIMARYDATASOURCE":
                            result = ChangePrimaryDataSource();
                            break;
                        case "GETCALAMPODOMETERHISTORY":
                            result = GetCalampOdometerHistory();
                            break;
                        case "GETCALAMPODOMETERHISTORYPREVIEW":
                            result = GetCalampOdometerHistoryPreview();
                            break;
                        case "GETPEDIGREEODOMETERHISTORY":
                            result = GetPedigreeOdometerHistory();
                            break;
                        case "GETPEDIGREEODOMETERHISTORYPREVIEW":
                            result = GetPedigreeOdometerHistoryPreview();
                            break;
                        case "GETTIMEZONES":
                            result = GetTimeZones();
                            break;
                        case "GETCALAMPENGINEHOURSHISTORY":
                            result = GetCalampEngineHoursHistory();
                            break;
                        case "GETCALAMPENGINEHOURSHISTORYPREVIEW":
                            result = GetCalampEngineHoursHistoryPreview();
                            break;
                        case "GETPEDIGREEENGINEHOURSHISTORY":
                            result = GetPedigreeEngineHoursHistory();
                            break;
                        case "GETPEDIGREEENGINEHOURSHISTORYPREVIEW":
                            result = GetPedigreeEngineHoursHistoryPreview();
                            break;
                        case "CHECKODOMETERMINNIMUMTIME":
                            result = CheckOdometerMinnimumTime();
                            break;
                        case "CHECKENGINEHOURMINIMUMTIME":
                            result = CheckEngineHourMinimumTime();
                            break;
                        case "GETUSERPERMISSION":
                            result = GetUserPermission();
                            break;
                        case "ADDMANUALLYINPUTODOMETER":
                            result = AddManuallyInputOdometer();
                            break;
                        case "ADDMANUALLYINPUTENGINEHOURS":
                            result = AddManuallyInputEngineHours();
                            break;
                    }
                }
            }
            catch (Exception ex)
            {
                SystemParams.WriteLog("error", "MachineDeviceBasePage", ex.Message, ex.ToString());
                throw ex;
            }
            string json = JsonConvert.SerializeObject(result);
            Response.Write(json);
            Response.End();
        }

        #region Rentals

        private object SearchRentals()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var searchtext = HttpUtility.HtmlDecode(clientdata[1]);
                    var sdate = HttpUtility.HtmlDecode(clientdata[2]);
                    var edate = HttpUtility.HtmlDecode(clientdata[3]);
                    var machineid = HttpUtility.HtmlDecode(clientdata[4]);

                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    if (string.IsNullOrWhiteSpace(companyid) && SystemParams.IsDealer)
                        return new MachineRentalInfo[0];

                    AssetRentalInfo[] rentalinfos = CreateClient<AssetQueryClient>(companyid).GetAssetRentals(companyid, searchtext, session.User.UID);
                    if (rentalinfos == null)
                        return new MachineRentalInfo[0];

                    List<MachineRentalInfo> rentals = new List<MachineRentalInfo>();
                    foreach (AssetRentalInfo ri in rentalinfos)
                    {
                        MachineRentalInfo mi = new MachineRentalInfo();
                        Helper.CloneProperty(mi, ri);
                        mi.RentalRate = (decimal)ri.RentalRate;
                        rentals.Add(mi);
                    }

                    if (!string.IsNullOrWhiteSpace(machineid))
                        rentals = rentals.Where(m => m.MachineID == Convert.ToInt64(machineid)).ToList();

                    if (!string.IsNullOrWhiteSpace(sdate))
                    {
                        DateTime startdate = Convert.ToDateTime(sdate);
                        rentals = rentals.Where(m => m.RentalDate >= startdate).ToList();
                    }
                    if (!string.IsNullOrWhiteSpace(edate))
                    {
                        DateTime enddate = Convert.ToDateTime(edate).AddDays(1).AddSeconds(-1);
                        rentals = rentals.Where(m => m.RentalDate <= enddate).ToList();
                    }

                    return rentals.OrderBy(m => m.RentalDate);
                }
                else
                    return new MachineRentalInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object SearchRentalsByAsset()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string data = Request.Params["ClientData"];
                    string[] ps = JsonConvert.DeserializeObject<string[]>(data);
                    string companyid = ps[0];
                    long assetid = 0;
                    long.TryParse(ps[1], out assetid);

                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    if (string.IsNullOrWhiteSpace(companyid) && SystemParams.IsDealer)
                        return new MachineRentalInfo[0];

                    AssetRentalInfo[] rentalinfos = CreateClient<AssetQueryClient>(companyid).SearchRentalsByAsset(companyid, assetid, session.User.UID);
                    if (rentalinfos == null)
                        return new MachineRentalInfo[0];

                    List<MachineRentalInfo> rentals = new List<MachineRentalInfo>();
                    foreach (AssetRentalInfo ri in rentalinfos)
                    {
                        MachineRentalInfo mi = new MachineRentalInfo();
                        Helper.CloneProperty(mi, ri);
                        mi.RentalRate = (decimal)ri.RentalRate;
                        rentals.Add(mi);
                    }

                    if (rentals != null && rentals.Count > 0)
                    {
                        DateTime nowdate = DateTime.Now;
                        //当前时间所在的rental
                        MachineRentalInfo rental = rentals.FirstOrDefault(m => m.RentalDate <= nowdate && nowdate.Date <= ((m.ReturnDate ?? m.ProjectReturnDate ?? DateTime.MaxValue)));
                        if (rental == null)//当前时间的下一个rental                                
                            rental = rentals.Where(m => m.RentalDate >= nowdate.Date).OrderBy(m => m.RentalDate).FirstOrDefault();
                        if (rental == null)//最新rental
                            rental = rentals[0];

                        rental.Selected = true;
                    }
                    if (rentals == null)
                        return new MachineRentalInfo[0];

                    return rentals.OrderBy(m => m.RentalDate);
                }
                else
                    return new MachineRentalInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object SearchRentalChangeHistory()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var searchtext = HttpUtility.HtmlDecode(clientdata[1]);
                    var sdate = HttpUtility.HtmlDecode(clientdata[2]);
                    var edate = HttpUtility.HtmlDecode(clientdata[3]);
                    var machineid = HttpUtility.HtmlDecode(clientdata[4]);
                    var rentalid = HttpUtility.HtmlDecode(clientdata[5]);

                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    if (string.IsNullOrWhiteSpace(companyid) && SystemParams.IsDealer)
                        return new RentalChangeHistoryInfo[0];

                    AssetRentalChangeHistoryInfo[] assetrentals = CreateClient<AssetQueryClient>(companyid).GetAssetRentalChangeHistory(companyid, Convert.ToInt64(rentalid));
                    if (assetrentals == null)
                        return new RentalChangeHistoryInfo[0];
                    List<RentalChangeHistoryInfo> rentals = new List<RentalChangeHistoryInfo>();
                    foreach (AssetRentalChangeHistoryInfo ari in assetrentals)
                    {
                        RentalChangeHistoryInfo mri = new RentalChangeHistoryInfo();
                        Helper.CloneProperty(mri, ari);
                        mri.RentalRate = (decimal)ari.RentalRate;
                        rentals.Add(mri);
                    }

                    if (!string.IsNullOrWhiteSpace(sdate))
                    {
                        DateTime startdate = Convert.ToDateTime(sdate);
                        rentals = rentals.Where(m => m.RentalDate >= startdate).ToList();
                    }
                    if (!string.IsNullOrWhiteSpace(edate))
                    {
                        DateTime enddate = Convert.ToDateTime(edate).AddDays(1).AddSeconds(-1);
                        rentals = rentals.Where(m => m.RentalDate <= enddate).ToList();
                    }
                    return rentals.OrderBy(m => m.LastUpdateDate);
                }
                else
                    return new MachineRentalInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object GetRentalInfo()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var rentalid = HttpUtility.HtmlDecode(clientdata[1]);

                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    if (string.IsNullOrWhiteSpace(companyid) && SystemParams.IsDealer)
                        return new MachineRentalInfo[0];

                    AssetRentalInfo rentalinfo = CreateClient<AssetQueryClient>(companyid).GetAssetRentalInfo(companyid, Convert.ToInt64(rentalid));

                    MachineRentalInfo rental = new MachineRentalInfo();
                    Helper.CloneProperty(rental, rentalinfo);
                    rental.RentalRate = (decimal)rentalinfo.RentalRate;
                    return rental;
                }
                else
                    return new MachineRentalInfo();
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object SaveRental()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var data = HttpUtility.HtmlDecode(clientdata[1]);
                    MachineRentalInfo rentalInfo = JsonConvert.DeserializeObject<MachineRentalInfo>(data);

                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    AssetRentalInfo rental = new AssetRentalInfo();
                    Helper.CloneProperty(rental, rentalInfo);
                    rental.RentalRate = (double)rentalInfo.RentalRate;
                    long rentalid = CreateClient<AssetQueryClient>(companyid).SaveAssetRental(companyid, rental, session.User.UID);

                    return rentalid;
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object DeleteRental()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var id = HttpUtility.HtmlDecode(clientdata[1]);
                    long rentalid = Convert.ToInt64(id);

                    if (!SystemParams.IsDealer)
                        companyid = SystemParams.CompanyID;

                    CreateClient<AssetQueryClient>(companyid).DeleteAssetRental(companyid, rentalid, session.User.UID);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetSelectMachinesByCompany()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var companyid = HttpUtility.HtmlDecode(Request.Params["ClientData"]);

                    FISqlConnection db = null;
                    if (SystemParams.IsDealer)
                    {
                        string connetionstring = SystemParams.GetDbStringByCompany(companyid);
                        db = new FISqlConnection(connetionstring);
                    }
                    MachineItem[] machines = MachineManagement.GetMachines(session.User.UID, "", companyid);
                    if (machines == null)
                        return new MachineItem[0];

                    return machines.Where(m => m.Hide == false).OrderBy(m => m.ShowName).ToArray();
                }
                else
                    return new MachineItem[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }


        private object GetSelectMachinesByRental()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var companyid = HttpUtility.HtmlDecode(Request.Params["ClientData"]);

                    FISqlConnection db = null;
                    if (SystemParams.IsDealer)
                    {
                        string connetionstring = SystemParams.GetDbStringByCompany(companyid);
                        db = new FISqlConnection(connetionstring);
                    }
                    MachineItem[] machines = MachineManagement.GetSelectMachinesByRental(session.SessionID, session.User.UID, "", companyid);
                    if (machines == null)
                        return new MachineItem[0];

                    return machines.Where(m => m.Hide == false).OrderBy(m => m.ShowName).ToArray();
                }
                else
                    return new MachineItem[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion       

        private object SaveGPSDevice()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    if (!CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.MANAGE_DEVICES))
                        return "";

                    var clientdata = Request.Form["ClientData"];
                    var data = HttpUtility.HtmlDecode(clientdata);
                    DeviceItem deviceitem = JsonConvert.DeserializeObject<DeviceItem>(data);
                    if (string.IsNullOrWhiteSpace(deviceitem.ContractorID))
                        deviceitem.ContractorID = SystemParams.CompanyID;

                    FFSDevice.DeviceInfo device = new FFSDevice.DeviceInfo();
                    Helper.CloneProperty(device, deviceitem);
                    if (deviceitem.PairedAsset != null && deviceitem.PairedAsset.Id > 0)
                        device.PairedAsset = new PairedAssetInfo() { Id = deviceitem.PairedAsset.Id };

                    if (device.Id < 0)
                        device = CreateClient<DeviceProvider>(deviceitem.ContractorID).AddNewDevice(deviceitem.ContractorID, device, session.User.UID);
                    else
                        CreateClient<DeviceProvider>(deviceitem.ContractorID).UpdateDevice(deviceitem.ContractorID, device, session.User.UID);

                    //Device Assignment
                    //List<StringKeyValue> list = new List<StringKeyValue>();
                    //StringKeyValue kv = new StringKeyValue();
                    //kv.Key = device.Id.ToString();
                    //kv.Value = mid;
                    //kv.Tag1 = device.ContractorID;
                    //kv.Tag2 = device.Notes;
                    //list.Add(kv);
                    //MachineServiceClient2 mc = SystemParams.GetMachineServiceClient();
                    //mc.SaveDeviceAssignments(0, list.ToArray());//修改Admin数据库
                    //SaveDeviceAssignments(list[0], session.User.UID);//修改本地数据库                    

                    return new string[] { device.Id.ToString(), "OK" };
                }
                else
                {
                    return "Failed";
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object GetGPSDevices()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string data = Request.Params["ClientData"];
                    string[] ps = JsonConvert.DeserializeObject<string[]>(data);
                    string contractorid = ps[0];
                    if (string.IsNullOrEmpty(contractorid))
                        contractorid = SystemParams.CompanyID;
                    string searchtxt = HttpUtility.HtmlDecode(ps[1]);
                    FFSDevice.DeviceInfo[] devs = CreateClient<DeviceProvider>(contractorid).GetDevices(contractorid, searchtxt);
                    List<DeviceItem> list = new List<DeviceItem>();
                    foreach (var dev in devs)
                    {
                        DeviceItem deviceitem = new DeviceItem();
                        Helper.CloneProperty(deviceitem, dev);

                        if (dev.PairedAsset != null)
                        {
                            deviceitem.PairedAsset = new PairedAssetItem();
                            Helper.CloneProperty(deviceitem.PairedAsset, dev.PairedAsset);
                        }

                        list.Add(deviceitem);
                    }

                    return list.ToArray();
                }
                else
                {
                    return new DeviceItem[0];
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object ChangeGPSContractor()
        {
            try
            {
                var user = GetCurrentUser();
                if (user != null)
                {
                    string data = Request.Params["ClientData"];
                    string[] ps = JsonConvert.DeserializeObject<string[]>(data);
                    long deviceid = -1;
                    long.TryParse(ps[0], out deviceid);
                    string newcontractorid = ps[1];
                    string notes = HttpUtility.HtmlDecode(ps[2]);
                    CreateClient<DeviceProvider>().ChangeDeviceContractor(deviceid, newcontractorid, notes, user.IID);

                    return "OK";
                }
                else
                    return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object GetGPSSources()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    return FFSDevice.DeviceInfo.DEVICESES;
                }
                else
                {
                    return new KeyValuePair<string, string>();
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetDeviceComments()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    string[] ps = JsonConvert.DeserializeObject<string[]>(clientdata);
                    string contractorid = ps[0];
                    if (string.IsNullOrEmpty(contractorid))
                        contractorid = SystemParams.CompanyID;
                    long deviceid = 0;
                    long.TryParse(ps[1], out deviceid);

                    CommentInfo[] comments = CreateClient<DeviceProvider>(contractorid).GetDeviceComments(contractorid, deviceid);
                    List<CommentItem> list = new List<CommentItem>();
                    foreach (var c in comments)
                    {
                        CommentItem citem = new CommentItem();
                        Helper.CloneProperty(citem, c);

                        list.Add(citem);
                    }

                    return list.ToArray();
                }
                else
                {
                    return new CommentItem[0];
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object AddDeviceComment()
        {
            try
            {
                var user = GetCurrentUser();
                if (user != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    string[] ps = JsonConvert.DeserializeObject<string[]>(clientdata);
                    string contractorid = ps[0];
                    if (string.IsNullOrEmpty(contractorid))
                        contractorid = SystemParams.CompanyID;
                    long deviceid = 0;
                    long.TryParse(ps[1], out deviceid);
                    string comment = ps[2];

                    CreateClient<DeviceProvider>(contractorid).SubmitDeviceComment(contractorid, user.IID, deviceid, comment);
                }
                return "";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetMachines()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string searchtxt = HttpUtility.HtmlDecode(Request.Params["ClientData"]);

                    long[] localmachines = null;
                    var user = Users.UserManagement.GetUserByIID(session.User.UID);
                    if (user.UserType < Users.UserTypes.Admin)
                        localmachines = CreateClient<AssetQueryClient>().GetAvailableAssetsForUsers(SystemParams.CompanyID, session.User.UID);

                    MachineServiceClient2 mc = SystemParams.GetMachineServiceClient();
                    MachineInfo2[] machines = mc.GetMachineInfoItemsByCompanyID(SystemParams.CompanyID, searchtxt);
                    List<MachineItem> list = new List<MachineItem>();
                    if (machines != null && machines.Length > 0)
                    {
                        CustomerProvider cust = SystemParams.GetCustomerProvider();
                        CustomerInfo[] companys = cust.GetCustomers("");

                        foreach (var mi in machines)
                        {
                            if (mi.Hide)
                                continue;
                            if (!SystemParams.IsDealer && user.UserType < Users.UserTypes.Admin && !localmachines.Contains(mi.MachineID))
                                continue;//Contractor站点需要获取有权限的机器
                            MachineItem machineitem = new MachineItem();
                            Helper.CloneProperty(machineitem, mi);
                            machineitem.EngineHours = Math.Round(machineitem.EngineHours, 2);
                            CustomerInfo dcompany = companys.FirstOrDefault(m => m.ID == machineitem.DealerID);
                            if (dcompany != null)
                                machineitem.Dealer = dcompany.Name;
                            CustomerInfo ccompany = companys.FirstOrDefault(m => m.ID == machineitem.ContractorID);
                            if (ccompany != null)
                                machineitem.Contractor = ccompany.Name;
                            list.Add(machineitem);
                        }
                    }
                    return list.OrderBy((m) => m.VIN).ToArray();
                }
                else
                    return new MachineItem[0];
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetMachines", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetContractors()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string searchtxt = HttpUtility.HtmlDecode(Request.Params["ClientData"]);

                    CustomerProvider cust = SystemParams.GetCustomerProvider();
                    CustomerInfo[] compnays = cust.GetContractors(SystemParams.CompanyID);

                    List<StringKeyValue> list = new List<StringKeyValue>();
                    foreach (var cm in compnays)
                    {
                        StringKeyValue kv = new StringKeyValue();
                        kv.Key = cm.ID;
                        kv.Value = cm.Name;
                        list.Add(kv);
                    }
                    return list.OrderBy((m) => m.Value).ToArray();

                }
                else
                    return new StringKeyValue[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetMachineTypes()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    AssetType[] types = CreateClient<AssetClassProvider>().GetAssetTypes(SystemParams.CompanyID);
                    types = types.OrderBy((t) => t.Name).ToArray();
                    List<StringKeyValue> list = new List<StringKeyValue>();
                    foreach (AssetType md in types)
                    {
                        StringKeyValue kv = new StringKeyValue();
                        kv.Key = md.ID.ToString();
                        kv.Value = md.Name;
                        list.Add(kv);
                    }
                    return list.ToArray();

                }
                else
                    return new StringKeyValue[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetContractorsByUser()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    CustomerInfo[] companys = GetCompanyIDByUserIID(session.User.UID);
                    if (companys == null || companys.Length <= 0)
                        return new StringKeyValue[0];

                    List<StringKeyValue> list = new List<StringKeyValue>();
                    foreach (var cm in companys)
                    {
                        StringKeyValue kv = new StringKeyValue();
                        kv.Key = cm.ID;
                        kv.Value = cm.Name;
                        list.Add(kv);
                    }

                    return list.OrderBy((m) => m.Value).ToArray();

                }
                else
                    return new StringKeyValue[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        //delear可操作的contractor
        private CustomerInfo[] GetCompanyIDByUserIID(string useriid)
        {
            CustomerProvider cust = SystemParams.GetCustomerProvider();
            CustomerInfo[] allcompany = cust.GetContractors(SystemParams.CompanyID);
            string[] contractors = Acl.GetUserAvailableContractors(useriid);

            if (contractors != null && contractors.Length > 0)
            {
                List<CustomerInfo> list = new List<CustomerInfo>();
                foreach (string id in contractors)
                {
                    if (!string.IsNullOrWhiteSpace(id))
                    {
                        CustomerInfo ci = allcompany.FirstOrDefault(m => m.ID == id);

                        if (ci != null)
                            list.Add(ci);
                    }
                }
                return list.ToArray();
            }
            else
                return null;
        }

        private object SaveMachineGroup()
        {
            if (GetCurrentLoginSession() != null)
            {
                if (!CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.MANAGE_ASSETS))
                    return "";
                string clientdata = Request.Form["ClientData"];
                clientdata = HttpUtility.HtmlDecode(clientdata);
                MachineGroup mg = JsonConvert.DeserializeObject<MachineGroup>(clientdata);

                MachineManagement.SaveMachineGroup(mg);

                return "OK";
            }
            return "Failed";
        }

        private object SaveAssetGroup()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string clientdata = Request.Form["ClientData"];
                    clientdata = HttpUtility.HtmlDecode(clientdata);
                    AssetGroupInfo ag = JsonConvert.DeserializeObject<AssetGroupInfo>(clientdata);
                    if (string.IsNullOrEmpty(ag.Id))
                    {
                        // add
                        ag.Id = Guid.NewGuid().ToString();
                    }
                    CreateClient<AssetDataAdjustClient>().UpdataAssetGroup(SystemParams.CompanyID, ag, session.User.UID);
                    return ag.Id;
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.SaveAssetGroup", ex.Message, ex.ToString());
                return "Failed to save asset group: " + ex.Message;
            }
        }

        private object DeleteMachineGroup()
        {
            if (GetCurrentLoginSession() != null)
            {
                string clientdata = Request.Form["ClientData"];
                string groupID = HttpUtility.HtmlDecode(clientdata);

                int result = MachineManagement.DeleteMachineGroup(groupID);
                if (result == -1)
                    return "-1";

                return "OK";
            }
            return "Failed";
        }

        private object DeleteAssetGroup()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string clientdata = Request.Form["ClientData"];
                    string groupID = HttpUtility.HtmlDecode(clientdata);

                    CreateClient<AssetDataAdjustClient>().DeleteAssetGroup(SystemParams.CompanyID, groupID, session.User.UID);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.DeleteAssetGroup", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetMachineGroups()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {

                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var searchtext = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    FISqlConnection db = null;
                    if (SystemParams.IsDealer)
                    {
                        string connetionstring = SystemParams.GetDbStringByCompany(companyid);
                        db = new FISqlConnection(connetionstring);
                    }

                    var groups = MachineManagement.GetMachineGroups(searchtext, db);
                    return groups.OrderBy((m) => m.GroupName).ToArray();
                }
                else
                    return new MachineItem[0];
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetMachineGroups", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetAssetGroups()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {

                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var searchtext = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    var groups = CreateClient<AssetQueryClient>(companyid).GetAssetGroups(companyid, searchtext, session.User.UID);
                    return groups.OrderBy(g => g.Name).ToArray();
                }
                else
                    return new AssetGroupInfo[0];
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetAssetGroups", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetAssetList()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {

                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var searchtext = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;
                    var hidden = (clientdata[2] == "1");

                    var items = CreateClient<AssetQueryClient>(companyid).GetAssetListItemsByUser(companyid, session.User.UID, searchtext, hidden);
                    return items.OrderBy(g => g.VIN).Select(i => new
                    {
                        i.Id,
                        Name = string.IsNullOrEmpty(i.Name2) ? i.Name : i.Name2,
                        i.VIN,
                        i.MakeName,
                        i.ModelName,
                        i.TypeName,
                        EngineHours = Math.Round(i.EngineHours ?? 0, 2),
                        Odometer = Math.Round(i.Odometer ?? 0, 2)
                    }).ToArray();
                }
                else
                    return new AssetGroupInfo[0];
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetAssetList", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetJobsiteAssetList()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {

                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var companyid = HttpUtility.HtmlDecode(clientdata[0]);
                    var searchtext = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;
                    var jobsiteid = long.Parse(clientdata[2]);

                    var items = CreateClient<JobSiteProvider>(companyid).GetAssetsNotInJobSite(companyid, jobsiteid, searchtext, session.User.UID);
                    return items.Select(i => new
                    {
                        Id = i.AssetId,
                        Name = string.IsNullOrEmpty(i.AssetName2) ? i.AssetName : i.AssetName2,
                        i.VIN,
                        i.MakeName,
                        i.ModelName,
                        i.TypeName,
                        DistanceFromSite = Math.Round(i.DistanceFromSite, 2),
                        i.DistanceUnits,
                        i.Suggested
                    }).ToArray();
                }
                else
                    return new AssetGroupInfo[0];
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetJobsiteAssetList", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetMachineGroupByUser()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var groups = MachineManagement.GetMachineGroupByUser(session.User.UID);

                    return groups.OrderBy((m) => m.GroupName).ToArray();
                }
                else
                    return new MachineItem[0];
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetMachineGroupByUser", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetMachinesByGroup()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"];
                    var groupid = HttpUtility.HtmlDecode(clientdata);

                    var allMachines = MachineManagement.GetMachines(session.SessionID, "", "");
                    var machines = MachineManagement.GetMachineByGroup(groupid);
                    MachineGroupInfoItem mgi = new MachineGroupInfoItem();
                    mgi.AllMachines = allMachines.Where(m => m.Hide == false).OrderBy((m) => m.VIN).ToArray();
                    mgi.Machines = machines.OrderBy((m) => m.VIN).ToArray();

                    return mgi;
                }
                else
                    return "";
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetMachinesByGroup", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetAssetsByGroup()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"];
                    var groupid = HttpUtility.HtmlDecode(clientdata);

                    return CreateClient<AssetQueryClient>().GetAssetsByAssetGroup(SystemParams.CompanyID, groupid);
                }
                else
                    return "";
            }
            catch (Exception ex)
            {
                AddLog("ERROR", "MachineDeviceBasePage.GetAssetsByGroup", ex.Message, ex.ToString());
                return ex.Message;
            }
        }

        private object GetAssetMakes()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var clientdata = Request.Form["ClientData"];
                    var searchtxt = HttpUtility.HtmlDecode(clientdata);

                    AssetMake[] makes = CreateClient<AssetClassProvider>().GetAssetMakes(searchtxt);
                    List<AssetMakeItem> ls = new List<AssetMakeItem>();
                    foreach (var mk in makes)
                    {
                        AssetMakeItem item = new AssetMakeItem();
                        Helper.CloneProperty(item, mk);
                        ls.Add(item);
                    }
                    return ls.OrderBy(m => m.Name).ToArray();

                }
                else
                    return new AssetMakeItem[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object GetAssetModels()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var clientdata = Request.Form["ClientData"];
                    string[] ps = JsonConvert.DeserializeObject<string[]>(clientdata);
                    int makeid = -1;
                    int.TryParse(ps[0], out makeid);
                    var searchtxt = HttpUtility.HtmlDecode(ps[1]);

                    AssetModel[] models = CreateClient<AssetClassProvider>().GetAssetModels(makeid, searchtxt);
                    List<AssetModelItem> ls = new List<AssetModelItem>();
                    foreach (var md in models)
                    {
                        //if (!string.IsNullOrEmpty(md.AddedBy)
                        //    && !md.AddedBy.Equals(SystemParams.CompanyID, StringComparison.OrdinalIgnoreCase))
                        //    continue;
                        AssetModelItem item = new AssetModelItem();
                        Helper.CloneProperty(item, md);
                        if (md.MakeId > 0)
                        {
                            item.MakeID = md.MakeId;
                            item.MakeName = md.MakeName;
                        }
                        if (md.TypeId > 0)
                        {
                            item.TypeID = md.TypeId;
                            item.TypeName = md.TypeName;
                        }
                        ls.Add(item);
                    }

                    return ls.OrderBy(m => m.Name).ToArray();
                }
                else
                    return new AssetModelItem[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object SaveMachineMake()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string clientdata = Request.Form["ClientData"];
                    clientdata = HttpUtility.HtmlDecode(clientdata);
                    AssetMakeItem item = JsonConvert.DeserializeObject<AssetMakeItem>(clientdata);

                    if (item.ID > 0)//界面不允许修改和删除
                        return "OK";

                    CreateClient<AssetClassProvider>().UpdateOrCreateMake(item.ID, item.Name, session.User.UID);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object SaveMachineModel()
        {
            try
            {
                var user = GetCurrentUser();
                bool permission = CheckRight(SystemParams.CompanyID, Feature.MANAGE_ASSETS);
                if (user != null && (user.UserType == Users.UserTypes.SupperAdmin || user.UserType == Users.UserTypes.Admin))
                {
                    string clientdata = Request.Form["ClientData"];
                    clientdata = HttpUtility.HtmlDecode(clientdata);
                    AssetModelItem item = JsonConvert.DeserializeObject<AssetModelItem>(clientdata);

                    if (item.ID > 0)//界面不允许修改和删除
                        return "OK";

                    CreateClient<AssetClassProvider>().UpdateOrCreateModel(item.MakeID, item.ID, item.Name, item.TypeID, user.IID);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object DeleteMachineMake()
        {
            return "OK";//界面不允许修改和删除
            //try
            //{
            //    if (GetCurrentLoginSession() != null)
            //    {
            //        string clientdata = Request.Form["ClientData"];
            //        int id = Convert.ToInt32(HttpUtility.HtmlDecode(clientdata));

            //        MachineServiceClient2 mc = SystemParams.GetMachineServiceClient();
            //        mc.DeleteMachineMake(id);

            //        return "OK";
            //    }
            //    return "Failed";
            //}
            //catch (Exception ex)
            //{
            //    return ex.Message;
            //}
        }

        private object DeleteMachineModel()
        {
            return "OK";//界面不允许修改和删除
            //try
            //{
            //    var user = GetCurrentUser();
            //    if (GetCurrentLoginSession() != null)
            //    {
            //        string clientdata = Request.Form["ClientData"];
            //        int id = Convert.ToInt32(HttpUtility.HtmlDecode(clientdata));

            //        SystemParams.AssetClassClient.DeleteModel(id, user.IID);
            //        //MachineServiceClient2 mc = SystemParams.GetMachineServiceClient();
            //        //mc.DeleteMachineModel(id);

            //        return "OK";
            //    }
            //    return "Failed";
            //}
            //catch (Exception ex)
            //{
            //    return ex.Message;
            //}
        }

        private object GetActiveJobsites()
        {
            try
            {
                JobSiteViewItem[] items = null;
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = Request.Form["ClientData"];
                    string companyid = HttpUtility.HtmlDecode(clientdata);
                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    var jss = CreateClient<JobSiteProvider>(companyid).GetJobSiteItems(companyid, "", false);
                    List<JobSiteViewItem> list = new List<JobSiteViewItem>();
                    foreach (var js in jss)
                    {
                        JobSiteViewItem item = new JobSiteViewItem();
                        item.ID = js.ID;
                        item.Name = js.Name;

                        list.Add(item);
                    }
                    items = list.ToArray();
                }
                else
                {
                    items = new JobSiteViewItem[0];
                }
                return items.OrderBy(m => m.Name);
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetContacts()
        {
            try
            {
                var session = GetCurrentLoginSession();
                Users.UserInfo[] users = null;
                if (session != null)
                {
                    //contact = ContactManagement.GetContacts();
                    string clientdata = Request.Form["ClientData"];
                    string companyid = HttpUtility.HtmlDecode(clientdata);
                    if (string.IsNullOrEmpty(companyid))
                        companyid = SystemParams.CompanyID;

                    users = UserManagement.GetActiveUsers(session.SessionID, companyid);
                    users = users.OrderBy(u => u.DisplayName).ToArray();
                }
                else
                {
                    users = new Users.UserInfo[0];
                }
                return users;
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object ChangeMachineIconFile()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    StringKeyValue kv = JsonConvert.DeserializeObject<StringKeyValue>(clientdata);

                    HttpPostedFile uploadFile = null;
                    byte[] iconfilebyte = null;
                    if (Request.Files.Count > 0)
                    {
                        uploadFile = Request.Files[0];
                        iconfilebyte = ConvertFile2bytes(uploadFile);
                    }
                    FISqlConnection db = null;
                    if (SystemParams.IsDealer)
                    {
                        string companyid = kv.Key;
                        if (string.IsNullOrEmpty(companyid))
                            companyid = SystemParams.CompanyID;
                        string connetionstring = SystemParams.GetDbStringByCompany(companyid);
                        db = new FISqlConnection(connetionstring);
                    }
                    MachineManagement.ChangeMachineIconFile(Convert.ToInt64(kv.Value), uploadFile == null ? "" : uploadFile.FileName, iconfilebyte, db);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #region Asset Attachment

        private object GetAttachments()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    long assetid = Convert.ToInt64(HttpUtility.HtmlDecode(clientdata[1]));
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    AssetAttachmentInfo[] atts = CreateClient<AssetAttachmentProvider>(customerid).GetAttachments(customerid, assetid);
                    if (atts == null || atts.Length <= 0)
                        return new AssetAttachmentItem[0];

                    List<AssetAttachmentItem> list = new List<AssetAttachmentItem>();
                    foreach (AssetAttachmentInfo att in atts)
                    {
                        AssetAttachmentItem item = new AssetAttachmentItem();
                        Helper.CloneProperty(item, att);
                        item.AddedOn = item.AddedOn.AddHours(SystemParams.GetHoursOffset());
                        list.Add(item);
                    }
                    return list.OrderBy(m => m.AddedOn).ToArray();
                }
                else
                    return new AssetAttachmentItem[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object AddAttachment()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    StringKeyValue kv = JsonConvert.DeserializeObject<StringKeyValue>(clientdata);
                    string customerid = kv.Key;
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    HttpPostedFile uploadFile = null;
                    byte[] iconfilebyte = null;
                    if (Request.Files.Count > 0)
                    {
                        uploadFile = Request.Files[0];
                        iconfilebyte = ConvertFile2bytes(uploadFile);
                    }

                    AssetAttachmentInfo att = new AssetAttachmentInfo();
                    att.AssetId = Convert.ToInt64(kv.Value);
                    att.FileName = uploadFile == null ? "" : uploadFile.FileName;
                    att.Notes = kv.Tag1;
                    att.AddedByUserIID = loginsession.User.UID;
                    att.FileData = iconfilebyte;
                    att.VisibleOnWorkOrder = Helper.IsTrue(kv.Tag2);

                    long attid = CreateClient<AssetAttachmentProvider>(customerid).AddAttachment(customerid, att);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object DeleteAttachment()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var attid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    CreateClient<AssetAttachmentProvider>(customerid).Delete(customerid, Convert.ToInt64(attid), loginsession.User.UID);
                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }

        }

        #endregion

        #region Adjust Odometer
        private object GetAssetCurrentOdometer()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    AssetOdometerInfo[] odometers = CreateClient<AssetQueryClient>(customerid).GetAssetCurrentOdometer(customerid, Convert.ToInt64(assetid));
                    if (odometers == null || odometers.Length <= 0)
                        return new OdometerInfo[0];

                    List<OdometerInfo> list = new List<OdometerInfo>();
                    foreach (AssetOdometerInfo odo in odometers)
                    {
                        OdometerInfo item = new OdometerInfo();
                        Helper.CloneProperty(item, odo);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new OdometerInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        private object GetCalampOdometerHistory()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    DateTime now = DateTime.Now.ToUniversalTime();
                    CalampOdoInfo[] odometers = CreateClient<AssetQueryClient>(customerid).GetCalampOdometerHistory(customerid, Convert.ToInt64(assetid), now.AddDays(-6), now);
                    if (odometers == null || odometers.Length <= 0)
                        return new CalampOdoInfo[0];

                    List<CalampOdometerInfo> list = new List<CalampOdometerInfo>();
                    foreach (CalampOdoInfo odo in odometers)
                    {
                        CalampOdometerInfo item = new CalampOdometerInfo();
                        Helper.CloneProperty(item, odo);
                        item.AsofTime_Local = item.AsofTime;
                        item.Gps_Calc = Math.Round(item.Gps_Calc, 2);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new CalampOdoInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetCalampOdometerHistoryPreview()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustOdometerInfo p = JsonConvert.DeserializeObject<AdjustOdometerInfo>(clientdata);
                    if (string.IsNullOrEmpty(p.CustomerID))
                        p.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = p.OdometerDate.AddMinutes(-p.OffsetMinute);

                    CalampOdoInfo[] odometers = CreateClient<AssetQueryClient>(p.CustomerID).GetCalampOdometerHistoryPreview(p.CustomerID, p.AssetID, p.Odometer, p.UOM, utctime);
                    if (odometers == null || odometers.Length <= 0)
                        return new CalampOdoInfo[0];

                    List<CalampOdometerInfo> list = new List<CalampOdometerInfo>();
                    foreach (CalampOdoInfo odo in odometers)
                    {
                        CalampOdometerInfo item = new CalampOdometerInfo();
                        Helper.CloneProperty(item, odo);
                        item.AsofTime_Local = item.AsofTime.AddMinutes(p.OffsetMinute);
                        item.Gps_Calc = Math.Round(item.Gps_Calc, 2);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new CalampOdoInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetPedigreeOdometerHistory()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    DateTime now = DateTime.Now.ToUniversalTime();
                    PedigreeOdoInfo[] odometers = CreateClient<AssetDataAdjustClient>(customerid).GetPedigreeOdometerHistory(customerid, Convert.ToInt64(assetid), now.AddDays(-6), now);
                    if (odometers == null || odometers.Length <= 0)
                        return new CalampOdoInfo[0];

                    List<PedigreeOdometerInfo> list = new List<PedigreeOdometerInfo>();
                    foreach (PedigreeOdoInfo odo in odometers)
                    {
                        PedigreeOdometerInfo item = new PedigreeOdometerInfo();
                        Helper.CloneProperty(item, odo);
                        item.AsofTime_Local = item.AsofTime;
                        item.Gps_Calc = Math.Round(item.Gps_Calc, 2);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new PedigreeOdometerInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetPedigreeOdometerHistoryPreview()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustOdometerInfo p = JsonConvert.DeserializeObject<AdjustOdometerInfo>(clientdata);
                    if (string.IsNullOrEmpty(p.CustomerID))
                        p.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = p.OdometerDate.AddMinutes(-p.OffsetMinute);

                    PedigreeOdoInfo[] odometers = CreateClient<AssetDataAdjustClient>(p.CustomerID).GetPedigreeOdometerHistoryPreview(p.CustomerID, p.AssetID, p.Odometer, p.UOM, utctime);
                    if (odometers == null || odometers.Length <= 0)
                        return new CalampOdoInfo[0];

                    List<PedigreeOdometerInfo> list = new List<PedigreeOdometerInfo>();
                    foreach (PedigreeOdoInfo odo in odometers)
                    {
                        PedigreeOdometerInfo item = new PedigreeOdometerInfo();
                        Helper.CloneProperty(item, odo);
                        item.AsofTime_Local = item.AsofTime.AddMinutes(p.OffsetMinute);
                        item.Gps_Calc = Math.Round(item.Gps_Calc, 2);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new PedigreeOdometerInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }


        private object SaveAdjustOdometer()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustOdometerInfo odo = JsonConvert.DeserializeObject<AdjustOdometerInfo>(clientdata);
                    if (string.IsNullOrEmpty(odo.CustomerID))
                        odo.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = odo.OdometerDate.AddMinutes(-odo.OffsetMinute);//UTC
                    DateTime localtime = utctime.AddHours(SystemParams.GetHoursOffset());

                    bool isallowed = false;
                    if (!loginsession.User.IsForesightUser)
                        isallowed = CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.ASSET_ATTRIBUTE_ADJUSTMENT);
                    //isallowed = UserManagement.CheckUserPermission(loginsession.SessionID, loginsession.User.UID, 20);

                    if (loginsession.User.IsForesightUser || isallowed)
                        CreateClient<AssetDataAdjustClient>(odo.CustomerID).AdjustOdometer(odo.CustomerID, odo.AssetID, localtime, utctime, odo.Odometer, odo.UOM, odo.Notes, loginsession.User.UID);

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion

        #region Add Odometer
        private object AddManuallyInputOdometer()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustOdometerInfo odo = JsonConvert.DeserializeObject<AdjustOdometerInfo>(clientdata);
                    if (string.IsNullOrEmpty(odo.CustomerID))
                        odo.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = odo.OdometerDate.AddMinutes(-odo.OffsetMinute);//UTC

                    bool isallowed = false;
                    if (!loginsession.User.IsForesightUser)
                        isallowed = CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.ASSET_ATTRIBUTE_ADJUSTMENT);
                    //isallowed = UserManagement.CheckUserPermission(loginsession.SessionID, loginsession.User.UID, 20);

                    if (loginsession.User.IsForesightUser || isallowed)
                        CreateClient<AssetDataAdjustClient>(odo.CustomerID).AddManuallyInputOdometer(odo.CustomerID, odo.AssetID, loginsession.User.UID, odo.Odometer, odo.UOM, utctime, odo.Notes);
                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }
        #endregion

        #region Adjust EngineHours

        private object GetAssetCurrentEngineHours()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    AssetEngineHoursInfo[] enginehours = CreateClient<AssetQueryClient>(customerid).GetAssetCurrentEngineHours(customerid, Convert.ToInt64(assetid));
                    if (enginehours == null || enginehours.Length <= 0)
                        return new EngineHoursInfo[0];

                    List<EngineHoursInfo> list = new List<EngineHoursInfo>();
                    foreach (AssetEngineHoursInfo eng in enginehours)
                    {
                        EngineHoursInfo item = new EngineHoursInfo();
                        Helper.CloneProperty(item, eng);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new EngineHoursInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetCalampEngineHoursHistory()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    DateTime now = DateTime.Now.ToUniversalTime();
                    CalampHourInfo[] eninehours = CreateClient<AssetQueryClient>(customerid).GetCalampHourHistory(customerid, Convert.ToInt64(assetid), now.AddDays(-6), now);
                    if (eninehours == null || eninehours.Length <= 0)
                        return new CalampEngineHoursInfo[0];

                    List<CalampEngineHoursInfo> list = new List<CalampEngineHoursInfo>();
                    foreach (CalampHourInfo eng in eninehours)
                    {
                        CalampEngineHoursInfo item = new CalampEngineHoursInfo();
                        Helper.CloneProperty(item, eng);
                        item.AsofTime_Local = item.AsofTime;
                        item.Gps_Calc = Math.Round(item.Gps_Calc, 2);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new CalampEngineHoursInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetCalampEngineHoursHistoryPreview()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustEngineHoursInfo p = JsonConvert.DeserializeObject<AdjustEngineHoursInfo>(clientdata);
                    if (string.IsNullOrEmpty(p.CustomerID))
                        p.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = p.EngineHoursDate.AddMinutes(-p.OffsetMinute);

                    CalampHourInfo[] odometers = CreateClient<AssetQueryClient>(p.CustomerID).GetCalampHourHistoryPreview(p.CustomerID, p.AssetID, p.EngineHours, "Hour", utctime);
                    if (odometers == null || odometers.Length <= 0)
                        return new CalampEngineHoursInfo[0];

                    List<CalampEngineHoursInfo> list = new List<CalampEngineHoursInfo>();
                    foreach (CalampHourInfo odo in odometers)
                    {
                        CalampEngineHoursInfo item = new CalampEngineHoursInfo();
                        Helper.CloneProperty(item, odo);
                        item.AsofTime_Local = item.AsofTime.AddMinutes(p.OffsetMinute);
                        item.Gps_Calc = Math.Round(item.Gps_Calc, 2);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new CalampEngineHoursInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetPedigreeEngineHoursHistory()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    DateTime now = DateTime.Now.ToUniversalTime();
                    PedigreeHourInfo[] eninehours = CreateClient<AssetDataAdjustClient>(customerid).GetPedigreeHourHistory(customerid, Convert.ToInt64(assetid), now.AddDays(-6), now);
                    if (eninehours == null || eninehours.Length <= 0)
                        return new PedigreeEngineHoursInfo[0];

                    List<PedigreeEngineHoursInfo> list = new List<PedigreeEngineHoursInfo>();
                    foreach (PedigreeHourInfo eng in eninehours)
                    {
                        PedigreeEngineHoursInfo item = new PedigreeEngineHoursInfo();
                        Helper.CloneProperty(item, eng);
                        item.AsofTime_Local = item.AsofTime;
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new PedigreeEngineHoursInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetPedigreeEngineHoursHistoryPreview()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustEngineHoursInfo p = JsonConvert.DeserializeObject<AdjustEngineHoursInfo>(clientdata);
                    if (string.IsNullOrEmpty(p.CustomerID))
                        p.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = p.EngineHoursDate.AddMinutes(-p.OffsetMinute);

                    PedigreeHourInfo[] eninehours = CreateClient<AssetDataAdjustClient>(p.CustomerID).GetPedigreeHourHistoryPreview(p.CustomerID, p.AssetID, p.EngineHours, "Hour", utctime);
                    if (eninehours == null || eninehours.Length <= 0)
                        return new PedigreeEngineHoursInfo[0];

                    List<PedigreeEngineHoursInfo> list = new List<PedigreeEngineHoursInfo>();
                    foreach (PedigreeHourInfo odo in eninehours)
                    {
                        PedigreeEngineHoursInfo item = new PedigreeEngineHoursInfo();
                        Helper.CloneProperty(item, odo);
                        item.AsofTime_Local = item.AsofTime.AddMinutes(p.OffsetMinute);
                        item.VBUS_Calc = Math.Round(item.VBUS_Calc, 2);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new PedigreeEngineHoursInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object SaveAdjustEngineHours()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustEngineHoursInfo eng = JsonConvert.DeserializeObject<AdjustEngineHoursInfo>(clientdata);

                    if (string.IsNullOrEmpty(eng.CustomerID))
                        eng.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = eng.EngineHoursDate.AddMinutes(-eng.OffsetMinute);//UTC
                    DateTime localtime = utctime.AddHours(SystemParams.GetHoursOffset());

                    bool isallowed = false;
                    if (!loginsession.User.IsForesightUser)
                        isallowed = CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.ASSET_ATTRIBUTE_ADJUSTMENT);
                    //isallowed = UserManagement.CheckUserPermission(loginsession.SessionID, loginsession.User.UID, 20);
                    if (loginsession.User.IsForesightUser || isallowed)
                        CreateClient<AssetDataAdjustClient>(eng.CustomerID).AdjustEngineHours(eng.CustomerID, eng.AssetID, localtime, utctime, eng.EngineHours, eng.Notes, loginsession.User.UID);
                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion

        #region Add EngineHours
        private object AddManuallyInputEngineHours()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustEngineHoursInfo eng = JsonConvert.DeserializeObject<AdjustEngineHoursInfo>(clientdata);

                    if (string.IsNullOrEmpty(eng.CustomerID))
                        eng.CustomerID = SystemParams.CompanyID;

                    DateTime utctime = eng.EngineHoursDate.AddMinutes(-eng.OffsetMinute);//UTC

                    bool isallowed = false;
                    if (!loginsession.User.IsForesightUser)
                        isallowed = CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.ASSET_ATTRIBUTE_ADJUSTMENT);
                    //isallowed = UserManagement.CheckUserPermission(loginsession.SessionID, loginsession.User.UID, 20);
                    if (loginsession.User.IsForesightUser || isallowed)
                        CreateClient<AssetDataAdjustClient>(eng.CustomerID).AddManuallyInputEngineHours(eng.CustomerID, eng.AssetID, loginsession.User.UID, eng.EngineHours, utctime, eng.Notes);
                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion

        #region Adjust Location

        private object GetAssetCurrentLocation()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    AssetLocationInfo[] locations = CreateClient<AssetQueryClient>(customerid).GetAssetCurrentLocation(customerid, Convert.ToInt64(assetid));
                    if (locations == null || locations.Length <= 0)
                        return new LocationInfo[0];

                    List<LocationInfo> list = new List<LocationInfo>();
                    foreach (AssetLocationInfo loc in locations)
                    {
                        LocationInfo item = new LocationInfo();
                        Helper.CloneProperty(item, loc);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new LocationInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion

        #region Adjust IdleHours

        private object GetAssetCurrentIdleHours()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    AssetIdlehoursInfo[] ihs = CreateClient<AssetQueryClient>(customerid).GetAssetCurrentIdleHours(customerid, Convert.ToInt64(assetid));
                    if (ihs == null || ihs.Length <= 0)
                        return new IdlehoursInfo[0];

                    List<IdlehoursInfo> list = new List<IdlehoursInfo>();
                    foreach (AssetIdlehoursInfo ih in ihs)
                    {
                        IdlehoursInfo item = new IdlehoursInfo();
                        Helper.CloneProperty(item, ih);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new IdlehoursInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion

        #region Adjust FuelUsed

        private object GetAssetCurrentFuelUsed()
        {
            try
            {
                if (GetCurrentLoginSession() != null)
                {
                    var clientdata = Request.Form["ClientData"].Split((char)170);
                    var customerid = HttpUtility.HtmlDecode(clientdata[0]);
                    var assetid = HttpUtility.HtmlDecode(clientdata[1]);
                    if (string.IsNullOrEmpty(customerid))
                        customerid = SystemParams.CompanyID;

                    AssetFuelusedInfo[] fus = CreateClient<AssetQueryClient>(customerid).GetAssetCurrentFuelUsed(customerid, Convert.ToInt64(assetid));
                    if (fus == null || fus.Length <= 0)
                        return new FuelusedInfo[0];

                    List<FuelusedInfo> list = new List<FuelusedInfo>();
                    foreach (AssetFuelusedInfo fu in fus)
                    {
                        FuelusedInfo item = new FuelusedInfo();
                        Helper.CloneProperty(item, fu);
                        list.Add(item);
                    }
                    return list.ToArray();
                }
                else
                    return new FuelusedInfo[0];
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion

        #region Set Primary

        private object ChangePrimaryDataSource()
        {
            try
            {
                var loginsession = GetCurrentLoginSession();
                if (loginsession != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    PrimaryDataSourceInfo item = JsonConvert.DeserializeObject<PrimaryDataSourceInfo>(clientdata);
                    if (string.IsNullOrEmpty(item.CustomerID))
                        item.CustomerID = SystemParams.CompanyID;

                    bool isallowed = false;
                    if (!loginsession.User.IsForesightUser)
                        isallowed = CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.ASSET_ATTRIBUTE_ADJUSTMENT);
                    //isallowed = UserManagement.CheckUserPermission(loginsession.SessionID, loginsession.User.UID, 20);
                    if (loginsession.User.IsForesightUser || isallowed)
                    {
                        if (item.Type == 0)
                        {
                            CreateClient<AssetDataAdjustClient>(item.CustomerID).ChangeOdometerPrimaryDataSource(item.CustomerID, item.AssetID, item.DataSource, item.SubSource, item.Notes, loginsession.User.UID);
                        }
                        else if (item.Type == 1)
                        {
                            CreateClient<AssetDataAdjustClient>(item.CustomerID).ChangeEngineHoursPrimaryDataSource(item.CustomerID, item.AssetID, item.DataSource, item.SubSource, item.Notes, loginsession.User.UID);
                        }
                        else if (item.Type == 2)
                        {
                            CreateClient<AssetDataAdjustClient>(item.CustomerID).ChangeLocationPrimaryDataSource(item.CustomerID, item.AssetID, item.DataSource, item.SubSource, item.Notes, loginsession.User.UID);
                        }
                        else if (item.Type == 3)
                        {
                            CreateClient<AssetDataAdjustClient>(item.CustomerID).ChangeIdlehoursPrimaryDataSource(item.CustomerID, item.AssetID, item.DataSource, item.SubSource, item.Notes, loginsession.User.UID);
                        }
                        else if (item.Type == 4)
                        {
                            CreateClient<AssetDataAdjustClient>(item.CustomerID).ChangeFuelUsedPrimaryDataSource(item.CustomerID, item.AssetID, item.DataSource, item.SubSource, item.Notes, loginsession.User.UID);
                        }
                    }

                    return "OK";
                }
                return "Failed";
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        #endregion


        private object GetMachineDetailURL()
        {
            var clientdata = Context.Request.Params["ClientData"];
            string[] pvs = JsonConvert.DeserializeObject<string[]>(clientdata);
            if (pvs.Length == 2)
            {
                int openMode = 0;
                string url = MachineDetailWorkspace.GenerateMachineDetailWSPURL(pvs[0], pvs[1], out openMode);
                return new string[] { openMode.ToString(), url };
            }
            return "";
        }

        private object GetTimeZones()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    var timezones = SystemParams.GetTimeZones();
                    return timezones;
                }
                else
                {
                    throw new Exception("not login.");
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object CheckOdometerMinnimumTime()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustOdometerInfo p = JsonConvert.DeserializeObject<AdjustOdometerInfo>(clientdata);
                    if (string.IsNullOrEmpty(p.CustomerID))
                        p.CustomerID = SystemParams.CompanyID;

                    DateTime odometertime = p.OdometerDate.AddMinutes(-p.OffsetMinute);

                    AssetOdometerInfo odometer = CreateClient<AssetQueryClient>(p.CustomerID).GetAssetCurrentOdometer(p.CustomerID, p.AssetID).FirstOrDefault(m => m.IsPrimary);
                    if (odometer == null)
                        return true;
                    AssetDataAdjustClient client = CreateClient<AssetDataAdjustClient>(p.CustomerID);
                    DateTime mintime = client.GetAssetOdometerMinimumAsofTime(p.CustomerID, p.AssetID, odometer.DataSource, odometer.SubSource, false);
                    DateTime maxtime = client.GetAssetOdometerMaximumAsofTime(p.CustomerID, p.AssetID, odometer.DataSource, odometer.SubSource, false);

                    if (odometertime < mintime)
                        return 1;
                    if (odometertime > maxtime.AddMinutes(1) || odometertime > DateTime.UtcNow)//10825要求增加1分钟
                        return 2;

                    return 0;
                }
                else
                {
                    throw new Exception("not login.");
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object CheckEngineHourMinimumTime()
        {
            try
            {
                var session = GetCurrentLoginSession();
                if (session != null)
                {
                    string clientdata = HttpUtility.HtmlDecode(Request.Params["ClientData"]);
                    AdjustEngineHoursInfo p = JsonConvert.DeserializeObject<AdjustEngineHoursInfo>(clientdata);
                    if (string.IsNullOrEmpty(p.CustomerID))
                        p.CustomerID = SystemParams.CompanyID;

                    DateTime hourstime = p.EngineHoursDate.AddMinutes(-p.OffsetMinute);

                    AssetEngineHoursInfo hours = CreateClient<AssetQueryClient>(p.CustomerID).GetAssetCurrentEngineHours(p.CustomerID, p.AssetID).FirstOrDefault(m => m.IsPrimary);
                    if (hours == null)//获取当前IsPrimary数据源
                        return true;

                    AssetDataAdjustClient client = CreateClient<AssetDataAdjustClient>(p.CustomerID);
                    DateTime mintime = client.GetAssetEngineHourMinimumAsofTime(p.CustomerID, p.AssetID, hours.DataSource, hours.SubSource, false);
                    DateTime maxtime = client.GetAssetEngineHourMaximumAsofTime(p.CustomerID, p.AssetID, hours.DataSource, hours.SubSource, false);

                    if (hourstime < mintime)
                        return 1;
                    if (hourstime > maxtime.AddMinutes(1) || hourstime > DateTime.UtcNow)
                        return 2;

                    return 0;
                }
                else
                {
                    throw new Exception("not login.");
                }
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private object GetUserPermission()
        {
            try
            {
                var session = GetCurrentLoginSession();
                bool result = false;
                if (session != null)
                {
                    result = CheckRight(SystemParams.CompanyID, Foresight.Fleet.Services.User.Feature.ASSET_ATTRIBUTE_ADJUSTMENT);
                    //result = UserManagement.CheckUserPermission(session.SessionID, session.User.UID, 20);
                }
                return result;
            }
            catch (Exception ex)
            {
                return ex.Message;
            }
        }

        private class MachineGroupInfoItem
        {
            public MachineItem[] AllMachines { get; set; }
            public MachineItem[] Machines { get; set; }
        }

        public class MachineDeviceItem
        {
            public GpsDeviceItem Device { get; set; }
            public MachineItem Machine { get; set; }
        }
    }
}