using System;
using System.Configuration;
using System.Data;
using System.Data.SqlClient;
using System.IO;
using System.Net;
using System.Net.Http;
using System.Net.Http.Headers;
using System.Text.RegularExpressions;
using System.Web.Http;
using DataLinkMesWork2;

namespace WebApi
{
    [RoutePrefix("api/checkimage")]
    public class CheckImageController : ApiController
    {
        private readonly string _defaultRoot = @"D:\\XDCheckImages";

        public class ImageUploadRequest
        {
            public string ProductCode { get; set; }
            public string Remark { get; set; }
            public string ImageBase64 { get; set; }
            public string FileExt { get; set; }
        }

        public class ImageDownloadRequest
        {
            public string Path { get; set; }
        }

        private string GetRootPath()
        {
            string root = null;
            try
            {
                root = ConfigurationManager.AppSettings["XD_CheckImageRootPath"];
            }
            catch
            {
            }

            if (string.IsNullOrWhiteSpace(root))
            {
                root = _defaultRoot;
            }

            return root;
        }

        private string SanitizeForPath(string input)
        {
            if (string.IsNullOrEmpty(input)) return string.Empty;
            char[] invalid = Path.GetInvalidFileNameChars();
            var value = input.Trim();
            foreach (var c in invalid)
            {
                value = value.Replace(c.ToString(), string.Empty);
            }
            value = value.Replace("/", string.Empty).Replace("\\", string.Empty);
            return value;
        }

        private string GetExtensionFromRequest(ImageUploadRequest request)
        {
            string ext = ".jpg";
            if (request == null) return ext;

            if (!string.IsNullOrWhiteSpace(request.FileExt))
            {
                ext = request.FileExt.Trim();
                if (!ext.StartsWith("."))
                {
                    ext = "." + ext;
                }
                return ext;
            }

            if (!string.IsNullOrWhiteSpace(request.ImageBase64) &&
                request.ImageBase64.StartsWith("data:", StringComparison.OrdinalIgnoreCase))
            {
                try
                {
                    var match = Regex.Match(request.ImageBase64, "^data:(?<mime>[^;]+);base64,", RegexOptions.IgnoreCase);
                    if (match.Success)
                    {
                        var mime = match.Groups["mime"].Value.ToLowerInvariant();
                        if (mime == "image/png") return ".png";
                        if (mime == "image/gif") return ".gif";
                        if (mime == "image/bmp") return ".bmp";
                        if (mime == "image/webp") return ".webp";
                        if (mime == "image/tiff" || mime == "image/tif") return ".tif";
                        if (mime == "image/jpeg" || mime == "image/jpg") return ".jpg";
                    }
                }
                catch
                {
                }
            }

            return ext;
        }

        private string GetContentType(string fileName)
        {
            var extension = Path.GetExtension(fileName).ToLowerInvariant();
            if (extension == ".bmp") return "image/bmp";
            if (extension == ".jpg" || extension == ".jpeg") return "image/jpeg";
            if (extension == ".png") return "image/png";
            if (extension == ".gif") return "image/gif";
            if (extension == ".tiff" || extension == ".tif") return "image/tiff";
            if (extension == ".webp") return "image/webp";
            return "application/octet-stream";
        }

        private bool IsPathSafe(string fullPath)
        {
            try
            {
                var basePath = Path.GetFullPath(GetRootPath());
                var requestedPath = Path.GetFullPath(fullPath);
                return requestedPath.StartsWith(basePath, StringComparison.OrdinalIgnoreCase);
            }
            catch
            {
                return false;
            }
        }

        [HttpPost]
        [Route("upload")]
        public IHttpActionResult Upload([FromBody] ImageUploadRequest request)
        {
            try
            {
                if (request == null ||
                    string.IsNullOrWhiteSpace(request.ProductCode) ||
                    string.IsNullOrWhiteSpace(request.Remark) ||
                    string.IsNullOrWhiteSpace(request.ImageBase64))
                {
                    return Ok(new { success = false, message = "产品编号、备注和图片不能为空" });
                }

                string productCode = SanitizeForPath(request.ProductCode);
                string remark = SanitizeForPath(request.Remark);
                if (string.IsNullOrEmpty(productCode))
                {
                    return Ok(new { success = false, message = "产品编号无效" });
                }

                string ext = GetExtensionFromRequest(request);
                string base64 = request.ImageBase64.Trim();
                int commaIndex = base64.IndexOf(',');
                if (base64.StartsWith("data:", StringComparison.OrdinalIgnoreCase) && commaIndex > 0)
                {
                    base64 = base64.Substring(commaIndex + 1);
                }

                byte[] bytes;
                try
                {
                    bytes = Convert.FromBase64String(base64);
                }
                catch
                {
                    return Ok(new { success = false, message = "图片数据格式错误" });
                }

                var now = DateTime.Now;
                string datePart = now.ToString("yyyyMMdd");
                string timePart = now.ToString("HHmmss");

                string fileName = string.Format("{0}-{1}-{2}{3}", timePart, productCode, remark, ext);
                string relativePath = string.Format("/{0}/{1}", datePart, fileName);

                string root = GetRootPath();
                string directory = Path.Combine(root, datePart);
                if (!Directory.Exists(directory))
                {
                    Directory.CreateDirectory(directory);
                }

                string fullPath = Path.Combine(directory, fileName);

                if (!IsPathSafe(fullPath))
                {
                    return Ok(new { success = false, message = "目标路径不安全" });
                }

                File.WriteAllBytes(fullPath, bytes);

                string errorMessage;
                var sqlParameters = new SqlParameter[4];
                sqlParameters[0] = new SqlParameter("@产品编号", SqlDbType.NVarChar, 500) { Value = (object)request.ProductCode ?? DBNull.Value };
                sqlParameters[1] = new SqlParameter("@备注", SqlDbType.NVarChar, 500) { Value = (object)request.Remark ?? DBNull.Value };
                sqlParameters[2] = new SqlParameter("@图片路径", SqlDbType.NVarChar, 500) { Value = (object)relativePath ?? DBNull.Value };
                sqlParameters[3] = new SqlParameter("@图片名称", SqlDbType.NVarChar, 500) { Value = (object)fileName ?? DBNull.Value };

                bool dbOk = DataAccess2.ExecuteStoredProcedure("XD_检测图片上传_增加", ref sqlParameters, out errorMessage);
                if (!dbOk)
                {
                    return Ok(new { success = false, message = "图片已保存，但写入数据库失败:" + errorMessage });
                }

                return Ok(new
                {
                    success = true,
                    message = "上传成功",
                    data = new
                    {
                        产品编号 = request.ProductCode,
                        备注 = request.Remark,
                        图片路径 = relativePath,
                        图片名称 = fileName
                    }
                });
            }
            catch (Exception ex)
            {
                return Ok(new { success = false, message = "服务器错误:" + ex.Message });
            }
        }

        [HttpPost]
        [Route("download")]
        public IHttpActionResult Download([FromBody] ImageDownloadRequest request)
        {
            try
            {
                if (request == null || string.IsNullOrWhiteSpace(request.Path))
                {
                    return Ok(new { success = false, message = "文件路径不能为空" });
                }

                string root = GetRootPath();
                string relative = request.Path.Replace("\\", "/").Trim();
                if (relative.StartsWith("/"))
                {
                    relative = relative.Substring(1);
                }
                string fullPath = Path.Combine(root, relative.Replace('/', Path.DirectorySeparatorChar));

                if (!IsPathSafe(fullPath) || !File.Exists(fullPath))
                {
                    return Ok(new { success = false, message = "文件不存在" });
                }

                var fileInfo = new FileInfo(fullPath);
                var contentType = GetContentType(fileInfo.Name);

                var response = new HttpResponseMessage(HttpStatusCode.OK)
                {
                    Content = new StreamContent(new FileStream(fullPath, FileMode.Open, FileAccess.Read, FileShare.Read))
                };
                response.Content.Headers.ContentType = new MediaTypeHeaderValue(contentType);
                response.Content.Headers.ContentDisposition = new ContentDispositionHeaderValue("inline")
                {
                    FileName = fileInfo.Name
                };

                return ResponseMessage(response);
            }
            catch (Exception ex)
            {
                return Ok(new { success = false, message = "下载文件失败:" + ex.Message });
            }
        }
    }
}
