using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Xml;

namespace PXP.Crawler.API.Utils
{
    public sealed class Null
    {
        public static string XmlAttributeValueFromDBNull(XmlAttribute xAttr)
        {
            if (xAttr == null)
            {
                return "";
            }
            else
            {
                return xAttr.Value;
            }
        }

        public static object NullDBNull(object val)
        {
            if (val == null)
            {
                return System.DBNull.Value;
            }
            else
            {
                return val;
            }
        }

        public static DateTime NullDateTime(object val)
        {
            return NullDateTime(val, DateTime.Now);
        }

        public static DateTime NullDateTime(object val, DateTime def)
        {
            if (IsDBNull(val))
            {
                return def;
            }
            if (val is DateTime)
            {
                return (DateTime)val;
            }
            try
            {
                return Convert.ToDateTime(val);
            }
            catch (ArgumentException ae)
            {
                return def;
            }
        }

        public static bool? NullBoolFromXmlElement(XmlElement el)
        {
            if (el != null)
            {
                bool res;
                if (bool.TryParse(el.InnerText, out res))
                {
                    return res;
                }
            }

            return null;
        }

        public static string NullStringFromXmlElement(XmlElement el)
        {
            if (el == null)
            {
                return null;
            }

            string es = StringFromNullXmlElement(el);
            if (es.Length > 0)
            {
                return es;
            }

            return null;
        }

        public static double? NullDoubleFromXmlElement(XmlElement el)
        {
            if (el == null)
            {
                return null;
            }

            string els = StringFromNullXmlElement(el);
            if (CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator == ",")
            {
                els = els.Replace(".", CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator);
            }
            else
            {
                els = els.Replace(",", CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator);
            }

            if (els.Length == 0)
            {
                return null;
            }
            else
            {
                double dval;
                if (double.TryParse(el.InnerText, NumberStyles.Integer, CultureInfo.CurrentCulture, out dval))
                {
                    return dval;
                }
                else
                {
                    return null;
                }
            }
        }

        public static int? NullIntFromXmlElement(XmlElement el)
        {
            if (el == null)
            {
                return null;
            }

            string els = StringFromNullXmlElement(el);
            if (CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator == ",")
            {
                els = els.Replace(".", CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator);
            }
            else
            {
                els = els.Replace(",", CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator);
            }

            if (els.Length == 0)
            {
                return null;
            }
            else
            {
                double dval;
                if (double.TryParse(el.InnerText, NumberStyles.Integer, CultureInfo.CurrentCulture, out dval))
                {
                    return Convert.ToInt32(dval);
                }
                else
                {
                    return null;
                }
            }
        }

        public static int IntFromNullXmlElement(XmlElement el)
        {
            string els = StringFromNullXmlElement(el);
            if (CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator == ",")
            {
                els = els.Replace(".", CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator);
            }
            else
            {
                els = els.Replace(",", CultureInfo.CurrentCulture.NumberFormat.NumberDecimalSeparator);
            }

            if (els.Length == 0)
            {
                return 0;
            }
            else
            {
                double dval;
                if (double.TryParse(el.InnerText, NumberStyles.Integer, CultureInfo.CurrentCulture, out dval))
                {
                    return Convert.ToInt32(dval);
                }
                else
                {
                    return 0;
                }
            }
        }

        public static string StringFromNullXmlAttribute(XmlAttribute at)
        {
            if (at == null)
            {
                return "";
            }

            return at.Value;
        }

        public static string StringFromNullXmlElement(XmlElement el)
        {
            return StringFromNullXmlElement(el, "");
        }

        public static string StringFromNullXmlElement(XmlElement el, string defaultValue)
        {
            if (el == null)
            {
                return defaultValue;
            }

            return el.InnerText;
        }

        public static string StringFromDBNull(object val)
        {
            return StringFromDBNull(val, "", false);
        }

        public static string StringFromDBNull(object val, string defaultValue, bool defaultIfEmpty)
        {
            if (IsDBNull(val))
                return defaultValue;

            if (defaultIfEmpty)
                if (val.ToString().Trim().Length == 0)
                    return defaultValue;

            return Convert.ToString(val);
        }

        public static bool BoolFromDBNull(object val)
        {
            return BoolFromDBNull(val, false);
        }

        public static bool BoolFromDBNull(object val, bool defaultValue)
        {
            if (IsDBNull(val))
                return defaultValue;

            return Convert.ToBoolean(val);
        }

        public static object NullDBNull(int? val)
        {
            if (val == null)
                return System.DBNull.Value;
            return val;
        }

        public static int IntFromDBNull(object val)
        {
            if (IsDBNull(val))
                return 0;

            return Convert.ToInt32(val);
        }

        public static int IntFromDBNull(object val, int defaultValue)
        {
            if (IsDBNull(val))
                return defaultValue;

            return Convert.ToInt32(val);
        }
        public static int IntFromDBNull( ref Dictionary<string, string> parameters, string keyName, int defaultValue)
        {
            if (!parameters.ContainsKey(keyName))
                return defaultValue;

            object pv = parameters[keyName];

            if (IsDBNull(pv))
                return defaultValue;

            return Convert.ToInt32(pv);
        }

        public static float SingleFromDBNull(object val)
        {
            if (IsDBNull(val))
                return 0;

            return Convert.ToSingle(val);
        }

        public static bool IsDBNull(object val)
        {
            if (val == null)
            {
                return true;
            }
            if (val == DBNull.Value)
            {
                return true;
            }
            return false;
        }

        public static bool IsDBNullEmpty(object val)
        {
            if (IsDBNull(val))
            {
                return true;
            }
            if (val is string)
            {
                if (((string)val).Trim().Length == 0)
                {
                    return true;
                }
            }
            return false;
        }

        public static bool DBNullBool(object val)
        {
            if (val == null)
            {
                return false;
            }
            else if (val == DBNull.Value)
            {
                return false;
            }
            else
            {
                return Convert.ToBoolean(val);
            }
        }

        public static Object DBNullStringEmpty(string val)
        {
            if (val.Trim().Length == 0)
                return DBNull.Value;
            return val;
        }
    }
}
