public ServerStatus_Result ServerStatus_Classic(string OPCURL)
        {
            ServerStatus_Result ServerStatus_Result = new ServerStatus_Result();

            Opc.Da.Server ConnectedOPDAServer;
            try
            {
                ConnectedOPDAServer = ConnectToOPCServer(OPCURL);
                if (ConnectedOPDAServer == null)
                {
                    return new ServerStatus_Result()
                           {
                               success = false, error = "Fail to Connect to OPC Server '" + OPCURL + "'"
                           }
                }
                ;
                ServerStatus serverStatus = ConnectedOPDAServer.GetStatus();
                ServerStatus_Result.result  = (serverStatus.ServerState == serverState.running);
                ServerStatus_Result.success = true;
                return(ServerStatus_Result);
            }
            catch (Exception ex)
            {
                return(new ServerStatus_Result()
                {
                    success = false, error = ex.ToString()
                });
            }
        }
        public BrowseTag_Classic_Result BrowseTag_Classic(string OPCURL, string ItemId)
        {
            BrowseTag_Classic_Result BrowseTag_Classic_Result = new BrowseTag_Classic_Result();

            Opc.Da.Server ConnectedOPDAServer;
            try
            {
                ConnectedOPDAServer = ConnectToOPCServer(OPCURL);
                if (ConnectedOPDAServer == null)
                {
                    return new BrowseTag_Classic_Result()
                           {
                               success = false, result = null, error = "Fail to Connect to OPC Server '" + OPCURL + "'"
                           }
                }
                ;

                ItemPropertyCollection[] PropertiesCollections = ConnectedOPDAServer.GetProperties(
                    new ItemIdentifier[] { new ItemIdentifier(ItemId) },
                    new Opc.Da.PropertyID[] { new PropertyID(1), new PropertyID(2), new PropertyID(3), new PropertyID(4),
                                              new PropertyID(5), new PropertyID(100), new PropertyID(101) },
                    true); // begin a browse.

                if (PropertiesCollections != null)
                {
                    foreach (ItemPropertyCollection Properties in PropertiesCollections)
                    {
                        foreach (Opc.Da.ItemProperty property in Properties)
                        {
                            if (!property.ResultID.Succeeded() || property.Value == null)
                            {
                                continue;
                            }
                            string PropertyName = property.ID.ToPropertyName();
                            if (PropertyName == null)
                            {
                                continue;
                            }

                            //Create a Property Node (Can be Value, Data Type,etc)
                            PropertyNode PN = new PropertyNode(PropertyName, property.Description, Opc.Convert.ToString(property.Value), property.ResultID.Succeeded());

                            //For certain properties, there are special case handlers
                            switch (property.ID.Code)
                            {
                            case 1:     //Data Type
                                System.Type PropertyType = property.Value.GetType();
                                //if (PropertyType.FullName == "System.RuntimeType")
                                //{
                                //    System.Type TTT = (System.Type)(property.Value);
                                //    var DT = TTT.ToString();
                                //    var DTComp = DT.Split('.');
                                //    AddedNode.DataTypeString = DTComp.Last();
                                //}
                                //BrowseTag_Classic_Result.DataType = PropertyType;
                                BrowseTag_Classic_Result.result.DataTypeString = PropertyType.Name;
                                break;

                            case 2:     //Value
                                if (property.Value is Array)
                                {
                                    BrowseTag_Classic_Result.result.Value = "";
                                    foreach (object element in (Array)property.Value)
                                    {
                                        string ValueElement = Opc.Convert.ToString(element);
                                        BrowseTag_Classic_Result.result.Value += ValueElement + ",";
                                        PN.ArrayValues.Add(new ArrayValue(ValueElement));
                                    }
                                    if (BrowseTag_Classic_Result.result.Value != null)
                                    {
                                        BrowseTag_Classic_Result.result.Value = BrowseTag_Classic_Result.result.Value.RemoveLastCharacter();
                                    }
                                }
                                else
                                {
                                    BrowseTag_Classic_Result.result.Value = PN.Value;
                                }
                                break;

                            case 3:     //Quality
                                Quality Q = (Quality)(property.Value);
                                BrowseTag_Classic_Result.result.Quality = (Q.QualityBits == qualityBits.good || Q.QualityBits == qualityBits.goodLocalOverride);
                                break;

                            case 5:     //Timestamp
                                if (property.Value is accessRights AR)
                                {
                                    BrowseTag_Classic_Result.result.AccessLevel = AR.ToAccessLevel();
                                }
                                break;

                            case 100:     //Engineering Unit
                                BrowseTag_Classic_Result.result.EngineeringUnit = PN.Value.ToString();
                                break;

                            case 101:     //Description
                                BrowseTag_Classic_Result.result.Description = PN.Value.ToString();
                                break;
                            }
                            BrowseTag_Classic_Result.result.properties.Add(PN);
                        }
                    }
                    BrowseTag_Classic_Result.success = true;

                    return(BrowseTag_Classic_Result);
                }
            }
            catch (Exception ex)
            {
                return(new BrowseTag_Classic_Result()
                {
                    success = false, error = ex.ToString()
                });
            }
            return(new BrowseTag_Classic_Result()
            {
                success = false, error = ""
            });
        }
        public BrowseGeneric_Result BrowseBranch_Classic(string OPCURL, string ItemId)
        {
            Exception       Exception = null;
            List <BaseNode> Output    = new List <BaseNode>();

            Opc.Da.Server ConnectedOPDAServer;
            try
            {
                ConnectedOPDAServer = ConnectToOPCServer(OPCURL);
                if (ConnectedOPDAServer == null)
                {
                    Exception = new Exception("Fail to Connect to OPC Server '" + OPCURL + "'");
                    return(new BrowseGeneric_Result()
                    {
                        success = false, result = null, error = Exception.ToString()
                    });
                }
            }
            catch (Exception ex)
            {
                return(new BrowseGeneric_Result()
                {
                    success = false, result = null, error = ex.ToString()
                });
            }


            Opc.Da.BrowseElement[] Elements = null;
            try
            {
                if (ItemId == null)
                {
                    Elements = ConnectedOPDAServer.Browse(null, _BrowseFilters, out Opc.Da.BrowsePosition position);
                }
                else
                {
                    Elements = ConnectedOPDAServer.Browse(new ItemIdentifier(null, ItemId), _BrowseFilters, out Opc.Da.BrowsePosition position); // begin a browse.
                    if (Elements == null)
                    {
                        Elements = ConnectedOPDAServer.Browse(new ItemIdentifier(ItemId, null), _BrowseFilters, out position);                   // begin a browse.
                    }
                }
                if (Elements != null)
                {
                    foreach (Opc.Da.BrowseElement Element in Elements)
                    {
                        if (Element.IsItem) //If it is an OPC Tag Item
                        {
                            TagNode AddedNode = null;
                            if (!string.IsNullOrWhiteSpace(Element.ItemName))
                            {
                                Output.Add(AddedNode = new TagNode(Element.ItemName, OPCURL));
                            }
                            else if (!string.IsNullOrWhiteSpace(Element.ItemPath))
                            {
                                Output.Add(AddedNode = new TagNode(Element.ItemPath, OPCURL));
                            }
                            else if (!string.IsNullOrWhiteSpace(Element.Name))
                            {
                                Output.Add(AddedNode = new TagNode(Element.Name, OPCURL));
                            }
                            if (AddedNode != null && Element.Properties != null)
                            {
                                foreach (Opc.Da.ItemProperty property in Element.Properties)
                                {
                                    if (!property.ResultID.Succeeded() || property.Value == null)
                                    {
                                        continue;
                                    }
                                    string PropertyName = property.ID.ToPropertyName();
                                    if (PropertyName == null)
                                    {
                                        continue;
                                    }
                                    //Create a Property Node (Can be Value, Data Type,etc)
                                    PropertyNode PN = new PropertyNode(PropertyName, property.Description, Opc.Convert.ToString(property.Value), property.ResultID.Succeeded());

                                    //For certain properties, there is special case
                                    switch (property.ID.Code)
                                    {
                                    case 1:     //Data Type
                                        System.Type PropertyType = property.Value.GetType();
                                        if (PropertyType.FullName == "System.RuntimeType")
                                        {
                                            System.Type TTT    = (System.Type)(property.Value);
                                            var         DT     = TTT.ToString();
                                            var         DTComp = DT.Split('.');
                                            AddedNode.DataTypeString = DTComp.Last();
                                        }
                                        break;

                                    case 2:     //Value
                                        if (property.Value is Array)
                                        {
                                            foreach (object element in (Array)property.Value)
                                            {
                                                string ValueElement = Opc.Convert.ToString(element);
                                                AddedNode.Value += ValueElement + ",";
                                                PN.ArrayValues.Add(new ArrayValue(ValueElement));
                                            }
                                            if (AddedNode.Value != null)
                                            {
                                                AddedNode.Value = AddedNode.Value.RemoveLastCharacter();
                                            }
                                        }
                                        else
                                        {
                                            AddedNode.Value = PN.Value;
                                        }
                                        break;

                                    case 3:     //Quality
                                        Opc.Da.Quality Q = (Opc.Da.Quality)(property.Value);
                                        AddedNode.QualityOK = (Q.QualityBits == Opc.Da.qualityBits.good || Q.QualityBits == Opc.Da.qualityBits.goodLocalOverride);
                                        break;

                                    case 5:     //Timestamp
                                        if (property.Value is Opc.Da.accessRights AR)
                                        {
                                            AddedNode.AccessLevel = AR.ToAccessLevel();
                                        }
                                        break;

                                    case 100:     //Engineering Unit
                                        AddedNode.EngineeringUnit = PN.Value.ToString();
                                        break;

                                    case 101:     //Description
                                        AddedNode.Description = PN.Value.ToString();
                                        break;
                                    }
                                    AddedNode.Properties.Add(PN);
                                }
                            }
                        }
                        else //If it is a Branch
                        {
                            BranchNode AddedNode = null;
                            if (!string.IsNullOrWhiteSpace(Element.ItemName))
                            {
                                Output.Add(AddedNode = new BranchNode(Element.ItemName, OPCURL));
                            }
                            else if (!string.IsNullOrWhiteSpace(Element.ItemPath))
                            {
                                Output.Add(AddedNode = new BranchNode(Element.ItemPath, OPCURL));
                            }
                            else if (!string.IsNullOrWhiteSpace(Element.Name))
                            {
                                Output.Add(AddedNode = new BranchNode(Element.Name, OPCURL));
                            }
                        }
                    }
                    return(new BrowseGeneric_Result()
                    {
                        success = true, result = Output
                    });
                }
            }
            catch (Exception ex)
            {
                Exception = ex;
            }
            return(new BrowseGeneric_Result()
            {
                success = false, result = null, error = Exception?.ToString()
            });
        }