using System.Collections.Generic;
using System.Linq;
using System.Text.Json.Serialization;
using isnd.Data.Catalog;

namespace isnd
{
    class WebApiReferenceHandler : ReferenceHandler
{
    public WebApiReferenceHandler() => Reset();
    private ReferenceResolver? _rootedResolver;
    public override ReferenceResolver CreateResolver() => _rootedResolver!;
    public void Reset() => _rootedResolver = new WebApiReferenceResolver();
}

    public class WebApiReferenceResolver : ReferenceResolver
    {
        private int delautIdCounter;

        Dictionary<string, HappyIdOwner> HappyIdOwners { get; set; } 

        Dictionary<int,object> Objects {get; set;} 

        public WebApiReferenceResolver()
        {
            delautIdCounter = 0;
            HappyIdOwners = new Dictionary<string, HappyIdOwner>();
            Objects = new Dictionary<int, object>();
        }

        public override void AddReference(string referenceId, object value)
        {
            if (value is HappyIdOwner)
            {
                string hoi = (value as HappyIdOwner).GetId();
                if (HappyIdOwners.ContainsKey(hoi))
                {
                    return;
                }
                HappyIdOwners[hoi] = value as HappyIdOwner;
            }
            else
            {
                if (Objects.ContainsValue(value))
                {
                    return;
                }

                delautIdCounter++;
                Objects[delautIdCounter] = value;
            } 
        }

        public override string GetReference(object value, out bool alreadyExists)
        {
            if (value is HappyIdOwner)
            {
                string oid = (value as HappyIdOwner).GetId();
                if (oid == null)
                    throw new System.Exception("HappyIdOwner Id property is null");
                if (HappyIdOwners.ContainsKey(oid))
                {
                    alreadyExists=true;
                    return oid;
                }
                alreadyExists=false;
                AddReference(oid, value);
                return oid;
            }
            alreadyExists=false;
           
            if (Objects.ContainsValue(value))
            {
                alreadyExists=true;
                return Objects.First( ode => ode.Value ==value).Key.ToString();
            }
            alreadyExists=false;
            delautIdCounter++;
            Objects[delautIdCounter]=value;
            return delautIdCounter.ToString();
        }

        public override object ResolveReference(string referenceId)
        {
            if (HappyIdOwners.ContainsKey(referenceId))
                return HappyIdOwners[referenceId];
            int refNId;
            if (int.TryParse(referenceId, out refNId))
            {
                if (Objects.ContainsKey(refNId))
                {
                    return Objects[refNId];
                }
            }
            return null;
        }
    }
}