using Ato.CD.Inbound.Shared;
using Ato.EN.IntegrationServices.CodeGenerationRS;
using Ato.EN.IntegrationServices.CodeGenerationTRT;
using DataContracts;
using System.Collections.Generic;
using System.Runtime.CompilerServices;

namespace Ato.CD.Inbound.TRT
{
    public class CrossFormValidatorRS : ICrossFormValidator
    {
        private RS2018 childDocument { get; set; }

        public List<ProcessMessageDocument> response { get; private set; }

        private TRT2026 parentDocument { get; set; }

        public CrossFormValidatorRS(TRT2026 parent, object child)
        {
            childDocument = (RS2018)child;
            parentDocument = parent;
            response = new List<ProcessMessageDocument>();
        }

        public List<ProcessMessageDocument> ValidateCrossFormRules()
        {
            VRATOGEN402009();
            VRATORS000137();
            VRATORS000138();
            VRATORS000150();

            return response;
        }

        #region Validation Rules

        #region VR.ATO.GEN.402009

        /*  VR.ATO.GEN.402009
        The Entity Identifier on the Schedule must equal the Entity Identifier on the Parent Return

        Legacy Rule Format:
        IF (RP:entity.identifier.TFN <> PARENT RETURN:RP:entity.identifier.TFN)
            RETURN VALIDATION MESSAGE
        ENDIF

        Technical Business Rule Format:
         IF (RP:entity.identifier.TFN <> PARENT RETURN:RP:entity.identifier.TFN)
            RETURN VALIDATION MESSAGE
        ENDIF

        Data Elements:
            
        ^TRT5 = TRT:RP:Identifiers.TaxFileNumber.Identifier
            
        ^RS TFN = RS:RP:Identifiers.TaxFileNumber.Identifier
        */
        [MethodImpl(MethodImplOptions.AggressiveInlining)]
        public virtual void VRATOGEN402009()
        {
            bool assertion = !parentDocument.TRT5.Equals(childDocument.RPIdentifierTFN);

            if (assertion)
            {
                response.Add(new ProcessMessageDocument()
                {
                    Code = "CMN.ATO.GEN.402009",
                    Severity = ProcessMessageSeverity.Error,
                    Description = @"Your supplied TFN does not match the TFN supplied on the form it was submitted with",
                    LongDescription = @"Your supplied TFN does not match the TFN supplied on the parent form it was submitted with",
                    Location = "/xbrli:xbrl/xbrli:context/xbrli:entity/xbrli:identifier",
                    Parameters = new ProcessMessageParameters {
                        new ProcessMessageParameter { Name = "RuleIdentifier", Value = "VR.ATO.GEN.402009" },
                        new ProcessMessageParameter { Name = "TRT5", Value = parentDocument.TRT5 },
                        new ProcessMessageParameter { Name = "RS TFN", Value = childDocument.RPIdentifierTFN }
                    }
                });
            }
        }

        #endregion // VR.ATO.GEN.402009

        #region VR.ATO.RS.000137

        /*  VR.ATO.RS.000137
        Number of weeks property rented must be equal to or less than 52

        Legacy Rule Format:
        IF (PARENT RETURN <> "IITR") AND ([RS25] > 52)  
            RETURN VALIDATION MESSAGE
        ENDIF

        [RS25] = RS:RP:bafot.02.00:RealEstateProperty.RentalWeeks.Count

        Technical Business Rule Format:
        (PARENT <> 'IITR') AND (^RS25 > 52)

        Data Elements:
            
        RP:^RS25 = bafot.02.00:RealEstateProperty.RentalWeeks.Count
        */
        [MethodImpl(MethodImplOptions.AggressiveInlining)]
        public virtual void VRATORS000137()
        {
            bool assertion = childDocument.RS25.GetValueOrDefault() > 52;

            if (assertion)
            {
                response.Add(new ProcessMessageDocument()
                {
                    Code = "CMN.ATO.RS.000137",
                    Severity = ProcessMessageSeverity.Error,
                    Description = @"Number of weeks property rented must not exceed 52",
                    Location = "/xbrli:xbrl/tns:RealEstateProperty.RentalWeeks.Count",
                    Parameters = new ProcessMessageParameters {
                        new ProcessMessageParameter { Name = "RuleIdentifier", Value = "VR.ATO.RS.000137" },
                        new ProcessMessageParameter { Name = "RS27", Value = childDocument.RS27.GetValueOrDefault().ToString() }
                    }
                });
            }
        }

        #endregion // VR.ATO.RS.000137

        #region VR.ATO.RS.000138

        /*  VR.ATO.RS.000138
        Number of weeks property was available for rent this year must be equal to or less than 52

        Legacy Rule Format:
        IF (PARENT RETURN <> "IITR") AND ([RS27] > 52)  
        RETURN VALIDATION MESSAGE
        ENDIF

        [RS27] = RS:RP:bafot.02.00:RealEstateProperty.RentalWeeksAvailable.Count

        Technical Business Rule Format:
        (PARENT <> 'IITR') AND (^RS27 > 52)

        Data Elements:

        RP:^RS27 = bafot.02.00:RealEstateProperty.RentalWeeksAvailable.Count
        */
        [MethodImpl(MethodImplOptions.AggressiveInlining)]
        public virtual void VRATORS000138()
        {
            bool assertion = childDocument.RS27.GetValueOrDefault() > 52;

            if (assertion)
            {
                response.Add(new ProcessMessageDocument()
                {
                    Code = "CMN.ATO.RS.000138",
                    Severity = ProcessMessageSeverity.Error,
                    Description = @"Number of weeks property was available for rent this year cannot exceed 52 weeks",
                    Location = "/xbrli:xbrl/tns:RealEstateProperty.RentalWeeksAvailable.Count",
                    Parameters = new ProcessMessageParameters {
                        new ProcessMessageParameter { Name = "RuleIdentifier", Value = "VR.ATO.RS.000138" },
                        new ProcessMessageParameter { Name = "RS27", Value = childDocument.RS27.GetValueOrDefault().ToString() }
                    }
                });
            }
        }

        #endregion // VR.ATO.RS.000138 

        #region VR.ATO.RS.000150

        /*  VR.ATO.RS.000150
        The Entity name must be the same as the name on the main form

        Legacy Rule Format:
        IF (PARENT RETURN <> SET("IITR","TRTAMI") AND [RS14] <> PARENT RETURN(pyde.xx.xx:OrganisationNameDetails.OrganisationalName.Text (IN TUPLE(xbrli\organisationame2.xx.xx:OrganisationNameDetails) WHERE (pyde.xx.xx:OrganisationNameDetails.OrganisationalType.Code = "MN") AND (pyde.xx.xx:OrganisationNameDetails.Currency.Code = "C")))) OR (PARENT RETURN = SET("IITR","TRTAMI") AND [RS14] <> PARENT RETURN:RP:pyde.xx.xx:OrganisationNameDetails.OrganisationalName.Text)
            RETURN VALIDATION MESSAGE
        ENDIF

        [RS14] = RS:RP:pyde.02.00:OrganisationNameDetails.OrganisationalName.Text

        Technical Business Rule Format:
        (PARENT <> SET("IITR","TRTAMI") AND ^RS14 <> ^ParentORGN.T) OR (PARENT = SET("IITR","TRTAMI") AND ^RS14 <> PARENT:^RS14)

        Data Elements:

        RP:^RS14 = pyde.02.00:OrganisationNameDetails.OrganisationalName.Text
            
        RP:^TRT6 = OrganisationNameDetails.OrganisationalName.Text
        */
        [MethodImpl(MethodImplOptions.AggressiveInlining)]
        public virtual void VRATORS000150()
        {
            bool assertion = !parentDocument.TRT6.Equals(childDocument.RS14);

            if (assertion)
            {
                response.Add(new ProcessMessageDocument
                {
                    Code = "CMN.ATO.RS.000150",
                    Severity = ProcessMessageSeverity.Error,
                    Description = @"The Entity name must be the same as the name on the main form",
                    Location = "/xbrli:xbrl/tns:OrganisationNameDetails.OrganisationalName.Text",
                    Parameters = new ProcessMessageParameters {
                        new ProcessMessageParameter { Name = "RuleIdentifier", Value = "VR.ATO.RS.000150" },
                        new ProcessMessageParameter { Name = "RS14", Value = childDocument.RS14 },
                        new ProcessMessageParameter { Name = "TRT6", Value = parentDocument.TRT6 }
                    }
                });
            }
        }

        #endregion // VR.ATO.RS.000150

        #endregion Validation Rules
    }
}