Wednesday 15 February 2017

C# Interface

What is Interface in C#?
A) It is as simple as Class with out implementation. Only declaration of the events, methods, properties, mean .
All the methods and events which are there in interface should be inherited in  the class and should be implemented for each members in the interface.


Why Interface in C#?
A) in .Net we can't do multiple inheritance.
Ex:

class Honda
{
    //Honda Relations--Members
}

class Toyota{
    //Toyota Relations--Members
}

class
 myCarHonda,Toyota //Multiple Inheritance

{
    //Accessing both Relations class members.}

When you compile above code, we will get error.
Class " "cannot have multiple base classes: ".....Honda" and "Toyota"

The reason was .Net doesn't support multiple inheritance


So Interface is the option for multiple inheritance

Ex:
 ODDEVEN.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace InterFaceDemo
{
    interface IOne
    {
        void ONE();//Pure Abstract Method Signature
    }
    interface ITwo
    {
        void TWO();
    }
    interface IThree:IOne
    {
        void THREE();
    }
    interface IFour
    {
        void FOUR();
    }
    interface IFive:IThree
    {
        void FIVE();
    }
    interface IEVEN:ITwo,IFour
    {

    }
    class ODDEVEN:IEVEN,IFive//Must Implement all the abstract method, in Derived class.
    {
        public void ONE()//Implementation of Abstract Method.
        {
            Console.WriteLine("This is ONE");
        }
        public void TWO()
        {
            Console.WriteLine("This is TWO");
        }
        public void THREE()
        {
            Console.WriteLine("This is THERE");
        }
        public void FOUR()
        {
            Console.WriteLine("This is FOUR");
        }
        public void FIVE()
        {
            Console.WriteLine("This is FIVE");
        }

    }
}

Program.cs
 
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace InterFaceDemo
{
    class Program
    {
        static void Main(string[] args)
        {
            Console.WriteLine("This is ODD");
            IFive obj1 = new ODDEVEN();
            obj1.ONE();
            obj1.THREE();
            obj1.FIVE();


            Console.WriteLine("\n\nThis is EVEN");
            IEVEN obj2 = new ODDEVEN();
            obj2.TWO();
            obj2.FOUR();


            Console.ReadLine();
        }
    }
}
-----------------

//if( System.Diagnostics.Debugger.Launch() ) System.Diagnostics.Debugger.Break();
        var externalOwner = this.getProperty("external_owner");
        if (!string.IsNullOrEmpty(externalOwner) && externalOwner == "Aras.Document.MS-Office")
        {
            string partId = this.getID();
            try
            {
                IExcelReader excelReader = new ExcelReader(new DataAccessLayer(this.getInnovator()), new ExcelManager());
                excelReader.Extract(partId);
            }
            catch (Exception ex)
            {
                return this.getInnovator().newError(string.Format(CultureInfo.InvariantCulture, "Error occured while reading of excel file. Message: {0}", ex.Message));
            }
            finally
            {

            }
        }
        return this;
    }

    // IExcelApi is added to support unit testing
    internal interface IExcelManager
    {
        List<ExcelDataSet> ReadSheetViaDefindNames(string fname);
    }

    internal class ExcelManager : IExcelManager
    {
        public List<ExcelDataSet> ReadSheetViaDefindNames(string fname)
        {
            var data = new List<ExcelDataSet>();
            using (DocumentFormat.OpenXml.Packaging.SpreadsheetDocument doc = DocumentFormat.OpenXml.Packaging.SpreadsheetDocument.Open(fname, false))
            {
                data = this.Read(doc);
            }
            return data;
        }
        private List<ExcelDataSet> Read(DocumentFormat.OpenXml.Packaging.SpreadsheetDocument doc)
        {
            var data = new List<ExcelDataSet>();

            var definedNames = GetDefinedNames(doc.WorkbookPart);

            foreach (DefinedNameVal definedName in definedNames)
            {
                var worksheetPart = GetWorkSheetPart(doc.WorkbookPart, definedName);
                var cellValue = GetCellValue(worksheetPart, doc.WorkbookPart.SharedStringTablePart, definedName.StartColumn, definedName.StartRow);

                data.Add(new ExcelDataSet { Name = definedName.Key, DisplayText = cellValue });
            }
            return data;
        }
        private List<DefinedNameVal> GetDefinedNames(DocumentFormat.OpenXml.Packaging.WorkbookPart workbookPart)
        {
            List<DefinedNameVal> definedNames = new List<DefinedNameVal>();
            foreach (DocumentFormat.OpenXml.Spreadsheet.DefinedName name in workbookPart.Workbook.GetFirstChild<DocumentFormat.OpenXml.Spreadsheet.DefinedNames>())
            {
                //Parse defined name string…
                string key = name.Name;
                string reference = name.InnerText;
                string sheetName = reference.Split('!')[0];
                sheetName = sheetName.Trim('\"');

                //Assumption: None of my defined names are relative defined names (i.e. A1)
                string range = reference.Split('!')[1];
                string[] rangeArray = range.Split('$');
                string startCol = rangeArray[1];
                string startRow = rangeArray[2].TrimEnd(':');
                string endCol = null;
                string endRow = null;

                if (rangeArray.Length > 3)
                {
                    endCol = rangeArray[3];
                    endRow = rangeArray[4];
                }

                definedNames.Add(new DefinedNameVal()
                {
                    Key = key,
                    SheetName = sheetName,
                    StartColumn = startCol,
                    StartRow = startRow,
                    EndColumn = endCol,
                    EndRow = endRow
                });
            }
            return definedNames;
        }
        private DocumentFormat.OpenXml.Packaging.WorksheetPart GetWorkSheetPart(DocumentFormat.OpenXml.Packaging.WorkbookPart workbookPart, DefinedNameVal definedName)
        {
            //get worksheet based on defined name
            string relId = workbookPart.Workbook.Descendants<DocumentFormat.OpenXml.Spreadsheet.Sheet>()
                            .Where(s => definedName.SheetName.Equals(s.Name))
                            .First()
                            .Id;
            return (DocumentFormat.OpenXml.Packaging.WorksheetPart)workbookPart.GetPartById(relId);
        }
        private string GetCellValue(DocumentFormat.OpenXml.Packaging.WorksheetPart worksheetPart, DocumentFormat.OpenXml.Packaging.SharedStringTablePart stringTablePart, string startCol, string startRow)
        {
            string reference = startCol + startRow;
            //get exact cell based on reference
            DocumentFormat.OpenXml.Spreadsheet.Cell cell = worksheetPart.Worksheet.Descendants<DocumentFormat.OpenXml.Spreadsheet.Cell>()
                       .Where(c => reference.Equals(c.CellReference))
                       .FirstOrDefault();
            if (null == cell)
                return "";
            return GetValue(cell, stringTablePart);

        }
        private string GetValue(DocumentFormat.OpenXml.Spreadsheet.Cell cell, DocumentFormat.OpenXml.Packaging.SharedStringTablePart stringTablePart)
        {
            if (cell.ChildElements.Count == 0)
                return null;
            //get cell value
            string value = cell.CellValue.InnerText;
            //Look up real value from shared string table
            if ((cell.DataType != null) && (cell.DataType == DocumentFormat.OpenXml.Spreadsheet.CellValues.SharedString))
                value = stringTablePart.SharedStringTable.ChildElements[Int32.Parse(value)].InnerText;
            return value;
        }
    }
    internal class DefinedNameVal
    {
        public string Key { get; set; }
        public string SheetName { get; set; }
        public string StartColumn { get; set; }
        public string StartRow { get; set; }
        public string EndColumn { get; set; }
        public string EndRow { get; set; }
    }

    internal class ExcelDataSet
    {
        public string Name { get; set; }
        public string DisplayText { get; set; }
        public string Type { get; set; }
    }
    internal interface IExcelReader
    {
        void Extract(string partId);
    }
    internal class ExcelReader : IExcelReader
    {
        private IDataAccessLayer _dataAccessLayer;
        private IExcelManager _excelManager;

        public ExcelReader(IDataAccessLayer dataAccessLayer, IExcelManager excelManager)
        {
            _dataAccessLayer = dataAccessLayer;
            _excelManager = excelManager;
        }
        public void Extract(string partId)
        {
            string tempFolder = "", excelFilePath = "";
            try
            {
                string tempDirectory = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName());
                Directory.CreateDirectory(tempDirectory);
                tempFolder = tempDirectory;

                //Read the file content
                string aml = "<Item action='get' type='Part File'>" +
                             "  <source_id>" + partId + "</source_id>" +
                             "</Item>";

                var partFiles = _dataAccessLayer.applyAML(string.Format("<AML>{0}</AML>", aml));
                if (partFiles.getItemCount() == 0)//there is no file available
                    return;

                var partExcelFile = partFiles.getItemByIndex(0).getRelatedItem();
                partExcelFile.checkout(tempFolder);

                //fetch data from excel
                excelFilePath = Path.Combine(tempFolder, partExcelFile.getProperty("filename"));
                var data = _excelManager.ReadSheetViaDefindNames(excelFilePath);

                //update the part properties          
                UpdatePartProperties(data, partId);
            }
            catch
            {
                throw;
            }
            finally
            {
                if (File.Exists(excelFilePath))
                    File.Delete(excelFilePath);
                if (Directory.Exists(tempFolder))
                    Directory.Delete(tempFolder);
            }
        }
        private void UpdatePartProperties(List<ExcelDataSet> dataSet, string partId)
        {
            string partPropertyStartTemplate = "<Item type='Part Item Characteristic Value' id='{0}' action='edit'>";
            string itemCharIdTemplate = "<item_characteristic_id>{0}</item_characteristic_id>";
            string displayTextTemplate = "<display_value>{0}</display_value>";
            string propertyTypeTemplate = "<item_characteristic_value_type>{0}</item_characteristic_value_type>";
            string partPropertyEndTemplate = "</Item>";
            string aml = "<Item action='get' type='Part Item Characteristic Value' select='item_characteristic_name,item_characteristic_value_type,item_characteristic_id'>" +
                        "<source_id>" + partId + "</source_id>" +
                        "</Item>";

            var partProperties = _dataAccessLayer.applyAML(string.Format("<AML>{0}</AML>", aml));
            int itemCount = partProperties.getItemCount();

            for (int i = 0; i < itemCount; i++)
            {
                //get the part property
                var partProperty = partProperties.getItemByIndex(i);
                //extract the values
                var itemCharName = partProperty.getProperty("item_characteristic_name");
                var itemCharType = partProperty.getProperty("item_characteristic_value_type");
                var itemCharId = partProperty.getProperty("item_characteristic_id");

                var charName = itemCharName.Replace(" ", "");
                var excelData = dataSet.FirstOrDefault(ds => ds.Name == charName);
                if (null == excelData)
                    continue;

                StringBuilder builder = new StringBuilder();
                builder.Append(string.Format(partPropertyStartTemplate, partProperty.getID()));
                builder.Append(string.Format(itemCharIdTemplate, itemCharId));
                builder.Append(string.Format(displayTextTemplate, excelData.DisplayText));
                builder.Append(string.Format(propertyTypeTemplate, itemCharType));
                builder.Append(partPropertyEndTemplate);

                var result = _dataAccessLayer.applyAML(string.Format("<AML>{0}</AML>", builder.ToString()));

                if (result.isError())
                {
                    throw new Exception("Unable to update the part properties relationships");
                }
            }
        }
    }
    internal interface IDataAccessLayer
    {
        Item apply(Item itemToApply);
        Item applyAML(string amlToApply);
    }

    internal class DataAccessLayer : IDataAccessLayer
    {
        private Innovator _inn;

        public DataAccessLayer(Innovator innovator)
        {
            _inn = innovator;
        }
        public Item apply(Item itemToApply)
        {
            return itemToApply.apply();
        }
        public Item applyAML(string amlToApply)
        {
            return _inn.applyAML(amlToApply);
        }
    }

    #region MethodFooter
    public void func(
                IServerConnection InnovatorServerASP,
                XmlDocument inDom,

                XmlDocument outDom
                )
    {
    #endregion