<repo_name>Szaharov/DMS2CloudIntegration<file_sep>/WSComponents/src/WSComponents.Tests/Utility.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WSComponents.Tests
{
    public static  class Utility
    {
        public static int DEFAULT_TIMEOUT = 5000;

        public static void WaitWithPeriodicalCallback(ref bool canExit, int TotalTime, Action callback)
        {
            int retryCount = TotalTime;
            while (!canExit)
            {
                System.Threading.Thread.Sleep(1);

                callback();
                retryCount -= 1;

                if (retryCount == 0)
                {
                    throw new Exception("Waiting for exit timed out"); ;
                }
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CeaseCollaborationDialog/CeaseCollaborationDialog.xaml.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;

namespace Workshare.Components.Views.CeaseCollaborationDialog
{
    /// <summary>
    /// Interaction logic for CeaseCollaborationDialog.xaml
    /// </summary>
    public partial class CeaseCollaborationDialog : OwnWindow
    {
        private IModuleView _view;

        public CeaseCollaborationDialog()
        {
            InitializeComponent();
        }

        public CeaseCollaborationDialog(ModuleBase module, CommandInvoker commandInvoker, IEnumerable<IDMSItem> items, IModuleView view)
        {
            InitializeComponent();
            _view = view;

            DataContext = new CeaseCollaborationDialogViewModel(module, commandInvoker, items, this, _view);

            this.Loaded += CeaseCollaborationDialog_Loaded;
            this.Closed += CeaseCollaborationDialog_Closed;
        }

        void CeaseCollaborationDialog_Closed(object sender, EventArgs e)
        {
            _view.TopWindow = IntPtr.Zero;
            _view.SuppressProgressDialog(false);
        }

        void CeaseCollaborationDialog_Loaded(object sender, RoutedEventArgs e)
        {
            var vm = (CeaseCollaborationDialogViewModel)DataContext;
            _view.SuppressProgressDialog(true);

            if (vm.ScanCommand.CanExecute(""))
            {
                vm.ScanCommand.Execute("");
            }
        }

        private void OwnWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
        {
            var vm = (CeaseCollaborationDialogViewModel)DataContext;
            if (vm != null) vm.OnViewClosing();
        }

        private void RadioButton_Checked(object sender, RoutedEventArgs e)
        {
            var vm = (CeaseCollaborationDialogViewModel)DataContext;
            this.Tag = (sender as RadioButton).Tag;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/Visitors/ScanVisitor.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Globalization;
using System.Linq;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.DmsItems.Visitors
{
    public class ScanVisitor:DMSVisitor
    {
        public override PageIterator Iterator
        {
            set
            {
                Result.Iterator = value;
            }
            get { return Result.Iterator; }
        }

        public SummaryProcessResult  Result { get; private set; }

        public ScanOptions Options { set; get; }

        private readonly Stack<ItemMap> _resultStack = new Stack<ItemMap>();

        readonly DmsScanStrategyBase _dmsScanStrategy;

        public ScanVisitor(DmsScanStrategyBase dmsScanStrategy)
        {
            _dmsScanStrategy = dmsScanStrategy;
            Options = new ScanOptions();
            Options.UseForceRequest = true;
        }

        public void Initialize(SummaryProcessResult result)
        {
            this.Result = result ?? new SummaryProcessResult();
            this._resultStack.Clear();
            this._resultStack.Push(Result);
        }

        void HandleMapError(ItemMap map, Exception ex)
        {
            Logger.WriteError(string.Format("Error during scaning item map."), ex);
            map.ProcessState = ProcessState.Error;
            map.Error = ex;
        }


        FileMap GetExistedAlreadyScannedFileMap(string localId, ItemMap parentMap)
        {
            return parentMap.Maps.OfType<FileMap>().FirstOrDefault(a =>string.Equals(a.GetLocalId(),localId));
        }

        FolderMap GetExistedAlreadyScannedFolderMap(string localId, ItemMap parentMap)
        {
            return parentMap.Maps.OfType<FolderMap>().FirstOrDefault(a => string.Equals(a.GetLocalId(), localId));
        }
        FolderMap GetExistedAlreadyScannedFolderMapByWsId(int wsId, ItemMap parentMap)
        {
            return parentMap.Maps.OfType<FolderMap>().FirstOrDefault(a => string.Equals(a.GetWsId(), wsId));
        }

        FileMap GetExistedAlreadyScannedFileMapByWsId(int wsId, ItemMap parentMap)
        {
            return parentMap.Maps.OfType<FileMap>().FirstOrDefault(a => string.Equals(a.GetWsId(), wsId));
        }

        bool IsInUnchangeableState(ItemMap map)
        {
            return map.ProcessState == ProcessState.Error || map.ProcessState == ProcessState.Processed;
        }

        public override bool VisitEnter(BaseDMSFile baseDMSFile)
        {
            Logger.WriteTrace(string.Format("VisitEnter file {0}", baseDMSFile));

            var parentresult = _resultStack.Peek();
            var localFile = (IDMSFile) baseDMSFile;
            var existed = GetExistedAlreadyScannedFileMap(localFile.DMSId.ToString(CultureInfo.InvariantCulture), parentresult);
            var alreadyScanned = existed != null;
            var fileMap = existed??new FileMap();
            fileMap.LocalFile = localFile;
            if (!alreadyScanned)
            {
                parentresult.AddIf(fileMap);
            }
            _resultStack.Push(fileMap);

            try
            {
                if (Options.Cancellation.IsCancelled) return false;

                var options = new DmsFileScanOptions() { UseForceRequest = Options.UseForceRequest };
                var res = _dmsScanStrategy.Scan(baseDMSFile, fileMap, options);
                if (!IsInUnchangeableState(fileMap))
                {
                    fileMap.ProcessState = res.Result;
                }
                fileMap.Error = res.Error;
                return !options.SkipChildren;
            }
            catch (Exception ex)
            {
                HandleMapError(fileMap, ex);
                return false;
            }
        }

        public override void Visit(BaseDMSFile dmsfile)
        {
            Logger.WriteTrace(string.Format("Visit file {0}", dmsfile));

            if (Options.Cancellation.IsCancelled) return;

            var currentFileMap = (FileMap)_resultStack.Peek();
            try
            {
                var options = new DmsFileScanOptions() { UseForceRequest = Options.UseForceRequest };
                var res = _dmsScanStrategy.ScanForNewVersionsOnWs(dmsfile, currentFileMap, options);
                if (!IsInUnchangeableState(currentFileMap))
                {
                    currentFileMap.ProcessState = res.Result;
                    currentFileMap.Error = res.Error;
                }
            }
            catch (Exception ex)
            {
                HandleMapError(currentFileMap, ex);
            }
        }

        public override void VisitLeave(BaseDMSFile baseDMSFile)
        {
            Logger.WriteTrace(string.Format("VisitLeave file {0}", baseDMSFile));
            _resultStack.Pop();
        }

        public override bool VisitEnter(BaseDMSFolder baseDMSFolder)
        {
            Logger.WriteTrace(string.Format("VisitEnter folder {0}", baseDMSFolder));
            var dmsFolder = (IDMSFolder) baseDMSFolder;
            var parentMap = _resultStack.Peek();
            var existed = GetExistedAlreadyScannedFolderMap(dmsFolder.DMSId.ToString(CultureInfo.InvariantCulture), parentMap);
            var folderMap = existed ?? new FolderMap();
            parentMap.AddIf(folderMap);
            _resultStack.Push(folderMap);
            folderMap.LocalFolder = dmsFolder;

            try
            {
                if (Options.Cancellation.IsCancelled) return false;
                var param = new DmsFolderScanOptions() { UseForceRequest = Options.UseForceRequest };
                var res=_dmsScanStrategy.Scan(baseDMSFolder, folderMap, param);

                folderMap.ProcessState = res.Result;
                folderMap.Error = res.Error;
                return !param.SkipChildren;
            }
            catch (Exception ex)
            {
                HandleMapError(folderMap, ex);
                return true;
            }
        }

        public override void Visit(BaseDMSFolder dmsFolder)
        {
            Debug.WriteLine(string.Format("Visit folder {0}", dmsFolder));
        }

        public override void VisitLeave(BaseDMSFolder baseDMSFolder)
        {
            Debug.WriteLine(string.Format("VisitEnter _folder {0}", baseDMSFolder));
            _resultStack.Pop();
        }

        public override void Visit(BaseDmsVersion baseDmsVersion)
        {
            Debug.WriteLine(string.Format("Visit version {0}", baseDmsVersion));
            var parentMap = (FileMap) _resultStack.Peek();

            if (Options.Cancellation.IsCancelled) return;
            
            var versionMap = new VersionMap();
            parentMap.AddIf(versionMap);
            try
            {
                versionMap.LocalVersion = (IDmsVersion) baseDmsVersion;
                var options = new DmsVersionScanOptions() { UseForceRequest = Options.UseForceRequest };
                var res = _dmsScanStrategy.Scan(baseDmsVersion, versionMap, options);
                versionMap.ProcessState = res.Result;
                versionMap.Error = res.Error;
            }
            catch (Exception ex)
            {
                HandleMapError(versionMap, ex);
            }
        }

        public override void GetNewEntries(out List<WsFolder> wsfolders, out List<WsFile> wsfiles)
        {
            var currentMap = (FolderMap)_resultStack.Peek();
            _dmsScanStrategy.GetWsItemsToVisit(currentMap, out wsfolders, out wsfiles, Options.UseForceRequest);
        }

        public override bool VisitEnter(WsFolder wsFolder, out List<WsFolder> wsFolders, out List<WsFile> wsFiles)
        {
            wsFolders=new List<WsFolder>();
            wsFiles=new List<WsFile>();
            var parentMap = _resultStack.Peek();
            var existed = GetExistedAlreadyScannedFolderMapByWsId(wsFolder.Id, parentMap);
            if (existed == null)
            {
                existed = new FolderMap {WsFolder = wsFolder};
                parentMap.AddIf(existed);
            }
            _resultStack.Push(existed);
            try
            {
                wsFolders = existed.WsFolder.SubFolders.ToList();
                wsFiles = existed.WsFolder.Files.ToList();
                return true;
            }
            catch (Exception ex)
            {
                HandleMapError(existed, ex);
                return false;
            }
        }

        public override void VisitLeave(WsFolder wsFolder)
        {
            _resultStack.Pop();
        }

        public override void Visit(WsFolder wsFolder)
        {
            
        }

        public override void Visit(WsFile file)
        {
            var parentMap = _resultStack.Peek();
            var existed = GetExistedAlreadyScannedFileMapByWsId(file.Id, parentMap);
            if (existed != null) return;
            var map = new FileMap {WsFile = file};
            try
            {
                parentMap.AddIf(map);
                var wsVersions = map.WsFile.Versions.ToList();
                foreach (var ver in wsVersions)
                {
                    var verMap = new VersionMap {WsVersion = ver};
                    map.AddIf(verMap);
                }
            }
            catch (Exception ex)
            {
                HandleMapError(map, ex);
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/BaseDMSFolder.cs
﻿
namespace Workshare.Integration.Processor.DmsItems
{
    public abstract class BaseDMSFolder : BaseDMSItem
    {
     //TODO remove this class
    }

    public class SingleChildDMSFolder : BaseDMSFolder
    {
        internal readonly BaseDMSFolder _folder;
        public SingleChildDMSFolder Next { get; set; }

        public BaseDMSFile File { get; set; }

        public SingleChildDMSFolder()
        {
        }
        
        public SingleChildDMSFolder(BaseDMSFolder folder)
        {
            _folder = folder;
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshate.HookEvents/ProcessIManageEvents.cs
﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Net;
using System.Runtime.InteropServices;
using System.Threading;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.Worksite.iManExt2;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components.Interfaces;
using Workshare.Components.WSLogger;
using Workshare.IManage;


namespace Workshare.HookEvents
{
    [ClassInterface(ClassInterfaceType.None)]
    [Guid("125A2A8C-375E-4B95-ADC4-7EF1EAF8C247")]
    [ComVisible(true)]
    public class ProcessIManageEvents
    {
        public static readonly string GETSELECTEDITEMS = "SelectedIManObjects";
        public static readonly string GETDESTINATIONOBJECT = "DestinationObject";
        public static readonly string GETNRTDOCUMENTS = "SelectedNRTDocuments";

        private const int MAXWAITTIME = 5000;
        Thread _newFileChecker;
        Thread _waitForFileTask;
        readonly object _lockObject = new object();

        private static bool _inProgress = false;
        private static Queue<HookWorkUnit> _hooks= new Queue<HookWorkUnit>();

        private readonly System.Web.Script.Serialization.JavaScriptSerializer jss = new System.Web.Script.Serialization.JavaScriptSerializer();
        private readonly string tmpFilePart = Path.GetTempPath() + "WsCheckoutFiles.tmp";
        private static bool _firstLaunch = true;
        private static List<CheckoutFile> _CheckoutFiles;

        public ProcessIManageEvents()
        {
            if (_firstLaunch && (IsRunDescSite && !HasRunnedFileSite || IsRunFileSite && !HasRunnedDescSite))
            {
                _firstLaunch = false;
                File.WriteAllText(tmpFilePart, "[]");
            }

            if (_CheckoutFiles == null)
            {
                if (File.Exists(tmpFilePart)) _CheckoutFiles = jss.Deserialize<List<CheckoutFile>>(System.IO.File.ReadAllText(tmpFilePart));
                if (_CheckoutFiles == null) _CheckoutFiles = new List<CheckoutFile>();
            }
        }

        bool _continueWatching;
        bool ContinueWatching
        {
            get
            {
                lock (_lockObject)
                {
                    return _continueWatching;
                }
            }
            set
            {
                lock (_lockObject)
                {
                    _continueWatching = value;
                }
            }
        }

        private static void ExecutePendingWorkUnits()
        {
            _inProgress = false;
            lock (_hooks)
            {
                if (_hooks.Any())
                {
                    var hookUnit = _hooks.Dequeue();
                    hookUnit.Execute();
                }
            }
        }

        public class HookWorkUnit
        {
            public void Execute()
            {
                _inProgress = true;
                try
                {
                    m_action();
                }
                catch (Exception ex)
                {
                    Logger.WriteError(ex);
                }
            }
            public HookWorkUnit(Action action)
            {
                m_action = action;
            }
            protected Action m_action;
        }

        public static bool IsRunFileSite
        {
            get
            {
                return Process.GetCurrentProcess().MainModule.ModuleName.ToLower().Contains("outlook");
            }
        }

        public static bool IsRunDescSite
        {
            get
            {
                return Process.GetCurrentProcess().MainModule.ModuleName.ToLower().Contains("manage");
            }
        }

        public static bool HasRunnedFileSite
        {
            get
            {
                foreach (var p in Process.GetProcesses())
                {
                    try { if (p.MainModule.ModuleName.ToLower().Contains("outlook")) return true; }
                    catch { }
                }
                return false;
            }
        }

        public static bool HasRunnedDescSite
        {
            get
            {
                foreach (var p in Process.GetProcesses())
                {
                    try { if (p.MainModule.ModuleName.ToLower().Contains("manage")) return true; }
                    catch { }
                }
                return false;
            }
        }

        private static int _lastImportedDocNumber = -1;
        public static int LastImportedDocNumber
        {
            get { return _lastImportedDocNumber; }
            set { _lastImportedDocNumber = value; }
        }

        public static List<object> GetImportedDocuments(ContextItems context)
        {
            try
            {
                var docs = new List<object>() { context.Item("ImportedDocument") };
                if (docs != null && docs.Count == 1)
                {
                    if (((IManDocument)docs[0]).Number != LastImportedDocNumber)
                    {
                        return docs;
                    }
                }
            }
            catch (ArgumentException ex)
            {
                Logger.Write("ImportedDocument list is empty", Severity.Information);
            }
            return new List<object>();
        }

        private static string GetServerIp(string hostname)
        {
            IPHostEntry entry = Dns.GetHostEntry(hostname);
            return entry.AddressList.FirstOrDefault().ToString().Replace(".", "_");
        }

        private static string SetServerKey(IManDocument _file)
        {
            try
            {
                if (_file != null)
                {
                    var session = _file.Database.Session;
                    var nrtdms = session.DMS.ObjectID;
                    IPAddress server_ip;
                    var ipAddres = "!server:";

                    if (IPAddress.TryParse(session.ServerName, out server_ip))
                    {
                        ipAddres += session.ServerName.Replace(".", "_");
                    }
                    else
                    {
                        ipAddres += GetServerIp(session.ServerName);
                    }
                    return nrtdms + ipAddres;
                }
                return "";
            }
            catch
            {
                return "";
            }
        }

        public static void ProcessEvent(IEnumerable items, EventOperation operation, string command)
        {
            Logger.Write("Start ProcessEvent", Severity.Information);

            if (items != null)
            {
                List<object> docs = items.Cast<object>().ToList();

                if (docs.Count>0 && string.IsNullOrEmpty(Workshare.IManage.Application.iManInstance.ServerKey))
                {
                    Workshare.IManage.Application.iManInstance.ServerKey = SetServerKey(docs[0] as IManDocument);
                }

                if (docs.Count == 1)
                {
                    if (operation == EventOperation.AddNewDoc)
                    {
                        LastImportedDocNumber = ((IManDocument)docs[0]).Number;
                    }
                }
                foreach (var itm in items)
                {
                    if (itm is IManDocument && (operation != EventOperation.MoveFile || operation == EventOperation.MoveFile && !(itm as IManDocument).CheckedOut))
                    {
                        string str = (itm as IManDocument).Number.ToString();
                        Logger.Write("ProcessEvent for doc with ID=" + str, Severity.Information);
                        Workshare.IManage.Application.iManInstance.View.ShowFileSyncDialog(itm, operation, command);
                    }
                }
            }
        }

        public static void ProcessEvent(ContextItems items, EventOperation operation, string command)
        {
            Logger.Write("------------------- ProcessEvent Start -------------------", Severity.Information);
            Logger.WriteTrace("EventOperation : " + operation.ToString());
            Logger.WriteTrace("Command : " + command);
            Logger.WriteTrace("");

            var docs = items.Item(ProcessIManageEvents.GETSELECTEDITEMS) as IEnumerable;

            Logger.Write("------------------- ProcessEvent Stop -------------------", Severity.Information);

            ProcessEvent(docs, operation, command);
        }

        public void HookFileSaveCmd(object cmd)
        {
            Logger.WriteTrace(string.Format("Raised save file iManage event"));
            if (HooksDisabler.DisableHooks)
            {
                Logger.WriteTrace(string.Format("Hooks are disabled"));    
                return;
            }
            var view = Application.iManInstance.View;
            ContinueWatching = false;
            if (!IsRunFileSite && !IsRunDescSite)
            {
                Logger.WriteTrace(string.Format("Raised save file iManage event"));
                ContinueWatching = false;
                if (!IsRunFileSite && !IsRunDescSite)
                {
                    var icmd = cmd as IManFileSaveDlg;
                    // ??? SetServerKey(icmd);
                    if (icmd != null && icmd.NewDocument != null)
                    {
                        var doc = icmd.NewDocument as IManDocument;
                        if (doc != null)
                        {
                            var path = doc.CheckoutPath;
                            var unit = new HookWorkUnit(() =>
                            {
                                if (!File.Exists(path))
                                {
                                    _waitForFileTask = new Thread(() =>
                                    {
                                        try
                                        {
                                            Logger.WriteTrace(
                                                string.Format(
                                                    "Document {0} was not found in check out path {1}. Start waiting thread.",
                                                    doc.Name, path));
                                            var passed = 0;
                                            while (!File.Exists(path) && passed < MAXWAITTIME)
                                            {
                                                passed += 100;
                                                Thread.Sleep(100);
                                            }
                                            Logger.WriteTrace(
                                                string.Format(
                                                    "Document {0} was found in check out path {1} after {2} seconds of waiting",
                                                    doc.Name, path, passed == 0 ? 0 : passed/100));
                                            ProcessEvent(new List<IManDocument> {icmd.NewDocument as IManDocument},
                                                EventOperation.AddNewDoc, "HookFileSaveCmd -> OfficeFileSaveCmd 1");
                                        }
                                        catch (Exception ex)
                                        {
                                            Logger.WriteError(ex);
                                        }
                                        ExecutePendingWorkUnits();

                                        var newFile = new CheckoutFile();

                                        newFile.Path = doc.CheckoutPath;
                                        newFile.Number = doc.Number;
                                        newFile.Version = doc.Version;
                                        newFile.lastAction = CheckoutFile.LastAction.Default;
                                        newFile.EditDateTicks = new FileInfo(doc.CheckoutPath).LastWriteTime.Ticks;

                                        _CheckoutFiles.Add(newFile);
                                    });
                                    _waitForFileTask.TrySetApartmentState(ApartmentState.STA);
                                    // as "ProcessEvent" will create the application entry point from the background thread 
                                    // we should create Application before in order to have the dispatcher acossiated with the main thread.
                                    _waitForFileTask.Start();
                                }
                                else
                                {
                                    ProcessEvent(new List<IManDocument> {icmd.NewDocument as IManDocument},EventOperation.AddNewDoc, "HookFileSaveCmd -> OfficeFileSaveCmd 2");
                                    ExecutePendingWorkUnits();
                                }
                            });
                            if (!_inProgress)
                            {
                                unit.Execute();
                            }
                            else
                            {
                                _hooks.Enqueue(unit);
                            }
                        }
                    }
                }
            }
        }

        private CheckoutFile GetCheckoutFile(int number)
        {
            return _CheckoutFiles.FirstOrDefault(f => f.Number == number);
        }

        public void HookCheckoutCmd(object cmd, object dlg)
        {
            if (!IsRunDescSite && !IsRunFileSite) return;

            var chin_cmd = cmd as CheckinCmd;
            var docs = chin_cmd.Context.Item(GETNRTDOCUMENTS) as IEnumerable;

            foreach (IManDocument doc in docs)
            {
                var cFile = GetCheckoutFile(doc.Number);
                if (cFile == null)
                {
                    cFile = new CheckoutFile();
                    cFile.Number = doc.Number;
                    _CheckoutFiles.Add(cFile);
                }

                cFile.Path = doc.CheckoutPath;
                cFile.Version = doc.Version;
                cFile.EditDateTicks = new FileInfo(doc.CheckoutPath).LastWriteTime.Ticks;
            }
            File.WriteAllText(tmpFilePart, jss.Serialize(_CheckoutFiles));
        }

        public void HookCheckinCmd_PostOnOK(object cmd)
        {
            Logger.WriteTrace(string.Format("HookCheckinCmd_PostOnOK"));
            if (HooksDisabler.DisableHooks)
            {
                Logger.WriteTrace(string.Format("Hooks are disabled"));
                return;
            }

            var chin_cmd = cmd as CheckinCmd;

            if (chin_cmd != null)
            {
                var docs = chin_cmd.Context.Item(GETNRTDOCUMENTS) as IEnumerable;

                if (!IsRunFileSite && !IsRunDescSite)
                {
                    try
                    {
                        var _docs = new List<IManDocument>();

                        foreach (var doc in docs)
                        {
                            var file = GetCheckoutFile((doc as IManDocument).Number);
                            if (file == null) continue;

                            if (file.ToUpload)
                            {
                                _docs.Add(doc as IManDocument);
                                file.ToUpload = false;
                            }
                            else
                            {
                                ((Workshare.IManage.Presenter.ModulePresenter)Application.iManInstance.Presenter).UpdateSyncInfo(doc);
                            }

                            if (file.ToRemove)
                            {
                                _CheckoutFiles.Remove(file);
                                File.WriteAllText(tmpFilePart, jss.Serialize(_CheckoutFiles));
                            }
                            else
                            {
                                if (file.lastAction != CheckoutFile.LastAction.Default)
                                {
                                    file.EditDateTicks = new FileInfo(file.Path).LastWriteTime.Ticks;
                                    file.lastAction = CheckoutFile.LastAction.Default;
                                }
                            }
                        }

                        if (_docs.Count > 0)
                        {
                            var unit = new HookWorkUnit(() =>
                            {
                                ProcessEvent(docs, EventOperation.UpdateCurrent, "HookCheckInCmd -> WordCheckinCmd");
                                ExecutePendingWorkUnits();
                            });
                            if (!_inProgress)
                            {
                                unit.Execute();
                            }
                            else
                            {
                                _hooks.Enqueue(unit);
                            }
                        }
                    }
                    catch { }
                }
                else
                {
                    //when file was opened in iManage and changed
                    object calledFromIntegration = ProcessIManageEvents.GetCmdContextItemValueByName(chin_cmd.Context, "IManExt.CalledFromIntegration");
                    if (calledFromIntegration != null && Convert.ToBoolean(calledFromIntegration) == true && docs.OfType<object>().Count() == 1)
                    {
                        var doc = docs.OfType<IManDocument>().FirstOrDefault();
                        if (doc != null)
                        {
                            var file = GetCheckoutFile(doc.Number);
                            if (file.ToUpload)
                            {
                                ProcessEvent(new List<IManDocument>() { doc }, EventOperation.AddNewVersion, "HookCheckInCmd -> Update File Which Has Changed After Its Openning");
                            }
                        }
                    }
                    else
                    {
                        //-----------
                        var updateversion = (bool)chin_cmd.Context.Item("IManExt.CheckinAsNewDocOrNewVer");
                        if (!updateversion)
                        {
                            //user just update current version of the document
                            ProcessEvent(docs, ((updateversion) ? EventOperation.AddNewVersion : EventOperation.UpdateCurrent), "HookCheckInCmd -> Replace Original");
                        }
                        else
                        {
                            // try to get newly added document. if we can get this - then user select new document option
                            var importedDocs = GetImportedDocuments(chin_cmd.Context);
                            if (importedDocs.Count != 0)
                            {
                                // Hooks: 21543 - FileSite - "New docunemt"
                                ProcessEvent(importedDocs, EventOperation.AddNewDoc, "HookCheckInCmd -> New Document");
                            }
                            else
                            {
                                // new document wasn't created and user select new version opton
                                ProcessEvent(docs, ((updateversion) ? EventOperation.AddNewVersion : EventOperation.UpdateCurrent), "HookCheckInCmd -> New Version");
                            }
                        }
                        //-------------------
                    }
                }
            }
        }
        public void HookFileSaveCmd_PostOnOK(object dlg)
        {
            if (!IsRunFileSite && !IsRunDescSite)
            {
                var save_dlg = dlg as IIManFileSaveDlg;
                var doc = save_dlg.NewDocument as IManDocument;

                var file = GetCheckoutFile(doc.Number);

                if (file != null && file.lastAction != CheckoutFile.LastAction.Default)
                {
                    file.lastAction = CheckoutFile.LastAction.Default;
                    file.EditDateTicks = new FileInfo(file.Path).LastWriteTime.Ticks;
                }
            }
        }

        public void HookCheckinCmd(object cmd, object dlg)
        {
            Logger.WriteTrace(string.Format("HookCheckInCmd"));
            if (HooksDisabler.DisableHooks)
            {
                Logger.WriteTrace(string.Format("Hooks are disabled"));
                return;
            }
            var view = Application.iManInstance.View;
            ContinueWatching = false;
            
            var chin_cmd = cmd as CheckinCmd;

            if (chin_cmd != null)
            {
                //chin_cmd.Context.OfType<object>().ToList().ForEach(p => Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));                        
                var docs = chin_cmd.Context.Item(GETNRTDOCUMENTS) as IEnumerable;

                if (!IsRunFileSite && !IsRunDescSite)
                {
                    var chin_dlg = dlg as ICheckinDlg;

                    try
                    {
                        foreach (IManDocument doc in docs)
                        {
                            var file = GetCheckoutFile(doc.Number);
                            Logger.Write("file is" + (file == null ? "null" : file.ToString()), Severity.Information);
                            if (file != null && doc != null)
                            {
                                if (chin_dlg != null && chin_dlg.Database != null && chin_dlg.CheckinOption == CheckinDisposition.nrReplaceOriginal)
                                {
                                    Logger.Write("file replace original", Severity.Information);
                                    file.lastAction = CheckoutFile.LastAction.ReplaceOriginal;
                                    file.ToUpload = true;
                                }
                                else if (file != null && file.Version == doc.Version && file.lastAction == CheckoutFile.LastAction.Default && new FileInfo(file.Path).LastWriteTime.Ticks != file.EditDateTicks)
                                {
                                    Logger.Write("ticks are not equal", Severity.Information);
                                    file.ToUpload = true;
                                    file.ToRemove = true;
                                }
                            }
                        }
                    }
                    catch (Exception ex)
                    {
                        Logger.WriteError("error happen... ", ex);
                    }
                    
                    Logger.Write("checkin cmd finish", Severity.Information);
                }
                else
                {
                    //when file was opened in iManage and changed
                    object calledFromIntegration = ProcessIManageEvents.GetCmdContextItemValueByName(chin_cmd.Context, "IManExt.CalledFromIntegration");
                    if (calledFromIntegration != null && Convert.ToBoolean(calledFromIntegration) == true && docs.OfType<object>().Count() == 1)
                    {
                        var doc = docs.OfType<IManDocument>().FirstOrDefault();
                        if (doc != null)
                        {
                            var file = GetCheckoutFile(doc.Number);
                            if (new FileInfo(file.Path).LastWriteTime.Ticks != file.EditDateTicks)
                            {
                                file.ToUpload = true;
                            }
                            else
                            {
                                file.ToUpload = false;
                            }
                        }
                    }
                }
            }
        }

        public void HookNewVersionCmd(object cmd, object dlg)
        {
            Logger.WriteTrace(string.Format("HookCheckInCmd"));
            if (HooksDisabler.DisableHooks)
            {
                Logger.WriteTrace(string.Format("Hooks are disabled"));
                return;
            }
            var view = Application.iManInstance.View;
            ContinueWatching = false;
            
            var ver_cmd = cmd as NewVersionCmd;
            var ver_dlg = dlg as INewVersionDlg;

            if (ver_cmd != null && ver_dlg != null && ver_dlg.NRTDocument != null)
            {
                try
                {
                    var curDoc = ver_dlg.NRTDocument as IManDocument;

                    if (!IsRunFileSite && !IsRunDescSite)
                    {
                        //chin_cmd.Context.OfType<object>().ToList().ForEach(p => Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                        var lastDoc = curDoc.LatestVersion;

                        var file = GetCheckoutFile(curDoc.Number);

                        if (file != null)
                        {
                            file.Path = lastDoc.CheckoutPath;
                            file.Version = lastDoc.Version;
                            file.lastAction = CheckoutFile.LastAction.NewVersion;
                            file.ToUpload = true;
                        }
                    }
                    else
                    {
                        object NoCmdUI = ProcessIManageEvents.GetCmdContextItemValueByName(ver_cmd.Context, "IManExt.NewVersionCmd.NoCmdUI");
                        if (NoCmdUI == null)//'New Version Profile' dialog was called from "Copy"->"Copy As New Version" context's file menu
                        {
                            ProcessEvent(new List<IManDocument>() { curDoc }, EventOperation.AddNewVersion, "HookNewVersionCmd -> Copy As New Version");
                        }
                    }
                }
                catch (Exception)
                {
                }
            }
        }

        private void FolderChecker(IManFolder folder, int fileMaxID)
        {
            int waittime = 0;
            Logger.Write("Start FolderChecker", Severity.Information);
            while (ContinueWatching && waittime <= MAXWAITTIME)
            {
                Thread.Sleep(500);
                if (ContinueWatching)
                {
                    waittime += 500;
                    var docs = new List<IManDocument>();
                    Logger.Write("Scan folder contents", Severity.Information);
                    foreach (object content in folder.Contents)
                    {
                        if (content is IManDocument)
                        {
                            docs.Add((IManDocument) content);
                        }
                    }

                    int cmax = docs.Max(x => x.Number);
                    Logger.Write("find max doc id = "+cmax.ToString(), Severity.Information);
                    if (cmax >= fileMaxID)
                    {
                        Logger.Write("Get appropriate doc", Severity.Information);
                        IManDocument doc = docs.Where(x => x.Number == cmax).FirstOrDefault();
                        if (doc != null)
                        {
                            ContinueWatching = false;
                            // as "ProcessEvent" will create the application entry point from the background thread 
                            // we should create Application before in order to have the dispatcher acossiated with the main thread.
                            ProcessEvent(new List<IManDocument>() {doc}, EventOperation.AddNewDoc, "FolderChecker -> OutlookAddDoc");
                        }
                    }
                }
            }
            ExecutePendingWorkUnits();
        }

        public void HookNewProfileCmd_PostOnOK(object cmd)
        {
            Logger.WriteTrace(string.Format("HookNewProfileDlg"));
            if (HooksDisabler.DisableHooks)
            {
                Logger.WriteTrace(string.Format("Hooks are disabled"));
                return;
            }

            var profCmd = cmd as NewProfileCmd;
            if (profCmd != null)
            {
                object callByFileSaveAs = ProcessIManageEvents.GetCmdContextItemValueByName(profCmd.Context, "CallByFileSaveAs");
                if (IsRunFileSite && (callByFileSaveAs == null || Convert.ToBoolean(callByFileSaveAs) == false))
                {
                    try
                    {
                        var fld = ProcessIManageEvents.GetCmdContextItemValueByName(profCmd.Context, "DestinationObject") as IManFolder;
                        List<IManDocument> docs = new List<IManDocument>();
                        foreach (object content in fld.Contents)
                        {
                            if (content is IManDocument)
                            {
                                docs.Add((IManDocument)content);
                            }
                        }
                        ContinueWatching = true;

                        //don'use new Thread - in case of Outlook when we drag&drop files the login dialog is displayed only once when we just closed it last time without logging
                        //_newFileChecker = new Thread(new ThreadStart(() =>
                        //{
                            try
                            {
                                int maxid = docs.Count == 0 ? -1 : docs.Max(x => x.Number);
                                Logger.WriteWarning(maxid.ToString());
                                var unit = new HookWorkUnit(() => FolderChecker(fld, maxid));
                                if (!_inProgress)
                                {
                                    unit.Execute();
                                }
                                else
                                {
                                    _hooks.Enqueue(unit);
                                }
                            }
                            catch (Exception ex)
                            {
                                Logger.WriteError(ex);
                            }
                        //}));
                        //_newFileChecker.TrySetApartmentState(ApartmentState.STA);
                        //_newFileChecker.Start();
                        //System.Windows.Forms.MessageBox.Show(docs.Max(x=>x.Number).ToString());
                    }
                    catch (Exception ex)
                    {
                    }
                }
            }
        }

        public static object GetCmdContextItemValueByName(ContextItems context, string itemName)
        {
            object ret = null;

            if (context != null)
            {
                var cmdContextEnum = context.GetEnumerator();
                while (cmdContextEnum.MoveNext())
                {
                    var currItem = cmdContextEnum.Current as IContextItem;
                    if (currItem.Name.Equals(itemName, StringComparison.OrdinalIgnoreCase))
                        return currItem.Value;
                }
            }
            else
            {
                Logger.WriteTrace(string.Format("GetNewProfileCmdContextItemValueByName: Trying get value from empty context. ItemName: {0}", itemName));
            }

            return ret;
        }
        public class CheckoutFile
        {
            public enum LastAction { Default, ReplaceOriginal, NewVersion }

            public string Path;
            public long EditDateTicks;
            public int Number;
            public int Version;
            public LastAction lastAction;
            public bool ToUpload;
            public bool ToRemove;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/TreePathFinder.cs
﻿using Workshare.Integration.Interfaces;

namespace Workshare.Integration.Processor.DmsItems
{
    public class TreePathFinder
    {
        public TreePathFinder()
        {
        }
        
        public void FindPath(BaseDMSFolder folder, SingleChildDMSFolder currentFolder)
        {
            var parent = (BaseDMSFolder)(((IDMSItem)folder).ParentFolder);
            if (parent == null ) 
            {
                return;
            }

            currentFolder.Next = new SingleChildDMSFolder(parent);
            FindPath(parent, currentFolder.Next);
        }

        public SingleChildDMSFolder Reverse(SingleChildDMSFolder item)
        {
            if (item == null || item.Next == null)
            {
                return item;
            }

            var firstItem = Reverse(item.Next);

            var currentItem = item.Next;
            item.Next = null;
            currentItem.Next = item;

            return firstItem;
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/JsonParser.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WorksharePlatform
{
    public static class JsonParser
    {
        #region Private Methods

        private static FolderDetails ExtractFolder(string folder)
        {
            var found = new FolderDetails();
            found.Ancestry = ExtractIntValue(folder, "ancestry");
            found.Name = ExtractStringValue(folder, "name");
            found.Id = ExtractIntValue(folder, "id");
            found.Url = ExtractStringValue(folder, "url");
            found.Description = ExtractStringValue(folder, "description");
            found.ParentId = ExtractIntValue(folder, "parent_id");
            found.FileCounter = ExtractIntValue(folder, "file_counter");
            found.MemberCount = ExtractIntValue(folder, "members_counter");
            found.NotifyOwner = bool.Parse(ExtractStringValue(folder, "notify_owner"));
            var isdeleted = false;
            if (bool.TryParse(ExtractStringValue(folder, "is_deleted"), out isdeleted))
            {
                found.IsDeleted = isdeleted;
            }
            string DateExpire = ExtractStringValue(folder, "expires_at");
            if (DateExpire == "null")
            {
                found.ExpiresAt = null;
            }
            else
            {
                found.ExpiresAt = DateTime.Parse(DateExpire);
            }
            found.Permissions = ExtractPermissions(folder, found.Id);
            found.Owner = ExtractUserData(ExtractNode(folder, "owner"));
            found.Creator = ExtractUserData(ExtractNode(folder, "creator"));
            found.ChildFoldersCounter = ExtractIntValue(folder, "folder_counter");
            return found;
        }

        private static UserDetails ExtractUserData(string node)
        {
            UserDetails res = new UserDetails();
            res.Email = ExtractStringValue(node, "email");
            res.UserId = ExtractStringValue(node, "uuid");
            res.UserName = ExtractStringValue(node, "name");
            return res;
        }

        public static UserDetails ParseUserInfo(string userinfo)
        {
            UserDetails res = new UserDetails();
            res.UserName = ExtractStringValue(userinfo, "name");
            return res;
        }

        private static Permissions ExtractPermissions(string permissions, int folder_id)
        {
            var res = new Permissions();
            res.FolderId = folder_id;
            res.PermissionSet = new Dictionary<string, bool>();
            res.PermissionSet.Add("can_download_original", ExtractStringValue(permissions, "can_download_original") == "true");
            res.PermissionSet.Add("can_upload_changes", ExtractStringValue(permissions, "can_upload_changes") == "true");
            res.PermissionSet.Add("can_view_tracking", ExtractStringValue(permissions, "can_view_tracking") == "true");
            res.PermissionSet.Add("can_manipulate", ExtractStringValue(permissions, "can_manipulate") == "true");
            res.PermissionSet.Add("can_comment", ExtractStringValue(permissions, "can_comment") == "true");
            res.PermissionSet.Add("can_invite_with_link", ExtractStringValue(permissions, "can_invite_with_link") == "true");
            res.PermissionSet.Add("can_access_anonymously", ExtractStringValue(permissions, "can_access_anonymously") == "true");
            res.PermissionSet.Add("can_download_pdf", ExtractStringValue(permissions, "can_download_pdf") == "true");
            res.PermissionSet.Add("can_delete", ExtractStringValue(permissions, "can_delete") == "true");
            res.PermissionSet.Add("inherits_from_parent", ExtractStringValue(permissions, "inherits_from_parent") == "true");

            return res;
        }

        private static string ExtractStringValue(string node, string name)
        {
            var startPos = node.IndexOf(string.Format("\"{0}\":", name)) + name.Length + 3;
            bool isInQuotes = false;
            var found = string.Empty;
            for (int i = startPos; i < node.Length; i++)
            {
                if (node[i] == '\"'
                    && isInQuotes == false)
                {
                    isInQuotes = true;
                    continue;
                }
                else if (node[i] == '\"'
                    && isInQuotes && node[i - 1] != '\\')
                {
                    isInQuotes = false;
                    break;
                }

                if (node[i] == '}' &&
                    isInQuotes == false)
                {
                    break;
                }

                if (node[i] == ',' &&
                    isInQuotes == false)
                {
                    break;
                }

                found += node[i];
            }
            return found.Replace("\\\"", "\"");
        }

        private static string ExtractAuthorizationValue(string node, string name)
        {
            var startPos = node.IndexOf(string.Format("\\\"{0}\\\":", name)) + name.Length + 5;
            bool isInQuotes = false;
            var found = string.Empty;
            for (int i = startPos; i < node.Length; i++)
            {
                if (node[i] == '\\'
                    && isInQuotes == false)
                {
                    isInQuotes = false;
                    continue;
                }
                else if (node[i] == '\\'
                    && isInQuotes)
                {
                    isInQuotes = false;
                    break;
                }
                if (node[i] == '\"'
                    && isInQuotes == false)
                {
                    isInQuotes = true;
                    continue;
                }
                else if (node[i] == '\"'
                    && isInQuotes)
                {
                    isInQuotes = false;
                    break;
                }

                if (node[i] == '}' &&
                    isInQuotes == false)
                {
                    break;
                }

                if (node[i] == ',' &&
                    isInQuotes == false)
                {
                    break;
                }

                found += node[i];
            }
            return found;
        }

        private static int ExtractIntValue(string node, string name)
        {
            var temp = ExtractStringValue(node, name);
            int id;
            if (int.TryParse(temp, out id))
            {
                return id;
            }
            return 0;
        }

        private static long ExtractLongValue(string node, string name)
        {
            var temp = ExtractStringValue(node, name);
            long id;
            if (long.TryParse(temp, out id))
            {
                return id;
            }
            return 0;
        }

        private static string ExtractNode(string node, string name)
        {
            var startPos = node.IndexOf(string.Format("\"{0}\":{{", name)) + name.Length + 5;
            var endPos = node.IndexOf("},", startPos);
            if (endPos < 0)
            {
                endPos = node.Length;
            }

            var subNode = node.Substring(startPos, endPos - startPos);
            return subNode;
        }

        private static string ExtractNodeWithSubNodes(string node, string name)
        {
            var startPos = node.IndexOf(string.Format("\"{0}\":{{", name)) + name.Length + 5;
            var endPos = node.IndexOf("}},", startPos);
            
            if (endPos < 0)
            {
                endPos = node.Length;
                return node.Substring(startPos, endPos - startPos);
            }
            
            endPos++;

            var subNode = node.Substring(startPos, endPos - startPos);
            return subNode + ",";
        }

        private static List<string> ExtractArrayNode(string node, string name)
        {
            var start = node.IndexOf(string.Format("\"{0}\":[{{", name));
            if (start > -1)
            {
                var startPos = start + name.Length + 5;
                var endPos = node.LastIndexOf("}]}");
                if (endPos < 0)
                {
                    endPos = node.Length;
                }
                var subNode = node.Substring(startPos, endPos - startPos);
                var elements = subNode.Split(new[] { "},{" }, StringSplitOptions.RemoveEmptyEntries);

                return elements.ToList();
            }
            else
            {
                return new List<string>();
            }
        }


        private static FileComment ExtractFileComment(string result)
        {
            var found = new FileComment();

            found.Id = ExtractIntValue(result, "id");
            found.CreatedAt = ExtractDate(result, "created_at");
            found.UserName = ExtractStringValue(result, "name");
            found.FileId = ExtractIntValue(result, "file_id");
            found.PageNumber = ExtractIntValue(result, "page_number");
            found.FileVersion = ExtractIntValue(result, "file_version");
            found.Body = ExtractStringValue(result, "body");
            found.ReplyToId = ExtractIntValue(result, "reply_to_id");
            found.Positional = ParsePositional(result);

            return found;
        }

        internal static Positional ParsePositional(string data)
        {
            Positional positional;

            positional.x = ExtractIntValue(data, "x_position");
            positional.y = ExtractIntValue(data, "y_position");
            positional.width = ExtractIntValue(data, "width");
            positional.height = ExtractIntValue(data, "height");

            return positional;
        }


        private static FileVersionDetails ExtractVersion(string result, bool isChunked)
        {
            var found = new FileVersionDetails();
            found.Name = ExtractStringValue(result, "file_name");
            found.Size = ExtractLongValue(result, "file_size");
            found.Id = ExtractIntValue(result, "id");
            found.FileId = ExtractIntValue(result, "file_id");
            found.Version = ExtractIntValue(result, "version");
            found.ImageUrl = ExtractStringValue(result, "page1_full");
            found.ThumbUrl = ExtractStringValue(result, "page1_thumb");
            found.Creator = ExtractUserData(ExtractNode(result, "creator"));
            DateTime created_at;
            DateTime.TryParse(ExtractStringValue(result, "created_at"), out created_at);
            found.CreateDate = created_at;
            if (isChunked == false)
            {
                var node = ExtractNode(result, "upload");

                found.AclType = ExtractStringValue(node, "acl");
                found.Action = ExtractStringValue(node, "action");
                found.AwsAccessKey = ExtractStringValue(node, "AWSAccessKeyId");
                found.Key = ExtractStringValue(node, "key");
                found.Policy = ExtractStringValue(node, "policy");
                found.Signature = ExtractStringValue(node, "signature");
                found.SuccessRedirect = ExtractStringValue(node, "success_action_redirect");
                found.ContentType = ExtractStringValue(node, "Content-Type");
                found.Cache = ExtractStringValue(node, "Cache-Control");
                found.Encryption = ExtractStringValue(node, "x-amz-server-side-encryption");
            }
            else
            {
                var node = ExtractNode(result, "complete_file");

                found.CompleteId = ExtractIntValue(node, "id");
            }

            found.ApiVersion = ApiVersion.One;

            return found;
        }

        private static FileVersionDetails ExtractVersion3(string result, bool isChunked)
        {
            var found = new FileVersionDetails();
            found.Name = ExtractStringValue(result, "file_name");
            found.Id = ExtractIntValue(result, "id");
            found.FileId = ExtractIntValue(result, "file_id");
            found.Version = ExtractIntValue(result, "version");
            found.ImageUrl = ExtractStringValue(result, "page1_full");
            found.ThumbUrl = ExtractStringValue(result, "page1_thumb");
            found.Creator = ExtractUserData(ExtractNode(result, "creator"));
            DateTime created_at;
            DateTime.TryParse(ExtractStringValue(result, "created_at"), out created_at);
            found.CreateDate = created_at;
            if (isChunked == false)
            {
                var node = ExtractNode(result, "complete_file");

                var uploadNode = ExtractNode(node, "upload");

                found.Action = ExtractStringValue(uploadNode, "action");
                found.HttpVerb = ExtractStringValue(uploadNode, "http_verb");
                found.SuccessRedirect = ExtractStringValue(uploadNode, "success_action_redirect");

                var authNode = ExtractNode(uploadNode, "auth_headers");

                found.ContentLength = ExtractAuthorizationValue(authNode, "content-length");
                found.Authorization = ExtractAuthorizationValue(authNode, "authorization");
                found.ContentType = ExtractAuthorizationValue(authNode, "content-type");
                found.Encryption = ExtractAuthorizationValue(authNode, "x-amz-server-side-encryption");
                found.AuthDate = ExtractAuthorizationValue(authNode, "x-amz-date");
            }
            else
            {
                var node = ExtractNode(result, "complete_file");

                found.CompleteId = ExtractIntValue(node, "id");
            }

            found.ApiVersion = ApiVersion.Three;

            return found;
        }

        #endregion

        public static UserDetails ParseCurrentUserData(string user)
        {
            var res = new UserDetails();
            res.UserId = ExtractStringValue(user, "uuid");
            res.Email = ExtractStringValue(user, "email");
            res.UserName = string.Format("{0} {1}", ExtractStringValue(user, "first_name"), ExtractStringValue(user, "last_name"));
            res.RootFolderId = ExtractIntValue(user, "root_folder_id");
            var nodeAccount = ExtractNode(user, "account");

            var domain = ExtractStringValue(nodeAccount, "name");
            res.Domain = string.Equals(domain, "null") ? string.Empty : domain;
            res.AccountId = ExtractStringValue(nodeAccount, "id");
            res.AccountUuId = ExtractStringValue(nodeAccount, "uuid");
            return res;
        }

        public static List<UserDetails> ParseAccountUsersData(string users)
        {
            var ret = new List<UserDetails>();

            var usersNode = ExtractArrayNode(users, "users");
            foreach (var user in usersNode)
            {
                ret.Add(new UserDetails()
                {
                    UserId = ExtractStringValue(user, "uuid"),
                    Email = ExtractStringValue(user, "email"),
                    UserName = string.Format("{0} {1}", ExtractStringValue(user, "first_name"), ExtractStringValue(user, "last_name"))
                });
            }

            return ret;
        }

        public static WSServer ParseWSServerData(string data)
        {
            WSServer res = new WSServer();
            res.ServerUrl = ExtractStringValue(data, "server");
            res.QuesryString = ExtractStringValue(data, "query_string");
            var nd = ExtractNode(data, "query_params");
            res.ctype = ExtractStringValue(nd, "ctype");
            res.token = ExtractStringValue(nd, "token");
            return res;
        }

        public static FileDetails ParseFileData(string file, int folderId)
        {
            var newFile = new FileDetails();
            newFile.Id = ExtractIntValue(file, "id");
            newFile.FriendlyName = ExtractStringValue(file, "name");
            newFile.Name = ExtractStringValue(file, "file_name");
            newFile.RemoteUrl = ExtractStringValue(file, "url");
            //newFile.FolderId = folderId;
            newFile.UpdateDate = ExtractDate(file, "updated_at");
            newFile.CreatedAt = ExtractDate(file, "created_at");
            newFile.FolderId = ExtractIntValue(file, "folder_id");
            newFile.VersionNumber = ExtractIntValue(file, "version");
            newFile.DownloadPassword = ExtractStringValue(file, "password");
            newFile.Creator = ExtractUserData(ExtractNode(file, "creator"));
            newFile.Updater = ExtractUserData(ExtractNode(file, "updater"));
            string deleted = ExtractStringValue(file, "is_deactivated");
            newFile.IsDeleted = (string.IsNullOrEmpty(deleted) || deleted == "false") ? false : true;
            return newFile;
        }

        private static DateTime ExtractDate(string result, string name)
        {
            var str = ExtractStringValue(result, name);
            DateTime d;
            DateTime.TryParse(str, out d);
            return d;
        }

        public static IEnumerable<FileDetails> ParseFilesResult(string result, int folderId)
        {
            var files = new List<FileDetails>();

            var fileNodes = ExtractArrayNode(result, "files");
            var pagintation = ExtractNode(result, "pagination");
            foreach (var file in fileNodes)
            {
                files.Add(ParseFileData(file, folderId));
            }
            return files;
        }

        public static IEnumerable<UserDetails> ParseMembersResult(string result)
        {
            var members = new List<UserDetails>();
            var ancestors = ExtractArrayNode(result, "members");
            foreach (var ancestor in ancestors)
            {
                members.Add(ExtractUserData(ancestor));
            }
            return members;
        }

        public static IEnumerable<FolderDetails> ParseFoldersResult(string result)
        {
            var found = new List<FolderDetails>();
            if (result.Contains("["))
            {
                var indexof = result.IndexOf("[");
                if (indexof + 2 < result.Length)
                {
                    var array = result.Substring(indexof + 2);
                    if (array.Length > 3)
                    {
                        array = array.Remove(array.Length - 3);
                        var folders = array.Split(new[] { "},{" }, StringSplitOptions.RemoveEmptyEntries);

                        foreach (var folder in folders)
                        {
                            found.Add(ExtractFolder(folder));
                        }
                    }
                }
            }
            return found;
        }

        public static FolderDetails ParseFolderResult(string result)
        {
            return ExtractFolder(result);
        }

        public static FolderDetails ParseFolderResult(byte[] result)
        {
            var returnResponse = Encoding.UTF8.GetString(result);
            return ExtractFolder(returnResponse);
        }

        public static FileVersionDetails ParseVersionResult(byte[] results, bool isChunked)
        {
            var returnResponse = Encoding.UTF8.GetString(results);

            var node = ExtractNode(returnResponse, "upload");
            var result = ExtractVersion(returnResponse, isChunked);
            
            if (ExtractStringValue(node, "action") != @"https://skydox-manuel.s3.amazonaws.com/")
            {
                result.ApiVersion = ApiVersion.Three;
            }

            return result;
        }

        public static FileVersionDetails ParseVersionResult3(byte[] results, bool isChunked)
        {
            var returnResponse = Encoding.UTF8.GetString(results);

            var node = ExtractNode(returnResponse, "upload");

            return ExtractVersion3(returnResponse, isChunked);
        }

        public static List<FileVersionDetails> ParseVersionsResult(string result)
        {
            var versions = new List<FileVersionDetails>();

            var versionNodes = ExtractArrayNode(result, "file_versions");
            foreach (var node in versionNodes)
            {
                versions.Add(ExtractVersion(node, true));
            }
            return versions;
        }

        public static List<FileComment> ParseFileCommentsResult(string result)
        {
            var found = new List<FileComment>();
            if (result.Contains("["))
            {
                var indexof = result.IndexOf("[");
                if (indexof + 2 < result.Length)
                {
                    var array = result.Substring(indexof + 2);
                    if (array.Length > 3)
                    {
                        array = array.Remove(array.Length - 3);
                        var comments = array.Split(new[] { "},{" }, StringSplitOptions.RemoveEmptyEntries);

                        foreach (var comment in comments)
                        {
                            found.Add(ExtractFileComment(comment));
                        }
                    }
                }
            }
            return found;
        }

        public static string ParseMultiPartId(byte[] results)
        {
            var returnResponse = Encoding.UTF8.GetString(results);
            var node = ExtractNode(returnResponse, "multipart_upload");
            return ExtractStringValue(node, "id");
        }

        public static MultiPartDetails ParseMultiPart(string results)
        {
            var multiPart = new MultiPartDetails();
            try
            {
                var node = ExtractNode(results, "multipart_upload");
                var subNode = ExtractNode(node, "parameters");
                multiPart.Action = ExtractStringValue(subNode, "action");
                multiPart.ContentType = ExtractStringValue(subNode, "Content-Type");
                multiPart.Authorisation = ExtractStringValue(subNode, "Authorization");
                multiPart.AmsDate = ExtractStringValue(subNode, "x-amz-date");
            }
            catch (Exception)
            {
            }
            return multiPart;
        }

        internal static DialogSettings ParseDialogSettings(string data)
        {
            var settings = new DialogSettings();
            settings.dialog_create_folder_height = ExtractIntValue(data, "dialog_create_folder_height");
            settings.dialog_create_folder_width = ExtractIntValue(data, "dialog_create_folder_width");
            settings.dialog_login_height = ExtractIntValue(data, "dialog_login_height");
            settings.dialog_login_width = ExtractIntValue(data, "dialog_login_width");
            settings.dialog_select_folder_height = ExtractIntValue(data, "dialog_select_folder_height");
            settings.dialog_select_folder_width = ExtractIntValue(data, "dialog_select_folder_width");
            return settings;
        }

        internal static List<Activity> ParseActivities(string activities, int folderid, int fileid, int fileversion = 0)
        {
            var activitesNodes = ExtractArrayNode(activities, "activities");
            var activityList = new List<Activity>();

            if (activitesNodes == null)
                return null;

            foreach (var activity in activitesNodes)
            {
                if ((fileid == ExtractIntValue(activity, "file_id") && fileversion == ExtractIntValue(activity, "file_version")) && folderid == 0) 
                    activityList.Add(ParseActivity(activity));
                else if((fileid == ExtractIntValue(activity, "file_id") && fileversion == 0) && folderid == 0) // get all versions
                    activityList.Add(ParseActivity(activity));
                else if(folderid != 0)
                    activityList.Add(ParseActivity(activity));
            }

            return activityList;
        }

        internal static Activity ParseActivity(string data)
        {
            var activity = new Activity();

            activity.Noun = ExtractStringValue(data, "noun");
            activity.Verb = ExtractStringValue(data, "verb");
            activity.TimeCreated = ExtractStringValue(data, "created_at");
            activity.CurrentVersion = ExtractIntValue(data, "file_version");
            activity.ActyvityId = ExtractStringValue(data, "id");

            var member = ExtractNode(data, "member");

            if (!string.IsNullOrEmpty(member))
                activity.MemberId = ExtractIntValue(member, "id");

            var nodeCreator = ExtractNode(data, "creator");

            if(!string.IsNullOrEmpty( nodeCreator))
                activity.UserName = ExtractStringValue(nodeCreator, "name");

            var nodeChanges = ExtractNodeWithSubNodes(data, "changes");

            if (!string.IsNullOrEmpty(nodeChanges))
            {
                
                var nodeName = ExtractNode(nodeChanges, "name");

                if (!string.IsNullOrEmpty(nodeName) && nodeChanges.Contains("name"))
                {
                    activity.ChangesNameOld = ExtractStringValue(nodeName, "old");
                    activity.ChangesNameNew = ExtractStringValue(nodeName, "new");
                }

                var nodeVersion = ExtractNode(nodeChanges, "version");

                if (!string.IsNullOrEmpty(nodeVersion) && nodeChanges.Contains("version"))
                {
                    activity.ChangesVersionOld = ExtractIntValue(nodeVersion, "old");
                    activity.ChangesVersionNew = ExtractIntValue(nodeVersion, "new");
                }
            }

            var nodeFolder = ExtractNode(data, "folder");

            if (!string.IsNullOrEmpty(nodeFolder))
                activity.FolderName = ExtractStringValue(nodeFolder, "name");

            return activity;
        }



        internal static Dictionary<string, int> Parsepagination(string data)
        {
            var pagination = new Dictionary<string, int>();

            pagination.Add("current_page", ExtractIntValue(data, "current_page"));
            pagination.Add("total_entries", ExtractIntValue(data, "total_entries"));
            pagination.Add("total_pages", ExtractIntValue(data, "total_pages"));

            return pagination;
        }

        public class Pagination
        {
            public int CurrentPage { get; set; }
            public int TotalEntries { get; set; }
 
            public int TotalPages { get; set; }
        }
 
        internal static Pagination ParsePagination(string data)
        {
            var pagination = new Pagination();
 
            pagination.CurrentPage = ExtractIntValue(data, "current_page");
            pagination.TotalEntries = ExtractIntValue(data, "total_entries");
            pagination.TotalPages = ExtractIntValue(data, "total_pages");
 
            return pagination;
        }

        internal static List<Member> ParseMembers(string data)
        {
            var members = new List<Member>();
            var membersNodes = ExtractArrayNode(data, "members");

            foreach (var member in membersNodes)
            {
                members.Add(ParseMember(member));
            }

            return members;
        }

        internal static Member ParseMember(string data)
        {
            var memeber = new Member();

            memeber.MemberName = ExtractStringValue(data, "name");
            memeber.MemberId = ExtractIntValue(data, "id");
            memeber.Email = ExtractStringValue(data, "email");
            memeber.IsDeleted = ExtractStringValue(data, "is_deleted") == "true";

            return memeber;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/SyncDialog/SyncDialogWindow.xaml.cs
﻿using System.Collections.Generic;
using System.Linq;
using System.Windows;
using System.Windows.Input;
using Workshare.Components.Views.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.SyncDialog
{
    /// <summary>
    /// Returns selected by user actions for given activities
    /// </summary>
    public partial class SyncDialogWindow2
    {
        ConflictOptions ConflictOption { get; set; }
        ConflictVersionOptions VersionsOption { get; set; }
        public bool IsClose { get; private set; }
        
        public SyncDialogWindow2()
        {
            InitializeComponent();
        }

        private SyncDialogViewModel Vm
        {
            get
            {
                return (SyncDialogViewModel) DataContext;
            }
        }

        private void UpdateViewModel()
        {
            Vm.SelectedVersionsOption = VersionsOption;
            Vm.SelectedAction = ConflictOption;
        }

        public IEnumerable<ImportDocumentAction> GetSelectedActions()
        {
            return Vm.GetSelectedActions();
        }

        public SyncDialogWindow2(IEnumerable<ImportFileActivity> importActivities)
            : this()
        {
            var firstActivity = importActivities.First();
            var newCount = importActivities.Count(a => a.Changes.Any(c => c.Type == ChangeType.RemoteAdded));
            var allCount = importActivities.Count();
            var dmsName = firstActivity.DmsFile == null ? string.Empty : firstActivity.DmsFile.Name;
            var wsName = firstActivity.Filename;
            var onlyNewFiles = allCount == newCount;
            var versionsCount =
                firstActivity.Changes.Where(a => a.NewerVersions != null && a.NewerVersions.Any())
                    .Select(a => a.NewerVersions.Count)
                    .FirstOrDefault();
            this.DataContext = new SyncDialogViewModel(importActivities, wsName, dmsName, versionsCount, allCount, newCount, onlyNewFiles);
            cb_latestVersion.IsChecked = true;
            cb_newDocument.IsChecked = true;
            if (onlyNewFiles)
            {
                grSaveType.IsEnabled = false;
            }
            if (allCount == 1 && versionsCount == 1 && onlyNewFiles)
            {
                cb_allVersion.IsEnabled = false;
            }
        }

        private void DockPanel_MouseDown_1(object sender, MouseButtonEventArgs e)
        {
            OnTitleMouseDown(sender, e);
        }

        private void cb_LatestVersion_Checked(object sender, RoutedEventArgs e)
        {
            VersionsOption = ConflictVersionOptions.Latest;
            UpdateViewModel();
        }

        private void cb_AllVersions_Checked(object sender, RoutedEventArgs e)
        {
            VersionsOption = ConflictVersionOptions.All;
            UpdateViewModel();
        }

        private void cb_newDocument_Checked_1(object sender, RoutedEventArgs e)
        {
            ConflictOption = ConflictOptions.KeepBoth;
            UpdateViewModel();
        }

        private void cb_newVersion_Checked_1(object sender, RoutedEventArgs e)
        {
            ConflictOption = ConflictOptions.Replace;
            UpdateViewModel();
        }

        private void OwnWindow_Closed(object sender, System.EventArgs e)
        {
            IsClose = true;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/SettingsStorage/SettingsOptions.cs
﻿namespace Workshare.Integration.SettingsStorage
{
    public static class SettingsOptions
    {
        public static readonly string PagingSizeInTrueSync = "ActivitiesPerPage";
    }
}
<file_sep>/WSComponents/src/Mixpanel.NET/Services/EventTrackerService.cs
using System;
using System.Collections.Generic;
using System.Text;
using Mixpanel.NET.Events;
using Workshare.Components.WSLogger;

namespace Mixpanel.NET.Services
{
    // REDO IT IMM
    // internal static class Tracker
    public static class EventTrackerService
    {
        static bool _enableReporting = true;
        static string _proxyUrl = "http://events.workshare.com";
        static string _mixpanelProjectToken = "d3ee5e47158b4405beb1dcca3ae8e664";
        
        public static bool IsReportingEnabled()
        {
            return _enableReporting;
        }
                
        static TrackerOptions GetOptions()
        {
            TrackerOptions options = new TrackerOptions();
            options.SetEventTime = true;

            if (!String.IsNullOrEmpty(_proxyUrl))
            {
                options.ProxyUrl = _proxyUrl;
            }

            return options;
        }

        static MixpanelTracker GetTracker(string token)
        {
            return new MixpanelTracker(_mixpanelProjectToken, null, GetOptions());
        }

        static string GetEventName(string eventName)
        {
            return "Integration_DMS_IMAN_" + eventName;
        }
        
        //This method is used to add events
        public static bool Track(string eventName, IDictionary<string, object> properties)
        {            
            try
            {
                if (!IsReportingEnabled())
                {
                    return true;
                }

                eventName = GetEventName(eventName);

                MixpanelTracker tracker = GetTracker(_mixpanelProjectToken);
                bool result = tracker.Track(eventName, properties);
                
                LogTrace(eventName, properties);
                
                return result;
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                return false;
            }
        }

        static void LogTrace(string eventName, IDictionary<string, object> properties)
        {
            StringBuilder sb = new StringBuilder("Mixpanel ");
            sb.Append("Event: ").Append(eventName).Append(" Properties: ");
                
            if (properties.ContainsKey("Name"))
            {
                sb.Append("Name=[").Append(properties["Name"]).Append("] ");
            }

            foreach (var kvp in properties)
            {
                if (String.Compare(kvp.Key, "Name") != 0)
                {
                    sb.Append(kvp.Key).Append("=[").Append(kvp.Value).Append("] ");
                }
            }
            Logger.WriteTrace(sb.ToString());
        }
    }
}<file_sep>/WSComponents/src/WSComponents/Services/ErrorReporterService.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Components.Interfaces;
using Workshare.Integration.Exceptions;

namespace Workshare.Components.Services
{
    public class ErrorReporterService
    {
        private readonly List<KeyValuePair<Guid, ItemException>> _errors;
        readonly IModuleView _view;

        public ErrorReporterService(IModuleView view)
        {
            _view = view;
            _errors = new List<KeyValuePair<Guid, ItemException>>();
        }

        public void Add(Guid scopeId, ItemException error)
        {
            var item = new KeyValuePair<Guid, ItemException>(scopeId, error);
            _errors.Add(item);
        }

        public void AddRange(Guid scopeId, List<ItemException> errors)
        {
            foreach (var itemException in errors)
            {
                var item = new KeyValuePair<Guid, ItemException>(scopeId, itemException);
                _errors.Add(item);
            }
        }

        public void Add(Guid scopeId, Exception error)
        {
            var item = new KeyValuePair<Guid, ItemException>(scopeId, new ItemException {Error = error});
            _errors.Add(item);
        }

        public void AddRange(Guid scopeId, List<Exception> errors)
        {
            foreach (var exception in errors)
            {
                var item = new KeyValuePair<Guid, ItemException>(scopeId, new ItemException {Error = exception});
                _errors.Add(item);
            }
        }
        
        public bool IsEmpty
        {
            get { return !_errors.Any(); }
        }

        public void ReportIfNeeded(Guid scopeId)
        {
            if (IsEmpty) { return; }

            var exceptions = _errors.Where(r => r.Key == scopeId).Select(k => k.Value).Distinct();
            _view.ShowErrors(exceptions);

            ClearService(scopeId);
        }

        private void ClearService(Guid scopeId)
        {
            _errors.RemoveAll(e => e.Key == scopeId);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/ActionStrategy/UploadStrategy.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using Workshare.Components.Helpers;
using Workshare.Components.WSLogger;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Properties;
using Workshare.Integration.WsProxies;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Integration.Processor.Strategies.ActionStrategy
{
    public class UploadStrategy : ActionStrategy
    {
        readonly WsProxy _wsProxy;
        readonly IAuthProvider _auth;
        readonly DmsWorkerBase _dmsWorker;
        readonly SyncInfoService _syncInfoService;

        public UploadStrategy(WsProxy wsProxy, IAuthProvider auth, DmsWorkerBase dmsWorker, SyncInfoService syncInfoService)
            : base(syncInfoService)
        {
            this._wsProxy = wsProxy;
            this._auth = auth;
            this._dmsWorker = dmsWorker;
            this._syncInfoService = syncInfoService;
        }

        void EnsureParentFolderExistsOnWs(WsUser user, FileMap fileMap)
        {
            var firstAncesstoronWs = fileMap.Parent as FolderMap;
            var ancesstors = new List<FolderMap>();
            while (firstAncesstoronWs != null && !firstAncesstoronWs.HasRemote())
            {
                ancesstors.Insert(0, firstAncesstoronWs);
                firstAncesstoronWs = firstAncesstoronWs.Parent as FolderMap;
            }
            if (firstAncesstoronWs != null)
            {
                var currentParent=firstAncesstoronWs;
                foreach (var toCreate in ancesstors)
                {
                    var createdFolder=_wsProxy.CreateFolder(user,currentParent.WsFolder.Id, toCreate.LocalFolder.DisplayName);
                    toCreate.WsFolder = createdFolder;
                    _syncInfoService.UpdateSyncInfo(toCreate.LocalFolder, new ActionContext(Services.ActionType.Upload)
                    {
                        WsFolder=createdFolder
                    });
                    currentParent = toCreate;
                }
            }
        }

        public override ProcessResult Process(FileMap fileMap, ItemMapActivityAction action)
        {
            try
            {
                var uploadAction = (UploadDocumentAction)action;
                var user = _auth.GetCurrentWSUser2();

                var allLocalVersionMaps = fileMap.Maps.OfType<VersionMap>().Where(a => a.HasLocal());

                foreach (var versionMap in allLocalVersionMaps)
                {
                    if (uploadAction.VersionIds.Contains(versionMap.LocalVersion.Id))
                    {
                        var filePath = _dmsWorker.GetFilePath(versionMap.LocalVersion);
                        var name = _dmsWorker.GetName(versionMap.LocalVersion);
                        var friendlyName = _dmsWorker.GetFriendlyName(versionMap.LocalVersion);

                        var friendlyNameOnWorkshare = !string.IsNullOrEmpty(friendlyName)
                            ? friendlyName
                            : (!string.IsNullOrEmpty(name) ? FileUtils.GetFileNameWithoutExtension(name) : "unknown");
                        var nameOnWorkshare = !string.IsNullOrEmpty(name) ? name : "unknown";

                        if (!fileMap.HasRemote())
                        {
                            var parentFolderMap = fileMap.GetLocalParent();

                            _syncInfoService.CanUpdateSyncInfoOrThrow(fileMap.LocalFile, Operations.Send);
                            _syncInfoService.CanUpdateSyncInfoOrThrow(versionMap, Operations.Send);
                            _dmsWorker.CanUpdateVersionOrThrow(versionMap.LocalVersion, Operations.Send);
                            _syncInfoService.CanUpdateSendDataOrThrow(parentFolderMap);

                            EnsureParentFolderExistsOnWs(user, fileMap);
                            if (parentFolderMap.WsFolder != null)
                            {
                                var parentFolderId = parentFolderMap.WsFolder.Id;
                                var uploadedFile = _wsProxy.UploadFile(user,
                                    WsUtils.RemoveInvalidSymbolsFromFileName(friendlyNameOnWorkshare),
                                    WsUtils.RemoveInvalidSymbolsFromFileName(nameOnWorkshare), filePath, parentFolderId);
                                _dmsWorker.AddHistory(versionMap.LocalVersion, string.Empty, string.Format(RES.STR_HISTORY_ITEMEXPORT, DateTime.Now.ToString(Activity.TimeFormat)), Operations.Send);
                                _syncInfoService.UpdateSyncInfo(fileMap.LocalFile, new ActionContext(Services.ActionType.Upload)
                                {
                                    WsFile = uploadedFile
                                });
                                fileMap.WsFile = uploadedFile;
                                versionMap.WsVersion = uploadedFile.Versions.FirstOrDefault();
                                _syncInfoService.UpdateSyncInfo(versionMap.LocalVersion, new ActionContext(Services.ActionType.Upload)
                                {
                                    WsVersion = versionMap.WsVersion
                                });
                                if (parentFolderMap.HasLocal())
                                {
                                    _syncInfoService.UpdateSendDataInfo(parentFolderMap.LocalFolder,
                                        new List<int> { uploadedFile.Id });
                                }
                            }
                            else if (parentFolderMap.ProcessState == ProcessState.Error)
                            {
                                throw parentFolderMap.Error;
                            }
                            else
                            {
                                throw new Exception("No parent folder linked to Workshare");
                            }

                        }
                        else
                        {
                            _dmsWorker.CanUpdateVersionOrThrow(versionMap.LocalVersion, Operations.Send);
                            _syncInfoService.CanUpdateSyncInfoOrThrow(versionMap, Operations.Send);
                            var wsVersion = _wsProxy.UploadNewVersion(user, fileMap.WsFile, filePath, name);
                            _dmsWorker.AddHistory(versionMap.LocalVersion, string.Empty, string.Format(RES.STR_HISTORY_ITEMEXPORT, DateTime.Now.ToString(Activity.TimeFormat)), Operations.Send);
                            _syncInfoService.UpdateSyncInfo(versionMap.LocalVersion, new ActionContext(Services.ActionType.Upload)
                            {
                                WsVersion = wsVersion
                            });
                            versionMap.WsVersion = wsVersion;
                        }
                    }
                }

                return ProcessResult.Processed;
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode(HttpStatusCode.Forbidden) || ex.IsStatusCode(HttpStatusCode.Unauthorized))
                {
                    throw new CloudFolderAccessDenied(Resources.STR_UNABLE_SYNC, Resources.STR_UNABLESYNCFILE_TEXT, ex);
                }
                if (ex.IsConnectionError())
                {
                    throw new OfflineException();
                }

                Logger.WriteError("UploadStrategy Process catch WebException : ", ex);
                throw;
            }
            catch (Exception ex)
            {
                if (ex.IsConnectionError())
                {
                    throw new OfflineException();
                } 
                
                Logger.WriteError("UploadStrategy Process catch Exception : ", ex);
                throw;
            }
        }

        public override ProcessResult Process(FolderMap folderMap, ItemMapActivityAction action)
        {
            return ProcessResult.Processed;
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshate.HookEvents/HookMoveFolderCmd.cs
﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Diagnostics;
using System.Runtime.InteropServices;
using Com.Interwoven.WorkSite.iManage;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.Worksite.iManExt2;
using Workshare.Components.Interfaces;
using Workshare.Components.WSLogger;

namespace Workshare.HookEvents
{
    [ClassInterface(ClassInterfaceType.None)]
    [Guid("F311F3A1-E00E-48F3-AA23-A4580A97B8B3")]
    [ComVisible(true)]
    public class HookMoveFolderCmd : ICommand, Com.Interwoven.Worksite.iManExt2._ICommandEvents_Event
    {
        IManMoveFolderCmd cmd;

        bool isCancel = true;

        public HookMoveFolderCmd()
        {
            cmd = new IManMoveFolderCmd();
            cmd.OnCancel += cmd_OnCancel;
            cmd.OnInitDialog += cmd_OnInitDialog;
            cmd.PostOnOK += cmd_PostOnOK;
            cmd.PreOnOK += cmd_PreOnOK;
        }

        public int Accelerator
        {
            get
            {
                return cmd.Accelerator;
            }
            set
            {
                cmd.Accelerator = value;
            }
        }

        public object Bitmap
        {
            get
            {
                return cmd.Bitmap;
            }
            set
            {
                cmd.Bitmap = value;
            }
        }

        public ContextItems Context
        {
            get
            {
                return cmd.Context;
            }
        }

        private List<IManDocument> GetFiles(IManFolder folder)
        {
            List<IManDocument> ret = new List<IManDocument>();

            foreach (object content in folder.Contents)
            {
                if (content is IManDocument)
                    ret.Add(content as IManDocument);
            }

            if (folder.SubFolders != null)
            {
                foreach (IManFolder subFolder in folder.SubFolders)
                    ret.AddRange(GetFiles(subFolder));
            }

            return ret;
        }

        public void Execute()
        {
            cmd.Execute();
            if (isCancel) // !!! unfortunatelly 'isCancel' is always true - 'targetFolder' is used to determine should we start sync process or not
            {
                try
                {
                    var targetFolder = ProcessIManageEvents.GetCmdContextItemValueByName(Context, "SelectedTargetIManFolderObject");
                    if (targetFolder != null)
                    {
                        IManFolder selectedFolder = ProcessIManageEvents.GetCmdContextItemValueByName(Context, "SelectedFolderObject") as IManFolder;
                        if (selectedFolder != null)
                        {
                            List<IManDocument> selectedObjectsList = new List<IManDocument>(GetFiles(selectedFolder));
                            if (selectedObjectsList.Count > 0)
                                ProcessIManageEvents.ProcessEvent(selectedObjectsList, EventOperation.MoveFolder, "HookMoveFolderCmd -> Execute");
                        }
                        else
                        {
                            Logger.Write("HookMoveFolderCmd: There is no data about selected folder", Severity.Information);
                        }
                    }
                }
                catch (Exception exc)
                {
                    Logger.Write(exc, Severity.Error);
                }
            }
        }

        public string HelpFile
        {
            get
            {
                return cmd.HelpFile;
            }
            set
            {
                cmd.HelpFile = value;
            }
        }

        public int HelpID
        {
            get
            {
                return cmd.HelpID;
            }
            set
            {
                cmd.HelpID = value;
            }
        }

        public string HelpText
        {
            get
            {
                return cmd.HelpText;
            }
            set
            {
                cmd.HelpText = value;
            }
        }

        public void Initialize(ContextItems Context)
        {
            cmd.Initialize(Context);
        }

        public string MenuText
        {
            get
            {
                return cmd.MenuText;
            }
            set
            {
                cmd.MenuText = value;
            }
        }

        public string Name
        {
            get
            {
                return cmd.Name;
            }
            set
            {
                cmd.Name = value;
            }
        }

        public int Options
        {
            get
            {
                return cmd.Options;
            }
            set
            {
                cmd.Options = value;
            }
        }

        public int Status
        {
            get
            {
                return cmd.Status;
            }
            set
            {
                cmd.Status = value;
            }
        }

        public Commands SubCommands
        {
            get
            {
                return cmd.SubCommands;
            }
            set
            {
                cmd.SubCommands = value;
            }
        }

        public string Title
        {
            get
            {
                return cmd.Title;
            }
            set
            {
                cmd.Title = value;
            }
        }

        public CommandType Type
        {
            get
            {
                return cmd.Type;
            }
            set
            {
                cmd.Type = value;
            }
        }

        public void Update()
        {
            cmd.Update();
        }

        void cmd_PreOnOK(object pMyInterface)
        {
            isCancel = false;
            if (PreOnOK != null)
            {
                PreOnOK(pMyInterface);
            }
        }

        void cmd_PostOnOK(object pMyInterface)
        {
            if (PostOnOK != null)
            {
                PostOnOK(pMyInterface);
            }
        }

        void cmd_OnInitDialog(object pMyInterface)
        {
            if (OnInitDialog != null)
            {
                OnInitDialog(pMyInterface);
            }
        }

        void cmd_OnCancel(object pMyInterface)
        {
            isCancel = true;
            if (OnCancel != null)
            {
                OnCancel(pMyInterface);
            }
        }

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_OnCancelEventHandler OnCancel;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_OnInitDialogEventHandler OnInitDialog;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_PostOnOKEventHandler PostOnOK;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_PreOnOKEventHandler PreOnOK;

    }
}<file_sep>/WSComponents/src/WSIntegration/WsProxies/WsProxy.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Net;
using Workshare.Components.Helpers;
using Workshare.Components.WSLogger;
using WorksharePlatform;

namespace Workshare.Integration.WsProxies
{
    public class WsProxy
    {
        public WsFile TryGetFile(WsUser wsUser, int fileId, int parentFolderId)
        {
            var file = PlatformService.TryGetFile(wsUser._user, fileId, parentFolderId);
            return file == null ? null : new WsFile(file, wsUser._user);
        }

        public WsFolder TryGetFolder(WsUser wsUser, int folderId)
        {
            var folder = PlatformService.TryGetFolder(wsUser._user, folderId);
            return folder == null ? null : new WsFolder(folder, wsUser._user);
        }

        public static bool IsFolderExist(WsUser wsUser, int folderId)
        {
            return PlatformService.IsFolderExists(wsUser._user, folderId, -1);
        }

        public IEnumerable<Activity> GetFileActivities(WsUser user, WsFile wsFileInfo, string lastActivityId)
        {
            return PlatformService.GetFileActivitiesImanage(user._user, wsFileInfo.file, 0, lastActivityId);
        }

        public WsVersion UploadNewVersion(WsUser user, WsFile wsFile, string filePath, string name)
        {
            if (wsFile == null) throw new ArgumentNullException("wsFile");
            wsFile.file.FilePath = filePath;
            wsFile.file.FriendlyName = FileUtils.GetFileNameWithoutExtension(name);
            wsFile.file.Name = name;
            PlatformService.UploadNewVersionOfFile3(user._user, wsFile.file);
            var versionNumber = wsFile.file.CurrentVersion.Version;
            wsFile.Versions = null;//TODO look maybe we can avoid refreshing of versions
            return wsFile.Versions.First(a => a.Version == versionNumber);

        }

        public void DeleteFile(WsUser _user, int _fileId)
        {
            PlatformService.DeleteFile2(_user._user, _fileId);
        }

        public void DeleteFolder(WsUser _user, int _folderId)
        {
            PlatformService.DeleteFolder(_user._user, _folderId);
        }

        public void AddAccountDataToWDS(WsUser _user, string _key, string _data)
        {
            PlatformService.CreateOrUpdateWDSDictionary(_user._user, _key, _data, RoleOfDictionary.accounts);
        }

        public string GetAccountDataFromWDS(WsUser _user, string _key)
        {
            return PlatformService.GetWDSDictionary(_user._user, _key, RoleOfDictionary.accounts);
        }

        public void DeleteAccountDataOnWDS(WsUser _user, string _key)
        {
            PlatformService.DeleteWDSDictionary(_user._user, _key, RoleOfDictionary.accounts);
        }

        public void AddUserDataToWDS(WsUser _user, string _key, string _data)
        {
            PlatformService.CreateOrUpdateWDSDictionary(_user._user, _key, _data, RoleOfDictionary.users);
        }

        public string GetUserDataFromWDS(WsUser _user, string _key)
        {
            return PlatformService.GetWDSDictionary(_user._user, _key, RoleOfDictionary.users);
        }

        public void DeleteUserDataOnWDS(WsUser _user, string _key)
        {
            PlatformService.DeleteWDSDictionary(_user._user, _key, RoleOfDictionary.users);
        }

        public bool IsUserLoggedIn(UserDetails user)
        {
            if (user == null)
            {
                return false;
            }

            string hostUri = PlatformService.ServiceUrl4 + "/current_user.json";

            try
            {
                var myReq = (HttpWebRequest)WebRequest.Create(hostUri);
                if (user.IsProxyEnable)
                {
                    myReq.Proxy = user.Proxy;
                    myReq.Proxy.Credentials = user.ProxyCredentials;
                }
                myReq.Method = "GET";
                myReq.Timeout = 2000;
                myReq.CookieContainer = user.SessionCookies;

                using (var response = (HttpWebResponse)myReq.GetResponse())
                {
                    using (var reader = new StreamReader(response.GetResponseStream()) )
                    {
                        string responcestring = reader.ReadToEnd();
                        if (!(responcestring.Contains("Not logged in") && responcestring.Contains("errors")))
                            return true;                        
                    }

                }
            }

            catch (Exception ex)
            {
                Logger.Write(ex, Severity.Warning);
            }

            return false;
        }

        internal WsFile UploadFile(WsUser user, string friendlyName, string name, string filePath, int parentFolderId)
        {
            var file = new FileDetails()
            {
                Name = name,
                FilePath = filePath,
                FriendlyName = friendlyName,
                FolderId = parentFolderId
            };
            try
            {
                PlatformService.UploadFile3(user._user, file);
                var createdFile = PlatformService.GetFile(user._user, file.Id, parentFolderId);
                var wscreatedFile = new WsFile(createdFile, user._user);
                var currentVersion = wscreatedFile.CurrentVersion;//TODO now it is requiered as some code uses directy Platformservice instead of Proies
                return wscreatedFile;
            }
            finally
            {
                //in case of exception we should delete temp files from temporary folder anyway
                file.DeleteFile();
            }
        }

        internal WsFolder CreateFolder(WsUser user, int parentId, string name)
        {
            var res = PlatformService.CreateFolder(user._user, name, "", parentId);
            return new WsFolder(res, user._user);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/ActivityFinder.cs
﻿using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Changes.Visitors;
using Workshare.Integration.Processor.Maps;

namespace Workshare.Integration.Processor.Changes
{
    public class ActivityFinder
    {
        private readonly ModuleBase _module;

        public ActivityFinder(ModuleBase module)
        {
            this._module=module;
        }

        public List<ImportFileActivity> GetImportActivities(ItemMap scanResult, IEnumerable<ImportFileActivity> existedActivities, bool useForceRequest = true)
        {
            var opt = new Options() { UseForceRequest = useForceRequest };
            opt.DoNotUpdate = true;
            var visitor = _module.Resolve<ImportActivityFinder>();
            visitor.FoundedActivities = existedActivities == null ? new List<ImportFileActivity>() : existedActivities.ToList();
            visitor.ActivitiesToUpdate = opt.ActivitiesToUpdateOnly;
            visitor.Options = opt;
            scanResult.Apply(visitor);
            return visitor.FoundedActivities;
        }

        public List<UploadFileActivity> GetUploadActivities(ItemMap scanResult, IEnumerable<UploadFileActivity> existedActivities, bool useForceRequest = true)
        {
            var opt = new Options() {UseForceRequest = useForceRequest};
            opt.DoNotUpdate = true;
            var visitor = _module.Resolve<UploadActivityFinder>();
            visitor.FoundedActivities = existedActivities == null ? new List<UploadFileActivity>() : existedActivities.ToList();
            visitor.ActivitiesToUpdate = opt.ActivitiesToUpdateOnly;
            visitor.Options = opt;
            scanResult.Apply(visitor);
            return visitor.FoundedActivities;
        }

        public void UpdateImportActivities(SummaryProcessResult scanResult, IEnumerable<ImportFileActivity> existedActivities, List<string> activityIdsToUpdate = null)
        {
            var opt = new Options()
            {
                ActivitiesToUpdateOnly = activityIdsToUpdate,
                UseForceRequest = true 
            };
            var visitor = _module.Resolve<ImportActivityFinder>();
            visitor.FoundedActivities = existedActivities == null ? new List<ImportFileActivity>() : existedActivities.ToList();
            visitor.ActivitiesToUpdate = opt.ActivitiesToUpdateOnly;
            visitor.Options = opt;
            scanResult.Apply(visitor);
        }

        public void UpdateUploadActivities(SummaryProcessResult scanResult, IEnumerable<UploadFileActivity> existedActivities, List<string> activityIdsToUpdate = null)
        {
            var opt = new Options()
            {
                UseForceRequest = true,
                ActivitiesToUpdateOnly = activityIdsToUpdate
            };
            var visitor = _module.Resolve<UploadActivityFinder>();
            visitor.FoundedActivities = existedActivities == null ? new List<UploadFileActivity>() : existedActivities.ToList();
            visitor.ActivitiesToUpdate = opt.ActivitiesToUpdateOnly;
            visitor.Options = opt;
            scanResult.Apply(visitor);
        }

        public void UpdateActivities(SummaryProcessResult scanResult, IEnumerable<FileMapActivity> existedActivities, List<string> activityIdsToUpdate = null)
        {
            UpdateImportActivities(scanResult, existedActivities.OfType<ImportFileActivity>(), activityIdsToUpdate);
            UpdateUploadActivities(scanResult, existedActivities.OfType<UploadFileActivity>(), activityIdsToUpdate);
        }

        public List<ItemMap> GetErrors(ItemMap scanResult)
        {
            return GetErrorsInternal(scanResult);
        }

        List<ItemMap> GetErrorsInternal(ItemMap map)
        {
            var res = new List<ItemMap>();

            if (map.Error != null)
            {
                res.Add(map);
            }

            foreach (var childMap in map.Maps)
            {
                res.AddRange(GetErrorsInternal(childMap));
            }

            return res;
        }


        //TODO make get update methods and remove initialize
        public IEnumerable<FileMapActivity> GetAllActivities(ItemMap scanResult, IEnumerable<FileMapActivity> existedActivities, bool useForceRequest = true)
        {
            var res = new List<FileMapActivity>();

            res.AddRange(this.GetImportActivities(scanResult, existedActivities.OfType<ImportFileActivity>(), useForceRequest).OfType<FileMapActivity>());
            res.AddRange(this.GetUploadActivities(scanResult, existedActivities.OfType<UploadFileActivity>(), useForceRequest).OfType<FileMapActivity>());

            return res;
        }

        public class Options
        {
            public IEnumerable<string> ActivitiesToUpdateOnly;
            public bool DoNotUpdate { set; get; }
            public bool UseForceRequest { get; set; }
        }
    }
}

<file_sep>/OpenText/src/Workshare.OpenText/Registering.cs
﻿using Microsoft.Win32;


namespace Workshare.OpenText
{
    public static class Registering
    {
        static string APP_CLSID = "Workshare.OpenText.WSOTMenuWrapper";//"{08986AE5-D79F-4EE7-B876-D1C69F09C01B}";
        static readonly string REGKEY = @"SOFTWARE\Hummingbird\PowerDOCS\OM\EventHandlers";
        static readonly string KeyName = @"WorkshareIntegration";

        public static void RegisterMenus()
        {
            var rkey = Registry.LocalMachine.OpenSubKey(REGKEY, true);
            if (rkey != null)
            {
                var kExtMenu = rkey.CreateSubKey(KeyName);
                if (kExtMenu != null)
                {
                    object def_value = kExtMenu.GetValue("");
                    if (def_value == null || string.IsNullOrEmpty(def_value.ToString()))
                    {
                        kExtMenu.SetValue("", APP_CLSID);
                    }
                }
                
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/BaseDMSItem.cs
﻿
namespace Workshare.Integration.Processor
{
    public abstract class BaseDMSItem
    {
        //TODO remove
    }
}
<file_sep>/WSComponents/src/WSIntegration/Enums/ConflictOptions.cs
﻿namespace Workshare.Integration.Enums
{
    public enum ConflictOptions
    {
        None,
        KeepBoth,
        Replace,
        UpdateOnTheWorkshare
    }

    public enum ConflictVersionOptions
    { 
        None,
        Latest,
        All
    }

    public enum CheckOutOptions
    {
        None,
        CheckOut,
        DontCheckOut
    }
}
<file_sep>/WSComponents/src/WSIntegration/Exceptions/CannotUpdateSyncInfoException.cs
﻿using System;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Properties;

namespace Workshare.Integration.Exceptions
{
    public class CannotUpdateDataOnWebDataStorageExeption:BaseException
    {
        public CannotUpdateDataOnWebDataStorageExeption(string message)
            : base("",message)
        {
        }
        public CannotUpdateDataOnWebDataStorageExeption(string message, Exception inner)
            : base("",message, inner)
        {
        }
    }

    public class CannotGetDataFromWebDataStorageExeption : BaseException
    { 
        public CannotGetDataFromWebDataStorageExeption(string message)
            : base(Resources.STR_CONNECTION_ERROR_CAPTION, message)
        {
        }
        public CannotGetDataFromWebDataStorageExeption(string message, Exception inner)
            : base("",message, inner)
        {
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CeaseCollaborationDialog/WorkUnits/ScanWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Threading;
using System.Windows.Forms.VisualStyles;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.DmsItems.Visitors;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies.ActionStrategy;

namespace Workshare.Components.Views.CeaseCollaborationDialog.WorkUnits
{
    public class ScanWorkUnit : WorkUnit
    {
        private readonly List<IDMSItem> _items;
        private readonly CeaseCollaborationDialogViewModel _vm;
        private readonly Thread _scanThread;

        public ScanWorkUnit(IModuleView view, IEnumerable<IDMSItem> items, CeaseCollaborationDialogViewModel vm, Thread scanThread, bool loadingMore = false)
            : base(view)
        {
            if (view == null) throw new ArgumentNullException("view");
            if (items == null) throw new ArgumentNullException("items");
            if (vm == null) throw new ArgumentNullException("vm");
            _items = items.ToList();
            _vm = vm;
            Name = "Scanning";
            TargetItems = _items.Select(a => new TargetItem(a.ID.ToString())
            {
                Name = a.Name
            }).ToArray();
            StatusDescription = "Scanning...";
            _scanThread = scanThread = new Thread(new ThreadStart(Scan));
        }


        public override void OnAdded()
        {
            _vm.State = CeaseCollaborationDialogViewModel.StateEnum.Scanning;
        }

        public override void Execute()
        {
            try
            {
                _scanThread.Start();
            }
            catch (Exception ex)
            {
                _view.ShowError(ex);
            }
        }

        private void Scan()
        {
            Logger.WriteTrace("ScanWorkUnit.Execute");
            var processor = _vm.Module.Resolve<Processor>();
            var adapter = _vm.Module.Resolve<ActivityFinder>();
            List<ItemMap> errors = new List<ItemMap>();

            SummaryProcessResult scanMaps = null;

            if (_items.FirstOrDefault() is IDMSFolder)
            {
                var itemToScan = _items.OfType<BaseDMSFolder>().First();
                scanMaps = processor.ScanFirstPage(itemToScan, null, null);
            }
            else
            {
                scanMaps = processor.DirectScanFile(_items.OfType<BaseDMSFile>());
            }
            errors = adapter.GetErrors(scanMaps);
            _vm.OnCompleted(errors, scanMaps);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents.Tests/TestWorkUnit.cs
﻿using System.Collections.Generic;
using Moq;
using NUnit.Framework;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Interfaces;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using WorksharePlatform;
using System.Linq;
using System;
using Workshare.Integration.Processor.Changes.Activities;

namespace WSComponents.Tests
{
    [TestFixture]
    public class TestWorkUnit
    {
        Mock<IDMSFile> file1;
        Mock<IDMSFile> file2;
        Mock<IDMSFolder> fld;
        List<IDMSItem> lst;
        List<FileMapActivity> lstToSkip;
        Mock<IWSIntegration> integration;
        Mock<IWSComponentsApp> app;
        Mock<IModuleView> view;

        [SetUp]
        public void Setup()
        {
            integration = new Mock<IWSIntegration>();
            view = new Mock<IModuleView>();
            app = new Mock<IWSComponentsApp>();
            app.Setup(x => x.Integration).Returns(integration.Object);
            WSApplication.Instance = app.Object;
            file1 = new Mock<IDMSFile>();
            file2 = new Mock<IDMSFile>();
            fld = new Mock<IDMSFolder>();
            fld.Setup(x => x.Files).Returns(new List<IDMSFile>() { file2.Object });
            lst = new List<IDMSItem>() { file1.Object, fld.Object };
            lstToSkip = new List<FileMapActivity>();
        }

//        [Test]
        public void TestSendItems_SendCalled()
        { 
            int DestFolderID = 10;
            integration.Setup(x => x.SendItems(lst, It.IsAny<FolderDetails>(), It.IsAny<OperationContext>())).Callback<IEnumerable<IDMSItem>, FolderDetails, OperationContext>((a, b, c) => { Assert.IsTrue(b.Id == DestFolderID); });
            SendWorkUnit su = new SendWorkUnit(view.Object, lst, lstToSkip, DestFolderID, CheckOutOptions.CheckOut);
            su.Execute();
            Assert.AreEqual(su.TargetItems, lst);
            integration.Verify(x=>x.SendItems(lst, It.IsAny<FolderDetails>(), It.IsAny<OperationContext>()), Times.Once());
        }

//        [Test]
        public void TestSyncItems_SyncCalled()
        {
            List<SyncItemInformation> si = new List<SyncItemInformation>()
            {
                new SyncItemInformation(fld.Object, ConflictOptions.None, ConflictVersionOptions.None),
                new SyncItemInformation(file1.Object, ConflictOptions.None, ConflictVersionOptions.None)
            };
            SynhWorkUnit su = new SynhWorkUnit(view.Object, si, lstToSkip, lst, OperationStage.First);
            su.Execute();
            Assert.IsTrue(su.TargetItems.Contains((TargetItem)fld.Object));
            Assert.IsTrue(su.TargetItems.Contains((TargetItem)file1.Object));
            Assert.IsFalse(su.TargetItems.Contains((TargetItem)file2.Object));
            integration.Verify(x => x.SyncItems(si, It.IsAny<OperationContext>()), Times.Once());
        }

//        [Test]
        public void TestSendItems_SendRaiseError()
        {
            int DestFolderID = 10;
            ItemsErrorsCollection errs = new ItemsErrorsCollection(null);
            errs.Add(file1.Object, new CloudFileNotFound("Test error"));
            integration.Setup(x => x.SendItems(lst, It.IsAny<FolderDetails>(), It.IsAny<OperationContext>())).Throws(new MultiItemsException(errs, null));
            SendWorkUnit su = new SendWorkUnit(view.Object, lst, lstToSkip, DestFolderID, CheckOutOptions.CheckOut);
            su.OnError += (a, e) =>
                {
                    Assert.IsTrue(e.Error is MultiItemsException);
                    e.Handled = true;
                };
            su.Execute();
            integration.Verify(x => x.SendItems(lst, It.IsAny<FolderDetails>(), It.IsAny<OperationContext>()), Times.Once());
        }

//        [Test]
        public void TestSyncItems_SyncRaiseError_CloudUnAuthorized()
        {
            var auth = new Mock<IAuthProvider>();
            app.Setup(x => x.AuthProvider).Returns(auth.Object);

            List<SyncItemInformation> si = new List<SyncItemInformation>()
            {
                new SyncItemInformation(fld.Object, ConflictOptions.None, ConflictVersionOptions.None),
                new SyncItemInformation(file1.Object, ConflictOptions.None, ConflictVersionOptions.None)
            };

            integration.Setup(x => x.SyncItems(si, It.IsAny<OperationContext>())).Throws(new CloudUnAuthorized());
            SynhWorkUnit su = new SynhWorkUnit(view.Object, si, lstToSkip, lst, OperationStage.First);
            su.OnError += (a, e) =>
            {
                Assert.IsTrue(e.Error is MultiItemsException);
            };
            su.Execute();

            integration.Verify(x => x.SyncItems(si, It.IsAny<OperationContext>()), Times.Once());
            auth.Verify(x => x.SetCurrentUser(null), Times.Once());
            view.Verify(x => x.ShowError(It.IsAny<string>()), Times.Once());
        }

    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Strategies/ProcessStrategy.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.WsProxies;
using Workshare.Integration.Enums;
using Workshare.Integration;
using WorksharePlatform;
using Workshare.IManage.Contrete;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Modularity;

namespace Workshare.IManage.Strategies
{
    class ProcessStrategy : Workshare.Integration.Processor.Strategies.ProcessStrategy
    {
        public ProcessStrategy(ModuleBase module, WsProxy wsProxy, IAuthProvider auth,DmsWorkerBase dmsWorker,SyncInfoService syncInfoService)
            : base(module,wsProxy, auth, dmsWorker, syncInfoService)
        {
        }
        
    }

}
<file_sep>/WSComponents/src/WSIntegration/WsProxies/WsUser.cs
﻿using System;
using System.Net;
using WorksharePlatform;

namespace Workshare.Integration.WsProxies
{
    public class WsUser
    {
        public UserDetails _user;

        public WsUser(UserDetails user)
        {
            if (user == null) throw new ArgumentNullException("user");
            this._user = user;
        }

        public string AuthToken { get { return _user.AuthToken; } set { _user.AuthToken = value; } }

        public CookieContainer SessionCookies { get { return _user.SessionCookies; } set { _user.SessionCookies = value; } }

        public string UserName { get { return _user.UserName; } }

        public string Domain
        {
            get
            {
                var res = _user.Domain;
                if (string.IsNullOrEmpty(res))
                {
                    res = WsUtils.GetEmailDomain(Email);
                }
                return res;
            }
        }

        public bool InPrivateDomain
        {
            get
            {
                return !string.IsNullOrEmpty(_user.Domain);
            }
        }

        public string Email
        {
            get { return _user.Email; }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Activities/ImportFileActivity.cs
﻿namespace Workshare.Integration.Processor.Changes.Activities
{
    public class ImportFileActivity : FileMapActivity
    {
        public ImportFileActivityState State { set; get; }

        public ImportFileActivity()
        {
            Type = "ImportActivity";
        }

        public override bool InKindOfErrorState()
        {
            return State == ImportFileActivityState.Error
                   || State == ImportFileActivityState.CheckedOutOnAnotherMachine
                   || State == ImportFileActivityState.CheckedOutToAnother
                   || State == ImportFileActivityState.NoAccessOnWorkshare
                   || State == ImportFileActivityState.LockedByAnotherProcess;
        }

        public override bool InKindOfProceeedState()
        {
            return State == ImportFileActivityState.Imported;
        }

        public override bool InKindOfProcessingState()
        {
            return State == ImportFileActivityState.Importing;
        }

        public override string ToString()
        {
            return string.Format("ImportFileActivity State={0}; Id={1}, Changes={2}", State, MapId,Changes.AsString());
        }
    }

    public enum ImportFileActivityState { 
        Scanned,
        Imported,
        Error,
        Importing, 
        CheckedOutToAnother, 
        CheckedOutOnAnotherMachine, 
        NoAccessOnWorkshare,
        LockedByAnotherProcess,
        DeletingLink,
        LinkIsDeleted,
        NoAccessOnDMS
    };
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/WorkshareIntegration.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;
using WorksharePlatform;
using WorkshareCloud.Common;
using System.IO;
using System.Web;
using System.Xml;
using WorkshareCloud.Common.Enums;
using WorkshareCloud.Common.Receivers;
using System.Net;

namespace WorkshareCloud.Common
{

    public class WorkshareIntegration
    {

        #region public

        public static WorkshareIntegration Instance
        {
            get
            {
                return new WorkshareIntegration();
            }

        }

        public static ICollection<SPListItem> GetListItem(ItemID[] items, Guid listGuid, SPWeb web)
        {

            var list = web.Lists.GetList(listGuid, false);
            if (list != null)
            {
                List<SPListItem> itms = new List<SPListItem>();
                foreach (var itm in items)
                {
                    itms.Add(list.GetItemById(itm.id));
                }
                return itms;
            }
            return null;
        }

        public void ClearFolderSyncDataIfNeed(SPListItem item)
        {
            var current_folder = item;
            while (current_folder != null && CheckFolderIsNeedToClearSyncData(current_folder))
            {
                ClearFolderCloudData(current_folder);
                current_folder = current_folder.Folder.ParentFolder.Item;
            }
        }

        void SyncItems(List<SyncItemInfo> infos, Guid listGuid, UserDetails user)
        {
            if (infos.Any())
            {
                using (var errorlist = new ItemsErrorsCollection())
                {
                    CloudAuthenication.CheckIfAuth(user);
                    var items = GetListItem(infos.Select(x => x.item).ToArray(), listGuid, SPContext.Current.Web);
                    var parentList = items.First().ParentList;
                    parentList.CheckWSFieldOrThrow();
                    //bool idNotInitialize = !EnsureListInitialized(parentList);

                    foreach (SPListItem listitem in items)
                    {
                        SafeFuncCall(errorlist, listitem, new ExceptionListSignal() { IsAll = true, IsList = true }, () =>
                        {
                            //var item = (idNotInitialize) ? parentList.GetItemById(listitem.ID) : listitem;
                            var item = listitem;

                            if (item.IsFolder())
                            {
                                SyncFolder(item.Folder, user);
                            }
                            else
                            {
                                SyncFile(item, (ConflictOptions)infos.Where(x => x.item.id == item.ID).First().conflictOption, user);
                            }
                        });
                    }
                }
            }
        }

        public void SyncItems(List<SyncItemInformation> infos, UserDetails user)
        {
            using (var errorlist = new ItemsErrorsCollection())
            {
                foreach (var syncInfo in infos)
                {
                    Guid ListGuid;
                    if (Extensions.GuidTryParse(syncInfo.listGuid, out ListGuid))
                    {
                        SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsAll = true, IsList = true }, () =>
                        {
                            //var item = GetListItem(syncInfo.items, ListGuid, SPContext.Current.Web);
                            SyncItems(syncInfo.items, ListGuid, user);
                        });
                    }
                    else
                    {
                        throw new BadRequest(string.Format("Cannot parse ListGuid={0}", syncInfo.listGuid));
                    }
                }
            }
        }

        public void SendItems(List<SendItemInformation> infos, UserDetails user)
        {
            using (var errorlist = new ItemsErrorsCollection())
            {
                foreach (var sendInfo in infos)
                {
                    Guid ListGuid;
                    int folderId;
                    if (Extensions.GuidTryParse(sendInfo.listGuid, out ListGuid) && int.TryParse(sendInfo.folderId, out folderId))
                    {
                        SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsAll = true, IsList = true }, () =>
                        {
                            var items = GetListItem(sendInfo.items.ToArray(), ListGuid, SPContext.Current.Web);
                            SendItems(items, folderId, user);
                        });
                    }
                    else
                    {
                        throw new BadRequest(string.Format("ListGuid={0} FolderId={1}", sendInfo.listGuid, sendInfo.folderId));
                    }
                }
            }
        }

        void SendItems(ICollection<SPListItem> items, int folderId, UserDetails user)
        {
            if (items.Any())
            {
                using (var errorlist = new ItemsErrorsCollection())
                {
                    CloudAuthenication.CheckIfAuth(user);
                    SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsAll = true, IsList = true }, () =>
                    {
                        var parentList = items.First().ParentList;

                        parentList.CheckWSFieldOrThrow();

                        if (!CheckFolderExistsWhenSendOrThrow(user, folderId, -1))
                        {
                            throw new CloudFolderNotFound(folderId, false);
                        }

                        try // need if destination folder on the cloud was deleted during send operation
                        {
                            foreach (SPListItem listitem in items)
                            {
                                SafeFuncCall(errorlist, listitem, new ExceptionListSignal() { IsAll = true, IsList = true, FolderError = true }, () =>
                                {
                                    var item = listitem;

                                    if (item.IsFolder())
                                    {
                                        SendFolder(item.Folder, folderId, user);
                                    }
                                    else
                                    {
                                        SendFile(item, folderId, user);
                                    }
                                });
                            }
                        }
                        catch (CloudFolderNotFound ex)
                        {
                            // if destination folder was deleted then clear already processed files from link
                            foreach (SPListItem listitem in items)
                            {
                                SafeFuncCall(errorlist, listitem, new ExceptionListSignal() { IsAll = true, IsList = true }, () =>
                                {
                                    var item = listitem;

                                    if (item.IsFolder())
                                    {
                                        SyncFolder(item.Folder, user, true);
                                    }
                                    else
                                    {
                                        ClearFileCloudData(item);
                                    }
                                });
                            }
                            errorlist.Clear();
                            errorlist.Add(null, ex);
                        }
                    });
                }
            }
        }

        const string CustomXSLT = "Cloud.xsl";

        internal string GetCreateFieldAsXml(Guid oId)
        {
            XmlElement element = new XmlDocument().CreateElement("Field"); // Creating the “Field” element for the Inner XML schema
            element.SetAttribute("ID", oId.ToString()); // Setting the GUID of the field from value passed
            element.SetAttribute("Type", "CloudPathField"); // Setting the Type name registered in the “Fldtypes*.xml” file
            element.SetAttribute("Name", CloudPathFieldValue.CloudField); // Setting the Field name registered in the “Fldtypes*.xml” file
            element.SetAttribute("DisplayName", CloudPathFieldValue.CloudField); // Any unique Display Name 
            element.SetAttribute("Required", "FALSE");
            element.SetAttribute("ShowInNewForm", "FALSE");
            element.SetAttribute("ShowInEditForm", "FALSE");
            element.SetAttribute("ShowInDisplayForm", "FALSE");
            element.SetAttribute("ShowInViewForms", "FALSE");
            element.SetAttribute("ShowInVersionHistory", "FALSE");
            return element.OuterXml; // Returning the OuterXML to create the field as XML


        }

        public bool EnsureListInitialized(SPList list)
        {
            try
            {
                list.ParentWeb.AllowUnsafeUpdates = true;
                var wasUpdated = false;
                if (!list.Fields.ContainsFieldWithStaticName(CloudPathFieldValue.CloudField))
                {
                    list.CheckPermissionkOrThrow(SPBasePermissions.ManageLists);

                    var field = GetCreateFieldAsXml(Guid.NewGuid());
                    //SPField field = list.Fields.CreateNewField(SPFieldType.Text.ToString(), CloudPathFieldValue.CloudField);
                    //field.ShowInNewForm = false;
                    //field.ShowInEditForm = false;
                    //field.ShowInDisplayForm = false;
                    //field.ShowInViewForms = false;
                    //field.ShowInVersionHistory = false;
                    //list.Fields.Add(field);
                    list.Fields.AddFieldAsXml(field);
                    list.Update();

                    wasUpdated = true;
                }
                for (int i = 0; i < list.Views.Count; i++)
                {
                    var view = list.Views[i];
                    if (!view.ViewFields.Exists(CloudPathFieldValue.CloudField))
                    {
                        view.ViewFields.Add(CloudPathFieldValue.CloudField);
                        view.Update();
                        wasUpdated = true;
                    }
                    //if (!string.Equals(view.XslLink, CustomXSLT))
                    //{
                    //    view.XslLink = CustomXSLT;
                    //    view.Update();
                    //    wasUpdated = true;
                    //}
                }

                UpdateReceiver(list);


                if (wasUpdated) { list.ParentWeb.Audit.WriteItemUpdate(list); }

                return !wasUpdated;
            }
            finally
            {
                list.ParentWeb.AllowUnsafeUpdates = false;
            }
        }
        #endregion

        #region privates
        private static readonly char[] InvalidSharePointFileNameCharacters = { '~', '#', '%', '&', '*', ':', '<', '>', '?', '/', '\\', '{', '}', '|' };
        readonly string MISSEDONCLOUD = "Item was deleted from Workshare";

        void UpdateReceiver(SPList list)
        {
            list.EventReceivers.OfType<SPEventReceiverDefinition>().Where(p => string.Equals(p.Class, typeof(WorkshareReceiver).FullName)).ToList().ForEach(receiver => receiver.Delete());

            list.EventReceivers.Add(SPEventReceiverType.ItemCheckingIn, typeof(WorkshareReceiver).Assembly.FullName, typeof(WorkshareReceiver).FullName);

            //list.EventReceivers.Add(SPEventReceiverType.ItemCheckedIn, typeof(WorkshareReceiver).Assembly.FullName, typeof(WorkshareReceiver).FullName);

            //list.EventReceivers.Add(SPEventReceiverType.ItemUncheckedOut, typeof(WorkshareReceiver).Assembly.FullName, typeof(WorkshareReceiver).FullName);

            list.EventReceivers.Add(SPEventReceiverType.ItemAdding, typeof(WorkshareReceiver).Assembly.FullName, typeof(WorkshareReceiver).FullName);
        }

        private int SendFolder(SPFolder folder, int folderId, UserDetails user)
        {
            int newfolderId = -1;
            if (!(new CloudPathFieldValue((string)folder.Item[CloudPathFieldValue.CloudField]).HasValue))
            {
                using (var errorlist = new ItemsErrorsCollection())
                {
                    SafeFuncCall(errorlist, folder.Item, new ExceptionListSignal() { IsWeb = true, FolderError = true }, () =>
                    {
                        FolderDetails newFolder;
                        try
                        {
                            newFolder = PlatformService.CreateFolder(user, folder.Name, "desc", folderId);
                        }
                        catch (WebException ex)
                        {
                            if (IsStatusCode(ex, (HttpStatusCode)403))
                            {
                                throw new CloudFolderAccessDenied(Properties.Resources.STR_UNABLE_SEND, Properties.Resources.STR_UNANBESENDFOLDER_TEXT, ex);
                            }
                            else
                            {
                                throw;
                            }
                        }

                        RunUnsafeUpdate(folder.Item.Web, () =>
                        {
                            folder.Item.SetCloudValue(newFolder);
                            folder.Item.SystemUpdate(false);
                        });

                        string itemSendInfo = "";
                        foreach (SPFolder item in folder.SubFolders)
                        {
                            SafeFuncCall(errorlist, item.Item, new ExceptionListSignal() { IsAll = true, IsList = true, FolderError = true }, () =>
                            {
                                int folderID = SendFolder(item, newFolder.Id, user);
                                if (folderID > 0)
                                {
                                    itemSendInfo += folderID.ToString() + ";";
                                }
                            });
                        }


                        foreach (SPFile file in folder.Files)
                        {
                            SafeFuncCall(errorlist, file.Item, new ExceptionListSignal() { IsAll = true, IsList = true, IsWeb = true, FolderError = true }, () =>
                            {
                                int fileID = SendFile(file.Item, newFolder.Id, user);
                                if (fileID > 0)
                                {
                                    itemSendInfo += fileID.ToString() + ";";
                                }
                            });
                        }
                        RunUnsafeUpdate(folder.Item.Web, () =>
                        {
                            if (folder.Item.Properties.Contains("SyncedFileData"))
                            {
                                folder.Item.Properties.Remove("SyncedFileData");
                            }
                            folder.Item.Properties.Add("SyncedFileData", itemSendInfo);
                            folder.Item.SystemUpdate(false);
                        });
                        folder.ParentWeb.Audit.WriteItemSent(folder.Item, newFolder, PlatformService.GetAncestor(user, folderId));
                        newfolderId = newFolder.Id;
                    });
                }
            }
            else
            {
                throw new AlreadySentException();
            }
            return newfolderId;
        }

        private void SyncFilesInFolder(SPFolder folder, List<FileDetails> filesOnCloud, UserDetails user)
        {
            using (var errorlist = new ItemsErrorsCollection())
            {
                // sync existing files
                List<int> filesOnSP = new List<int>();
                foreach (SPFile item in folder.Files)
                {
                    var fileCloudData = new CloudPathFieldValue((string)(item.Item)[CloudPathFieldValue.CloudField]);
                    if (fileCloudData.ItemId > 0)
                    {
                        filesOnSP.Add(fileCloudData.ItemId);
                    }
                    SafeFuncCall(errorlist, item.Item, new ExceptionListSignal() { IsAll = true, IsWeb = true }, () =>
                    {
                        SyncFile(item.Item, ConflictOptions.None, user);
                        //item.Item.Update();
                    });
                }
                string processedFilesString = folder.Item.Properties.Contains("SyncedFileData") ? folder.Item.Properties["SyncedFileData"].ToString() : "";
                var processedFiles = processedFilesString.Split(new string[] { ";" }, StringSplitOptions.RemoveEmptyEntries);
                foreach (var fileID in filesOnCloud.Select(x => x.Id).Except(filesOnSP))
                {
                    SafeFuncCall(errorlist, folder.Item, new ExceptionListSignal() { IsAll = true, IsWeb = true }, () =>
                    {
                        var cloudFile = filesOnCloud.Where(x => x.Id == fileID).First();
                        if (!processedFiles.Contains(cloudFile.Id.ToString()))
                        {
                            try
                            {
                                processedFilesString += cloudFile.Id + ";";
                                PlatformService.GetVersionDetails(user, cloudFile);
                                AddNewFileToSharePoint(folder, cloudFile, PlatformService.DownloadFile(user, fileID));
                                RunUnsafeUpdate(folder.Item.Web, () =>
                                    {
                                        if (folder.Item.Properties.Contains("SyncedFileData"))
                                        {
                                            folder.Item.Properties["SyncedFileData"] = processedFilesString;
                                        }
                                        else
                                        {
                                            folder.Item.Properties.Add("SyncedFileData", processedFilesString);
                                        }
                                        folder.Item.SystemUpdate(false);
                                    });
                            }
                            catch (WebException e)
                            {
                                if (IsStatusCode(e, (HttpStatusCode)403))
                                {
                                    throw new CloudFolderAccessDenied(Properties.Resources.STR_UNABLE_SYNC, Properties.Resources.STR_UNABLESYNCFILE_TEXT, e);
                                }
                                else
                                {
                                    throw;
                                }
                            }
                        }
                    });

                }
            }
        }

        private void AddNewFileToSharePoint(SPFolder folder, FileDetails file, string filePath)
        {
            RunUnsafeUpdate(folder.ParentWeb, () =>
            {
                SPFile fl = folder.Files.AddWSFile(RemoveInvalidSymbols(file.Name), filePath);
                //fl.Item.SetCloudValue(file);
                //fl.Item.SystemUpdate(false);
                RunUnsafeUpdate(fl.Item.Web, () => { fl.CheckOut(); });
                folder.ParentWeb.Audit.WriteItemSynced(folder.Item, file);
            });
        }

        private void SyncSubFolderInFolder(SPFolder folder, IEnumerable<FolderDetails> foldersOnCloud, UserDetails user)
        {
            using (var errorlist = new ItemsErrorsCollection())
            {
                // sync existing folders
                Dictionary<int, string> folderOnSP = new Dictionary<int, string>();
                foreach (SPFolder item in folder.SubFolders)
                {
                    var folderCloudData = new CloudPathFieldValue((string)(item.Item)[CloudPathFieldValue.CloudField]);
                    if (folderCloudData.ItemId > 0)
                    {
                        folderOnSP.Add(folderCloudData.ItemId, RemoveInvalidSymbols(item.Name));
                    }
                    SafeFuncCall(errorlist, item.Item, new ExceptionListSignal() { IsAll = true, IsList = true, IsWeb = true }, () =>
                    {
                        SyncFolder(item, user);
                        //item.Item.Update();
                    });
                }

                // add new folders from cloud to SP and sync it
                string processedFolderString = folder.Item.Properties.Contains("SyncedFileData") ? folder.Item.Properties["SyncedFileData"].ToString() : "";
                var processedFolders = processedFolderString.Split(new string[] { ";" }, StringSplitOptions.RemoveEmptyEntries);
                var newFolders = foldersOnCloud.Select(f => f.Id).Except(folderOnSP.Select(x => x.Key));
                foreach (var folderID in newFolders)
                {
                    SafeFuncCall(errorlist, folder.Item, new ExceptionListSignal() { IsAll = true, IsList = true, IsWeb = true }, () =>
                    {
                        var cloudFolder = foldersOnCloud.Where(x => x.Id == folderID).First();
                        if (!processedFolders.Contains(cloudFolder.Id.ToString()))
                        {
                            RunUnsafeUpdate(folder.Item.Web, () =>
                            {
                                processedFolderString += cloudFolder.Id + ";";
                                SPFolder fld = folder.SubFolders.Add(folder.ServerRelativeUrl + "/" + RemoveInvalidSymbols(cloudFolder.Name) + "/");
                                if (folder.Item.Properties.Contains("SyncedFileData"))
                                { 
                                    folder.Item.Properties["SyncedFileData"] = processedFolderString; 
                                } 
                                else
                                {
                                    folder.Item.Properties.Add("SyncedFileData", processedFolderString);
                                }
                                folder.Update();
                                folder.Item.SystemUpdate(false);
                                fld.Item.SetCloudValue(cloudFolder);
                                fld.Item.SystemUpdate(false);
                                SyncFolder(fld, user);
                            });
                        }
                    });
                }
            }
        }

        private void ClearFolderCloudData(SPListItem folder)
        {
            RunUnsafeUpdate(folder.Web, () =>
            {
                folder.SetCloudValue((FolderDetails)null);
                if (folder.Properties.Contains("SyncedFileData"))
                {
                    folder.Properties.Remove("SyncedFileData");
                }
                folder.SystemUpdate(false);
            });
        }

        private bool CheckFolderExistsWhenSendOrThrow(UserDetails user, int itemID, int parentFolderID)
        {
            try
            {
                return PlatformService.IsFolderExists(user, itemID, parentFolderID);
            }
            catch (WebException ex)
            {
                if (IsStatusCode(ex, (HttpStatusCode)403))
                {
                    throw new CloudFolderAccessDenied(Properties.Resources.STR_UNABLE_SEND, Properties.Resources.STR_UNABLESENDITEM_TEXT, ex);
                }
                else
                {
                    throw;
                }
            }
        }

        private bool CheckFolderExistsWhenSyncOrThrow(UserDetails user, int itemID, int parentFolderID)
        {
            try
            {
                return PlatformService.IsFolderExists(user, itemID, parentFolderID);
            }
            catch (WebException ex)
            {
                if (IsStatusCode(ex, (HttpStatusCode)403))
                {
                    throw new CloudFolderAccessDenied(Properties.Resources.STR_UNABLE_SYNC, Properties.Resources.STR_UNABLESYNCITEM_TEXT, ex);
                }
                else
                {
                    throw;
                }
            }
        }

        private void SyncFolder(SPFolder folder, UserDetails user, bool ClearFieldData = false)
        {
            using (var errorlist = new ItemsErrorsCollection())
            {

                SafeFuncCall(errorlist, folder.Item, new ExceptionListSignal() { IsWeb = true }, () =>
                {
                    var CloudPathData = new CloudPathFieldValue((string)(folder.Item)[CloudPathFieldValue.CloudField]);
                    if (CloudPathData.HasValue)
                    {
                        //var cloudfolder = PlatformService.GetFolder(_user, CloudPathData.FolderId); // need for check if user can access to folder
                        if (!ClearFieldData && CheckFolderExistsWhenSyncOrThrow(user, CloudPathData.ItemId, CloudPathData.ParentFolderId))
                        {
                            SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsList = true }, () =>
                            {
                                SyncFilesInFolder(folder, PlatformService.GetFiles(user, CloudPathData.ItemId), user);
                            });

                            SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsList = true }, () =>
                            {
                                SyncSubFolderInFolder(folder, PlatformService.GetChildFolders(user, CloudPathData.ItemId), user);
                            });

                            if (CheckFolderIsNeedToClearSyncData(folder.Item)) // all files sync OK then clear folder sync data
                            {
                                ClearFolderCloudData(folder.Item);
                            }
                        }
                        else
                        {// folder was removed from cloud so we should clear Cloud field for all subitems and clear cloud field for this folder

                            // clear cloud field for files in the folder
                            foreach (SPFile file in folder.Files)
                            {
                                SafeFuncCall(errorlist, file.Item, new ExceptionListSignal() { IsAll = true }, () =>
                                {
                                    var fileclouddata = new CloudPathFieldValue((string)(file.Item)[CloudPathFieldValue.CloudField]);
                                    FileDetails fd = fileclouddata.HasValue ? PlatformService.GetFile(user, fileclouddata.ItemId, fileclouddata.ParentFolderId) : null;
                                    ClearFileCloudData(file.Item);
                                    if (fileclouddata.HasValue)
                                    {
                                        file.Item.Web.Audit.WriteItemStopSync(file.Item, MISSEDONCLOUD, fd);
                                    }
                                });
                            }

                            //clear cloud field for all subfolders
                            foreach (SPFolder item in folder.SubFolders)
                            {
                                SafeFuncCall(errorlist, item.Item, new ExceptionListSignal() { IsAll = true, IsList = true }, () =>
                                {
                                    SyncFolder(item, user, true);
                                });
                            }

                            SafeFuncCall(errorlist, folder.Item, new ExceptionListSignal() { IsAll = true }, () =>
                            {
                                ClearFolderCloudData(folder.Item);
                                folder.ParentWeb.Audit.WriteItemStopSync(folder.Item, MISSEDONCLOUD);
                            });

                            if (!ClearFieldData)
                            {
                                throw new CloudFolderNotFound(CloudPathData.ParentFolderId, PlatformService.IsFolderExists(user, CloudPathData.ParentFolderId, -1));
                            }
                        }
                    }
                });
            }
        }

        private bool CheckFolderIsNeedToClearSyncData(SPListItem item)
        { 
            if (item == null) { return false; }
            SPList list = item.ParentList;
            SPFolder folder = item.Folder;
            if (folder.Item == null) { return false; } // check if item is root folder 
            if (folder == null)
            {
                SPFile file = item.File;
                if (file == null || file.ParentFolder == null || file.ParentFolder.Item == null)
                {
                    return false;
                }
                else
                {
                    folder = file.ParentFolder;
                }
            }
            SPQuery qry = new SPQuery();
            qry.Folder = folder;
            qry.Query = 
                "<Where> "+
                    "<Or> "+
                        "<IsNotNull><FieldRef Name='" + CloudPathFieldValue.CloudField + "'/></IsNotNull> "+
                        "<And> "+
                            "<Neq><FieldRef Name='CheckoutUser' LookupId='TRUE'/><Value Type='Integer'><UserID/></Value></Neq> "+
                            "<IsNotNull><FieldRef Name='CheckoutUser'/></IsNotNull> "+
                        "</And> "+
                    "</Or> " +
                "</Where>";
            SPListItemCollection res = list.GetItems(qry);
            return res.Count == 0;
        }

        private void ClearFileCloudData(SPListItem file)
        {
            RunUnsafeUpdate(file.Web, () =>
            {
                file.SetCloudValue((FileDetails)null);
                file.SystemUpdate(false);
            });
        }

        private void SyncFile(SPListItem item, ConflictOptions conflictOption, UserDetails _user)
        {
            SafeFuncCall(null, null, new ExceptionListSignal() { IsWeb = true }, () =>
            {
                //CloudAuthenication.CheckIfAuth();
                Exception ex = null;
                item.CheckPermissionkOrThrow(SPBasePermissions.EditListItems);
                item.CheckNotCheckedOutToOtherUserOrThrow();
                var CloudPathData = new CloudPathFieldValue((string)item[CloudPathFieldValue.CloudField]);
                if (CloudPathData.HasValue)
                {
                    try
                    {
                        var folder = PlatformService.GetFolder(_user, CloudPathData.ParentFolderId); // need for check if user can access to folder
                        if (folder != null)
                        {
                            var file = PlatformService.GetFiles(_user, CloudPathData.ParentFolderId).Where(x => x.Id == CloudPathData.ItemId).FirstOrDefault();
                            // if file is null so it was deleted from cloud and we should clear synchronization data from sharepoint
                            if (file != null)
                            {
                                var cloud_versions = PlatformService.GetVersionDetails(_user, file);
                                var currentFileVersion = cloud_versions.Where(x => x.Id == CloudPathData.VersionId).FirstOrDefault();
                                if (currentFileVersion != null)
                                {
                                    var cloudIsNewer = cloud_versions.Where(x => x.Version > currentFileVersion.Version).Any();
                                    var SPFileModified = (DateTime)item[SPBuiltInFieldId.Modified];
                                    bool SPFileIsNewer = SPFileModified != null && SPFileModified.Ticks > CloudPathData.ItemModifiedBy;
                                    // file on the cloud is newer
                                    if (cloudIsNewer && (!SPFileIsNewer || conflictOption == ConflictOptions.Replace))
                                    {
                                        var filepath = PlatformService.DownloadFile(_user, CloudPathData.ItemId);
                                        UpdateFileOnSharepoint(item, filepath, file);
                                        item.Web.Audit.WriteItemSync(item, file);
                                    }
                                    else
                                        if (cloudIsNewer && (SPFileIsNewer && conflictOption == ConflictOptions.KeepBoth))
                                        {
                                            AddNewFileToSharePoint(item.File.ParentFolder, file, PlatformService.DownloadFile(_user, file.Id));
                                            //ClearFileCloudData(item);
                                        }

                                        else //file on the sharepoint is newer
                                        {
                                            if (SPFileIsNewer && conflictOption == ConflictOptions.None)
                                            {
                                                if (cloudIsNewer)
                                                {
                                                    ex = new FileConflictException(item.Name, file.Name, item.ID, item.ParentList.ID, SPFileModified, file.CurrentVersion.CreateDate, item.File.ModifiedBy.Name, file.CurrentVersion.Creator.UserName);
                                                }
                                                else
                                                {
                                                    //ex = new FileOnSharePointIsNewer(item.Name, item.ID);
                                                    UploadNewFileVersionToWorkshareCloud(_user, item, file);
                                                    item.Web.Audit.WriteItemSync(item, file);
                                                }
                                            }
                                        }
                                }
                                else
                                {
                                    //how they can delete version??
                                    ex = new VersionDoesNotExist();
                                }
                            }
                            else
                            {
                                // file was removed from cloud
                                FileDetails fd = PlatformService.GetFile(_user, CloudPathData.ItemId, CloudPathData.ParentFolderId);
                                ClearFileCloudData(item);
                                item.Web.Audit.WriteItemStopSync(item, MISSEDONCLOUD, fd);
                                ex = new CloudFileNotFound(CloudPathData.ParentFolderId, PlatformService.IsFolderExists(_user, CloudPathData.ParentFolderId, -1));
                            }
                        }

                        if (ex != null)
                        {
                            Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService);
                            throw ex;
                        }
                        ClearFileCloudData(item.File.Item);
                    }
                    catch (WebException e)
                    {
                        if (IsStatusCode(e, (HttpStatusCode)403))
                        {
                            throw new CloudFolderAccessDenied(Properties.Resources.STR_UNABLE_SYNC, Properties.Resources.STR_UNABLESYNCFILE_TEXT, e);
                        }
                        else
                        {
                            throw;
                        }
                    }
                }
            });

        }

        private void ThrowIfFolderNotExists(UserDetails user, int folderID)
        {
            if (!PlatformService.IsFolderExists(user, folderID, -1))
                throw new CloudFolderNotFound(folderID, false);
        }

        private int SendFile(SPListItem item, int folderId, UserDetails user)
        {
            int fileID = -1;
            ThrowIfFolderNotExists(user, folderId);
            SafeFuncCall(null, null, new ExceptionListSignal() { IsWeb = true }, () =>
            {
                if (item != null && item.File != null)
                {

                    item.CheckPermissionkOrThrow(SPBasePermissions.EditListItems);
                    item.CheckNotCheckedOutToOtherUserOrThrow();
                    if (!item.IsCheckedOutToCurrentUser())
                    {
                        RunUnsafeUpdate(item.Web, () =>
                        {
                            item.File.CheckOut();
                        });
                    }

                    if (!(new CloudPathFieldValue((string)item[CloudPathFieldValue.CloudField]).HasValue))
                    {
                        fileID = UploadFileToWorkshareCloud(item, folderId, user);
                        item.Web.Audit.WriteItemSent(new[] { item }, new FolderDetails() { Id = folderId }, PlatformService.GetAncestor(user, folderId));
                    }
                    else
                    {
                        throw new AlreadySentException();
                    }
                }
            });
            return fileID;
        }

        private bool UploadNewFileVersionToWorkshareCloud(UserDetails user, SPListItem item, FileDetails file)
        {
            var value = item.GetCloudValue();
            if (value != null)
            {
                //TO DO - need to make sure whether we have FilePath
                //file.FilePath
                file.Name = item.Name;

                RunUnsafeUpdate(item.Web, () =>
                {
                    PlatformService.UploadNewVersionOfFile(user, file);
                    //item.SetCloudValue(file);
                    //item.SystemUpdate(false);
                });
                return true;
            }
            return false;
        }

        private int UploadFileToWorkshareCloud(SPListItem item, int folderId, UserDetails user)
        {
            var value = item.GetCloudValue();
            if (value != null)
            {
                var fileDetailes = new FileDetails()
                {
                    Name = item.Name,
                    FriendlyName = ((string.IsNullOrEmpty(item.DisplayName)) ? Path.GetFileNameWithoutExtension(item.Name) : item.DisplayName),
                    //TO DO - need to get FilePath
                    //FilePath
                    FolderId = folderId
                };

                try
                {
                    RunUnsafeUpdate(item.Web, () =>
                    {
                        PlatformService.UploadFile3(user, fileDetailes);
                        item.SetCloudValue(fileDetailes);
                        item.SystemUpdate(false);
                    });
                    return fileDetailes.CurrentVersion.FileId;
                }
                catch (WebException ex)
                {
                    if (IsStatusCode(ex, (HttpStatusCode)403))
                    {
                        throw new CloudFolderAccessDenied(Properties.Resources.STR_UNABLE_SEND, Properties.Resources.STR_UNABLESENDFILE_TEXT, ex);
                    }
                    else
                    {
                        throw;
                    }
                }
            };
            return -1;
        }

        private bool UpdateFileOnSharepoint(SPListItem item, string filePath, FileDetails file)
        {
            using (Stream stream = File.Open(filePath, FileMode.Open, FileAccess.Read, FileShare.None))
            {
                RunUnsafeUpdate(item.Web, () =>
                {
                    item.File.SaveBinary(stream, new SPFileSaveBinaryParameters() { CreateVersion = false, CheckRequiredFields = false });
                    //item.File.Item["Name"] = file.Version.Name; we can upload on workshare cloud new version with new name, but new name is not displayed in Web UI
                    //item.File.Item.SetCloudValue(file);
                    item.File.Item.SystemUpdate(false);
                });
                return true;
            }
        }

        private class ExceptionListSignal
        {
            public bool IsList = false;
            public bool IsWeb = false;
            public bool IsAll = false;
            public bool FolderError = false;
        }

        public static bool IsStatusCode(WebException ex, HttpStatusCode code)
        {
            return ex.Response != null && ex.Response is HttpWebResponse && (((HttpWebResponse)ex.Response).StatusCode == code);
        }

        private void SafeFuncCall(ItemsErrorsCollection errorlist, SPListItem item, ExceptionListSignal flags, Action func)
        {
            try
            {
                try
                {
                    func();
                }
                catch (Exception ex)
                {
                    ReThrowException(ex);
                }
            }
            catch (Exception ex)
            {
                Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService);

                if (flags.FolderError && ex is CloudFolderNotFound)
                {
                    throw;
                }

                if (flags.IsList && ex is ListProcessException)
                {
                    if (errorlist != null)
                    {
                        errorlist.AddRange(((ListProcessException)ex).errorList);
                    }
                    return;
                }
                if (ex is CloudUnAuthorized)
                {
                    throw;
                }
                if (flags.IsWeb && ex is System.Net.WebException)
                {
                    if (errorlist != null && item != null)
                    {
                        errorlist.Add(item, ex);
                        return;
                    }
                    else
                    {
                        throw;
                    }
                }
                if (flags.IsAll)
                {
                    if (errorlist != null && item != null)
                    {
                        errorlist.Add(item, ex);
                        return;
                    }
                    else
                    {
                        throw;
                    }
                }
                else
                {
                    throw;
                }
            }
        }

        public static void ReThrowException(Exception ex)
        {
            if (ex is System.Net.WebException)
            {

                var webEx = (System.Net.WebException)ex;
                if (webEx.Response is System.Net.HttpWebResponse)
                {
                    var code = ((System.Net.HttpWebResponse)(webEx.Response)).StatusCode;

                    if (code == System.Net.HttpStatusCode.Unauthorized)
                    {
                        throw new CloudUnAuthorized(ex);
                    }
                }
            }
            else if (ex is UnauthorizedAccessException)
            {
                throw new CloudUnAuthorized(ex);
            }
            else if ((ex.Message.Contains("no such file or folder") || (ex.Message.Contains("file not found") || ex is FileNotFoundException)))
            {
                throw new ItemNotFound(ex);
            }
            throw ex;
        }

        private void RunUnsafeUpdate(SPWeb web, Action func)
        {
            try
            {
                web.AllowUnsafeUpdates = true;
                func();
            }
            finally
            {
                web.AllowUnsafeUpdates = false;
            }
        }

        private string RemoveInvalidSymbols(string name)
        {
            StringBuilder _name = new StringBuilder(name);
            for (int i = 0; i < InvalidSharePointFileNameCharacters.Length; i++)
            {
                _name.Replace(InvalidSharePointFileNameCharacters[i], '_');
            }
            
            return _name.ToString().Trim();

        }

        #endregion
    }

    public class SyncItemInformations
    {
        public SyncItemInformations()
        {
            infos = new List<SyncItemInformation>();
        }
        public List<SyncItemInformation> infos { set; get; }

    }
    public class SyncItemInformation
    {
        public List<SyncItemInfo> items { set; get; }
        public string listGuid { set; get; }
    }

    public class SendItemInformations
    {
        public SendItemInformations()
        {
            infos = new List<SendItemInformation>();
        }
        public List<SendItemInformation> infos { set; get; }
    }

    public class SendItemInformation
    {
        public List<ItemID> items { set; get; }
        public string listGuid { set; get; }
        public string folderId { set; get; }
    }

    public class SyncItemInfo
    {
        public ItemID item;
        public int conflictOption; //0 - show error when conflict, 1 - use file from cloud, 2 - create new file on the Sharepoint
    }

    public class ItemID
    {
        public int id;
        public int FSObjType;
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/ChangeToTextConverter.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
using System.Windows.Data;
using Workshare.Components.WSLogger;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;

namespace Workshare.Components.Views.TrueSyncDialog
{
    class ChangeToTextConverter:IValueConverter
    {
        public string TimeFormat = "HH:mm dd/MM";
        public string TimeFormatDateOnly = "dd/MM";

        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            try
            {
                var change = value as FileActivityChange;
                var sb = new StringBuilder();
                if (change != null)
                {
                    var wsFile = change.Parent.WsFile;
                    switch (change.Type)
                    {
                        case ChangeType.Uploaded:
                        {
                            if (wsFile != null)
                            {
                                sb.AppendFormat("Shared in Workshare by {0} since {1}", wsFile.Creator.UserName,
                                    wsFile.CreatedAt.ToString(TimeFormatDateOnly));
                            }
                            else
                            {
                                sb.Append("Shared");
                            }
                            break;
                        }
                        case ChangeType.RemoteDeleted:
                        {
                            sb.Append("Deleted or moved from Workshare");
                            break;
                        }

                        case ChangeType.RemoteAdded:
                        {
                            if (wsFile != null)
                            {
                                var lastVersion =
                                    change.NewerVersions.OrderByDescending(p => p.Version).FirstOrDefault();
                                string versionUpdater = lastVersion == null ? "" : lastVersion.Creator.UserName;
                                string versionUploadDate = lastVersion == null
                                    ? ""
                                    : lastVersion.CreateDate.ToString(TimeFormat);
                                sb.AppendFormat("New document uploaded by {0} at {1}", versionUpdater, versionUploadDate);
                            }
                            else
                            {
                                sb.Append("New document uploaded");
                            }
                            break;
                        }
                        case ChangeType.RemoteChanged:
                        {
                            if (wsFile != null)
                            {
                                var lastVersion =
                                    change.NewerVersions.OrderByDescending(p => p.Version).FirstOrDefault();
                                string versionUpdater = lastVersion == null ? "" : lastVersion.Creator.UserName;
                                string versionUploadDate = lastVersion == null ? "" : lastVersion.CreateDate.ToString(TimeFormat);
                                sb.AppendFormat("New version uploaded by {0} at {1}", versionUpdater, versionUploadDate);
                            }
                            else
                            {
                                sb.Append("New version uploaded");
                            }
                            break;
                        }

                        case ChangeType.LocalChanged:
                        {
                            sb.AppendFormat("File changed locally after sharing in Workshare");
                            break;
                        }

                        case ChangeType.NamesDiffer:
                        {
                            if (wsFile != null)
                            {
                                sb.AppendFormat("Name differs. In Workshare : {0}. Locally : {1}", change.WsName,
                                    change.LocalName);
                            }
                            else
                            {
                                sb.Append("Local and remote name are different");
                            }
                            break;
                        }

                        case ChangeType.BothChanged:
                        {
                            sb.AppendFormat("File was changed locally and remotely after sharing in Workshare");
                            break;
                        }

                        case ChangeType.DocTypeChanged:
                        {
                            sb.AppendFormat("Document type changed from {0} to {1}", change.LocalDocType,
                                change.WsDocType);
                            break;
                        }

                        case ChangeType.NotSentVersion:
                        {
                            sb.AppendFormat("Local version #{0} not sent. Saved at {1}", change.VersionNumber,
                                change.SavedTime);
                            break;
                        }

                        case ChangeType.VersionChangedAfterSend:
                        {
                            sb.AppendFormat("Version #{0} was changed after send. Saved at {1}", change.VersionNumber,
                                change.SavedTime);
                            break;
                        }

                        case ChangeType.FolderSharedWithOthers:
                        {
                            sb.AppendFormat("Folder shared by {0} with {1} other(s)", change.FolderSharedBy.UserName,
                                change.OtherMemebersCount);
                            break;
                        }

                        default:
                        {
                            sb.AppendFormat("{0}", change);
                            break;
                        }
                    }
                }

                return sb.ToString();
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                return "Error during detecting of changes";
            }
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Authentication/AuthentificationForm.cs
﻿using System;
using System.Net;
using System.Runtime.InteropServices;
using System.Text;
using System.Windows.Forms;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.WSLogger;
using Workshare.Integration.Exceptions;
using WorkshareCloud.ServiceProxy.ProxyHelper;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Views.Authentication
{
    public partial class AuthentificationForm : Form
    {
//        public readonly static string LoginRelUri = string.Format("login?claim_token_url={1}&reuse_session=1", HttpUtility.UrlEncode(PlatformService.HostWithSchema.ToString()).Replace("%2520", "%20"));
        public readonly static string LoginRelUri = string.Format("login?device[app_uid]={0}", WSApplication.Instance.APP_CODE);

        Uri LoginUri
        {
            get
            {
                return new Uri(WSApplication.Instance.Server + LoginRelUri);
            }
        }

        public Exception Error { get; set; }

        public AuthentificationForm()
        {
            InitializeComponent();
            var sh = new ScriptHelper();
            sh.act_LaunchInBrowser = (a) => { this.webBrowserForm.Navigate(a); };
            this.webBrowserForm.ObjectForScripting = sh;
            this.Disposed += AuthentificationForm_Disposed;
            this.Text = RES.STR_LOGIN_WINDOW_TITLE;
            this.Width = 1020;
            this.Height = 800;
            //this.StartPosition = FormStartPosition.CenterParent;
            this.Load += AuthentificationForm_Load;
            //webBrowserForm.ScriptErrorsSuppressed = true; breaks authentication with domain credentials
            webBrowserForm.Navigated += (object sender, WebBrowserNavigatedEventArgs args) =>
            {
                Action<HtmlDocument> blockAlerts = (HtmlDocument d) =>
                {
                    HtmlElement h = d.GetElementsByTagName("head")[0];
                    HtmlElement s = d.CreateElement("script");
                    mshtml.IHTMLScriptElement e = (mshtml.IHTMLScriptElement)s.DomElement;
                    e.text = "window.alert=function(){};";
                    h.AppendChild(s);
                };
                var b = sender as WebBrowser;
                blockAlerts(b.Document);
                for (int i = 0; i < b.Document.Window.Frames.Count; i++)
                    try { blockAlerts(b.Document.Window.Frames[i].Document); }
                    catch (Exception) { };
            };
            webBrowserForm.NavigateError += webBrowserForm_NavigateError;
            webBrowserForm.Navigated += webBrowserForm_Navigated;
            webBrowserForm.DocumentCompleted += webBrowserForm_DocumentCompleted;
            webBrowserForm.IsWebBrowserContextMenuEnabled = false;
            webBrowserForm.AllowWebBrowserDrop = false;
        }

        void webBrowserForm_NavigateError(object sender, NewWebBrowser.WebBrowserNavigateErrorEventArgs e)
        {
            if (e.StatusCode == (int)HttpStatusCode.ProxyAuthenticationRequired)
            {
                Error = new OfflineException(RES.STR_CONNECTION_ERROR_TEXT_PROXYAUTHENTICATIONREQUIRED, null); 
            }
            else
            {
                Error = new OfflineException();
            }

            webBrowserForm.Navigate("about:blank");
            this.DialogResult = DialogResult.Abort;
            this.Close();
        }

        void webBrowserForm_DocumentCompleted(object sender, WebBrowserDocumentCompletedEventArgs e)
        {
            if (webBrowserForm.Document != null)
            {
                var loginctrl = webBrowserForm.Document.GetElementById("user_session_email");
                if (loginctrl != null)
                {
                    loginctrl.Focus();
                }
            }
            this.pb_Loader.Visible = false;
        }

        void AuthentificationForm_Disposed(object sender, EventArgs e)
        {
           webBrowserForm.Dispose();
        }

        void AuthentificationForm_Load(object sender, EventArgs e)
        {
            Logger.Write("Version of WebBrowser installed: " + webBrowserForm.Version, Severity.Information);

            if (ProxyDetector.CheckForProxy(User, this.Handle))
            {

                if (webBrowserForm.Version.Major <= ModuleViewBase.IE8MAJORVERSION)
                {
                    webBrowserForm.Navigate(LoginUri, null, null, @"User-Agent:Mozilla/4.0 (compatible; MSIE 8.0)");
                }
                else
                {
                     webBrowserForm.Navigate(LoginUri);
                }
            }
            else
            {
                this.DialogResult = DialogResult.Cancel;
                this.Close();
            }
        }

        public CookieContainer Cookies = new CookieContainer();
        public UserDetails User =WSApplication.Instance.AuthProvider.GetCurrentWSUser();

        void webBrowserForm_Navigated(object sender, WebBrowserNavigatedEventArgs e)
        {
            Logger.Write("Redirected to a: " + e.Url, Severity.Information);

            // This has been added to enable the Single Sign on with PingOne
            if (e.Url.ToString().EndsWith("/sso/login"))
                return;

            if (e.Url.ToString().StartsWith("https://sso.connect.pingidentity.com/sso"))
                return;

            if (e.Url.ToString().EndsWith("startsso.aspx?sp=pingone"))
                return;


            var doc = webBrowserForm.Document;
            if (doc != null)
            {
                var str = CookieReader.Reader.GetCookie(LoginUri.ToString());

                if (!string.IsNullOrEmpty(str))
                {
                    var splits = str.Split(';');
                    if (splits.Length > 1)
                    {
                        foreach (var cookie in splits)
                        {
                            var cookieSplit = cookie.Split('=');
                            if (cookie.Length < 2) continue;
                            var cookieName = cookieSplit[0].Trim();
                            if (string.Equals(cookieName, DMSAuthProvider.DeviceCredential, StringComparison.InvariantCultureIgnoreCase))//(string.Equals(cookieName, ManAuthProvider._session_id, StringComparison.InvariantCultureIgnoreCase) || string.Equals(cookieName, ManAuthProvider.user_credentials, StringComparison.InvariantCultureIgnoreCase))
                            {
                                var cookieObj = new Cookie(cookieName, cookieSplit[1]);
                                Cookies.Add(WSApplication.Instance.Server, cookieObj);
                            }
                        }
                    }
                }
                if (!doc.Url.AbsolutePath.Contains("login") && Cookies.Count == 1 /*&& !doc.Url.AbsolutePath.IsDiscarded("user_sessions")*/)
                {
                    if (User == null) 
                    { 
                        User = new UserDetails() { SessionCookies = Cookies };
                    } 
                    else 
                    {
                        User.SessionCookies = Cookies;
                    }
                    this.DialogResult = (Cookies.Count == 1) ? DialogResult.OK : DialogResult.Cancel;
                    this.Close();
                }
            }
            else
            {
                Logger.Write("HTML DOCUMENT IS NULL: " + e.Url, Severity.CriticalError);
            }
        }

    }

    [ComVisible(true)]
    public class ScriptHelper
    {
        public Action<string> act_LaunchInBrowser
        {
            get;
            internal set;
        }

        public void launchUrlInBrowser(string url)
        {
            if (act_LaunchInBrowser != null)
            {
                act_LaunchInBrowser(url);
            }
        }
    }

    internal class CookieReader
    {
        /// <summary>
        /// Enables the retrieval of cookies that are marked as "HTTPOnly". 
        /// Do not use this flag if you expose a scriptable interface, 
        /// because this has security implications. It is imperative that 
        /// you use this flag only if you can guarantee that you will never 
        /// expose the cookie to third-party code by way of an 
        /// extensibility mechanism you provide. 
        /// Version:  Requires Internet Explorer 8.0 or later.
        /// </summary>
        private const int INTERNET_COOKIE_HTTPONLY = 0x00002000;

        [DllImport("wininet.dll", SetLastError = true)]
        private static extern bool InternetGetCookieEx(
            string url,
            string cookieName,
            StringBuilder cookieData,
            ref int size,
            int flags,
            IntPtr pReserved);

        /// <summary>
        /// Returns cookie contents as a string
        /// </summary>
        /// <param name="url"></param>
        /// <returns></returns>
        public string GetCookie(string url)
        {
            int size = 512;
            var sb = new StringBuilder(size);
            if (!InternetGetCookieEx(url, null, sb, ref size, INTERNET_COOKIE_HTTPONLY, IntPtr.Zero))
            {
                if (size < 0)
                {
                    return null;
                }
                sb = new StringBuilder(size);
                if (!InternetGetCookieEx(url, null, sb, ref size, INTERNET_COOKIE_HTTPONLY, IntPtr.Zero))
                {
                    return null;
                }
            }
            return sb.ToString();
        }

        public static CookieReader Reader = new CookieReader();
    }
}
<file_sep>/SharePoint/src/WorksharePointCloud/Layouts/WorkshareCloud/FileIconHandler.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web;
using System.Net;
using System.IO;
using System.Web.Script.Serialization;
using WorkshareCloud.Common;
using Microsoft.SharePoint.Utilities;
using Microsoft.SharePoint;

namespace WorkshareCloud.Layouts.WorkshareCloud
{
    class FileIconHandler : IHttpHandler
    {
        public bool IsReusable
        {
            get { return false; }
        }

        public void ProcessRequest(HttpContext context)
        {
            try
            {
                string str_size = context.Request.QueryString["size"];
                IconSize size = IconSize.Size16;
                if (string.Equals(str_size, "32"))
                {
                    size = IconSize.Size32;
                }
                var filename = context.Request.QueryString["filename"];
                if (string.IsNullOrEmpty(filename))
                {
                    filename = "a.txt";
                }

                if (new[] { "32", "16" }.Contains(str_size))
                {
                    var iconUrl = SPUtility.ConcatUrls("/_layouts/images/", SPUtility.MapToIcon(SPContext.Current.Web, filename, "", size));
                    context.Response.Redirect(iconUrl, false);
                }
                else if (string.Equals(str_size, "40"))
                {
                    var iconUrl = getMedium(Path.GetExtension(filename));
                    context.Response.Redirect(iconUrl, false);
                }
            }
            catch (Exception)
            {
                context.Response.Redirect("/_layouts/images/ictxt.gif", false);
            }
        }
        private static readonly string[] WordExt = { ".docx", ".docm", ".dotx", ".dotm", ".doc", ".dot", ".rtf" };

        private static readonly string[] ExcelExt = {
		                                            	".xl", ".xlsx", ".xlsm", ".xlsb", ".xlam", ".xltx", ".xltm", ".xls",
		                                            	".xlt"
		                                            };

        private static readonly string[] PptExt = {
		                                          	".pptx", ".ppt", ".pptm", ".ppsx", ".pps", ".ppsm", ".potx", ".pot",
		                                          	".potm", ".odp"
		                                          };
        private static readonly string[] PDFExt = { ".pdf" };

        private static readonly string[] AudioExt = { ".mp3", ".wav", ".flac", ".aac" };
        private static readonly string[] VideoExt = { ".avi", ".mp4", ".mov", ".mkv" };
        private static readonly string[] ImageExt = { ".bmp", ".jpg", ".jpeg", ".jpe", ".jfif", ".ico", ".png", ".tif", ".tiff", ".dib", ".raw", ".gif" };

        string getMedium(string ext)
        {
            var imageUrl = "/_layouts/WorkshareCloud/Images/docs/";
            if (WordExt.Contains(ext))
            {
                imageUrl += "doc-medium.png";
            }
            else if (ExcelExt.Contains(ext))
            {
                imageUrl += "xls-medium.png";
            }
            else if (PptExt.Contains(ext))
            {
                imageUrl += "ppt-medium.png";
            }
            else if (PDFExt.Contains(ext))
            {
                imageUrl += "pdf-medium.png";
            }
            else if (ImageExt.Contains(ext))
            {
                imageUrl += "image-medium.png";
            }
            else if (AudioExt.Contains(ext))
            {
                imageUrl += "audio-medium.png";
            }
            else if (VideoExt.Contains(ext))
            {
                imageUrl += "video-medium.png";
            }
            else
            {
                imageUrl += "generic-medium.png";
            }
            return imageUrl;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/Visitors/BreakLinkVisitor.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Components.WSLogger;
using Workshare.Integration.Processor.Services;

namespace Workshare.Integration.Processor.Maps.Visitors
{
    internal class BreakLinkVisitor : ItemMapVisitor
    {
        private readonly SyncInfoService _syncInfoService;
        private readonly Stack<ItemMap> _currentParent = new Stack<ItemMap>();

        public BreakLinkVisitor(SyncInfoService syncInfoService)
        {
            _syncInfoService = syncInfoService;
        }


        public override bool VisitEnter(FileMap fileMap)
        {
            var parentFolderMap = _currentParent.Peek() as FolderMap;
            if (parentFolderMap.HasLocal()&&fileMap.HasLocal())
            {
                var parentInfo=_syncInfoService.GetSyncInfo(parentFolderMap.LocalFolder);
                var fileSyncInfo = _syncInfoService.GetSyncInfo(fileMap.LocalFile);
                if (parentInfo != null && fileSyncInfo!=null && fileSyncInfo.ParentId==parentInfo.ItemId)
                {
                    _syncInfoService.BreakLink(fileMap.LocalFile);
                }
            }

            return false;
        }

        public override bool VisitEnter(FolderMap folderMap)
        {
            var parentMap = _currentParent.Count == 0 ? null : _currentParent.Peek();
            _currentParent.Push(folderMap);
            try
            {
                var parentFolderMap = parentMap as FolderMap;
                if (parentMap == null || parentFolderMap.HasLocal())
                {
                    var parentInfo = (parentFolderMap != null)
                        ? _syncInfoService.GetSyncInfo(parentFolderMap.LocalFolder)
                        : null;
                    var folderSyncInfo = (folderMap.HasLocal()) ? _syncInfoService.GetSyncInfo(folderMap.LocalFolder) : null;
                    return folderSyncInfo != null &&
                           (parentInfo == null || folderSyncInfo.ParentId == parentInfo.ItemId);
                }

                return false;
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                folderMap.Error = ex;
                folderMap.ProcessState=ProcessState.Error;
                return true;
            }
            
        }

        public override void VisitLeave(FolderMap folderMap)
        {
            _currentParent.Pop();
        }

        public override void Visit(FolderMap foldermap)
        {
            try
            {
                _syncInfoService.BreakLink(foldermap.LocalFolder);
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                foldermap.Error = ex;
                foldermap.ProcessState = ProcessState.Error;
            }
            
        }

        public override void Visit(FileMap fileMap)
        {
            try
            {
                _syncInfoService.BreakLink(fileMap.LocalFile);
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                fileMap.Error = ex;
                fileMap.ProcessState = ProcessState.Error;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/UserDetails.cs
﻿using System.Net;
using System.Globalization;
namespace WorksharePlatform
{
    public class UserDetails
    {
        public UserDetails()
        {
           Host = PlatformService.Host;
           Proxy = null;
        }
        public string UserId { get; set; }
        public string AccountUuId { get; set; }
        public string AccountId { get; set; }
        public string Company { get; set; }
        public string Email { get; set; }
        public string Password { get; set; }
        public string ConfirmPassword { get; set; }
        public string UserName { get; set; }
        public string Phone { get; set; }
        public CookieContainer SessionCookies { get; set; }
        public ICredentials ProxyCredentials { get; set; }
        public WebProxy Proxy { get; set; }

        public string AuthToken { get; set; }
        public int CurrentFolderId { get; set; }
        public string Host { get; set; }
        public string ServiceUrl
        {
            get
            {
                return PlatformService.ServiceUrl;
            }
        }

        public bool IsProxyEnable
        {
            get
            {
                return Proxy != null;
            }
        }


        public int RootFolderId { get; set; }

        public string Domain { get; set; }
    }
}
<file_sep>/WSComponents/src/WSCloudService/FileVersionDetails.cs
﻿using System;

namespace WorksharePlatform
{
    public class FileVersionDetails
    {
        public int Id { get; set; }
        public int FileId { get; set; }
        public int CompleteId { get; set; }
        public string MultiPartId { get; set; }
        public bool IsChunkingRequired { get; set; }
        public string Name { get; set; }
        public long Size { get; set; }
        public int Version { get; set; }
        public string Action { get; set; }
        public string Key { get; set; }
        public string AwsAccessKey { get; set; }
        public string AclType { get; set; }
        public string Policy { get; set; }
        public string Signature { get; set; }
        public string SuccessRedirect { get; set; }
        public string ContentType { get; set; }
        public string Cache { get; set; }
        public string Encryption { get; set; }
        public string ImageUrl { get; set; }
        public string ThumbUrl { get; set; }
        public UserDetails Creator { get; set; }
        public DateTime CreateDate { get; set; }

        public ApiVersion ApiVersion { get; set; }

        //parameters for api v1.3
        public string ContentLength { get; set; }
        public string UserAgent { get; set; }
        public string Authorization { get; set; }
        public string HttpVerb { get; set; }
        public string AuthDate { get; set; }
    }

    public enum ApiVersion { One = 1, Three = 2 }
}

<file_sep>/WSComponents/src/WSIntegration/Common/OwnCancellationTokenSource.cs
﻿using System;
using Workshare.Components.WSLogger;

namespace Workshare.Integration.Common
{
    public class OwnCancellationTokenSource
    {
        private string id;

        public OwnCancellationTokenSource()
        {
            id = Guid.NewGuid().ToString();
        }

        private bool _cancelled;

        public bool IsCancelled {
            get { return _cancelled; }
        }

        public void Cancel()
        {
            _cancelled = true;
            Logger.WriteTrace(string.Format("cancellation token {0} was set to true", id));
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Common/ActivityCounter.cs
﻿#define ENABLE_COUNTER
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics;
using System.Linq;
using System.Threading;
using Workshare.Components.Concrete;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.WsProxies;
using WorksharePlatform;


namespace Workshare.Components.Common
{
    class ActivityInfo
    {
        public IDMSFolder Folder;
        public DateTime UpdateTime;
        public List<FileMapActivity> Changes;

        public int FoldersActivity
        {
            get
            {
                return Changes.Count;
            }
        }
    }

    enum ActivityUpdateAction
    {
        Update,
        Remove
    }

    public class ActivityCounter
    {
        static ActivityCounter _instance = null;
        IDMSFolder _currentFolder;
        Thread updateFolderThread = null;
        Dictionary<int, ActivityInfo> _counterArr;
        object lock_object;
        const int UpdateFolderInterval = 30000;
        BackgroundWorker _worker;
        ModuleBase _module;
        WsProxy _wsProxy;

        ActivityCounter(ModuleBase module)
        {
            _module = module;
            _counterArr = new Dictionary<int, ActivityInfo>();
            lock_object = new object();
            _currentFolder = null;
            _worker = new BackgroundWorker();
            _worker.DoWork+=_worker_DoWork;
            _wsProxy = new WsProxy();
        }

        void AddFoldersActivityCount(IDMSFolder _folder, List<FileMapActivity> _changes)
        {
            lock (lock_object)
            {
                if (_counterArr.ContainsKey(_folder.DMSId))
                {
                    _counterArr[_folder.DMSId].Changes = _changes;
                    _counterArr[_folder.DMSId].UpdateTime = DateTime.Now;
                }
                else
                {
                    _counterArr.Add(_folder.DMSId, new ActivityInfo() { Changes = _changes, Folder = _folder, UpdateTime = DateTime.Now });
                }
            }
        }

        public void Remove(IDMSFolder folder)
        {
            lock (lock_object)
            {
                if (_counterArr.ContainsKey(folder.DMSId))
                {
                    _counterArr.Remove(folder.DMSId);
                }
                if (_counterArr.Count > 0)
                {
                    _currentFolder = _counterArr.First().Value.Folder;
                }
            }
        }

        public static ActivityCounter Instance
        {
            get
            {
                return _instance ?? (_instance = new ActivityCounter(WSApplication.Instance.Module)); 
            }
        }

        public IDMSFolder CurrentFolder
        {
            get
            {
                return _currentFolder;
            }
            set
            {
                if (value != null) 
                {
                    try
                    {
                        if (_currentFolder == null || _currentFolder.DMSId != value.DMSId)
                        {
                            _currentFolder = value;
                            UpdateUserFolder(_currentFolder);
                        }
                    }
                    catch (Exception ex)
                    {
                        Logger.WriteError("Error in update user folder for the counter", ex);
                    }
                }
            }
        }

        public int ActivityCount(IDMSFolder _folder)
        {
            lock(lock_object)
            {

                if (_counterArr.ContainsKey(_folder.DMSId))
                {
                    return _counterArr[_folder.DMSId].FoldersActivity;
                }
                else
                {
                    return -1;
                }
            }
        }

        bool NeedToScanAll
        {
            get
            {
                lock (lock_object)
                {
                    return _counterArr.Count == 0;
                }
            }
        }

        bool CheckIfNeedUpdateFolder(IDMSFolder _folder)
        {
            TimeSpan diff = TimeSpan.Zero;
            lock (lock_object)
            {

                if (_counterArr.ContainsKey(_folder.DMSId))
                {
                    diff = DateTime.Now - _counterArr[_folder.DMSId].UpdateTime;
                }
            }
            if (diff == TimeSpan.Zero)
            {
                return true;
            }
            else
            {
                return diff.TotalMilliseconds >= UpdateFolderInterval;
            }
        }

        void _worker_DoWork(object sender, DoWorkEventArgs e)
        {
            try
            {
                while (true)
                {
                    try
                    {
                        ProcessFolder(_currentFolder);
                        Thread.Sleep(10000);
                    }
                    catch (ThreadAbortException)
                    {
                        
                    }
                    catch (Exception ex)
                    {
                        Logger.WriteError(ex);
                        Thread.Sleep(10000);
                    }
                }
            }
            catch (Exception ex)
            {
                Trace.TraceError(ex.ToString());
            }
        }

        void UpdateFoldersActivityCount(IDMSFolder _folder, ActivityUpdateAction updateAction, List<FileMapActivity> _changes = null)
        {
            lock (lock_object)
            {
                switch (updateAction)
                {
                    case ActivityUpdateAction.Remove:
                        Remove(_folder);
                        break;
                    case ActivityUpdateAction.Update:
                        AddFoldersActivityCount(_folder, _changes);
                        break;
                }
            }
        }

        private void ProcessFolder(IDMSFolder folder)
        {
            if (folder.IsDeleted)
            {
                Instance.Remove(folder);
                return;
            }

            var processor = _module.Resolve<Processor>();
            var scanmaps = processor.Scan(new List<BaseDMSItem> { (BaseDMSItem)folder }, new ScanOptions() { UseForceRequest = false });

            var counterVisitor = new CounterVisitor(UpdateFoldersActivityCount, _module);
            scanmaps.Apply(counterVisitor);
        }

        bool fullScanInProgress = false;

        void FullScan(IDMSItem _item)
        {
            try
            {
                fullScanInProgress = true;
                if (_item != null && _item.RootFolder() != null)
                {
                    List<IDMSFolder> flds = _item.RootFolder().SubFolders.ToList();
                    foreach (var fld in flds)
                    {
                        ProcessFolder(fld);
                    }
                }

            }
            catch(Exception ex)
            {
                Logger.Write("Full scan activity error",ex, Severity.Error);
            }
            finally
            {
                fullScanInProgress = false;
                _worker.RunWorkerAsync();
            }
        }


        public void UpdateUserFolder(IDMSFolder _folder, bool force = false)
        {
            var usr = WSApplication.Instance.AuthProvider.GetCurrentWSUser();
            // if user is loged in
            if (_folder != null && !_folder.IsDeleted && _wsProxy.IsUserLoggedIn(usr))
            {
                // for the first time scan all folders
                if (NeedToScanAll && !fullScanInProgress)
                {
                    var fullscanthread = new Thread(() =>
                    {
                        try
                        {
                            FullScan(_folder);
                        }
                        catch (Exception ex)
                        {
                            Logger.WriteError(ex);
                        }
                        
                    });
#if ENABLE_COUNTER
                    fullscanthread.Start();
#endif
                }

                if (CheckIfNeedUpdateFolder(_folder) || force)
                {
                    if (updateFolderThread != null && updateFolderThread.ThreadState == System.Threading.ThreadState.Running)
                    {
                        updateFolderThread.Abort();
                        updateFolderThread.Join();
                        updateFolderThread = null;
                    }
                    updateFolderThread = new Thread(() =>
                    {
                        try
                        {
                            ProcessFolder(_folder);
                        }
                        catch (Exception ex)
                        {
                            Logger.WriteError(ex);
                        }
                    });
#if ENABLE_COUNTER
                    updateFolderThread.Start();
#endif
                }
            }

        }

    }


    class CounterVisitor : ItemMapVisitor
    {
        internal delegate void UpdateFunctionDelegate(IDMSFolder _folder, ActivityUpdateAction _updateAction, List<FileMapActivity> _changes = null);
        internal UpdateFunctionDelegate updateFunction;

        ModuleBase _module;

        public CounterVisitor(UpdateFunctionDelegate _updateFunction, ModuleBase module)
        {
            updateFunction = _updateFunction;
            _module = module;
        }

        public override void Visit(FileMap result)
        {
        }

        public override void Visit(FolderMap foldermap)
        {
            if (foldermap != null && foldermap.LocalFolder != null && foldermap.WsFolder != null)
            {
                var sis = _module.Resolve<SyncInfoService>();
                if (!foldermap.HasRemote() && foldermap.ProcessState == ProcessState.Scanned && foldermap.LocalFolder != null && sis.GetSyncInfo(foldermap.LocalFolder, false) == null)
                {
                    updateFunction(foldermap.LocalFolder, ActivityUpdateAction.Update, new List<FileMapActivity>());
                }
                else
                {
					var adapter = new ActivityFinder(WSApplication.Instance.Module);
                    updateFunction(foldermap.LocalFolder, ActivityUpdateAction.Update, adapter.GetAllActivities(foldermap, new List<FileMapActivity>(), false).Where(TrueSyncDialogViewModel.FilterActivities).ToList());
                }
            }
            else if (foldermap != null && foldermap.LocalFolder != null && foldermap.WsFolder == null)
            {
                updateFunction(foldermap.LocalFolder, ActivityUpdateAction.Remove);
            }
        }

        public override bool VisitEnter(FolderMap folderMap)
        {
            return true;
        }

        public override void VisitLeave(FolderMap folderProcessResult)
        {
            
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/ProcessStrategy.cs
﻿using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies.ActionStrategy;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Strategies
{
    public class ProcessStrategy : DmsProcessStrategyBase
    {
        WsProxy wsProxy;
        IAuthProvider auth;
        DmsWorkerBase dmsWorker;
        SyncInfoService syncInfoService;
        ModuleBase module;
        public ProcessStrategy(ModuleBase module, WsProxy wsProxy, IAuthProvider auth, DmsWorkerBase dmsWorker, SyncInfoService syncInfoService)
        {
            this.wsProxy=wsProxy;
            this.auth = auth;
            this.dmsWorker = dmsWorker;
            this.syncInfoService = syncInfoService;
            this.module = module;
        }

        public override ProcessResult Process(FileMap fileMap, DmsProcessOptions dmsProcessOptions)
        {
            return ProcessInternal(fileMap, dmsProcessOptions);
        }

        public ProcessResult ProcessInternal(ItemMap fileMap, DmsProcessOptions dmsProcessOptions)
        {
            var forthisNode = dmsProcessOptions.Actions
                .Where(a => (a.Activity == null ? a.ActivityId : a.Activity.MapId) == fileMap.Id)
                   .Distinct(new CompareByType()).ToList();

            var res = new ProcessResult(fileMap.ProcessState);
            foreach (var action in forthisNode)
            {
                ActionStrategy.ActionStrategy actionStrategy = null;
                if (action.Type == ActionType.None)
                {
                    continue;
                }
                else if (action.Type == ActionType.Import)
                {
                    actionStrategy = module.Resolve<ImportStrategy>();
                }
                else if (action.Type == ActionType.Upload)
                {
                    actionStrategy = module.Resolve<UploadStrategy>();
                }
                else if (action.Type == ActionType.CeaseCollaboration)
                {
                    actionStrategy = module.Resolve<CeaseCollaborationStrategy>();
                }
                Debug.Assert(actionStrategy != null, "New action type?");
                
                if (fileMap is FolderMap)
                {
                    res = actionStrategy.Process((FolderMap) fileMap, action);
                }
                else if(fileMap is FileMap)
                {
                    res = actionStrategy.Process((FileMap)fileMap, action);
                    
                }
                if (res.Result == ProcessState.Cancelled || res.Result == ProcessState.Error)
                {
                    return res;
                }
            }
            return res;
        }

        public override ProcessResult Process(FolderMap foldermap, DmsProcessOptions dmsProcessOptions)
        {
            return ProcessInternal(foldermap, dmsProcessOptions);
        }


        public class CompareByType : IEqualityComparer<ItemMapActivityAction>
        {
            public bool Equals(ItemMapActivityAction x, ItemMapActivityAction y)
            {
                return x.Type == y.Type;
            }

            public int GetHashCode(ItemMapActivityAction obj)
            {
                return obj.Type.GetHashCode();
            }
        }

        
    }

}
<file_sep>/WSComponents/src/WSIntegration/Common/CollaborationItemInformation.cs
﻿using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using WorksharePlatform;

namespace Workshare.Integration.Common
{
    public class CollaborationItemInformation: SyncItemInformation
    {
        public IDMSItem item;
        public FileDetails wsItem;
        public ConflictOptions syncOption;
        public ConflictVersionOptions verOptions;
        public bool AddOnlyNewFiles;//if sync _folder then only new files should be added

        public CollaborationItemInformation(IDMSItem _item, ConflictOptions _option, ConflictVersionOptions _verOptions) : base(_item, _option, _verOptions)
        {
            item = _item;
            syncOption = _option;
            verOptions = _verOptions;
            wsItem = null;
        }

        public CollaborationItemInformation(FileDetails _wsitem, IDMSItem _item, ConflictOptions _option, ConflictVersionOptions _verOptions): base(_wsitem, _item, _option, _verOptions)
        {
            wsItem = _wsitem;
            syncOption = _option;
            verOptions = _verOptions;
            item = _item;
        }

        public CollaborationItemInformation CopyFor(IDMSItem item)
        {
            return new CollaborationItemInformation(item, syncOption, verOptions);
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/CeaseCollaborationCommand.cs
﻿using System;
using System.Linq;
using System.Runtime.InteropServices;
using Workshare.Components;
using Workshare.Components.Helpers;
using Workshare.Components.Properties;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;

namespace Workshare.IManage
{
    public class CeaseCollaborationCommand : Command
    {
        //public override object Bitmap
        //{
        //    get
        //    {
        //        return Resources.workshare_collaboration.GetHbitmap();
        //    }
        //    set { }
        //}

        public override string MenuText
        {
            get
            {
                return "Close Collaboration";
            }
            set
            {
            }
        }

        public override string HelpText
        {
            get { return MenuText + "\nCollaboration item"; }
            set { }
        }

        public override void ExecuteAction()
        {
            var contextItems = GetContextItems().ToList();
            if (!contextItems.Any())
            {
                return;
            }

            if (!Application.iManInstance.Presenter.LoginIfNeeded())
            {
                return;
            }
            Application.iManInstance.ClientType = GetClientType();
            var linkedItems = contextItems.Where(p => syncService.GetSyncInfo(p, false) != null);
            var someItemsLinked = linkedItems.Any();
            var hasPermissions = contextItems.All(p => p.DoesUserHavePermissions(Permissions.EditItem));
            var anyTaskAlreadyInProgress = Application.iManInstance.Presenter.IsAnyItemInProgress();
            var someCheckedOutToOther = contextItems.Any(a => a.IsCheckedOutToOtherUser());

            var canCallob = someItemsLinked
                          && hasPermissions
                          && !anyTaskAlreadyInProgress
                          && !someCheckedOutToOther;
            if (canCallob)
            {
                Application.iManInstance.View.OnCollaborationItemsClicked(new CollaborationItemsClickedArgs(linkedItems.Select(p => new CollaborationItemInformation(p, ConflictOptions.None, ConflictVersionOptions.None))));
            }
            else if (!someItemsLinked)
            {
                if (contextItems.HasOnlyOneFile())
                {
                    ShowError(
                        new BaseException(Resources.STR_CollaborationItemsCommand_ExecuteAction_Unable_to_cease,
                            Resources.STR_ERROR_TEXT_File_is_not_sent_to_Workshare_), contextItems.FirstOrDefault());
                }
                else if (contextItems.HasOnlyOneFolder())
                {
                    ShowError(
                        new BaseException(Resources.STR_CollaborationItemsCommand_ExecuteAction_Unable_to_cease,
                            Resources.STR_ERROR_TEXT_Folder_is_not_sent_to_Workshare_), contextItems.FirstOrDefault());
                }
                else
                {
                    ShowError(
                        new BaseException(Resources.STR_CollaborationItemsCommand_ExecuteAction_Unable_to_cease,
                            Resources.STR_ExecuteAction_All_items_are_not_sent_to_Workshare), contextItems.FirstOrDefault());
                }
            }
            else if (anyTaskAlreadyInProgress)
            {
                ShowError(new BaseException(Resources.STR_CollaborationItemsCommand_ExecuteAction_Unable_to_cease, 
                    Resources.STR_ExecuteAction_Some_another_task_is_already_in_progress), contextItems.FirstOrDefault());
            }
            else if (someCheckedOutToOther)
            {
                ShowError(new BaseException(Resources.STR_CollaborationItemsCommand_ExecuteAction_Unable_to_cease, 
                    Resources.STR_ExecuteAction_File_is_checked_out_to_another_users), contextItems.FirstOrDefault());
            }
            else
            {
                ShowError(new DMSUnAuthorizedException(), contextItems.FirstOrDefault());
            }
        }
    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("9DC1D747-703C-43F5-9255-A3DFF7F177F6")]
    [ComVisible(true)]
    public class DocumentCeaseCollaborationCommand : CeaseCollaborationCommand
    {
        public override string HelpText
        {
            get
            {
                return "Close Collaboration for document on Workshare\nClose Collaboration";
            }
            set
            {
                base.HelpText = value;
            }
        }
    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("C7E01420-25DC-40D1-8736-FCE298657FBE")]
    [ComVisible(true)]
    public class FolderCeaseCollaborationCommand : CeaseCollaborationCommand
    {

        public override string HelpText
        {
            get
            {
                return "Close Collaboration for folder on Workshare\nClose Collaboration";
            }
            set
            {
                base.HelpText = value;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Progress/VMs/ProgressViewModel.cs
﻿using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
using System.Windows;
using System.Windows.Threading;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.Progress.VMs;
using Workshare.Components.Views.TrueSyncDialog.WorkUnits;
using Workshare.Components.WSLogger;

namespace Workshare.Components.Views.Progress
{
    class ProgressViewModel : BasePropertyChanged<ProgressViewModel>, IDisposable
    {
        readonly Dispatcher _dispatcher;

        public ObservableCollection<ProgressItemVm> Items { set; get; }

        public RelayCommand ClearCmd { set; get; }
        public RelayCommand RemoveItem{ set; get; }

        private CommandInvoker _invoker;

        public Visibility Visible
        {
            get
            {
                return (Items.Count > 0) && (!_supress) ? Visibility.Visible : Visibility.Hidden;
            }
            set
            {
            }
        }


        public ProgressViewModel()
        {
            Items = new ObservableCollection<ProgressItemVm>()
            {
             new ProgressItemVm()
             {
                 Name = "Processing something",
                 TargetItems = new ObservableCollection<TargetItemVm>()
                 {
                     new TargetItemVm(new TargetItem("as")
                     {
                         Name = "asd.docx"
                     })
                 }
             }
            };
        }

        public ProgressViewModel(CommandInvoker invoker)
        {
            _invoker = invoker;
            Items = new ObservableCollection<ProgressItemVm>();
            _dispatcher = Dispatcher.CurrentDispatcher;
            _invoker.WorkUnitAdded += invoker_WorkUnitAdded;
            _invoker.WorkCompleted += invoker_WorkCompleted;
        }
        bool _supress;
        public void Suppress(bool tosuppress)
        {
            this._supress = tosuppress;
            TriggerVisibilityChanged();
        }

        void TriggerVisibilityChanged()
        {
            //TODO Recview investigate
            ///We assume that view will be opened during all process life. But sometimes it is can be closed (if parent set and owner is closed)
            /// then it will fail. For now we just do not set Owner for Progress window
            /// Need to review design of progress window infrastructure
            try
            {
                this.PropertyHasChanged(a => a.Visible);
            }
            catch (InvalidOperationException ex)
            {
                Logger.WriteError(ex);
            }
        }

        void invoker_WorkUnitAdded(IWorkUnit obj)
        {
            if(obj==null)return;
            Logger.WriteTrace(string.Format("ProgressViewModel invoker_WorkUnitAdded Type={0}",obj.GetType()));
            if (obj is ScanWorkUnit || obj is CeaseCollaborationDialog.WorkUnits.ScanWorkUnit) return;
            InvokeiNDispatcherThread(() =>
            {                
                var existedProgressItem = Items.FirstOrDefault(a => a.Name == obj.Name);
                if (existedProgressItem == null)
                {
                    existedProgressItem = new ProgressItemVm()
                    {
                        Name = obj.Name
                    };
                }

                foreach (var item in obj.TargetItems)
                {
                    var newItemVm = new TargetItemVm(item);

                    existedProgressItem.TargetItems.Add(newItemVm);
                }

                if (!Items.Contains(existedProgressItem))
                {
                    Items.Add(existedProgressItem);
                }
                existedProgressItem.PropertyChangedAll();
                TriggerVisibilityChanged();
            });
        }

        void InvokeiNDispatcherThread(Action act)
        {
            if (_dispatcher.CheckAccess())
            {
                act();
            }
            else
            {
                _dispatcher.Invoke(act);
            }
        }

        void invoker_WorkCompleted(IWorkUnit obj)
        {
            InvokeiNDispatcherThread(() =>
            {
                var existedProgressItem = Items.FirstOrDefault(a => a.Name == obj.Name);
                if (existedProgressItem != null)
                {
                    foreach (var targetItem in obj.TargetItems)
                    {
                        var toRemove = existedProgressItem.TargetItems.Where(a => a.IsFor(targetItem)).ToList();
                        toRemove.ForEach(a => existedProgressItem.TargetItems.Remove(a));
                    }

                    if (existedProgressItem.TargetItems.Count == 0)
                    {
                        Items.Remove(existedProgressItem);
                    }
                    existedProgressItem.PropertyChangedAll();
                    TriggerVisibilityChanged();
                }
            });
        }

        public void Dispose()
        {
            _invoker.WorkUnitAdded -= invoker_WorkUnitAdded;
            _invoker.WorkCompleted -= invoker_WorkCompleted;
        }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/WSOTMenuInitializer.cs
﻿using System;
using System.Runtime.InteropServices;
using Hummingbird.DM.Extensions.Interop.DOCSObjects;
using Hummingbird.DM.Extensions.Interop.VHELPER;
using Workshare.Components.WSLogger;
using Workshare.OpenText.Concrete;


namespace Workshare.OpenText
{
    [ComVisible(true)]
    [ClassInterface(ClassInterfaceType.None)]
    [Guid("08986AE5-D79F-4EE7-B876-D1C69F09C01B")]
    public class WSOTMenuWrapper : IOMEventHandler, IOMDocumentMenuSink, IOMDocumentEventSink
    {
        VBConnector connector;
        public short ExecuteMenuItem(IDocProfiles pProfiles, string bstrCmdID)
        {
            try
            {
                CommandHelper.ExecuteMenu(pProfiles, bstrCmdID);
            }
            catch (Exception ex)
            {
                Logger.Write("Trying to EXECUTE menu item", ex, Severity.CriticalError);
            }

            return (short)HResultCodes.HS_NEXT_HANDLER;
        }

        public void GetMenuItems(IDocProfiles pProfiles, ControlMenu pMenu)
        {
            try
            {
                var mnu = CommandHelper.GetCommandName(pProfiles);
                var OTMenu = pMenu.GetMenu();
                if (mnu != null)
                {
                    bool AlreadyExist = false;
                    int i = 1;
                    while (!AlreadyExist && i<=OTMenu.Count)
                    {
                        if (string.Equals(OTMenu[i].ID, mnu.ID, StringComparison.InvariantCultureIgnoreCase))
                        {
                            AlreadyExist = true;
                        }
                        i++;
                    }

                    if (!AlreadyExist)
                    {
                        pMenu.AddVerb(mnu.ID, mnu.Name, mnu.Parent, mnu.InsertBefore, 0);
                    }
                    //pMenu.SetVerbIcons(mnu.ID, false, (int)RES.Workshare_48x48.Handle, (int)RES.Workshare_48x48.Handle, (int)RES.Workshare_48x48.Handle);
                }
            }
            catch (Exception ex)
            {
                Logger.Write("Trying to ADD menu item", ex, Severity.CriticalError);
            }
        }

        public void SelectionChanged(IDocProfiles pProfiles, ControlMenu pMenu)
        {
            //throw new NotImplementedException();
        }
        
        public void Init(IApplication pApp)
        {
            //System.Diagnostics.Debugger.Launch();
            try
            {
                connector = new VBConnector();
                int interfacesConnected;
                interfacesConnected = connector.Connect(pApp, this);
                Application.OTInstance.ParentWindow = pApp.DefParentWindow;
                Application.OTInstance.UserDST = pApp.DST;
                Application.OTInstance.CurrentLibraryName = pApp.CurrentLibrary.Name;
                Application.OTInstance.CurrentUser = pApp.CurrentLibrary.UserName;
            }
            catch { }

        }

        public void Terminate(IApplication pApp)
        {
            connector = null;
        }

        public short ProfileEvent(short sEventID, short sEventType, IProfile pProfile, Hummingbird.DM.Extensions.Interop.DOCSObjects.IBCCoreCtx pParams)
        {
            try
            {
                if (sEventType == 2 && (sEventID == (int)eDOCSDEventType.DE_UNLOCK || sEventID == (int)eDOCSDEventType.DE_RELEASE_DOC ))
                {
                    if (pProfile.Columns.Count > 0 && pProfile.Columns[Application.OTInstance.SENDINFO_FIELD].Value.ToString() != "")
                    {
                        pProfile.Columns[Application.OTInstance.SENDINFO_FIELD].Value = "";
                        pProfile.Save(0);
                    }
                }
            }
            catch
            { }

            return (short)HResultCodes.HS_NEXT_HANDLER;
        }

        public short VersionEvent(short sEventID, short sEventType, IVersion pVersion, Hummingbird.DM.Extensions.Interop.DOCSObjects.IBCCoreCtx pParams)
        {
            try
            {
                if (sEventType == 2 && (sEventID == (int)eDOCSDEventType.DE_CHECK_OUT || sEventID == (int)eDOCSDEventType.DE_LOCK))
                {
                    var pProfile = pVersion.Profile;
                    if (pProfile.Columns.Count > 0 && pProfile.Columns[Application.OTInstance.SENDINFO_FIELD].Value.ToString() != "")
                    {
                        pProfile.Columns[Application.OTInstance.SENDINFO_FIELD].Value = "";
                        pProfile.Save(0);
                    }
                }
            }
            catch
            { }

            return (short)HResultCodes.HS_NEXT_HANDLER;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncUploadFilesDialog/VMs/FileUploadActivityVm.cs
﻿using Workshare.Components.Views.TrueSyncDialog;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.TrueSyncUploadFilesDialog.VMs
{
    public class FileUploadActivityVm : UploadFileActivityVm
    {
        public FileUploadActivityVm()
            : base(null)
        {
        }

        public FileUploadActivityVm(UploadFileActivity data)
            : base(data)
        {
            _data = data;
        }
        
        public override bool DiscardAlwaysVisible
        {
            get { return true; }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Interfaces/IWSIntegration.cs
﻿using System.Collections.Generic;
using Workshare.Integration.Common;
using WorksharePlatform;

namespace Workshare.Integration.Interfaces
{
    public interface IWSIntegration
    {
        void SendItems(IEnumerable<IDMSItem> localItems, FolderDetails folder, OperationContext args);
    }
}
<file_sep>/SharePoint/src/WorksharePointCloud/ULSLogger.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint.Administration;

namespace WorkshareCloud
{
    internal class DiagnosticService : SPDiagnosticsServiceBase
    {
        private static string DiagnosticsAreaName = "SharePointEmails";

        public DiagnosticService()
        {
        }

        public DiagnosticService(string name, SPFarm farm)
            : base(name, farm)
        {

        }

        protected override IEnumerable<SPDiagnosticsArea> ProvideAreas()
        {
            List<SPDiagnosticsCategory> categories = new List<SPDiagnosticsCategory>();
            foreach (string catName in Enum.GetNames(typeof(Category)))
            {
                uint catId = (uint)(int)Enum.Parse(typeof(Category), catName);
                categories.Add(new SPDiagnosticsCategory(catName, TraceSeverity.Verbose, EventSeverity.Error, 0, catId));
            }

            yield return new SPDiagnosticsArea(DiagnosticsAreaName, categories);
        }

        public static DiagnosticService Local
        {
            get
            {
                return SPDiagnosticsServiceBase.GetLocal<DiagnosticService>();
            }
        }

        public SPDiagnosticsCategory this[Category id]
        {
            get
            {
                return Areas[DiagnosticsAreaName].Categories[id.ToString()];
            }
        }
    }

    public enum Category
    {
        Default,
        SelectFolderPage,
        NewFolderPage,
        CloudService
    }
    public enum SeverityEnum
    {
        Trace,
        Warning,
        Information,
        Error,
        CriticalError,
        Verbose
    }


    public class Logger
    {
        private static DiagnosticService Local
        {
            get
            {
                if (_local == null)
                {
                    _local = DiagnosticService.Local;
                }
                if (_local == null) throw new NullReferenceException("DiagnosticService is null");
                return _local;
            }
        }static DiagnosticService _local;

        public static void WriteTrace(string text, TraceSeverity severety)
        {
            WriteTrace(text, severety, Category.Default);
        }

        public static void WriteTrace(string text, TraceSeverity severety, Category category)
        {
            Local.WriteTrace(1, Local[category], severety, text);
        }
    }
}
<file_sep>/iManageIntegration/Src/CustomFieldsChooser/ChooseCustomField.cs
﻿using Microsoft.Win32;
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Windows.Forms;
using Workshare.IManage;
using RES = Workshare.Autonomy.Configuration.Properties.Resources;
namespace CustomFieldsChooser
{
    public partial class ChooseCustomField : Form
    {
        //this is an alias for imProfileAttributeID.imProfileCustom13 enum
        private readonly int imProfileCustom13 = 37;
        private readonly int imProfileCustom25 = 49;

        public ChooseCustomField()
        {
            InitializeComponent();
            this.StartPosition = FormStartPosition.CenterScreen;
            this.Shown += new EventHandler(dlg_shown);
        }

        private void dlg_shown(object sender, EventArgs e)
        {
            this.TopMost = true;
            this.checkedListBox1.SelectionMode = this.checkedListBox2.SelectionMode = SelectionMode.One;
            this.checkedListBox1.CheckOnClick = this.checkedListBox2.CheckOnClick = true;

            var checkedcustom = Registering.GetCustomFieldValue();
            if (checkedcustom != null && checkedcustom >= imProfileCustom13 && checkedcustom <= imProfileCustom13 + 3)
                this.checkedListBox1.SetItemChecked(checkedcustom - imProfileCustom13 ?? 0, true);

            var checkedcustomicon = Registering.GetCustomIconFieldValue();
            if (checkedcustomicon != null && checkedcustomicon >= imProfileCustom25 && checkedcustomicon <= imProfileCustom25 + 2)
                this.checkedListBox2.SetItemChecked(checkedcustomicon - imProfileCustom25 ?? 0, true);
        }

        private void button1_Click(object sender, EventArgs e)
        {
            SafeRegistryOperation(() =>
                {
                    int checkedCustom = -1, checkedCustomIcon = -1;

                    for (int ix = 0; ix < checkedListBox1.Items.Count; ++ix)
                    {
                        if (checkedListBox1.GetItemChecked(ix))
                        {
                            checkedCustom = ix + imProfileCustom13;
                            break;
                        }
                    }
                    if (checkedCustom != -1)
                        Registering.SetCustomFieldValue(checkedCustom);
                    else
                        Registering.RemoveCustomFieldValues();

                    for (int ix = 0; ix < checkedListBox2.Items.Count; ++ix)
                    {
                        if (checkedListBox2.GetItemChecked(ix))
                        {
                            checkedCustomIcon = ix + imProfileCustom25;
                            break;
                        }
                    }
                    if (checkedCustomIcon != -1)
                        Registering.SetCustomIconFieldValue(checkedCustomIcon);
                    else
                        Registering.RemoveCustomIconFieldValues();

                    this.Close();
                });
        }

        private void checkedListBox1_ItemCheck(object sender, ItemCheckEventArgs e)
        {
            if (e.NewValue == CheckState.Checked)
            {
                for (int ix = 0; ix < checkedListBox1.Items.Count; ++ix)
                {
                    if (e.Index != ix)
                    {
                        checkedListBox1.SetItemChecked(ix, false);
                    }
                }
            }
        }

        private void checkedListBox2_ItemCheck(object sender, ItemCheckEventArgs e)
        {
            if (e.NewValue == CheckState.Checked)
            {
                for (int ix = 0; ix < checkedListBox2.Items.Count; ++ix)
                {
                    if (e.Index != ix)
                    {
                        checkedListBox2.SetItemChecked(ix, false);
                    }
                }
            }
        }

        private void button2_Click(object sender, EventArgs e)
        {
            this.Close();
        }

        void SafeRegistryOperation(Action action)
        {
            try
            {
                action();
            }
            catch (Exception ex)
            {
                if (ex is System.UnauthorizedAccessException || ex is System.Security.SecurityException)
                {
                    MessageBox.Show(RES.STR_CANNOT_RIGHT_WRITE_REGISTRY,RES.STR_ERROR_DLG_TITLE);
                }
                else
                {
                    throw;
                }

            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/DocumentAction.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Enums;
using Workshare.Integration.Processor.Changes;

namespace Workshare.Integration.Processor
{
    public abstract class ItemMapActivityAction
    {
        public ItemMapActivityAction(string id)
        {
            ActivityId = id;
            Actions = new List<ItemMapActivityAction>();
            this.Title = GetType().Name;
        }

        public ItemMapActivityAction(ItemMapActivity activity)
        {
            Activity = activity;
            ActivityId = activity.Id;
            Actions = new List<ItemMapActivityAction>();
            this.Title = GetType().Name;
        }

        public ItemMapActivity Activity { get; set; }
        //for now must be same as ItemMapActivity.Id
        public string ActivityId { set; get; }
        public abstract ActionType Type { get; }

        public virtual string Title { get; set; }

        public List<ItemMapActivityAction> Actions { set; get; }

        public void AddAction(ItemMapActivityAction action)
        {
            if (!this.Actions.Contains(action))
            {
                this.Actions.Add(action);
            }
        }

        public void AddAction(IEnumerable<ItemMapActivityAction> actions)
        {
            foreach (var action in actions)
            {
                this.Actions.Add(action);
            }
        }
    }

    public class ItemMapActivityActionGroup : ItemMapActivityAction
    {
        public ItemMapActivityActionGroup(string title)
            : base("")
        {
            this.Title = title;
        }

        public override ActionType Type
        {
            get { return ActionType.None; }
        }
    }

    public class ImportDocumentAction : ItemMapActivityAction
    {
        public ImportDocumentAction(ItemMapActivity activity, string title, ConflictVersionOptions a, ImportType b)
            : base(activity)
        {
            this.Title = title;
            this.ImportType = b;
            this.ImportVersionsAction = a;
        }

        public override ActionType Type { get { return ActionType.Import; } }
        public ImportType ImportType { set; get; }
        public ConflictVersionOptions ImportVersionsAction { set; get; }
        public bool ImportBreakLink { set; get; }
    }

    public class UploadDocumentAction : ItemMapActivityAction
    {
        public UploadDocumentAction(ItemMapActivity activity, string title)
            : base(activity)
        {
            this.Title = title;
            this.VersionIds = new List<string>();
        }

        public override ActionType Type { get { return ActionType.Upload; } }

        public UploadType UploadType { set; get; }

        public List<string> VersionIds { get; private set; }
    }

    public class CeaseCollaborationAction : ItemMapActivityAction
    {
        public CeaseCollaborationAction(string documentChangeId, CeaseCollaborationType fileAction, CeaseCollaborationImportType importAction)
            : base(documentChangeId)
        {
            FileAction = fileAction;
            ImportAction = importAction;
        }
        public override ActionType Type { get { return ActionType.CeaseCollaboration; } }

        public CeaseCollaborationImportType ImportAction { get; private set; }
        public CeaseCollaborationType FileAction { get; private set; }
    }

    public enum ActionType { None, Import, Upload, CeaseCollaboration }
    public enum ImportType { None, AsNewVersion, AsNewDocument, AsRelatedDocument }
    public enum UploadType { None, SpecificVersions }
    public enum CeaseCollaborationImportType { None, WithComments, WithoutComments }
    public enum CeaseCollaborationType { Delete, Skip }
    public enum CeaseCollaborationCloseSpaceError { None, RemoteDeleted, CheckOutToOtherUser, CheckOutFileNotFound, NoAccessToDeleteOnWS, NoAccessToDownloadFileFromWS }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Processor.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.DmsItems.Visitors;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Maps.Visitors;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Integration.Processor
{
    public class Processor
    {
        readonly ModuleBase _module;
        private readonly DmsWorkerBase _dmsWorker;
        private readonly TreePathFinder _treePathFinder;

        public Processor(ModuleBase module, DmsWorkerBase dmsWorker, TreePathFinder treePathFinder)
        {
            _module = module;
            _dmsWorker = dmsWorker;
            _treePathFinder = treePathFinder;
        }

        public SummaryProcessResult Scan(List<BaseDMSItem> items, ScanOptions options)
        {
            return ScanFirstPage((BaseDMSFolder)items.First(), options, null);
        }

        public SummaryProcessResult ScanFirstPage(BaseDMSFolder folder, ScanOptions options, IItemsDetector detector)
        {
            return InternalScanNextPage(folder, options, new SummaryProcessResult(), detector);
        }

        public SummaryProcessResult ScanNextPage(BaseDMSFolder folder, ScanOptions options,
            SummaryProcessResult previousScan)
        {
            if (previousScan == null) throw new ArgumentNullException("previousScan");
            return InternalScanNextPage(folder, options, previousScan, null);
        }

        private SummaryProcessResult InternalScanNextPage(BaseDMSFolder folder, ScanOptions options, SummaryProcessResult scanResultToProceed, IItemsDetector detector)
        {
            Logger.WriteTrace(string.Format("ScanNextPage"));
            scanResultToProceed = scanResultToProceed ?? new SummaryProcessResult();
            options = options ?? new ScanOptions() { UseForceRequest = true };
            var visitor = _module.Resolve<ScanVisitor>();
            visitor.Initialize(scanResultToProceed);
            visitor.Options = options;
            try
            {
                var iterator = scanResultToProceed.Iterator;
                iterator = iterator ?? new PageIterator(options.ItemsPerPage, visitor, folder, detector);
                scanResultToProceed.Iterator = iterator;
                iterator.VisitNextPage();
                if (options.Cancellation.IsCancelled)
                {
                    visitor.Result.ProcessState = ProcessState.Cancelled;
                }
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                visitor.Result.ProcessState = ProcessState.Error;
                visitor.Result.Error = ex;
            }
            return visitor.Result;
        }

        public SummaryProcessResult DirectScanFile(IEnumerable<BaseDMSFile> files)
        {
            Logger.WriteTrace("DirectScanFile");
            SummaryProcessResult scanResultToProceed = new SummaryProcessResult();
            ScanOptions options = new ScanOptions() { UseForceRequest = true };
            var visitor = _module.Resolve<ScanVisitor>();
            visitor.Initialize(scanResultToProceed);
            visitor.Options = options;

            try
            {
                foreach (var file in files)
                {
                    var iterator = new PageIterator(int.MaxValue, visitor, file, null);
                    iterator.VisitNextPage();                   
                }

                if (options.Cancellation.IsCancelled)
                {
                    visitor.Result.ProcessState = ProcessState.Cancelled;
                }
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                visitor.Result.ProcessState = ProcessState.Error;
                visitor.Result.Error = ex;
            }
            return visitor.Result;
        }

        public IEnumerable<SummaryProcessResult> ScanFile(BaseDMSFile item, ScanOptions options)
        {
            Logger.WriteTrace(string.Format("ScanFile"));
            var results = new List<SummaryProcessResult>();
            var parents = _dmsWorker.GetParents(item).ToList();

            if (parents.Any())
            {
                foreach (var parent in parents)
                {
                    var bottomLevelFolder = new SingleChildDMSFolder((BaseDMSFolder)parent) { File = item };
                    _treePathFinder.FindPath((BaseDMSFolder)parent, bottomLevelFolder);
                    var topLevelFolder = _treePathFinder.Reverse(bottomLevelFolder);

                    var result = Scan(new List<BaseDMSItem> { topLevelFolder }, options);
                    results.Add(result);
                }
            }
            else
            {
                var result = Scan(new List<BaseDMSItem> { item }, options);
                results.Add(result);
            }

            return results;
        }

        public SummaryProcessResult Process(SummaryProcessResult scanResult, ProcessOptions options)
        {
            Logger.WriteTrace(string.Format("Process"));
            var processVisitor = _module.Resolve<ProcessVisitor>();
            processVisitor.Initialize(options);
            try
            {
                scanResult.Apply(processVisitor);
            }
            catch (Exception ex)
            {
                scanResult.ProcessState = ProcessState.Error;
                scanResult.Error = ex;
            }
            return scanResult;
        }

        public void BreakLink(ItemMap root)
        {
            Logger.WriteTrace(string.Format("BreakLink"));
            var visitor = _module.Resolve<BreakLinkVisitor>();
            root.Apply(visitor);
        }
    }

    public class ProcessOptions
    {
        public ProcessOptions()
            : this(new OwnCancellationTokenSource())
        {
        }

        public ProcessOptions(OwnCancellationTokenSource cancellation)
        {
            this.ActionsToApply = new List<ItemMapActivityAction>();
            this.Cancellation = cancellation;
        }

        public OwnCancellationTokenSource Cancellation
        {
            private set;
            get;
        }

        public List<ItemMapActivityAction> ActionsToApply { private set; get; }
    }

    public class ScanOptions
    {
        public ScanOptions()
            : this(new OwnCancellationTokenSource())
        {
            ItemsPerPage = int.MaxValue;
        }

        public ScanOptions(OwnCancellationTokenSource cancellation)
        {
            this.Cancellation = cancellation;
            this.ItemsPerPage = int.MaxValue;
            UseForceRequest = true;
        }

        public OwnCancellationTokenSource Cancellation
        {
            private set;
            get;
        }

        public int ItemsPerPage { get; set; }

        public bool UseForceRequest { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/ErrorsWindow/ErrorsViewModel.cs
﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Linq;
using System.Windows.Input;
using Workshare.Components.Views.Common;
using Workshare.Integration.Common;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using WorksharePlatform;
using Permissions = Workshare.Integration.Enums.Permissions;


namespace Workshare.Components.Views.ErrorsWindow
{
    class ErrorsViewModel : OwnViewModel
    {
        readonly BindingList<ItemErrorViewModel> _errors = new BindingList<ItemErrorViewModel>();
        public BindingList<ItemErrorViewModel> Errors { get { return _errors; } }
        public ErrorsViewModel()
        {
            Errors.Add(new ItemErrorViewModel(new FakeFile
            {
                DisplayName = "asdasdasd.docx"
            }, 
            new BaseException("Caption1","TestError1")));

            Errors.Add(new ItemErrorViewModel(new FakeFile
            {
                DisplayName = "asdasdasd.docx"
            }, 
            new BaseException("Caption1", "TestError1")));

            Errors.Add(new ItemErrorViewModel(new FakeFile
            {
                DisplayName = "asdasdasd.docx"
            }, 
            new BaseException("Caption1", "long error long error long error  long error  long error long error long error long error long error long error long error")));
        }

        public ErrorsViewModel(IEnumerable<ItemException> errors)
        {
            if (errors != null)
            {
                errors.ToList().ForEach(p => Errors.Add(new ItemErrorViewModel(p.Item, p.Error)));
            }

            CloseCommand = new RelayCommand(p => RaiseClose(false));
        }

        public ICommand CloseCommand { set; get; }

        
    }

    public class ItemErrorViewModel
    {
        public IDMSItem Item { private set; get; }
        public Exception Error { private set; get; }
        public ItemErrorViewModel(IDMSItem item, Exception error)
        {
            Item = item;
            Error = error;
        }
    }

    #region Fakes
    class FakeFile : IDMSFile
    {
        public string GetFilePath()
        {
            throw new NotImplementedException();
        }

        public DateTime Modified
        {
            get { throw new NotImplementedException(); }
        }

        public bool IsCheckedOutFileExists()
        {
            throw new NotImplementedException();
        }

        public List<IDMSFolder> ParentFolders
        {
            get { throw new NotImplementedException(); }
        }

        public IDMSFile GetLatest()
        {
            throw new NotImplementedException();
        }

        public void DiscardCheckout(bool deleteCheckOutFile = false)
        {
            throw new NotImplementedException();
        }

        public IEnumerable<IDmsVersion> GetVersions()
        {
            throw new NotImplementedException();
        }

        public IDmsVersion AddVersion(string filePath, FileDetails file, List<Activity> activities, string versionFriendlyName = null, bool checkInVersion = false, bool keepLocalState = false)
        {
            throw new NotImplementedException();
        }

        public IDMSItemID ID
        {
            get { throw new NotImplementedException(); }
        }

        public int DMSId
        {
            get { throw new NotImplementedException(); }
        }

        public string Name
        {
            get;
            set;
        }

        public bool DoesUserHavePermissions(Permissions permissions)
        {
            throw new NotImplementedException();
        }

        public bool CheckedOutToUser
        {
            get { throw new NotImplementedException(); }
        }

        public bool CheckedOut
        {
            get { throw new NotImplementedException(); }
        }

        public string DisplayName
        {
            get;
            set;
        }

        public IDMSFolder ParentFolder
        {
            get { throw new NotImplementedException(); }
        }

        public bool WasUpdatedAfterSend2(bool useForceRequest = true)
        {
            throw new NotImplementedException();
        }

        public void OnBeforeSending(OperationContext context)
        {
            throw new NotImplementedException();
        }

        public void OnAfterSending(OperationContext context)
        {
            throw new NotImplementedException();
        }

        public void OnSendError(object args, Exception e)
        {
            throw new NotImplementedException();
        }

        public void AddHistory(string eventName, string eventComment, Integration.Operations operation)
        {
            throw new NotImplementedException();
        }

        public void AddHistories(List<Activity> activities)
        {
            throw new NotImplementedException();
        }

        public IDMSFolder RootFolder()
        {
            throw new NotImplementedException();
        }


        public string DMSItemKey
        {
            get { throw new NotImplementedException(); }
        }
    }


    class FakeFolder : IDMSFolder
    {

        public IDMSFolder AddSubFolder(FolderDetails cloudFolder)
        {
            throw new NotImplementedException();
        }

        public IEnumerable<IDMSFolder> SubFolders
        {
            get;
            set;
        }

        public IEnumerable<IDMSFile> Files
        {
            get;
            set;
        }

        public bool IsDeleted
        {
            get { throw new NotImplementedException(); }
        }

        public IDMSItemID ID
        {
            get { throw new NotImplementedException(); }
        }

        public int DMSId
        {
            get { throw new NotImplementedException(); }
        }

        public string Name
        {
            get;
            set;
        }

        public bool DoesUserHavePermissions(Permissions permissions)
        {
            throw new NotImplementedException();
        }

        public bool CheckedOutToUser
        {
            get { throw new NotImplementedException(); }
        }

        public bool CheckedOut
        {
            get { throw new NotImplementedException(); }
        }

        public string DisplayName
        {
            get;
            set;
        }

        public IDMSFolder ParentFolder
        {
            get { throw new NotImplementedException(); }
        }

        public bool WasUpdatedAfterSend2(bool useForceRequest = true)
        {
            throw new NotImplementedException();
        }

        public void OnBeforeSending(OperationContext context)
        {
            throw new NotImplementedException();
        }

        public void OnAfterSending(OperationContext context)
        {
            throw new NotImplementedException();
        }

        public void OnSendError(object args, Exception e)
        {
            throw new NotImplementedException();
        }

        public void AddHistory(string eventName, string eventComment, Integration.Operations operation)
        {
            throw new NotImplementedException();
        }

        public void AddHistories(List<Activity> activities)
        {
            throw new NotImplementedException();
        }

        public IDMSFolder RootFolder()
        {
            throw new NotImplementedException();
        }


        public string DMSItemKey
        {
            get { throw new NotImplementedException(); }
        }
    }
    #endregion
}
<file_sep>/WSComponents/src/WSComponents/Presenter/ModulePresenterBase.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Threading;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Exceptions;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.WsProxies;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;


namespace Workshare.Components.Presenter
{
    public abstract class ModulePresenterBase : IModulePresenter
    {
        protected readonly CommandInvoker invoker;
        private readonly IModuleView _view;
        readonly WsProxy _wsProxy;

        protected ModulePresenterBase(IModuleView view)
        {
            _view = view;
            invoker = new CommandInvoker();
            _wsProxy = new WsProxy();
            ShowProgress();
        }

        public void ShowProgress()
        {
            var threadApartment = Thread.CurrentThread.GetApartmentState();
            if (threadApartment != ApartmentState.STA)
            {
                Logger.WriteWarning("Startin ProgressWindow is separate thread");
                var newWindowThread = new Thread(() =>
                {
                    _view.ShowProgressWindow(invoker);
                    System.Windows.Threading.Dispatcher.Run();
                });
                newWindowThread.SetApartmentState(ApartmentState.STA);
                newWindowThread.IsBackground = true;
                newWindowThread.Start();
            }
            else
            {
                Logger.WriteWarning("Startin ProgressWindow is current thread");
                _view.ShowProgressWindow(invoker);
            }
        }

        private DialogSettings _currentDialogSettings;
        public DialogSettings GetCurrentDialogSettings(UserDetails user)
        {
            if (_currentDialogSettings == null)
            {
                _currentDialogSettings = GetDialogSettingsFromWorkshare(user);
            }
            return _currentDialogSettings;
        }

        public virtual bool IsAnyItemInProgress()
        {
            return invoker.GetAllWorks().Any();
        }

        public virtual void OnCollaborationItemsClicked(CollaborationItemsClickedArgs args)
        {
            InvokeInSTAThreadIfNeed(() =>
            {
                if (LoginIfNeeded())
                {
                    CollaborationItems(args.Items);
                }
            });
        }

        private void CollaborationItems(IEnumerable<CollaborationItemInformation> items)
        {
            var dmsItems = items.Select(p => p.item);
            var dlg = new Views.CeaseCollaborationDialog.CeaseCollaborationDialog(WSApplication.Instance.Module, invoker, dmsItems, _view);
            new System.Windows.Interop.WindowInteropHelper(dlg).Owner = _view.ActivieWindowHandle;
            dlg.ShowDialog();
        }

        public virtual WorkUnit GetSendCommand(IEnumerable<IDMSItem> items, IEnumerable<FileMapActivity> itemsToSkip, int destFolderId, CheckOutOptions option)
        {
            var res = new SendWorkUnit(_view, items, destFolderId, option);
            res.OnError += res_OnError;
            return res;
        }

        protected CheckOutOptions ShowCheckOutDialogIfNeed(SendItemsClickedArgs args)
        {
            return _view.ShowCheckOutDialogIfNeed(args);
        }

        public virtual void OnSendItemsClicked(SendItemsClickedArgs args)
        {
            InvokeInSTAThreadIfNeed(() =>
            {
                bool repeat = true;
                while (repeat)
                {
                    if (LoginIfNeeded())
                    {

                        var res = _view.ShowSelectFolder(GetCurrentDialogSettings(WSApplication.Instance.AuthProvider.GetCurrentWSUser()));
                        if (res > -1)
                        {
                            invoker.AddToQueue(GetSendCommand(args.Items, new List<FileMapActivity>(), res, CheckOutOptions.CheckOut));
                            repeat = false;
                        }
                        else if (res == -1)
                        {
                            repeat = false;
                        }
                        else if (res == -10) // we lost auth credentials
                        {
                            var user = WSApplication.Instance.AuthProvider.GetCurrentWSUser();
                            if (user != null)
                            {
                                user.AuthToken = string.Empty;
                                user.SessionCookies = null;
                            }
                        }
                    }
                    else
                    {
                        repeat = false;
                    }
                }
            });

        }

        public abstract void OnSyncItemsClicked(SyncItemsClickedArgs args);

        private void res_OnError(object sender, WorkUnitErrorEventArgs e)
        {
            var error = e.Error as MultiItemsException;
            if (error != null)
            {
                e.Handled = true;
                var multi = error;
                var errors = multi.errorList.AsQueryble().ToList();
                if (errors.Any())
                {
                    _view.ShowErrors(errors);
                }
            }
        }

        public virtual bool LoginIfNeeded()
        {
            try
            {
                var user = WSApplication.Instance.AuthProvider.GetCurrentWSUser();
                if (!WorkshareCloud.ServiceProxy.ProxyHelper.ProxyDetector.CheckForProxy(user, _view.ActivieWindowHandle))
                {
                    return false;
                }
                if (user != null)
                {
                    if (!string.IsNullOrEmpty(user.AccountUuId))
                    {
                        return true;
                    }

                    if (_wsProxy.IsUserLoggedIn(user))
                    {
                        return true;
                    }
                }

                var res = _view.ShowLogin(out user, GetCurrentDialogSettings(user));

                if (res)
                {
                    WSApplication.Instance.AuthProvider.SetCurrentUser(user);
                }
                return res;
            }
            catch (WebException ex)
            {
                if (ex.Status == WebExceptionStatus.Timeout)
                {
                    var exceptions = new List<ItemException>()
                    {
                        new ItemException() { Error = new OfflineException(RES.STR_CONNECTION_ERROR_TEXT_TIMEOUT, ex.InnerException) }
                    };

                    WSApplication.Instance.View.ShowErrors(exceptions);
                }

                return false;
            }
        }

        #region public common methods

        public static void InvokeInSTAThreadIfNeed(Action act)
        {
            if (Thread.CurrentThread.GetApartmentState() == ApartmentState.STA)
            {
                act();
            }
            else
            {
                Exception threadEx = null;
                var thread = new Thread((a) =>
                {
                    try
                    {
                        act();
                    }
                    catch (Exception ex)
                    {
                        threadEx = ex;
                    }
                });

                thread.SetApartmentState(ApartmentState.STA);
                thread.Start();
                while (thread.IsAlive)
                {
                    Thread.Sleep(1);
                    System.Windows.Forms.Application.DoEvents();
                }
                if (threadEx != null)
                {
                    throw threadEx;
                }
            }
        }

        #endregion

        #region internal region


        protected readonly DialogSettings DefaultDialogSettings = new DialogSettings()
        {
            dialog_create_folder_height = 514,
            dialog_create_folder_width = 596,
            dialog_select_folder_height = 514,
            dialog_select_folder_width = 596,
            dialog_login_height = 728,
            dialog_login_width = 1026
        };

        DialogSettings GetDialogSettingsFromWorkshare(UserDetails user)
        {
            try
            {
                return PlatformService.GetDialogSettings(user);
            }
            catch (Exception ex)
            {
                Logger.Write("Cannot load setting for dilogs. Will be used default.", ex, Severity.Error);
                return DefaultDialogSettings;
            }
        }
        #endregion

    }
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/Enums/ConflictOptions.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WorkshareCloud.Common.Enums
{
    public enum ConflictOptions
    {
        None = 0,
        Replace = 1, 
        KeepBoth = 2,
        UpdateOnTheWorkshare = 3
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CeaseCollaborationDialog/CeaseCollaborationDialogViewModel.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Reflection;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Threading;
using Workshare.Components.Concrete;
using Workshare.Components.Helpers;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.CeaseCollaborationDialog.WorkUnits;
using Workshare.Components.Views.Common;
using Workshare.Components.Views;
using Workshare.Components.Views.Progress.VMs;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using RES_INT = Workshare.Integration.Properties.Resources;
using RES_CMP = Workshare.Components.Properties.Resources;

namespace Workshare.Components.Views.CeaseCollaborationDialog
{
    public class CeaseCollaborationDialogViewModel : OwnViewModel<CeaseCollaborationDialogViewModel>
    {
        const string LastPart = "been uploaded and shared on Workshare.\nPlease select your options from the menus and confirm your choice.";
        readonly Dispatcher _dispatcher;

        public ModuleBase Module { get; set; }
        private readonly SyncInfoService _syncInfoService;

        internal SummaryProcessResult ScanResult;
        internal Dictionary<CeaseCollaborationCloseSpaceError, List<FileMap>> CeaseCollaborationCloseSpaceErrorFiles = new Dictionary<CeaseCollaborationCloseSpaceError, List<FileMap>>();

        private CeaseCollaborationDialog _dialog;
        private System.Threading.Thread _scanThread;

        private List<IDMSItem> _items;

        private StateEnum _state;
        public StateEnum State
        {
            get { return _state; }
            set
            {
                if (_state != value)
                {
                    _state = value;
                    PropertyHasChanged(p => p.State);
                }
            }
        }

        public CeaseCollaborationImportType ImportAction { get; private set; }
        public CeaseCollaborationType FileAction { get; private set; }

        public CeaseCollaborationDialogViewModel()
        {
            ConfirmCommand = CancelCommand = new RelayCommand((p) => { RaiseClose(false); });
            _dialogDesc = "The document {DocumentName} has " + LastPart;
        }

        public CeaseCollaborationDialogViewModel(ModuleBase module, CommandInvoker invoker, IEnumerable<IDMSItem> items, CeaseCollaborationDialog dialog, IModuleView view)
        {
            if (items == null || items.Count() == 0) throw new ArgumentException("The parameter cannot be null or empty", "items");

            _dispatcher = Dispatcher.CurrentDispatcher;
            Module = module;
            _syncInfoService = module.Resolve<SyncInfoService>();
            _items = items.ToList();
            _dialog = dialog;

            ConfirmCommand = new RelayCommand((p) =>
            {
                ImportAction = (CeaseCollaborationImportType)_dialog.Tag;
                FileAction = _dialog.chkFileActionBox.IsChecked == true ? CeaseCollaborationType.Delete : CeaseCollaborationType.Skip;

                List<ItemException> itemExceptions = new List<ItemException>();

                CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.CheckOutToOtherUser].ForEach(i =>
                    {
                        itemExceptions.Add(new ItemException() { Item = i.LocalFile, Error = new BaseException(RES_CMP.STR_UNABLE_TO_CLOSE_COLLABORATION_SPACE, RES_CMP.STR_ExecuteAction_File_is_checked_out_to_another_users) });
                    });

                CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.CheckOutFileNotFound].ForEach(i =>
                    {
                        itemExceptions.Add(new ItemException() { Item = i.LocalFile, Error = new BaseException(RES_CMP.STR_UNABLE_TO_CLOSE_COLLABORATION_SPACE, RES_INT.STR_LOCALFILENOTFOUND_WITHFILENAME_TEXT) });
                    });

                if (FileAction == CeaseCollaborationType.Delete && CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS].Count > 0)
                {
                    int countFilesOnWS = CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.None].Count;
                    int NoAccessToDeleteOnWSCount = countFilesOnWS - CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS].Count;
                    itemExceptions.Add(new ItemException() { Item = null, Error = new BaseException(RES_CMP.STR_UNABLE_TO_CLOSE_COLLABORATION_SPACE, string.Format(RES_CMP.STR_NO_PRIVILEGE_TO_DELETE_FILES_FROM_WS, NoAccessToDeleteOnWSCount, countFilesOnWS)) });
                }

                if (ImportAction != CeaseCollaborationImportType.None && CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS].Count > 0)
                {
                    int countFilesOnWS = CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.None].Count;
                    int NoAccessToDownloadFileFromWSCount = countFilesOnWS - CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS].Count;
                    itemExceptions.Add(new ItemException() { Item = null, Error = new BaseException(RES_CMP.STR_UNABLE_TO_CLOSE_COLLABORATION_SPACE, string.Format(RES_CMP.STR_NO_PRIVILEGE_TO_DOWNLOAD_FILES_FROM_WS, NoAccessToDownloadFileFromWSCount, countFilesOnWS)) });
                }

                if (itemExceptions.Count != 0)
                    view.ShowErrors(itemExceptions);

                bool canConfirm = itemExceptions.Count == 0;

                if (canConfirm)
                {
                    var unit = new ProcessWorkUnit(view, _items, this);
                    invoker.AddToQueue(unit);
                }

                RaiseClose(true);
            });

            ScanCommand = new RelayCommand((p) =>
                {
                    var unit = new ScanWorkUnit(view, _items, this, _scanThread);
                    invoker.AddToQueue(unit);
                });

            BreakLinkCommand = new RelayCommand((p) =>
                {
                    var breakWorkUnit = new BreakWorkUnit(this, view);
                    breakWorkUnit.Execute();
                    RaiseClose(false);
                });

            CancelCommand = new RelayCommand((p) => { RaiseClose(false); });

            if (_items.Count() > 1)
            {
                _dialogDesc = string.Format("The {0} selected documents have " + LastPart, _items.Count());
            }
            else if (_items.Count() == 1)
            {
                IDMSItem item = _items.First();
                if (item is IDMSFile) _dialogDesc = string.Format("The document \"{0}\" has " + LastPart, item.Name);
                else if (item is IDMSFolder) _dialogDesc = string.Format("The folder \"{0}\" has " + LastPart, item.Name);
            }
        }

        private List<FileMap> GetCeaseCollaborationCloseSpaceErrorFiles(IEnumerable<ItemMap> maps, CeaseCollaborationCloseSpaceError error)
        {
            List<FileMap> ret = new List<FileMap>();

            if (maps != null)
            {
                if (maps.OfType<FileMap>().Count() > 0)
                {
                    if (error == CeaseCollaborationCloseSpaceError.RemoteDeleted)
                    {
                        maps.OfType<FileMap>().Where(i => !i.HasRemote() && _syncInfoService.IsLinked(i.LocalFile, false)).ToList().ForEach(j => ret.Add(j));
                    }
                    else if (error == CeaseCollaborationCloseSpaceError.CheckOutToOtherUser)
                    {
                        maps.OfType<FileMap>().Where(i => i.LocalFile != null && i.LocalFile.IsCheckedOutToOtherUser()).ToList().ForEach(j => ret.Add(j));
                    }
                    else if (error == CeaseCollaborationCloseSpaceError.CheckOutFileNotFound)
                    {
                        maps.OfType<FileMap>().Where(i => i.LocalFile != null && i.LocalFile.CheckedOut && !i.LocalFile.IsCheckedOutFileExists()).ToList().ForEach(j => ret.Add(j));
                    }
                    else if (error == CeaseCollaborationCloseSpaceError.None)
                    {
                        maps.OfType<FileMap>().Where(i => i.HasRemote()).ToList().ForEach(j => ret.Add(j));
                    }
                }

                if (maps.OfType<FolderMap>().Count() > 0)
                {
                    if (error == CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS || error == CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS)
                    {
                        maps.OfType<FolderMap>().ToList().ForEach(i =>
                        {
                            if (error == CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS || error == CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS)
                            {
                                bool canAddMap = false;

                                if (error == CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS && i.WsFolder != null && i.WsFolder._folder != null && !i.WsFolder._folder.Permissions.CanAddOrRemoveFiles)
                                    canAddMap = true;
                                else if (error == CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS && i.WsFolder != null && i.WsFolder._folder != null && !i.WsFolder._folder.Permissions.DownloadFiles)
                                    canAddMap = true;

                                if (canAddMap)
                                {
                                    var currUser = Module.Resolve<IAuthProvider>().GetCurrentWSUser2();
                                    if (!i.WsFolder.Owner._user.UserId.Equals(currUser._user.UserId, StringComparison.OrdinalIgnoreCase))
                                        i.Maps.OfType<FileMap>().Where(j => j.HasRemote()).ToList().ForEach(k => ret.Add(k));
                                }

                            }
                            
                            if (i.Maps.Any(j => j is FolderMap))
                                ret.AddRange(GetCeaseCollaborationCloseSpaceErrorFiles(i.Maps, error));
                        });
                    }
                    else
                    {
                        maps.OfType<FolderMap>().ToList().ForEach(i => ret.AddRange(GetCeaseCollaborationCloseSpaceErrorFiles(i.Maps, error)));
                    }
                }
            }

            return ret;
        }

        private void CeaseCollaborationDialogViewModel_OnCompleted_Init(IEnumerable<ItemMap> maps)
        {
            CeaseCollaborationCloseSpaceErrorFiles.Add(CeaseCollaborationCloseSpaceError.None, GetCeaseCollaborationCloseSpaceErrorFiles(maps, CeaseCollaborationCloseSpaceError.None));
            CeaseCollaborationCloseSpaceErrorFiles.Add(CeaseCollaborationCloseSpaceError.RemoteDeleted, GetCeaseCollaborationCloseSpaceErrorFiles(maps, CeaseCollaborationCloseSpaceError.RemoteDeleted));
            CeaseCollaborationCloseSpaceErrorFiles.Add(CeaseCollaborationCloseSpaceError.CheckOutToOtherUser, GetCeaseCollaborationCloseSpaceErrorFiles(maps, CeaseCollaborationCloseSpaceError.CheckOutToOtherUser));
            CeaseCollaborationCloseSpaceErrorFiles.Add(CeaseCollaborationCloseSpaceError.CheckOutFileNotFound, GetCeaseCollaborationCloseSpaceErrorFiles(maps, CeaseCollaborationCloseSpaceError.CheckOutFileNotFound));
            CeaseCollaborationCloseSpaceErrorFiles.Add(CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS, GetCeaseCollaborationCloseSpaceErrorFiles(maps, CeaseCollaborationCloseSpaceError.NoAccessToDeleteOnWS));
            CeaseCollaborationCloseSpaceErrorFiles.Add(CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS, GetCeaseCollaborationCloseSpaceErrorFiles(maps, CeaseCollaborationCloseSpaceError.NoAccessToDownloadFileFromWS));
        }

        public void OnCompleted(List<ItemMap> errors, SummaryProcessResult scanResult)
        {
            ScanResult = scanResult;

            this._dispatcher.Invoke(new Action(() =>
            {
                if (errors.Any(p => p.Error.IsConnectionError()))
                {
                    this.State = StateEnum.NetError;
                }
                else if (ScanResult.Maps.OfType<FolderMap>().Any() && FolderDeletedOnWs())
                {
                    this.State = StateEnum.RootFolderDeleted;
                }
                else if (errors.Any(p => p.Error.IsCloudFolderAccessDenied()))
                {
                    this.State = StateEnum.Forbidden;
                }
                else
                {
                    CeaseCollaborationDialogViewModel_OnCompleted_Init(scanResult.Maps);
                    this.State = StateEnum.Default;
                }
            }));
        }

        public void OnViewClosing()
        {
            if (_scanThread != null) _scanThread.Abort();
        }

        private bool FolderDeletedOnWs()
        {
            var folder = ScanResult.Maps.OfType<FolderMap>();
            return folder.All(f => !f.HasRemote() && f.ProcessState == ProcessState.Scanned);
        }

        public RelayCommand ConfirmCommand { get; set; }
        public RelayCommand CancelCommand { get; set; }
        public RelayCommand ScanCommand { get; set; }
        public RelayCommand BreakLinkCommand { get; set; }

        public string DialogDescription { get { return _dialogDesc; } }
        private string _dialogDesc = "";

        public enum StateEnum { Default, Scanning, NetError, RootFolderDeleted, Forbidden }
    }
}
<file_sep>/WSComponents/src/WSCloudService/Permissions.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WorksharePlatform
{
    public class Permissions
    {
        public int FolderId { get; set; }
        internal Dictionary<string, bool> PermissionSet { get; set; }
        public bool User_must_login
        {
            get 
            {
                if (PermissionSet.ContainsKey("can_access_anonymously"))
                {
                    return !PermissionSet["can_access_anonymously"];
                }
                else
                {
                    return false;
                }
            }
            set 
            {
                if (PermissionSet.ContainsKey("can_access_anonymously"))
                {
                    PermissionSet["can_access_anonymously"] = !value;
                }
                else
                {
                    PermissionSet.Add("can_access_anonymously", !value);
                }
            }
        }

        public bool Member_may_invite
        {
            get
            {
                if (PermissionSet.ContainsKey("can_invite_with_link"))
                {
                    return PermissionSet["can_invite_with_link"];
                }
                else
                {
                    return false;
                }
            }
            set
            {
                if (PermissionSet.ContainsKey("can_invite_with_link"))
                {
                    PermissionSet["can_invite_with_link"] = value;
                }
                else
                {
                    PermissionSet.Add("can_invite_with_link", value);
                }
            }
        }

        public bool CanAddOrRemoveFiles
        {
            get
            {
                if (PermissionSet.ContainsKey("can_manipulate"))
                {
                    return PermissionSet["can_manipulate"];
                }
                else
                {
                    return false;
                }
            }
            set
            {
                if (PermissionSet.ContainsKey("can_manipulate"))
                {
                    PermissionSet["can_manipulate"] = value;
                }
                else
                {
                    PermissionSet.Add("can_manipulate", value);
                }
            }
        }

        public bool CanAddVersions
        {
            get
            {
                if (PermissionSet.ContainsKey("can_upload_changes"))
                {
                    return PermissionSet["can_upload_changes"];
                }
                else
                {
                    return false;
                }
            }
            set
            {
                if (PermissionSet.ContainsKey("can_upload_changes"))
                {
                    PermissionSet["can_upload_changes"] = value;
                }
                else
                {
                    PermissionSet.Add("can_upload_changes", value);
                }
            }
        }

        public bool DownloadFiles
        {
            get
            {
                if (PermissionSet.ContainsKey("can_download_original"))
                {
                    return PermissionSet["can_download_original"];
                }
                else
                {
                    return false;
                }
            }
            set
            {
                if (PermissionSet.ContainsKey("can_download_original"))
                {
                    PermissionSet["can_download_original"] = value;
                }
                else
                {
                    PermissionSet.Add("can_download_original", value);
                }
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CheckOutDialog/CheckOutDialog.xaml.cs
﻿using Workshare.Components.Views.Common;
using Workshare.Integration.Enums;


namespace Workshare.Components.Views.CheckOutDialog
{
    /// <summary>
    /// Interaction logic for CheckOutDialog.xaml
    /// </summary>
    public partial class CheckOutDialog : OwnWindow
    {
        public CheckOutDialog()
        {
            InitializeComponent();
            this.DataContext = new CheckOutDilalogModel();
            btnCheckOut.Focus();
        }

        public string FileName
        {
            set
            {
                var model = this.DataContext as CheckOutDilalogModel;

                if (null != model)
                {
                    model.FileName= value;
                }
            }
        }

        public CheckOutOptions Result
        {
            get
            {
                var model = DataContext as CheckOutDilalogModel;

                if (model != null)
                {
                    return model.Result;
                }
                else
                {
                    return CheckOutOptions.None;
                }
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Progress/ProgressWindow.xaml.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;
using System.Windows;
using System.Windows.Data;
using System.Windows.Input;
using System.Windows.Interop;
using System.Windows.Media;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Views.Common;
using Workshare.Components.WSLogger;
using RES = Workshare.Components.Properties.Resources;
using RES_INT = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Views.Progress
{
    /// <summary>
    /// Interaction logic for ProgressWindow.xaml
    /// </summary>
    partial class ProgressWindow : Window
    {
        private readonly CommandInvoker _invoker;

        public ProgressWindow()
        {
            InitializeComponent();
        }

        public ProgressWindow(CommandInvoker invoker):this()
        {
            _invoker = invoker;
            this.LbItems.MouseDoubleClick += lbItems_MouseDoubleClick;
            this.Loaded += ProgressWindow_Loaded;
            this.Closed += ProgressWindow_Closed;
        }

        void ProgressWindow_Closed(object sender, EventArgs e)
        {
            Logger.WriteTrace("ProgressWindow_Closed");
            var viewModel = this.DataContext as ProgressViewModel;
            viewModel.Dispose();
            WSApplication.Instance.View.ShowProgressWindow(_invoker);
        }

        void ProgressWindow_Loaded(object sender, RoutedEventArgs e)
        {
            Logger.WriteTrace("ProgressWindow_Loaded");
            this.DataContext = new ProgressViewModel(_invoker);
        }

        public void Suppress(bool suppress)
        {
            this.Dispatcher.BeginInvoke(new Action(() =>
                {
                    var viewModel = this.DataContext as ProgressViewModel;
                    if (viewModel != null)
                    {
                        viewModel.Suppress(suppress);
                    }
                }));
        }

        void lbItems_MouseDoubleClick(object sender, MouseButtonEventArgs e)
        {
            var viewModel = this.DataContext as ProgressViewModel;
            if (viewModel != null && viewModel.RemoveItem!= null)
            {
                var a = e.OriginalSource as FrameworkElement;
                viewModel.RemoveItem.Execute(a.DataContext);
            }
        }

        private void Window_Closing(object sender, System.ComponentModel.CancelEventArgs e)
        {
            Logger.WriteTrace("ProgressWindow_Closed");
            var viewModel = this.DataContext as ProgressViewModel;
            if (viewModel != null)
            {
                e.Cancel = true;
                viewModel.ClearCmd.Execute(null);
            }
        }

        int OwnerBorder = 35;
        int OwnerBottomHeight = 45;

        [DllImport("user32.dll")]
        static extern IntPtr GetActiveWindow();

        private void SetPosition()
        {

            var parentWindw = Process.GetCurrentProcess().MainWindowHandle;

            if (parentWindw != IntPtr.Zero)
            {
                RECT rect = new RECT();
                if (GetWindowRect(parentWindw, ref rect))
                {
                    this.Top = rect.Top + OwnerBottomHeight;
                    this.Left = rect.Right - this.ActualWidth - OwnerBorder;
                    return;
                }
            }
            this.Top = OwnerBorder;
            this.Left = SystemParameters.VirtualScreenWidth - this.ActualWidth - OwnerBorder;
        }

        private void Window_SizeChanged_1(object sender, SizeChangedEventArgs e)
        {
            SetPosition();
        }

        [DllImport("user32.dll", SetLastError = true)]
        [return: MarshalAs(UnmanagedType.Bool)]
        static extern bool GetWindowRect(IntPtr hWnd, ref RECT lpRect);
        [StructLayout(LayoutKind.Sequential)]
        private struct RECT
        {
            public int Left;
            public int Top;
            public int Right;
            public int Bottom;
        }
    }

    public class StatusToDMSConverter : IValueConverter
    {
        Dictionary<WorkStatus, ImageSource> cache = new Dictionary<WorkStatus, ImageSource>();
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if (value is WorkStatus)
            {
                var val = (WorkStatus)value;

                if (!cache.ContainsKey(val))
                {
                    System.Drawing.Bitmap img;
                    switch (val)
                    {
                        case WorkStatus.Processing:
                        case WorkStatus.Pending:
                            {
                                img = RES.Synchronize;
                                break;
                            }
                        case WorkStatus.Success:
                            {
                                img = RES.Apply;
                                break;
                            }
                        default:
                            {
                                img = RES.Error;
                                break;
                            }
                    }
                    var bitmap = Utils.Convert(img,ImageFormat.Png);
                    cache[val] = bitmap;
                }
                return cache[val];
            }
            return null;
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
    public class StatusToTextConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if (value is WorkStatus)
            {
                switch ((WorkStatus)value)
                {
                    case WorkStatus.Processing:
                    case WorkStatus.Pending:
                        {
                            if (parameter is TrueSynhWorkUnit)
                            {
                                return RES_INT.STR_WORK_STATUS_SYNCHRONIZATION_TEXT;
                            }
                            //else if (parameter is SynhWorkUnit)
                            //{
                            //    return RES_INT.STR_WORK_STATUS_SYNCHRONIZATION_TEXT;
                            //}
                            else if (parameter is SendWorkUnit)
                            {
                                return RES_INT.STR_WORK_STATUS_SENDING_TEXT;
                            }
                            else
                            {
                                return "Processing";
                            }
                        }
                    case WorkStatus.Success:
                        {
                            return RES_INT.STR_WORK_STATUS_FINISHED_TEXT;
                        }
                    case WorkStatus.Error:
                        {
                            return RES_INT.STR_WORK_STATUS_ERROR_TEXT;
                        }
                    default:
                        {
                            break;
                        }
                }
            }
            return null;
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Concrete/eDOCSEventType.cs
﻿namespace Workshare.OpenText.Concrete
{
    enum eDOCSDEventType
    {
        DE_OPEN = 1,
        DE_OPEN_COMPATIBLE = 2,
        DE_LOCK = 3,
        DE_UNLOCK = 4,
        DE_DELETE = 5,
        DE_PRINT = 6,
        DE_PREVIEW = 7,
        DE_SELECT_FOR_EDIT = 8,
        DE_RELEASE_DOC = 9,
        DE_SAVE = 10,
        DE_NEW_VERSION = 11,
        DE_NEW_DOC = 12,
        DE_CHECK_OUT = 13,
        DE_UPLOAD = 14,
        DE_DOWNLOAD = 15,
        DE_LOCK_FOR_EDIT = 16,
        DE_UNLOCK_VERSION = 17,
        DE_ADD_LINK = 18,
        DE_REMOVE_LINK = 19,
        DE_UPDATE_LINK = 20
    }
}
<file_sep>/WSComponents/src/WSIntegration/WsProxies/WsFolder.cs
﻿using System.Collections.Generic;
using System.Linq;
using WorksharePlatform;

namespace Workshare.Integration.WsProxies
{
    public class WsFolder
    {
        //TODO make non-public
        public FolderDetails _folder;
        readonly UserDetails _user;
        public WsFolder(FolderDetails folder, UserDetails user)
        {
            this._folder = folder;
            this._user = user;
        }

        public int Id { get { return _folder.Id; } }

        IEnumerable<WsFile> _files;
        public IEnumerable<WsFile> Files
        {
            get
            {
                if (_files == null)
                {
                    _files = PlatformService.GetFiles(_user, _folder.Id).Select(a => new WsFile(a, _user));
                }
                return _files;
            }
        }

        IEnumerable<WsFolder> _subFolders;
        public IEnumerable<WsFolder> SubFolders
        {
            get
            {
                if (_subFolders == null)
                {
                    _subFolders = PlatformService.GetChildFolders(_user, _folder.Id).Select(a => new WsFolder(a, _user));
                }
                return _subFolders;
            }
        }

        public string Url { get { return _folder.Url; } }

        public WsUser Owner { get { return new WsUser(_folder.Owner); } }


        /// <summary>
        /// retruns members only directly set to current folder - ignores parent folder members
        /// </summary>
        public int MemberCount { get { return _folder.MemberCount; } }

        private IEnumerable<WsMember> _members;


        /// <summary>
        /// returns members including parend folders
        /// </summary>
        public IEnumerable<WsMember> Members
        {
            get
            {
                if (_members == null)
                {
                    _members = PlatformService.GetMembers(_user, this.Id).Select(a => new WsMember(_user, a));
                }
                return _members;
            }
        }

        public string Name {
            get { return _folder.Name; }
        }

        public bool IsDeleted {
            get { return _folder.IsDeleted; }
        }

        public int ParentId {
            get { return _folder.ParentId; }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncUploadFilesDialog/WorkUnits/ScanWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using Workshare.Components.Common;
using Workshare.Components.Views.TrueSyncDialog;
using Workshare.Components.Views.TrueSyncUploadFilesDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.Exceptions;

namespace Workshare.Components.Views.TrueSyncUploadFilesDialog.WorkUnits
{
    public class ScanWorkUnit : WorkUnit
    {
        private readonly TrueSyncFilesScanDialogVm _vm;
        private readonly DmsWorkerBase _dmsWorker;
        private readonly MapController _mapController;

        public ScanWorkUnit(TrueSyncFilesScanDialogVm vm, DmsWorkerBase dmsWorker) : base(vm.View)
        {
            _vm = vm;
            _mapController = vm.Module.Resolve<MapController>();
            _dmsWorker = dmsWorker;
        }

        public override void OnAdded()
        {
            _vm.State = TrueSyncFilesScanDialogVm.StateEnum.Loading;
        }

        public override void Execute()
        {
            try
            {
                var processor = _vm.Module.Resolve<Processor>();
                var scanResults = processor.ScanFile((BaseDMSFile)_vm.File, new ScanOptions() { UseForceRequest = true });

                bool vmShouldRaiseClose = false;
                
                foreach (var result in scanResults)
                {
                    var activities = new List<UploadFileActivity>();
                    var activityFinder = _vm.Module.Resolve<ActivityFinder>();
                    var uploadActivities = activityFinder.GetUploadActivities(result, null);
                    var errors = activityFinder.GetErrors(result);

                    if (errors.Any())
                    {
                        if (errors.First().Error.IsCloudFolderAccessDenied())
                        {
                            _vm.State = TrueSyncFilesScanDialogVm.StateEnum.NoAccessOnWorkshare;
                        }
                        else
                        {
                            _vm.Error = errors.First().Error;
                            _vm.State = TrueSyncFilesScanDialogVm.StateEnum.Error;
                        }
                    }
                    else
                    {
                        var uploadActivity = uploadActivities
                            .FirstOrDefault(a => a.DmsId == _vm.File.ID.ToString()
                                                    && _vm.ActivityToDisplay(a));
                        if (uploadActivity != null)
                        {

                            var folderMap = _mapController.GetFirstParentLinkedWithExistedOnWs(result, uploadActivity.MapId);
                            if (folderMap != null)
                            {
                                var mapAnylizer = _vm.Module.Resolve<MapAnylizer>();
                                var isFolderSharedWithExternal = mapAnylizer.IsFolderSharedWithExternalUsers(folderMap);
                                activities.Add(uploadActivity);

                                var result2 = result;
                                _vm.Dispatcher.Invoke(new Action(() =>
                                {
                                    _vm.ParentScans.Add(new ParentScan
                                    {
                                        Activities =
                                            new ObservableCollection<FileUploadActivityVm>(
                                                activities.Select(a => new FileUploadActivityVm(a))),
                                        Scan = result2
                                    });

                                    _vm.WorkspaceName = mapAnylizer.GetName(folderMap);
                                    _vm.PropertyHasChanged(a => a.WorkspaceName);
                                    _vm.IsSharedExternally = isFolderSharedWithExternal;

                                    if (!isFolderSharedWithExternal)
                                    {
                                        StartAutoUploadingIfNeed();
                                    }

                                    if(vmShouldRaiseClose)
                                        vmShouldRaiseClose = false;

                                    _vm.State = TrueSyncFilesScanDialogVm.StateEnum.Default;
                                }));
                            }
                            else
                            {
                                Logger.WriteWarning("File not in the synced _folder");
                                _vm.State = TrueSyncFilesScanDialogVm.StateEnum.NoInSyncedFolder;
                                vmShouldRaiseClose = true;
                            }
                        }
                        else
                        {
                            Logger.WriteWarning("No items found for uploading of file");
                            _vm.State = TrueSyncFilesScanDialogVm.StateEnum.NoChangesDetected;
                            vmShouldRaiseClose = true;
                        }
                    }
                }

                if (vmShouldRaiseClose)
                    _vm.Dispatcher.Invoke(new Action(() => _vm.RaiseClose(false)));

            }
            catch (Exception ex)
            {
                _vm.View.ShowError(ex);
            }
        }

        void StartAutoUploadingIfNeed()
        {
            if (!_vm.ParentScans.Any() || _vm.ParentScans.Count == 1)
            {
                var parentScan = _vm.ParentScans.First();
                if (parentScan.Activities.Any() && parentScan.Activities.Count == 1)
                {
                    var activity = parentScan.Activities.Single();
                    var action = activity.Actions.FirstOrDefault();
                    if (action != null)
                    {
                        _vm.ExecuteDocumentAction(new[]{action});
                    }
                }
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Exceptions/Exceptions.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Common;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Properties;
using WorksharePlatform;

namespace Workshare.Integration.Exceptions
{
    /// <summary>
    /// workshare is inavailable
    /// </summary>

    public class ItemException
    {
        public IDMSItem Item
        {
            set;
            get;
        }

        public Exception Error
        {
            set;
            get;
        }

        public FileDetails WSItem
        {
            get;
            set;
        }
    }

    public class ItemsErrorsCollection : IDisposable
    {
        readonly List<ItemException> _mErrors = new List<ItemException>();
        readonly OperationContext _context;

        public ItemsErrorsCollection(OperationContext context)
        {
            _context=context;
        }

        public void Add(IDMSItem item, Exception ex)
        {
            _mErrors.Add(new ItemException
            {
                Item = item,
                Error = ex,
                WSItem = null
            });
        }

        public void Add(FileDetails item, Exception ex)
        {
            _mErrors.Add(new ItemException
            {
                WSItem = item,
                Error = ex,
                Item = null
            });
        }

        public void Add(FileDetails wsitem, IDMSItem item, Exception ex)
        {
            _mErrors.Add(new ItemException
            {
                WSItem = wsitem,
                Error = ex,
                Item = item
            });
        }

        public void Clear()
        {
            _mErrors.Clear();
        }

        void Add(ItemException ex)
        {
            _mErrors.Add(ex);
        }

        public void AddRange(ItemsErrorsCollection errors)
        {
            errors.AsQueryble().ToList().ForEach(Add);
        }

        public IQueryable<ItemException> AsQueryble()
        {
            return _mErrors.AsQueryable();
        }

        public int Count
        {
            get
            {
                return _mErrors.Count;
            }
        }

        public void Check()
        {
            if (Count > 0)
            {
                throw new MultiItemsException(this, _context);
            }
        }

        public void Dispose()
        {
            Check();
        }
    }

    public class BaseException : Exception
    {
        protected BaseException()
        { }

        public BaseException(string caption, string msg)
            : base(msg)
        {
            Caption = caption;
        }

        public BaseException(string caption, string msg, Exception ex)
            : base(msg, ex)
        {
            Caption = caption;
        }

        public string Caption { get; private set; }
    }

    public class OfflineException : BaseException
    {
        public OfflineException()
            : base(Resources.STR_CONNECTION_ERROR_CAPTION, Resources.STR_CONNECTION_ERROR_TEXT)
        {
        }
        public OfflineException(Exception inner)
            : base(Resources.STR_CONNECTION_ERROR_CAPTION, Resources.STR_CONNECTION_ERROR_TEXT, inner)
        {
        }

        public OfflineException(string message, Exception inner)
            : base(Resources.STR_CONNECTION_ERROR_CAPTION, message, inner)
        {
        }
    }

    public class CannotGetDataFromServer : BaseException
    {
        public CannotGetDataFromServer()
            : base(Resources.STR_CONNECTION_ERROR_CAPTION, Resources.STR_CONNECTION_ERROR_TEXT)
        {
        }

        public CannotGetDataFromServer(Exception inner)
            : base(Resources.STR_CONNECTION_ERROR_CAPTION, Resources.STR_CONNECTION_ERROR_TEXT, inner)
        {
        }
    }

    /// <summary>
    /// exeptions during processing of items
    /// </summary>
    public class MultiItemsException : BaseException
    {
        public ItemsErrorsCollection errorList;
        public OperationContext OperationContext { get; private set; }
        public MultiItemsException(ItemsErrorsCollection errList, OperationContext operationContext)
            : base(Resources.STR_ERROR_HAPPEN, "")
        {
            errorList = errList;
            OperationContext = operationContext;
        }

        public override string ToString()
        {
            var text = string.Empty;
            errorList.AsQueryble().Where(a => a != null).ToList().ForEach(p => text += ((p.Item==null)?"no item":p.Item.Name) + " : " + ((p.Error != null) ? p.Error.Message : p.GetType().Name) + Environment.NewLine + p.Error.StackTrace + Environment.NewLine);
            return text;
        }
    }

    public class LocalFileNotFound : BaseException
    {
        public LocalFileNotFound()
            : base(Resources.STR_LOCALFILENOTFOUND_CAPTION, Resources.STR_LOCALFILENOTFOUND_TEXT)
        {
        }
    }

    public class CheckedOutOnAnotherMachine : Exception
    {
        public string MachineName { set; get; }

        public CheckedOutOnAnotherMachine(string machineName)
        {
            this.MachineName = machineName;
        }
    }

    public class LockedByAnotherProcessException : BaseException
    {
        public LockedByAnotherProcessException(string filename)
            : base(
                string.IsNullOrEmpty(filename) ? Resources.STR_ERROR_CAPTION_File_is_locked : string.Format(Resources.STR_ERROR_CAPTION_File___0___is_locked_, filename),
                Resources.STR_ERROR_TEXT_File_is_currently_opened_in_the_another_application)
        {
        }
    }

    public class CloudFileNotFound : CloudItemNotFound
    {
        public CloudFileNotFound(string operation_message)
            : base(operation_message, Resources.STR_CLOUDFILENOTFOUND)
        { }
    }

    public class CloudItemNotFound : BaseException
    {
        protected CloudItemNotFound(string operationMessage, string message)
            : base(operationMessage, message)
        {
        }
    }

    public class CloudFolderNotFound : CloudItemNotFound
    {
        public CloudFolderNotFound(string operationMessage)
            : base(operationMessage, Resources.STR_CLOUDFOLDERNOTFOUND)
        { }
    }

    public class DMSItemNotFound : BaseException
    {
        public DMSItemNotFound(string caption, string name)
            : base(caption, name)
        { }
    }

    /// <summary>
    /// not enough permissions
    /// </summary>
    public class CloudFolderAccessDenied : BaseException
    {
        public CloudFolderAccessDenied(string caption, string text, Exception ex)
            : base(caption, text, ex)
        { }
    }

    public class FileAlreadySentException : BaseException
    {
        public FileAlreadySentException()
            : base(Resources.STR_UNABLE_SEND, Resources.STR_FILE_ALREADY_SENT)
        {
        }
    }

    public class FolderAlreadySentException : BaseException
    {
        public FolderAlreadySentException()
            : base(Resources.STR_UNABLE_SEND, Resources.STR_FOLDER_ALREADY_SENT)
        {
        }
    }

    public class FileCheckoutedToAnotherUser : BaseException
    {
        public FileCheckoutedToAnotherUser(Operations oper, string userName = "")
            : base((oper == Operations.Send) ? Resources.STR_UNABLE_SEND : Resources.STR_UNABLE_SYNC,
            (oper == Operations.Send) ? Resources.STR_FILEISCHECKEDOUTBYANOTHERUSER_TEXT : Resources.STR_FILEISCHECKEDOUTBYANOTHERUSER_TEXT_SYNC)
        {
            this.UserName = userName;
        }

        public string UserName { private set; get; }

        public FileCheckoutedToAnotherUser(string userName="")
            : base(Resources.STR_UNABLE_SEND, Resources.STR_FILEISCHECKEDOUTBYANOTHERUSER_TEXT)
        {
            this.UserName = userName;
        }
    }

    //not authenticated on workshare
    public class CloudUnAuthorized : BaseException
    {
        public CloudUnAuthorized()
            : base(Resources.STR_WRONGAUTH_CAPTION, Resources.STR_WRONGAUTH_TEXT)
        { }
        public CloudUnAuthorized(Exception ex)
            : base(Resources.STR_WRONGAUTH_CAPTION, Resources.STR_WRONGAUTH_TEXT, ex)
        { }

    }

    public class CannotProcessItemException : BaseException
    {
        public CannotProcessItemException()
            : base(Resources.STR_UNABLE_SEND, Resources.STR_LONG_FILE_NAME_TEXT)
        {
        }
    }


	public class DMSUnAuthorizedException: BaseException
    {
		public DMSUnAuthorizedException()
             : base(Resources.STR_DO_NOT_HAVE_PERMISSION_CAPTION, Resources.STR_DO_NOT_HAVE_PERMISSION_TEXT)
        {
		}
    }
}

<file_sep>/WSComponents/src/WSIntegration/Interfaces/IAuthProvider.cs
﻿using Workshare.Integration.WsProxies;
using WorksharePlatform;

namespace Workshare.Integration.Interfaces
{
    public interface IAuthProvider
    {
        UserDetails GetCurrentWSUser();
        WsUser GetCurrentWSUser2();
        void SetCurrentUser(UserDetails user);
        UserDetails CheckIfAuth();
    }
}
<file_sep>/WSComponents/src/WSComponents/Helpers/Helpers.cs
﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using Workshare.Integration.Interfaces;

namespace Workshare.Components.Helpers
{
    public class WinFormHelper : System.Windows.Forms.IWin32Window
    {
        IntPtr m_Handle;
        public WinFormHelper(IntPtr pParent)
        {
            m_Handle = pParent;
        }
        public IntPtr Handle
        {
            get { return m_Handle; }
        }

    }

    static class WinInetHelper
    {
        [System.Runtime.InteropServices.DllImport("wininet.dll", CharSet = System.Runtime.InteropServices.CharSet.Auto, SetLastError = true)]
        static extern bool InternetSetOption(int hInternet, int dwOption, IntPtr lpBuffer, int dwBufferLength);


        public static void ResetSession()
        {
            return;
            int option = (int)3/* INTERNET_SUPPRESS_COOKIE_PERSIST*/;
            var ptr = Marshal.AllocHGlobal(Marshal.SizeOf(option));
            try
            {
                Marshal.StructureToPtr(option, ptr, false);
                InternetSetOption(0, 81/*INTERNET_OPTION_SUPPRESS_BEHAVIOR*/, ptr, Marshal.SizeOf(option));
            }
            finally
            {
                Marshal.Release(ptr);
            }
        }
    }

    public static class CollectionExt
    {
        public static bool HasOnlyOneFile(this IEnumerable<IDMSItem> collection)
        {
            if (collection == null) return false;
            return collection.All(a => a is IDMSFile) && collection.Count() == 1;
        }
        public static bool HasOnlyOneFolder(this IEnumerable<IDMSItem> collection)
        {
            if (collection == null) return false;
            return collection.All(a => a is IDMSFolder) && collection.Count() == 1;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Exceptions/CannotAddHistoryException.cs
﻿using System;
using Workshare.Integration.Exceptions;

namespace Workshare.Components.Exceptions
{
    public class CannotAddHistoryException : BaseException
    {
        public CannotAddHistoryException(string message)
            : base("",message)
        {
        }
        public CannotAddHistoryException(string message, Exception inner)
            : base("",message, inner)
        {
        }
    }
}
<file_sep>/README.md
dmssync
=======<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Visitors/ChangesDetector.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using Workshare.Components.Helpers;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Changes.Visitors
{
    public class ChangesDetector
    {
        private readonly DmsWorkerBase _dmsWorker;
        private readonly IAuthProvider _auth;
        private readonly SyncInfoService _syncInfoService;

        public DetectorOptions opt;

        public ChangesDetector(DmsWorkerBase dmsWorker, IAuthProvider auth, SyncInfoService syncInfoService)
        {
            this._dmsWorker = dmsWorker;
            this._auth = auth;
            _syncInfoService = syncInfoService;
            opt = new DetectorOptions() { UseForceRequest = true };
        }
        public void AddSharedChangeIfDetected(FileMap filemap, FileMapActivity fileActivity)
        {
            if (filemap.WsFile != null)
            {
                fileActivity.AddChange(new FileActivityChange
                {
                    Type = ChangeType.Uploaded,
                });
            }
        }

        string GetWsFileName(FileMap filemap)
        {
            return (filemap.WsFile != null) ? (FileUtils.ChangeExtension(filemap.WsFile.FriendlyName, FileUtils.GetExtension(filemap.WsFile.Name))) : null;
        }

        string GetLocalFileName(FileMap filemap)
        {
            return (filemap.LocalFile != null) ? filemap.LocalFile.Name : null;
        }

        public void AddRenameChangeIfDetected(FileMap filemap, FileMapActivity fileActivity)
        {
            var wsFilename = GetWsFileName(filemap);
            var localFilename = GetLocalFileName(filemap);
            if (!string.IsNullOrEmpty(wsFilename) && !string.IsNullOrEmpty(localFilename)
                   && !string.Equals(FileUtils.GetFileNameWithoutExtension(wsFilename), FileUtils.GetFileNameWithoutExtension(localFilename), StringComparison.InvariantCultureIgnoreCase))
            {
                fileActivity.AddChange(new FileActivityChange
                {
                    Type = ChangeType.NamesDiffer,
                    LocalName = localFilename,
                    WsName = wsFilename
                });
            }
        }

        public void AddTypeChangedIfDetected(FileMap filemap, FileMapActivity fileActivity)
        {
            var wsFilename = GetWsFileName(filemap);
            var localFilename = GetLocalFileName(filemap);
            if (!string.Equals(FileUtils.GetExtension(wsFilename), FileUtils.GetExtension(localFilename),
                       StringComparison.InvariantCultureIgnoreCase))
            {
                var oldType = FileUtils.GetExtension(localFilename);
                var newType = FileUtils.GetExtension(wsFilename);
                if (oldType != null && newType != null)
                {
                    oldType = oldType.Replace(".", "").ToUpper();
                    newType = newType.Replace(".", "").ToUpper();
                }

                if (!string.IsNullOrEmpty(oldType) && !string.IsNullOrEmpty(newType))
                {
                    fileActivity.AddChange(new FileActivityChange
                    {
                        LocalDocType = oldType,
                        WsDocType = newType,
                        Type = ChangeType.DocTypeChanged
                    });
                }
            }
        }

        private FolderMap GetFirstFolderSentToWs(FileMap fileMap)
        {

            //TODO use GetFirstParentLinkedWithExistedOnWs
            var current = fileMap.IndirectParent ?? fileMap.Parent as FolderMap;

            while (current != null && current.WsFolder == null)
            {
                current = fileMap.IndirectParent ?? current.Parent as FolderMap;
            }
            return current;
        }

        internal void AddFolderSharedIfDetected(FileMapActivity fileActivity, FileMap fileMap)
        {
            var folderMap = GetFirstFolderSentToWs(fileMap);
            if (folderMap == null || folderMap.WsFolder == null) return;
            var wsFolder = folderMap.WsFolder;

            if (fileMap.LocalFile == null) return;
            WsUser currentUser = _auth.GetCurrentWSUser2();

            var otherMembersCount = wsFolder.Members.GetWithoutCurrentUser(currentUser).Count();
               

            fileActivity.AddChange(new FileActivityChange
            {
                Type = ChangeType.FolderSharedWithOthers,
                FolderSharedBy = wsFolder.Owner,
                OtherMemebersCount = otherMembersCount,
                OtherMemberViewLink = wsFolder.Url
            });
        }

        internal void AddLastUnSentOrChangedVersionIfDetected(FileMapActivity fileActivity, FileMap fileMap)
        {
            var allLinkedVerionMaps =
                fileMap.Maps.OfType<VersionMap>()
                    .Where(a => a.HasLocal() && a.HasRemote())
                    .OrderByDescending(a => a.LocalVersion.Number);
            var lastLinkedVersionMap = allLinkedVerionMaps.FirstOrDefault();
            
            var allNotLinkedVersionMaps = fileMap.Maps.OfType<VersionMap>().Where(a => a.HasLocal() && !a.HasRemote());

            var lastChangedNotLinkedVersionMap = allNotLinkedVersionMaps
                //.OrderByDescending(a => a.LocalVersion.Number)
                .FirstOrDefault(a => a.LocalVersion.EditTime == allNotLinkedVersionMaps.Max(x => x.LocalVersion.EditTime));
            var syncInfo = _syncInfoService.GetSyncInfo(fileMap, opt.UseForceRequest);
            bool addLastNotLinked = lastChangedNotLinkedVersionMap != null && lastLinkedVersionMap == null
                                    ||
                                    lastChangedNotLinkedVersionMap != null
                                    && lastLinkedVersionMap.LocalVersion.Number < lastChangedNotLinkedVersionMap.LocalVersion.Number
                                    ||
                                    lastChangedNotLinkedVersionMap != null && syncInfo != null
                                    && lastChangedNotLinkedVersionMap.LocalVersion.Number > syncInfo.LastUploadedDmsVerNum
                                    ||
                                    lastChangedNotLinkedVersionMap != null
                                    && lastLinkedVersionMap.LocalVersion.Number > lastChangedNotLinkedVersionMap.LocalVersion.Number 
                                    && lastChangedNotLinkedVersionMap.LocalVersion.EditTime > lastLinkedVersionMap.LocalVersion.EditTime;

            if (addLastNotLinked)
            {
                fileActivity.AddChange(new FileActivityChange
                {
                    Type = ChangeType.NotSentVersion,
                    SavedTime = _dmsWorker.GetEditTime(lastChangedNotLinkedVersionMap.LocalVersion),
                    VersionNumber = lastChangedNotLinkedVersionMap.LocalVersion.Number,
                    LocalVersionId = lastChangedNotLinkedVersionMap.LocalVersion.Id
                });
            }
            else 
            {
                foreach (var sentversion in allLinkedVerionMaps.Reverse())
                {
                    if (sentversion.LocalVersion.WasChangedAfterSend2(opt.UseForceRequest))
                    {
                        fileActivity.AddChange(new FileActivityChange()
                        {
                            Type = ChangeType.VersionChangedAfterSend,
                            SavedTime = _dmsWorker.GetEditTime(sentversion.LocalVersion),
                            VersionNumber = sentversion.LocalVersion.Number,
                            LocalVersionId = sentversion.LocalVersion.Id
                        });
                        break;
                    }
                }
            }
        }


        internal void AddChangesIfDetected(FileMap fileMap, FileMapActivity documentChanges)
        {
            if (fileMap.HasLocal() && fileMap.HasRemote())
            {
                var syncInfo = _syncInfoService.GetSyncInfo(fileMap, opt.UseForceRequest);
                var versionMaps = fileMap.Maps.OfType<VersionMap>().ToList();

                var onlyRemoteVersionMaps = versionMaps.Where(p => p.LocalVersion == null && p.WsVersion != null).ToList();

                var lastWsVersionNumImportedToDms =
                    fileMap.WsFile.Versions.Where(p => syncInfo != null && p.Id == syncInfo.LastImportedWsVerId)
                        .Select(a => a.Version).FirstOrDefault();
                var newVersions =
                    onlyRemoteVersionMaps.Where(
                        a => a.HasRemote() && a.WsVersion.Version > lastWsVersionNumImportedToDms)
                        .Select(a => a.WsVersion)
                        .ToList();
                var newversionsExist = newVersions.Any();
                var localWasUpdated = fileMap.LocalFile != null && fileMap.LocalFile.WasUpdatedAfterSend2(opt.UseForceRequest);
                if (newversionsExist && localWasUpdated)
                {
                    documentChanges.AddChange(new FileActivityChange
                    {
                        Type = ChangeType.BothChanged,
                        NewerVersions = newVersions,
                    });
                }
                else if (newversionsExist)
                {
                    documentChanges.AddChange(new FileActivityChange
                    {
                        Type = ChangeType.RemoteChanged,
                        NewerVersions = newVersions,
                    });
                }
                else if (localWasUpdated)
                {
                    documentChanges.AddChange(new FileActivityChange
                    {
                        Type = ChangeType.LocalChanged
                    });
                }
            }
        }

        internal void AddNotModifiedIfdetected(FileMap fileMap, ImportFileActivity documentChanges)
        {
            if (documentChanges.Changes.Any())
            {
                return;
            }

            if (fileMap.LocalFile != null && fileMap.WsFile != null)
            {
                documentChanges.AddChange(new FileActivityChange
                {
                    Type = ChangeType.NotModified
                });
            }
        }

        internal void AddDeleted(FileMap fileMap, ImportFileActivity documentChanges)
        {
            if (fileMap.ProcessState == ProcessState.Error) return;
            if (fileMap.HasLocal() && !fileMap.HasRemote() && _syncInfoService.GetSyncInfo(fileMap.LocalFile, opt.UseForceRequest) != null)
            {
                documentChanges.AddChange(new FileActivityChange
                {
                    Type = ChangeType.RemoteDeleted
                });
            }
        }

        internal void AddAddedOnWs(FileMap fileMap, ImportFileActivity documentChanges)
        {
            if (fileMap.WsFile != null && fileMap.LocalFile == null)
            {
                documentChanges.AddChange(new FileActivityChange
                {
                    Type = ChangeType.RemoteAdded,
                    NewerVersions = fileMap.WsFile.Versions.ToList()
                });
            }
        }

        internal void AddNotSent(FileMap fileMap, ImportFileActivity documentChanges)
        {
            if (fileMap.LocalFile != null && _syncInfoService.GetSyncInfo(fileMap.LocalFile, opt.UseForceRequest) == null)
            {
                documentChanges.AddChange(new FileActivityChange
                {
                    Type = ChangeType.NotSent
                });
            }
        }
    }

    public class DetectorOptions
    {
        public bool UseForceRequest { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents.Tests/TestAuthProvider.cs
﻿using NUnit.Framework;
using Workshare.Components.Concrete;

namespace WSComponents.Tests
{
    [TestFixture]
    public class TestAuthProvider
    {
        [Test]
        public void TestGetUserDefault_NotNull()
        {
            var auth_provider = new DMSAuthProvider();
            Assert.IsNotNull(auth_provider.GetCurrentWSUser(), "Auth provider must not return NULL user");
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Exceptions/FileCannotBeCheckedInException.cs
﻿using System;
using Workshare.Integration.Exceptions;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Exceptions
{
    public class FileCannotBeCheckedInException : BaseException
    {
        public FileCannotBeCheckedInException(string reasonMessage)
            : base(RES.STR_UNABLE_SYNC, string.Format(RES.STR_FILE_CANNOT_BE_CHECKEDIN, reasonMessage))
        {
        }
    }

    public class FileUnlockFailedException : BaseException
    {
        public FileUnlockFailedException()
            : base(RES.STR_UNABLE_SYNC, RES.STR_FILE_CANNOT_BE_UNLOCKED)
        {
        }
    }

    public class FileCannotBeDeletedException : BaseException
    {
        public FileCannotBeDeletedException(Exception inner)
            : base("","Cannot remove the file. "+inner.Message,inner)
        {
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Interfaces/ICloseRequester.cs
﻿using System;

namespace Workshare.Components.Interfaces
{
    public interface ICloseRequester
    {
        event Action<bool?> CloseRequested;
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/ItemMap.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Processor.DmsItems.Visitors;

namespace Workshare.Integration.Processor.Maps
{

    public enum ProcessState{
        Scanned,
        Processed, 
        Error, 
        Cancelled}

    public abstract class ItemMap
    {
        string _id;
        public string Id
        {
            get
            {
                if (string.IsNullOrEmpty(_id))
                {
                    _id=GetId();
                }
                return _id;
            }

            protected set
            {
                _id = value;
            }
        }

        readonly List<ItemMap> _maps;
        public IEnumerable<ItemMap> Maps { get { return _maps; } }

        public ItemMap Parent { private set; get; }

        public ItemMap IndirectParent { set; get; }

        public Exception Error;

        public ProcessState ProcessState { set; get; }

        protected ItemMap()
        {
            _maps = new List<ItemMap>();
        }

        public void AddIf(ItemMap map)
        {
            map.Parent = this;
            if (!_maps.Contains(map))
            {
                _maps.Add(map);
            }
        }

        public abstract void Apply(ItemMapVisitor visitor);

        public abstract string GetId();

        public override string ToString()
        {
            return string.Format("{0} : State={1}, Id={2}, ChildrenCount={3}",this.GetType().Name,ProcessState,Id,_maps.Count);
        }
    }

    public class SummaryProcessResult : ItemMap
    {
        public PageIterator Iterator { get; set; }

        public override void Apply(ItemMapVisitor visitor)
        {
            foreach (var item in this.Maps.ToList())
            {
                item.Apply(visitor);
            }
        }

        public override string GetId()
        {
            return "SummaryProcessResult";
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Extensions/LocalFileExtensions.cs
﻿using System;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;


namespace Workshare.Integration.Extensions
{
    public static class LocalFileExtentions
    {
        public static void CheckPermissionkOrThrow(this IDMSItem obj, Permissions permissions)
        {
            if (!obj.DoesUserHavePermissions(permissions))
            {
                throw new UnauthorizedAccessException();
            }
        }

        public static void CheckNotCheckeOutToOtherUserOrThrow(this IDMSFile item, Operations oper)
        {
            if (item != null)
            {
                if (item.IsCheckedOutToOtherUser()) throw new FileCheckoutedToAnotherUser(oper);
                if (!item.IsCheckedOutFileExists()) throw new LocalFileNotFound();
            }
        }

        public static bool IsCheckedOutToOtherUser(this IDMSItem item)
        {
            if (item != null)
            {
                return (item.CheckedOut && !item.CheckedOutToUser);
            }
            return true;
        }

    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/SyncItemsCommand.cs
﻿using System;
using System.Collections.Generic;
using System.Drawing;
using System.Globalization;
using System.Linq;
using System.Runtime.InteropServices;
using Com.Interwoven.Worksite.iManExt;
using Workshare.Components;
using Workshare.Components.Helpers;
using Workshare.Components.Properties;
using Workshare.IManage.Views;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.DmsItems;


namespace Workshare.IManage
{

    public class SyncItemsCommand : Command
    {
        public override object Bitmap {
            get
            {
                return Resources.workshare_sync_from.GetHbitmap();
            }
            set { }
        }

        public override string MenuText
        {
            get
            {
                return "Sync from Workshare";
            }
            set
            {
            }
        }

        public override string HelpText {
            get { return MenuText + "\nSync item"; }
            set { }
        }

        public override void ExecuteAction()
        {
            
            var contextItems = GetContextItems().ToList();
            if (!contextItems.Any())
            {
                return;
            }

            if (!Application.iManInstance.Presenter.LoginIfNeeded())
            {
                return;
            }

            var linkedItemsCount = contextItems.Count(p => syncService.GetSyncInfo(p) != null);
            var allItemsAreLinked = linkedItemsCount == contextItems.Count;
            var someItemsLinked = linkedItemsCount > 0;
            var hasPermissions = contextItems.All(p => p.DoesUserHavePermissions(Permissions.EditItem));
            var anyTaskAlreadyInProgress = Application.iManInstance.Presenter.IsAnyItemInProgress();
            var someCheckedOutToOther = contextItems.Any(a => a.IsCheckedOutToOtherUser());
            var canSync = allItemsAreLinked
                          && hasPermissions
                          && !anyTaskAlreadyInProgress
                          && !someCheckedOutToOther;
            if (canSync)
            {
                Application.iManInstance.View.OnSynchItemsClicked(new SyncItemsClickedArgs(contextItems.Select(p => new SyncItemInformation(p, ConflictOptions.None, ConflictVersionOptions.None))));
            }
            else if (!someItemsLinked)
            {
                if (contextItems.HasOnlyOneFile())
                {
                    ShowError(
                        new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync,
                            Resources.STR_ERROR_TEXT_File_is_not_sent_to_Workshare_), contextItems.FirstOrDefault());
                }
                else if (contextItems.HasOnlyOneFolder())
                {
                    ShowError(
                        new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync,
                            Resources.STR_ERROR_TEXT_Folder_is_not_sent_to_Workshare_), contextItems.FirstOrDefault());
                }
                else
                {
                    ShowError(
                        new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync,
                            Resources.STR_ExecuteAction_All_items_are_not_sent_to_Workshare),
                        contextItems.FirstOrDefault());
                }
            }
            else if (!allItemsAreLinked)
            {
                ShowError(new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync, Resources.STR_ExecuteAction_Some_items_are_not_sent_to_Workshare), contextItems.FirstOrDefault());
            }
            else if (anyTaskAlreadyInProgress)
            {
                ShowError(new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync, Resources.STR_ExecuteAction_Some_another_task_is_already_in_progress), contextItems.FirstOrDefault()); 
            }
            else if (someCheckedOutToOther)
            {
                ShowError(new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync, Resources.STR_ExecuteAction_File_is_checked_out_to_another_users), contextItems.FirstOrDefault()); 
            }
            else
            {
                ShowError(new DMSUnAuthorizedException(),contextItems.FirstOrDefault());
            }
        }
    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("41CF85DC-221B-48F5-8159-4083A4A18786")]
    [ComVisible(true)]
    public class DocumentSyncItemsCommand : SyncItemsCommand
    {
        public override string HelpText
        {
            get
            {
                return "Sync document from Workshare\nSync from Workshare";
            }
            set
            {
                base.HelpText = value;
            }
        }

        public override int Status
        {
            get
            {
                //Context.OfType<object>().ToList().ForEach(p => System.Diagnostics.Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                bool IsAnyDocumentSelected = false;
                try
                {
                    var items = GetContextItems();
                    if (items.Count == 1 && (items[0] is Workshare.Integration.Interfaces.IDMSFolder))
                    {
                        var fld = items[0] as Workshare.Integration.Interfaces.IDMSFolder;
                        IsAnyDocumentSelected = fld.Files.Count() > 0;
                    }
                    else
                    {
                        IsAnyDocumentSelected = items.OfType<Workshare.Integration.Interfaces.IDMSFile>().Any();
                    }
                }
                catch
                { }

                return (int)((IsAnyDocumentSelected && !Application.iManInstance.Presenter.IsAnyItemInProgress() && IsAnyServerAvailable()) ? CommandStatus.nrActiveCommand : CommandStatus.nrGrayedCommand);
            }
            set
            {

            }
        }

    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("0BDF6E98-73AC-4B5C-9D08-247D1F7E475F")]
    [ComVisible(true)]
    public class FolderSyncItemsCommand : SyncItemsCommand
    {

        public override string HelpText
        {
            get
            {
                return "Sync folder from Workshare\nSync from Workshare";
            }
            set
            {
                base.HelpText = value;
            }
        }
    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("EB73626D-1145-491B-9866-F88FC890662D")]
    [ComVisible(true)]
    public class FolderTrueSyncItemsCommand : Command
    {

        public Bitmap ResizeBitmap(Bitmap b, int nWidth, int nHeight)
        {
            var result = new Bitmap(nWidth, nHeight);
            using (Graphics g = Graphics.FromImage(result))
                g.DrawImage(b, 0, 0, nWidth, nHeight);
            return result;
        }

        public override object Bitmap
        {
            get
            {
                if (GetClientType() == iManType.DeskSite)
                {
                    return Resources.workshare_sync.GetHbitmap();
                }
                if (Application.iManInstance.ClientVersion == "9")
                {
                    return ResizeBitmap(GetBitmap(GetSelectedFolders()), 32, 32).GetHbitmap();
                }
                return ResizeBitmap(GetBitmap(GetSelectedFolders()), 16, 16).GetHbitmap();
            }
            set
            {
            }
        }

        private void DrawFilesToSyncCountEllipse(string cnt, Graphics gr, int ellipseDeltaX, int stringDeltaX)
        {
            int initialStringX = 19;
            int initialEllipseXData = 16;

            gr.FillEllipse(new SolidBrush(Color.FromArgb(243, 129, 48)), new Rectangle(initialEllipseXData - ellipseDeltaX, 0, initialEllipseXData + ellipseDeltaX, 16));
            gr.DrawEllipse(new Pen(Color.White), new Rectangle(initialEllipseXData - ellipseDeltaX, 0, initialEllipseXData + ellipseDeltaX, 16));
            gr.DrawString(cnt, new Font("Arial", 8, FontStyle.Bold),
                new SolidBrush(Color.White), initialStringX - stringDeltaX, 1);
        }

        private Bitmap GetBitmap(List<IDMSFolder> contextItems)
        {
            var bm = new Bitmap(Properties.Resources.sync_ribbon_icon32);
            if (contextItems.Count() == 1)
            {
                int cnt =
                    Components.Common.ActivityCounter.Instance.ActivityCount(
                        contextItems.ToList()[0]);
                if (cnt > 0 && Status == (int)CommandStatus.nrActiveCommand)
                {
                    Graphics gr = Graphics.FromImage(bm);


                    if (Application.iManInstance.ClientVersion == "9")
                    {
                        if (cnt < 10)
                        {
                            DrawFilesToSyncCountEllipse(cnt.ToString(CultureInfo.InvariantCulture), gr, 0, 0);
                        }
                        else
                        {
                            if (cnt < 100)
                            {
                                DrawFilesToSyncCountEllipse(cnt.ToString(CultureInfo.InvariantCulture), gr, 2, 3);
                            }
                            else
                            {
                                DrawFilesToSyncCountEllipse("99+", gr, 6, 9);
                            }
                        }
                    }
                    else
                    {
                        gr.FillEllipse(new SolidBrush(Color.FromArgb(243, 129, 48)), new Rectangle(16, 0, 16, 16));
                    }
                }

            }
            return bm;
        }

        public override object LargeBitmap
        {
            get
            {
                var bm = GetBitmap(GetSelectedFolders());
                return bm.GetHbitmap();
            }
            set
            {
                
            }
        }

        public override string Name
        {
            get
            {
                return this.GetType().FullName;
            }
            set
            {
            }
        }

        public override string MenuText
        {
            get
            {

                return "Sync";
            }
            set
            {
                base.MenuText = value;
            }
        }

        public override CommandType Type
        {
            get
            {
                return CommandType.nrStandardCommand;
            }
            set
            {
                base.Type = value;
            }
        }

        public override int Status
        {
            get
            {
                if (IsAnyServerAvailable() || base.Status == (int)CommandStatus.nrActiveCommand)
                {
                    var contextItems = GetSelectedFolders().ToList();
                    var fld = contextItems.FirstOrDefault();
                    Components.Common.ActivityCounter.Instance.CurrentFolder = fld;
                    return (int)((fld != null && fld.DoesUserHavePermissions(Permissions.EditItem)) ? CommandStatus.nrActiveCommand : CommandStatus.nrGrayedCommand);
                }
                else
                {
                    return (int)CommandStatus.nrGrayedCommand;
                }
            }
            set
            {

            }
        }

        public override string HelpText
        {
            get
            {
                return "Sync folder from Workshare\nSync folder";
            }
            set
            {
                
            }
        }

        public override void ExecuteAction()
        {
            if (Application.iManInstance.Presenter.IsAnyItemInProgress()) return;

            if (!Application.iManInstance.Presenter.LoginIfNeeded())
            {
                return;
            }

            Application.iManInstance.ClientType = GetClientType();
            var contextItems = GetSelectedFolders().ToList();
            var items = GetContextItems().ToList();
            var hasPermissions = contextItems.All(p => p.DoesUserHavePermissions(Permissions.EditItem));
            var anyTaskAlreadyInProgress = Application.iManInstance.Presenter.IsAnyItemInProgress();
            var someCheckedOutToOther = GetContextItems().Any(a => a.IsCheckedOutToOtherUser());
            var foldersIsSentToWS = contextItems.All(p => syncService.GetSyncInfo(p) != null);

            bool canTrueSync = contextItems.OfType<BaseDMSFolder>().Count() == 1
                && foldersIsSentToWS
                && hasPermissions
                && !anyTaskAlreadyInProgress;

            if (canTrueSync)
            {
                ((ModuleView)Application.iManInstance.View).OnTrueSyncItemsClicked(new SyncItemsClickedArgs(contextItems.Select(p => new SyncItemInformation(p, ConflictOptions.None, ConflictVersionOptions.None))), (GetClientType() == iManType.FileSite));
            }
            else if (!hasPermissions)
            {
                ShowError(new DMSUnAuthorizedException(), items.FirstOrDefault());
            }
            else if (!foldersIsSentToWS)
            {
                ShowError(new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync, Resources.STR_ERROR_TEXT_Folder_is_not_sent_to_Workshare_), items.FirstOrDefault());
            }
            else if (anyTaskAlreadyInProgress)
            {
                ShowError(new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync, Resources.STR_ExecuteAction_Some_another_task_is_already_in_progress), items.FirstOrDefault());
            }
            else if (someCheckedOutToOther)
            {
                ShowError(new BaseException(Resources.STR_SyncItemsCommand_ExecuteAction_Unable_to_sync, Resources.STR_ExecuteAction_File_is_checked_out_to_another_users), items.FirstOrDefault());
            }
            else
            {
                ShowError(new DMSUnAuthorizedException(), items.FirstOrDefault());
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Interfaces/IWorkUnit.cs
﻿using System.Collections.Generic;
using Workshare.Components.Common;
using Workshare.Integration.Interfaces;

namespace Workshare.Components.Interfaces
{
    public interface IWorkUnit
    {
        void Execute();
        WorkStatus Status { get; set; }
        string StatusDescription { get; set; }
        string Name { get; }
        TargetItem[] TargetItems { get; }
        string ItemName { set; get; }
        void OnAdded();
    }

    public class TargetItem
    {
        public string Id { private set; get; }
        public string Name { set; get; }

        public TargetItem(string id)
        {
            this.Id = id;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/VMs/FileActivityBaseVm.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.TrueSyncDialog.VMs
{
    public abstract class FileActivityBaseVm<T> : ItemMapActivityVm<T>, IFileActivityBaseVm
    {
        private FileMapActivity _data;

        public FileActivityBaseVm(FileMapActivity activity)
        {
            if (activity == null) throw new ArgumentNullException("activity");
            this._data = activity;
        }

        public override string Id
        {
            get { return _data.Id; }
        }

        public override string MapId
        {
            get { return _data.MapId; }
        }

        public override string Name
        {
            get { return _data.Filename; }
        }

        public string ViewOnlineUrl
        {
            get { return _data.ViewOnlineUrl; }
        }

        public override bool IsDiscarded
        {
            get
            {
                return _data.IsDiscarded;
            }
            set
            {
                _data.IsDiscarded = value;
            }
        }

        public override object data
        {
            get { return _data; }
        }

        public string CheckOutTo
        {
            get { return _data.CheckedOutTo; }
        }

        public string CheckOutMachine
        {
            get { return _data.CheckOutMachine; }
        }

        public DateTime LastUpdateTime
        {
            get { return _data.WsLastUpdateDate; }
        }

        public virtual bool DiscardAlwaysVisible 
        {
            get { return false; } 
        }

        public Visibility DiscardVisibility
        {
            get
            {
                if (DiscardAlwaysVisible)
                {
                    return Visibility.Visible;
                }
                return (_data.IsDiscarded ? Visibility.Hidden : Visibility.Visible);
            }
        }

        public string Error
        {
            get
            {
                if (_data.Error != null)
                {
#if DEBUG
                    return _data.Error.ToString();
#else
                    return _data.Error.Message;
#endif
                }
                return string.Empty;
            }
        }

        public List<DocumentActionVM> Actions
        {
            get { return _data.Actions.Select(a => new DocumentActionVM(a, this)).ToList(); }
        }

        public virtual bool IsInProgress 
        {
            get { return false; }
        }

        internal bool CanExecuteAction(DocumentActionVM action)
        {
            return _data.CanExecute(action.action);
        }
    }

    public interface IFileActivityBaseVm
    {
        string ViewOnlineUrl { get; }
        bool IsInProgress { get; }
        List<DocumentActionVM> Actions { get; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Progress/VMs/TargetItemVm.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Components.Interfaces;

namespace Workshare.Components.Views.Progress.VMs
{
    public class TargetItemVm
    {
        private readonly TargetItem _item;

        public bool IsFor(TargetItem item)
        {
            return item == this._item;
        }

        public TargetItemVm(Interfaces.TargetItem item)
        {
            this._item = item;
        }

        public string Id
        {
            get
            {
                return _item.Id;
            }
        }

        public string Name
        {
            get { return _item.Name; }
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/CookieAwareClient.cs
﻿using System;
using System.Collections.Generic;
using System.Text;
using System.Net;
using System.IO;
using System.Collections.Specialized;
using System.Globalization;

namespace WorksharePlatform
{
    public class CookieAwareClient
        : WebClient
    {

        public const string TmpAuthToken = "<PASSWORD>";
        public CookieAwareClient()
            : this(new UserDetails())
        {
        }

        public CookieAwareClient(UserDetails user)
        {
            User = user;
            if (User.SessionCookies == null)
            {
                CookieContainer = new CookieContainer();
            }
            Timeout = 5 * 60 * 1000; // 5 Minutes
            Encoding = Encoding.UTF8;
        }
        #region Private Methods

        private int WriteEncoded(Stream formDataStream, string data)
        {
            byte[] bytes = Encoding.UTF8.GetBytes(data);
            if (formDataStream != null)
            {
                formDataStream.Write(bytes, 0, bytes.Length);
            }
            return bytes.Length;
        }

        private int WriteData(Stream formDataStream, byte[] data, int bufferLength)
        {
            if (formDataStream != null)
            {
                formDataStream.Write(data, 0, bufferLength);
            }
            return bufferLength;
        }

        private void WriteMultipartFormData(Stream requestStream, Dictionary<string, object> parameters, string boundary)
        {
            foreach (var param in parameters)
            {
                if (param.Value is FileDetails)
                {
                    // The parameter is file data. Add header info and file data bytes.
                    var fileToUpload = (FileDetails)param.Value;

                    string fileName = fileToUpload.Name;

                    string header = string.Format("--{0}\r\nContent-Disposition: form-data; name=\"{1}\"; filename=\"{2}\";\r\nContent-Type: {3}\r\n\r\n",
                     boundary,
                     param.Key,
                     fileName,
                     fileToUpload.CurrentVersion.ContentType ?? "application/octet-stream");

                    WriteEncoded(requestStream, header);

                    using (Stream fileStream = File.Open(fileToUpload.FilePath, FileMode.Open, FileAccess.Read, FileShare.None))
                    {
                        using (BinaryReader br = new BinaryReader(fileStream))
                        {
                            WriteData(requestStream, br.ReadBytes((int)fileStream.Length), (int)fileStream.Length);
                        }
                    }

                    WriteEncoded(requestStream, "\r\n");
                }
                else
                {
                    string data = param.Value.ToString();

                    // The parameter is a value type. Add header info, convert the value data to a string and add that value string.
                    string postData = string.Format("--{0}\r\nContent-Disposition: form-data; name=\"{1}\"\r\n\r\n{2}\r\n",
                    boundary,
                    param.Key,
                    data);

                    WriteEncoded(requestStream, postData);
                }
            }

            // Write the footer info.
            string footer = string.Format("--{0}--\r\n", boundary);
            WriteEncoded(requestStream, footer);
        }

        private void WriteMultipartFormData3(Stream requestStream, FileDetails file)
        {
            using (Stream fileStream = File.Open(file.FilePath, FileMode.Open, FileAccess.Read, FileShare.None))
            {
                using (BinaryReader br = new BinaryReader(fileStream))
                {
                    WriteData(requestStream, br.ReadBytes((int)fileStream.Length), (int)fileStream.Length);
                }
            }
        }

        private void WritePutUserWDSValue(Stream requestStream, byte[] data)
        {
            WriteData(requestStream, data, data.Length);
        }

        private HttpWebResponse FollowRedirection(string location)
        {
            var request = (HttpWebRequest)WebRequest.Create(location);
            request.CookieContainer = CookieContainer;
            request.ReadWriteTimeout = Timeout;
            request.AllowAutoRedirect = true;
            if (User.IsProxyEnable)
            {
                request.Proxy = User.Proxy;
                request.Proxy.Credentials = User.ProxyCredentials;
            }

            return (HttpWebResponse)request.GetResponse();
        }

        #endregion

        #region Protected Methods

        protected override WebRequest GetWebRequest(Uri address)
        {
            var urlWithToken = address.ToString();
            if (!string.IsNullOrEmpty(User.AuthToken))
            {

                if (!urlWithToken.Contains("?"))
                {
                    urlWithToken += "?";
                }
                else
                {
                    if (!urlWithToken.EndsWith("&"))
                    {
                        urlWithToken += "&";
                    }
                }

                if (User.SessionCookies.Count < 2)
                {
                    urlWithToken += TmpAuthToken + "=" + User.AuthToken;
                }
                 User.AuthToken = null;
            }

            var request = base.GetWebRequest(new Uri(urlWithToken));
            var httpRequest = request as HttpWebRequest;
            if (httpRequest!=null)
            {
                httpRequest.CookieContainer = CookieContainer;
                httpRequest.AutomaticDecompression = DecompressionMethods.GZip | DecompressionMethods.Deflate;
                if (User.IsProxyEnable)
                {
                    httpRequest.Proxy = User.Proxy;
                    httpRequest.Proxy.Credentials = User.ProxyCredentials;
                }
            }
            
            return httpRequest;
        }

        public const string user_credentials = "<PASSWORD>";
        public const string _session_id = "_session_id";
        public const string device_credential = "device_credentials";
        public const string cloudemail = "cloudemail";

        protected override WebResponse GetWebResponse(WebRequest request)
        {
            var response = base.GetWebResponse(request);

            var cookies = ((HttpWebResponse)response).Cookies;
            var temp = new CookieContainer();
            var authCookiesCount = 0;
            foreach (Cookie cookie in cookies)
            {
                if (string.Equals(cookie.Name, device_credential, StringComparison.InvariantCultureIgnoreCase))
                    //|| string.Equals(cookie.Name, _session_id, StringComparison.InvariantCultureIgnoreCase))
                {
                    authCookiesCount++;
                }
                temp.Add(cookie);
            }
            if (authCookiesCount == 1)
            {
                CookieContainer = temp;
            }
            return response;
        }

        #endregion

        public string DownloadFile()
        {
            string filePath = Path.GetTempFileName();
            DownloadFile(Uri, filePath);
            return filePath;
        }

        public byte[] PostValues(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl, action));
            return UploadValues(Uri, "POST", queries);
        }

        public byte[] PostValuesVersion3(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl3, action));
            return UploadValues(Uri, "POST", queries);
        }

        public byte[] PostValues4(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl4, action));
            return UploadValues(Uri, "POST", queries);
        }

        public byte[] PutValues(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl, action));
            return UploadValues(Uri, "PUT", queries);
        }

        public string GetString(string action)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl, action));
            string res = DownloadString(Uri);
            if (res.StartsWith("<!DOCTYPE html", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new UnauthorizedAccessException();
            }
            return res;
        }

        public string GetString2(string action)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl2, action));
            string res = DownloadString(Uri);
            if (res.StartsWith("<!DOCTYPE html", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new UnauthorizedAccessException();
            }
            return res;
        }

        public string GetString3(string action)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl3, action));
            string res = DownloadString(Uri);
            if (res.StartsWith("<!DOCTYPE html", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new UnauthorizedAccessException();
            }
            return res;
        }

        public string GetString4(string action)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl4, action));
            string res = DownloadString(Uri);
            if (res.StartsWith("<!DOCTYPE html", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new UnauthorizedAccessException();
            }
            return res;
        }

        public string GetDictionaryString(string action)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceDictionaryUrl, action));
            
            string res = DownloadString(Uri);
            if (res.StartsWith("<!DOCTYPE html", StringComparison.InvariantCultureIgnoreCase))
            {
                throw new UnauthorizedAccessException();
            }
            return res;
        }

        public byte[] DeleteValues(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl, action));
            return UploadValues(Uri, "DELETE", queries);
        }

        public byte[] DeleteValues2(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl2, action));
            return UploadValues(Uri, "DELETE", queries);
        }

        public byte[] DeleteValues3(string action, NameValueCollection queries)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl3, action));
            return UploadValues(Uri, "DELETE", queries);
        }

        public void DeleteDictionary(string action)
        {
            Uri =
                new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceDictionaryUrl,
                    action));
            var request = (HttpWebRequest) WebRequest.Create(Uri);

            request.Method = "DELETE";
            request.Timeout = Timeout;
            request.CookieContainer = CookieContainer;

            if (User.IsProxyEnable)
            {
                request.Proxy = User.Proxy;
                request.Proxy.Credentials = User.ProxyCredentials;
            }

            using (var response = (HttpWebResponse)request.GetResponse())
            {
                // Get the URL of the new page.
                //string location = response.GetResponseHeader("Location");
                // Close the previous response.
                response.Close();
                // Get the HTTP web response of the new page.
                /*using (FollowRedirection(location))
                {
                    
                }*/
                
            }
        }

        public byte[] GetData(string action)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceUrl, action));
            var data = DownloadData(Uri);
            return RemoveTrailingNulls(data);
        }

        public static byte[] RemoveTrailingNulls(byte[] data)
        {
            int i = data.Length - 1;
            while (data[i] == 0)
            {
                --i;
            }
            var newData = new byte[i + 1];
            Array.Copy(data, newData, i + 1);
            return newData;
        }

        public void MultipartFormData(string url, Dictionary<string, object> parameters)
        {
            const string formDataBoundary = "-----------------------------28947758029299";
            const string contentType = "multipart/form-data; boundary=" + formDataBoundary;

            // Creating HTTP web request.
            var request = (HttpWebRequest) WebRequest.Create(url);
            request.Method = "POST";
            request.Timeout = Timeout;
            request.ContentType = contentType;
            request.AllowAutoRedirect = false;
            request.AllowWriteStreamBuffering = true;
            request.CookieContainer = CookieContainer;
            if (User.IsProxyEnable)
            {
                request.Proxy = User.Proxy;
                request.Proxy.Credentials = User.ProxyCredentials;
            }
            // Get request stream.
            using (Stream requestStream = request.GetRequestStream())
            {
                // Writing to request stream.
                WriteMultipartFormData(requestStream, parameters, formDataBoundary);
            }

            using (var response = (HttpWebResponse) request.GetResponse())
            {
                var statusCode = (int) response.StatusCode;
                if (statusCode >= 300 && statusCode < 400)
                {
                    // Get the URL of the new page.
                    string location = response.GetResponseHeader("Location");
                    // Close the previous response.
                    response.Close();
                    // Get the HTTP web response of the new page.
                    using (FollowRedirection(location))
                    {
                    }
                }
            }
        }

        public void MultipartFormData3(string url, FileDetails file, string method = "POST")
        {
            // Creating HTTP web request.
            var request = (HttpWebRequest)WebRequest.Create(url);
            request.Method = method;
            request.Timeout = Timeout;
            request.AllowAutoRedirect = false;
            request.AllowWriteStreamBuffering = true;
            request.CookieContainer = CookieContainer;

            //Headers
            request.ContentType = file.CurrentVersion.ContentType;
            request.UserAgent = "WorkshareProtect";
            request.Headers.Add(HttpRequestHeader.Authorization, file.CurrentVersion.Authorization);
            request.Headers.Add("x-amz-date", file.CurrentVersion.AuthDate);
            request.Headers.Add("x-amz-server-side-encryption", file.CurrentVersion.Encryption);

            if (User.IsProxyEnable)
            {
                request.Proxy = User.Proxy;
                request.Proxy.Credentials = User.ProxyCredentials;
            }
            // Get request stream.
            using (Stream requestStream = request.GetRequestStream())
            {
                // Writing to request stream.
                WriteMultipartFormData3(requestStream, file);
            }

            using (var response = (HttpWebResponse) request.GetResponse())
            {
                var statusCode = (int) response.StatusCode;
                if (statusCode >= 300 && statusCode < 400)
                {

                    // Get the URL of the new page.
                    string location = response.GetResponseHeader("Location");
                    // Close the previous response.
                    response.Close();
                    // Get the HTTP web response of the new page.
                    using (FollowRedirection(location))
                    {

                    }
                }
            }
        }

        public void PutUserWDSValue(string action, string dicData)
        {
            Uri = new Uri(string.Format(CultureInfo.CurrentCulture, "{0}/{1}", PlatformService.ServiceDictionaryUrl, action));
            var request = (HttpWebRequest)WebRequest.Create(Uri);

            request.Method = "PUT";
            request.Timeout = Timeout;
            request.AllowAutoRedirect = false;
            request.AllowWriteStreamBuffering = true;
            request.CookieContainer = CookieContainer;
            request.ContentType = "application/json";

            if (User.IsProxyEnable)
            {
                request.Proxy = User.Proxy;
                request.Proxy.Credentials = User.ProxyCredentials;
            }

            var encoding = new ASCIIEncoding();
            byte[] data = encoding.GetBytes(dicData);

            // Get request stream.
            using (Stream requestStream = request.GetRequestStream())
            {
                // Writing to request stream.
                WritePutUserWDSValue(requestStream, data);
            }

            using (var response = (HttpWebResponse) request.GetResponse())
            {
                var statusCode = (int) response.StatusCode;
                if (statusCode >= 300 && statusCode < 400)
                {
                    // Get the URL of the new page.
                    string location = response.GetResponseHeader("Location");
                    // Close the previous response.
                    response.Close();
                    // Get the HTTP web response of the new page.
                    using (FollowRedirection(location))
                    {
                    }
                }
            }
        }

        public CookieContainer CookieContainer
        {
            get
            {
                return User.SessionCookies;
            }
            set
            {
                User.SessionCookies = value;
            }
        }
        public Uri Uri { get; set; }
        public UserDetails User { get; private set; }
        public int Timeout { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Common/WorkspaceNameConverter.cs
﻿using System;
using System.Windows.Data;

namespace Workshare.Components.Views.Common
{
    public class WorkspaceNameConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if (value is string)
            {
                return string.Format("Activity for the {0} on Workshare", value);
            }
            return "Activity for the workspace on Workshare";
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
<file_sep>/SharePoint/Common/VersionInfoBlock/AssemblyVersionInfoBlock.cs
using System;
using System.Reflection;
using System.Runtime.InteropServices;
// This common assembly info file is used by all assemblies to define version, etc.
// If you want to add a Assembly unique value, you must add a AssemblyInfo file
// to your project.

// When you add this file to new projects, you must 'Add existing file' and
// open it with the dropdown arrow with 'Link File'.  Otherwise it will copy
// the file to the local directory and it won't get updated.

[assembly: AssemblyInformationalVersion("1.0.0.0")]
[assembly: AssemblyVersion("1.0.0.0")]

#if !THIRD_PARTY_LIBRARY
[assembly: AssemblyProduct("Workshare SharePoint Integration")]
[assembly: AssemblyCompany("Workshare")]
[assembly: AssemblyCopyright("Copyright �1998-2013 Workshare")]
[assembly: AssemblyTrademark("")]
[assembly: AssemblyCulture("")]
#endif

[assembly: AssemblyFileVersion("0.0.0.0")]
[assembly: AssemblyConfiguration("")]
[assembly: AssemblyDelaySign(false)]
[assembly: AssemblyKeyName("")]

#if !_COMVISIBLE_DEFINED
[assembly: ComVisible(false)]
#endif

#if !_CLSCOMPLIANT_DEFINED
[assembly: CLSCompliant(true)]
#endif
<file_sep>/OpenText/src/Workshare.OpenText/CommandHelper.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Hummingbird.DM.Extensions.Interop.DOCSObjects;
using Workshare.Components;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using Workshare.OpenText.Concrete;
using Workshare.OpenText.Contrete;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.OpenText
{
    public static class CommandHelper
    {
        static readonly string SendMenuID = "WorkshareSend";
        static readonly string SyncMenuID = "WorkshareSync";

        public static WSOTMenuItem GetCommandName(IDocProfiles items)
        {
            if (Application.OTInstance.Presenter.IsAnyItemInProgress())
            {
                return null;
            }

            if (items != null && items.Count > 0)
            {
                bool IsSend = true;
                bool IsSync = true;
                
                foreach (IProfile prof in items)
                {
                    
                    prof.Fetch();

                    var SendInfo = (OTSyncInfo)OTSyncInfo.Parse(prof.Columns[Application.OTInstance.SENDINFO_FIELD].Value.ToString());

                    // send/sync operate allow 
                    if (prof.Columns["STATUS"].Value.ToString() == "0" // for any items if it not check out and not locked
                        || ((prof.Columns["STATUS"].Value.ToString() != "0" && string.Compare(Application.OTInstance.CurrentUser, HistoryHelper.GetLastCheckedOutUser(prof as Hummingbird.DM.Extensions.Interop.DECore.BCObject), StringComparison.InvariantCultureIgnoreCase) == 0) // if item is checked out/locked for current user
                        &&  string.Compare("FOLDER", prof.Columns["TYPE_ID"].Value.ToString(), StringComparison.InvariantCultureIgnoreCase) != 0) // and item is not a locked folder
                        )
                    {
                        if ((prof.Columns["STATUS"].Value.ToString() == "0" && string.Compare("FOLDER", prof.Columns["TYPE_ID"].Value.ToString(), StringComparison.InvariantCultureIgnoreCase) != 0) || SendInfo == null || SendInfo.DMSItemId != prof.DocNumber)
                        {
                            IsSync = false;
                        }
                        else
                        {
                            IsSend = false;
                        }
                    }
                    else
                    {
                        IsSync = IsSend = false;
                    }

                    if (!IsSync && !IsSend)
                    {
                        return null;
                    }
                }

                var mnu = new WSOTMenuItem() { Parent = "DOCSOPEN.DOCUMENT", InsertBefore = "DOCSOPEN.CheckOut" };
                if (IsSend)
                {
                    mnu.ID = SendMenuID;
                    mnu.Name = RES.STR_MENU_SEND;
                }
                else
                    if (IsSync)
                    {
                        mnu.ID = SyncMenuID;
                        mnu.Name = RES.STR_MENU_SYNC;
                    }
                return mnu;
            }
            else
            {
                return null;
            }
        }

        public static IEnumerable<IDMSItem> GetSelectedItems(IDocProfiles items)
        {
            var selected = new List<IDMSItem>();
            foreach (IProfile prof in items)
            {
                if (prof.CurrentVersion == null)
                {
                    selected.Add(new ManFolder(prof as IProject));
                }
                else
                {
                    selected.Add(new OTFile(prof));
                }
            }

            return selected;
        }

        public static void ExecuteMenu(IDocProfiles items, string mnuID)
        {
            if (!Application.OTInstance.Presenter.IsAnyItemInProgress())
            {
                // we should do it every time before execute menu in case of we cannot create ApplicationClass manually and cannot store it one time for all work in version 5.3.1
                if (items != null && items.Count > 0 && (string.Equals(mnuID, SendMenuID, StringComparison.InvariantCultureIgnoreCase) || string.Equals(mnuID, SyncMenuID, StringComparison.InvariantCultureIgnoreCase)))
                {
                    if (items[1].Library != null && items[1].Library.Application != null)
                    {
                        var pApp = items[1].Library.Application;
                        Application.OTInstance.ParentWindow = pApp.DefParentWindow;
                        Application.OTInstance.UserDST = pApp.DST;
                        Application.OTInstance.CurrentLibraryName = pApp.CurrentLibrary.Name;
                        Application.OTInstance.CurrentLibrary = pApp.CurrentLibrary;
                        Application.OTInstance.CurrentUser = pApp.CurrentLibrary.UserName;
                    }

                    if (string.Equals(mnuID, SendMenuID, StringComparison.InvariantCultureIgnoreCase))
                    {
                        Application.OTInstance.View.OnSendItemsClicked(new SendItemsClickedArgs(GetSelectedItems(items)));
                    }

                    if (string.Equals(mnuID, SyncMenuID, StringComparison.InvariantCultureIgnoreCase))
                    {
                        Application.OTInstance.View.OnSynchItemsClicked(new SyncItemsClickedArgs(GetSelectedItems(items).Select(p => new SyncItemInformation(p, ConflictOptions.None, ConflictVersionOptions.None))));
                    }
                }
            }
        }
    }

    public class WSOTMenuItem
    {
        public string Name { get; set; }
        public string ID { get; set; }
        public string InsertBefore { get; set; }
        public string Parent { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/UserControls/ActivityToViewOnlineVisibilityConverter.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Data;
using Workshare.Components.Views.TrueSyncDialog.VMs;

namespace Workshare.Components.Views.TrueSyncDialog.UserControls
{
    class ActivityToViewOnlineVisibilityConverter:IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            var activity = value as IFileActivityBaseVm;
            if (activity != null)
            {
                return string.IsNullOrEmpty(activity.ViewOnlineUrl) ? Visibility.Collapsed : Visibility.Visible;
            }
            return Visibility.Visible;
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Views/ModuleView.cs
﻿using System;
using System.Runtime.InteropServices;
using System.Windows.Interop;
using Workshare.Components.Presenter;
using Workshare.Components.Views;
using Workshare.Components.Views.ConflictResolver;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using Workshare.OpenText.Presenter;

namespace Workshare.OpenText.Views
{
    public class ModuleView: ModuleViewBase
    {

        public ModuleView(IWSIntegration integration)
            : base(integration)
        {
            Application.OTInstance.ParentChanged += OTInstance_ParentChanged;
        }

        void OTInstance_ParentChanged(object sender, EventArgs e)
        {
            if (progressWindow != null)
            {
                progressWindow.Dispatcher.BeginInvoke(new Action(() =>
                {
                    if (progressWindow.IsLoaded)
                    {
                        new WindowInteropHelper(progressWindow).Owner = MainWindowHandle;
                    }
                }));
            }
        }

        [DllImport("user32.dll", ExactSpelling = true, CharSet = CharSet.Auto)]
        public static extern IntPtr GetParent(IntPtr hWnd);

        public override ModulePresenterBase CreatePresenter(IWSIntegration integration)
        {
            return new ModulePresenter(this);
        }

        public override IntPtr ActivieWindowHandle
        {
            get
            {
                if (Application.OTInstance.ParentWindow != 0)
                {
                    var fromOT = new IntPtr(Application.OTInstance.ParentWindow);
                    var parent = GetParent(fromOT);
                    _MainWindowHandle = parent != IntPtr.Zero ? parent : fromOT;
                }
                return _MainWindowHandle;
            }
            set
            {
                _MainWindowHandle = value;
            }
        }

        internal ConflictOptions ShowConflictDialog(ConflictItemData wsFile, ConflictItemData localFile)
        {
            Logger.Write("ModuleView::ShowConflictDialog() START", Severity.Information);
            return (ConflictOptions)dispatcher.Invoke(new Func<ConflictOptions>(() =>
            {
                var dlg = new ConflictResolverWindow(wsFile, localFile, Properties.Resources.STR_CONFLICT_DLG_OPENTEXT_TITLE);
                SetMainAsParent(dlg);
                dlg.DisableOwner = true;
                dlg.ShowDialog();
                return dlg.Result;
            }));
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/Visitors/GetCeaseCollaborationActionsVisitor.cs
﻿using System.Collections.Generic;
using Workshare.Integration.Processor.Maps;

namespace Workshare.Integration.Processor
{
    public class GetCeaseCollaborationActionsVisitor : ItemMapVisitor
    {
        private CeaseCollaborationImportType _importAction;
        private CeaseCollaborationType _fileAction;

        public void Initialize(CeaseCollaborationImportType importAction, CeaseCollaborationType fileAction)
        {
            Result = new List<ItemMapActivityAction>();
            _importAction = importAction;
            _fileAction = fileAction;
        }

        public override void Visit(FileMap fileMap)
        {
            Result.Add(new CeaseCollaborationAction(fileMap.Id, _fileAction, _importAction));

        }

        public override void Visit(FolderMap folderMap)
        {
            Result.Add(new CeaseCollaborationAction(folderMap.Id, _fileAction, _importAction));
        }

        public List<ItemMapActivityAction> Result { get; private set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CheckOutDialog/CheckOutDilalogModel.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using Workshare.Components.Concrete;
using Workshare.Components.Views.Common;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using System.Reflection;

namespace Workshare.Components.Views.CheckOutDialog
{
    public class CheckOutDilalogModel : OwnViewModel
    {

        public CheckOutDilalogModel()
        {
            this.FileName = "a.doc";
            CheckOutCommand = new RelayCommand((p) =>
            {
                Result = CheckOutOptions.CheckOut;
                RaiseClose(true);
            });

            DontCheckOutCommand = new RelayCommand((p) =>
            {
                Result = CheckOutOptions.DontCheckOut;
                RaiseClose(true);
            });

            CancelCommand = new RelayCommand((p) =>
            {
                Result = CheckOutOptions.None;
                RaiseClose(false);
            });
        }

        public RelayCommand CheckOutCommand { get; set; }
        public RelayCommand DontCheckOutCommand { get; set; }
        public RelayCommand CancelCommand { get; set; }
        public IDMSFile File { get; set; }
        public string FileName
        {
            set
            {
                if (m_Filename != value)
                {
                    m_Filename = value;
                    this.PropertyHasChanged("FileName");
                }
            }

            get
            {
                return m_Filename;
            }
        }
        public string DialogTitle { get { return m_Filename; } }
        private string m_Filename = "";
        internal CheckOutOptions Result { get; set; }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/SendToWSCommand.cs
﻿using System;
using System.Linq;
using System.Runtime.InteropServices;
using Com.Interwoven.Worksite.iManExt;
using Workshare.Components;
using Workshare.Components.Helpers;
using Workshare.Components.Properties;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;


namespace Workshare.IManage
{
    
    public class SendToWSCommand : Command
    {
        public override string MenuText
        {
            get
            {
                return "Send to Workshare";
            }
            set
            {
                base.MenuText = value;
            }
        }

        public override object Bitmap
        {
            get
            {
                return Resources.workshare_sync_to.GetHbitmap();
            }
            set { }
        }

        public override string HelpText
        {
            get { return MenuText + "\nSend item"; }
            set { }
        }

        public override void ExecuteAction()
        {
            var contextItems = GetContextItems();
            if (!contextItems.Any())
            {
                return;
            }

            if (!Application.iManInstance.Presenter.LoginIfNeeded())
            {
                return;
            }
            Application.iManInstance.ClientType = GetClientType();
            var notLinkedItemsCount = contextItems.Count(p => syncService.GetSyncInfo(p, false) == null);
            var allItemsAreNotLinked = notLinkedItemsCount == contextItems.Count;
            var someItemsNotLinked = notLinkedItemsCount > 0;
            var someCheckedOutToOther = contextItems.Any(a => a.IsCheckedOutToOtherUser());
            var hasPermissions = contextItems.All(p => p.DoesUserHavePermissions(Permissions.EditItem));
            var anyTaskAlreadyInProgress = Application.iManInstance.Presenter.IsAnyItemInProgress();

            var canSend = !someCheckedOutToOther
                          && allItemsAreNotLinked
                          && hasPermissions
                          && !anyTaskAlreadyInProgress;
            if (canSend)
            {
                Application.iManInstance.View.OnSendItemsClicked(new SendItemsClickedArgs(contextItems));
            }
            else if (!someItemsNotLinked)
            {
                if (contextItems.HasOnlyOneFile())
                {
                     ShowError(
                        new BaseException(Resources.SendToWSCommand_ExecuteAction_Unable_to_send,
                           Resources.STR_ERROR_TEXT_File_is_sent_to_Workshare), contextItems.FirstOrDefault());
                }
                else if(contextItems.HasOnlyOneFolder())
                {
                    ShowError(
                        new BaseException(Resources.SendToWSCommand_ExecuteAction_Unable_to_send,
                          Resources.STR_ERROR_TEXT_Folder_is_sent_to_Workshare), contextItems.FirstOrDefault());
                }
                else
                {
                    ShowError(
                        new BaseException(Resources.SendToWSCommand_ExecuteAction_Unable_to_send,
                            Resources.STR_ExecuteAction_All_items_are_sent_to_Workshare), contextItems.FirstOrDefault());
                }
            }
            else if (!allItemsAreNotLinked)
            {
                ShowError(new BaseException(Resources.SendToWSCommand_ExecuteAction_Unable_to_send, Resources.STR_ExecuteAction_Some_items_are_already_sent_to_Workshare), contextItems.FirstOrDefault());
            }
            else if (anyTaskAlreadyInProgress)
            {
                ShowError(new BaseException(Resources.SendToWSCommand_ExecuteAction_Unable_to_send, Resources.STR_ExecuteAction_Some_another_task_is_already_in_progress), contextItems.FirstOrDefault());
            }
            else if (someCheckedOutToOther)
            {
                ShowErrors(new BaseException(Resources.SendToWSCommand_ExecuteAction_Unable_to_send, Resources.STR_ExecuteAction_File_is_checked_out_to_another_users), contextItems.Where(i => i.IsCheckedOutToOtherUser()).ToList());
            }
            else
            {
                ShowError(new DMSUnAuthorizedException(),contextItems.FirstOrDefault());
            }
        }
    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("AFDBB083-A23B-43F1-9005-0E4080668928")]
    [ComVisible(true)]
    public class DocumentSendToWSCommand : SendToWSCommand
    {
        public override string HelpText
        {
            get
            {
                return "Send document to Workshare\nSend to Workshare";
            }
            set
            {
                base.HelpText = value;
            }
        }

        public override int Status
        {
            get
            {
                //Context.OfType<object>().ToList().ForEach(p => System.Diagnostics.Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                bool IsAnyDocumentSelected = false;
                try
                {
                    var items = GetContextItems();
                    if (items.Count == 1 && (items[0] is Workshare.Integration.Interfaces.IDMSFolder))
                    {
                        var fld = items[0] as Workshare.Integration.Interfaces.IDMSFolder;
                        IsAnyDocumentSelected = fld.Files.Count() > 0;
                    }
                    else
                    {
                        IsAnyDocumentSelected = items.OfType<Workshare.Integration.Interfaces.IDMSFile>().Any();
                    }
                }
                catch
                { }

                return (int)((IsAnyDocumentSelected && !Application.iManInstance.Presenter.IsAnyItemInProgress() && IsAnyServerAvailable()) ? CommandStatus.nrActiveCommand : CommandStatus.nrGrayedCommand);
            }
            set
            {

            }
        }

    }

    [ClassInterface(ClassInterfaceType.None)]
    [Guid("C990BEBD-D0F4-4363-B869-6EA4E129462D")]
    [ComVisible(true)]
    public class FolderSendToWSCommand : SendToWSCommand
    {
        public override string HelpText
        {
            get
            {
                return "Send folder to Workshare\nSend to Workshare";
            }
            set
            {
                base.HelpText = value;
            }
        }
    }
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/Exceptions.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Script.Serialization;
using Microsoft.SharePoint;

namespace WorkshareCloud.Common
{
    public class ItemException
    {
        public string Name
        {
            get
            {
                return Item != null ? SPItem.Name : "";
            }
        }

        public string Url
        {
            get
            {
                return Item != null ? SPItem.Url : "";
            }
        }

        public int ID
        {
            get
            {
                return Item != null ? SPItem.ID : -1;
            }
        }

        public Guid ParentListID
        {
            get
            {
                return Item != null ? SPItem.ParentList.ID : Guid.Empty;
            }
        }

        public object Item
        {
            set;
            get;
        }

        public Exception Error
        {
            set;
            get;
        }

        public SPListItem SPItem
        {
            get
            {
                return Item as SPListItem;
            }
        }
    }

    public class ItemsErrorsCollection : IDisposable
    {
        List<ItemException> m_errors = new List<ItemException>();

        public void Add(object item, Exception ex)
        {
            m_errors.Add(new ItemException()
            {
                Item = item,
                Error = ex
            });
        }

        void Add(ItemException ex)
        {
            m_errors.Add(ex);
        }

        public void Clear()
        {
            m_errors.Clear();
        }

        public void AddRange(ItemsErrorsCollection errors)
        {
            errors.AsQueryble().ToList().ForEach(p => this.Add(p));
        }

        public IQueryable<ItemException> AsQueryble()
        {
            return m_errors.AsQueryable();
        }

        public int Count
        {
            get
            {
                return m_errors.Count;
            }
        }

        public void Check()
        {
            if (this.Count > 0)
            {
                throw new ListProcessException(this);
            }
        }

        public void Dispose()
        {
            Check();
        }
    }

    interface IData
    {
        string ToJSON();
        int Code { get; }
    }

    public class ListProcessException : BaseException
    {
        const int FOLDER_NOT_FOUND_ID = -1;
        public ItemsErrorsCollection errorList;
        public ListProcessException(ItemsErrorsCollection errList)
            : base(Properties.Resources.STR_ERROR_HAPPEN, "")
        {
            errorList = errList;
        }

        public override string ToJSON()
        {
            var res = (errorList ?? new ItemsErrorsCollection()).AsQueryble()
                //.Where(i => i.SPItem != null)
                .Select(p =>
                     new
                     {
                         name = p.Name,
                         url = p.Url,
                         error = p.Error.Message,
                         caption = (p.Error is BaseException)?((BaseException)p.Error).Caption:"",
                         code = (p.Error is IData) ? ((IData)p.Error).Code : 0,
                         itemId = p.ID,
                         listGuid = "{" + p.ParentListID + "}",
                         folderId = (p.Error is CloudItemNotFound) ? ((((CloudItemNotFound)p.Error).IsParentFolderExists) ? ((CloudItemNotFound)p.Error).DestinationFolderID : FOLDER_NOT_FOUND_ID) : FOLDER_NOT_FOUND_ID,
                         data = (p.Error is IData) ? ((IData)p.Error).ToJSON() : ""
                     }
                );
            return new JavaScriptSerializer().Serialize(res);
        }
    }

    public class BaseException : Exception, IData
    {
        public BaseException()
            : base()
        { }

        public BaseException(string caption, string msg)
            : base(msg)
        {
            Caption = caption;
        }

        public BaseException(string caption, string msg, Exception ex)
            : base(msg, ex)
        {
            Caption = caption;
        }

        public string Caption { get; private set; }

        public virtual string ToJSON()
        { 
            return ""; 
        }

        public virtual int Code { get { return 0; } }
    }

    public class CloudFieldNotFound : BaseException
    {
        public CloudFieldNotFound()
            : base(Properties.Resources.STR_ERROR, Properties.Resources.STR_VIEWNOTINITIALIZED_TEXT)
        {
        }
        public CloudFieldNotFound(string message)
            : base(Properties.Resources.STR_ERROR, message)
        {
        }

    }
    public class OfflineException : BaseException
    {
        public OfflineException(string message, Exception inner)
            : base(Properties.Resources.STR_CONNECTION_ERROR_CAPTION, message, inner)
        {
        }
    }
    
    public class FileConflictException : BaseException
    {
        public DateTime fileSP;
        public DateTime fileCloud;
        public string filenameSP, filenameCloud;
        public int fileid;
        public Guid listguid;
        string userCloud, userSP;
        public FileConflictException(string f_name_sp, string f_name_cloud, int f_id, Guid listID,  DateTime fileOnSP, DateTime fileOnCloud, string user_sp, string user_cloud)
            : base(Properties.Resources.STR_FILECONFLICT_CAPTION, Properties.Resources.STR_FILECONFLICT_TEXT)
        {
            filenameSP = f_name_sp;
            filenameCloud = f_name_cloud;
            listguid = listID;
            userCloud = user_cloud;
            userSP = user_sp;
            fileid = f_id;
            fileSP = fileOnSP;
            fileCloud = fileOnCloud;
        }

        public override string ToJSON()
        {
            return new JavaScriptSerializer().Serialize(new 
            {
                spModified=fileSP.ToString(),
                wsModified=fileCloud.ToString(),
                spName = filenameSP,
                wsName = filenameCloud,
                id=fileid,
                listGUID=listguid.ToString(),
                spUser=userSP,
                wsUser=userCloud
            });
        }

        public override int Code
        {
            get { return 503; }
        }
    }

    public class BadRequest : BaseException
    {

        public BadRequest(string inputRequest)
            : base(Properties.Resources.STR_ERROR, string.Format("BadRequest. Additional Data:\n{0}", inputRequest))
        {
        }
    }

    public class ItemNotFound : BaseException
    {
        public ItemNotFound()
            : base(Properties.Resources.STR_LOCALFILENOTFOUND_CAPTION, Properties.Resources.STR_LOCALFILENOTFOUND_TEXT)
        {
        }

        public ItemNotFound(Exception inner)
            : base(Properties.Resources.STR_LOCALFILENOTFOUND_CAPTION, Properties.Resources.STR_LOCALFILENOTFOUND_TEXT, inner)
        {
        }
        public override string ToJSON()
        {
            return new JavaScriptSerializer().Serialize(new
            {
                Description = Properties.Resources.STR_LOCALFILENOTFOUND_TEXT
            });
        }

        public override int Code
        {
            get { return 310; }
        }
    }

    public class CloudItemNotFound : BaseException
    {
        public bool IsParentFolderExists;
        public int DestinationFolderID;
        public CloudItemNotFound(string msg, int destFolderId, bool folderExists)
            : base(Properties.Resources.STR_UNABLE_SYNC, msg)
        {
            DestinationFolderID = destFolderId;
            IsParentFolderExists = folderExists;
        }

        public override string ToJSON()
        {
            return new JavaScriptSerializer().Serialize(new
            {
                Message
            });
        }

        public override int Code
        {
            get { return 406; }
        }
    }

    public class CloudFileNotFound : CloudItemNotFound
    {
        public CloudFileNotFound(int destFolderId, bool folderExists)
            : base(Properties.Resources.STR_CLOUDFILENOTFOUND, destFolderId, folderExists)
        { }
    }

    public class CloudFolderNotFound : CloudItemNotFound
    {
        public CloudFolderNotFound(int destFolderId, bool folderExists)
            : base(Properties.Resources.STR_CLOUDFOLDERNOTFOUND, destFolderId, folderExists)
        { }
    }

    public class CloudFolderAccessDenied : BaseException
    {
        public CloudFolderAccessDenied(string Caption, string Text)
            : base(Caption, Text)
        { }

        public CloudFolderAccessDenied(string Caption, string Text, Exception ex)
            : base(Caption, Text, ex)
        { }
    }


    public class VersionDoesNotExist : BaseException
    { }

    public class FileCheckoutedToAnotherUser : BaseException
    {
        public FileCheckoutedToAnotherUser()
            : base(Properties.Resources.STR_UNABLE_SEND, Properties.Resources.STR_FILEISCHECKEDOUTBYANOTHERUSER_TEXT)
        { }
    }

    public class AlreadySentException : BaseException
    {
        public AlreadySentException()
            : base(Properties.Resources.STR_FILE_ALREADY_SENT, "")
        { }
    }

     public class CloudUnAuthorized : BaseException
    {
         public CloudUnAuthorized()
             : base(Properties.Resources.STR_WRONGAUTH_CAPTION, Properties.Resources.STR_WRONGAUTH_TEXT)
        { }
         public CloudUnAuthorized(Exception ex)
             : base(Properties.Resources.STR_WRONGAUTH_CAPTION, Properties.Resources.STR_WRONGAUTH_TEXT, ex)
         { }

    }

}

<file_sep>/WSComponents/src/WSIntegration/WsIntegrationModule.cs
﻿using Microsoft.Practices.Unity;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.DmsItems.Visitors;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Maps.Visitors;
using Workshare.Integration.SyncInfo;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration
{
    public class WsIntegrationModule : ModuleBase
    {
        protected override void Initialize()
        {
            base.Initialize();
            this.Container.RegisterType<WsProxy>();            
            this.Container.RegisterType<Processor.Processor>();
            this.Container.RegisterType<ActivityFinder>();
            this.Container.RegisterType<ScanVisitor>();
            this.Container.RegisterType<ProcessVisitor>();
            this.Container.RegisterType<MapController>();
            this.Container.RegisterType<MapAnylizer>();
            this.Container.RegisterType<TreePathFinder>();
            this.Container.RegisterType<Processor.Changes.Visitors.ChangesDetector>();
            this.Container.RegisterType<ISyncInfoFactory, Factory>();
        }
    }

}
<file_sep>/OpenText/src/Workshare.OpenText/Concrete/OTItemID.cs
﻿using Hummingbird.DM.Extensions.Interop.DOCSObjects;
using System;
using Workshare.Integration.Interfaces;

namespace Workshare.OpenText.Contrete
{
    class ManItemID : IDMSItemID
    {
        int obj_ID;
        public ManItemID(IProfile doc)
        {
            if (doc!=null)
            {
                obj_ID = doc.DocNumber;
            }
            else
            {
                throw new ArgumentException("doc");
            }
        }

        public ManItemID(IProject fld)
        {
            if (fld != null)
            {
                obj_ID = fld.ProjectID;
            }
            else
            {
                throw new ArgumentException("folder");
            }
        }

        public bool EqualTo(IDMSItemID obj)
        {
            if (obj is ManItemID)
            {
                return ((ManItemID)obj).obj_ID == this.obj_ID;
            }
            return false;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncUploadFilesDialog/VMs/FileResultsVm.cs
﻿using System.Collections.ObjectModel;
using Workshare.Integration.Processor.Maps;

namespace Workshare.Components.Views.TrueSyncUploadFilesDialog.VMs
{
    public class ParentScan
    {
        public SummaryProcessResult Scan { set; get; }
        public ObservableCollection<FileUploadActivityVm> Activities { set; get; }
    }
}
<file_sep>/WSComponents/src/WSIntegration/SyncInfo/FolderSyncInfo.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Web.Script.Serialization;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;

namespace Workshare.Integration.SyncInfo
{

    class SendDataInfo : ISendDataInfo
    {
        List<int> _items = new List<int>();

        public string DataType
        {
            get { return "FolderSendDataInfo"; }
            set { }
        }

        public static ISendDataInfo Parse(string value)
        {
            try
            {
                if (string.IsNullOrEmpty(value)) return Create();
                var ser = new JavaScriptSerializer();
                return ser.Deserialize<SendDataInfo>(value);
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                return null;
            }
        }

        public override string ToString()
        {
            var ser = new JavaScriptSerializer();
            return ser.Serialize(this);
        }

        public static ISendDataInfo Create()
        {
            return new SendDataInfo();
        }

        public string FolderID
        {
            get;
            set;
        }

        public List<int> Items
        {
            get
            {
                return _items;
            }
            set
            {
                _items = value;
            }
        }
    }

    class FolderSyncInfo:ISyncInfo
    {
        public FolderSyncInfo()
        {
        }

        public string DataType
        {
            get { return "FolderSyncInfo"; }
            set { }
        }

        public int ParentId
        {
            get;
            set;
        }

        public int LastUploadedDmsVerNum
        {
            get;
            set;
        }

        public int LastImportedWsVerId
        {
            get;
            set;
        }

        public int ItemId
        {
            get;
            set;
        }

        public string DMSItemId
        {
            get;
            set;
        }

        public string Modified
        {
            get;
            set;
        }

        public string ActivityId
        {
            get;
            set;
        }

        public List<IVersionSyncInfo> vInfos
        {
            get { return new List<IVersionSyncInfo>(); }
            set { }
        }

        public List<IVersionSyncInfo> GetvInfos()
        {
            return new List<IVersionSyncInfo>();
        }

        public void AddVInfo(IVersionSyncInfo info)
        {
         
        }

        public override string ToString()
        {
            var ser = new JavaScriptSerializer();
            return ser.Serialize(this);
        }

        public static FolderSyncInfo Parse(string value)
        {
            try
            {
                if (string.IsNullOrEmpty(value)) return null;
                var ser = new JavaScriptSerializer();
                return ser.Deserialize<FolderSyncInfo>(value);
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                return null;
            }
        }
        
    }
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/Extensions.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;
using WorksharePlatform;
using System.Xml.Linq;

namespace WorkshareCloud.Common
{
    public static class Extensions
    {
        public static bool GuidTryParse(string stringGuid, out Guid trueGuid)
        {
            try
            {
                trueGuid = new Guid(stringGuid);
                return true;
            }
            catch (Exception)
            {
                trueGuid = Guid.Empty; return false;
            }
        }
    }

    public static class AuditExtensions
    {
        const string SOURCE_NAME = "WorkshareCloud";

        static string getAuditString(string _event, string _message)
        {
            return string.Format("Date: {0} || Event: {1} || Message: {2}", DateTime.Now.ToString("MMM/d/yyyy"), _event, _message); 
        }

        static string getSendData(FolderDetails folder, FolderMembers members, string filename, string fileurl)
        {
            string mails = "";
            members.Members.Select(x => x.Email + "; ").ToList().ForEach(x => mails += x);
            return getAuditString("Sending", string.Format("Folder: ID - {0}, Name - {1}, Members - {2}, FileName - {3}, File URL - {4}", folder.Id.ToString(), folder.Name, mails, filename, fileurl));
        }

        static string getUpdateData(SPList list)
        {
            return getAuditString("Updating",string.Format("List title - {0}", list.Title));
        }

        static string getSyncData(SPListItem item, FileDetails file)
        {
            return getAuditString("Synchronization", string.Format("SharePoint file URL - {0}, Workshare file ID - {1}, Workshare file name - {2},  Workshare folder ID - {3}", item.Url, file.Id.ToString(), file.Name, file.FolderId.ToString()));
        }

        static string getSyncedData(SPListItem item, FileDetails file)
        {

            return getAuditString("File was added to SharePoint", string.Format(" Sharepoint file URL - {0}, Workshare file ID - {1}, Workshare file name - {2}, Workshare folder ID - {3}", item.Url, file.Id.ToString(), file.Name, file.FolderId.ToString()));
        }

        static string getUnSyncData(SPListItem item, string reason, FileDetails file)
        {

            return getAuditString("Stop Synchronization", string.Format("SharePoint file URL - {0}, file ID - {1}, Reason: {2}, User who deleted - {3}", item.Url, file.Id.ToString(), reason, file.Updater.Email));
        }

        static string getUnSyncData(SPListItem item, string reason)
        {

            return getAuditString("Stop Synchronization", string.Format("SharePoint file URL - {0}, Reason: {1}, ", item.Url, reason));
        }

        public static void WriteItemSent(this SPAudit audit, ICollection<SPListItem> items, FolderDetails folder, FolderMembers members)
        {
            try
            {
                if (audit != null)
                {
                    foreach (var item in items)
                    {
                        audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getSendData(folder, members, item.Name, item.Url));
                    }
                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }
        public static void WriteItemSent(this SPAudit audit, SPListItem item, FolderDetails folder, FolderMembers members)
        {
            try
            {
                if (audit != null)
                {
                    audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getSendData(folder, members, item.Name, item.Url));
                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }
        public static void WriteItemSync(this SPAudit audit, SPListItem item, FileDetails file)
        {
            try
            {
                if (audit != null)
                {
                    audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getSyncData(item, file));

                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }
        public static void WriteItemSynced(this SPAudit audit, SPListItem item, FileDetails file)
        {
            try
            {
                if (audit != null)
                {
                    audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getSyncedData(item, file));

                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }

        public static void WriteItemUpdate(this SPAudit audit, SPList list)
        {
            try
            {
                if (audit != null)
                {
                    audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getUpdateData(list));
                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }
        public static void WriteItemStopSync(this SPAudit audit, SPListItem item, string reason, FileDetails file)
        {
            try
            {
                if (audit != null)
                {
                    audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getUnSyncData(item, reason, file));
                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }

        public static void WriteItemStopSync(this SPAudit audit, SPListItem item, string reason)
        {
            try
            {
                if (audit != null)
                {
                    audit.WriteAuditEvent(SPAuditEventType.Custom, SOURCE_NAME, getUnSyncData(item, reason));
                }
            }
            catch (Exception ex)
            { Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.High, Logging.Category.CloudService); }
        }

    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Application.cs
﻿using System;
using Hummingbird.DM.Extensions.Interop.DOCSObjects;
using Hummingbird.DM.Server.Interop.PCDClient;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Interfaces;
using Workshare.Integration.Interfaces;
using Workshare.OpenText.Integration;
using Workshare.OpenText.Views;

namespace Workshare.OpenText
{
    class Application : WSApplication
    {

        public override string APP_CODE { get { return "Workshare-OpenText"; } }
        public readonly string DATASTORE_FIELD = "WS_DATAINFO";
        public readonly string SENDINFO_FIELD = "WS_SENDINFO";

        //public static IApplication _app;

        Application():base()
        {
            WorksharePlatform.PlatformService.Host = WorksharePlatform.PlatformService.MY_SERVER;
            WorksharePlatform.PlatformService.UseHostFromRegistry = true;
        }

        public static Application OTInstance
        {
            get
            {
                if (Instance == null)
                {
                    Instance = new Application();
                }
                return Instance as Application;
            }
        }

        public string UserDST
        {
            get;
            set;
        }

        public string CurrentUser
        {
            get;
            set;
        }
        public string CurrentLibraryName
        {
            get;
            set;
        }
        ILibrary _currentLib = null;
        public ILibrary CurrentLibrary
        {
            get
            {
                return _currentLib;
            }
            set 
            {
                _currentLib = value;
            }
        }

        public string GetItemName(string itemName)
        {

            int ver = 1;
            string newName = itemName;
            PCDSearch s = new PCDSearch();
            s.SetDST(UserDST);
            s.SetSearchObject("def_qbe");
            s.AddSearchLib(CurrentLibraryName);
            s.AddReturnProperty("docname");
            s.AddReturnProperty("docnum");

            int res = s.AddSearchCriteria("DOCNAME", newName);
            res = s.Execute();
            while (s.GetRowsFound() > 0)
            {
                s.ReleaseResults();
                newName = itemName+"_"+ver.ToString();
                ver++;
                s.AddSearchCriteria("DOCNAME", newName);
                s.Execute();
            }

            return newName;
        }

        private string GetCompatibleFileExtension(string fext)
        {
            string res = fext.ToUpper().Replace(".", "");
            if (res == "DOCX" || res == "XLSX" || res == "PPTX" || res == "VSDX" || res =="MPPX")
            {
                res = res.Substring(0, 3);
            }
            return res;
        }

        private readonly string[] imageFormats = { "BMP", "ICO", "JPG", "JPEG", "GIF", "TIFF", "PNG", "TIF", "WMF", "EMF" };

        public string GetDocClassByFileExtension(string fext)
        {
            string ext = GetCompatibleFileExtension(fext);
            /*if (imageFormats.Contains(ext))
            {
                return "IMG";
            }
            else
            {
                return "DOC";
            }*/
            return "DEFAULT";
        }

        public string GetAppIDByFileExtension(string fext, ILibrary lib)
        {
            string ext = GetCompatibleFileExtension(fext);

            IApplications apps = lib.AppInformation;
            for (int i = 1; i<= apps.Count; i++)
            {
                IAppInfo info = apps[i];
                if (string.Compare(info.DefaultExtension, ext, StringComparison.InvariantCultureIgnoreCase) == 0)
                {
                    return info.ID;
                }
            }
            return "";
        }

        int _ParentWindow = 0;
        public event EventHandler ParentChanged;
        public int ParentWindow
        {
            get { return _ParentWindow; }
            set
            {
                if(_ParentWindow!=value)
                {
                    _ParentWindow = value;
                    if (ParentChanged != null)
                    {
                        ParentChanged(null, EventArgs.Empty);
                    }
                }
            }

        }

        private IModuleView _view;
        public override IModuleView View
        {
            get
            {
                if (_view == null)
                {
                    _view = new ModuleView(Application.OTInstance.Integration);

                }
                return _view;
            }
            set { _view = value; }
        }

        public override IWSIntegration Integration
        {
            get
            {
                if (_integration == null)
                {
                    _integration = new WorkshareIntegration(this.AuthProvider);
                }
                return _integration;
            }
        }

        public override Workshare.Integration.Modularity.ModuleBase Module
        {
            get { throw new NotImplementedException(); }
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.Integration/WorkshareIntegration.cs
﻿//#define SLEEP 
using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.IO;
using System.Linq;
using System.Net;
using System.Runtime.InteropServices;
using System.Text;
using Workshare.Components;
using Workshare.Components.Exceptions;
using Workshare.Components.Extensions;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Integration
{
    public class WorkshareIntegration : WSIntegrationBase
    {

        #region public

        public event EventHandler<ItemAddedFromWSArgs> ItemAddedFromWS;

        public event EventHandler<ItemSentArgs> ItemSentToWS;

        public event EventHandler<ItemUpdatedLocallyArgs> ItemUpdatedLocally;

        public event EventHandler<ItemUpdatedOnWSArgs> ItemUpdatedOnWS;

        public WorkshareIntegration(IAuthProvider authProvider)
        {
            ServicePointManager.DefaultConnectionLimit = int.MaxValue;//TODO remove this line. fix problem with multiple files uploading
            m_authProvider = authProvider;
        }

        public override void SyncItems(IEnumerable<SyncItemInformation> localItems, OperationContext context)
        {
            if (localItems.Any())
            {
                using (var errorlist = new ItemsErrorsCollection(context))
                {
                    var user = m_authProvider.CheckIfAuth();

                    foreach (SyncItemInformation item in localItems)
                    {
                        SafeFuncCall(errorlist, item.item, new ExceptionListSignal() { IsAll = true, IsList = true }, Operations.Sync, () =>
                        {
                            if (item.item is IDMSFolder)
                            {
                                SyncFolder((item.item as IDMSFolder), user, context);
                            }
                            else if (item.item is IDMSFile)
                            {
                                SyncFile((item.item as IDMSFile), item.syncOption, user, context);
                            }
                        });
                    }
                }
            }
        }

        public override void SendItems(IEnumerable<IDMSItem> localItems, FolderDetails folder, OperationContext args)
        {
#if SLEEP
            Thread.Sleep(5000);
#endif
            SendItems(localItems, folder.Id, args);
        }

        public override void SendItems(IEnumerable<IDMSItem> localItems, int folderId, OperationContext context)
        {
#if SLEEP
            Thread.Sleep(5000);
#endif
            using (var errorlist = new ItemsErrorsCollection(context))
            {
                try
                {
                    var user = m_authProvider.CheckIfAuth();
                    SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsAll = true, IsList = true, FolderError = true }, Operations.Send, () =>
                    {
                        if (!CheckFolderExistsWhenSendOrThrow(user, folderId, -1))
                        {
                            throw new CloudFolderNotFound(RES.STR_UNABLE_SEND);
                        }
                        if (localItems.Any())
                        {

                            foreach (IDMSItem item in localItems)
                            {
                                SafeFuncCall(errorlist, item, new ExceptionListSignal() { IsAll = true, IsList = true, FolderError = true }, Operations.Send, () =>
                                {
                                    if (item is IDMSFolder)
                                    {
                                        SendFolder((IDMSFolder)item, folderId, user, context, null);
                                    }
                                    else if (item is IDMSFile)
                                    {
                                        SendFile((IDMSFile)item, folderId, user, context);
                                    }
                                });
                            }

                            errorlist.Check();
                        }
                    });
                }
                catch (CloudFolderNotFound ex)
                {
                    SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsAll = true, IsList = true }, Operations.Send, () =>
                    {
                        if (localItems.Any())
                        {
                            var user = m_authProvider.CheckIfAuth();
                            foreach (IDMSItem item in localItems)
                            {
                                SafeFuncCall(errorlist, item, new ExceptionListSignal() { IsAll = true, IsList = true }, Operations.Send, () =>
                                {
                                    if (item is IDMSFolder)
                                    {
                                        SyncFolder((IDMSFolder)item, user, context, true);
                                    }
                                    else if (item is IDMSFile)
                                    {
                                        ((IDMSFile)item).UpdateSyncInfo(null, true);
                                    }
                                });
                            }
                        }
                    });
                    errorlist.Clear();
                    errorlist.Add(null, ex);
                    errorlist.Check();
                }
            }
        }

        #endregion

        

        #region privates

        

        void RaiseItemSent(ItemSentArgs args)
        {
            if (ItemSentToWS != null)
            {
                ItemSentToWS(this, args);
            }
        }
        void RaiseItemUpdatedLocally(ItemUpdatedLocallyArgs args)
        {
            if (ItemUpdatedLocally != null)
            {
                ItemUpdatedLocally(this, args);
            }
        }
        void RaiseItemUpdatedOnWS(ItemUpdatedOnWSArgs args)
        {
            if (ItemUpdatedOnWS != null)
            {
                ItemUpdatedOnWS(this, args);
            }
        }
        void RaiseItemAddedFromWS(ItemAddedFromWSArgs args)
        {
            if (ItemAddedFromWS != null)
            {
                ItemAddedFromWS(this, args);
            }
        }



        #region Sync

        private void SyncFilesInFolder(IDMSFolder folder, List<FileDetails> filesOnCloud, UserDetails user, OperationContext context)
        {
            using (var errorlist = new ItemsErrorsCollection(context))
            {
                // sync existing files
                List<int> localFiles = new List<int>();
                foreach (IDMSFile item in folder.Files)
                {
                    var synhInfo = item.GetSyncInfo();
                    if (synhInfo != null)
                    {
                        localFiles.Add(synhInfo.ItemId);
                    }
                    SafeFuncCall(errorlist, item, new ExceptionListSignal() { IsAll = true, IsWeb = true }, Operations.Sync, () =>
                        {
                            SyncFile(item, ConflictOptions.None, user, context);
                        });
                }

                List<int> addedFiles = new List<int>();
                var processedFiles = folder.GetSendDataInfo();
                foreach (var fileID in filesOnCloud.Select(x => x.Id).Except(localFiles))
                {
                    if (!processedFiles.Contains(fileID))
                    {
                        SafeFuncCall(errorlist, folder, new ExceptionListSignal() { IsAll = true, IsWeb = true, FileError = true}, Operations.Sync, () =>
                        {
                            FileDetails cloudFile = filesOnCloud.Where(x => x.Id == fileID).First();
                            PlatformService.GetVersionDetails(user, cloudFile);
                            cloudFile.Data = PlatformService.DownloadFile(user, fileID);
                            IDMSFile newFile = folder.AddFile(cloudFile);
                            newFile.Description = cloudFile.FriendlyName;
                            newFile.OnAfterSync(context);
                            RaiseItemAddedFromWS(new ItemAddedFromWSArgs(newFile));
                            addedFiles.Add(cloudFile.Id);
                        });
                    }
                }
                folder.UpdateSendDataInfo(addedFiles);
            }
        }

        private void SyncSubFolderInFolder(IDMSFolder folder, IEnumerable<FolderDetails> foldersOnCloud, UserDetails user, OperationContext context)
        {
            using (var errorlist = new ItemsErrorsCollection(context))
            {
                // sync existing folders
                Dictionary<int, string> folderOnSP = new Dictionary<int, string>();
                foreach (IDMSFolder subFolder in folder.SubFolders)
                {
                    SafeFuncCall(errorlist, subFolder, new ExceptionListSignal() { IsAll = true, IsList = true, IsWeb = true }, Operations.Sync, () =>
                            {
                                SyncFolder(subFolder, user, context);
                            });

                    var synhInfo = subFolder.GetSyncInfo();
                    if (synhInfo != null)
                    {
                        folderOnSP.Add(synhInfo.ItemId, subFolder.Name);
                    }
                }

                // add new folders from cloud to SP and sync it
                List<int> addedFolders = new List<int>();
                var processedItems = folder.GetSendDataInfo();
                var newFolders = foldersOnCloud.Select(f => f.Id).Except(folderOnSP.Select(x => x.Key));
                foreach (var folderID in newFolders)
                {
                    if (!processedItems.Contains(folderID))
                    {
                        SafeFuncCall(errorlist, folder, new ExceptionListSignal() { IsAll = true, IsList = true, IsWeb = true }, Operations.Sync, () =>
                        {
                            var cloudFolder = foldersOnCloud.Where(x => x.Id == folderID).First();
                            var localsubFolder = folder.AddSubFolder(cloudFolder);

                            RaiseItemAddedFromWS(new ItemAddedFromWSArgs(folder));
                            addedFolders.Add(cloudFolder.Id);
                            SyncFolder(localsubFolder, user, context);
                        });
                    }
                }
                folder.UpdateSendDataInfo(addedFolders);
            }

        }

        private void SyncFolder(IDMSFolder folder, UserDetails user, OperationContext context, bool ClearFieldData = false)
        {
            using (var errorlist = new ItemsErrorsCollection(context))
            {

                SafeFuncCall(errorlist, folder, new ExceptionListSignal() { IsWeb = true }, Operations.Sync, () =>
                {
                    var synhInfo = folder.GetSyncInfo();
                    if (synhInfo != null)
                    {
                        if (!ClearFieldData && CheckFolderExistsWhenSyncOrThrow(user, synhInfo.ItemId, synhInfo.ParentFolderId))
                        {
                            SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsList = true }, Operations.Sync, () =>
                            {
                                SyncFilesInFolder(folder, PlatformService.GetFiles(user, synhInfo.ItemId), user, context);
                            });

                            SafeFuncCall(errorlist, null, new ExceptionListSignal() { IsList = true }, Operations.Sync, () =>
                            {
                                SyncSubFolderInFolder(folder, PlatformService.GetChildFolders(user, synhInfo.ItemId), user, context);
                            });

                            folder.OnAfterSync(context);
                        }
                        else
                        {// folder was removed from cloud so we should clear Cloud field for all subitems and clear cloud field for this folder

                            // clear cloud field for files in the folder
                            foreach (IDMSFile file in folder.Files)
                            {
                                SafeFuncCall(errorlist, file, new ExceptionListSignal() { IsAll = true }, Operations.Sync, () =>
                                {
                                    var sInfo = file.GetSyncInfo();
                                    
                                    if (sInfo != null && sInfo.ParentFolderId == synhInfo.ItemId)
                                    {
                                        file.CheckNotCheckeOutToOtherUserOrThrow();

                                        file.UpdateSyncInfo(null, true);
                                        RaiseItemUpdatedLocally(new ItemUpdatedLocallyArgs(file));
                                    }

                                });
                                // file.Item.Web.Audit.WriteItemStopSync(file.Item, MISSEDONCLOUD);
                            }

                            //clear cloud field for all subfolders
                            foreach (IDMSFolder item in folder.SubFolders)
                            {
                                SafeFuncCall(errorlist, item, new ExceptionListSignal() { IsAll = true, IsList = true }, Operations.Sync, () =>
                                {
                                    SyncFolder(item, user, context, true);
                                });
                            }

                            if (errorlist.Count == 0)
                            {
                                SafeFuncCall(errorlist, folder, new ExceptionListSignal() { IsAll = true }, Operations.Sync, () =>
                                {
                                     folder.UpdateSyncInfo(null, true);
                                     RaiseItemUpdatedLocally(new ItemUpdatedLocallyArgs(folder));
                                });
                            }
                            if (!ClearFieldData)
                            {
                                throw new CloudFolderNotFound(RES.STR_UNABLE_SYNC);
                            }
                        }
                    }
                });
            }
        }

        private void SyncFile(IDMSFile localFile, ConflictOptions SyncOption, UserDetails user, OperationContext context)
        {
            localFile.CheckPermissionkOrThrow(Workshare.Integration.Enums.Permissions.EditItem);
            var syncInfo = localFile.GetSyncInfo();
            if (syncInfo != null)//already synhed
            {
                localFile.CheckNotCheckeOutToOtherUserOrThrow();
                try
                {
                    var wsFile = GetFileDetailsFromWorkshare(user, syncInfo.ItemId, syncInfo.ParentFolderId);
                    // if file is null so it was deleted from cloud and we should clear synchronization data from sharepoint
                    if (wsFile != null)
                    {
                        var wsPermissions = PlatformService.GetFolder(user, wsFile.FolderId).Permissions;
                        var wsFileVersions = PlatformService.GetVersionDetails(user, wsFile);
                        var wsVersionForLocalFile = wsFileVersions.Where(x => x.Id == syncInfo.VersionId).FirstOrDefault();
                        if (wsVersionForLocalFile != null)
                        {
                            var wsFileIsNewer = wsFileVersions.Where(x => x.Version > wsVersionForLocalFile.Version).Any();

                            // file on the cloud is newer
                            if (wsFileIsNewer && (SyncOption == ConflictOptions.Replace || (!localFile.WasUpdatedAfterSend(syncInfo) && SyncOption == ConflictOptions.None)))
                            {
                                // if cloud file was updated and we select "Replcae file" on the file conflict dialog or select Save as new version in file synchronize dialog
                                if (SyncOption == ConflictOptions.Replace)
                                {
                                    var wsFileData = PlatformService.DownloadFile(user, syncInfo.ItemId);
                                    UpdateLocalFileName(localFile, wsFile);
                                    localFile.Update(wsFileData, wsFile);
                                    RaiseItemUpdatedLocally(new ItemUpdatedLocallyArgs(localFile));
                                    localFile.OnAfterSync(context);
                                }
                                else
                                {
                                    if (!localFile.WasUpdatedAfterSend(syncInfo) && SyncOption == ConflictOptions.None)
                                    {
                                        throw new FileOnCloudIsNewerException(localFile, wsFile.FriendlyName, wsFile.Version.CreateDate, wsFile.Version.Creator.UserName);
                                    }
                                }
                            }
                            // if file on the cloud is newer and  we select "Keep both files" on the file conflict dialog or select Save as new document in file synchronize dialog
                            else if (wsFileIsNewer /*&& localFile.ItemIsNewer(syncInfo)*/ && SyncOption == ConflictOptions.KeepBoth)
                            {
                                // add new copy of the file to iManager
                                wsFile.Data = PlatformService.DownloadFile(user, wsFile.Id);
                                bool newFileIsAdded = false;
                                IDMSFile newFile = null;
                                if (localFile.ParentFolder != null)
                                {
                                    newFile = ((IDMSFolder)localFile.ParentFolder).AddFile(wsFile, out newFileIsAdded, true);
                                }
                                else
                                {
                                    newFile = localFile.AddFile(wsFile, out newFileIsAdded, true);
                                }

                                if (newFileIsAdded)
                                {
                                    UpdateLocalFileName(localFile, wsFile);
                                    localFile.UpdateSyncInfo(null, true);
                                    if (newFile != null)
                                    {
                                        RaiseItemAddedFromWS(new ItemAddedFromWSArgs(newFile));
                                    }
                                    // if local file was changed then we check in changes, otherwise we discard check out for file

                                    if (localFile.WasUpdatedAfterSend(syncInfo))
                                    {
                                        localFile.OnAfterSync(context);
                                    }
                                    else
                                    {
                                        localFile.UpdateSyncInfo(null, true);
                                    }
                                }
                            }
                            else if (localFile.WasUpdatedAfterSend(syncInfo) && SyncOption == ConflictOptions.None)//file on local DMS is newer
                            {
                                if (wsFileIsNewer)
                                {
                                    throw new FileConflictException(localFile, wsFile.FriendlyName, wsFile.Version.CreateDate, wsFile.Version.Creator.UserName);
                                }
                                else
                                {
                                    UploadNewFileVersionToWorkshareCloud(user, localFile, wsFile);

                                    RaiseItemUpdatedOnWS(new ItemUpdatedOnWSArgs(localFile));

                                    localFile.UpdateSyncInfo(null, true);
                                    //localFile.OnAfterSync(args);
                                }
                            }
                            else if (!wsFileIsNewer && !localFile.WasUpdatedAfterSend(syncInfo))
                            {
                                // file wasn't changed neither on WS nor on local machine, but could be renamed 
                                
                                if (!wsPermissions.DownloadFiles)
                                {
                                    throw new CloudFolderAccessDenied(RES.STR_UNABLE_SYNC, RES.STR_UNABLESYNCFILE_TEXT);
                                }

                                UpdateLocalFileName(localFile, wsFile);
                                localFile.UpdateSyncInfo(null, true);
                                if (!syncInfo.WasAlreadyCheckedOut)
                                {
                                    localFile.DiscardCheckout();
                                }
                            }
                        }
                        else
                        {
                            //how they can delete version??
                            throw new VersionDoesNotExist(); ;
                        }
                    }
                    else
                    {
                        // file was removed from cloud
                        localFile.UpdateSyncInfo(null, true);

                        RaiseItemUpdatedLocally(new ItemUpdatedLocallyArgs(localFile));

                        //if all parent folder was deleted from workshare
                        if (localFile.ParentFolder != null)
                        {
                            var flddata = localFile.ParentFolder.GetSyncInfo();
                            if (flddata != null)
                            {
                                var cloudfolder = PlatformService.GetFolder(user, flddata.ItemId);
                                if (cloudfolder == null || cloudfolder.IsDeleted || ItemWasMoved(user, cloudfolder.ParentId, flddata.ParentFolderId))
                                {
                                    SyncFolder(localFile.ParentFolder, user, context, true);
                                    throw new CloudFolderNotFound(RES.STR_UNABLE_SYNC);
                                }
                            }
                        }

                        throw new CloudFileNotFound(RES.STR_UNABLE_SYNC);
                    }
                }
                catch (CloudFolderAccessDenied)
                {
                    throw;
                }
                catch (WebException ex)
                {
                    if (IsStatusCode(ex, (HttpStatusCode)403))
                    {
                        throw new CloudFolderAccessDenied(RES.STR_UNABLE_SYNC, RES.STR_UNABLESYNCFILE_TEXT, ex);
                    }
                    else
                    {
                        throw;
                    }
                }
            }
            if (context.Stage == OperationStage.Second)
            {
                if (!context.IsRootElementForOperation(localFile))
                {
                    localFile.ParentFolder.OnAfterSync(context);
                }
            }
            localFile.RemoveTempFileIfNeed();
        }

        #endregion

        #region Sending

        private int SendFolder(IDMSFolder folder, int parentFolderId, UserDetails user, OperationContext context, List<int> parentChildren)
        {
            int newFolderID = -1;
            using (var errorlist = new ItemsErrorsCollection(context))
            {
                List<int> sentItems = new List<int>();
                SafeFuncCall(errorlist, folder, new ExceptionListSignal() { IsWeb = true, FolderError = true }, Operations.Send, () =>
                {
                    folder.OnBeforeSending(context);
                    FolderDetails newFolder = null;
                    try
                    {
                        newFolder = PlatformService.CreateFolder(user, folder.Name, folder.Name, parentFolderId);
                    }
                    catch(WebException ex)
                    {
                        if (IsStatusCode(ex, (HttpStatusCode)403))
                        {
                            throw new CloudFolderAccessDenied(RES.STR_UNABLE_SEND, RES.STR_UNANBESENDFOLDER_TEXT, ex);
                        }
                        else
                        {
                            throw;
                        }
                    }
                    folder.UpdateSyncInfo(newFolder, true);
                    if (parentChildren != null)
                    {
                        parentChildren.Add(newFolder.Id);
                    }
                    RaiseItemSent(new ItemSentArgs(folder));

                    foreach (IDMSFolder item in folder.SubFolders)
                    {
                        SafeFuncCall(errorlist, item, new ExceptionListSignal() { IsAll = true, IsList = true, FolderError = true }, Operations.Send, () =>
                            {
                                var si = item.GetSyncInfo();
                                if (si == null)
                                {
                                    SendFolder(item, newFolder.Id, user, context, sentItems);
                                }
                                else
                                {
                                    sentItems.Add(si.ItemId);
                                    throw new FolderAlreadySentException();
                                }
                            });

                    }
                    foreach (IDMSFile file in folder.Files)
                    {

                        SafeFuncCall(errorlist, file, new ExceptionListSignal() { IsAll = true, IsList = true, IsWeb = true, FolderError = true }, Operations.Send, () =>
                        {
                            if (file.GetSyncInfo() == null)
                            {
                                sentItems.Add(SendFile(file, newFolder.Id, user, context));
                            }
                            else
                            {
                                throw new FileAlreadySentException();
                            }
                        });

                    }
                    folder.UpdateSendDataInfo(sentItems);
                    newFolderID = newFolder.Id;
                });
            }
            return newFolderID;
        }

        private int SendFile(IDMSFile localfile, int folderId, UserDetails user, object args)
        {
            localfile.CheckPermissionkOrThrow(Workshare.Integration.Enums.Permissions.EditItem);
            localfile.OnBeforeSending(args);
            localfile.CheckNotCheckeOutToOtherUserOrThrow();

            try
            {
                var fileId = UploadFileToWorkshareCloud(localfile, folderId, user);
                RaiseItemSent(new ItemSentArgs(localfile));
                return fileId;
            }
            catch (Exception ex)
            {
                localfile.OnSendError(args, ex);
                throw;
            }
        }

        #endregion

        #region utility

        #endregion

        #endregion
    }

}
<file_sep>/WSComponents/src/WSIntegration/WsUtils.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.WsProxies;
using WorksharePlatform;

namespace Workshare.Integration
{
    public static class WsUtils
    {
        static readonly char[] InvalidFileNameCharacters = { '~', '#', '%', '&', '*', ':', '<', '>', '?', '/', '\\', '{', '}', '|' };

        public static string RemoveInvalidSymbolsFromFileName(string name)
        {
            var _name = new StringBuilder(name);
            for (int i = 0; i < InvalidFileNameCharacters.Length; i++)
            {
                _name.Replace(InvalidFileNameCharacters[i], '_');
            }

            return _name.ToString().Trim();
        }

        public static string GetEmailDomain(string email)
        {
            if (string.IsNullOrEmpty(email)) return string.Empty;

            var indexAt = email.LastIndexOf('@');
            if (indexAt > -1)
            {
                return email.Substring(indexAt+1, email.Length - indexAt-1);
            }
            else
            {
                return string.Empty;
            }
        }

        public static IEnumerable<WsMember> GetWithoutCurrentUser(this IEnumerable<WsMember> members, WsUser user)
        {
            var currentUserEmail = user == null ? string.Empty : user.Email;
            if (string.IsNullOrEmpty(currentUserEmail))
            {
                return members;
            }
            return members.Where(a => !string.Equals(a.Email, currentUserEmail, StringComparison.InvariantCultureIgnoreCase));
        }

        public static string IdOrNull(this Activity a)
        {
            return a == null ? null : a.ActyvityId;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/SyncDialog/SyncDialogViewModel.cs
﻿using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using Workshare.Components.Concrete;
using Workshare.Components.Views.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.SyncDialog
{
    public class SyncDialogViewModel : OwnViewModel
    {
        private readonly IEnumerable<ImportFileActivity> _activities;

        public RelayCommand OKCommand { get; set; }
        public RelayCommand CancelCommand { get; set; }
        public bool? ApplyToAll { get; set; }
        public Visibility ShowApplyToAll { get; set; }
        public Visibility SubTitleVisibility { get; set; }
        public int VersionCount { get; set; }
        public int FilesCount { get; set; }
        public int NewFilesCount { get; set; }
        public bool AddFiles { get; set; }
        public string LocalFileName { get; set; }
        public string WsFileName { get; set; }

        internal CheckinDlgResult Result { get; set; }


        ConflictOptions? _selected;
        ConflictVersionOptions? _versions;

        public ConflictOptions? SelectedAction
        {
            set
            {
                _selected = value;
                if (OKCommand != null)
                {
                    OKCommand.RaiseCanExecutechanged();
                }
            }
        }
        private ImportType Convert(ConflictOptions conflictOptions)
        {
            switch (conflictOptions)
            {
                case ConflictOptions.Replace:
                    return ImportType.AsNewVersion;
                case ConflictOptions.KeepBoth:
                    return ImportType.AsNewDocument;
                default:
                    return ImportType.None;
            }
        }
        public IEnumerable<ImportDocumentAction> GetSelectedActions()
        {
            var res = new List<ImportDocumentAction>();
            foreach (var activity in _activities)
            {
                var neededImportType = activity.HasChange(ChangeType.RemoteAdded)
                    ? ImportType.AsNewDocument
                    : Convert(Result.option);
                var matchedAction = activity.GetAllAvailableActions()
                    .OfType<ImportDocumentAction>()
                        .Where(
                            a =>
                                a.ImportVersionsAction == Result.versions
                                && a.ImportType == neededImportType)
                        .ToList();
                if (matchedAction.Any())
                {
                    res.Add(matchedAction.First());
                }
            }
            return res;
        }

        public ConflictVersionOptions? SelectedVersionsOption
        {
            set
            {
                _versions = value;
                if (OKCommand != null)
                {
                    OKCommand.RaiseCanExecutechanged();
                }
            }
        }

        public SyncDialogViewModel()
        {
            LocalFileName = "testDocx.docx";
            VersionCount = 2;

        }

        CheckinDlgResult GetResult(ConflictOptions opt, ConflictVersionOptions ver)
        {
            return new CheckinDlgResult() { ApplyToAll = true /*this.ApplyToAll.HasValue ? this.ApplyToAll.Value : false*/, option = opt, versions = ver };
        }

        public SyncDialogViewModel(IEnumerable<ImportFileActivity> activities,  string wsFileName, string localFileName, int versionsCount, int filesCount, int newFilesCount, bool onlyNewFiles)
        {
            _activities = activities;

            this.LocalFileName = localFileName ?? string.Empty;
            this.WsFileName = wsFileName ?? string.Empty;
            this.AddFiles = onlyNewFiles;
            this.NewFilesCount = newFilesCount;
            VersionCount = versionsCount;
            FilesCount = filesCount;
            ShowApplyToAll = Visibility.Collapsed;
            SubTitleVisibility = Visibility.Visible;

            OKCommand = new RelayCommand((p) => (_selected.HasValue), (p) =>
            {
                Result = GetResult(GetAction(), GetVersionOption());
                RaiseClose(true);
            });
            CancelCommand = new RelayCommand((p) =>
            {
                Result = GetResult(ConflictOptions.None, ConflictVersionOptions.None);
                RaiseClose(false);
            });
        }

        private ConflictOptions GetAction()
        {
            return _selected ?? ConflictOptions.None;
        }

        private ConflictVersionOptions GetVersionOption()
        {
            return _versions ?? ConflictVersionOptions.None;
        }        

        public string DialogTitle
        {
            get
            {
                if (FilesCount == 1)
                {
                    if (NewFilesCount > 0)
                    {
                        return string.Format("You have selected to add the file \"{0}\"", (WsFileName.Length > 40) ? WsFileName.Substring(0, 37) + "..." : WsFileName);
                    }
                    else
                    {
                        return string.Format("You have selected to sync the file \"{0}\"", (LocalFileName.Length > 40) ? LocalFileName.Substring(0, 37) + "..." : LocalFileName);
                    }
                }
                else
                {
                    var sb = new StringBuilder();
                    if (NewFilesCount == FilesCount)
                    {
                        sb.Append(string.Format("You have selected to add {0} files", NewFilesCount));
                    }
                    else
                    {
                        sb.Append(string.Format("You have selected to sync {0} files", FilesCount));
                        if (NewFilesCount > 0)
                        {
                            sb.Append(string.Format(" ({0} existed, {1} new on Workshare)", FilesCount - NewFilesCount,
                                NewFilesCount));
                        }
                    }
                    return sb.ToString();
                }
            }
        }
        public string DialogSubTitle
        {
            get
            {
                var sb = new StringBuilder();
                if (FilesCount == 1)
                {
                    sb.Append("This file possibly has more than one new version on Workshare.");
                }
                else
                {
                    sb.Append("Some of this files may have multiple new versions on Workshare");
                }

                return sb.ToString();
            }
        }
        public string AllVersionCaption
        {
            get
            {
                var sb = new StringBuilder();
                if (FilesCount == 1)
                {
                    sb.Append(string.Format("All versions ({0} version(s))", VersionCount));
                }
                else
                {

                    sb.Append("All versions of all files");
                };
                return sb.ToString();
            }

        }

      
    }
}


<file_sep>/WSComponents/src/WSComponents.Tests/TestCommandInvoker.cs
﻿using Moq;
using NUnit.Framework;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using System.Windows.Forms;

namespace WSComponents.Tests
{
    [TestFixture]
    public class TestCommandInvoker
    {
        [Test]
        public void TestExecuteCommand()
        {
            bool cmd1Called = false;
            bool cmd2Called = false;
            bool checkActionAddedEvent = false;
            bool checkActionCompleteEvent = false;
            bool checkIsBusyChangedEvent = false;

            CommandInvoker inv = new CommandInvoker();
            inv.WorkCompleted += (a) => { checkActionCompleteEvent = true; };
            inv.WorkUnitAdded += (a) => { checkActionAddedEvent = true; };
            inv.IsBusyChanged += (a) => { if (a) checkIsBusyChangedEvent = true; };

            var cmd = new Mock<IWorkUnit>();
            cmd.Setup(x => x.Execute()).Callback(() => { cmd1Called = true; Assert.IsTrue(inv.IsBusy); });
            var cmd2 = new Mock<IWorkUnit>();
            cmd2.Setup(x => x.Execute()).Callback(() => { cmd2Called = true; Assert.IsTrue(inv.IsBusy); });

            Assert.IsFalse(inv.IsBusy, "Invoker is empty and should be free");

            inv.AddToQueue(cmd.Object);
            inv.AddToQueue(cmd2.Object);
            Utility.WaitWithPeriodicalCallback(ref cmd1Called, Utility.DEFAULT_TIMEOUT, Application.DoEvents);
            Utility.WaitWithPeriodicalCallback(ref cmd2Called, Utility.DEFAULT_TIMEOUT, Application.DoEvents);

            Assert.IsTrue(cmd1Called, "command 1 was not called");
            Assert.IsTrue(cmd2Called, "command 2 was not called");
            Assert.IsFalse(inv.IsBusy, "Invoker is empty and should be free");
            Assert.IsTrue(checkActionAddedEvent, "Action added event was not fired");
            Assert.IsTrue(checkActionCompleteEvent, "Action complete event was not fired");
            Assert.IsTrue(checkIsBusyChangedEvent, "Chenged busy state event was not fired");
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/ProxyHelper/ProxyDetector.cs
﻿using System;
using System.Net;
using System.Threading;
using System.Windows.Forms;
using WorksharePlatform;
using WorksharePlatform.ServiceProxy.ProxyHelper;

namespace WorkshareCloud.ServiceProxy.ProxyHelper
{
    public static class ProxyDetector
    {
        static CredentialCache GetCredentialsCache(Uri address, NetworkCredential creds)
        {
            if (creds == null) return null;
            var cache = new CredentialCache();
            cache.Add(address, "Basic", creds);

            if (!string.IsNullOrEmpty(creds.Domain))//ntlm requires domain should be set separately
            {
                cache.Add(address, "NTLM", creds);
            }
            else
            {
                cache.Add(address, "NTLM", new NetworkCredential(GetLogin(creds.UserName), creds.Password, GetDomain(creds.UserName)));
            }
            return cache;
        }

        static string GetDomain(string s)
        {
            int stop = s.IndexOf("\\");
            if (stop > -1)
            {
                return s.Substring(0, stop);
            }

            stop = s.IndexOf("@");
            if (stop > -1 && stop < s.Length - 1)
            {
                return s.Substring(stop + 1, s.Length - stop - 1);
            }

            return string.Empty;
        }

        static string GetLogin(string s)
        {
            int stop = s.IndexOf("\\");
            if (stop > -1 && stop < s.Length - 1)
            {
                return s.Substring(stop + 1, s.Length - stop - 1);
            }

            stop = s.IndexOf("@");
            if (stop > -1)
            {
                return s.Substring(0, stop);
            }

            return s;
        }

        public static bool CheckForProxy(UserDetails user, IntPtr owner)
        {
            if (user.IsProxyEnable)
            {
                return true;
            }

            Uri _host = PlatformService.HostWithSchema;
            Uri proxyURI = null;
            var t = new Thread(() =>
            {
                proxyURI = WebRequest.GetSystemWebProxy().GetProxy(_host);
            });
            t.Start();
            while (t.IsAlive)
            {
                Thread.Sleep(10);
            }
                
            ICredentials resultCredentials = new CredentialCache();
            NetworkCredential proxyCred = null;
            WebProxy proxy = new WebProxy(proxyURI, true)
            {
                Credentials = CredentialCache.DefaultNetworkCredentials
            };

            if (proxyURI != null && !string.IsNullOrEmpty(proxyURI.AbsoluteUri) && !proxy.Address.Equals(_host))
            {
                user.Proxy = proxy;
                
                var dlg = new CredentialDialog();
                dlg.Target = proxyURI.AbsoluteUri;
                dlg.MainInstruction = "The server " + proxyURI.Host + " at proxy requires a username and password";
                dlg.ShowSaveCheckBox = true;
                dlg.IsSaveChecked = true;
                dlg.ShowUIForSavedCredentials = false;
                dlg.UseApplicationInstanceCredentialCache = false;
                dlg.WindowTitle = "Windows Security";

                

                string usrname = PlatformRegistryHelper.getFromRegisrty(RegData.Username);
                string usrpass = PlatformRegistryHelper.getFromRegisrty(RegData.Userpass);
                if (!string.IsNullOrEmpty(usrname))
                {
                    proxyCred = new NetworkCredential(usrname, usrpass);
                    dlg.UserName = usrname;
                    dlg.Password = <PASSWORD>;
                }

                bool ProxySettingsDetected = false;
                while (!ProxySettingsDetected)
                {
                    HttpWebRequest myRequest = (HttpWebRequest)HttpWebRequest.Create(_host);
                    HttpWebResponse myResponse;
                    try
                    {
                        if (proxyCred != null)
                        {
                            resultCredentials = GetCredentialsCache(proxy.Address, proxyCred);
                        }
                        else
                        {
                            resultCredentials = CredentialCache.DefaultNetworkCredentials;
                        }

                        myRequest.Proxy = proxy;
                        myRequest.Proxy.Credentials = resultCredentials;
                        myResponse = (HttpWebResponse)myRequest.GetResponse();
                        ProxySettingsDetected = true;
                    }
                    catch(Exception e)
                    {
                        if (e is WebException && e.Message.Contains("407"))
                        {
                            if (dlg.ShowDialog(owner) == DialogResult.OK)
                            {

                                proxyCred = dlg.Credentials;
                                if (dlg.IsSaveChecked && dlg.ShowSaveCheckBox)
                                {
                                    PlatformRegistryHelper.setToRegisrty(RegData.Username, dlg.UserName);
                                    PlatformRegistryHelper.setToRegisrty(RegData.Userpass, dlg.Password);
                                }
                            }
                            else
                            {
                                user.Proxy = null;
                                user.ProxyCredentials = null;
                                return false;
                            }
                        }
                        else
                        {
                            ProxySettingsDetected = true;
                        }
                    }
                }
            }

            user.ProxyCredentials = resultCredentials;
            return true;
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Presenter/ModulePresenter.cs
﻿using System.Collections.Generic;
using System.Linq;
using System.Windows.Forms;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Presenter;
using Workshare.Components.WSLogger;
using Workshare.IManage.Views;
using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Services;

namespace Workshare.IManage.Presenter
{
    public class ModulePresenter :ModulePresenterBase
    {
        readonly ModuleView _view;

        public ModulePresenter(IModuleView view)
            : base(view)
        {
            _view = view as ModuleView;
        }

        public void OnSyncItemsClicked(SyncItemsClickedArgs args, bool fromRibbon)
        {
            var folders = args.Items.Select(p => p.item).OfType<IDMSFolder>().ToList();

            if (folders.Count() == 1)
            {
                if (LoginIfNeeded())
                {
                    if (Application.iManInstance.ClientType == iManType.FileSite)
                    {
                        ActivityCounter.Instance.UpdateUserFolder(folders.FirstOrDefault());
                    }

                    _view.ShowTrueSyncDialog(invoker, folders.OfType<IDMSItem>(), (res, itemsToSkip) =>
                    {
                        if (Application.iManInstance.ClientType == iManType.FileSite)
                        {
                            ActivityCounter.Instance.UpdateUserFolder(ActivityCounter.Instance.CurrentFolder, true);
                        }
                    }, fromRibbon);
                }
            }
            else
            {
                if (LoginIfNeeded())
                {
                    var syncWU = new TrueSynhWorkUnit(_view, args.Items);
                    invoker.AddToQueue(syncWU);
                }
                //   base.OnSyncItemsClicked(args);
            }
        }

        public override void OnSyncItemsClicked(SyncItemsClickedArgs args)
        {
            this.OnSyncItemsClicked(args, false);
        }

        public void UpdateSyncInfo(object doc)
        {
            if (doc is IManDocument)
            {
                var manfile = new Workshare.IManage.Contrete.ManFile((IManDocument)doc);
                Logger.Write("Try get sync info", Severity.Information);
                var syncinfo = Application.iManInstance.Module.Resolve<SyncInfoService>().GetSyncInfo(manfile);
                if (syncinfo != null)
                {
                    Logger.Write("try update sync info", Severity.Information);
                    Application.iManInstance.Module.Resolve<SyncInfoService>().UpdateSyncInfo(
                        manfile.GetVersions().Where(a => a.Number == ((IManDocument)doc).Version).FirstOrDefault(),
                        new ActionContext(Workshare.Integration.Processor.Services.ActionType.Upload));
                }
            }
        }

        public override void OnSendItemsClicked(SendItemsClickedArgs args)
        {
            //TODO move to base class
            InvokeInSTAThreadIfNeed(() =>
            {  
                bool repeat = true;
                while (repeat)
                {
                    if (LoginIfNeeded())
                    {
                        if (Application.iManInstance.ClientType == iManType.FileSite)
                        {
                            ActivityCounter.Instance.UpdateUserFolder(ActivityCounter.Instance.CurrentFolder);
                        }
                        var checkOutDialogResult = ShowCheckOutDialogIfNeed(args);
                        if (checkOutDialogResult == Workshare.Integration.Enums.CheckOutOptions.None)
                        {
                            repeat = false;
                        }
                        else
                        {
                            var res = _view.ShowSelectFolder(GetCurrentDialogSettings(Application.iManInstance.AuthProvider.GetCurrentWSUser()));
                            if (res > -1)
                            {
                                invoker.AddToQueue(GetSendCommand(args.Items, new List<FileMapActivity>(), res, checkOutDialogResult));
                                repeat = false;
                            }
                            else if (res == -1)
                            {
                                repeat = false;
                            }
                            else if (res == -10) // we lost auth credentials
                            {
                                var user = Application.iManInstance.AuthProvider.GetCurrentWSUser();
                                if (user != null)
                                {
                                    user.AuthToken = string.Empty;
                                    user.SessionCookies = null;
                                }
                            }
                        }
                    }
                    else
                    {
                        repeat = false;
                    }
                }
            });
        }
    }

}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/ScanStrategy.cs
﻿using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Strategies
{
    public class ScanStrategy : DmsScanStrategyBase
    {
        readonly WsProxy _wsProxy;
        readonly IAuthProvider _auth;
        readonly SyncInfoService _syncInfoService;

        public ScanStrategy(WsProxy wsProxy, IAuthProvider auth, SyncInfoService syncInfoService)
        {
            _wsProxy = wsProxy;
            _auth = auth;
            _syncInfoService = syncInfoService;
        }

        public void EnsureIndirectParent(ItemMap map, ISyncInfo syncInfo, bool useForceRequest)
        {
            var parent = map.Parent as FolderMap;
            var parentWsId = -1;
            var wsParent = (parent != null) ? parent.WsFolder : null;
            if (wsParent != null)
            {
                parentWsId = wsParent.Id;
            }
            else
            {
                if (parent!=null && parent.LocalFolder != null)
                {
                    var parentSyncInfo = _syncInfoService.GetSyncInfo(parent.LocalFolder, useForceRequest);
                    if (parentSyncInfo!=null)
                    {
                        parentWsId = parentSyncInfo.ItemId;
                    }
                }
            }
            if (parentWsId != -1)
            {
                if (syncInfo != null && parentWsId != syncInfo.ParentId)
                {
                    var actualParentFoldermap = new FolderMap();
                    try
                    {
                        actualParentFoldermap.WsFolder = _wsProxy.TryGetFolder(_auth.GetCurrentWSUser2(), syncInfo.ParentId);
                    }
                    catch (Exception ex)
                    {
                        Logger.WriteError(ex);
                        actualParentFoldermap.ProcessState = ProcessState.Error;
                        actualParentFoldermap.Error = ex;
                    }
                    map.IndirectParent = actualParentFoldermap;
                }
            }
        }

        public Exception GetAncestorParentsError(ItemMap item)
        {
            if (item.IndirectParent != null)
            {
                return item.IndirectParent.ProcessState == ProcessState.Error ? item.IndirectParent.Error??new Exception("Parent in error") : null;
            }
            if (item.IndirectParent == null)
            {
                if (item.Parent != null)
                {
                    if (item.Parent.ProcessState==ProcessState.Error)
                    {
                        return item.Parent.Error ?? new Exception("Parent in error");
                    }
                    return GetAncestorParentsError(item.Parent);
                }
            }
            return null;
        }

        public override ScanResult Scan(BaseDMSFile dmsfile, FileMap fileMap, DmsFileScanOptions dmsScanOptions)
        {
            var manFile = (IDMSFile) dmsfile;
            var parentFolderMap = fileMap.Parent as FolderMap;

            WsFile file = null;
            if (fileMap.WsFile != null)
            {
                file = fileMap.WsFile;
            }
            else
            {
                var syncInfo = _syncInfoService.GetSyncInfo(manFile, dmsScanOptions.UseForceRequest);

                if (syncInfo != null)
                {
                    var wsParentFolder = (parentFolderMap != null) ? parentFolderMap.WsFolder : null;
                    var parentFolderFiles = ((wsParentFolder != null) ? parentFolderMap.WsFolder.Files : null) ??
                                            new List<WsFile>();
                    file =
                        parentFolderFiles.FirstOrDefault(
                            f => f.Id == syncInfo.ItemId && f.FolderId == syncInfo.ParentId);

                    if (file == null && (wsParentFolder == null || wsParentFolder.Id != syncInfo.ParentId))
                    {
                        var user = _auth.GetCurrentWSUser2();
                        file = _wsProxy.TryGetFile(user, syncInfo.ItemId, syncInfo.ParentId);
                    }
                    EnsureIndirectParent(fileMap, syncInfo, dmsScanOptions.UseForceRequest);       
                }
            }


            fileMap.WsFile = file;

            var fileMapError = GetAncestorParentsError(fileMap);
            if (fileMapError != null)
            {
                return ScanResult.ErrorResult(fileMapError);
            }

            return ScanResult.Scanned;
        }

        public override ScanResult Scan(BaseDMSFolder baseDMSFolder, FolderMap folderMap, DmsFolderScanOptions param)
        {
            var folder = (IDMSFolder) baseDMSFolder;
            var parentFolderMap = folderMap.Parent as FolderMap;
           
            WsFolder wsFolder = null;
            if (folderMap.WsFolder != null)
            {
                wsFolder = folderMap.WsFolder;
            }
            else
            {
                var syncInfo = _syncInfoService.GetSyncInfo(folder, param.UseForceRequest);
                if (syncInfo != null)
                {

                    var wsParentFolder = (parentFolderMap != null) ? parentFolderMap.WsFolder : null;
                    if (parentFolderMap != null && parentFolderMap.WsFolder != null)
                    {
                        wsFolder = parentFolderMap.WsFolder.SubFolders.FirstOrDefault(p => p.Id == syncInfo.ItemId);
                    }
                    if (wsFolder == null)
                    {
                        wsFolder = _wsProxy.TryGetFolder(_auth.GetCurrentWSUser2(), syncInfo.ItemId);
                    }
                }
                EnsureIndirectParent(folderMap, syncInfo, param.UseForceRequest);
            }

            folderMap.WsFolder = wsFolder;
            var folderMapError = GetAncestorParentsError(folderMap);
            if (folderMapError != null)
            {
                return ScanResult.ErrorResult(folderMapError);
            }
            return ScanResult.Scanned;
        }

        public override ScanResult Scan(BaseDmsVersion dmsVersion, VersionMap versionMap, DmsVersionScanOptions args)
        {
            var info = _syncInfoService.GetSyncInfo((IDmsVersion)dmsVersion, args.UseForceRequest);
            var fileMap = (FileMap)versionMap.Parent;
            var wsFile = fileMap.WsFile;
            if (wsFile != null && info!=null)
            {
                versionMap.WsVersion = wsFile.Versions.FirstOrDefault(p => p.Id.ToString(CultureInfo.InvariantCulture) == info.CurWsVerId);
            }

            return ScanResult.Scanned;
        }


        //TODO this method should not know anything about new or not new versions. It should just build maps.But in this case Changes detector should be revisited as it depends on current behavior
        public override ScanResult ScanForNewVersionsOnWs(BaseDMSFile dmsfile, FileMap fileMap, DmsFileScanOptions options)
        {
            var syncInf = _syncInfoService.GetSyncInfo((IDMSFile)dmsfile, options.UseForceRequest);
            var wsFile = fileMap.WsFile;
            if (syncInf != null && wsFile != null)
            {
                var wsVersions = wsFile.Versions.ToList();
                var lastImportedWsVersion = wsVersions.FirstOrDefault(a => a.Id == syncInf.LastImportedWsVerId);
                foreach (var version in wsVersions)
                {
                    if (lastImportedWsVersion != null && version.Version <= lastImportedWsVersion.Version) continue;
                    if (fileMap.ContainsChildWsVersion(version.Id)) continue;
                    if (syncInf.AnyVersionIsLinkedWithWsVersion(version.Id)) continue;

                    var versionMap = new VersionMap {WsVersion = version};
                    fileMap.AddIf(versionMap);
                    versionMap.ProcessState = ProcessState.Scanned;
                }
            }
            return ScanResult.Scanned;
        }

        public override ScanResult GetWsItemsToVisit(FolderMap parentFolderMap, out List<WsFolder> wsFoldersToVisit, out List<WsFile> wsFilesToVisit, bool useForceRequest = true)
        {
            wsFoldersToVisit=new List<WsFolder>();
            wsFilesToVisit=new List<WsFile>();
            var wsIdsOfSentFiles = parentFolderMap.Maps.OfType<FileMap>()
                .Select(a => _syncInfoService.GetSyncInfo(a, useForceRequest))
                .Where(p => p != null)
                .Select(p => p.ItemId);
            var wsIdsOfSentFolders = parentFolderMap.Maps.OfType<FolderMap>()
                .Select(a => _syncInfoService.GetSyncInfo(a, useForceRequest))
                .Where(p => p != null)
                .Select(p => p.ItemId);

            var filesOnWorkshareThatIsNotNew = wsIdsOfSentFiles.Concat(_syncInfoService.GetSendData(parentFolderMap, useForceRequest));
            var foldersOnWorkshareThatIsNotNew = wsIdsOfSentFolders.Concat(_syncInfoService.GetSendData(parentFolderMap, useForceRequest));

            if (parentFolderMap.WsFolder == null)
            {
                try
                {
                    parentFolderMap.WsFolder = _wsProxy.TryGetFolder(_auth.GetCurrentWSUser2(), _syncInfoService.GetSyncInfo(parentFolderMap, useForceRequest).ItemId);
                }
                catch {}
            }

            if (parentFolderMap.WsFolder != null)
            {
                wsFilesToVisit =
                    parentFolderMap.WsFolder.Files.Where(f => !filesOnWorkshareThatIsNotNew.Contains(f.Id)).ToList();
                wsFoldersToVisit =
                    parentFolderMap.WsFolder.SubFolders.Where(f => !foldersOnWorkshareThatIsNotNew.Contains(f.Id))
                        .ToList();
            }

            return ScanResult.Scanned;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration.Tests/TestOperationContext.cs
﻿using System.Collections.Generic;
using Moq;
using NUnit.Framework;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;

namespace WSIntegration.Tests
{

    class TestItemID : IDMSItemID
    {
        int obj_ID;
        public TestItemID(int obj_id)
        {
            obj_ID = obj_id;
        }

        public bool EqualTo(IDMSItemID obj)
        {
            if (obj is TestItemID)
            {
                return ((TestItemID)obj).obj_ID == this.obj_ID;
            }
            return false;
        }
    }

    [TestFixture]
    public class TestOperationContext
    {
        [Test]
        public void TestOperationContext_IsRootElement()
        {
            var item1 = new Mock<IDMSItem>();
            var item2 = new Mock<IDMSItem>();
            var item3 = new Mock<IDMSItem>();
            var erroritem = new Mock<IDMSItem>();
            var itemID1 = new TestItemID(1);
            var itemID2 = new TestItemID(2);
            var itemID3 = new TestItemID(3);
            var errorItemID = new TestItemID(4);
            item1.Setup(x => x.ID).Returns(itemID1);
            item2.Setup(x => x.ID).Returns(itemID2);
            item3.Setup(x => x.ID).Returns(itemID3);
            erroritem.Setup(x => x.ID).Returns(errorItemID);

            List<IDMSItem> lst = new List<IDMSItem>();
            lst.Add(item1.Object);
            lst.Add(item2.Object);
            lst.Add(item3.Object);

            List<FileMapActivity> lstToSkip = new List<FileMapActivity>();

            var ctx = new OperationContext(lst, lstToSkip);

            Assert.IsTrue(ctx.IsRootElementForOperation(item2.Object), "Item should be triggered as root, but shouldn't");
            Assert.IsTrue(ctx.IsRootElementForOperation(item3.Object), "Item should be triggered as root, but shouldn't");
            Assert.IsFalse(ctx.IsRootElementForOperation(erroritem.Object), "Error item triggered as root");
            Assert.IsTrue(ctx.Stage == OperationStage.First,"Step did not set up to First");
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/Utils/FileUtils.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Text;
//TODO uncomment
//using Workshare.Components.WSLogger;

namespace Workshare.Components.Helpers
{
    public static class FileUtils
    {
        public static string GetExtension(string name)
        {
            if (string.IsNullOrEmpty(name)) return name;

            var lastIndex = name.LastIndexOf('.');
            if (lastIndex > 0)
            {
                return name.Substring(lastIndex);
            }

            return string.Empty;
        }

        public static string GetFileNameWithoutExtension(string name)
        {
            if (string.IsNullOrEmpty(name)) return name;

            var lastIndex = name.LastIndexOf('.');
            if (lastIndex > 0)
            {
                return name.Remove(lastIndex);
            }

            return name;
        }

        public static string ChangeExtension(string name, string extension)
        {
            return GetFileNameWithoutExtension(name) + extension;
        }

        public static void SafeDelete(string filePath)
        {
            try
            {
                if (string.IsNullOrEmpty(filePath)) return;
                File.Delete(filePath);
            }
            catch (Exception ex)
            {
                //TODO uncomment
                //Logger.WriteError(ex);
            }
        }

        public static bool IsFileLocked(string filePath)
        {
            try
            {
                if (string.IsNullOrEmpty(filePath) || !File.Exists(filePath)) return false;
                using (var stream = File.OpenWrite(filePath))
                {
                    return false;
                }
            }
            catch (DirectoryNotFoundException)
            {
                return false;
            }
            catch (FileNotFoundException)
            {
                return false;
            }
            catch
            {
                return true;
            }
        }
    }
}<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/Visitors/DMSVisitor.cs
﻿using System.Collections.Generic;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.DmsItems.Visitors
{
    public abstract class DMSVisitor
    {
        public abstract PageIterator Iterator { set; get; }

        public abstract bool VisitEnter(BaseDMSFolder baseDMSFolder);

        public abstract void Visit(BaseDMSFolder dmsFolder);

        public abstract void VisitLeave(BaseDMSFolder baseDMSFolder);

        public abstract bool VisitEnter(BaseDMSFile baseDMSFile);

        public abstract void Visit(BaseDMSFile dmsfile);

        public abstract void VisitLeave(BaseDMSFile baseDMSFile);

        public abstract void Visit(BaseDmsVersion baseDmsVersion);

        public abstract void GetNewEntries(out List<WsFolder> wsfolders, out List<WsFile> wsfiles);

        public abstract bool VisitEnter(WsFolder wsFolder, out List<WsFolder> wsFolders, out List<WsFile> wsFiles);
        public abstract void VisitLeave(WsFolder wsFolder);
        public abstract void Visit(WsFolder wsFolder);

        public abstract void Visit(WsFile file);
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/Visitors/PageIterator.cs
﻿using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.DmsItems.Visitors
{

    /// <summary>
    /// iterates throught local items and new remote also stops when page count number of new items was got.
    /// </summary>
    public class PageIterator
    {
        private readonly int _pageItems;
        private readonly DMSVisitor _visitor;
        private readonly BaseDMSItem _root;

        public bool HasMore { private set; get; }
        private readonly IItemsDetector _itemsDetector;
        private int _prevTotalItemsCount;
        private int _currentTotalItemsCount;

        public PageIterator(int pageItems, DMSVisitor visitor, BaseDMSItem root, IItemsDetector counter)
        {
            _itemsDetector = counter;
            _pageItems = pageItems;
            _visitor = visitor;
            _root = root;
            HasMore = true;
        }

        private bool _skipping;

        public void VisitNextPage()
        {
            _skipping = false;
            _prevTotalItemsCount = _currentTotalItemsCount;
            if (HasMore)
            {
                HasMore = false;
                if (_root is BaseDMSFolder) Apply((BaseDMSFolder)_root);
                else if (_root is BaseDMSFile) Apply((BaseDMSFile)_root);
            }

            _visitor.Iterator = this;
        }

        void CheckPage(bool isLastItem)
        {
            if (_itemsDetector!=null)
            {
                _currentTotalItemsCount = _itemsDetector.GetCurrentItemsCount(_visitor);
                if (_currentTotalItemsCount - _prevTotalItemsCount >= _pageItems)
                {
                    _skipping = !isLastItem;
                }
            }
        }

        private void Apply(SingleChildDMSFolder folder)
        {
            if (_visitor.VisitEnter(folder._folder))
            {
                if (folder.Next != null)
                {
                    Apply(folder.Next);
                }

                if (folder.File != null)
                {
                    Apply(folder.File);
                }
            }
            _visitor.VisitLeave(folder._folder);
        }

        void Apply(BaseDMSFolder folder)
        {
            var singleChildFolder = folder as SingleChildDMSFolder;
            if (singleChildFolder != null)
            {
                this.Apply(singleChildFolder);
                return;
            }
            if (_visitor.VisitEnter(folder))
            {
                var folders = ((IDMSFolder)folder).SubFolders;

                foreach (var subfolder in folders.OfType<BaseDMSFolder>())
                {
                    if (_skipping)
                    {
                        HasMore = true;
                        continue;
                    }
                    Apply(subfolder);
                }

                //Task 22006. GroupBy used to select only latest version when worksite shows all versions in Document view.
                var files = ((IDMSFolder)folder).Files.GroupBy(x => x.DMSId).Select(x => x.First().GetLatest()).OfType<BaseDMSFile>().ToArray();

                foreach (var file in files)
                {
                    if (_skipping)
                    {
                        HasMore = true;
                        continue;
                    }
                    Apply(file);
                    CheckPage(false);
                }

                List<WsFile> wsfiles;
                List<WsFolder> wsfolders;
                _visitor.GetNewEntries(out wsfolders, out wsfiles);

                foreach (var wsFolder in wsfolders)
                {
                    if (_skipping)
                    {
                        HasMore = true;
                        continue;
                    }
                    Apply(wsFolder);
                }

                foreach (var wsFile in wsfiles)
                {
                    if (_skipping)
                    {
                        HasMore = true;
                        continue;
                    }
                    Apply(wsFile);
                    CheckPage(false);
                }

                _visitor.Visit(folder);
            }
            _visitor.VisitLeave(folder);
        }

        void Apply(WsFile file)
        {
            _visitor.Visit(file);
        }

        void Apply(WsFolder wsFolder)
        {
            List<WsFolder> wsFolders;
            List<WsFile> wsFiles;
            if (_visitor.VisitEnter(wsFolder, out wsFolders, out wsFiles))
            {
                foreach (var wsFld in wsFolders)
                {
                    if (_skipping)
                    {
                        HasMore = true;
                        continue;
                    }
                    Apply(wsFld);
                }
                foreach (var wsFile in wsFiles)
                {
                    if (_skipping)
                    {
                        HasMore = true;
                        continue;
                    }
                    Apply(wsFile);
                    CheckPage(false);
                }
                _visitor.Visit(wsFolder);    
            }
            _visitor.VisitLeave(wsFolder);
            
        }

        void Apply(BaseDmsVersion version)
        {
            _visitor.Visit(version);
        }

        void Apply(BaseDMSFile file)
        {
            if (_visitor.VisitEnter(file))
            {
                var dmsFile = (IDMSFile)file;

                var versions = dmsFile.GetVersions();

                foreach (var ver in versions.OfType<BaseDmsVersion>())
                {
                    Apply(ver);
                }

                _visitor.Visit(file);
            }
            _visitor.VisitLeave(file);
        }
    }


    /// <summary>
    /// Helps iterator to understand whether iteration should be ended or not
    /// </summary>
    public interface IItemsDetector
    {
        int GetCurrentItemsCount(DMSVisitor visitor);
    }

   
}
<file_sep>/WSComponents/src/WSComponents/Enums/ImportOptions.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Workshare.Components.Enums
{
    public enum ImportOptions
    {
        AsNewFile = 1,
        AsNewVersion = 2,
        AsRelatedDocument = 3
    }
}
<file_sep>/WSComponents/src/WSIntegration/Exceptions/ExceptionExts.cs
﻿using System;
using System.Net;
using System.Runtime.InteropServices;
using Workshare.Components.WSLogger;
using WorksharePlatform;

namespace Workshare.Integration.Exceptions
{
    public static class ExceptionExts
    {
        public static bool IsConnectionError(this Exception ex)
        {
            var wex = ex as WebException;
            if (wex != null)
            {
                if (wex.IsStatusCode((System.Net.HttpStatusCode) 502))
                    return true;
                var responce = wex.Response as HttpWebResponse;
                return responce == null;
            }

            var cex = ex as COMException;
            if (cex != null)
            {
                if (cex.ErrorCode == -2147221399 || cex.ErrorCode == -2147221402 || cex.ErrorCode == -2147221503)
                {
                    Logger.WriteError((Exception) cex);
                    return true;
                }
            }

            return ex is OfflineException;
        }

        public static bool IsConnectionTimeOutError(this Exception ex)
        {
            var wex = ex as WebException;
            if (wex != null)
            {
                return wex.IsStatusCode(HttpStatusCode.GatewayTimeout);
            }

            return false;
        }

        public static bool IsCloudFolderAccessDenied(this Exception ex)
        {
            var wex = ex as WebException;

            return ex is CloudFolderAccessDenied || wex.IsStatusCode(HttpStatusCode.Forbidden);
        }

        public static bool IsUnauthorized(this Exception ex)
        {
            var wex = ex as WebException;

            return ex is CloudUnAuthorized || wex.IsStatusCode(HttpStatusCode.Unauthorized);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Resources/injectedJS.js
function init() {
	if (window.addEventListener) {
		window.addEventListener("message", receiver, false);
	}
	else {
		window.attachEvent("onmessage", receiver);
	}

    try
    {
        window.onload = function () {
            var el = document.body;
            el.style.overflowY = "hidden";
        }
    }
    catch (err) {
    }
};

function jsLogger(e) {
         window.external.Log(e);
    }

function GetDialogResult(data) {
    try {        
        var res = JSON.parse(data);
        if (res) {
            return res;
        }
        else {
            return data;
        }
    }
    catch (err) {
        return data;
    }
}
function receiver(e) {
	var res = GetDialogResult(e.data);
	if (res) {
	    if (res.cancel) {
			window.external.onCancel();
		}
		else if (res.folder_id || res.folder_id==0) {
			window.external.onOk(res.folder_id);
		}
		else {
		    alert("no folder id");
		    window.external.onCancel();
		}
	}
};
<file_sep>/SharePoint/src/WorkshareCloud.Common/ListItemExtension.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;
using System.IO;
using WorksharePlatform;
using System.Collections;

namespace WorkshareCloud.Common
{
    public static class ListItemExtension
    {
        public static void CheckPermissionkOrThrow(this SPSecurableObject obj, SPBasePermissions permissions)
        {
            if (!obj.DoesUserHavePermissions(permissions))
            {
                throw new UnauthorizedAccessException();
            }
        }

        public static void CheckWSFieldOrThrow(this SPList obj)
        {
            if (!obj.Fields.ContainsFieldWithStaticName(CloudPathFieldValue.CloudField))
            {
                throw new CloudFieldNotFound();
            }
        }

        public static void CheckNotCheckedOutToOtherUserOrThrow(this SPListItem item)
        {
            if (item.File != null)
            {
                var checkoutedTo = item.File.CheckedOutByUser;
                if (checkoutedTo != null && checkoutedTo.ID != item.Web.CurrentUser.ID) throw new FileCheckoutedToAnotherUser();
            }
        }

        public static bool IsCheckedOutToCurrentUser(this SPListItem item)
        {
            if (item.File != null)
            {
                var checkoutedTo = item.File.CheckedOutByUser;
                if (checkoutedTo != null && checkoutedTo.ID == item.Web.CurrentUser.ID) 
                {
                    return true; 
                }
            }
            return false;
        }



        public static CloudPathFieldValue GetCloudValue(this SPListItem item)
        {
            if (item.Fields.ContainsFieldWithStaticName(CloudPathFieldValue.CloudField))
            {
                return new CloudPathFieldValue((string)item[CloudPathFieldValue.CloudField]);
            }
            else
            {
                throw new CloudFieldNotFound(CloudPathFieldValue.CloudField);
            }
        }

        public static bool IsFolder(this SPListItem item)
        {
            if (item.FileSystemObjectType == SPFileSystemObjectType.Folder)
            {
                return true;
            }
            return false;
        }

        public static CloudPathFieldValue SetCloudValue(this SPListItem item, FileDetails fileDetails)
        {
            if (item.Fields.ContainsFieldWithStaticName(CloudPathFieldValue.CloudField))
            {
                if (fileDetails != null)
                {
                    var val = new CloudPathFieldValue(fileDetails, item);
                    item[CloudPathFieldValue.CloudField] = val.ToString();
                    return val;
                }
                else
                {
                    item[CloudPathFieldValue.CloudField] = CloudPathFieldValue.Empty.ToString();
                    return null;
                }
            }
            else
            {
                throw new CloudFieldNotFound(CloudPathFieldValue.CloudField);
            }
        }

        public static void ClearCloudValue(this Hashtable item)
        {
            item[CloudPathFieldValue.CloudField] = string.Empty;
        }

        public static CloudPathFieldValue SetCloudValue(this SPListItem item, FolderDetails folderDetails)
        {
            if (item.Fields.ContainsFieldWithStaticName(CloudPathFieldValue.CloudField))
            {
                if (folderDetails != null)
                {
                    var val = new CloudPathFieldValue(folderDetails, item);
                    item[CloudPathFieldValue.CloudField] = val.ToString();
                    return val;
                }
                else
                {
                    item[CloudPathFieldValue.CloudField] = CloudPathFieldValue.Empty.ToString();
                    return null;
                }
            }
            else
            {
                throw new CloudFieldNotFound(CloudPathFieldValue.CloudField);
            }
        }

        public static SPFile AddWSFile(this SPFileCollection files, string name, string filePath)
        {
            var basename = name;
            var filename = basename;
            int fileaddings = 1;
            while (true)
            {
                try
                {
                    //TO DO - need to redevelop to give ability to add files which size is more than Int32.MaxValue
                    SPFile item = null;
                    int fileSize = (int)FileDetails.GetFileSizeByFilePath(filePath);
                    using (Stream stream = File.Open(filePath, FileMode.Open, FileAccess.Read, FileShare.None))
                    {
                        using (BinaryReader br = new BinaryReader(stream))
                        {
                            item = files.Add(files.Folder.ServerRelativeUrl + "/" + filename, br.ReadBytes(fileSize), false, "", false);
                        }
                    }

                    if (item != null)
                        item.Update();
                    //files.Folder.Item.SystemUpdate(false);
                    return item;
                }
                catch (SPException ex)
                {
                    if (ex.ErrorCode == -2130575257)//file with such name exists
                    {
                        filename = string.Format("{0} - ({1})", Path.GetFileNameWithoutExtension(basename), fileaddings) + Path.GetExtension(basename);
                    }
                    else
                    {
                        throw;
                    }
                }
                fileaddings++;
            }
        }

        public static byte[] GetFile(this SPListItem item)
        {
            using (var stream = item.File.OpenBinaryStream())
            {
                return stream.ReadFully();
            }
        }
        public static byte[] ReadFully(this Stream input)
        {
            byte[] buffer = new byte[16 * 1024];
            using (MemoryStream ms = new MemoryStream())
            {
                int read;
                while ((read = input.Read(buffer, 0, buffer.Length)) > 0)
                {
                    ms.Write(buffer, 0, read);
                }
                return ms.ToArray();
            }
        }

    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/WorkUnits/BreakFolderLinkWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Components.Views.TrueSyncDialog.WorkUnits
{
    class BreakFolderLinkWorkUnit:WorkUnit
    {
        private readonly TrueSyncDialogViewModel _vm;
        public BreakFolderLinkWorkUnit(TrueSyncDialogViewModel vm, IModuleView view):base(view)
        {
            _vm = vm;
        }

        public override void Execute()
        {
            var processor = _vm.Module.Resolve<Processor>();
            processor.BreakLink(_vm.ScanResult);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Interfaces/ISyncInfoFactory.cs
﻿namespace Workshare.Integration.Interfaces
{
    public interface ISyncInfoFactory
    {
        ISyncInfo CreateFileInfo();
        ISyncInfo CreateFolderInfo();
        IVersionSyncInfo CreateVersionInfo();
        ISendDataInfo CreateSendDataInfo();
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/UserControls/ChangeTemplateSelector.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using Workshare.Components.WSLogger;
using Workshare.Integration.Processor.Changes;

namespace Workshare.Components.Views.TrueSyncDialog.UserControls
{
    public class ChangeTemplateSelector:DataTemplateSelector
    {
        public override DataTemplate SelectTemplate(object item, DependencyObject container)
        {
            try
            {
                var change = item as FileActivityChange;
                var element = container as FrameworkElement;
                if (element != null && change != null)
                {
                    var templateName = string.Empty;
                    switch (change.Type)
                    {
                        case ChangeType.FolderSharedWithOthers:
                            templateName = "FolderSharedWithOthersTemplete";
                            break;
                        default:
                            templateName = "CommonChangeTemplete";
                            break;
                    }

                    return element.FindResource(templateName) as DataTemplate;
                }
                return null;
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                return null;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/AsposePdf/AsposePdf.cs
﻿using System.Collections.Generic;

using WorksharePlatform;

namespace Workshare.Integration.AsposePdf
{
    public class AsposePdfHelper
    {
        public AsposePdfHelper()
        {
        }

        public byte[] AddCommentInData(byte[] data, List<FileComment> comments)
        {
            if (comments.Count == 0)
            {
                return data;
            }

            //MemoryStream inStream = new MemoryStream(data);
            //Document doc = new Document(inStream);

            //var list = comments.OrderBy(x => x.ReplyToId == 0 ? x.Id : x.ReplyToId).ThenBy(x => x.CreatedAt);

            //Aspose.Pdf.InteractiveFeatures.DefaultAppearance default_appearance = new DefaultAppearance("Arial", 10, System.Drawing.Color.Black);
            //FreeTextAnnotation lastAnnotation;
            //foreach (var comment in comments)
            //{
            //    FreeTextAnnotation ann = new FreeTextAnnotation(doc.Pages[comment.PageNumber], new Aspose.Pdf.Rectangle(comment.Positional.x, comment.Positional.y, comment.Positional.width, comment.Positional.height), default_appearance);
            //    ann.Contents = comment.Creator.UserName  + ":\n" + comment.Body;
            //    ann.Opacity = 0.0;
            //    ann.Modified = comment.CreatedAt;
            //    if (comment.ReplyToId == 0)
            //    {
            //        lastAnnotation = ann;
            //    }
            //    else
            //    {
            //        ann.InReplyTo = lastAnnotation;
            //    }
            //    doc.Pages[comment.PageNumber].Annotations.Add(ann);
            //}

            //MemoryStream stream = new MemoryStream();
            //doc.Save(stream);
            //return stream.ToArray();
            return data;
        }

    }
}
<file_sep>/iManageIntegration/Common/VersionInfoBlock/AssemblyVersionInfoBlock.cs
using System;
using System.Reflection;
using System.Runtime.InteropServices;
// This common assembly info file is used by all assemblies to define version, etc.
// If you want to add a Assembly unique value, you must add a AssemblyInfo file
// to your project.

// When you add this file to new projects, you must 'Add existing file' and
// open it with the dropdown arrow with 'Link File'.  Otherwise it will copy
// the file to the local directory and it won't get updated.

#if !THIRD_PARTY_LIBRARY
[assembly: AssemblyProduct("Workshare IManage Integration")]
#endif
<file_sep>/WSComponents/src/WSComponents/Views/CeaseCollaborationDialog/WorkUnits/BreakWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Windows.Forms.VisualStyles;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.DmsItems.Visitors;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies.ActionStrategy;

namespace Workshare.Components.Views.CeaseCollaborationDialog.WorkUnits
{
    public class BreakWorkUnit : WorkUnit
    {
        private readonly CeaseCollaborationDialogViewModel _vm;
        public BreakWorkUnit(CeaseCollaborationDialogViewModel vm, IModuleView view)
            : base(view)
        {
            _vm = vm;
        }

        public override void Execute()
        {
            var processor = _vm.Module.Resolve<Processor>();
            processor.BreakLink(_vm.ScanResult.Maps.First());
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/Activity.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;

namespace WorksharePlatform
{
    public class Activity
    {
        public string Noun { get; set; }
        public string Verb { get; set; }
        public string UserName { get; set; }
        public string FolderName { get; set; }
        public string ChangesNameOld { get; set; }
        public string ChangesNameNew { get; set; }
        public string TimeCreated { get; set; }
        public int ChangesVersionNew { get; set; }
        public int ChangesVersionOld { get; set; }
        public bool HistoryModify { get; private set; }
        public int MemberId { get; set; }
        public string MemberName { get; set; }
        public int CurrentVersion { get; set; }
        public string ActyvityId { get; set; }
        public const string TimeFormat = "dd MMM yyyy HH:mm";

        bool UserNameIsEmpty(string userName )
        {
            return string.Equals(userName, "null", StringComparison.InvariantCulture) || string.IsNullOrEmpty(userName);
        }

        private String GetUserNameOrAnonymousUser(string userName)
        {
            return UserNameIsEmpty(userName) ? "Unauthenticated user" : userName;
        }

        public string GetComment()
        {
            DateTime date;
            DateTime.TryParse(TimeCreated, out date);

            if (string.Equals(Noun, "File", StringComparison.InvariantCulture) && string.Equals(Verb, "Update", StringComparison.InvariantCulture))
            {
                HistoryModify = true;

                if ((ChangesNameOld != null && ChangesNameNew != null) && !string.Equals(ChangesNameOld, ChangesNameNew, StringComparison.InvariantCulture))
                    return string.Format(Properties.Resources.STR_ACTIVITY_FILE_RENAMED, GetUserNameOrAnonymousUser(UserName), date.ToString(TimeFormat));
               
                if (ChangesVersionOld < ChangesVersionNew)
                    return string.Format(Properties.Resources.STR_ACTIVITY_ADDED_NEW_VERSION, GetUserNameOrAnonymousUser(UserName), date.ToString(TimeFormat));
         
            }
            else if (string.Equals(Verb, "Download", StringComparison.InvariantCulture))
            {
                HistoryModify = false;
                return string.Format(Properties.Resources.STR_ACTIVITY_FILE_DOWNLOADED, GetUserNameOrAnonymousUser(UserName), date.ToString(TimeFormat));
            }

            if (string.Equals(Noun, "Comment", StringComparison.InvariantCulture) && string.Equals(Verb, "Create", StringComparison.InvariantCulture))
            {
                HistoryModify = true;
                return string.Format(Properties.Resources.STR_ACTIVITY_COMMENT_ADDED, date.ToString(TimeFormat)); 
            }

            if (string.Equals(Noun, "Member", StringComparison.InvariantCulture) &&
                string.Equals(Verb, "Create", StringComparison.InvariantCulture))
            {
                HistoryModify = false;
                if (!UserNameIsEmpty(UserName))
                {
                    return string.Format(Properties.Resources.STR_ACTIVITY_USER_ADDED, UserName,
                        GetUserNameOrAnonymousUser(MemberName), date.ToString(TimeFormat));
                }
                else
                {
                    return string.Format(Properties.Resources.STR_ACTIVITY_USER_ADDED_BY_SYSTEM,
                        GetUserNameOrAnonymousUser(MemberName), date.ToString(TimeFormat));
                }
            }
            return string.Empty;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Extensions/DMSItemExtensions.cs
﻿using System.Collections.Generic;
using Workshare.Integration.Interfaces;

namespace Workshare.Integration.Extensions
{
    public static class DMSItemExtensions
    {
        public static List<IDMSFolder> GetParentFolders(this IDMSItem item)
        {
            if (item is IDMSFile)
            {
                return ((IDMSFile)item).ParentFolders;
            }
            else if (item is IDMSFolder)
            {
                var parent = ((IDMSFolder)item).ParentFolder;
                if (parent != null)
                {
                    return new List<IDMSFolder> { parent };
                }
            }
            return new List<IDMSFolder>();
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/FileMapActivityChange.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Changes
{
    public enum ChangeType { 
        NotModified, 
        BothChanged, 
        LocalChanged, 
        RemoteChanged, 
        RemoteAdded, 
        NotSent, 
        RemoteDeleted, 
        NamesDiffer, 
        Uploaded, 
        DocTypeChanged, 
        FolderSharedWithOthers, 
        NotSentVersion, 
        VersionChangedAfterSend }

    public class FileActivityChange
    {
        public FileActivityChange()
        {
            this.ChangeDate = DateTime.Now;
        }

        public ChangeType Type { set; get; }

        public DateTime ChangeDate { set; get; }

        public string LocalName { set; get; }
        public string WsName { set; get; }
        public string LocalDocType { get; set; }
        public string WsDocType { get; set; }
        public string OtherMemberViewLink { get; set; }
        public int OtherMemebersCount { set; get; }


        List<WsVersion> _newerVersions = new List<WsVersion>();

        public List<WsVersion> NewerVersions
        {
            get { return _newerVersions; }
            set
            {
                _newerVersions = value ?? new List<WsVersion>();
            }
        }

        public override string ToString()
        {
            return Type.ToString();
        }

        public FileMapActivity Parent { get; internal set; }

        public DateTime SavedTime { get; set; }

        public int VersionNumber { get; set; }

        public string LocalVersionId { get; set; }

        public WsUser FolderSharedBy { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncUploadFilesDialog/WorkUnits/ProcessWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using Workshare.Components.Common;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.Views.TrueSyncUploadFilesDialog.VMs;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.TrueSyncUploadFilesDialog.WorkUnits
{
    public class ProcessWorkUnit:WorkUnit
    {
          private TrueSyncFilesScanDialogVm vm;

        private IEnumerable<DocumentActionVM> actions;

          public ProcessWorkUnit(TrueSyncFilesScanDialogVm vm, IEnumerable<DocumentActionVM> actionsToExecute)
              : base(vm.View)
        {
            this.vm = vm;
              this.actions = actionsToExecute;
        }

        public override void OnAdded()
        {
            foreach (var actionVm in actions)
            {
                actionVm.activityVm. OnStartProcessing();
            }   
        }

        public override void Execute()
        {
            try
            {
                foreach (var documentActionVm in actions)
                {
                    ParentScan parentScan = vm.ParentScans.First();

                    var processor = vm.Module.Resolve<Processor>();
                    var processOptions = new ProcessOptions();
                    processOptions.ActionsToApply.AddRange(actions.Select(a => a.action).ToList());
                    var processedScan = processor.Process(parentScan.Scan, processOptions);

                    var activityFinder = vm.Module.Resolve<ActivityFinder>();
                    var uploadActivities = parentScan.Activities.Select(a => a.data).OfType<UploadFileActivity>();
                    activityFinder.UpdateUploadActivities(processedScan, uploadActivities);

                    var toUpdate = actions.Select(a => a.activityVm).ToList();
                    vm.Dispatcher.Invoke(new Action(() => toUpdate.ForEach(a => a.PropertyChangedAll())));
                    if (uploadActivities.All(a => a.State == UploadFileActivityState.Uploaded))
                    {
                        vm.Dispatcher.BeginInvoke(new Action(() => vm.RaiseClose(true)));
                        return;
                    }
                }
            }
            catch (Exception ex)
            {
                vm.View.ShowError(ex);
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/DmsScanStrategyBase.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Strategies
{
    public abstract class DmsScanStrategyBase
    {
        //scans file and populates map with appropriate values
        public abstract ScanResult Scan(BaseDMSFile dmsFile, FileMap fileResult, DmsFileScanOptions args);

        //scans _folder and populates map with appropriate values
        public abstract ScanResult Scan(BaseDMSFolder dmsFolder, FolderMap map, DmsFolderScanOptions args);

        //scan _folder for new wsFilesToVisit on ws and adds new child maps to flder map
        //public abstract ScanResult ScanForNewFilesOnWs(FolderMap parentFolderMap, DmsFolderScanOptions args);
        
        //scans document version and populates map with appropriate values
        public abstract ScanResult Scan(BaseDmsVersion dmsVersion, VersionMap versionMap, DmsVersionScanOptions args);

        public abstract ScanResult ScanForNewVersionsOnWs(BaseDMSFile dmsfile, FileMap currentFileMap, DmsFileScanOptions options);

        public abstract ScanResult GetWsItemsToVisit(FolderMap parentFolderMap, out List<WsFolder> wsFoldersToVisit, out List<WsFile> wsFilesToVisit, bool useForceRequest = true);
    }

    public class ScanResult
    {
        public static ScanResult Scanned = new ScanResult(ProcessState.Scanned);
        public static ScanResult Cancelled = new ScanResult(ProcessState.Cancelled);

        public static ScanResult ErrorResult(Exception ex)
        {
            return new ScanResult(ProcessState.Error)
            {
                Error = ex
            };
        }

        public ScanResult(ProcessState result)
        {
            Result = result;
        }
        public ProcessState Result { private set; get; }
        public Exception Error { set; get; }
    }

    public class DmsFileScanOptions
    {
        public bool SkipChildren { get; set; }
        public bool UseForceRequest { get; set; }
    }

    public class DmsFolderScanOptions
    {
        public bool SkipChildren { get; set; }
        public bool UseForceRequest { get; set; }
    }

    public class DmsVersionScanOptions
    {
        public bool UseForceRequest { get; set; }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Interfaces/IDMSItems.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Integration.Common;
using WorksharePlatform;

namespace Workshare.Integration.Interfaces
{
    public interface IDMSItemID
    {
        bool EqualTo(IDMSItemID obj);
    }

    public interface IDMSItem
    {
        IDMSItemID ID { get; }
        int DMSId { get; }
        string DMSItemKey { get; }
        string Name { get; set; }
        bool DoesUserHavePermissions(Enums.Permissions permissions);
        bool CheckedOutToUser { get; }
        bool CheckedOut { get; }
        string DisplayName { get; set; }
        IDMSFolder ParentFolder { get; }
        bool WasUpdatedAfterSend2(bool useForceRequest = true);
        void OnBeforeSending(OperationContext context);
        void OnAfterSending(OperationContext context);
        void OnSendError(object args, Exception e);
        void AddHistory(string eventName, string eventComment, Workshare.Integration.Operations operation);
        void AddHistories(List<Activity> activities);
        IDMSFolder RootFolder();
    }

    public interface IDMSFolder:IDMSItem
    {
        IDMSFolder AddSubFolder(FolderDetails cloudFolder);
        IEnumerable<IDMSFolder> SubFolders { get; set; }
        IEnumerable<IDMSFile> Files { get; set; }
        bool IsDeleted { get; }
    }

    public interface IDMSFile:IDMSItem
    {
        string GetFilePath();
        DateTime Modified { get; }
        bool IsCheckedOutFileExists();
        List<IDMSFolder> ParentFolders { get; }
        IDMSFile GetLatest();
        void DiscardCheckout(bool deleteCheckOutFile = false);
        IEnumerable<IDmsVersion> GetVersions();//all versions including latest version
        IDmsVersion AddVersion(string filePath, FileDetails file, List<Activity> activities, string versionFriendlyName = null, bool checkInVersion = false, bool keepLocalState = false);
    }

    public interface IDmsVersion
    {
        string Id{get;}
        int Number{get;}
        object ID { get; }
        DateTime EditTime { get; }
        IDMSFile GetLatestFile();
        bool WasChangedAfterSend2(bool useForcerequest = true );
        IDMSFile AsFile();
    }

}
<file_sep>/WSComponents/src/WSCloudService/Member.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WorksharePlatform
{
    public class Member
    {
        public string MemberName { get; set; }
        public int    MemberId { get; set; }

        public bool IsDeleted { get; set; }
        public string Email { get; set; }
    }
}
<file_sep>/WSComponents/src/WSCloudService/MultiPartDetails.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WorksharePlatform
{
    public class MultiPartDetails
    {
        public int PartNum { get; set; }
        public string Action { get; set; }
        public string ContentType { get; set; }
        public string Authorisation { get; set; }
        public string AmsDate { get; set; }
        public long Loaded { get; set; }
    }
}
<file_sep>/WSComponents/src/WSCloudService/PlatformService.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.Specialized;
using System.Diagnostics;
using System.Globalization;
using System.IO;
using System.Linq;
using System.Net;
using System.Security.Cryptography;
using System.Text;
using System.Threading;
using Microsoft.Win32;

namespace WorksharePlatform
{
    class CompareStrAsDate : IComparer<string>
    {
        public int Compare(string x, string y)
        {
            var d1 = DateTime.Now;
            var d2 = DateTime.Now;

            if (DateTime.TryParse(x, out d1) && DateTime.TryParse(y, out d2))
            {
                return DateTime.Compare(d1, d2);
            }
            return 0;
        }
    }

    public enum RoleOfDictionary { users, accounts }

    public static class PlatformService
    {
        private static int _retried;
        const int LimitEntriesPerPage = 100;

        static PlatformService()
        {
            ServicePointManager.ServerCertificateValidationCallback += ((sender, certificate, chain, sslPolicyErrors) => true);
        }

        public static void SignUp(UserDetails user)
        {
            var queryStrings = new NameValueCollection();

            queryStrings.Add("user[start_trial_on_validation]", "false");
            queryStrings.Add("user[utm_source]", "");
            queryStrings.Add("user[utm_content]", "");
            queryStrings.Add("start_trial", "true");
            queryStrings.Add("user[company_name]", user.Company);
            queryStrings.Add("user[username]", user.UserName);
            queryStrings.Add("user[email]", user.Email);
            queryStrings.Add("user[password]", user.Password);
            queryStrings.Add("user[password_confirmation]", user.ConfirmPassword);
            using (var client = new CookieAwareClient(user))
            {
                var result = client.PostValues("sign_ups.json", queryStrings);
                var returnResponse = Encoding.UTF8.GetString(result);
                returnResponse.Contains(string.Format("\"name\":\"{0}\"", user.UserName));
            }

            // Response could be {"id":362,"name":"WPLTEST 01","email":"<EMAIL>","uuid":"cb25e9c7-b82f-4509-a228-dcef5340a870",
            //"avatar":"https://skydox-public.s3.amazonaws.com/images/profile_pic.png","phone_number":null,"company_name":"Workshare Testing",
            //"is_unknown_user":true,"is_deactivated":false,"is_admin":false,"is_enterprise_admin":false,"account_multipart_allowed":false,
            //"start_trial_on_validation":true,"created_at":"2012-10-11T09:46:34Z","updated_at":"2012-10-11T10:34:21Z",
            //"validated_at":null,"account":{"id":345,"name":"Workshare","created_at":"2012-10-11T09:46:34Z","domain":null,"custom_logo":null},
            //"root_folder_id":3180,"inbox_folder_id":3181,"sent_folder_id":3182}
        }

        public static void RefreshUserIfNeeded(UserDetails user)
        {
            if (user.RootFolderId == 0)
            {
                RefreshUserData(user);
            }
        }

        public static void RefreshUserData(UserDetails user)
        {
            using (var client = new CookieAwareClient(user))
            {
                var result = client.GetString4("current_user.json?includes=u.profile,u.folders,a.core");

                var userData = JsonParser.ParseCurrentUserData(result);

                user.UserId = userData.UserId;
                user.AccountId = userData.AccountId;
                user.AccountUuId = userData.AccountUuId;
                user.RootFolderId = userData.RootFolderId;
                user.Email = userData.Email;
                user.UserName = userData.UserName;
                user.Domain = userData.Domain;
            }
        }

        public static List<UserDetails> GetAccountUsersData(UserDetails user)
        {
            using (var client = new CookieAwareClient(user))
            {
                var result = client.GetString3(string.Format("accounts/{0}/users.json", user.AccountId));
                var usersData = JsonParser.ParseAccountUsersData(result);

                var paginationDataDict = JsonParser.Parsepagination(result);
                int pagesCount = paginationDataDict.ContainsKey("total_pages") ? paginationDataDict["total_pages"] : 0;
                for (int i = 2; i <= pagesCount; i++)
                {
                    result = client.GetString3(string.Format("accounts/{0}/users.json?page={1}", user.AccountId, i));
                    usersData.AddRange(JsonParser.ParseAccountUsersData(result));
                }

                usersData.ForEach(u =>
                {
                    u.Domain = user.Domain;
                    u.AccountId = user.AccountId;
                    u.AccountUuId = user.AccountUuId;
                });

                return usersData;
            }
        }

        public static void Login(UserDetails user)
        {
            var queryStrings = new NameValueCollection();
            queryStrings.Add("user_session[email]", user.Email);
            queryStrings.Add("user_session[password]", user.Password);

            using (var client = new CookieAwareClient(user))
            {
                client.PostValues("user_sessions.json", queryStrings);
                if (client.CookieContainer.Count == 0)                                           //refactored
                {
                    throw new UnauthorizedAccessException();
                }
            }
        }

        public static WSServer GetWSServer(UserDetails user, string type = "dms")
        {
            using (var client = new CookieAwareClient(user))
            {
                var result = client.GetString("push_settings.json?ctype=" + type);
                if (client.CookieContainer.Count == 0)                                           //refactored
                {
                    throw new UnauthorizedAccessException();
                }
                return JsonParser.ParseWSServerData(result);
            }
        }

        public static UserDetails GetUserByUserId(UserDetails user, string userid)
        {
            using (var client = new CookieAwareClient(user))
            {
                string result = client.GetString2(string.Format("users/find_by_token.json?token={0}", userid));
                return JsonParser.ParseUserInfo(result);
            }
        }

        public static List<FolderDetails> GetFolders(UserDetails user)
        {
            var found = new List<FolderDetails>();
            RefreshUserIfNeeded(user);
            using (var client = new CookieAwareClient(user))
            {
                string qry = "folders.json";
                var result = client.GetString4(qry);

                if (string.IsNullOrEmpty(result) == false)
                {
                    found.AddRange(JsonParser.ParseFoldersResult(result));
                }
            }
            return found;
        }

        public static bool IsFolderExists(UserDetails user, int folderId, int parentFolderId)
        {
            if (folderId == 0)
            {
                return true;
            }
            try
            {
                var folder = GetFolder(user, folderId);
                return folder != null && !folder.IsDeleted;
            }
            catch (WebException ex)
            {
                if (ex.Response != null && ((HttpWebResponse)ex.Response).StatusCode == HttpStatusCode.NotFound)
                {
                    return false;
                }
                throw;
            }
        }

        public static FolderDetails GetFolder(UserDetails user, int folderId)
        {
            using (var client = new CookieAwareClient(user))
            {
                var result = client.GetString4(string.Format("folders/{0}.json", folderId));

                if (!string.IsNullOrEmpty(result))
                {
                    var folder = JsonParser.ParseFolderResult(result);

                    if (folder.ParentId != folder.Ancestry)
                    {
                        string parentResult = string.Empty;

                        try
                        {
                            parentResult = client.GetString4(string.Format("folders/{0}.json", folder.ParentId));
                        }
                        catch (WebException e) 
                        {
                            // skip if we haven't access to a parent folder otherwise throw exeption
                            if (!e.IsStatusCode(HttpStatusCode.Forbidden)) throw;
                        }

                        if (!string.IsNullOrEmpty(parentResult))
                        {
                            var parentFolder = JsonParser.ParseFolderResult(parentResult);

                            if (parentFolder.IsDeleted)
                            {
                                folder.IsDeleted = true;
                            }
                        }
                    }

                    UserDetails userDetails = GetUserByUserId(user, folder.Owner.UserId);
                    folder.Owner.UserName = userDetails.UserName;

                    return folder;
                }
            }
            return null;
        }



        public static FolderDetails TryGetFolder(UserDetails user, int folderId)
        {
            FolderDetails folder;
            try
            {
                folder = GetFolder(user, folderId);
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode(HttpStatusCode.Unauthorized)) throw;
                if (ex.IsStatusCode(HttpStatusCode.NotFound))
                {
                    return null;
                }
                throw;
            }
            return folder;
        }

        public static DialogSettings GetDialogSettings(UserDetails user)
        {
            using (var client = new CookieAwareClient(user))
            {
                string result = client.GetString2(string.Format("settings.json"));
                if (string.IsNullOrEmpty(result) == false)
                {
                    return JsonParser.ParseDialogSettings(result);
                }
                return null;
            }
        }

        public static FolderMembers GetAncestor(UserDetails user, int folderId)
        {
            var members = new List<UserDetails>();
            using (var client = new CookieAwareClient(user))
            {
                string result = client.GetString(string.Format("folders/{0}/members/ancestry.json", folderId));
                members.AddRange(JsonParser.ParseMembersResult(result));
            }
            return new FolderMembers { Members = members };
        }

        public static FolderDetails CreateFolder(UserDetails user, string name, string description, int parentFolderId = 0, bool notifyOwner = true, DateTime? expireAt = null)
        {
            var queryStrings = new NameValueCollection
            {
                {"folder[name]", name},
                {"folder[description]", description},
                {"folder[notify_owner]", notifyOwner.ToString().ToLower()},
                {"folder[expires_at]", (expireAt == null) ? "null" : expireAt.Value.ToUniversalTime().ToString(CultureInfo.InvariantCulture)},
                {"folder[parent_id]", parentFolderId.ToString(CultureInfo.InvariantCulture)}
            };

            using (var client = new CookieAwareClient(user))
            {
                var result = client.PostValues4("folders.json", queryStrings);
                if (result != null)
                {
                    var folder = JsonParser.ParseFolderResult(result);

                    UserDetails userDetails = GetUserByUserId(user, folder.Owner.UserId);
                    folder.Owner.UserName = userDetails.UserName;

                    return folder;
                }
            }
            return null;
        }

        private static void SetInheritFromParentFolderPermission(UserDetails user, FolderDetails folder, bool state)
        {
            string action = string.Format("folders/{0}/permission.json", folder.Id);
            var queryStrings = new NameValueCollection
            {
                {"permission[inherits_from_parent]", state.ToString().ToLower()}
            };

            using (var client = new CookieAwareClient(user))
            {
                client.PutValues(action, queryStrings);
            }
        }

        public static void ApplyPermissionToFolder(UserDetails user, FolderDetails folder)
        {
            SetInheritFromParentFolderPermission(user, folder, false);

            string action = string.Format("folders/{0}/permission.json", folder.Id);
            var queryStrings = new NameValueCollection
            {
                {"permission[can_download_original]", folder.Permissions.DownloadFiles.ToString().ToLower()},
                {"permission[can_download_pdf]", folder.Permissions.DownloadFiles.ToString().ToLower()},
                {"permission[can_upload_changes]", folder.Permissions.CanAddVersions.ToString().ToLower()},
                {"permission[can_manipulate]", folder.Permissions.CanAddOrRemoveFiles.ToString().ToLower()},
                {"permission[can_access_anonymously]", (!folder.Permissions.User_must_login).ToString().ToLower()},
                {"permission[can_invite_with_link]", folder.Permissions.Member_may_invite.ToString().ToLower()}
            };

            using (var client = new CookieAwareClient(user))
            {
                client.PutValues(action, queryStrings);
            }
        }

        public static void ShareFolderWith(UserDetails user, FolderDetails folder, string emails, string mailSubject, string mailBody)
        {
            string action = string.Format("folders/{0}/add_member_by_email.json", folder.Id);

            var queryStrings = new NameValueCollection
            {
                {"invite_email_body", mailBody},
                {"invite_email_subject", mailSubject},
                {"invite_email_list", emails}
            };

            using (var client = new CookieAwareClient(user))
            {
                client.PostValues(action, queryStrings);
            }
        }

        public static void DeleteFolder(UserDetails user, int folderId)
        {
            using (var client = new CookieAwareClient(user))
            {
                client.DeleteValues(string.Format("folders/{0}.json", folderId), new NameValueCollection());
            }
        }

        public static void DeleteFile2(UserDetails user, int fileId)
        {
            try
            {
                using (var client = new CookieAwareClient(user))
                {
                    client.DeleteValues2(string.Format("files/{0}.json", fileId), new NameValueCollection());
                }
            }
            catch (WebException)
            {
                throw;
            }
        }

        public static void CopyFile(UserDetails user, int sourceFileId, int destinationFolderId)
        {
            const string action = "files/copy_from.json";

            var queryStrings = new NameValueCollection
            {
                {"source_file_id", sourceFileId.ToString(CultureInfo.InvariantCulture)},
                {"target_folder_id", destinationFolderId.ToString(CultureInfo.InvariantCulture)}
            };

            using (var client = new CookieAwareClient(user))
            {
                client.PostValues(action, queryStrings);
            }
        }

        public static void CreateVersionForNewFile3(UserDetails user, FileDetails file)
        {
            var queryStrings = new NameValueCollection { { "file_version[binary_file_file_name]", file.Name } };
            if (file.IsChunkingRequired == false)
            {
                queryStrings.Add("file_version[complete_file_provide_upload_info]", "true");
            }
            queryStrings.Add("file_version[name]", file.FriendlyName);
            queryStrings.Add("file_version[folder_id]", file.FolderId.ToString(CultureInfo.InvariantCulture));

            using (var client = new CookieAwareClient(user))
            {
                var results = client.PostValuesVersion3("file_versions.json", queryStrings);
                var currentVersion = JsonParser.ParseVersionResult3(results, file.IsChunkingRequired);

                file.CurrentVersion = currentVersion;
                file.Id = file.CurrentVersion.FileId;
            }
        }

        public static void CreateNewVersionOfFile(UserDetails user, FileDetails file)
        {
            var queryStrings = new NameValueCollection { { "deck_version[binary_file_file_name]", file.Name } };
            if (file.IsChunkingRequiredForUpload == false)
            {
                queryStrings.Add("deck_version[complete_file_provide_upload_info]", "true");
            }
            queryStrings.Add("deck_version[name]", file.FriendlyName);
            queryStrings.Add("deck_version[folder_id]", file.FolderId.ToString(CultureInfo.InvariantCulture));

            using (var client = new CookieAwareClient(user))
            {
                var results = client.PostValuesVersion3(string.Format("files/{0}/file_versions.json", file.Id), queryStrings);

                file.CurrentVersion = JsonParser.ParseVersionResult3(results, file.IsChunkingRequiredForUpload);
                file.CurrentVersion.FileId = file.Id;
            }
        }

        public static void CommitNewFile(UserDetails user, FileDetails file)
        {
            var start = Stopwatch.StartNew();
            try
            {
                var queryStrings = new NameValueCollection { { "file_version[apply_changes]", "true" } };

                using (var client = new CookieAwareClient(user))
                {
                    var results = client.PutValues(string.Format("file_versions/{0}.json", file.CurrentVersion.Id), queryStrings);
                    start.Stop();
                    var ver = JsonParser.ParseVersionResult(results, file.IsChunkingRequired);
                    if (ver != null)
                    {
                        file.CurrentVersion.Size = ver.Size;
                        _retried = 0;
                        return;
                    }
                }
            }
            catch (WebException ex)
            {
                start.Stop();
                var response = ex.Response as HttpWebResponse;
                if (response != null)
                {
                    if ((int)response.StatusCode == 422
                        && _retried < 3)
                    {
                        //Debug.WriteLine(string.Format("Retrying error as it is 422"), "PLATFORMTESTS");
                        Thread.Sleep(4000);
                        CommitNewFile(user, file);
                    }
                    else { throw; }

                }
                _retried = 0;
                throw;
            }
            throw new Exception();
        }

        public static void CommitNewVersionOfFile(UserDetails user, FileDetails file)
        {
            var start = Stopwatch.StartNew();
            try
            {
                var queryStrings = new NameValueCollection { { "deck_version[apply_changes]", "true" } };

                using (var client = new CookieAwareClient(user))
                {
                    var results = client.PutValues(string.Format("/deck_versions/{0}.json", file.CurrentVersion.Id), queryStrings);
                    start.Stop();
                    var ver = JsonParser.ParseVersionResult(results, file.IsChunkingRequired);
                    if (ver != null)
                    {
                        file.CurrentVersion.Size = ver.Size;
                        _retried = 0;
                        return;
                    }
                }
            }
            catch (WebException ex)
            {
                start.Stop();
                var response = ex.Response as HttpWebResponse;
                if (response != null)
                {
                    if ((int)response.StatusCode == 403
                        && _retried < 3)
                    {
                        //Debug.WriteLine(string.Format("Retrying error as it is 403"), "PLATFORMTESTS");
                        Thread.Sleep(4000);
                        CommitNewVersionOfFile(user, file);
                    }
                    else { throw; }
                }
                _retried = 0;
            }
            //return false;
            throw new Exception();
        }

        public static void CreateOrUpdateWDSDictionary(UserDetails user, string dicName, string dicData, RoleOfDictionary role)
        {
            RefreshUserIfNeeded(user);
            var id = role == RoleOfDictionary.users ? user.UserId : user.AccountUuId;
            using(var client = new CookieAwareClient(user))
            {
                client.PutUserWDSValue(string.Format(CultureInfo.CurrentCulture, "{0}/{1}/dictionaries/{2}.json", role, id, dicName), dicData);
            }
        }

        public static string GetWDSDictionary(UserDetails user, string dicName, RoleOfDictionary role)
        {
            RefreshUserIfNeeded(user);
            var id = role == RoleOfDictionary.users ? user.UserId : user.AccountUuId;
            using (var client = new CookieAwareClient(user))
            {
                var result = client.GetDictionaryString(string.Format(CultureInfo.CurrentCulture, "{0}/{1}/dictionaries/{2}.json", role, id, dicName));
                if (result != null)
                {
                    return result;
                }
            }

            return null;
        }

        public static List<string> GetWDSDictionaries(UserDetails user, RoleOfDictionary role)
        {
            RefreshUserIfNeeded(user);

            var results = new List<string>();
            var id = role == RoleOfDictionary.users ? user.UserId : user.AccountUuId;
            using (var client = new CookieAwareClient(user))
            {
                var result = client.GetDictionaryString(string.Format(CultureInfo.CurrentCulture, "{0}/{1}/dictionaries.json", role, id));
                if (result != null)
                {
                    var returnedStrings = result.Split(new[] { "}," }, StringSplitOptions.None).ToList();
                    var correctStrings = new List<string>();
                    int count = 0;
                    foreach (var item in returnedStrings)
                    {
                        var val = item;
                        count++;

                        if (returnedStrings.Count != count)
                        {
                            val = item + "}";
                        }

                        results.Add(val);
                    }
                    return results;
                }
            }

            return null;
        }

        public static void DeleteWDSDictionary(UserDetails user, string dicName, RoleOfDictionary role)
        {
            RefreshUserIfNeeded(user);
            var id = role == RoleOfDictionary.users ? user.UserId : user.AccountUuId;
            using (var client = new CookieAwareClient(user))
            {
                client.DeleteDictionary(string.Format(CultureInfo.CurrentCulture, "{0}/{1}/dictionaries/{2}.json", role, id, dicName));
            }
        }

        public static void PostToAwsSingle(UserDetails user, FileDetails file)
        {
            var queryStrings = new Dictionary<string, object>
            {
                {"key", file.CurrentVersion.Key},
                {"Cache-Control", file.CurrentVersion.Cache},
                {"AWSAccessKeyId", file.CurrentVersion.AwsAccessKey},
                {"acl", file.CurrentVersion.AclType},
                {"success_action_redirect", file.CurrentVersion.SuccessRedirect},
                {"policy", file.CurrentVersion.Policy},
                {"signature", file.CurrentVersion.Signature},
                {"Content-Type", file.CurrentVersion.ContentType},
                {"x-amz-server-side-encryption", file.CurrentVersion.Encryption},
                {"file", file}
            };

            using (var client = new CookieAwareClient(user))
            {
                client.MultipartFormData(file.CurrentVersion.Action, queryStrings);
            }
            //return false;
        }

        public static void PostToAwsSingle3(UserDetails user, FileDetails file)
        {
            var queryStrings = new Dictionary<string, object>
            {
                {"success_action_redirect", file.CurrentVersion.SuccessRedirect},
                {"file", file}
            };

            using (var client = new CookieAwareClient(user))
            {
                client.MultipartFormData3(file.CurrentVersion.Action, file, file.CurrentVersion.HttpVerb);
            }
        }

        public static void InitiateChunking(UserDetails user, FileDetails file)
        {
            var queryStrings = new NameValueCollection { { "initiate_multipart", "true" } };
            using (var client = new CookieAwareClient(user))
            {
                var result = client.PutValues(string.Format("/cloud_files/{0}.json", file.CurrentVersion.CompleteId), queryStrings);
                file.CurrentVersion.MultiPartId = JsonParser.ParseMultiPartId(result);
            }
        }

        public static void UploadFileInChunks(UserDetails user, FileDetails file)
        {
            long fileSize = FileDetails.GetFileSizeByFilePath(file.FilePath);
            var parts = fileSize / FileDetails.ChunkSize;
            if (fileSize % FileDetails.ChunkSize != 0)
            {
                // There was a remainder to the division, so add one to account for it.
                parts++;
            }

            using (Stream stream = File.Open(file.FilePath, FileMode.Open, FileAccess.Read, FileShare.None))
            {
                using (BinaryReader br = new BinaryReader(stream))
                {
                    for (int partNum = 1; partNum <= parts; partNum++)
                    {
                        GetMultiPartInfo(user, file, partNum);

                        long chunkSize = ((stream.Length - file.CurrentPart.Loaded) > FileDetails.ChunkSize) ? FileDetails.ChunkSize : (stream.Length - file.CurrentPart.Loaded);
                        UploadChunkToS3Bucket(user, file, br.ReadBytes((int)chunkSize));
                    }
                }
            }
        }

        public static void GetMultiPartInfo(UserDetails user, FileDetails file, int partNum)
        {
            using (var client = new CookieAwareClient(user))
            {
                // Notify Platform of the chunk to be uploaded
                var p = string.Format("multipart_upload_id={0}&part_number={1}", file.CurrentVersion.MultiPartId, partNum);
                var result = client.GetString(string.Format("/cloud_files/{0}.json?{1}"
                    , file.CurrentVersion.CompleteId, p));

                var loaded = file.CurrentPart == null ? 0 : file.CurrentPart.Loaded;
                file.CurrentPart = JsonParser.ParseMultiPart(result);

                if (string.IsNullOrEmpty(file.CurrentPart.Action) == false)
                {
                    file.CurrentPart.PartNum = partNum;
                    file.CurrentPart.Loaded = loaded;
                }
            }
        }

        public static List<FileVersionDetails> GetVersionDetails(UserDetails user, FileDetails file)
        {
            var versions = GetVersionDetails(user, file.Id);
            var maxVersionId = versions.Max(p => p.Version);
            file.Versions = versions;
            if (file.CurrentVersion == null || file.CurrentVersion.Version != maxVersionId)
            {
                file.CurrentVersion = versions.FirstOrDefault(p => p.Version == maxVersionId);
            }
            return file.Versions;
        }

        public static List<FileVersionDetails> GetVersionDetails(UserDetails user, int fileId)
        {
            var res = new List<FileVersionDetails>();
            GetFromAllPages(user, (client, paginationPart) =>
            {
                string action = string.Format("files/{0}/file_versions.json?{1}", fileId, paginationPart);

                var result = client.GetString2(action);

                res.AddRange(JsonParser.ParseVersionsResult(result).Except(res, new FileVersionIdComparer()));
                return result;
            });
            return res;

        }

        public static List<FileComment> GetFileComments(UserDetails user, int file_id)
        {
            using (var client = new CookieAwareClient(user))
            {
                string action = string.Format("comments.json?file_id={0}", file_id.ToString());

                var result = client.GetString(action);

                return JsonParser.ParseFileCommentsResult(result);
            }
        }

        public static List<FileVersionDetails> GetVersionDetails2(UserDetails user, FileDetails file)
        {
            var versions = GetVersionDetails2(user, file.Id);
            var maxVersionId = versions.Max(p => p.Version);
            file.Versions = versions;
            if (file.CurrentVersion == null || file.CurrentVersion.Version != maxVersionId)
            {
                file.CurrentVersion = versions.FirstOrDefault(p => p.Version == maxVersionId);
            }
            return file.Versions;
        }

        public static List<FileVersionDetails> GetVersionDetails2(UserDetails user, int fileId)
        {
            var res = new List<FileVersionDetails>();
            GetFromAllPages(user, (client, paginationPart) =>
            {
                string action = string.Format("files/{0}/file_versions.json?{2}", fileId, paginationPart);

                var result = client.GetString(action);

                res.AddRange(JsonParser.ParseVersionsResult(result).Except(res, new FileVersionIdComparer()));
                return result;
            });
            return res;
        }

        private static void UploadChunkToS3Bucket(UserDetails user, FileDetails file, byte[] data)
        {
            Stopwatch start = Stopwatch.StartNew();
            // S3 Upload
            using (var s3 = new CookieAwareClient(user))
            {
                s3.Uri = new Uri(file.CurrentPart.Action);
                s3.Headers.Clear();
                s3.Headers.Add("Content-Type", file.CurrentPart.ContentType);
                s3.Headers.Add("authorization", file.CurrentPart.Authorisation);
                s3.Headers.Add("x-amz-date", file.CurrentPart.AmsDate);
                file.CurrentPart.Loaded += data.Length;
                s3.UploadData(s3.Uri, "PUT", data);
                start.Stop();
            }
        }

        public static void CompleteChunking(UserDetails user, FileDetails file)
        {
            var queryStrings = new NameValueCollection
            {
                {"complete_multipart", "true"},
                {"multipart_upload_id", file.CurrentVersion.MultiPartId}
            };
            using (var client = new CookieAwareClient(user))
            {
                var result = client.PutValues(string.Format("/cloud_files/{0}.json", file.CurrentVersion.CompleteId), queryStrings);
                file.CurrentVersion.MultiPartId = JsonParser.ParseMultiPartId(result);
                if (string.IsNullOrEmpty(file.CurrentVersion.MultiPartId))
                {
                    throw new Exception("Cannot Complete cunking");
                }
            }
        }

        public static void UploadFile3(UserDetails user, FileDetails file)
        {
            CreateVersionForNewFile3(user, file);
            TryToUploadFile3(user, file);
            
            CommitNewFile(user, file);
        }

        private static void TryToUploadFile3(UserDetails user, FileDetails file, int count = 0)
        {
            int counter = count;
            try
            {
                if (file.IsChunkingRequired == false)
                {
                    PostToAwsSingle3(user, file);
                }
                else
                {
                    InitiateChunking(user, file);
                    UploadFileInChunks(user, file);
                    CompleteChunking(user, file);
                }
            }
            catch (WebException e)
            {
                if (e.IsStatusCode(HttpStatusCode.RequestTimeout) || e.IsStatusCode(HttpStatusCode.GatewayTimeout))
                { 
                    counter++;
                    if (counter <= 3)
                    {
                        TryToUploadFile3(user, file, counter);
                    }
                }
                throw;
            }
        }

        public static void UploadNewVersionOfFile(UserDetails user, FileDetails file)
        {
            CreateNewVersionOfFile(user, file);

            if (file.IsChunkingRequired == false)
            {
                if (file.CurrentVersion.ApiVersion == ApiVersion.One)
                {
                    PostToAwsSingle(user, file);
                }
                else { PostToAwsSingle3(user, file); }
            }
            else
            {
                InitiateChunking(user, file); //?
                UploadFileInChunks(user, file);
                CompleteChunking(user, file);
                #region Old_code
                //if (InitiateChunking(user, file))
                //{
                //    UploadFileInChunks(user, file);
                //    CompleteChunking(user, file);
                //}
                #endregion
            }
            CommitNewVersionOfFile(user, file);
        }

        public static void UploadNewVersionOfFile3(UserDetails user, FileDetails file)
        {
            CreateNewVersionOfFile(user, file);
            TryToUploadFile3(user, file);

            CommitNewVersionOfFile(user, file);
        }

        public static FileDetails GetFile(UserDetails user, int fileId, int folderId)
        {
            var stop = Stopwatch.StartNew();
            string result;
            RefreshUserIfNeeded(user);
            result = TryToGetFileResponse(user, fileId);
            stop.Stop();
            return JsonParser.ParseFileData(result, folderId);
        }

        private static string TryToGetFileResponse(UserDetails user, int fileId, int count = 0)
        {
            int counter = count;
            try
            {
                var client = new CookieAwareClient(user);
                return client.GetString2(string.Format("files/{0}.json", fileId));
            }
            catch (WebException e)
            {
                if (e.IsStatusCode(HttpStatusCode.RequestTimeout) || e.IsStatusCode(HttpStatusCode.GatewayTimeout))
                {
                    counter++;
                    if (counter <= 3)
                    {
                        TryToGetFileResponse(user, fileId, counter);
                    }
                }
                throw;
            }
        }

        public static FileDetails TryGetFile(UserDetails user, int fileId, int parentFolderIdToCheck = -1)
        {
            try
            {
                if (parentFolderIdToCheck == 0) parentFolderIdToCheck = user.RootFolderId;
                FileDetails file = GetFile(user, fileId, parentFolderIdToCheck);
                if (file.IsDeleted || (parentFolderIdToCheck != -1 && file.FolderId != parentFolderIdToCheck))
                {
                    return null;
                }

                return file;
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode(HttpStatusCode.Unauthorized)) throw;
                if (ex.IsStatusCode(HttpStatusCode.NotFound))
                {
                    return null;
                }
                
                throw;
            }
        }

        public static void GetFromAllPages(UserDetails user, Func<CookieAwareClient, string, string> action)
        {
            using (var client = new CookieAwareClient(user))
            {
                var prevPage = 0;
                while (true)
                {
                    string result = action(client, string.Format("limit={0}&page={1}", LimitEntriesPerPage, prevPage + 1));
                    var pagination = JsonParser.ParsePagination(result);
                    if (prevPage >= pagination.CurrentPage || pagination.CurrentPage >= pagination.TotalPages)
                    {
                        break;
                    }
                    prevPage = pagination.CurrentPage;
                }
            }
        }

        class FileIdComparer : IEqualityComparer<FileDetails>
        {
            public bool Equals(FileDetails x, FileDetails y)
            {
                return x.Id == y.Id;
            }

            public int GetHashCode(FileDetails obj)
            {
                return obj.Id;
            }
        }

        class FileVersionIdComparer : IEqualityComparer<FileVersionDetails>
        {
            public bool Equals(FileVersionDetails x, FileVersionDetails y)
            {
                return x.Id == y.Id;
            }

            public int GetHashCode(FileVersionDetails obj)
            {
                return obj.Id;
            }
        }

        public static List<FileDetails> GetFiles(UserDetails user, int folderId)
        {
            var files = new List<FileDetails>();
            RefreshUserIfNeeded(user);
            GetFromAllPages(user, (client, arg) =>
            {
                string result = TryToGetFilesResponse(client, folderId, arg);
                files.AddRange(JsonParser.ParseFilesResult(result, folderId).Except(files, new FileIdComparer()));
                return result;
            });

            return files;
        }

        private static string TryToGetFilesResponse(CookieAwareClient client, int folderId, string arg, int count = 0)
        {
            int counter = count;
            try
            {
                return client.GetString2(string.Format("folders/{0}/files.json?{1}", folderId, arg));
            }
            catch (WebException e)
            {
                if (e.IsStatusCode(HttpStatusCode.RequestTimeout) || e.IsStatusCode(HttpStatusCode.GatewayTimeout))
                {
                    counter++;
                    if (counter <= 3)
                    {
                        TryToGetFilesResponse(client, folderId, arg, counter);
                    }
                }
                throw;
            }
        }

        public static string DownloadFile(UserDetails user, FileDetails file)
        {
            return DownloadFile(user, file.Id);
        }

        public static string DownloadFile(UserDetails user, int fileId)
        {
            using (var client = new CookieAwareClient(user))
            {
                client.Uri = new Uri(ServiceUrl + string.Format("/files/{0}/download", fileId));
                return client.DownloadFile();
            }
        }

        public static string DownloadFileVersion(UserDetails user, int fileId, int versionId)
        {
            using (var client = new CookieAwareClient(user))
            {
                client.Uri = new Uri(ServiceUrl2 + string.Format("/files/{0}/download?version={1}", fileId, versionId));
                return client.DownloadFile();
            }
        }

        public static string DownloadFileInPdf(UserDetails user, int file_id)
        {
            using (var client = new CookieAwareClient(user))
            {
                client.Uri = new Uri(ServiceUrl + string.Format("/files/{0}/download_pdf", file_id));
                return client.DownloadFile();
            }
        }

        public static string DownloadFileVersionInPdf(UserDetails user, int file_id, int version_id)
        {
            using (var client = new CookieAwareClient(user))
            {
                client.Uri = new Uri(ServiceUrl4 + string.Format("/files/{0}/download_pdf?version={1}", file_id, version_id));
                return client.DownloadFile();
            }
        }

        public static string DownloadFileVersionInPdfWithComment(UserDetails user, string password, int versionId)
        {
            using (var client = new CookieAwareClient(user))
            {
                client.Uri = new Uri(ServiceUrl4 + string.Format("/d/{0}/pdfcomments?version={1}", password, versionId));
                return client.DownloadFile();
            }
        }

        public static List<FolderDetails> GetChildFolders(UserDetails user, int Folder_Id)
        {

            var found = new List<FolderDetails>();
            RefreshUserIfNeeded(user);
            using (var client = new CookieAwareClient(user))
            {
                string action = string.Format("folders.json?folder_id={0}", Folder_Id);
                var result = client.GetString(action);
                if (string.IsNullOrEmpty(result) == false)
                {
                    found.AddRange(JsonParser.ParseFoldersResult(result));
                }
            }
            return found;
        }



        public static readonly string DEFAULT_SERVER = MY_SERVER;

        public const string QA_SERVER = "qa.workshare.com";
        public const string MY_SERVER = "my.workshare.com";
        public const string DEV_SERVER = "dev2.workshare.com";


        public static bool UseHostFromRegistry = false;
        public static string _Host = null;
        public static string Host
        {
            get
            {
                if (UseHostFromRegistry)
                {
                    _Host = PlatformRegistryHelper.getFromRegisrty(RegData.Platform);
                }
                return _Host ?? DEFAULT_SERVER;
            }
            set
            {

                _Host = value;
            }
        }

        public static Uri HostWithSchema
        {
            get { return new Uri(string.Format("https://{0}", Host)); }
        }

        public static string ServiceUrl { get { return string.Format(CultureInfo.CurrentCulture, "https://{0}/api/v1.1", Host); } }
        public static string ServiceUrl2 { get { return string.Format(CultureInfo.CurrentCulture, "https://{0}/api/v1.2", Host); } }
        public static string ServiceUrl3 { get { return string.Format(CultureInfo.CurrentCulture, "https://{0}/api/v1.3", Host); } }
        public static string ServiceUrl4 { get { return string.Format(CultureInfo.CurrentCulture, "https://{0}/api/v1.4", Host); } }

        public static string ServiceDictionaryUrl { get { return string.Format(CultureInfo.CurrentCulture, "https://{0}/dictionaries/api/v1.0", Host); } }

        public static List<Activity> GetActivities(string request, UserDetails user, int folderId = 0, int fileId = 0, int version = 0)
        {
            Dictionary<string, int> pagination = null;
            var activityList = new List<Activity>();
            int page = 1;
            int totalPages = -1;

            RefreshUserIfNeeded(user);

            using (var client = new CookieAwareClient(user))
            {
                while (true)
                {
                    string result = client.GetString(request);

                    var activities = JsonParser.ParseActivities(result, folderId, fileId, version);

                    if (activities == null)
                        return null;

                    activityList.AddRange(activities);

                    if (pagination == null)
                    {
                        pagination = JsonParser.Parsepagination(result);
                        totalPages = pagination["total_pages"];
                    }

                    if (page >= totalPages || totalPages <= 0)
                    {
                        break;
                    }

                    page++;
                }
            }


            return activityList;
        }

        public static List<Activity> GetFileActivitiesImanage(UserDetails user, FileDetails wsFile, int version = 0, string lastActyvityId = "")
        {
            try
            {
                var requestFileActivity = string.IsNullOrEmpty(lastActyvityId) ? string.Format("notifications.json?file_id={0}&limit={1}&page={2}", wsFile.Id, LimitEntriesPerPage, 1) :
                    string.Format("notifications.json?file_id={0}&limit={1}&page={2}&later_than_id={3}", wsFile.Id, LimitEntriesPerPage, 1, lastActyvityId);

                var activityListFile = GetActivities(requestFileActivity, user, fileId: wsFile.Id);

                if (activityListFile == null)
                    return null;

                if (user.RootFolderId != wsFile.FolderId)
                {
                    var requestBase = string.Format("notifications.json?folder_id={0}&limit={1}&page={2}", wsFile.FolderId, LimitEntriesPerPage, 1);
                    var request = string.IsNullOrEmpty(lastActyvityId)
                        ? requestBase
                        : string.Format("{0}&later_than_id={1}", requestBase, lastActyvityId);

                    var activityListfolder = GetActivities(request, user, wsFile.FolderId);
                    if (activityListfolder.Any())
                    {
                        var sorted = activityListfolder.Where(p => p.Noun == "Member" && p.Verb == "Create").ToList();
                        var members = GetMembers(user, wsFile.FolderId);

                        foreach (var activity in sorted)
                        {
                            if (activity.CurrentVersion == 0)
                            {
                                if (wsFile.CurrentVersion == null)
                                {
                                    GetVersionDetails(user, wsFile);
                                }
                                DateTime dt;
                                if (DateTime.TryParse(activity.TimeCreated, out dt))
                                {
                                    var ver = wsFile.Versions.Where(v => v.CreateDate < dt)
                                        .Where(r => r != null)
                                        .OrderByDescending(t => t.CreateDate)
                                        .FirstOrDefault();

                                    activity.CurrentVersion = ver != null ? ver.Version : version;
                                }
                                else
                                {
                                    activity.CurrentVersion = wsFile.CurrentVersion != null ? wsFile.CurrentVersion.Version : version;
                                }
                            }
                            var firstMember = members.FirstOrDefault(p => p.MemberId == activity.MemberId);
                            if (firstMember != null)
                            {
                                activity.MemberName = firstMember.MemberName;
                            }
                        }

                        activityListFile.AddRange(sorted);

                        return activityListFile.OrderBy(p => p.TimeCreated, new CompareStrAsDate()).ToList();
                    }
                }


                activityListFile.Reverse();

                return activityListFile;
            }
            catch (WebException wex)
            {
                if (wex.IsStatusCode(HttpStatusCode.Unauthorized)) throw;
                return new List<Activity>();
            }

            catch (Exception)
            {
                return new List<Activity>();
            }
        }


        private static string GetRequestUrl(int fileId, int folderId, string lastActyvityId = "")
        {
            if (fileId != 0)
            {
                var requestFileActivity = string.IsNullOrEmpty(lastActyvityId)
                ? string.Format("notifications.json?file_id={0}&limit={1}&page={2}", fileId, LimitEntriesPerPage, 1)
                : string.Format("notifications.json?file_id={0}&limit={1}&page={2}&later_than_id={3}", fileId, LimitEntriesPerPage, 1,
                    lastActyvityId);

                return requestFileActivity;
            }

            var requestBase = string.Format("notifications.json?folder_id={0}&limit={1}&page={2}", folderId, LimitEntriesPerPage, 1);
            var request = string.IsNullOrEmpty(lastActyvityId)
                ? requestBase
                : string.Format("{0}&later_than_id={1}", requestBase, lastActyvityId);

            return request;
        }

        public static List<Member> GetMembers(UserDetails user, int folderId)
        {
            string result;
            Dictionary<string, int> pagination = null;
            var members = new List<Member>();//null;
            int page = 1;

            RefreshUserIfNeeded(user);

            using (var client = new CookieAwareClient(user))
            {
                while (true)
                {
                    //GET /api/v1.2/folders/368384/members/ancestry.json?page=1&rqtime=1390580996217 HTTP/1.1
                    result = client.GetString(string.Format("folders/{0}/members/ancestry.json?limit={1}&page={2}", folderId, LimitEntriesPerPage, page));
                    members.AddRange(JsonParser.ParseMembers(result));

                    if (pagination == null)
                    {
                        pagination = JsonParser.Parsepagination(result);
                    }

                    page++;

                    if (pagination["current_page"] == pagination["total_pages"])
                    {
                        break;
                    }
                }
            }

            return members;
        }

        public static bool IsStatusCode(this WebException ex, HttpStatusCode code)
        {
            if (ex == null) return false;
            return ex.Response != null && ex.Response is HttpWebResponse && (((HttpWebResponse)ex.Response).StatusCode == code);
        }

        public static DateTime GetFolderDeleteTime(UserDetails user, int folderId)
        {
            var deleteFolderActivity = GetActivities(GetRequestUrl(0, folderId), user, folderId).FirstOrDefault(a => (a.Noun == "Folder" && a.Verb == "Delete"));
            var folderDeleteTime = DateTime.Now;
            if (deleteFolderActivity != null)
            {
                DateTime.TryParse(deleteFolderActivity.TimeCreated, out folderDeleteTime);
            }

            return folderDeleteTime.ToLocalTime();
        }
    }


    public enum RegData { Platform, Username, Userpass }

    static class PlatformRegistryHelper
    {

        private static Boolean keyValueShouldBeEncrypted(RegData key)
        {
            if (key == RegData.Username || key == RegData.Userpass)
                return true;
            else
                return false;
        }

        private static string getEncryptedValueFromRegisrty(RegData key)
        {
            String ret = getValueFromRegisrty(key);

            if (!String.IsNullOrEmpty(ret))
            {
                //earlier there wasn't the encryption - if we read unencrypted value then encrypt it and resave in registry
                if (!PlatformCryptoHelper.IsStringEncrypted(ret))
                    setValueToRegisrty(key, PlatformCryptoHelper.GetEncryptedString(ret));
                else
                    ret = PlatformCryptoHelper.GetDecryptedString(ret);
            }

            return ret;
        }

        private static string getValueFromRegisrty(RegData key)
        {
            var regKey = Registry.CurrentUser.CreateSubKey(@"Software\Workshare");
            var platformValue = regKey.GetValue(key.ToString()) as string;
            if (string.IsNullOrEmpty(platformValue) && key == RegData.Platform)
            {
                regKey.SetValue(key.ToString(), PlatformService._Host ?? PlatformService.DEFAULT_SERVER);
                platformValue = PlatformService._Host;
            }
            regKey.Close();
            return platformValue;
        }

        private static void setEncryptedValueToRegisrty(RegData key, string value)
        {
            value = PlatformCryptoHelper.GetEncryptedString(value);
            setValueToRegisrty(key, value);
        }

        private static void setValueToRegisrty(RegData key, string value)
        {
            var regKey = Registry.CurrentUser.CreateSubKey(@"Software\Workshare");
            regKey.SetValue(key.ToString(), value);
            regKey.Close();
        }
        // <<<<<<< HEAD

        public static string getFromRegisrty(RegData key)
        {
            if (keyValueShouldBeEncrypted(key))
                return getEncryptedValueFromRegisrty(key);
            else
                return getValueFromRegisrty(key);
        }

        public static void setToRegisrty(RegData key, string value)
        {
            if (keyValueShouldBeEncrypted(key))
                setEncryptedValueToRegisrty(key, value);
            else
                setValueToRegisrty(key, value);
        }

    }

    static class PlatformCryptoHelper
    {
        private static readonly String base64Text = "BASE64";
        private static readonly String publicKeyXML = @"<RSAKeyValue><<KEY>><Exponent>AQAB</Exponent></RSAKeyValue>";
        private static readonly String privatePublicKeyPairXML = @"<<KEY>><Exponent>AQAB</Exponent><P>4<KEY>175Yzmwakng4ShPQ==</P><Q>xuf5HEv+3g/1ZIulF1EvT72j4OGdHYqAt/AiqDuJuDtJnRiid4v/qTsjv6Sn3bFg82vDW5f63vARnln/BLTgdw==</Q><DP>dy/kswGGkYmlD3glAQObQ165O/oIRkwD3kNLhdMsWZu4gVNTAdmAAK/2oRNN7+YZEVeqFwrh8Cck8oAGE5CFzQ==</DP><DQ>rcReps/les5qTUqKEdLFCF7eWkn/3pzvUsIhJOPOrvpslye8V8AgvBGEa5pHZK/fyQjuBIjDjBwi6DorRktWhQ==</DQ><InverseQ>LPP7hAqOwTLoGcu426KKtmoBS9LIYoVdM2NxLgjT7i2fc3H0rR4cv4n3LkOVk94kPfy/JlV5rpT6xvVcN9qprQ==</InverseQ><D>hZ4Z4h49UBWblOcY5b89CNxVHpO6MvyeIH+qDwKRfNlHivhxQ3R/XUvZM1dWxPKmOE8RCCPpi42TkEJ8GmijQzpfU5QtEOBlQn4GJ3Al9Yhzaok7s7ca+/g6rItplKrfN+LiG7qkuNZ5UVkkW/GZvUAlUfOFsoZHpo7L7bnm1OE=</D></RSAKeyValue>";

        public static string EncryptString(string stringToEncrypt)
        {
            RSACryptoServiceProvider rsaProvider = new RSACryptoServiceProvider(new CspParameters() { ProviderType = 1 /*PROV_RSA_FULL */ });

            // Import public key
            rsaProvider.FromXmlString(PlatformCryptoHelper.publicKeyXML);

            //Encrypt
            Byte[] bytesToEncrypt = Encoding.ASCII.GetBytes(stringToEncrypt);
            Byte[] encryptedBytes = rsaProvider.Encrypt(bytesToEncrypt, false);

            return Convert.ToBase64String(encryptedBytes);
        }

        /// <summary>
        /// Encrypt the string by using the RSA algorithm
        /// </summary>
        /// <param name="stringToEncrypt">String to be encrypted</param>
        /// <returns>Encrypted string (Base-64 string)</returns>
        public static string GetEncryptedString(string stringToEncrypt)
        {
            String ret = String.Empty;

            try
            {
                //need for IsStringEncrypted method
                stringToEncrypt = stringToEncrypt + base64Text;

                ret = EncryptString(stringToEncrypt);
            }
            //ignore - Workshare.Components.WSLogger is not accessible here but we should add the ability to log in
            catch (EncoderFallbackException)
            {
            }
            catch (ArgumentNullException)
            {
            }
            catch (CryptographicException)
            {
            }

            return ret;
        }

        private static string DecryptString(string stringToDecrypt)
        {
            RSACryptoServiceProvider rsaProvider = new RSACryptoServiceProvider(new CspParameters() { ProviderType = 1 /*PROV_RSA_FULL */ });

            // Import private/public key pair
            rsaProvider.FromXmlString(PlatformCryptoHelper.privatePublicKeyPairXML);

            //Decrypt
            Byte[] bytesToDecrypt = Convert.FromBase64String(stringToDecrypt);
            Byte[] decryptedBytes = rsaProvider.Decrypt(bytesToDecrypt, false);

            return Encoding.ASCII.GetString(decryptedBytes);
        }

        /// <summary>
        /// Decrypt the string by using the RSA algorithm
        /// </summary>
        /// <param name="stringToDecrypt">String to be decrypted</param>
        /// <returns>Decrypted string (ASCII character set)</returns>
        public static string GetDecryptedString(string stringToDecrypt)
        {
            String ret = String.Empty;
            try
            {
                ret = PlatformCryptoHelper.DecryptString(stringToDecrypt);

                //GetEncryptedString method inserts base64Text into the end of string to be encrypted - need to remove it
                ret = ret.Remove(ret.LastIndexOf(base64Text), (base64Text.Length));
            }
            //ignore - Workshare.Components.WSLogger is not accessible here but we should add the ability to log in
            catch (ArgumentOutOfRangeException)
            {
            }
            catch (EncoderFallbackException)
            {
            }
            catch (ArgumentNullException)
            {
            }
            catch (CryptographicException)
            {
            }

            return ret;
        }

        /// <summary>
        /// Determine if string is a decrypted string or not
        /// </summary>
        /// <param name="value">String to determine</param>
        /// <returns>true - string is a decrypted string, false - otherwise</returns>
        public static bool IsStringEncrypted(string value)
        {
            try
            {
                if (DecryptString(value).EndsWith(base64Text))
                    return true;
            }
            catch (Exception)
            {
            }

            return false;
        }

    }
}

<file_sep>/WSComponents/src/WSComponents/Views/Common/CommandInvoker.cs
﻿using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Diagnostics;
using System.Linq;
using System.Threading;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Integration.Extensions;
using Workshare.Integration.Interfaces;

namespace Workshare.Components.Views.Common
{
    public class CommandInvoker
    {
        System.ComponentModel.BackgroundWorker worker = new BackgroundWorker();
        Queue<IWorkUnit> workqueue = new Queue<IWorkUnit>();
        AutoResetEvent workAdded = new AutoResetEvent(false);

        public event Action<IWorkUnit> WorkUnitAdded;
        public event Action<IWorkUnit> WorkCompleted;

        public CommandInvoker()
        {
            worker.DoWork += worker_DoWork;
            worker.RunWorkerAsync();
        }

        public void AddToQueue(IWorkUnit workUnit)
        {
            lock (workqueue)
            {
                workUnit.Status = WorkStatus.Pending;
                workUnit.OnAdded();
                if (WorkUnitAdded != null)
                {
                    WorkUnitAdded(workUnit);
                }
                workqueue.Enqueue(workUnit);
                workAdded.Set();
            }
        }

        bool m_IsBusy = false;
        public bool IsBusy
        {
            set
            {
                if (m_IsBusy != value)
                {
                    m_IsBusy = value;
                    if (IsBusyChanged != null)
                    {
                        IsBusyChanged(m_IsBusy);
                    }
                }
            }
            get
            {
                return m_IsBusy;
            }
        }

        public List<IWorkUnit> GetAllWorks()
        {
            var res = new List<IWorkUnit>();
            res.AddRange(workqueue.ToList());
            var workinprogress = workInProgress;
            if(workinprogress!=null)
            {
                res.Add(workinprogress);
            }
            return res;
        }

        IWorkUnit workInProgress = null;
        void worker_DoWork(object sender, DoWorkEventArgs e)
        {
            try
            {
                while (true)
                {
                    try
                    {
                        lock (workqueue)
                        {
                            if (workqueue.Count > 0)
                            {
                                IsBusy = true;
                                workInProgress = workqueue.Dequeue();
                            }
                        }
                        if (workInProgress == null)
                        {
                            IsBusy = false;
                            workAdded.WaitOne();
                        }
                        else
                        {
                            workInProgress.Status = WorkStatus.Processing;
                            workInProgress.Execute();
                            
                            workInProgress.Status = WorkStatus.Success;
                        }
                    }
                    catch (ThreadAbortException)
                    {
                        throw;
                    }
                    catch (Exception ex)
                    {
                        Trace.TraceError(ex.ToString());
                        if (workInProgress != null)
                        {
                            workInProgress.StatusDescription = ex.Message;
                        }
                    }
                    finally
                    {
                        if (workInProgress != null)
                        {
                            if (workInProgress.Status != WorkStatus.Success)
                            {
                                workInProgress.Status = WorkStatus.Error;
                            }
                            if (WorkCompleted != null)
                            {
                                WorkCompleted(workInProgress);
                            }
                            workInProgress = null;
                        }
                    }
                }
            }
            catch (Exception ex)
            {
                Trace.TraceError(ex.ToString());
            }
        }

        public event Action<bool> IsBusyChanged;

    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/WorkUnits/ProcessWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Interfaces;
using Workshare.Components.Services;
using Workshare.Components.Views.TrueSyncDialog;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using RES = Workshare.Integration.Properties.Resources;


namespace Workshare.Components.Views.TrueSyncDialog.WorkUnits
{
    public class ProcessWorkUnit : WorkUnit
    {
        private readonly IEnumerable<DocumentActionVM> _actionsVmToProcess;
        private readonly TrueSyncDialogViewModel _vm;
        private readonly ErrorReporterService _errorsReporter;
        private readonly ModuleBase _module;

        public ProcessWorkUnit(ModuleBase module, IModuleView view, IEnumerable<DocumentActionVM> actionsVmToProcess,
            TrueSyncDialogViewModel vm)
            : base(view)
        {
            _module = module;
            _actionsVmToProcess = actionsVmToProcess;
            _vm = vm;
            _errorsReporter = _module.Resolve<ErrorReporterService>();

            var activity = _actionsVmToProcess.Select(a => a.activityVm).First();

            if (activity is ImportFileActivityVm)
            {
                this.Name = string.Format("Importing from Workshare");
            }
            else if (activity is UploadFileActivityVm)
            {
                this.Name = string.Format("Uploading to Workshare");
            }
            else
            {
                this.Name = string.Format("Processing");
            }
            TargetItems = new TargetItem[]
            {
                new TargetItem(activity.Id)
                {
                    Name = activity.Name
                }
            };

            this.StatusDescription = "Importing...";
        }

        public override void OnAdded()
        {
            foreach (var documentAction in _actionsVmToProcess)
            {
                documentAction.activityVm.OnStartProcessing();
            }
            base.OnAdded();
        }

        public override void Execute()
        {
            try
            {
                var scanResult = _vm.ScanResult;
                var processor = _module.Resolve<Processor>();
                var processOptions = new ProcessOptions();
                processOptions.ActionsToApply.AddRange(_actionsVmToProcess.Select(a => a.action));
                scanResult = processor.Process(scanResult, processOptions);

                var adapter = _module.Resolve<ActivityFinder>();
                var errors = adapter.GetErrors(scanResult);
                var processedIds = _actionsVmToProcess.Select(a => a.action.ActivityId).ToList();
                var errorIds = _actionsVmToProcess.Select(a => a.action.Activity.MapId).ToList();
                var activities = _vm.AllActivities.Select(a => a.data).OfType<FileMapActivity>();
                adapter.UpdateActivities(scanResult, activities, processedIds);
                var errorsForWorkUnit = errors.Where(e => errorIds.Contains(e.Id)).ToList();

                if (_vm.IsViewClosed)
                {
                    if (errorsForWorkUnit.Any())
                    {
                        _errorsReporter.AddRange(_vm.Id, Integration.Processor.Maps.Ext.GetItemErrorsList(errorsForWorkUnit));
                    }
                    //don't use Dispatcher !!! Outlook is crashed if user opens pop-up menu during syncing process
                    //_vm.Dispatcher.Invoke(new Action(() =>
                    //{
                        if (!_vm.AllActivities.Any(a => ((IFileActivityBaseVm) a).IsInProgress))
                        {
                            _errorsReporter.ReportIfNeeded(_vm.Id);
                        }
                    //}));
                }
                else
                {
                    _vm.OnCompleted(errors, activities, scanResult);
                }
            }
            catch (Exception ex)
            {
                _view.ShowError(ex);
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/SyncInfo/FileSyncInfo.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Web.Script.Serialization;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;

namespace Workshare.Integration.SyncInfo
{
    internal class FileSyncInfo : ISyncInfo
    {
        public string DataType
        {
            get { return "FileSyncInfo"; }
            set { }
        }

        public int ParentId
        {
            get;
            set;
        }

        public int LastImportedWsVerId
        {
            get;
            set;
        }

        public int LastUploadedDmsVerNum
        {
            get;
            set;
        }

        public int ItemId
        {
            get;
            set;
        }

        public string DMSItemId
        {
            get;
            set;
        }

        public string Modified
        {
            get;
            set;
        }

        public string ActivityId
        {
            get;
            set;
        }

        public List<VersionInfo> VerInfos { set; get; }

        public List<IVersionSyncInfo> GetvInfos()
        {
            return VerInfos.OfType<IVersionSyncInfo>().ToList();
        }

        public void AddVInfo(IVersionSyncInfo info)
        {
            if (!VerInfos.Contains((VersionInfo) info))
            {
                VerInfos.Add((VersionInfo) info);
            }
        }

        public FileSyncInfo()
        {
            VerInfos = new List<VersionInfo>();
        }

        public override string ToString()
        {
            var ser = new JavaScriptSerializer();
            return ser.Serialize(this);
        }

        public IVersionSyncInfo GetVersionInfo(string id)
        {
            return VerInfos.FirstOrDefault(a => a.DmsVerId == id);
        }

        public static FileSyncInfo Parse(string value)
        {
            try
            {
                if (string.IsNullOrEmpty(value)) return null;
                var ser = new JavaScriptSerializer();
                return ser.Deserialize<FileSyncInfo>(value);
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
                return null;
            }
        }
    }

    public class VersionInfo : IVersionSyncInfo
    {
        public VersionInfo()
        {
            WsVerIds=new List<string>();
        }
        public string DmsVerId { set; get; }
        public string CurWsVerId { get; set; }
        public List<string> WsVerIds { set; get; }
        public string DmsEditTime { set; get; }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Visitors/ImportActivityFinder.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Integration.Processor.Changes.Visitors
{
    public class ImportActivityFinder : ItemMapVisitor
    {
        readonly DiscardedService _discardedService;
        readonly ChangesDetector _detector;
        private readonly DmsWorkerBase _dmsWorker;

        private ActivityFinder.Options _options;
        public ActivityFinder.Options Options
        {
            get
            {
                return _options;
            }
            set
            {
                _options = value ?? new ActivityFinder.Options();
            }
        }

        private SyncInfoService syncInfoService;
        public ImportActivityFinder(DiscardedService discardedService, ChangesDetector detector, DmsWorkerBase dmsWorker, SyncInfoService syncInfoService)
        {
            this._discardedService = discardedService;
            this._detector = detector;
            this._dmsWorker = dmsWorker;
            _options=new ActivityFinder.Options();
            this.syncInfoService = syncInfoService;
        }

        public IEnumerable<string> ActivitiesToUpdate = null;

        public List<ImportFileActivity> FoundedActivities = new List<ImportFileActivity>();

        public void UpdateState(ImportFileActivity activity, FileMap fileMap)
        {
            if (fileMap.ProcessState == ProcessState.Error)
            {
                if (fileMap.Error is FileCheckoutedToAnotherUser)
                {
                    activity.State = ImportFileActivityState.CheckedOutToAnother;
                    activity.CheckedOutTo = ((FileCheckoutedToAnotherUser)fileMap.Error).UserName;
                }
                else if (fileMap.Error is CheckedOutOnAnotherMachine)
                {
                    activity.State = ImportFileActivityState.CheckedOutOnAnotherMachine;
                    activity.CheckOutMachine = ((CheckedOutOnAnotherMachine)fileMap.Error).MachineName;
                }
                else if (fileMap.Error is LockedByAnotherProcessException)
                {
                    activity.State = ImportFileActivityState.LockedByAnotherProcess;
                    activity.Error = fileMap.Error;
                }
                else if (fileMap.Error.IsCloudFolderAccessDenied())
                {
                    activity.State = ImportFileActivityState.NoAccessOnWorkshare;
                    activity.Error = fileMap.Error;
                }
                else if (fileMap.Error is DMSUnAuthorizedException)
                {
                    activity.State = ImportFileActivityState.NoAccessOnDMS;
                    activity.Error = fileMap.Error;
                }
                else
                {
                    activity.State = ImportFileActivityState.Error;
                    activity.Error = fileMap.Error;
                }
            }
            else if (fileMap.ProcessState == ProcessState.Processed)
            {
                if (activity.State == ImportFileActivityState.Importing)
                {
                    activity.State = ImportFileActivityState.Imported;
                }
            }
            else if (fileMap.ProcessState == ProcessState.Scanned)
            {
                activity.State = ImportFileActivityState.Scanned;
            }
            else if (fileMap.ProcessState == ProcessState.Cancelled)
            {
                activity.State = ImportFileActivityState.Scanned;
            }
        }

        public override void Visit(FileMap fileMap)
        {
            var existed = FoundedActivities.FirstOrDefault(a => a.MapId == fileMap.Id);
            if (existed != null && _options.DoNotUpdate) return;
            var importActivity = existed ?? new ImportFileActivity();
            _detector.opt = new DetectorOptions() { UseForceRequest = _options.UseForceRequest };
            try
            {

                if (ActivitiesToUpdate == null || ActivitiesToUpdate.Contains(importActivity.Id))
                {
                    importActivity.Refresh(fileMap, _dmsWorker);

                    UpdateState(importActivity, fileMap);

                    if (!importActivity.InKindOfErrorState())
                    {

                        importActivity.ClearChanges();

                        _detector.AddSharedChangeIfDetected(fileMap, importActivity);

                        _detector.AddChangesIfDetected(fileMap, importActivity);

                        _detector.AddRenameChangeIfDetected(fileMap, importActivity);

                        _detector.AddTypeChangedIfDetected(fileMap, importActivity);

                        _detector.AddDeleted(fileMap, importActivity);

                        _detector.AddNotModifiedIfdetected(fileMap, importActivity);

                        _detector.AddAddedOnWs(fileMap, importActivity);

                        _detector.AddNotSent(fileMap, importActivity);

                        importActivity.IsDiscarded = _discardedService.IsDiscarded(importActivity);

                    }
                    importActivity.IsLinked = (syncInfoService.GetSyncInfo(fileMap, _options.UseForceRequest) != null);

                    this.RefreshAction(importActivity);
                }

                if (!FoundedActivities.Contains(importActivity) && ShouldDetectActivity(importActivity))
                {
                    FoundedActivities.Add(importActivity);
                }
            }
            catch (Exception ex)
            {
                importActivity.Error = ex;
                importActivity.State = ImportFileActivityState.Error;
            }
        }

        public virtual bool ShouldDetectActivity(ImportFileActivity activity)
        {
            return true;
        }

        private void RefreshAction(ImportFileActivity activity)
        {
            activity.Actions = new List<ItemMapActivityAction>();

            if (activity.State == ImportFileActivityState.Scanned)
            {
                var allVersionAsNewVersion = new ImportDocumentAction(activity, "As new version", ConflictVersionOptions.All, ImportType.AsNewVersion);
                var allversionsAsNewDocument = new ImportDocumentAction(activity, "As new file", ConflictVersionOptions.All, ImportType.AsNewDocument);
                var allversionsAsRelatedDocument = new ImportDocumentAction(activity, "As related file", ConflictVersionOptions.All, ImportType.AsRelatedDocument);
                var latestVersionAsNewVersion = new ImportDocumentAction(activity, "As new version", ConflictVersionOptions.Latest, ImportType.AsNewVersion);
                var latestVersionAsNewDocument = new ImportDocumentAction(activity, "As new file", ConflictVersionOptions.Latest, ImportType.AsNewDocument);
                var latestVersionAsRelatedDocument = new ImportDocumentAction(activity, "As related file", ConflictVersionOptions.Latest, ImportType.AsRelatedDocument);

                var allVersionsGroup = new ItemMapActivityActionGroup("All versions");
                var latestVersionGroup = new ItemMapActivityActionGroup("Latest version only");
                if (activity.Changes.Any(p => new List<ChangeType> { ChangeType.BothChanged, ChangeType.RemoteChanged }.Contains(p.Type)))
                {
                    allVersionsGroup.AddAction(new[] { allVersionAsNewVersion, allversionsAsNewDocument, allversionsAsRelatedDocument });
                    latestVersionGroup.AddAction(new[] { latestVersionAsNewVersion, latestVersionAsNewDocument, latestVersionAsRelatedDocument });
                }
                if (activity.Changes.Any(p => new List<ChangeType> { ChangeType.RemoteAdded }.Contains(p.Type)))
                {
                    latestVersionGroup.AddAction(latestVersionAsNewDocument);
                    allVersionsGroup.AddAction(allversionsAsNewDocument);
                }

                var import = new ItemMapActivityActionGroup("Import");

                if (allVersionsGroup.Actions.Any()) import.AddAction(allVersionsGroup);
                if (latestVersionGroup.Actions.Any()) import.AddAction(latestVersionGroup);


                foreach (var topLevel in new[] { import })
                {
                    if (topLevel.Actions.Any())
                    {
                        activity.Actions.Add(topLevel);
                    }
                }
            }
        }        
    }
}
<file_sep>/WSComponents/src/WSComponents/Common/WorkshareCustomEventArgs.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Integration.Common;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components
{
    public class ItemSentArgs : EventArgs
    {
        public ItemSentArgs(IDMSItem item)
        {
        }
    }

    public class ItemUpdatedLocallyArgs : EventArgs
    {
        public ItemUpdatedLocallyArgs(IDMSItem item)
        {
        }
    }

    public class ItemUpdatedOnWSArgs : EventArgs
    {
        public ItemUpdatedOnWSArgs(IDMSItem item)
        {
        }
    }

    public class TraceArgs : EventArgs
    {
        public TraceArgs()
        {
        }
    }

    public class ItemAddedFromWSArgs : EventArgs
    {
        public ItemAddedFromWSArgs(IDMSItem item)
        {
        }
    }

    public class SyncItemsClickedArgs
    {
        public IEnumerable<SyncItemInformation> Items { private set; get; }
        public IEnumerable<FileMapActivity> ItemsToSkip { get; set; }

        public SyncItemsClickedArgs(IEnumerable<SyncItemInformation> items)
        {
            Items = items;
            ItemsToSkip = new List<FileMapActivity>();
        }
    }

    public class SendItemsClickedArgs
    {
        public IEnumerable<IDMSItem> Items { private set; get; }
        public SendItemsClickedArgs(IEnumerable<IDMSItem> items)
        {
            Items = items;
        }
    }

    public class CollaborationItemsClickedArgs
    {
        public IEnumerable<CollaborationItemInformation> Items { private set; get; }
        public IEnumerable<FileMapActivity> ItemsToSkip { get; set; }

        public CollaborationItemsClickedArgs(IEnumerable<CollaborationItemInformation> items)
        {
            Items = items;
            ItemsToSkip = new List<FileMapActivity>();
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Modularity/ModuleBase.cs
﻿using Microsoft.Practices.Unity;

namespace Workshare.Integration.Modularity
{
    public abstract class ModuleBase
    {
        UnityContainer _Container;
        protected UnityContainer Container
        {
            get
            {
                if (_Container == null)
                {
                    _Container = new UnityContainer();
                }
                return _Container;
            }
        }

        public ModuleBase()
        {
            this.Initialize();
        }

        protected virtual void Initialize()
        {
        }


        public T Resolve<T>()
        {
            return Container.Resolve<T>();
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService.Tests/TestUtils.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using NUnit.Framework;
using WorksharePlatform;

namespace WorkshareCloud.ServiceProxy.Tests
{
    class TestUtils
    {
        public const string USER1="<EMAIL>";
        public const string USER1_PASS = "<PASSWORD>";

        public const string USER2 = "<EMAIL>";
        public const string USER2_PASS = "<PASSWORD>";
    }

    class UserContext:IDisposable
    {
        public static implicit operator UserDetails(UserContext m)
        {
            return m.User;
        }
        public UserDetails User { get; private set; }
        public UserContext(string email,string pass)
        {
            User = new UserDetails() { Email = email, Password = <PASSWORD> };
            PlatformService.Login(User);
        }

        public void Dispose()
        {
        }
    }


    public class Permisions
    {
        public bool Invite=true;
        public bool User_must_login=true;
        public bool DownloadFiles=true;
        public bool CanAddVersions=true;
    }
    public static class WS
    {
        public static FileDetails GetTestFile()
        {
            return new FileDetails()
            {
                Id=-1,
                FolderId=-1,
                Data=WSCloudService.Tests.Properties.Resources.testdoc1,
                Name="testdoc1.docx"
            };
        }
        public static FolderDetails CreateFolder(UserDetails user, Permisions perm, IEnumerable<string> shareTo = null, string fodlername = "testfolder")
        {
            var createdFodler = PlatformService.CreateFolder(user, fodlername, fodlername);
            Assert.IsNotNull(createdFodler);
            createdFodler.Permissions.Member_may_invite = perm.Invite;
            createdFodler.Permissions.User_must_login = perm.User_must_login;
            createdFodler.Permissions.DownloadFiles = perm.DownloadFiles;
            createdFodler.Permissions.CanAddVersions = perm.CanAddVersions;
            PlatformService.ApplyPermissionToFolder(user, createdFodler);
            string users = string.Empty;
            if (shareTo != null)
            {
                shareTo.ToList().ForEach(p => users += p + ";");
                PlatformService.ShareFolderWith(user, createdFodler, users, string.Empty, string.Empty);
            }
            
            return createdFodler;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/ModuleViewBase.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.InteropServices;
using System.Threading;
using System.Windows;
using System.Windows.Forms;
using System.Windows.Interop;
using System.Windows.Threading;
using Workshare.Components.Common;
using Workshare.Components.Helpers;
using Workshare.Components.Interfaces;
using Workshare.Components.Presenter;
using Workshare.Components.Views.Authentication;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.Progress;
using Workshare.Components.Views.SelectFolder;
using Workshare.Components.Views.SyncDialog;
using Workshare.Components.WSLogger;
using Workshare.Integration;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Services;
using WorksharePlatform;
using CheckOut_Dialog = Workshare.Components.Views.CheckOutDialog;

namespace Workshare.Components.Views
{
    public abstract class ModuleViewBase : IModuleView
    {
        const int THREAD_SLEEP_TIME = 2;
        public const int IE8MAJORVERSION = 8;

        protected Dispatcher dispatcher;

        public ModuleViewBase()
        {
            Debug.Assert(Thread.CurrentThread.GetApartmentState()==ApartmentState.STA);
            dispatcher = Dispatcher.CurrentDispatcher;
        }

        public ModuleViewBase(IWSIntegration integration):this()
        {
            m_presenter = CreatePresenter(integration);
        }

        public abstract ModulePresenterBase CreatePresenter(IWSIntegration integration);

        [DllImport("user32.dll")]
        [return: MarshalAs(UnmanagedType.Bool)]
        static extern bool IsWindow(IntPtr hWnd);

        protected IntPtr _MainWindowHandle;

        public virtual IntPtr ActivieWindowHandle
        {
            get
            {
                var res = IntPtr.Zero;
                if (!IsWindow(_MainWindowHandle))
                {
                    _MainWindowHandle = Process.GetCurrentProcess().MainWindowHandle;
                }
                res = _MainWindowHandle;
                if (this.TopWindow != IntPtr.Zero && IsWindow(this.TopWindow))
                {
                    res = TopWindow;
                }
                else
                {
                    TopWindow = IntPtr.Zero;
                }

                return res;
            }
            set
            {
                _MainWindowHandle = value;
            }
        }

        public IntPtr MainWindowHandle
        {
            get
            {
                var res = IntPtr.Zero;
                if (!IsWindow(_MainWindowHandle))
                {
                    _MainWindowHandle = Process.GetCurrentProcess().MainWindowHandle;
                }
                res = _MainWindowHandle;
                return res;
            }
        }

        #region Errors processiog
        public virtual void ShowErrors(IEnumerable<ItemException> errors)
        {
            SendWMClose("#32768");

            IEnumerable<ItemException> errs = errors;

            ItemException offlineException = errs.Where(e => e.Error is OfflineException).FirstOrDefault();

            if (offlineException != null)
            {
                errs = errs.Where(e => !(e.Error is OfflineException));
                errs = errs.Union( new List<ItemException> {offlineException});
            }

            var act = new Action(() =>
            {
                var dlg = new ErrorsWindow.ErrorsWindow(errs);
                SetMainAsParent(dlg);
                dlg.DisableOwner = true;
                dlg.ShowDialog();
            });
            
            ExecuteInAppropriateThread(act);
        }

        public virtual void ShowError(Exception ex)
        {
            Logger.WriteError(ex);
            if (ex is MultiItemsException)
            {
                SendWMClose("#32768");

                var multi = (MultiItemsException)ex;

                var act = new Action(() =>
                {
                    var dlg = new ErrorsWindow.ErrorsWindow(multi.errorList.AsQueryble());
                    SetMainAsParent(dlg);
                    dlg.DisableOwner = true;
                    dlg.ShowDialog();

                });

                ExecuteInAppropriateThread(act);
            }
            else
            {
                if (ex is BaseException)
                {
                    ShowError((BaseException) ex);
                }
                else
                {
                    ShowError(ex.ToString());
                }
            }
        }

        public virtual void ShowError(BaseException ex)
        {
            Logger.WriteError(ex);
            var exceptions = new List<ItemException>()
            {
                new ItemException() { Error = ex}
            };

            ShowErrors(exceptions);
        }

        public void ShowError(string message)
        {
            SendWMClose("#32768");

            ExecuteInAppropriateThread(() =>
            {
#if DEBUG
                System.Windows.Forms.MessageBox.Show(message, "FIX ME PLEASE!!!!.");
#else
                System.Windows.Forms.MessageBox.Show(string.Format("Unexpected error occured:\n{0}\n Please try again and if error is persisted contact support.", message), "Unexpected error");
#endif
            });
        }

        #endregion

        protected ProgressWindow progressWindow;
        public virtual void ShowProgressWindow(CommandInvoker invoker)
        {
            Logger.WriteTrace(string.Format("ShowProgressWindow"));
            progressWindow = new ProgressWindow(invoker);
            new WindowInteropHelper(progressWindow).Owner = Process.GetCurrentProcess().MainWindowHandle;
            progressWindow.Show();
        }

        public IModulePresenter m_presenter
        {
            get;
            set;
        }

        public virtual void OnSendItemsClicked(SendItemsClickedArgs args)
        {
            m_presenter.OnSendItemsClicked(args);
        }

        public virtual void OnSynchItemsClicked(SyncItemsClickedArgs args)
        {
            m_presenter.OnSyncItemsClicked(args);
        }

        public virtual void OnCollaborationItemsClicked(CollaborationItemsClickedArgs args)
        {
            m_presenter.OnCollaborationItemsClicked(args);
        }

        public virtual bool ShowLogin(out UserDetails user, DialogSettings settings)
        {
            Logger.Write("ModuleView::ShowLogin() START", Severity.Information);
            WinInetHelper.ResetSession();
            using (var loginWindow2 = new AuthentificationForm())
            {
                WinFormHelper helper = new WinFormHelper(ActivieWindowHandle);
                loginWindow2.AutoSize = true;
                loginWindow2.AutoSizeMode = System.Windows.Forms.AutoSizeMode.GrowOnly;
                loginWindow2.ClientSize = new System.Drawing.Size((settings.dialog_login_width > 0) ? settings.dialog_login_width : loginWindow2.Width, (settings.dialog_login_height > 0) ? settings.dialog_login_height : Math.Min(loginWindow2.Height, 700));
                loginWindow2.FormBorderStyle = System.Windows.Forms.FormBorderStyle.FixedDialog;
                loginWindow2.MaximizeBox = loginWindow2.MinimizeBox = false;

                var res=loginWindow2.ShowDialog(helper);
                user = loginWindow2.User;

                if (res == System.Windows.Forms.DialogResult.Abort && loginWindow2.Error != null)
                {
                    WSApplication.Instance.View.ShowError((BaseException)loginWindow2.Error);
                }

                return res == System.Windows.Forms.DialogResult.OK;
            }
        }

        public virtual int ShowSelectFolder(DialogSettings settings)
        {
            Logger.Write("ModuleView::ShowSelectFolder() START", Severity.Information);
            using (var folder = new SelectFolderForm())
            {
                folder.Width = (settings.dialog_select_folder_width > 0) ? settings.dialog_select_folder_width : folder.Width;
                folder.Height = (settings.dialog_select_folder_height > 0) ? settings.dialog_select_folder_height : folder.Height;
                folder.ShowDialog(GetMainWindow());
                return folder.SelectedFolderId;
            }
        }

        public virtual void ShowFileSyncDialog(object file, EventOperation operation, string command)
        { }

        private bool IsFolderHasFiles(IDMSFolder fld)
        {
            if (fld.Files.Count() > 0)
            {
                return true;
            }

            foreach (var f in fld.SubFolders)
            {
                if (IsFolderHasFiles(f))
                {
                    return true;
                }
            }

            return false;
        }

        public virtual CheckOutOptions ShowCheckOutDialogIfNeed(SendItemsClickedArgs args)
        {
            string filename = "";
            var items = args.Items.ToList();
            if (items.Count() == 1)
            {
                if (((items[0] is IDMSFolder) && (IsFolderHasFiles(items[0] as IDMSFolder))) || ((items[0] is IDMSFile) && !(items[0] as IDMSFile).CheckedOut))
                {
                    filename = items[0].Name;
                }
                else
                {
                    return CheckOutOptions.CheckOut;
                }
            }
            else 
            {
                if (!(items.Any(p => p is IDMSFolder) || items.Any(p => p is IDMSFile && !(p as IDMSFile).CheckedOut)))
                {
                    return CheckOutOptions.CheckOut;
                }
            }

            var checkOutDialog = new CheckOut_Dialog.CheckOutDialog();
            checkOutDialog.FileName = filename;
            SetMainAsParent(checkOutDialog);
            checkOutDialog.DisableOwner = true;

            if (checkOutDialog.ShowDialog() == true)
            {
                return checkOutDialog.Result;
            }
            else
            {
                return CheckOutOptions.None;
            }
        }

        #region protected

        protected void SetMainAsParent(Window window, bool currentActiveWindow = true)
        {
            var helper = new WindowInteropHelper(window);
            helper.Owner = currentActiveWindow ? ActivieWindowHandle:MainWindowHandle;
        }

        protected System.Windows.Forms.IWin32Window GetMainWindow()
        {
            return new WinFormHelper(ActivieWindowHandle);
        }

        protected void ExecuteInAppropriateThread(Action action)
        {
            ExecuteInAppropriateThread(() =>
            {
                Logger.Write("Execute in appropriate thread", Severity.Information);
                action();
                return "";
            });
        }

        protected T ExecuteInAppropriateThread<T>(Func<T> func)
        {
            if (dispatcher.CheckAccess())
            {
                return func();
            }
            return (T)dispatcher.Invoke(func);
        }

        #endregion



        public IntPtr TopWindow
        {
            get;set;
        }


        public void SuppressProgressDialog(bool p)
        {
            if(this.progressWindow!=null)
            {
                this.progressWindow.Suppress(p);
            }
        }

        [DllImport("user32.dll", SetLastError = true)]
        public static extern IntPtr FindWindow(string lpClassName, string lpWindowName);

        [DllImport("user32.dll", CharSet = CharSet.Auto)]
        static extern IntPtr SendMessage(IntPtr hWnd, int Msg, IntPtr wParam, IntPtr lParam);

        private void SendWMClose(string lpClassName, string lpWindowName = null)
        {
            ExecuteInAppropriateThread(() =>
            {
                var window = FindWindow(lpClassName, lpWindowName);
                var WM_CLOSE = 0x10;

                while (window != IntPtr.Zero)
                {
                    SendMessage(window, WM_CLOSE, IntPtr.Zero, IntPtr.Zero);
                    Thread.Sleep(50);
                    window = FindWindow(lpClassName, lpWindowName);
                }
            });
        }

        public List<ImportDocumentAction> SelectActions(List<ImportFileActivity> importActivities)
        {
            SendWMClose("#32768");

            return ExecuteInAppropriateThread(() =>
            {
                if (importActivities.Any())
                {
                    var deletedFiles = importActivities.Where(a => a.Changes.Any(c => c.Type == ChangeType.RemoteDeleted)).ToList();
                    var activitiesToProcess = importActivities.Where(a => deletedFiles.Where(d => d.Equals(a)).Count() == 0).ToList();

                    if (deletedFiles.Any())
                    {
                        foreach (var deletedFile in deletedFiles)
                        {
                            if (deletedFile.State != ImportFileActivityState.LinkIsDeleted)
                            {
                                var syncInfo = WSApplication.Instance.Module.Resolve<SyncInfoService>();
                                try
                                {
                                    deletedFile.DmsFile.AddHistory("FileDeletedOrMoved", "Synced from Workshare on " + DateTime.Now.ToString(Activity.TimeFormat) + ". File has been deleted or moved", Operations.Sync);
                                    syncInfo.BreakLink(deletedFile.DmsFile);
                                }
                                catch (FileCheckoutedToAnotherUser ex)
                                {
                                    WSApplication.Instance.View.ShowErrors(new ItemException[] { new ItemException() { Item = deletedFile.DmsFile, Error = ex } });
                                }
                            }
                        }
                    }

                    if (activitiesToProcess.Any())
                    {
                        var dlg = new SyncDialogWindow2(activitiesToProcess);
                        SetMainAsParent(dlg, false);

                        if (dlg.ShowDialog() == true)
                        {
                            return dlg.GetSelectedActions().ToList();
                        }
                    }
                }
                return new List<ImportDocumentAction>();
            });
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Services/SyncInfoService.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Components.WSLogger;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.SyncInfo;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Services
{
    /// TODO move all sync info related operations to this service, extract interface and move this class to IManage
    /// Also this class should depends on FolderMap, FileMap instead on directly relyes on IDmsFolder,IDmsFile
    public class SyncInfoService
    {
        private readonly DmsWorkerBase _dmsWorker;
        private readonly ISyncInfoFactory _syncInfoFactory;
        private readonly WebDataStorageService _wdsService;
        private readonly string FolderSyncInfoKey = "IMFolderSyncInfo:";
        private readonly string FolderSendDataKey = "IMFolderSendDataInfo:";
        private readonly string FileSyncInfoKey = "IMFileSyncInfo:";

        public SyncInfoService(DmsWorkerBase dmsWorker, ISyncInfoFactory syncInfoFactory, WebDataStorageService wdsService)
        {
            _dmsWorker = dmsWorker;
            _syncInfoFactory = syncInfoFactory;
            _wdsService = wdsService;
        }

        public virtual ISyncInfo GetSyncInfo(IDMSItem item, bool ForceRequest = true)
        {
            if (item is IDMSFile)
            {
                return GetSyncInfo((IDMSFile)item, ForceRequest);
            }
            else if (item is IDMSFolder)
            {
                return GetSyncInfo((IDMSFolder)item, ForceRequest);
            }
            else
            {
                return null;
            }
        }

        public virtual ISyncInfo GetSyncInfo(IDMSFolder folder, bool ForceRequest = true)
        {
            if (folder == null) return null;

            try
            {
                string key = FolderSyncInfoKey + folder.DMSItemKey;

                var _data = _wdsService.GetAccountData(key, DateTime.MinValue, ForceRequest);
                var currentprops = FolderSyncInfo.Parse(_data);
                if (currentprops != null && currentprops.DMSItemId == folder.DMSId.ToString())
                {
                    return currentprops;
                }
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error when get sync info for folder" + folder.ID.ToString(), ex);

                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                    throw new CannotGetDataFromWebDataStorageExeption(ex.Message);
            }
            return null;

        }

        public virtual ISyncInfo GetSyncInfo(IDMSFile file, bool ForceRequest = true)
        {
            if (file == null) return null;

            try
            {
                string key = FileSyncInfoKey + file.DMSItemKey;

                var _data = _wdsService.GetAccountData(key,file.Modified, ForceRequest);
                return FileSyncInfo.Parse(_data);
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error on get sync file info", ex);

                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                    throw new CannotGetDataFromWebDataStorageExeption(ex.Message);
            }
        }

        public virtual IEnumerable<int> GetSendData(IDMSFolder iDMSFolder, bool ForceRequest = true)
        {
            try
            {
                string key = FolderSendDataKey + iDMSFolder.DMSItemKey;
                var _data = _wdsService.GetAccountData(key, DateTime.MinValue, ForceRequest);
                var sdi = SendDataInfo.Parse(_data);
                return sdi.Items;
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error during get send data info", ex);

                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                    throw new CannotGetDataFromWebDataStorageExeption(ex.Message);
            }
        }

        public IVersionSyncInfo GetSyncInfo(IDmsVersion dmsVersion, bool ForceRequest = true)
        {
            if (dmsVersion == null) return null;

            var fileInfo = (FileSyncInfo)GetSyncInfo(dmsVersion.AsFile(), ForceRequest); 
            if (fileInfo != null)
            {
                return fileInfo.GetVersionInfo(dmsVersion.Id);
            }
            return null;
        }

        public virtual void SaveSyncInfo(IDMSFile file, ISyncInfo info)
        {
            try
            {
                string key = FileSyncInfoKey + file.DMSItemKey;
                if (info == null)
                {
                    _wdsService.DeleteAccountData(key);
                }
                else
                {
                    _wdsService.AddAccountData(key, info.ToString(), file.Modified);
                }
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error on Save sync file info", ex);

                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                    throw new CannotUpdateDataOnWebDataStorageExeption(ex.Message);
            }
        }

        public virtual void SaveSyncInfo(IDMSFolder folder, ISyncInfo info)
        {
            try
            {
                string key = FolderSyncInfoKey + folder.DMSItemKey;
                if (info == null)
                {
                    _wdsService.DeleteAccountData(key);
                }
                else
                {
                    _wdsService.AddAccountData(key, info.ToString(), DateTime.MinValue);
                }
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error on Save sync file info", ex);

                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                    throw new CannotUpdateDataOnWebDataStorageExeption(ex.Message);
            }
        }

        public virtual void SaveSendDataInfo(IDMSFolder folder, IEnumerable<int> itemsToStore)
        {
            try
            {
                var sdi = _syncInfoFactory.CreateSendDataInfo();
                sdi.Items = itemsToStore.ToList();
                sdi.FolderID = folder.DMSId.ToString();
                string _data = sdi.ToString();
                string key = FolderSendDataKey + folder.DMSItemKey.ToString();
                _wdsService.AddAccountData(key, _data, DateTime.MinValue);
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error during Save send data info", ex);

                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                    throw new CannotUpdateDataOnWebDataStorageExeption(ex.Message);
            }
        }


        public virtual void UpdateSendDataInfo(IDMSFolder iDMSFolder, List<int> newIds, bool ForceRequest = true)
        {
            var oldIds = GetSendData(iDMSFolder, ForceRequest);
            SaveSendDataInfo(iDMSFolder, oldIds.Union(newIds));
        }

        /// <summary>
        /// Should be called when some version was imported or uploaded. Should update only file level information as it knows nothing about which versions actually were processed
        /// Maybe this method should be removed and only for version and folder will be left
        /// </summary>
        /// <param name="file"></param>
        /// <param name="context"></param>
        public virtual void UpdateSyncInfo(IDMSFile file, ActionContext context)
        {
            context = context ?? ActionContext.Default;
            switch (context.Type)
            {
                case  ActionType.Import:
                {
                    var info = GetSyncInfoOrCreate(file);
                    info.DMSItemId = file.DMSId.ToString();
                    var wsFile = context.WsFile;
                    if (wsFile != null)
                    {
                        info.ItemId = wsFile.Id;
                        info.ParentId = wsFile.FolderId;
                        info.Modified = file.Modified.Ticks.ToString();
                        var lastImportedVersion = wsFile.Versions.FirstOrDefault(x => x.Id == info.LastImportedWsVerId);
                        if (lastImportedVersion == null || lastImportedVersion.Version < wsFile.CurrentVersion.Version)
                        {
                            info.LastImportedWsVerId = wsFile.CurrentVersion.Id;
                        }
                    }
                    info.ActivityId = context.LastActivity ?? info.ActivityId;
                    SaveSyncInfo(file, info);
                    break;
                }
                case ActionType.Upload:
                {
                    var info = GetSyncInfoOrCreate(file);
                    info.DMSItemId = file.DMSId.ToString();
                    var wsFile = context.WsFile;
                    if (wsFile != null)
                    {
                        info.ItemId = wsFile.Id;
                        info.ParentId = wsFile.FolderId;
                        info.Modified = file.Modified.Ticks.ToString();
                    }
                    info.ActivityId = context.LastActivity ?? info.ActivityId;
                    SaveSyncInfo(file, info);
                    break;
                }
            }
        }

        public ISyncInfo GetSyncInfoOrCreate(IDMSFile file, bool ForceRequest = true)
        {
            return GetSyncInfo(file, ForceRequest) ?? _syncInfoFactory.CreateFileInfo();
        }

        public ISyncInfo GetSyncInfoOrCreate(IDMSFolder folder, bool ForceRequest = true)
        {
            return GetSyncInfo(folder, ForceRequest) ?? _syncInfoFactory.CreateFolderInfo();
        }

        IVersionSyncInfo GetVersionInfoOrCreate(ISyncInfo info, IDmsVersion version, bool ForceRequest = true)
        {
            return info.GetvInfos().FirstOrDefault(a => a.DmsVerId == version.Id.ToString()) ?? _syncInfoFactory.CreateVersionInfo();
        }

       
        /// <summary>
        /// Should be called when version processsed. Can update File level and Version Level information as it knows which version as processed.
        /// </summary>
        /// <param name="version"></param>
        /// <param name="context"></param>
        public virtual void UpdateSyncInfo(IDmsVersion version, ActionContext context)//NEW
        {
            context = context ?? ActionContext.Default;
            var file = version.GetLatestFile();
            switch (context.Type)
            {
                case ActionType.Import:
                {
                    var info = GetSyncInfoOrCreate(file);
                    info.DMSItemId = file.DMSId.ToString();
                    var versionInfo=GetVersionInfoOrCreate(info, version);
                    versionInfo.DmsVerId = version.ID.ToString();
                    versionInfo.DmsEditTime = version.EditTime.Ticks.ToString();
                    var wsVersoin = context.WsVersion;
                    if (wsVersoin != null)
                    {
                        
                        var wsVersionId = wsVersoin.Id.ToString();
                        info.LastImportedWsVerId = wsVersoin.Id;
                        versionInfo.CurWsVerId = wsVersionId;
                        AddIfNotExists(versionInfo.WsVerIds,wsVersionId);
                    }
                    info.AddVInfo(versionInfo);
                    SaveSyncInfo(file, info);
                    break;
                }
                case ActionType.Upload:
                {
                    var info = GetSyncInfoOrCreate(file);
                    info.DMSItemId = file.DMSId.ToString();
                    info.LastUploadedDmsVerNum = (info.LastUploadedDmsVerNum < version.Number)
                        ? version.Number
                        : info.LastUploadedDmsVerNum;
                    var versionInfo = GetVersionInfoOrCreate(info, version);
                    var wsVersoin = context.WsVersion;
                    versionInfo.DmsVerId = version.ID.ToString();
                    versionInfo.DmsEditTime = version.EditTime.Ticks.ToString();
                    
                    if (wsVersoin != null)
                    {
                        var wsVersionId = wsVersoin.Id.ToString();
                        versionInfo.CurWsVerId = wsVersionId;
                        AddIfNotExists(versionInfo.WsVerIds, wsVersionId);
                    }                    
                    info.AddVInfo(versionInfo);
                    SaveSyncInfo(file, info);
                    break;
                }
            }
        }

        void AddIfNotExists<T>(ICollection<T> list, T item)
        {   
            if (!list.Contains(item))
            {
                list.Add(item);
            }
        }

     
        public virtual void UpdateSyncInfo(IDMSFolder folder, ActionContext context)
        {
            context = context ?? ActionContext.Default;
            switch (context.Type)
            {
                case ActionType.Import:
                case ActionType.Upload:
                {
                    var wsFolder = context.WsFolder;
                    if (wsFolder != null)
                    {
                        var info = GetSyncInfoOrCreate(folder);
                        info.DMSItemId = folder.DMSId.ToString();
                        info.ItemId = wsFolder.Id;
                        info.ParentId = wsFolder.ParentId;
                        info.ActivityId = context.LastActivity ?? info.ActivityId;
                        SaveSyncInfo(folder, info);
                    }
                    break;
                }
            }
        }

        public void BreakLink(IDMSFolder iDMSFolder)
        {
            if (iDMSFolder == null) return;
            SaveSyncInfo(iDMSFolder, null);
            SaveSendDataInfo(iDMSFolder, new int[0]);
        }

        public void BreakLink(IDMSFile iDMSFile)
        {
            if (iDMSFile == null) return;

            try
            {
                var syncinfo = GetSyncInfo(iDMSFile);
                var senddata = GetSendData(iDMSFile.ParentFolder);
                SaveSendDataInfo(iDMSFile.ParentFolder, senddata.Where(f => f != syncinfo.ItemId));
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error in BreakLink() for file", ex);
            }

            SaveSyncInfo(iDMSFile, null);
            if (!iDMSFile.WasUpdatedAfterSend2())
                iDMSFile.DiscardCheckout(true);
        }

        public bool IsLinked(IDMSFolder iDMSFolder)
        {
            if (iDMSFolder == null) return false;
            return GetSyncInfo(iDMSFolder) != null;
        }

        public bool IsLinked(IDMSFile iDMSFile, bool ForceRequest = true)
        {
            if (iDMSFile == null) return false;
            return GetSyncInfo(iDMSFile, ForceRequest) != null;
        }

        internal void CanUpdateSyncInfoOrThrow(IDMSFile iDMSFile, Operations operation)
        {
            if (iDMSFile == null) return;
            _dmsWorker.CanUpdateFileOrThrow(iDMSFile, operation);
        }

        public void CanUpdateSendDataOrThrow(FolderMap folderMap)
        {
            if (folderMap == null) return;
            _dmsWorker.CanUpdateFolderOrThrow(folderMap.LocalFolder);
        }

        public void CanUpdateSyncInfoOrThrow(VersionMap versionMap, Operations operation)
        {
            if(versionMap==null)return;
            _dmsWorker.CanUpdateVersionOrThrow(versionMap.LocalVersion, operation);
        }
    }

    public class ActionContext
    {
        public ActionContext(ActionType type)
        {
            this.Type = type;
        }
        public ActionType Type { private set; get; }
        public WsFile WsFile { set; get; }
        public WsVersion WsVersion { set; get; }

        public string LastActivity { set; get; }
        public WsFolder WsFolder { get; set; }

        public static readonly ActionContext Default =new ActionContext(ActionType.Unknown);
    }

    public enum ActionType
    {
        Unknown,
        Import,
        Upload
    }
}
<file_sep>/WSComponents/src/WSCloudService/ChunkInfo.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.IO;

namespace WorksharePlatform
{
    public class ChunkInfo
    {
        public MemoryStream Stream { get; set; }
        public int PartNumber { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/ConflictResolver/ConflictResolverWindow.xaml.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Windows.Data;
using System.Windows.Input;
using System.Windows.Media;
using Workshare.Components.Helpers;
using Workshare.Components.Views.Common;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using RES = Workshare.Components.Properties.Resources;

namespace Workshare.Components.Views.ConflictResolver
{
    /// <summary>
    /// Interaction logic for ConflictResolverWindow.xaml
    /// </summary>
    public partial class ConflictResolverWindow : OwnWindow
    {
        public ConflictOptions Result
        {
            get
            {
                return ((ConflictResolverViewModel)DataContext).Result;
            }
        }

        public ConflictResolverWindow()
        {
            InitializeComponent();
        }

        private void DockPanel_MouseDown_1(object sender, MouseButtonEventArgs e)
        {
            base.OnTitleMouseDown(sender, e);
        }
        public ConflictResolverWindow(ConflictItemData wsFile, ConflictItemData localFile, string DMSName)
            : this()
        {
            this.DataContext = new ConflictResolverViewModel(wsFile, localFile, DMSName);
        }
    }


    class NameToIconConverter : IValueConverter
    {
        private static readonly string[] WordExt = { ".docx", ".docm", ".dotx", ".dotm", ".doc", ".dot", ".rtf" };

        private static readonly string[] ExcelExt = {
		                                            	".xl", ".xlsx", ".xlsm", ".xlsb", ".xlam", ".xltx", ".xltm", ".xls",
		                                            	".xlt"
		                                            };

        private static readonly string[] PptExt = {
		                                          	".pptx", ".ppt", ".pptm", ".ppsx", ".pps", ".ppsm", ".potx", ".pot",
		                                          	".potm", ".odp"
		                                          };
        private static readonly string[] PDFExt = { ".pdf" };

        private static readonly string[] AudioExt = { ".mp3", ".wav", ".flac", ".aac" };
        private static readonly string[] VideoExt = { ".avi", ".mp4", ".mov", ".mkv" };
        private static readonly string[] ImageExt = { ".bmp", ".jpg", ".jpeg", ".jpe", ".jfif", ".ico", ".png", ".tif", ".tiff", ".dib", ".raw", ".gif" };

        private static readonly string[] TextExt = { ".txt" };

        Dictionary<string, ImageSource> cache = new Dictionary<string, ImageSource>();

        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            System.Drawing.Image image = null;
            var str = value as string;
            str = str ?? string.Empty;
            string ext = string.IsNullOrEmpty(str) ? "" : FileUtils.GetExtension(str).ToLower();
            if (!cache.ContainsKey(ext))
            {
                if (WordExt.Contains(ext))
                {
                    image = RES.doc_medium;
                }
                else if (ExcelExt.Contains(ext))
                {
                    image = RES.xls_medium;
                }
                else if (PptExt.Contains(ext))
                {
                    image = RES.ppt_medium;
                }
                else if (PDFExt.Contains(ext))
                {
                    image = RES.pdf_medium;
                }
                else if (ImageExt.Contains(ext))
                {
                    image = RES.image_medium;
                }
                else if (AudioExt.Contains(ext))
                {
                    image = RES.audio_medium;
                }
                else if (VideoExt.Contains(ext))
                {
                    image = RES.video_medium;
                }
                else if (TextExt.Contains(ext))
                {
                    image = RES.txt_medium;
                }
                else
                {
                    image = RES.generic_medium;
                }

                cache[str] = Utils.Convert(image, System.Drawing.Imaging.ImageFormat.Png);
            }
            return cache[str];
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/WorkshareIntegration.cs
﻿using Workshare.Integration;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Services;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.IManage.Integration
{
    public class WorkshareIntegration : WSIntegrationBase
    {
        public WorkshareIntegration(IAuthProvider authProvider,SyncInfoService syncService)
            : base(authProvider,syncService)
        {}
    }

}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Registering.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using System.Text.RegularExpressions;
using System.Windows.Forms;
using Microsoft.Win32;

namespace Workshare.IManage
{
    [ComVisible(false)]
    public class Registering
    {
        enum App { DeskSite, FIleSite , ImanExt, IIntegrationDlg}

        static char DELIMITER = ',';
        static readonly string[] OPEN_COMMANDS = new[] { "iManExt3.NewOpenCmd", "iManExt.OpenCmd", "@33979", "iManExt.ViewCmd", "IManExt2.NewImportCmd","iManExt.ImportNewVersionCmd" };
        static readonly string COMMANDS_VALUE_NAME="Commands";
        static readonly string CUSTOM_FIELD_PATH = @"SOFTWARE\Workshare\Autonomy\CustomFieldToUse";
        static readonly string CUSTOM_ICON_FIELD_PATH = @"SOFTWARE\Workshare\Autonomy\CustomIconFieldToUse";

        static readonly string SENDDOC_TO_WS_PROGID = typeof(DocumentSendToWSCommand).FullName;
        static readonly string SYNCDOC_FROM_WS_PROGID = typeof(DocumentSyncItemsCommand).FullName;
        static readonly string SENDFLD_TO_WS_PROGID = typeof(FolderSendToWSCommand).FullName;
        static readonly string SYNCFLD_FROM_WS_PROGID = typeof(FolderSyncItemsCommand).FullName;
        static readonly string TRUESYNCFLD_FROM_WS_PROGID = typeof(FolderTrueSyncItemsCommand).FullName;
        static readonly string COLLDOC_FROM_WS_PROGID = typeof(DocumentCeaseCollaborationCommand).FullName;
        static readonly string COLLFLD_FROM_WS_PROGID = typeof(FolderCeaseCollaborationCommand).FullName;

        static readonly string[] DOC_COMMANDS = new[] { SYNCDOC_FROM_WS_PROGID, SENDDOC_TO_WS_PROGID };
        static readonly string[] FLD_COMMANDS = new[] { COLLFLD_FROM_WS_PROGID, SYNCFLD_FROM_WS_PROGID, SENDFLD_TO_WS_PROGID };
        static readonly string[] TOOLBAR_COMMANDS = new[] { TRUESYNCFLD_FROM_WS_PROGID };

        static string[] GetMenuSubKeys(App app)
        {
            switch (app)
            {
                case App.DeskSite: return new[] 
                                                {
                                                    @"Commands\Menus\Document",
                                                    @"Commands\Popup Menus\Folder",
                                                    @"Commands\Menus\File"
                                                };
                case App.ImanExt: return new[] 
                                                {
                                                    @"Browse Dialog\Popup Menus\Folder",
                                                    @"Browse Dialog\Popup Menus\Document",
                                                    @"Express Search\Popup Menus\Document",
                                                    @"Enhanced Integration Dialog\Popup Menus\Document",
                                                    @"Enhanced Integration Dialog\Popup Menus\Folder"
                                                };
                case App.FIleSite: return new[] 
                                                {
                                                    @"Commands\Document",
                                                    @"Commands\Folder",
                                                    @"Commands\IManageMenu\"
                                                };
                case App.IIntegrationDlg: return new[] 
                                                {
                                                    @"Commands\PopupMenu",
                                                    @"Commands\TreePopupMenu\Folder"
                                                };
            }
            return new string[0];
        }

        static string[] GetAppKey(App app)
        {
            switch (app)
            {
                case App.ImanExt: return new[] { 
                    @"SOFTWARE\Interwoven\Worksite\Client\iManExt",
                    @"SOFTWARE\Interwoven\Worksite\8.0\iManExt",
                };
                case App.DeskSite: return new[] { 
                    @"SOFTWARE\Interwoven\Worksite\Client\DeskSite",
                    @"SOFTWARE\Interwoven\Worksite\8.0\DeskSite",
                };
                case App.FIleSite: return new[] { 
                    @"SOFTWARE\Interwoven\Worksite\Client\FileSite",
                    @"SOFTWARE\Interwoven\Worksite\8.0\FileSite",
                };
                case App.IIntegrationDlg: return new[] { 
                    @"SOFTWARE\Interwoven\Worksite\Client\iIntegrationDlg",
                    @"SOFTWARE\Interwoven\Worksite\8.0\iIntegrationDlg",
                };
            }
            return new string[0];
        }

        struct RegValue
        {
            public string Key;
            public string Value;
        }

        static RegValue[] GetRegKey()
        {
            return new RegValue[] 
            { 
                new RegValue() { Key = "IManExt3.FreezeDocumentCmd", Value = "{8848D5D3-F377-4D2D-A003-5B054DC0017D}"},
                new RegValue() { Key = "IManExt.ImportNewVersionCmd", Value = "{C6158533-AD43-449A-A480-C72174D03A5B}" },
                new RegValue() { Key = "IManExt2.NewImportCmd", Value = "{315C27E3-EEE9-46AE-B37B-37B0B24B19B2}" },
                new RegValue() { Key = "IManExt2.IManMoveContentsCmd", Value = "{44B80FA0-1E93-45D3-8A56-C2E03D83DA8E}" },
                new RegValue() { Key = "IManExt2.IManMoveFolderCmd", Value = "{F311F3A1-E00E-48F3-AA23-A4580A97B8B3}" }
            };
        }

        public static int? RegisterReg()
        {
            RegValue[] keys = GetRegKey();
            foreach (RegValue regValue in keys)
            {
                ReplaceRegistry(regValue.Key, regValue.Value);
            }
            return null;
        }

        static int? ReplaceRegistry(string key, string newValue)
        {
            try
            {
                RegistryKey regCR = Registry.ClassesRoot;
                RegistryKey regKey = regCR.OpenSubKey(key, true);
                RegistryKey regCLSID = regKey.OpenSubKey("CLSID", true);
                Registry.SetValue(regCLSID.Name, "", newValue);
            }
            catch (Exception e)
            {
            }

            return null;
        }

        public static int? UnRegisterReg()
        {
            RegValue[] keys = GetRegKey();
            foreach (RegValue regValue in keys)
            {
                string clsid = FindCLSIDByProgID(regValue.Key);
                if (clsid != null)
                {
                    ReplaceRegistry(regValue.Key, clsid);
                }
            }
            return null;
        }

        static string FindCLSIDByProgID(string progID)
        {
            RegistryKey regCR = Registry.ClassesRoot;
            RegistryKey regIDs = regCR.OpenSubKey("CLSID");

            String[] names = regIDs.GetSubKeyNames();
            foreach (String name in names)
            {
                try
                {
                    RegistryKey regCLSID = regIDs.OpenSubKey(name + "\\ProgID");
                    string value = (string)regCLSID.GetValue("");

                    string regexstr = String.Format(@"^{0}(\.\d)?$", progID);
                    Regex regex = new Regex(regexstr, RegexOptions.IgnoreCase);

                    if (regex.Matches(value).Count == 1)
                    {
                        return name;
                    }
                }
                catch (Exception ex)
                {
                }
            }
            return null;
        }
        
        public static int? GetCustomFieldValue() 
        {
            var customFieldKey = Registry.LocalMachine.OpenSubKey(CUSTOM_FIELD_PATH);
            if (customFieldKey != null)
            {
                int res;
                if (int.TryParse(customFieldKey.GetValue("index").ToString(), out res))
                    return res;
            }
            return null;
        }

        public static int? GetCustomIconFieldValue()
        {
            var customFieldKey = Registry.LocalMachine.OpenSubKey(CUSTOM_ICON_FIELD_PATH);
            if (customFieldKey != null)
            {
                int res;
                if (int.TryParse(customFieldKey.GetValue("index").ToString(), out res))
                    return res;
            }
            return null;
        }

        public static void SetCustomFieldValue(int value)
        {
            var cfKey = Registry.LocalMachine.CreateSubKey(CUSTOM_FIELD_PATH);
            cfKey.SetValue("index", value);
        }

        public static void SetCustomIconFieldValue(int value)
        {
            var cfKey = Registry.LocalMachine.CreateSubKey(CUSTOM_ICON_FIELD_PATH);
            cfKey.SetValue("index", value);
        }

        public static void RemoveCustomFieldValues()
        {
            if (Registry.LocalMachine.OpenSubKey(CUSTOM_FIELD_PATH) != null)
                Registry.LocalMachine.DeleteSubKey(CUSTOM_FIELD_PATH);
        }

        public static void RemoveCustomIconFieldValues()
        {
            if (Registry.LocalMachine.OpenSubKey(CUSTOM_ICON_FIELD_PATH) != null)
                Registry.LocalMachine.DeleteSubKey(CUSTOM_ICON_FIELD_PATH);
        }

        static App[] SupportedApps = new[] { App.DeskSite ,App.FIleSite,App.IIntegrationDlg,App.ImanExt};

        public const string WorkshareRegKey = "Workshare";

        static void AppendCommand(App app, string command,RegistryKey menuKey)
        {
            if (NeedRegister(app, command, menuKey))
            {
                var value = menuKey.GetValue(COMMANDS_VALUE_NAME) as string;
                if (!value.Contains(command))
                {
                    //bool hasOpenCommandAsFirst = false;
                    var cmdArr = value.Split(new char[] { DELIMITER });

                    var i = 0;
                    while (i<cmdArr.Length && OPEN_COMMANDS.Contains(cmdArr[i])) i++;

                    if (i == 0)
                    {
                        value = command + DELIMITER + value;
                    }
                    else
                    {
                        value = value.Replace(cmdArr[i - 1], cmdArr[i-1] + DELIMITER + command);
                    }
                }
                menuKey.SetValue(COMMANDS_VALUE_NAME, value);
            }
        }

        public static void SetToolbarOrderByKey(RegistryKey _key)
        { 
            App app = App.DeskSite;
            foreach (var appKey in GetAppKey(app))
            {
                using (var key = _key.OpenSubKey(appKey + @"\toolbar\toolbar-Bar4", true))
                {
                    if (key != null)
                    {
                        var v = key.GetValue("Buttons");
                        if (v != null)
                        {
                            var arr = v as byte[];
                            if (arr != null && arr.Length > 0)
                            {
                                int ar1 = -1, ar2 = -1, ts = -1;
                                int i = 0;
                                while (i + 1 < arr.Length)
                                {
                                    if (arr[i] == 241 && arr[i + 1] == 128) ar1 = i;
                                    if (arr[i] == 242 && arr[i + 1] == 128) ar2 = i;
                                    if (arr[i] == 234 && arr[i + 1] == 128) ts = i;
                                    i += 5;
                                }

                                if (ts < 0)
                                {
                                    if (ar1 > 0 && ar2 > 0)
                                    {
                                        int max = ar1 < ar2 ? ar2 : ar1;
                                        if ((max + 6) < arr.Length)
                                        {
                                            arr[max + 5] = 234;
                                            arr[max + 6] = 128;
                                        }
                                        else
                                        {
                                            arr.Concat(new byte[] { 234, 128, 0, 0, 0 });
                                        }
                                    }
                                    else
                                    {
                                        if (ar1 < 0) arr.Concat(new byte[] { 241, 128, 0, 0, 0 });
                                        if (ar2 < 0) arr.Concat(new byte[] { 242, 128, 0, 0, 0 });
                                        arr.Concat(new byte[] { 234, 128, 0, 0, 0 });
                                    }
                                }
                                key.SetValue("Buttons", arr);
                            }
                        }
                    }
                }
            }
        }

        public static void SetToolbarOrder()
        {
            SetToolbarOrderByKey(Registry.CurrentUser);
        }

        public static void RegisterMenus()
        {
            RegisterReg();

            //TODO refactor 
            //System.Diagnostics.Debugger.Launch();
            foreach (var app in SupportedApps)
            {
                foreach (var appKey in GetAppKey(app))
                {
                    var appRegKey = Registry.LocalMachine.OpenSubKey(appKey, true);
                    if (appRegKey != null)
                    {
                        foreach (var menuRelativePath in GetMenuSubKeys(app))
                        {
                            if (menuRelativePath.ToLower().Contains("IManageMenu".ToLower()))
                            {
                                using (var wsSubKey = appRegKey.CreateSubKey(menuRelativePath))
                                {
                                    var commands=wsSubKey.GetValue(COMMANDS_VALUE_NAME, WorkshareRegKey) as string;
                                    if (!commands.Contains(WorkshareRegKey))
                                    {
                                        commands = commands.TrimEnd(',') + "," + WorkshareRegKey;
                                    }
                                    wsSubKey.SetValue(COMMANDS_VALUE_NAME, commands);
                                }
                                using (var wsSubKey = appRegKey.CreateSubKey(menuRelativePath+@"\"+WorkshareRegKey))
                                {
                                    wsSubKey.SetValue("MenuText", WorkshareRegKey);
                                    wsSubKey.SetValue(COMMANDS_VALUE_NAME, TRUESYNCFLD_FROM_WS_PROGID);
                                }
                                
                                continue;
                            }
                            //setup true sync button 
                            if (app == App.DeskSite && menuRelativePath.ToLower().Contains("file"))
                            {
                                using (var menuKey = appRegKey.OpenSubKey(menuRelativePath, true))
                                {
                                    if (menuKey != null)
                                    {
                                        foreach (var command in TOOLBAR_COMMANDS)
                                        {
                                            AppendCommand(app, command, menuKey);
                                            SetToolbarOrderByKey(Registry.LocalMachine);
                                        }
                                    }
                                }
                                continue;
                            }
                            using (var menuKey = appRegKey.OpenSubKey(menuRelativePath, true))
                            {
                                if (menuKey != null)
                                {
                                    if (menuRelativePath.ToLower().Contains("folder"))
                                    {
                                        foreach (var command in FLD_COMMANDS)
                                        {
                                            AppendCommand(app, command, menuKey);
                                        }
                                    }
                                    else
                                    {
                                        foreach (var command in DOC_COMMANDS)
                                        {
                                            AppendCommand(app, command, menuKey);
                                        }
                                    }
                                }
                            }
                        }
                    }
                }
            }
        }

        private static bool NeedRegister(App app, string command, RegistryKey menuKey)
        {
            return true;
        }

        public static void UnRegisterMenus()
        {
            UnRegisterReg();

            foreach (var app in SupportedApps)
            {
                foreach (var appKey in GetAppKey(app))
                {
                    var appRegKey = Registry.LocalMachine.OpenSubKey(appKey, true);
                    if (appRegKey != null)
                    {
                        foreach (var menuRelativePath in GetMenuSubKeys(app))
                        {
                            using (var commands = appRegKey.OpenSubKey(menuRelativePath, true))
                            {
                                if (commands != null)
                                {
                                    var value = commands.GetValue(COMMANDS_VALUE_NAME) as string;
                                    foreach (var command in FLD_COMMANDS.Concat(DOC_COMMANDS).Concat(TOOLBAR_COMMANDS))
                                    {
                                        if (value != null && value.Contains(command))
                                        {
                                            value = value.Replace(command + DELIMITER, "");
                                            value = value.Replace(DELIMITER + command, "");
                                            commands.SetValue(COMMANDS_VALUE_NAME, value);
                                        }
                                    }

                                }
                            }
                        }
                    }
                }
            }
        }

        public static void ForceToUseIe8Standarts()
        {
            var procName = Process.GetCurrentProcess().MainModule.ModuleName;
            Registry.SetValue(@"HKEY_CURRENT_USER\SOFTWARE\Microsoft\Internet Explorer\MAIN\FeatureControl\FEATURE_BROWSER_EMULATION", procName, 8000);
        }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Concrete/OTFolder.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using Hummingbird.DM.Extensions.Interop.DOCSObjects;
using Hummingbird.DM.Server.Interop.PCDClient;
using Workshare.Components.Exceptions;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;


namespace Workshare.OpenText.Contrete
{
    class ManFolder : IDMSFolder
    {
        IProject m_folder;

        IProfile fld
        {
            get
            {
                return m_folder as IProfile;
            }
        }

        public ManFolder(IProject folder)
        {
            m_folder = folder;
            InitializeName();
        }

        private void InitializeName()
        {
            if (m_folder != null)
            {
                _name = m_folder.Name ?? null;
            }
        }

        public bool IsDeleted
        {
            get
            {
                return false;
            }
        }
       
        private bool DisplayImportDialog(WorksharePlatform.FileDetails file)
        {
            return false;
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, List<WorksharePlatform.Activity> activities, IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool update = true)
        {
            var a = true;

            return AddFile(file, out a, activities,versionIdsToSkip, useProfileDialog, SyncVerOption,StartVersion,update);
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, out bool added, List<WorksharePlatform.Activity> activities, IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool update = true)
        {
            Logger.Write("ManFolder::AddFile() START ", Severity.Information);
            added = false;
            try
            {
                Logger.Write("ManFolder::AddFile() useProfileDialog=" + useProfileDialog.ToString(), Severity.Information);
                if (useProfileDialog)
                {
                    var resadd = added;
                    Workshare.OpenText.Presenter.ModulePresenter.InvokeInSTAThreadIfNeed(() =>
                    {
                        resadd = DisplayImportDialog(file);
                    });
                    added = resadd;
                    return null;
                }
                else
                {
                    IProfile doc = Application.OTInstance.CurrentLibrary.CreateProfile("DEF_PROF");

                    string tmp = Path.GetTempFileName();
                    File.Copy(file.FilePath, tmp, true);

                    string FileType = Application.OTInstance.GetDocClassByFileExtension(Path.GetExtension(file.Name));
                    string AppType = Application.OTInstance.GetAppIDByFileExtension(Path.GetExtension(file.Name), Application.OTInstance.CurrentLibrary);
                    if (string.IsNullOrEmpty(AppType) && FileType == "IMG") // if noone else type for image file did not set - set the default image type
                    {
                        AppType = "DOCSIMAGE";
                    }

                    if (string.IsNullOrEmpty(AppType))
                    {
                        Logger.Write("ManFolder::AddFile() cannot detect AppType for file=" + useProfileDialog.ToString(), Severity.Information);
                        throw new FileNotCreatedException(string.Format(Properties.Resources.STR_CANNOT_ADD_NEW_FILE_WRONG_TYPE_ERROR_F, file.Name));
                    }
                    string FileName = Application.OTInstance.GetItemName(file.FriendlyName);
                    doc.Columns["TYPE_ID"].Value = FileType;
                    doc.Columns["DOCNAME"].Value = FileName;
                    doc.Columns["APP_ID"].Value = AppType;
                    doc.Columns["AUTHOR_ID"].Value = Application.OTInstance.CurrentUser;
                    doc.Columns["TYPIST_ID"].Value = Application.OTInstance.CurrentUser;
                    doc.Save(5);
                    if (doc.ErrCode != 0)
                    {
                        throw new FileNotCreatedException(string.Format(Properties.Resources.STR_CANNOT_ADD_NEW_FILE, FileName, doc.ErrText));
                    }
                    
                    Logger.Write("Trying to upload a file into DMS: " + tmp, Severity.Information);
                    if (doc.Versions!= null && doc.Versions.Count > 0)
                    {
                        var version = doc.Versions[1];
                        File.Copy(tmp, version.FilePath);

                        var Results = version.UploadFile();
                        version.UnlockVersion((short)tagVersionStatus.VS_NORMAL);

                        Logger.Write("Trying to upload a file into DMS: Succeded " + tmp, Severity.Information);
                    }

                    doc.ReleaseDoc();
                    if (m_folder != null)
                    {
                        m_folder.AddDocument(doc);
                    }

                    var createdFile = new OTFile(doc, m_folder);
                    added = true;
                    Logger.Write("ManFolder::AddFile() COMPLETE ", Severity.Information);
                    return createdFile;
                }
            }
            catch (FileNotCreatedException)
            {
                Logger.Write("ManFolder::AddFile() File Not Created Exception", Severity.Information);
                throw;
            }
            catch (Exception ex)
            {
                Logger.Write("ManFolder::AddFile() Exception="+ex.Message, Severity.Information);
                throw new FileNotCreatedException(ex.Message, ex);
            }
        }

        public IDMSFolder AddSubFolder(WorksharePlatform.FolderDetails cloudFolder)
        {
            try
            {
                Logger.Write("ManFolder::AddSubFolder() START ", Severity.Information);
                if (cloudFolder == null) throw new ArgumentNullException("cloudFolder");
                
                bool isAdded = false;
                
                var fld = m_folder.Library.CreateProject();
                string FolderName = Application.OTInstance.GetItemName(cloudFolder.Name);
                (fld as IProfile).Columns["TYPE_ID"].Value = "FOLDER";
                (fld as IProfile).Columns["DOCNAME"].Value = FolderName;
                (fld as IProfile).Columns["APP_ID"].Value = "FOLDER";
                (fld as IProfile).Columns["AUTHOR_ID"].Value = m_folder.Library.UserName;
                (fld as IProfile).Columns["TYPIST_ID"].Value = m_folder.Library.UserName;
                (fld as IProfile).Save(5);
                
                if (fld.ErrCode == 0)
                {
                    isAdded = m_folder.AddSubProject(fld);
                }
                
                if (isAdded)
                {
                    var addedFolder = m_folder.SubProjects[FolderName];
                    var createdFolder = new ManFolder(addedFolder);
                    createdFolder.UpdateSyncInfo(cloudFolder, true);
                    Logger.Write("ManFolder::AddSubFolder() COMPLETE ", Severity.Information);
                    return createdFolder;
                }
                Logger.Write("ManFolder::AddSubFolder() COMPLETE WITH NO SUCCESS ", Severity.Information);
                return null;
            }
            catch (Exception ex)
            {
                Logger.Write("ManFolder::AddSubFolder() Exception= "+ex.Message, Severity.Information);
                throw new FolderNotCreatedException(string.Format(RES.STR_CANNOT_ADD_NEW_FOLDER_ERROR_F, cloudFolder.Name, ex.Message));
            }
        }

        public void UpdateDisplayName(string name)
        {
            if (fld != null && fld.Name != name)
            {
                _name = Application.OTInstance.GetItemName(name);
                fld.Columns["DOCNAME"].Value = _name;
                fld.Save(0);
            }
        }

        public void UpdateSyncInfo(WorksharePlatform.FolderDetails folderDetails, bool silentUpdate)
        {
            //Logger.Write("ManFolder::UpdateSyncInfo() START ", Severity.Information);
            //try
            //{
            //    string fieldvalue = string.Empty;
            //    if (folderDetails != null)
            //    {
            //        var info = OTSyncInfo.Create(folderDetails, m_folder);
            //        if (info != null)
            //        {
            //            fieldvalue = info.ToString();
            //        }
            //    }
            //    Logger.Write("Sync info created ", Severity.Information);

            //    if (fld != null)
            //    {
            //        fld.Columns[Application.OTInstance.SENDINFO_FIELD].Value = fieldvalue;
            //        fld.Save(0);
            //    }
            //    else
            //    {
            //        PCDDocObject doc = new PCDDocObject();
            //        doc.SetDST(Application.OTInstance.UserDST);
            //        doc.SetObjectType("cyd_defprof");
            //        doc.SetProperty("%TARGET_LIBRARY", m_folder.Library.Name);
            //        doc.SetProperty("%OBJECT_IDENTIFIER", m_folder.ProjectID.ToString());
            //        doc.Fetch();

            //        Logger.Write("Target folder found ", Severity.Information);

            //        if (doc.ErrNumber == 0)
            //        {
            //            doc.SetProperty(Application.OTInstance.SENDINFO_FIELD, fieldvalue);
            //            if (folderDetails == null || string.IsNullOrEmpty(fieldvalue))
            //            {
            //                doc.SetProperty(Application.OTInstance.DATASTORE_FIELD, "");
            //            }
            //            doc.Update();
            //            Logger.Write("Sync info updated ", Severity.Information);
            //        }
            //        else
            //        {
            //            throw new CannotUpdateSyncInfoException(m_folder.ErrText);
            //        }
            //    }
            //    if (m_folder.ErrCode != 0)
            //    {
            //        throw new CannotUpdateSyncInfoException(m_folder.ErrText);
            //    }
            //} 
            //catch (CannotUpdateSyncInfoException)
            //{
            //    throw;
            //}
            //catch (Exception ex)
            //{
            //    throw new CannotUpdateSyncInfoException(ex.Message, ex);
            //}
            //Logger.Write("ManFolder::UpdateSyncInfo() Complete ", Severity.Information);
        }

        public ISyncInfo GetSyncInfo()
        {
            if (fld != null)
            {
                var res = (OTSyncInfo)OTSyncInfo.Parse(fld.Columns[Application.OTInstance.SENDINFO_FIELD].Value.ToString());
                if (res != null && res.DMSItemId == m_folder.ProjectID)
                   return res;
            }
            return null;
        }

        public bool WasUpdatedAfterSend(ISyncInfo synhInfo)
        {
            //TODO
            return false;
        }

        public IDMSItemID ID
        {
            get { return new ManItemID(m_folder); }
        }

        string _name = null;
        public string Name
        {
            get
            {
                if (string.IsNullOrEmpty(_name))
                {
                    InitializeName();
                }
                return _name;
            }
            set
            {
            }
        }

        public string Description
        {
            get
            {
                if (m_folder != null)
                {
                    return m_folder.Caption;
                }
                else
                {
                    return "";
                }
            }
            set
            {
            }
        }



        public bool DoesUserHavePermissions(Workshare.Integration.Enums.Permissions permissions)
        {
            /*switch (permissions)
            {
                case Integration.Enums.Permissions.EditItem: return (m_folder.EffectiveAccess & imAccessRight.imRightReadWrite) == imAccessRight.imRightReadWrite;
            }*/
            return true;
        }

        public bool CheckedOutToUser
        {
            get { return true; }
        }

        public bool CheckedOut
        {
            get 
            {
                return (fld == null)?false:(fld.Columns["STATUS"].Value.ToString() != "0"); 
            }
        }


        public string DisplayName
        {
            get
            {
                if (m_folder != null)
                {
                    return m_folder.Name;
                }
                else
                {
                    return "";
                }
            }
            set
            {
            }
        }

        public IEnumerable<IDMSFolder> SubFolders
        {
            get
            {
                Logger.Write("ManFolder::SubFolders GET ", Severity.Information);
                var list = new List<IDMSFolder>();
                if (m_folder != null)
                {
                    foreach (IProject subFolder in m_folder.SubProjects)
                    {
                        list.Add(new ManFolder(subFolder));
                    }
                }
                else
                {
                    foreach (IProject subFolder in Application.OTInstance.CurrentLibrary.Projects)
                    {
                        list.Add(new ManFolder(subFolder));
                    }
                }
                return list;
            }
            set
            {
            }
        }

        public IEnumerable<IDMSFile> Files
        {
            get
            {
                Logger.Write("ManFolder::Files GET ", Severity.Information);
                var list = new List<IDMSFile>();
                if (m_folder != null)
                {
                    foreach (IProfile content in m_folder.SubDocuments)
                    {
                        // in subdocuments property there are documents and folders
                        if (content.Columns["APP_ID"].Value.ToString() != "FOLDER")
                        {
                            //content.Fetch();
                            list.Add(new OTFile(content, m_folder));
                        }
                    }
                }
                else
                {
                    foreach (IProfile content in Application.OTInstance.CurrentLibrary.Projects)
                    {
                        if (content!=null && content.Columns["APP_ID"].Value.ToString() != "FOLDER")
                        {
                            //content.Fetch();
                            list.Add(new OTFile(content, m_folder));
                        }
                    }
                }
                return list;
            }
            set
            {
            }
        }

        public IDMSFolder ParentFolder
        {
            get
            {
                Logger.Write("ManFolder::ParentFolder GET ", Severity.Information);
                if (fld != null && fld.ParentProjects.Count > 0)
                {
                    return new ManFolder(fld.ParentProjects[1]);
                }
                return new ManFolder(null); // it's can be when folder located directly in root library
            }
        }


        public void OnBeforeSending(OperationContext context)
        {
           // throw new NotImplementedException();
        }


        public void SaveSendDataInfo2(IEnumerable<int> allItems)
        {
            throw new NotImplementedException();
        }

        public void ClearSendDataInfo()
        {
            // not necessary function for that time
            Logger.Write("ManFolder::ClearSendDataInfo() START ", Severity.Information);
            if (fld != null)
            {
                if (fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value.ToString() != "")
                {
                    fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value = "";
                }
                fld.Save(0);
                fld.Fetch();
                Logger.Write("ManFolder::ClearSendDataInfo() COMPLETE ", Severity.Information);
            }
        }

        public void UpdateSendDataInfo(IEnumerable<int> itemsID)
        {
            Logger.Write("ManFolder::UpdateSendDataInfo() START ", Severity.Information);
            List<int> data = new List<int>();
            if (fld != null)
            {
                if (fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value.ToString() != "")
                {
                    string[] items = fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value.ToString().Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
                    items.ToList().ForEach(x => { int a = 0; int.TryParse(x, out a); data.Add(a); });

                    fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value = "";
                }
                data.AddRange(itemsID);
                string datastring = "";
                data.ForEach(x => datastring += x.ToString() + ";");
                fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value = datastring;
                fld.Save(0);
                Logger.Write("Item sent information updated ", Severity.Information);
                fld.Fetch();
            }
            Logger.Write("ManFolder::UpdateSendDataInfo() COMPLETE ", Severity.Information);
        }

        public IEnumerable<int> GetSendDataInfo()
        {
            Logger.Write("ManFolder::GetSendDataInfo() START ", Severity.Information);
            List<int> data = new List<int>();
            if (fld != null)
            {
                fld.Fetch();
                if (fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value.ToString() != "")
                {
                    string[] items = fld.Columns[Application.OTInstance.DATASTORE_FIELD].Value.ToString().Split(new char[] { ';' }, StringSplitOptions.RemoveEmptyEntries);
                    items.ToList().ForEach(x => { int a = 0; int.TryParse(x, out a); data.Add(a); });
                }
            }
            Logger.Write("ManFolder::GetSendDataInfo() COMPLETE ", Severity.Information);
            return data;

        }

        public void OnSendError(object args, Exception e)
        {
            
        }

        public void OnAfterAdd(OperationContext args)
        {
        }


        public void OnAfterSending(OperationContext context)
        {
            
        }


        public void OnBeforeSync(OperationContext args)
        {
        }


        public void AddHistory(string eventName, string eventComment, Workshare.Integration.Operations operation)
        {
            if (m_folder !=null)
            {
                (m_folder as IProfile).AddDocumentActivity(eventComment);
                m_folder.Save(0);
            }
        }

        public void AddHistories(List<Activity> activities)
        {
            throw new NotImplementedException();
        }

        public void AddHistories(List<WorksharePlatform.Activity> activities, int version)
        {
        }


        public bool WasUpdatedAfterSend2(bool useForceRequest = true)
        {
            return false;
        }


        public void UpdateSendDataInfo2(IEnumerable<int> allItems)
        {

        }


        public int DMSId
        {
            get { return -1; }
        }

        public IDMSFolder RootFolder()
        {
            return null;
        }

        public string DMSItemKey
        {
            get { return ""; }
        }
    }
}
<file_sep>/OpenText/src/RegisterMenus/Program.cs
﻿using Workshare.OpenText;

namespace RegisterMenus
{
    class Program
    {
        static void Main(string[] args)
        {
            Registering.RegisterMenus();
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/WsProxies/WsMember.cs
﻿using WorksharePlatform;

namespace Workshare.Integration.WsProxies
{
    public class WsMember
    {
        private Member _member;
        private UserDetails _user;

        public WsMember(UserDetails user, Member member)
        {
            _member = member;
            _user = user;
        }

        public string Name
        {
            get { return _member.MemberName; }
        }

        public int Id
        {
            get { return _member.MemberId; }
        }

        public string Email
        {
            get
            {
                return _member.Email;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Enums/ItemState.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace Workshare.Components.Enums
{
    public enum ItemState
    {
        Added = 1,
        UpdatedAsNewVersion = 2,
        Deleted = 3
    }
}
<file_sep>/WSComponents/src/WSIntegration/Interfaces/ISyncInfo.cs
﻿using System.Collections.Generic;
using System.Linq;

namespace Workshare.Integration.Interfaces
{

    public interface IWebDataStorageData
    {
        string DataType { get; set; }
    }

    public interface ISendDataInfo : IWebDataStorageData
    {
        string FolderID { get; set; }
        List<int> Items { get; set; } 
    }

    public interface ISyncInfo : IWebDataStorageData
    {

        /// <summary>
        /// parent id  on Wprkshare
        /// </summary>
        int ParentId { get; set; }

        /// <summary>
        /// Last workshare version id that was imported
        /// </summary>
        int LastImportedWsVerId { get; set; }

        /// <summary>
        /// last dms version number that was uploaded to Workshare
        /// </summary>
        int LastUploadedDmsVerNum { get; set; }

        /// <summary>
        /// Id of item on workshare
        /// </summary>
        int ItemId { get; set; }

        /// <summary>
        /// id of item on DMS (should be independent on versions )
        /// </summary>
        string DMSItemId { get; set; }

        /// <summary>
        /// modified time of Dms item  when it was last time synced
        /// </summary>
        string Modified { get; set; }

        /// <summary>
        /// Last activity id on Worksahre that was downloaded from ws 
        /// </summary>
        string ActivityId { get; set; }

        /// <summary>
        /// returns info collection for versions. Most likely we should move this from here
        /// </summary>
        /// <returns></returns>
        List<IVersionSyncInfo> GetvInfos();

        void AddVInfo(IVersionSyncInfo info);
    }

    public static class Ext
    {
        public static bool IsLinked()
        {
            return false;
        }
    }

    public interface IVersionSyncInfo
    {
        /// <summary>
        /// Dms version Id - is used for as identifier of version info
        /// </summary>
        string DmsVerId { set; get; }

        /// <summary>
        /// Last ws version to which dms version was uploaded
        /// </summary>
        string CurWsVerId { set; get; }

        /// <summary>
        /// List of all ws version ids that were created from this dms version
        /// </summary>
        List<string> WsVerIds { set; get; }

        /// <summary>
        /// Dms edit time during last synchronization process of this version
        /// </summary>
        string DmsEditTime { get; set; }
    }

    public static class Exts
    {
        public static bool AnyVersionIsLinkedWithWsVersion(this ISyncInfo info,int wsVersionId)
        {
            if (info == null) return false;
            return info.GetvInfos().Any(a => a.AnyVersionIsLinkedWithWsVersion(wsVersionId));
        }
        public static bool AnyVersionIsLinkedWithWsVersion(this IVersionSyncInfo info, int wsVersionId)
        {
            if (info == null) return false;
            return info.WsVerIds.Any(a => string.Equals(a, wsVersionId.ToString()));
        }
        public static List<string> GetAllWsIds(this ISyncInfo info)
        {
            if (info == null) return new List<string>();
            return info.GetvInfos().Where(b => b != null).SelectMany(a => a.WsVerIds).ToList();
        }
        
    }
}
<file_sep>/WSComponents/src/Framework4Adapter/AsposePdfAdapter.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices;
using WorksharePlatform;

namespace Framework4Adapter
{
    // Class as an example by working with Framework4
    [ComVisible(true)]
    [Guid("A7D39745-C7C1-4DD1-86BB-CC45DEB009F5")]
    public class AsposePdfAdapter : IAsposePdfAdapter
    {
        public AsposePdfAdapter()
        {
        }

        public byte[] AddCommentInData(byte[] data, List<FileComment> comments)
        {
            return data;

        }
    }
}
<file_sep>/iManageIntegration/Src/Workshate.HookEvents/HookDeclareAsRecordCmd.cs
﻿using System;
using System.Runtime.InteropServices;
using System.Runtime.InteropServices.ComTypes;
using System.Windows.Forms;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.Worksite.iManExt3;

namespace Workshare.HookEvents
{
    [ClassInterface(ClassInterfaceType.None)]
    [Guid("8848D5D3-F377-4D2D-A003-5B054DC0017D")]
    [ComVisible(true)]
    public class HookDeclareAsRecordCmd : ICommand, Com.Interwoven.Worksite.iManExt3._ICommandEvents_Event
    {
        public event Com.Interwoven.Worksite.iManExt3._ICommandEvents_OnCancelEventHandler OnCancel;
        public event Com.Interwoven.Worksite.iManExt3._ICommandEvents_OnInitDialogEventHandler OnInitDialog;
        public event Com.Interwoven.Worksite.iManExt3._ICommandEvents_PostOnOKEventHandler PostOnOK;
        public event Com.Interwoven.Worksite.iManExt3._ICommandEvents_PreOnOKEventHandler PreOnOK;

        private FreezeDocumentCmd cmd;
        private bool isCancel = true;

        public HookDeclareAsRecordCmd()
        {
            //MessageBox.Show("Declare As Record");
            cmd = new FreezeDocumentCmd();
            //MessageBox.Show("Declare As Record: new");
            try
            {
                cmd.OnCancel += cmd_OnCancel;
                //MessageBox.Show("Declare As Record: event OnCancel");
                cmd.OnInitDialog += cmd_OnInitDialog;
                //MessageBox.Show("Declare As Record: event OnInitDialog");
                cmd.PostOnOK += cmd_PostOnOK;
                //MessageBox.Show("Declare As Record: event PostOnOk");
                cmd.PreOnOK += cmd_PreOnOK;
                //MessageBox.Show("Declare As Record: event PreOnOk");

            }
            catch (Exception ex)
            {
                //MessageBox.Show("Declare As Record: event" + ex);
            }
        }

        void cmd_OnCancel(object pMyInterface)
        {
            isCancel = true;
            {
                OnCancel(pMyInterface);
            }
        }

        void cmd_PreOnOK(object pMyInterface)
        {
            if (PreOnOK != null)
            {
                PreOnOK(pMyInterface);
            }
        }

        void cmd_PostOnOK(object pMyInterface)
        {
            if (PostOnOK != null)
            {
                PostOnOK(pMyInterface);
            }
        }

        void cmd_OnInitDialog(object pMyInterface)
        {
            if (OnInitDialog != null)
            {
                OnInitDialog(pMyInterface);
            }
        }

        public int Accelerator
        {
            get
            {
                return cmd.Accelerator;
            }
            set
            {
                cmd.Accelerator = value;
            }
        }

        public object Bitmap
        {
            get
            {
                return cmd.Bitmap;
            }
            set
            {
                cmd.Bitmap = value;
            }
        }

        public ContextItems Context
        {
            get
            {
                return cmd.Context;
            }
        }

        public void Execute()
        {
            cmd.Execute();
            if (!isCancel)
            {
                try
                {
                    //var pr = Process.GetCurrentProcess();
                    ////Context.OfType<object>().ToList().ForEach(p => Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                    //var docs = new List<object>() {Context.Item("Declare as Record")};
                    //ProcessIManageEvents.ProcessEvent(docs, EventOperation.DeclareAsRecord, "Declare as Record");
                }
                catch (Exception ex)
                {
                }
            }
        }

        public string HelpFile
        {
            get
            {
                return cmd.HelpFile;
            }
            set
            {
                cmd.HelpFile = value;
            }
        }

        public int HelpID
        {
            get
            {
                return cmd.HelpID;
            }
            set
            {
                cmd.HelpID = value;
            }
        }

        public string HelpText
        {
            get
            {
                return cmd.HelpText;
            }
            set
            {
                cmd.HelpText = value;
            }
        }

        private ContextItems ctx;

        public void Initialize(ContextItems Context)
        {
            cmd.Initialize(Context);

        }

        public string MenuText
        {
            get
            {
                return cmd.MenuText;
            }
            set
            {
                cmd.MenuText = value;
            }
        }

        public string Name
        {
            get
            {
                return cmd.Name;
            }
            set
            {
                cmd.Name = value;
            }
        }

        public int Options
        {
            get
            {
                return cmd.Options;
            }
            set
            {
                cmd.Options = value;
            }
        }

        public int Status
        {
            get
            {
                return cmd.Status;
            }
            set
            {
                cmd.Status = value;
            }
        }

        public Commands SubCommands
        {
            get
            {
                return cmd.SubCommands;
            }
            set
            {
                cmd.SubCommands = value;
            }
        }

        public string Title
        {
            get
            {
                return cmd.Title;
            }
            set
            {
                cmd.Title = value;
            }
        }

        public CommandType Type
        {
            get
            {
                return cmd.Type;
            }
            set
            {
                cmd.Type = value;
            }
        }

        public void Update()
        {
            cmd.Update();
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/Visitors/ItemMapVisitor.cs
﻿using Workshare.Integration.Processor.Maps;

namespace Workshare.Integration.Processor
{
    public abstract class ItemMapVisitor
    {
        public virtual bool VisitEnter(FileMap fileMap) { return true; }

        public virtual void Visit(FileMap fileMap) { }

        public virtual void VisitLeave(FileMap fileMap) { }

        public virtual bool VisitEnter(FolderMap folderMap) { return true; }

        public virtual void Visit(FolderMap foldermap) { }

        public virtual void VisitLeave(FolderMap folderMap) { }

        public virtual void Visit(VersionMap versionMap) { }
    }

}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/UserControls/WsActivitiesViewer.xaml.cs
﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Diagnostics;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Navigation;
using System.Windows.Shapes;
using Workshare.Components.Helpers;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration.Processor.Changes;

namespace Workshare.Components.Views.TrueSyncDialog.UserControls
{
    /// <summary>
    /// Interaction logic for WsActivitiesViewer.xaml
    /// </summary>
    public partial class WsActivitiesViewer : UserControl
    {

        public static readonly DependencyProperty ActivitySourceProperty = DependencyProperty.Register(
            "ActivitySource", typeof (IEnumerable), typeof (WsActivitiesViewer));

        public static readonly DependencyProperty DiscardCommandProperty = DependencyProperty.Register(
            "DiscardCommand", typeof(ICommand), typeof(WsActivitiesViewer));

        public WsActivitiesViewer()
        {            
            InitializeComponent();
        }

        public bool HasItems { get { return CurrentActivityItems.HasItems; } }

        public static readonly DependencyProperty NoItemsTextProperty = DependencyProperty.Register(
            "NoItemsText",
            typeof(string),
            typeof(WsActivitiesViewer));

        public string NoItemsText
        {
            get
            {
                return (string)GetValue(NoItemsTextProperty);
            }

            set
            {
                SetValue(NoItemsTextProperty, value);
            } 
        }

        public ICommand DiscardCommand
        {
            get
            {
                return (ICommand)GetValue(DiscardCommandProperty);
            }
            set
            {
                SetValue(DiscardCommandProperty, value);
            }
        }

        public IEnumerable ActivitySource
        {
            get
            {
                return (IEnumerable)GetValue(ActivitySourceProperty);
            }
            set
            {
                SetValue(ActivitySourceProperty, value);
            }
        }

        private void UIElement_OnMouseUp(object sender, MouseButtonEventArgs e)
        {
            var dataContext = ((FrameworkElement) sender).DataContext;

            var command = this.DiscardCommand;
            if (command != null)
            {
                if (command.CanExecute(dataContext))
                {
                    command.Execute(dataContext);
                }
            }
        }

        public static Window GetParentWindow(DependencyObject child)
        {
            var parentObject = VisualTreeHelper.GetParent(child);
            if (parentObject == null)
            {
                return null;
            }

            var parent = parentObject as Window;
            if (parent != null)
            {
                return parent;
            }
            return GetParentWindow(parentObject);
        }

        private void Hyperlink_OnRequestNavigate(object sender, RequestNavigateEventArgs e)
        {
            try
            {
                ProcessUtils.StartProcess(e.Uri.ToString());
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/VMs/UploadFileActivityVm.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.TrueSyncDialog
{
    public class UploadFileActivityVm : FileActivityBaseVm<ImportFileActivityVm>
    {
        internal UploadFileActivity _data;

        public UploadFileActivityVm()
            : base(null)
        {
        }

        public UploadFileActivityVm(UploadFileActivity data)
            : base(data)
        {
            _data = data;
        }

        public IEnumerable<FileActivityChange> Changes
        {
            get
            {
                var res = _data.Changes.ToList();
                return res;
            }
        }

        public string DefaultTitle
        {
            get
            {
                return "Upload";
            }
        }

        public override bool IsInProgress
        {
            get { return State == UploadFileActivityState.Uploading; }
        }

        public UploadFileActivityState State
        {
            get
            {
                return _data.State;
            }
            set
            {
                _data.State = value;
                this.PropertyHasChanged(s => s.State);
            }
        }



        public override void OnStartProcessing()
        {
            State=UploadFileActivityState.Uploading;
        }

        
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Concrete/HistoryHelper.cs
﻿using Hummingbird.DM.Extensions.Interop.DECore;
using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Components.WSLogger;

namespace Workshare.OpenText.Concrete
{
    public struct HistoryRowInfo
    {
        public DateTime DateOp;
        public string User;
        public string Operate;
    }

    public class HistoryHelper
    {
        public static List<HistoryRowInfo> GetHistory(BCObject obj)
        {
            List<HistoryRowInfo> _history = new List<HistoryRowInfo>();

            if (obj != null)
            {
                try
                {
                    Logger.Write("START getting history", Severity.Information);
                    Hummingbird.DM.Extensions.Interop.DECore.IBCEnumObjects eo;
                    BCCoreCtx ctx = new BCCoreCtx();
                    ctx.RegisterVariantParam("SID", "HistorySID");
                    ctx.RegisterVariantParam("UIContext", "History");
                    eo = obj.EnumChildObjects(ctx);
                    eo.OrderBy("START_DATE, START_TIME");
                    Hummingbird.DM.Extensions.Interop.DECore.IBCObject hr;
                    eo.Next(1, out hr);
                    while (hr != null)
                    {
                        string dat = hr.GetProperty("History", "HistoryDates", "START_DATE").ToString();
                        string tm = hr.GetProperty("History", "HistoryDates", "START_TIME").ToString();
                        string dsc = hr.GetProperty("History", "HistoryDates", "DESCRIPTION").ToString();
                        string usr = hr.GetProperty("History", "HistoryDates", "TYPIST_ID").ToString();
                        _history.Add(new HistoryRowInfo() { DateOp = DateTime.Parse(dat + " " + tm), Operate = dsc, User = usr });
                        eo.Next(1, out hr);
                    }
                    Logger.Write("FINISH getting history", Severity.Information);
                }
                catch
                {
                    Logger.Write("ERROR getting history", Severity.Information);
                }
            }

            return _history;
        }

        public static string GetLastCheckedOutUser(BCObject obj)
        {
            var _hist = GetHistory(obj);
            var checkedout = _hist.Where(x => x.Operate.Equals("Check-out", StringComparison.InvariantCultureIgnoreCase)).OrderByDescending(x=>x.DateOp);
            var operate = checkedout.FirstOrDefault();
            return operate.User;
        }

    }

}
<file_sep>/WSComponents/src/WSComponents/Views/Common/Utils.cs
﻿using System.Drawing;
using System.Drawing.Imaging;
using System.IO;
using System.Windows;
using System.Windows.Interop;
using System.Windows.Media;
using System.Windows.Media.Imaging;

namespace Workshare.Components.Views.Common
{
    static class Utils
    {
        public static ImageSource Convert(Image image, ImageFormat format)
        {
            var bitmap = new BitmapImage();
            bitmap.BeginInit();
            var memoryStream = new MemoryStream();
            // Save to a memory stream...
            image.Save(memoryStream, format);
            memoryStream.Seek(0, SeekOrigin.Begin);
            bitmap.StreamSource = memoryStream;
            bitmap.EndInit();
            return bitmap;
        }
        public static ImageSource ToImageSource(Icon icon)
        {
            ImageSource imageSource = Imaging.CreateBitmapSourceFromHIcon(
                icon.Handle,
                Int32Rect.Empty,
                BitmapSizeOptions.FromEmptyOptions());

            return imageSource;
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/Visitors/ProcessVisitor.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Integration.Processor.Maps.Visitors
{
    //for now only filemap can be processed directly
    public class ProcessVisitor:ItemMapVisitor
    {
        private ProcessOptions _options;

        readonly DmsProcessStrategyBase _dmsProcessStrategy;

        public ProcessVisitor(DmsProcessStrategyBase dmsProcessStrategy)
        {
            _dmsProcessStrategy = dmsProcessStrategy;
        }

        public void Initialize(ProcessOptions options)
        {
            _options = options;
        }

        IEnumerable<ItemMapActivityAction> GetActionsForMap(ItemMap map)
        {
            return _options.ActionsToApply
                .Where(a => (a.Activity == null ? a.ActivityId : a.Activity.MapId) == map.Id).Distinct();
        }

        public override void Visit(FileMap fileMap)
        {
            try
            {
                var forthisNode = GetActionsForMap(fileMap);

                var res = _dmsProcessStrategy.Process(fileMap, new DmsProcessOptions(forthisNode));
                fileMap.ProcessState = res.Result;
            }
            catch (Exception ex)
            {
                fileMap.ProcessState = ProcessState.Error;
                fileMap.Error = ex;
            }
        }

        public override void Visit(FolderMap foldermap)
        {
            try
            {
                var forthisNode = GetActionsForMap(foldermap);

                var res = _dmsProcessStrategy.Process(foldermap, new DmsProcessOptions(forthisNode));
                foldermap.ProcessState = res.Result;
            }
            catch (Exception ex)
            {
                foldermap.ProcessState = ProcessState.Error;
                foldermap.Error = ex;
            }
        }

        public override void VisitLeave(FolderMap folderProcessResult)
        {
        }

        public override void VisitLeave(FileMap fileMap)
        {
        }

        public override void Visit(VersionMap versionMap)
        {
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Interfaces/IWSComponentsApp.cs
﻿using System;
using Workshare.Components.Interfaces;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;

namespace Workshare.Components.Interfaces
{
    public interface IWSComponentsApp
    {
        IWSIntegration Integration { get; }
        IAuthProvider AuthProvider { get; }
        IModuleView View { get; set; }
        IModulePresenter Presenter { get; }
        ModuleBase Module { get; }
        Uri Server { get; }
        string APP_CODE { get; }
        string ServerKey { get; set; }
    }
}
<file_sep>/SharePoint/src/WorksharePointCloud/Layouts/WorkshareCloud/Auth_Token_Handler.aspx.cs
﻿using System;
using Microsoft.SharePoint;
using Microsoft.SharePoint.WebControls;
using WorkshareCloud.Common;

namespace WorkshareCloud.Layouts.WorkshareCloud
{
    public partial class Auth_Token_Handler : LayoutsPageBase
    {

        public const string TMP_AUTH_TOKEN = "<PASSWORD>";
        protected void Page_Load(object sender, EventArgs e)
        {
            var authToken=this.Request.QueryString[TMP_AUTH_TOKEN];
            if (!string.IsNullOrEmpty(authToken))
            {
                var user = CloudAuthenication.GetCurrentUser();
                user.AuthToken = authToken;
                CloudAuthenication.Update(user);
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Common/ConflictItemData.cs
﻿using System;

namespace Workshare.Integration.Common
{
    public class ConflictItemData
    {
        public string Name { set; get; }
        public string Modifier { set; get; }
        public string DateStr { set; get; }
        public DateTime Date { set; get; }
        public int VersionsNumber { get; set; }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Concrete/OTSynhInfo.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Integration.Interfaces;

namespace Workshare.OpenText.Contrete
{
    class OTSyncInfo : ISyncInfo
    {

        OTSyncInfo()
        {
        }
        public int ParentFolderId
        {
            get;
            set;
        }

        public int VersionId
        {
            get;
            set;
        }

        public int ParentId { get; set; }
        public int LastImportedWsVerId { get; set; }

        public int ItemId
        {
            get;
            set;
        }

        public string Modified
        {
            get;
            set;
        }

        public string ActivityId { get; set; }
        public List<IVersionSyncInfo> GetvInfos()
        {
            throw new NotImplementedException();
        }

        public void AddVInfo(IVersionSyncInfo info)
        {
            throw new NotImplementedException();
        }

        public IVersionSyncInfo GetOrCreate(string p)
        {
            throw new NotImplementedException();
        }

        public IVersionSyncInfo CreateVersionInfo()
        {
            throw new NotImplementedException();
        }

        public int DMSItemId
        {
            get;
            set;
        }

        public long CheckOutDate
        {
            get;
            set;
        }

        public bool WasAlreadyCheckedOut
        {
            get;
            set;
        }

        public bool NeedToCheckedOut
        {
            get;
            set;
        }

        const char DELIMITER = ';';

        public const long NOT_CHECKED_OUT_DATE = -1;

        public override string ToString()
        {
            return string.Format("{1}{0}{2}{0}{3}{0}{4}{0}{5}{0}{6}{0}{7}{0}{7}", DELIMITER, ParentFolderId, ItemId, VersionId, Modified, DMSItemId, CheckOutDate, WasAlreadyCheckedOut.ToString(), NeedToCheckedOut);
        }

        internal static OTSyncInfo Create(WorksharePlatform.FileDetails fileDetailes, DateTime ModifyDate, global::Hummingbird.DM.Extensions.Interop.DOCSObjects.IProfile m_document, bool IsAlreadyCheckedout, bool needToCheckOut)
        {
            var file = new OTFile(m_document);
            return new OTSyncInfo()
            {
                ItemId = fileDetailes.CurrentVersion.FileId,
                Modified = ModifyDate.Ticks.ToString(),
                ParentFolderId = fileDetailes.FolderId,
                VersionId = (fileDetailes.CurrentVersion != null) ? fileDetailes.CurrentVersion.Id : 0,
                DMSItemId = m_document.DocNumber,
                CheckOutDate = (file.CheckoutTime.HasValue) ? file.CheckoutTime.Value.Ticks : NOT_CHECKED_OUT_DATE,
                WasAlreadyCheckedOut = IsAlreadyCheckedout,
                NeedToCheckedOut = needToCheckOut
            };
        }

        internal static ISyncInfo Parse(string p)
        {
            if (!string.IsNullOrEmpty(p))
            {
                var splits = p.Split(DELIMITER);
                if (splits.Length == 7)
                {
                    return new OTSyncInfo()
                    {
                        ParentFolderId = int.Parse(splits[0]),
                        ItemId = int.Parse(splits[1]),
                        VersionId = int.Parse(splits[2]),
                        Modified = splits[3],
                        DMSItemId = int.Parse(splits[4]),
                        CheckOutDate = long.Parse(splits[5]),
                        WasAlreadyCheckedOut = bool.Parse(splits[6]),
                        NeedToCheckedOut = bool.Parse(splits[7])
                    };
                }
            }
            return null;
        }

        internal static OTSyncInfo Create(WorksharePlatform.FolderDetails folderDetails, global::Hummingbird.DM.Extensions.Interop.DOCSObjects.IProject m_folder)
        {
            if (folderDetails == null) return null;
            return new OTSyncInfo()
            {
                ItemId = folderDetails.Id,
                ParentFolderId = folderDetails.ParentId,
                VersionId = 0,
                Modified = "0",
                DMSItemId = m_folder.ProjectID
            };
        }


        public string LastActivityId
        {
            get;set;
        }


        string ISyncInfo.DMSItemId
        {
            get
            {
                throw new NotImplementedException();
            }
            set
            {
                throw new NotImplementedException();
            }
        }


        public System.Collections.Generic.List<int> ProcessedVersionIdss
        {
            get
            {
                throw new NotImplementedException();
            }
            set
            {
                throw new NotImplementedException();
            }
        }


        public int LastUploadedDmsVerNum
        {
            get
            {
                throw new NotImplementedException();
            }
            set
            {
                throw new NotImplementedException();
            }
        }

        public string DataType
        {
            get
            {
                throw new NotImplementedException();
            }
            set
            {
                throw new NotImplementedException();
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents.Tests/TestWSApplication.cs
﻿using NUnit.Framework;
using Workshare.Components.Concrete;

namespace WSComponents.Tests
{
    [TestFixture]
    public class TestWSApplication
    {

        [TestFixtureSetUp]
        public void Setup()
        {
 //           WSApplication.Instance = new WSApplication();
        }

//        [Test]
        public void Properties_NotNull()
        {
            Assert.IsNotNull(WSApplication.Instance.AuthProvider);
            Assert.IsNotNull(WSApplication.Instance.Integration);
            Assert.IsNotNull(WSApplication.Instance.View);
            Assert.IsNotNull(WSApplication.Instance.Presenter);
            Assert.IsNotNull(WSApplication.Instance.Server);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents.Tests/TestPresenterBase.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Moq;
using NUnit.Framework;
using Workshare.Components;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Interfaces;
using Workshare.Components.Presenter;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using WorksharePlatform;

namespace WSComponents.Tests
{

    class TestPresenter : ModulePresenterBase
    {
        public TestPresenter(IModuleView view, IWSIntegration integration)
            : base(view, integration)
        { }

        public override bool LoginIfNeeded()
        {
            return true;
        }

        public override DialogSettings GetCurrentDialogSettings(UserDetails user)
        {
            return DefaultDialogSettings;
        }
    }

    [TestFixture]
    public class TestPresenterBase
    {
        
        TestPresenter presenter;
        Mock<IModuleView> view;
        Mock<IWSIntegration> integration;
        Mock<IDMSFolder> fld;
        Mock<IDMSFile> file;
        Mock<IWSComponentsApp> app;

        [SetUp]
        public void Setup()
        {
            app = new Mock<IWSComponentsApp>();
            WSApplication.Instance = app.Object;
            view = new Mock<IModuleView>();
            integration = new Mock<IWSIntegration>();
            app.Setup(x => x.View).Returns(view.Object);
            app.Setup(x => x.Integration).Returns(integration.Object);

            presenter = new TestPresenter(app.Object.View, app.Object.Integration);
        }

        [Test]
        public void TestShowProgress()
        {
            view.Verify(x => x.ShowProgressWindow(It.IsAny<Workshare.Components.Views.Common.CommandInvoker>()), Times.Once());
        }

//        [Test]
        public void TestError_ShowOnlyErrorMessage()
        {
            ItemsErrorsCollection lst = new ItemsErrorsCollection(null);
            bool errorWasShown = false;
            fld = new Mock<IDMSFolder>();
            lst.Add(fld.Object, new CloudFolderNotFound("Folder not found"));
            file = new Mock<IDMSFile>();
            lst.Add(file.Object, new CloudFileNotFound("File not found"));
            MultiItemsException ex = new MultiItemsException(lst, null);
            view.Setup(x => x.ShowErrors(It.IsAny<IEnumerable<ItemException>>())).Callback<IEnumerable<ItemException>>((y) => { errorWasShown = true; Assert.IsTrue(y.Count() == 2); });

            presenter.res_OnError(null, new WorkUnitErrorEventArgs(null, ex));
            
            Assert.IsTrue(errorWasShown);
            view.Verify(x => x.ShowError(It.IsAny<Exception>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<string>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<BaseException>()), Times.Never());
        }

//        [Test]
        public void TestError_ShowOnlyOneMessageWhenFolderAccesDeny()
        {
            ItemsErrorsCollection lst = new ItemsErrorsCollection(null);
            bool errorWasShown = false;

            file = new Mock<IDMSFile>();
            lst.Add(file.Object, new CloudFileNotFound("Folder not found"));
            lst.Add(file.Object, new CloudFolderAccessDenied("Access Deny", "Folder Access Deny"));
            lst.Add(file.Object, new CannotProcessItemException());

            MultiItemsException ex = new MultiItemsException(lst, null);
            view.Setup(x => x.ShowErrors(It.IsAny<IEnumerable<ItemException>>())).Callback<IEnumerable<ItemException>>((y) => { errorWasShown = true; Assert.IsTrue(y.Count() == 1); });

            presenter.res_OnError(null, new WorkUnitErrorEventArgs(null, ex));

            Assert.IsTrue(errorWasShown);
            view.Verify(x => x.ShowError(It.IsAny<Exception>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<string>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<BaseException>()), Times.Never());
        }

//        [Test]
        public void TestError_ShowCheckinDialog()
        {
            ItemsErrorsCollection lst = new ItemsErrorsCollection(null);
            file = new Mock<IDMSFile>();
            var err = new FileOnCloudIsNewerException(file.Object, "CloudName", DateTime.Now, "Clouduser", 2);
            var file2 = new Mock<IDMSFile>();
            var err2 = new FileOnCloudIsNewerException(file2.Object, "CloudName2", DateTime.Now, "Clouduser2", 2);
            lst.Add(file.Object, err);
            lst.Add(file2.Object, err2);
            var ex = new MultiItemsException(lst, new OperationContext(new List<IDMSItem>() { file.Object, file2.Object }, new List<FileMapActivity>())); 

            int callCount = 0;
            bool canContinue = false;

            view.Setup(x => x.ShowCheckinDlg(It.IsAny<ConflictItemData>(), It.IsAny<IDMSFile>(), It.IsAny<bool>(), It.IsAny<int>(), It.IsAny<bool>())).Callback(() => { callCount++; }).Returns(new CheckinDlgResult() { ApplyToAll = false, option = Workshare.Integration.Enums.ConflictOptions.Replace });
            integration.Setup(x => x.SyncItems(It.IsAny<IEnumerable<SyncItemInformation>>(), It.IsAny<OperationContext>())).Callback(() => canContinue = true);
            Assert.IsFalse(presenter.IsAnyItemInProgress(), "We should not have any ityem in progress now, but in fact we have"); // we should add item to progress

            presenter.res_OnError(null, new WorkUnitErrorEventArgs(null, ex));

            Assert.IsTrue(callCount == 2, "Dialog should be displayed twice but it was not"); // we should show dialog twice
            
            view.Verify(x => x.ShowError(It.IsAny<Exception>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<string>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<BaseException>()), Times.Never());

            Utility.WaitWithPeriodicalCallback(ref canContinue, Utility.DEFAULT_TIMEOUT, System.Windows.Forms.Application.DoEvents);
            integration.Verify(x => x.SyncItems(It.IsAny<IEnumerable<SyncItemInformation>>(), It.IsAny<OperationContext>()), Times.Once(), "Sync method should be called");
            callCount = 0;

            // return applytoall = true and dialog should displayed only once
            view.Setup(x => x.ShowCheckinDlg(It.IsAny<ConflictItemData>(), It.IsAny<IDMSFile>(), It.IsAny<bool>(), It.IsAny<int>(), It.IsAny<bool>())).Callback(() => { callCount++; }).Returns(new CheckinDlgResult() { ApplyToAll = true, option = Workshare.Integration.Enums.ConflictOptions.Replace });
            presenter.res_OnError(null, new WorkUnitErrorEventArgs(null, ex));
            Assert.IsTrue(callCount == 1, "Dialog should be displayed once this time but it was not"); // we should show dialog once
        }

 //       [Test]
        public void TestError_ShowConflictDialog()
        {
            ItemsErrorsCollection lst = new ItemsErrorsCollection(null);
            file = new Mock<IDMSFile>();
            var err = new FileConflictException(file.Object, "CloudName", DateTime.Now, "Clouduser", 1);
            var file2 = new Mock<IDMSFile>();
            var err2 = new FileConflictException(file2.Object, "CloudName2", DateTime.Now, "Clouduser2", 1);
            lst.Add(file.Object, err);
            lst.Add(file2.Object, err2);
            var ex = new MultiItemsException(lst, new OperationContext(new List<IDMSItem>() { file.Object, file2.Object }, new List<FileMapActivity>())); 

            int callCount = 0;
            bool canContinue = false;

            integration.Setup(x => x.SyncItems(It.IsAny<IEnumerable<SyncItemInformation>>(), It.IsAny<OperationContext>())).Callback(() => canContinue = true);
            view.Setup(x => x.ShowConflictDialog(It.IsAny<ConflictItemData>(), It.IsAny<ConflictItemData>())).Callback(() => { callCount++; }).Returns(ConflictOptions.KeepBoth);

            presenter.res_OnError(null, new WorkUnitErrorEventArgs(null, ex));
            view.Verify(x => x.ShowError(It.IsAny<Exception>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<string>()), Times.Never());
            view.Verify(x => x.ShowError(It.IsAny<BaseException>()), Times.Never());
            Assert.IsTrue(callCount == 2, "Dialog should be displayed twice but it was not"); // we should show dialog twice
            Utility.WaitWithPeriodicalCallback(ref canContinue, Utility.DEFAULT_TIMEOUT, System.Windows.Forms.Application.DoEvents);
            integration.Verify(x => x.SyncItems(It.IsAny<IEnumerable<SyncItemInformation>>(), It.IsAny<OperationContext>()), Times.Once(), "Sync method should be called");

        }

//        [Test]
        public void TestSendToWorkshare()
        {
            bool canContinue = false;

            fld = new Mock<IDMSFolder>();
            file = new Mock<IDMSFile>();
            List<IDMSItem> lst = new List<IDMSItem>();
            lst.Add(file.Object);
            lst.Add(fld.Object);
            
            view.Setup(x => x.ShowSelectFolder(presenter.GetCurrentDialogSettings(null))).Returns(10);
            integration.Setup(x => x.SendItems(lst, It.IsAny<FolderDetails>(), It.IsAny<OperationContext>())).Callback(() => 
            {
                Assert.IsTrue(presenter.IsAnyItemInProgress(), "Items should be in progress in that moment");
                canContinue = true; 
            });
            var auth = new Mock<IAuthProvider>();
            auth.Setup(x => x.GetCurrentWSUser()).Returns(new UserDetails());
            app.Setup(x => x.AuthProvider).Returns(auth.Object);

            Assert.IsFalse(presenter.IsAnyItemInProgress(), "Items should not be in progress in that moment");
            presenter.OnSendItemsClicked(new SendItemsClickedArgs(lst));

            Utility.WaitWithPeriodicalCallback(ref canContinue, Utility.DEFAULT_TIMEOUT, System.Windows.Forms.Application.DoEvents);
            view.Verify(x => x.ShowSelectFolder(presenter.GetCurrentDialogSettings(null)), Times.Once(), "Select folder dialog was not shown");
            integration.Verify(x => x.SendItems(lst,It.IsAny<FolderDetails>(), It.IsAny<OperationContext>()), Times.Once(), "Send method should be called");
            Assert.IsFalse(presenter.IsAnyItemInProgress(), "Items should not be in progress in that moment");
        }

//        [Test]
        public void TestSyncToWorkshare()
        {
            bool canContinue = false;

            fld = new Mock<IDMSFolder>();
            file = new Mock<IDMSFile>();
            List<SyncItemInformation> lst = new List<SyncItemInformation>();
            lst.Add(new SyncItemInformation(file.Object, ConflictOptions.None, ConflictVersionOptions.None));
            lst.Add(new SyncItemInformation(fld.Object, ConflictOptions.None, ConflictVersionOptions.None));

            integration.Setup(x => x.SyncItems(It.IsAny<IEnumerable<SyncItemInformation>>(), It.IsAny<OperationContext>()))
                .Callback<IEnumerable<SyncItemInformation>, OperationContext>((a, b) => {
                    Assert.IsTrue(presenter.IsAnyItemInProgress(), "Items should be in progress in that moment");
                    if (a.Count() == 2)
                    {
                        canContinue = true;
                    } 
                });
            var auth = new Mock<IAuthProvider>();
            auth.Setup(x => x.GetCurrentWSUser()).Returns(new UserDetails());
            app.Setup(x => x.AuthProvider).Returns(auth.Object);

            Assert.IsFalse(presenter.IsAnyItemInProgress(), "Items should not be in progress in that moment");
            presenter.OnSyncItemsClicked(new SyncItemsClickedArgs(lst));

            Utility.WaitWithPeriodicalCallback(ref canContinue, Utility.DEFAULT_TIMEOUT, System.Windows.Forms.Application.DoEvents);
            integration.Verify(x => x.SyncItems(lst, It.IsAny<OperationContext>()), Times.Once(), "Sync method should be called");
            Assert.IsFalse(presenter.IsAnyItemInProgress(), "Items should not be in progress in that moment");
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Application.cs
﻿using System.Diagnostics;
using Microsoft.Win32;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Interfaces;
using Workshare.IManage.Integration;
using Workshare.IManage.Views;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;

namespace Workshare.IManage
{
    public class Application : WSApplication
    {
        Application():base()
        {
            Registering.ForceToUseIe8Standarts();
            
            WorksharePlatform.PlatformService.Host = WorksharePlatform.PlatformService.MY_SERVER;
            WorksharePlatform.PlatformService.UseHostFromRegistry = true;
        }

        public override IModulePresenter Presenter
        {
            get
            {
                return Application.iManInstance.View.m_presenter;
            }
        }

        public static Application iManInstance
        {
            get
            {
                if (Instance == null)
                {
                    Instance = new Application();
                }
                return Instance as Application;
            }
        }


        ModuleBase _module;
        public  override ModuleBase Module
        {
            get { return _module ?? (_module = new IManageModule()); }
        }

        private IModuleView _view;

        public override IModuleView View
        {
            get { return _view ?? (_view = Module.Resolve<IModuleView>()); }
            set { _view = value; }
        }

        public override string APP_CODE { get { return "Workshare-iManage"; } }
        public string SENDINFO_FIELD = "WORKSHARECLOUD";
        public string DATASTORE_FIELD = "WORKSHARESENDINFO";
        public string SUBCLASSNAME = "WORKSHARE";
        public iManType ClientType = iManType.DeskSite;
        private  string _clientVersion = "";
        public string ClientVersion
        {
            get
            {
                if (string.IsNullOrEmpty(_clientVersion))
                {
                    var reg = Registry.LocalMachine.OpenSubKey("SOFTWARE\\Interwoven\\WorkSite\\Client\\Common\\InstallRoot");
                    if (reg == null)
                    {
                        reg = Registry.LocalMachine.OpenSubKey("SOFTWARE\\Interwoven\\WorkSite\\8.0\\Common\\InstallRoot");
                        if (reg == null)
                        {
                            _clientVersion = "7";
                        }
                        else
                        {
                            _clientVersion = "8";
                        }
                    }
                    else
                    {
                        _clientVersion = "9";
                    }
                }
                return _clientVersion;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncUploadFilesDialog/TrueSyncUploadFilesDialog.xaml.cs
﻿using System;
using System.ComponentModel;
using System.Windows;
using Workshare.Components.Common;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.TrueSyncUploadFilesDialog.VMs;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using RES = Workshare.Components.Properties.Resources;


namespace Workshare.Components.Views.TrueSyncUploadFilesDialog
{
    /// <summary>
    /// Interaction logic for WordSendDialogWindow.xaml
    /// </summary>
    public partial class TrueSyncUploadFilesDialog : OwnWindow
    {
        public TrueSyncUploadFilesDialog()
        {
            InitializeComponent();
        }

        private readonly TrueSyncFilesScanDialogVm _vm;

        public TrueSyncUploadFilesDialog(ModuleBase module, TrueSyncFilesScanDialogVm vm)
        {
            InitializeComponent();
            this._vm = vm;
            Closing += TrueSyncUploadFilesDialog_Closing;
        }

        private void TrueSyncUploadFilesDialog_Closing(object sender, CancelEventArgs e)
        {
            bool needClose = true;

            try
            {
                Integration.Processor.Changes.Activities.UploadFileActivityState state = _vm.ParentScans[0].Activities[0].State;

                if (state == Integration.Processor.Changes.Activities.UploadFileActivityState.Uploading)
                {
                    needClose = false;
                }
            }
            catch (Exception ex)
            {
                needClose = ( _vm.State != TrueSyncFilesScanDialogVm.StateEnum.Loading );
            }

            if (!needClose)
            {
                WSApplication.Instance.View.ShowError(new BaseException(RES.STR_WORKSHARE_UPLOADING_DOCUMENT, RES.STR_WAIT_UPLOAD_COMPLETE));
                e.Cancel = true;
            }
        }

        public void Initiailize(IDMSFile file)
        {
            _vm.Initialize(file);
            DataContext = _vm;
        }

        private void OwnWindow_Loaded(object sender, RoutedEventArgs e)
        {
            _vm.RescanCommand.Execute(null);
        }
    }
}

<file_sep>/OpenText/src/Workshare.OpenText/Exceptions/ExceptionExts.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Text;

namespace Workshare.OpenText.Exceptions
{
    static class ExceptionExts
    {
        public static bool IsConnectionError(this Exception ex)
        {
            var wex = ex as WebException;
            if (wex != null)
            {
                var responce = wex.Response as HttpWebResponse;
                if (responce != null)
                {
                    return false;
                }
                else
                {
                    return true;
                }
            }
            return false;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/VMs/ImportFileActivityVm.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Globalization;
using System.Windows.Documents;
using System.Windows.Input;
using Workshare.Components.Enums;
using Workshare.Components.Views.Common;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes.Activities;
using RES = Workshare.Components.Properties.Resources;
using System.Linq;
using System.Windows;
using System.Diagnostics;
using Workshare.Integration.Exceptions;
using System.Net;
using Workshare.Integration.Enums;
using Workshare.Integration.Processor.Changes;
using Workshare.Components.Views.TrueSyncDialog.VMs;

namespace Workshare.Components.Views.TrueSyncDialog
{
    public class ImportFileActivityVm : FileActivityBaseVm<ImportFileActivityVm>
    {
        internal ImportFileActivity _data;

        public ImportFileActivityVm()
            : base(null)
        {

        }

        public ImportFileActivityVm(ImportFileActivity data)
            : base(data)
        {
            _data = data;
        }

        public IEnumerable<FileActivityChange> Changes
        {
            get
            {
                var res = _data.Changes.
                    Where(p => p.Type != ChangeType.NotModified
                               && p.Type != ChangeType.DocTypeChanged
                               && p.Type != ChangeType.NamesDiffer).ToList();
                return res;
            }
        }

        public string DefaultTitle
        {
            get
            {
                //don't forget - returned value is used in WsSplitButton.xaml
                if (_data.Changes.Any(p => p.Type == ChangeType.RemoteDeleted))
                    return "Break Link";
                else
                    return "Import";
            }
        }

        public override bool IsInProgress
        {
            get
            {
                return State == ImportFileActivityState.Importing;
            }
        }

        public ImportFileActivityState State
        {
            get
            {
                return _data.State;
            }
            set
            {
                if (_data.State != value)
                {
                    _data.State = value;
                    this.PropertyHasChanged(p => p.State);
                }
            }
        }

        public override void OnStartProcessing()
        {
            this.State = ImportFileActivityState.Importing;
        }
    }

    public interface IItemMapActivityVm
    {

        string Id { get; }

        string MapId { get; }

        void PropertyChangedAll();

        object data { get; }

        string Name { get; }

        bool IsDiscarded { get; set; }

        void OnStartProcessing();
    }

    public abstract class ItemMapActivityVm<T> : BasePropertyChanged<T>, IItemMapActivityVm
    {
        public abstract string Id { get; }
        public abstract string MapId { get; }
        public abstract object data { get; }
        public abstract string Name { get; }
        public abstract bool IsDiscarded { get; set; }


        public abstract void OnStartProcessing();
    }
}


<file_sep>/iManageIntegration/Src/Workshare.IManage/Strategies/DmsWorker.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components.Exceptions;
using Workshare.Components.Helpers;
using Workshare.IManage.Contrete;
using Workshare.Integration;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Strategies;
using WorksharePlatform;

namespace Workshare.IManage.Strategies
{
    /// <summary>
    /// Should depends only on DMS stuff
    /// </summary>
    public class DmsWorker : DmsWorkerBase
    {
        readonly ModuleBase _module;
        public DmsWorker(ModuleBase module)
        {
            _module = module;
        }

        public override void CanImportNewFileOrThrow(NewFileOptions options)
        {
            var folder = (ManFolder)options.ParentFolder;
            if (folder != null)
            {
                if (!folder.HasRightToAddNewFiles())
                {
                    throw new DMSUnAuthorizedException();
                }
            }
        }

        public override void ImportNewFile(NewFileOptions options)
        {
            try
            {
                if (options.VersionList == null) return;

                ManFile dmsFile = null;
                var parentFolder = (ManFolder)options.ParentFolder;

                bool first = true;
                foreach (var verInfo in options.VersionList)
                {
                    if (first)
                    {
                        var dlg = _module.Resolve<ImportDialog>();
                        var datebase = (parentFolder != null)
                            ? (parentFolder.m_folder.Database)
                            : ((options.BasedOnFile != null)
                                ? ((ManFile)options.BasedOnFile).m_document.Database
                                : null);

                        dlg.Initialize(parentFolder, verInfo.FilePath, verInfo.FriendlyName, datebase);

                        dlg.ShowDialog();
                        dmsFile = dlg.AddedFile;
                        if (dmsFile != null)
                        {
                            verInfo.createdVersion = dmsFile.GetVersions().Last();
                            //dmsFile.Description = options.WsFile.FriendlyName;
                            dmsFile.AddHistory(string.Empty,
                                string.Format(Workshare.Integration.Properties.Resources.STR_HISTORY_ADDFILETOFOLDER,
                                    DateTime.Now.ToString(Activity.TimeFormat)), Operations.Sync);
                            dmsFile.AddHistories(verInfo.Activities.ToList());
                        }
                        options.CreatedFile = dmsFile;

                    }
                    else if (dmsFile != null)
                    {
                        verInfo.createdVersion = dmsFile.GetLatest().AddVersion(verInfo.FilePath, verInfo.file.file, verInfo.Activities.ToList(), dmsFile.DisplayName);
                    }

                    first = false;
                }

                if (dmsFile != null)
                {
                    dmsFile.DiscardCheckout();
                }
            }
            catch (WebException)
            {
                throw;
            }
            catch (FileNotCreatedException)
            {
                throw;
            }
            catch (Exception ex)
            {
                throw new FileNotCreatedException(ex.Message, ex);
            }
            finally
            {
                //in case of exception we should delete temp files from temporary folder anyway
                foreach (var verInfo in options.VersionList)
                {
                    FileUtils.SafeDelete(verInfo.FilePath);
                    verInfo.file.file.DeleteFile();
                }
            }
        }

        public override void ImportNewVersion(NewVersionsOptions options)
        {
            if (options.VersionList == null) return;
            var dmsFile = (ManFile)options.File;

            if (dmsFile.CheckedOut)
            {
                if (FileUtils.IsFileLocked(dmsFile.CheckoutPath))
                {
                    throw new LockedByAnotherProcessException(dmsFile.Name);
                }

                if (dmsFile.IsLocalFileWasEdited())
                {
                    var version = dmsFile.CheckInFile(true);
                    dmsFile = (ManFile)((ManVersion)version).AsFile();
                }
            }

            foreach (var info in options.VersionList)
            {
                try
                {
                    IDmsVersion addedVersion = dmsFile.AddVersion(info.FilePath, info.file.file, info.Activities.ToList(), info.FriendlyName);
                    info.createdVersion = addedVersion;
                    dmsFile = (ManFile)((ManVersion)addedVersion).AsFile();
                }
                finally
                {
                    //in case of exception we should delete temp files from temporary folder anyway
                    FileUtils.SafeDelete(info.FilePath);
                    info.file.file.DeleteFile();
                }
            }
        }

        public override void CanImportNewVersionOrThrow(IDMSFile dmsFile)
        {
            var file = (ManFile)dmsFile;
            file.Refresh();
            var latestVersion = (ManFile)file.GetLatest();
            latestVersion.Refresh();
            if (latestVersion.CheckedOut && !latestVersion.CheckedOutToUser)
            {
                throw new FileCheckoutedToAnotherUser(file.GetCheckoutUser());
            }
        }

        public override void CanUpdateFileOrThrow(IDMSFile localFile, Operations operation)
        {
            var file = (ManFile)localFile;
            file.Refresh();
            if (!file.DoesUserHavePermissions(imAccessRight.imRightReadWrite))
            {
                throw new DMSUnAuthorizedException();
            }
            if (file.CheckedOut && !file.CheckedOutToUser)
            {
                throw new FileCheckoutedToAnotherUser(operation, file.GetCheckoutUser());
            }
        }

        public override void CanUpdateFolderOrThrow(IDMSFolder localFolder)
        {
            var folder = (ManFolder)localFolder;
            if (!folder.DoesUserHavePermissions(imAccessRight.imRightReadWrite))
            {
                throw new DMSUnAuthorizedException();
            }
        }

        public override void CanUpdateVersionOrThrow(IDmsVersion localVersion, Operations operation)
        {
            var version = (ManVersion)localVersion;
            CanUpdateFileOrThrow(version.AsFile(), operation);
        }

        public override void RelateDocument(IDMSFile mainFile, IDMSFile relatedFile, string comment)
        {
            var file = (ManFile)mainFile;
            file.RelateDocument(relatedFile, comment);
        }

        public override IDMSFolder CreateSubFolder(IDMSFolder folder, NewFolderOptions options)
        {
            return folder.AddSubFolder(options.WsFolder._folder);
        }

        public override string GetName(IDMSFile iDMSFile)
        {
            return iDMSFile.Name;
        }

        public override string GetFilePath(IDMSFile iDMSFile)
        {
            var file = (ManFile)iDMSFile;
            return file.GetCurrentCheckedInFile();
        }

        public override string GetFilePath(IDmsVersion dmsVersion)
        {
            var version = (ManVersion)dmsVersion;
            return version.GetCurrentCheckedInFile();
        }

        public override string GetName(IDmsVersion dmsVersion)
        {
            var version = (ManVersion)dmsVersion;
            return version.Name;
        }

        public override string GetFriendlyName(IDmsVersion dmsVersion)
        {
            var version = (ManVersion)dmsVersion;
            return version.DisplayName;
        }

        public override string GetFriendlyName(IDMSFolder folder)
        {
            var fld = (ManFolder)folder;
            return fld.DisplayName;
        }

        public override string GetFriendlyName(IDMSFile iDMSFile)
        {
            var fld = (ManFile)iDMSFile;
            return fld.Name;
        }

        public override DateTime GetEditTime(IDmsVersion dmsVersion)
        {
            var version = (ManVersion)dmsVersion;
            return version.EditTime;
        }

        public override DateTime GetEditTime(IDMSFile dmsFile)
        {
            var file = (ManFile)dmsFile;
            return file.GetLatest().Modified;
        }

        public override IEnumerable<BaseDMSItem> GetParents(BaseDMSFile item)
        {
            var file = (ManFile)item;
            return file.ParentFolders.OfType<BaseDMSItem>();
        }

        public override void AddHistory(IDmsVersion dmsVersion, string eventName, string comment, Operations operation)
        {
            ((ManVersion)dmsVersion).AddHistory(eventName, comment, operation);
        }

        public override void UnlockIfNotEdited(IDMSFile localFile)
        {
            var dmsFile = localFile as ManFile;
            if (dmsFile.CheckedOut)
            {
                if (FileUtils.IsFileLocked(dmsFile.CheckoutPath))
                {
                    throw new LockedByAnotherProcessException(dmsFile.Name);
                }

                if (!dmsFile.IsLocalFileWasEdited())
                {
                    dmsFile.CheckInFileEx(false, imCheckinDisposition.imCheckinReplaceOriginal);
                }
            }
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Common/WSApplication.cs
﻿using System;
using System.Net;
using Workshare.Components.Interfaces;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;

namespace Workshare.Components.Common
{
    public abstract class WSApplication : IWSComponentsApp
    {
        public virtual string APP_CODE { get { return ""; } }

        public string ServerKey { get; set; }

        //protected static WSApplication m_app = null;
        public static IWSComponentsApp Instance
        {
            get; protected set;
        }

        public Uri Server
        {
            get
            {
                return new Uri("https://" + WorksharePlatform.PlatformService.Host);
            }
        }

        public virtual IModulePresenter Presenter
        {
            get
            {
                return Instance.View.m_presenter;
            }
        }        

        public abstract IModuleView View
        {
            get; set;
        }

        protected IWSIntegration _integration;
        public virtual IWSIntegration Integration
        {
            get
            {
                if (_integration == null)
                {
                    ServicePointManager.DefaultConnectionLimit = int.MaxValue;//TODO remove this line. fix problem with multiple files uploading
                    _integration = Module.Resolve<IWSIntegration>();
                }
                return _integration;
            }
        }

        public abstract ModuleBase Module { get; }

        private IAuthProvider _authProvider;
        public virtual IAuthProvider AuthProvider
        {
            get { return _authProvider ?? (_authProvider = Module.Resolve<IAuthProvider>()); }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Activities/ItemMapActivity.cs
﻿using System;
using Workshare.Integration.Processor.Maps;

namespace Workshare.Integration.Processor.Changes
{
    public abstract class ItemMapActivity
    {
        public ItemMapActivity()
        {
            Id = Guid.NewGuid().ToString();
        }

        protected void Refresh(ItemMap map)
        {
            this.MapId = map.Id;
        }

        public string Id { set; get; }

        public string MapId { set; get; }

        public bool IsDiscarded { get; set; }

        public string Type { get; set; }

        public abstract bool InKindOfErrorState();
        public abstract bool InKindOfProceeedState();
        public abstract bool InKindOfProcessingState();
    }
}
<file_sep>/WSComponents/src/WSIntegration/WsProxies/WsVersion.cs
﻿using System;
using WorksharePlatform;

namespace Workshare.Integration.WsProxies
{
    public class WsVersion
    {
        internal FileVersionDetails version;
        UserDetails user;

        public WsVersion(FileVersionDetails version, UserDetails user)
        {
            this.version = version;
            this.user = user;
        }

        public int Id { get { return version.Id; } }

        public int Version { get { return version.Version; } }

        public WsUser Creator { get { return new WsUser(version.Creator); } }

        public DateTime CreateDate { get { return version.CreateDate; } }

        public string DownloadFileVersion()
        {
            return PlatformService.DownloadFileVersion(user, version.FileId, version.Version);
        }

        public string DownloadFileVersionInPdf()
        {
            return PlatformService.DownloadFileVersionInPdf(user, version.FileId, version.Version);
        }

        public string DownloadFileVersionInPdfWithComment(string password)
        {
            return PlatformService.DownloadFileVersionInPdfWithComment(user, password, version.Version);
        }

    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Activities/UploadFileActivity.cs
﻿namespace Workshare.Integration.Processor.Changes.Activities
{
    public class UploadFileActivity : FileMapActivity
    {
        public UploadFileActivityState State { set; get; }

        public UploadFileActivity()
        {
            Type = "UploadActivity";
        }

        public override bool CanExecute(ItemMapActivityAction action)
        {
            if (this.Actions == null) return false;
            if (!(action is UploadDocumentAction)) return false;
            if (this.State != UploadFileActivityState.Scanned)
            {
                return false;
            }

            if (!Actions.Contains(action))
            {
                return false;
            }

            return true;
        }

        public override bool InKindOfErrorState()
        {
            return State == UploadFileActivityState.Error
                   || State == UploadFileActivityState.CheckedOutOnAnotherMachine
                   || State == UploadFileActivityState.CheckedOutToAnother
                   || State == UploadFileActivityState.NoAccessOnWorkshare;
        }

        public override bool InKindOfProcessingState()
        {
            return State == UploadFileActivityState.Uploading;
        }

        public override bool InKindOfProceeedState()
        {
            return State == UploadFileActivityState.Uploaded;
        }

        public override string ToString()
        {
            return string.Format("UploadFileActivity State={0}; Id={1}; Changes={2}", State, MapId,Changes.AsString());
        }
    }

    public enum UploadFileActivityState { Scanned, Uploaded, Error, Uploading, CheckedOutToAnother, CheckedOutOnAnotherMachine, NoAccessOnWorkshare };

    
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/FolderMap.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Maps
{
    public class FolderMap : ItemMap
    {
        public IDMSFolder LocalFolder { set; get; }
        public WsFolder WsFolder { set; get; }

        public override void Apply(ItemMapVisitor visitor)
        {
            if (visitor.VisitEnter(this))
            {
                foreach (var item in this.Maps.ToList())
                {
                    item.Apply(visitor);
                }
                visitor.Visit(this);
            }
            visitor.VisitLeave(this);
        }



        public override string GetId()
        {
            return GetMapId(this);
        }

        public static string GetMapId(FolderMap map)
        {
            if (map.LocalFolder == null)
            {
                return map.WsFolder == null ? string.Format("localfolder:{0};wsfolder:{1}", -1, -1) : string.Format("localfolder:{0};wsfolder:{1}", -1, map.WsFolder.Id);
            }
            if (map.WsFolder == null)
            {
                return string.Format("localfolder:{0};wsfolder:{1}", map.LocalFolder.ID, -1);
            }
            return string.Format("localfolder:{0};wsfolder:{1}", map.LocalFolder.ID, map.WsFolder.Id);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Exceptions/FileNotCreatedException.cs
﻿using System;
using Workshare.Integration.Exceptions;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Exceptions
{
    public class FileNotCreatedException : BaseException
    {
        public FileNotCreatedException(string message)
            : base(RES.STR_UNABLESYNC_CAPTION, message)
        {
        }

        public FileNotCreatedException(string message, Exception inner)
            : base(RES.STR_UNABLESYNC_CAPTION, message, inner)
        {
        }
    }

    public class FolderNotCreatedException : BaseException
    {
        public FolderNotCreatedException(string message)
            : base(RES.STR_UNABLESYNC_CAPTION, message)
        {
        }

        public FolderNotCreatedException(string message, Exception inner)
            : base(RES.STR_UNABLESYNC_CAPTION, message, inner)
        {
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/ActionStrategy/ActionStrategy.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;

namespace Workshare.Integration.Processor.Strategies.ActionStrategy
{
    public abstract class ActionStrategy
    {
        protected SyncInfoService SyncInfoService;
        public ActionStrategy(SyncInfoService syncInfoService)
        {
            this.SyncInfoService = syncInfoService;
        }

        public abstract ProcessResult Process(Maps.FileMap fileMap, ItemMapActivityAction action);
        public abstract ProcessResult Process(FolderMap folderMap, ItemMapActivityAction action);

        protected void UpdateSendInfoForFolder(FolderMap foldermap, int newId)
        {
            var ids =  SyncInfoService.GetSendData(foldermap.LocalFolder).Distinct().ToList();
            if (foldermap.WsFolder != null)
            {
                var existedOnWsIds = foldermap.WsFolder.SubFolders.Select(p => p.Id)
                    .Concat(foldermap.WsFolder.Files.Select(f => f.Id).ToList());

                ids = existedOnWsIds.Intersect(ids).ToList();
            }

            if (ids == null)
            {
                ids = new List<int>();
            }
            if (!ids.Contains(newId))
            {
                ids.Add(newId);
            }

            SyncInfoService.UpdateSendDataInfo(foldermap.LocalFolder, ids);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Visitors/MapFinder.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Processor.Maps;

namespace Workshare.Integration.Processor.Changes.Visitors
{
    class MapFinder:ItemMapVisitor
    {
        private string id;
        public MapFinder(string id)
        {
            this.id = id;
        }

        public ItemMap Result { private set; get; }

        public override bool VisitEnter(FolderMap folderMap)
        {
            return Result == null;
        }

        public override void Visit(FolderMap foldermap)
        {
            if (foldermap.Id == id)
            {
                Result = foldermap;
            }
        }

        public override void Visit(FileMap fileMap)
        {
            if (fileMap.Id == id)
            {
                Result = fileMap;
            } 
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/ErrorsWindow/ErrorsWindow.xaml.cs
﻿using System.Collections.Generic;
using System.Text.RegularExpressions;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Documents;
using System.Windows.Input;
using Workshare.Components.Views.Common;
using Workshare.Integration.Exceptions;

namespace Workshare.Components.Views.ErrorsWindow
{
    /// <summary>
    /// Interaction logic for ErrorsWindow.xaml
    /// </summary>
    public partial class ErrorsWindow : OwnWindow
    {
        public ErrorsWindow()
        {
            InitializeComponent();
        }

        public ErrorsWindow(IEnumerable<ItemException> errors):this()
        {
            this.DataContext = new ErrorsViewModel(errors);
        }

        private void TitleBar_MouseDown(object sender, MouseButtonEventArgs e)
        {
            this.OnTitleMouseDown(sender, e);
        }

        private void richTB_Loaded_1(object sender, RoutedEventArgs e)
        {
            var richTextBox=(RichTextBox)sender;
            var context = richTextBox.DataContext as ItemErrorViewModel;
            if(context!=null)   
            {
                var document=richTextBox.Document??new FlowDocument();
                document.PagePadding = new Thickness(0);
                var paragraph = new Paragraph();
                foreach(var block in GetDescriptionBlocks(context))
                {
                   paragraph.Inlines.Add(block);
                }
                document.Blocks.Add(paragraph);
                richTextBox.Document = document;
            }
        }

        private IList<Inline> GetDescriptionBlocks(ItemErrorViewModel context)
        {
            var blocks = new List<Inline>();
            var regEx = new Regex("(\\$[a-z]+?\\$)", RegexOptions.IgnoreCase);
            var errorMessage = context.Error.Message;

            if (!string.IsNullOrEmpty(errorMessage))
            {
                if (context.Item == null)
                {
                    errorMessage = errorMessage.Replace("$NAME$", "");
                    errorMessage = Regex.Replace(errorMessage, " +", " ");
                    var run = new Run();
                    run.Text = errorMessage;
                    blocks.Add(run);
                }
                else
                {
                    var matches = regEx.Matches(errorMessage);
                    var splits = regEx.Split(errorMessage);
                    foreach (var s in splits)
                    {
                        var run = new Run();
                        if (string.Equals("$NAME$", s))
                        {
                            run.FontWeight = FontWeights.Bold;

                            run.Text = (context.Item != null) ? (context.Item.Name ?? context.Item.DisplayName) : string.Empty;
                        }
                        else
                        {
                            run.Text = s;
                        }
                        blocks.Add(run);
                    }
                }
            }

            return blocks;
        }

    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/ActionStrategy/ImportStrategy.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Net;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Properties;
using Workshare.Integration.WsProxies;
using WorksharePlatform;

namespace Workshare.Integration.Processor.Strategies.ActionStrategy
{
    public class ImportStrategy : ActionStrategy
    {
        readonly WsProxy _wsProxy;
        readonly IAuthProvider _auth;
        readonly DmsWorkerBase _dmsWorker;
        readonly SyncInfoService _syncInfoService;

        public ImportStrategy(WsProxy wsProxy, IAuthProvider auth, DmsWorkerBase dmsWorker, SyncInfoService syncInfoService)
            : base(syncInfoService)
        {
            this._wsProxy = wsProxy;
            this._auth = auth;
            this._dmsWorker = dmsWorker;
            this._syncInfoService = syncInfoService;
        }

        List<string> GetWsVersionIdsFromDms(FileMap fileMap, ISyncInfo syncInfo)
        {
            var res =
                              fileMap.Maps.OfType<VersionMap>()
                                  .Where(a => a.WsVersion != null && a.LocalVersion != null)
                                  .Select(a => a.WsVersion.Id.ToString()).ToList();

            if (syncInfo != null)
            {
                res.AddRange(syncInfo.GetAllWsIds());
            }
            return res;
        }

        public override ProcessResult Process(FileMap fileMap, ItemMapActivityAction action)
        {
            try
            {
                var importAction = (ImportDocumentAction)action;
                var user = _auth.GetCurrentWSUser2();
                if (fileMap.WsFile != null)
                {
                    var wsFileInfo = fileMap.WsFile;
                    var syncInfo = _syncInfoService.GetSyncInfo(fileMap);
                    var lastActivityId = (syncInfo == null) ? "" : syncInfo.ActivityId;
                    var activities =
                        new Func<List<Activity>>(
                            () => _wsProxy.GetFileActivities(user, wsFileInfo, lastActivityId).ToList());

                    var versionsToSikp = GetWsVersionIdsFromDms(fileMap, syncInfo);

                    if (importAction.ImportType == ImportType.AsNewDocument ||
                        importAction.ImportType == ImportType.AsRelatedDocument)
                    {
                        var parentFolderMap = fileMap.GetLocalParent();

                        CreateAncesstorFoldersIfNeeded(fileMap);

                        if (parentFolderMap.HasLocal())
                        {
                            var startVersion = 1;
                            if (syncInfo != null)
                            {
                                startVersion =
                                    fileMap.WsFile.Versions.Where(p => p.Id == syncInfo.LastImportedWsVerId)
                                        .Select(a => a.Version)
                                        .FirstOrDefault();
                                startVersion =
                                    fileMap.WsFile.Versions.OrderBy(a => a.Version)
                                        .Where(p => p.Version > startVersion)
                                        .Select(a => a.Version)
                                        .FirstOrDefault();
                                if (startVersion == 0)
                                {
                                    startVersion = 1;
                                }
                            }
                            var keepLinkForNewFile = !fileMap.HasLocal();
                            var newFile = ImportAsNewFile(wsFileInfo, parentFolderMap.LocalFolder, action, activities,
                                startVersion, fileMap.LocalFile, keepLinkForNewFile,versionsToSikp);
                            if (newFile != null)
                            {
                                UpdateSendInfoForFolder(parentFolderMap, wsFileInfo.Id);

                                if (!fileMap.HasLocal())
                                {
                                    fileMap.LocalFile = newFile;
                                }
                                else
                                {
                                    if (importAction.ImportType == ImportType.AsRelatedDocument)
                                    {
                                        RelateDocument(fileMap.LocalFile, newFile);
                                    }

                                    var newMap = new FileMap();
                                    newMap.LocalFile = newFile;
                                    if (_syncInfoService.GetSyncInfo(newMap) != null)
                                    {
                                        newMap.WsFile = fileMap.WsFile;
                                        newMap.ProcessState = ProcessState.Processed;
                                    }
                                    else
                                    {
                                        newMap.ProcessState = ProcessState.Scanned;
                                    }
                                    parentFolderMap.AddIf(newMap);

                                }

                                return ProcessResult.Processed;
                            }
                            else
                            {
                                return ProcessResult.Cancelled;
                            }
                        }
                    }
                    else if (importAction.ImportType == ImportType.AsNewVersion)
                    {
                        if (fileMap.HasLocal())
                        {
                            ImportAsNewVersion(fileMap.LocalFile, syncInfo, wsFileInfo, action, activities, versionsToSikp);
                            return ProcessResult.Processed;
                        }
                        else
                        {
                            Debug.Assert(false, "new version for null local file?");
                        }
                    }
                    else
                    {
                        Debug.Assert(false, "New ImportType?");
                    }

                }
                else
                {
                    Debug.Assert(false, "Importing deleted file");
                }

                return ProcessResult.Processed;
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode(HttpStatusCode.Forbidden) || ex.IsStatusCode(HttpStatusCode.Unauthorized))
                {
                    throw new CloudFolderAccessDenied(Resources.STR_UNABLE_SYNC, Resources.STR_UNABLESYNCFILE_TEXT, ex);
                }
                if (ex.IsConnectionError())
                {
                    throw new OfflineException();
                }
                throw;
            }
        }

        private void CreateAncesstorFoldersIfNeeded(FileMap fileMap)
        {
            if (fileMap == null) return;
            var curFolderMap = fileMap.Parent as FolderMap;
            var foldersToCreate = new List<FolderMap>();
            while (curFolderMap != null && curFolderMap.HasRemote() && !curFolderMap.HasLocal())
            {
                foldersToCreate.Add(curFolderMap);
                curFolderMap = curFolderMap.Parent as FolderMap;
            }

            if (curFolderMap.HasLocal())
            {
                foldersToCreate.Reverse();
                foreach (var folderToCreateMap in foldersToCreate)
                {
                    var newDmsFolder = _dmsWorker.CreateSubFolder(curFolderMap.LocalFolder, new NewFolderOptions
                    {
                        WsFolder = folderToCreateMap.WsFolder
                    });
                    if (newDmsFolder != null)
                    {
                        _syncInfoService.UpdateSyncInfo(newDmsFolder, new ActionContext(Services.ActionType.Upload)
                        {
                            WsFolder = folderToCreateMap.WsFolder
                        });;
                        folderToCreateMap.LocalFolder = newDmsFolder;

                        curFolderMap = folderToCreateMap;
                    }
                    else
                    {

                        Debug.Assert(false, "Why?");
                        break;
                    }
                }
            }
        }

        private void RelateDocument(IDMSFile mainFile, IDMSFile relatedFile)
        {
            _dmsWorker.RelateDocument(mainFile, relatedFile, "Related using Workshare");
        }

        private IDMSFile ImportAsNewFile(WsFile wsFile, IDMSFolder dmsFolder, ItemMapActivityAction action, Func<List<Activity>> activitiesFunc, int startVersionIncluding, IDMSFile basedOnFile, bool keepLinkForNewFile, List<string> versionsToSkip)
        {
            var versionsToCreate = new List<CreateversionInfo>();

            if (basedOnFile != null)
            {
                _syncInfoService.CanUpdateSyncInfoOrThrow(basedOnFile, Operations.Sync);
            }

            var importAction = (ImportDocumentAction)action;
            var activities = activitiesFunc();
            var lastActivity = activities.LastOrDefault();
            if (importAction.ImportVersionsAction == ConflictVersionOptions.All)
            {
                bool firstVersion = true;
                var versionsToAdd =
                    wsFile.Versions.Where(x => x.Version >= startVersionIncluding && !ShouldBeSkipped(versionsToSkip,x))
                    .OrderBy(x => x.Version).ToArray();
                foreach (var ver in versionsToAdd)
                {
                    var activitiesForCurrentVersion = new List<Activity>();
                    if (firstVersion)
                    {
                        activitiesForCurrentVersion.AddRange(activities.Where(x => x.CurrentVersion < ver.Version).ToList());
                    }
                    activitiesForCurrentVersion.AddRange(activities.Where(x => x.CurrentVersion == ver.Version).ToList());
                    versionsToCreate.Add(new CreateversionInfo
                    {
                        Activities = activitiesForCurrentVersion,
                        file = wsFile,
                        version = ver,
                        FriendlyName = wsFile.FriendlyName,
                        FilePath = ver.DownloadFileVersion()
                    });
                    firstVersion = false;
                }
            }
            else if (importAction.ImportVersionsAction == ConflictVersionOptions.Latest)
            {
                var lastVersion = wsFile.CurrentVersion;

                var startVersion = (wsFile.Versions.Select(p => p.Version).FirstOrDefault());
                startVersion = (startVersion == startVersionIncluding ? startVersion : startVersionIncluding - 1); //
                var activitiesForVersion = activities.ToList();
                if (basedOnFile != null)//importing new versions as new file
                {
                    activitiesForVersion = activities.Where(a => a.CurrentVersion >= startVersion).ToList();
                }

                versionsToCreate.Add(new CreateversionInfo
                {
                    Activities = activitiesForVersion,
                    file = wsFile,
                    version = lastVersion,
                    FriendlyName = wsFile.FriendlyName,
                    FilePath = lastVersion.DownloadFileVersion()
                });
            }

            var options = new NewFileOptions()
                    {
                        WsFile = wsFile,
                        ParentFolder = dmsFolder,
                        BasedOnFile = basedOnFile,
                        VersionList = versionsToCreate
                    };

            _dmsWorker.CanImportNewFileOrThrow(options);

            _dmsWorker.ImportNewFile(options);

            if (options.CreatedFile != null)
            {
                var importeVersionsIds = new List<int>();
                foreach (var verInfo in options.VersionList)
                {
                    if (keepLinkForNewFile)
                    {
                        _syncInfoService.UpdateSyncInfo(verInfo.createdVersion, new ActionContext(Services.ActionType.Import)
                        {
                            WsVersion = verInfo.version
                        }); 
                    }
                    importeVersionsIds.Add(verInfo.version.Id);
                }

                if (options.BasedOnFile != null)
                {
                    _syncInfoService.UpdateSyncInfo(options.BasedOnFile, new ActionContext(Services.ActionType.Import)
                    {
                        WsFile = wsFile,
                        LastActivity = lastActivity.IdOrNull()
                    });
                }
                if (keepLinkForNewFile)
                {
                    _syncInfoService.UpdateSyncInfo(options.CreatedFile, new ActionContext(Services.ActionType.Import)
                    {
                        WsFile = wsFile,
                        LastActivity = lastActivity.IdOrNull()
                    });
                    //_syncInfoService.UpdateSyncInfo(options.CreatedFile, wsFile, lastActivity);
                }
            }

            return options.CreatedFile;
        }

        bool ShouldBeSkipped(IEnumerable<string> toSkip, WsVersion ver)
        {
            return toSkip.Any(a => string.Equals(a, ver.Id.ToString()));
        }

        private void ImportAsNewVersion(IDMSFile dmsFile, ISyncInfo syncInfo, WsFile wsFile, ItemMapActivityAction action, Func<List<Activity>> allActivitiesFunc, IEnumerable<string> versionIdsToSkip)
        {
            _syncInfoService.CanUpdateSyncInfoOrThrow(dmsFile, Operations.Sync);
            _dmsWorker.CanImportNewVersionOrThrow(dmsFile);
            var allActivities = allActivitiesFunc();
            var lastActivity = allActivities.LastOrDefault();
            var importAction = (ImportDocumentAction)action;

            var versionInfos = new List<CreateversionInfo>();

            var versionId = (syncInfo == null) ? 0 : syncInfo.LastImportedWsVerId;
            var startFromVersion = wsFile.Versions.Where(p => p.Id == versionId).Select(p => p.Version).FirstOrDefault();
            if (startFromVersion == 0)
            {
                startFromVersion = 1;
            }

            var versionsToAdd = wsFile.Versions
                .Where(x => x.Version > startFromVersion && !versionIdsToSkip.Contains(x.Id.ToString()))
                .OrderBy(x => x.Version).ToArray();

            dmsFile.AddHistories(allActivities.Where( x => !(versionsToAdd.Any(version => version.Version == x.CurrentVersion)) ).ToList());

            if (importAction.ImportVersionsAction == ConflictVersionOptions.Latest)
            {
                versionsToAdd = wsFile.Versions.Where(x => x.Version > startFromVersion && !ShouldBeSkipped(versionIdsToSkip,x))
                .OrderBy(x => x.Version).ToArray();

                versionInfos.Add(new CreateversionInfo
                {
                    Activities = allActivities.Where(activity => versionsToAdd.Any(version => version.Version == activity.CurrentVersion)),
                    file = wsFile,
                    FriendlyName = wsFile.FriendlyName,
                    version = wsFile.CurrentVersion,
                    FilePath = wsFile.CurrentVersion.DownloadFileVersion()
                });
            }
            else if (importAction.ImportVersionsAction == ConflictVersionOptions.All)
            {
                foreach (var wsVersion in versionsToAdd)
                {
                    versionInfos.Add(new CreateversionInfo()
                    {
                        Activities = allActivities.Where(a => a.CurrentVersion == wsVersion.Version).ToList(),
                        file = wsFile,
                        FriendlyName = wsFile.FriendlyName,
                        version = wsVersion,
                        FilePath = wsVersion.DownloadFileVersion()
                    });
                }
            }

            var options = new NewVersionsOptions
                  {
                      File = dmsFile,
                      WsFile = wsFile,
                      VersionList = versionInfos
                  };

            _dmsWorker.ImportNewVersion(options);

            foreach (var ver in options.VersionList)
            {
                _syncInfoService.UpdateSyncInfo(ver.createdVersion, new ActionContext(Services.ActionType.Import)
                {
                    WsVersion = ver.version
                });
            }
            _syncInfoService.UpdateSyncInfo(dmsFile, new ActionContext(Services.ActionType.Import)
            {
                 WsFile = wsFile,
                 LastActivity = lastActivity.IdOrNull()
            }); 
        }

        public override ProcessResult Process(FolderMap folderMap, ItemMapActivityAction action)
        {
            return ProcessResult.Processed;
        }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Concrete/OTFile.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using Hummingbird.DM.Extensions.Interop.DECore;
using Hummingbird.DM.Extensions.Interop.DOCSObjects;
using Workshare.Components.Exceptions;
using Workshare.Components.Helpers;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.OpenText.Concrete;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.OpenText.Contrete
{
    

    class OTFile : IDMSFile
    {
        IProfile m_document = null;
        IProject m_Folder = null;
        //IManDocumentType newdoctype = null;
        bool wasAlreadyCheckedOut = false;
        bool m_bNeedToCleanTemp = false;
        string m_sTempCheckOutPath = "";

        List<HistoryRowInfo> _history = new List<HistoryRowInfo>();

        public OTFile(IProfile doc)
        {
            Logger.Write("ManFile::Create()", Severity.Information);
            m_document = doc;
            RefreshHistory();
        }

        public OTFile(IProfile doc, IProject folder)
            : this(doc)
        {
            m_Folder = folder;
        }

        private void RefreshHistory()
        {
            _history = HistoryHelper.GetHistory(m_document as BCObject);
        }


        public IDmsVersion AddVersion(string filePath, FileDetails file, List<Activity> activities, string versionFriendlyName = null,
            bool checkInVersion = false, bool keepLocalState = true)
        {
            throw new NotImplementedException();
        }

        public void UpdateSyncInfo(WorksharePlatform.FileDetails fileDetailes, bool silentUpdate, OperationContext ctx, WorksharePlatform.Activity last)
        {
            //Logger.Write("ManFile::UpdateSyncInfo() START", Severity.Information);
            //try
            //{
            //    string fieldvalue = string.Empty;
            //    if (fileDetailes != null && CheckedOutToUser)
            //    {
            //        DateTime LastEditDate = (ctx != null && ctx.CheckOutOption == Workshare.Integration.Enums.CheckOutOptions.CheckOut) ? EditDate : Modified;

            //        var info = OTSyncInfo.Create(fileDetailes, LastEditDate, m_document, wasAlreadyCheckedOut, (ctx == null) ? false : ctx.CheckOutOption == Workshare.Integration.Enums.CheckOutOptions.CheckOut);
            //        if (info != null)
            //        {
            //            fieldvalue = info.ToString();
            //        }
            //    }

            //    Logger.Write("ManFile::UpdateSyncInfo() Try fetch document from OpenText", Severity.Information);
            //    /*PCDDocObject doc = new PCDDocObject();
            //    doc.SetDST(Application.UserDST);
            //    doc.SetObjectType("cyd_defprof");
            //    doc.SetProperty("%TARGET_LIBRARY", m_document.Library.Name);
            //    doc.SetProperty("%OBJECT_IDENTIFIER", m_document.DocNumber.ToString());
            //    doc.SetProperty("%VERSION_ID", m_document.CurrentVersion.VersionID);
            //    doc.Fetch();
            //    if (doc.ErrNumber == 0)
            //    {
            //        doc.SetProperty(Application.SENDINFO_FIELD, fieldvalue);
            //        doc.Update();
            //    }
            //    else
            //    {
            //        throw new CannotUpdateSyncInfoException(m_document.ErrText);
            //    }*/
            //    m_document.Columns[Application.OTInstance.SENDINFO_FIELD].Value = fieldvalue;
            //    m_document.Save(0);

            //    if (m_document.ErrCode != 0)
            //    {
            //        throw new CannotUpdateSyncInfoException(m_document.ErrText);
            //    }

            //    Logger.Write("ManFile::UpdateSyncInfo() FINISH", Severity.Information);
            //}
            //catch (CannotUpdateSyncInfoException)
            //{
            //    Logger.Write("ManFile::UpdateSyncInfo() CannotUpdate error", Severity.Information);
            //    throw;
            //}
            //catch (Exception ex)
            //{
            //    Logger.Write("ManFile::UpdateSyncInfo() Exception error", Severity.Information);
            //    throw new CannotUpdateSyncInfoException(ex.Message, ex) ;
            //}
        }

        public void RemoveTempFileIfNeed()
        {
            if (m_bNeedToCleanTemp && !string.IsNullOrEmpty(m_sTempCheckOutPath))
            {
                if (File.Exists(m_sTempCheckOutPath))
                    File.Delete(m_sTempCheckOutPath);

                m_bNeedToCleanTemp = false;
                m_sTempCheckOutPath = string.Empty;
            }
        }

        public DateTime? CheckoutTime
        {
            get
            {
                Logger.Write("ManFile::CheckOutTime GET", Severity.Information);
                try
                {
                    DateTime? res = null;
                    if (CheckedOut)
                    {
                        var checkedout = _history.Where(x => x.Operate.Equals("Check-out", StringComparison.InvariantCultureIgnoreCase));
                        if (checkedout != null)
                        {
                            res = checkedout.Max(x => x.DateOp);
                        }
                    }
                    return res;
                }
                catch (Exception ex)
                {
                    Logger.Write(ex, Severity.Verbose);
                    return null;
                }
            }
        }

        public ISyncInfo GetSyncInfo()
        {
            Logger.Write("ManFile::GetSyncInfo() START", Severity.Information);
            m_document.Fetch();
            var res = (OTSyncInfo)OTSyncInfo.Parse(m_document.Columns[Application.OTInstance.SENDINFO_FIELD].Value.ToString());       
            // TODO Remove that for NEW WORKFLOW
            if ((!CheckedOutToUser) || (res != null && res.CheckOutDate == OTSyncInfo.NOT_CHECKED_OUT_DATE) || !CheckoutTime.HasValue || (res != null && res.CheckOutDate != CheckoutTime.Value.Ticks))
            {
                return null;
            }
            else
            {
                return res;
            }
        }

        public IDMSItemID ID
        {
            get { return new ManItemID(m_document); }
        }

        string _name = null;
        public string Name
        {
            get
            {
                if (_name == null)
                {
                    string ext = Path.GetExtension(m_document.Name);
                    string def_ext = Path.GetExtension(m_document.CurrentVersion.FilePath);
                    if (string.IsNullOrEmpty(ext) || string.Compare(ext.ToLower(), def_ext.ToLower(), StringComparison.InvariantCultureIgnoreCase) != 0)
                    {
                        _name = m_document.Name + def_ext;
                    }
                    else
                    {
                        _name = m_document.Name;
                    }

                }
                return _name;
            }
            set
            {
            }
        }

        public string Description
        {
            get
            {
                return m_document.CurrentVersion.Comment;
            }
            set
            {
                m_document.CurrentVersion.Comment = value;
            }
        }

        public bool DoesUserHavePermissions(Workshare.Integration.Enums.Permissions permissions)
        {
            /*switch (permissions)
            {
                case Integration.Enums.Permissions.EditItem: return (m_docuemnt.EffectiveAccess & imAccessRight.imRightReadWrite) == imAccessRight.imRightReadWrite;
            }*/
            return true;
        }

        public bool CheckedOutToUser
        {
            get
            {
                Logger.Write("ManFile::CheckedOutToUser GET", Severity.Information);
                RefreshHistory();
                var res = false;
                if (CheckedOut)
                {
                    var checkedout = _history.Where(x => x.Operate.Equals("Check-out"));
                    
                    if (checkedout != null)
                    {
                        DateTime lastCheckOutDate = checkedout.Max(z => z.DateOp);
                        var users = _history.Where(x => x.Operate.Equals("Check-out") && x.DateOp == lastCheckOutDate);
                        string checkedOutUser = users.Select(x => x.User).FirstOrDefault();
                        Logger.Write("NamFile::CheckedOutToUser Checkeduser="+checkedOutUser+" library user="+m_document.Library.UserName, Severity.Information);
                        res = string.Compare(checkedOutUser,m_document.Library.UserName, StringComparison.InvariantCultureIgnoreCase) == 0;
                    }
                }
                return res;
            }
        }

        public bool IsCheckedOutFileExists()
        {
            string checkedoutpath;
            if (!string.IsNullOrEmpty(m_document.CheckoutPath))
            {
                checkedoutpath = m_document.CheckoutPath + Path.GetFileName(m_document.CurrentVersion.FilePath);
            }
            else
            {
                checkedoutpath = m_document.CurrentVersion.FilePath;
            }

            if (CheckedOut && !string.IsNullOrEmpty(checkedoutpath))
            {
                return File.Exists(checkedoutpath);
            }
            else
            {
                return false;
            }
        }

        public bool CheckedOut
        {
            get 
            {
                Logger.Write("ManFile::CheckedOut GET", Severity.Information);
                m_document.Fetch();
                return !(m_document.Columns["STATUS"].Value.ToString() == "0"); 
            }
        }

        public void UpdateDisplayName(string name)
        {
            if (name != m_document.Columns["DOCNAME"].Value.ToString())
            {
                _name = Application.OTInstance.GetItemName(name);
                m_document.Columns["DOCNAME"].Value = _name;
                m_document.Save(0);
                _name = null;
            }
        }

        public void AddVersion(string filePath, WorksharePlatform.FileDetails file, List<WorksharePlatform.Activity> activities, bool checkInVersion = false)
        {
            Logger.Write("ManFile::Update START", Severity.Information);
            string path = (string.IsNullOrEmpty(m_document.CheckoutPath)) ? m_document.CurrentVersion.FilePath : m_document.CheckoutPath + Path.GetFileName(m_document.CurrentVersion.FilePath);
            try
            {
                Logger.Write("Trying to update checkouted file: " + path, Severity.Information);

                if (!string.IsNullOrEmpty(path))
                {
                    File.Copy(filePath, path, true);
                    var res = m_document.CreateVersionFromFile(0, path);
                    if (res == null)
                    {
                        throw new FileCannotBeCheckedInException("Error check in");
                    }
                }
            }
            catch (FileNotUpdatedException) 
            { 
                throw; 
            }
            catch (IOException ex)
            {
                Logger.Write("Failded to update checkouted file: " + path, Severity.Error);
                if (ex.Message.Contains("The process cannot access the file"))
                {
                    throw new FileNotUpdatedException(RES.STR_FILE_LOCKED_REASON, ex);
                }
                else
                {
                    throw new FileNotUpdatedException(ex.Message, ex);
                }
            }
        }

        public bool WasUpdatedAfterSend(ISyncInfo synhInfo)
        {
            return (synhInfo == null) ? false : !string.Equals(Modified.Ticks.ToString(), ((OTSyncInfo)synhInfo).Modified);
        }

        public DateTime EditDate
        { 
            get 
            {
                if (CheckedOut)
                {
                    string localfilepath = string.Empty;
                    try
                    {
                        localfilepath = m_document.CheckoutPath+Path.GetFileName(m_document.CurrentVersion.FilePath);
                        var localfile = new FileInfo(localfilepath);
                        return localfile.LastWriteTime;
                    }
                    catch (IOException ex)
                    {
                        Logger.Write("Failded to access to checkouted file: " + localfilepath, Severity.Error);
                        throw new FileNotFoundException(ex.Message, ex);
                    }
                }
                else
                {
                    return m_document.CurrentVersion.LastEditDate;
                }
            }
        }

        public string GetFilePath()
        {
            Logger.Write("OTFile::GetFilePath() START", Severity.Information);
            string localCopy = string.Empty;
            try
            {
                if (CheckedOut && !string.IsNullOrEmpty(m_document.CheckoutPath))
                {
                    Logger.Write("NamFile::GetFile() Gettin checked out file", Severity.Information);
                    localCopy = m_document.CheckoutPath + Path.GetFileName(m_document.CurrentVersion.FilePath);
                }
                else
                {
                    localCopy = m_document.CurrentVersion.FilePath;
                    Logger.Write("Trying to get copy of a file: " + localCopy, Severity.Information);
                    // do it for sure that we have latest version of the file
                    m_document.CurrentVersion.DownloadFile(); 
                    Logger.Write("Succeded: " + localCopy, Severity.Information);
                }

                Logger.Write("OTFile::GetFilePath() reading file data", Severity.Information);
                return localCopy;
            }
            catch (IOException ex)
            {
                Logger.Write("Failded to access to checkouted file: " + localCopy, Severity.Error);
                throw new LocalFileNotFound();
            }
            catch (Exception ex)
            { 
                Logger.Write("Error due getting of copy: " + localCopy, Severity.CriticalError);
                throw;
            }
        }

        public string DisplayName
        {
            get
            {
                return Path.GetFileNameWithoutExtension(Name);
            }
            set
            {
            }
        }

        public IDMSFolder ParentFolder
        {
            get
            {
                if (m_Folder == null && m_document.ParentProjects.Count == 1)
                {
                    m_Folder = m_document.ParentProjects[1];
                }

                if (m_Folder != null)
                {
                    return new ManFolder(m_Folder);
                }
                return null; // it's can be when file located directly in root library;
            }
        }

        public string Modifier
        {
            get
            {
                return m_document.CurrentVersion.Author;
            }
        }

        public DateTime Modified
        {
            get 
            {
                return m_document.CurrentVersion.LastEditDate; ; 
            }
        }

        const int INFINITY_DAYS = 10000;

        public void OnBeforeSending(OperationContext context)
        {
            Logger.Write("ManFile::OnBeforeSending() START", Severity.Information);
            if (!CheckedOut)
            {
                GetFileToCheckout();
            }
            else if (!CheckedOutToUser)
            {
                Logger.Write("ManFile::OnBeforeSending() File checked out to another user", Severity.Information);
                throw new FileCheckoutedToAnotherUser(Workshare.Integration.Operations.Send);
            }
            else
            {
                wasAlreadyCheckedOut = true;
            }
        }

        public void OnAfterSending(OperationContext context)
        {
            if (context.CheckOutOption == Workshare.Integration.Enums.CheckOutOptions.DontCheckOut && !wasAlreadyCheckedOut)
            {
                DiscardCheckout();
            }
        }

        public void OnAfterSync(OperationContext args)
        {
            Logger.Write("ManFile::OnAfterSync() START", Severity.Information);
            var si = (OTSyncInfo)OTSyncInfo.Parse(m_document.Columns[Application.OTInstance.SENDINFO_FIELD].Value.ToString());
            UpdateSyncInfo(null, true, null,null);
            if ((si == null || !si.WasAlreadyCheckedOut || !si.NeedToCheckedOut) && !WasUpdatedAfterSend(si))
            {
                DiscardCheckout();

                m_bNeedToCleanTemp = true;
                m_sTempCheckOutPath = m_document.CheckoutPath;
                RemoveTempFileIfNeed();
            }
        }

        public void OnAfterAdd(OperationContext args)
        {
            m_document.ReleaseDoc();
        }

        public void OnSendError(object args, Exception ex)
        {
            Logger.Write(ex, Severity.Error);
            if (!wasAlreadyCheckedOut)
            {
                DiscardCheckout();
            }
        }


        private void UpdateDocTypeIfNeed()
        {
        }

        public void DiscardCheckout(bool deleteCheckOutFile = false)
        {
            Logger.Write("ManFile::DiscardCheckout() START", Severity.Information);
            try
            {
                m_document.UnlockProfile(0, 0, "", 0);
                
                if (deleteCheckOutFile)
                    FileUtils.SafeDelete(m_document.CheckoutPath);
            }
            catch
            {
                throw new FileUnlockFailedException();
            }
        }

        public List<IDMSFolder> ParentFolders
        {
            get
            {
                var res = new List<IDMSFolder>();
                foreach (IProject folder in m_document.ParentProjects)
                {
                    res.Add(new ManFolder(folder));
                }
                return res;
            }
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, out bool added, List<WorksharePlatform.Activity> activities, IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool update = true)
        {
            Logger.Write("ManFolder::AddFile() START ", Severity.Information);
            added = false;
            try
            {
                Logger.Write("ManFolder::AddFile() useProfileDialog=" + useProfileDialog.ToString(), Severity.Information);
                /*if (useProfileDialog)
                {
                    var resadd = added;
                    Workshare.OpenText.Presenter.ModulePresenter.InvokeInSTAThreadIfNeed(() =>
                    {
                        resadd = DisplayImportDialog(file);
                    });
                    added = resadd;
                    return null;
                }
                else
                {*/
                    IProfile doc = Application.OTInstance.CurrentLibrary.CreateProfile("DEF_PROF");

                    string FileType = Application.OTInstance.GetDocClassByFileExtension(Path.GetExtension(file.Name));
                    string AppType = Application.OTInstance.GetAppIDByFileExtension(Path.GetExtension(file.Name), Application.OTInstance.CurrentLibrary);
                    if (string.IsNullOrEmpty(AppType) && FileType == "IMG") // if noone else type for image file did not set - set the default image type
                    {
                        AppType = "DOCSIMAGE";
                    }

                    if (string.IsNullOrEmpty(AppType))
                    {
                        Logger.Write("ManFolder::AddFile() cannot detect AppType for file=" + useProfileDialog.ToString(), Severity.Information);
                        throw new FileNotCreatedException(string.Format(Properties.Resources.STR_CANNOT_ADD_NEW_FILE_WRONG_TYPE_ERROR_F, file.Name));
                    }
                    string FileName = Application.OTInstance.GetItemName(file.FriendlyName);
                    doc.Columns["TYPE_ID"].Value = FileType;
                    doc.Columns["DOCNAME"].Value = FileName;
                    doc.Columns["APP_ID"].Value = AppType;
                    doc.Columns["AUTHOR_ID"].Value = Application.OTInstance.CurrentUser;
                    doc.Columns["TYPIST_ID"].Value = Application.OTInstance.CurrentUser;
                    doc.Save(5);
                    if (doc.ErrCode != 0)
                    {
                        throw new FileNotCreatedException(string.Format(Properties.Resources.STR_CANNOT_ADD_NEW_FILE, FileName, doc.ErrText));
                    }

                    
                    if (doc.Versions != null && doc.Versions.Count > 0)
                    {
                        var version = doc.Versions[1];
                        Logger.Write("Trying to upload a file into DMS: " + version.FilePath, Severity.Information);
                        File.Copy(file.FilePath, version.FilePath, true);

                        var Results = version.UploadFile();
                        version.UnlockVersion((short)tagVersionStatus.VS_NORMAL);

                        Logger.Write("Trying to upload a file into DMS: Succeded " + version.FilePath, Severity.Information);
                    }

                    //doc.ReleaseDoc();
                    if (m_Folder != null)
                    {
                        m_Folder.AddDocument(doc);
                    }

                    var createdFile = new OTFile(doc, m_Folder);
                    added = true;
                    Logger.Write("ManFolder::AddFile() COMPLETE ", Severity.Information);
                    return createdFile;
                //}
            }
            catch (FileNotCreatedException)
            {
                Logger.Write("ManFolder::AddFile() File Not Created Exception", Severity.Information);
                throw;
            }
            catch (Exception ex)
            {
                Logger.Write("ManFolder::AddFile() Exception=" + ex.Message, Severity.Information);
                throw new FileNotCreatedException(ex.Message, ex);
            }
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, List<WorksharePlatform.Activity> activities, IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool update = true)
        {
            var a = true;

            return AddFile(file, out a, activities,versionIdsToSkip, useProfileDialog, SyncVerOption,StartVersion, update);
        }

        private bool DisplayImportDialog(WorksharePlatform.FileDetails file)
        {
            return false;
        }

        public void AddHistory(string eventName, string eventComment, Workshare.Integration.Operations operation)
        {
            m_document.AddDocumentActivity(eventComment);
            m_document.Save(0);
        }

        public void AddHistories(List<Activity> activities)
        {
            throw new NotImplementedException();
        }

        public void GetFileToCheckout()
        {
            Logger.Write("ManFile::OnBeforeSending() Try to check out file", Severity.Information);
            m_document.CurrentVersion.CheckOut(DateTime.Now.AddDays(INFINITY_DAYS), "Workshare automatic Check-out", Path.GetTempPath());
        }



        public void OnBeforeSync(OperationContext args)
        {
        }

        public void AddHistories(List<WorksharePlatform.Activity> activities, int vesrion)
        {
        }


        public void RelateDocument(IDMSFile file, string comments)
        {
            //TODO
        }


        public void GetFileToCheckoutLatest()
        {

        }


        public void UpdateSyncInfo2(WorksharePlatform.FileDetails fileDetailes, string lastActivity)
        {

        }


        public bool WasUpdatedAfterSend2(bool useForceRequest = true)
        {
            return false;
        }


        public int DMSId
        {
            get { return -1; }
        }

        public IDMSFolder RootFolder()
        {
            return null;
        }


        IDmsVersion AddVersion(string filePath, WorksharePlatform.FileDetails file, List<WorksharePlatform.Activity> activities, string versionFriendlyNmae=null )
        {
            throw new NotImplementedException();
        }

        public IEnumerable<IDmsVersion> GetVersions()
        {
            throw new NotImplementedException();
        }

        public void CanUpdateProfileOrThrow()
        {
            throw new NotImplementedException();
        }

        public bool IsFileLocked()
        {
            throw new NotImplementedException();
        }


        public bool IsLocalFileWasEdited()
        {
            throw new NotImplementedException();
        }

        public IDmsVersion CheckInFile(bool keepCheckOut)
        {
            throw new NotImplementedException();
        }


        public IDMSFile GetLatest()
        {
            throw new NotImplementedException();
        }


        public string DMSItemKey
        {
            get { return ""; }
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/FileComment.cs
﻿using System;

namespace WorksharePlatform
{
    public struct Positional
    {
        public int x;
        public int y;
        public int width;
        public int height;
    }

    public class FileComment
    {
        public int Id { get; set; }
        public DateTime CreatedAt { get; set; }
        public int FileId { get; set; }
        public int PageNumber { get; set; }
        public int FileVersion { get; set;}
        public string Body { get; set; }
        public int ReplyToId { get; set; }
        public string UserName { get; set; }
        public Positional Positional { get; set; }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/BaseDMSFile.cs
﻿namespace Workshare.Integration.Processor
{
    public abstract class BaseDMSFile : BaseDMSItem
    {
      //TODO remove
    }
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/CloudAuthenication.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using WorksharePlatform;
using System.Web;
using System.Net;

namespace WorkshareCloud.Common
{
    public static class CloudAuthenication
    {
        public static void CheckIfAuth(UserDetails user)
        {
            if (!(user != null && (!string.IsNullOrEmpty(user.AuthToken) || (user.SessionCookies != null && user.SessionCookies.Count > 1))))
            {
                throw new CloudUnAuthorized();
            }
        }

        static public void Login(UserDetails user)
        {
            PlatformService.Login(user);
            Update(user);
           // AuthCurrentUser(user);
        }

        //static void AuthCurrentUser(UserDetails userDetails)
        //{
        //    var responce = HttpContext.Current.Response;

        //    foreach (Cookie cookie in userDetails.SessionCookies.GetCookies(new Uri(userDetails.ServiceUrl)))
        //    {
        //        responce.Cookies.Add(new HttpCookie(cookie.Name, cookie.Value));
        //    }

        //    responce.Cookies.Add(new HttpCookie(cloudemail, userDetails.Email));
        //}

        //static void RemoveAuth()
        //{
        //    var responce = HttpContext.Current.Response;

        //    responce.Cookies.Add(new HttpCookie(cloudemail, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //    responce.Cookies.Add(new HttpCookie(user_credentials, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //    responce.Cookies.Add(new HttpCookie(_session_id, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //}

        //static void RemoveAuth()
        //{
        //    var responce = HttpContext.Current.Response;

        //    responce.Cookies.Add(new HttpCookie(CookieAwareClient.TMP_AUTH_TOKEN, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //    responce.Cookies.Add(new HttpCookie(cloudemail, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //    responce.Cookies.Add(new HttpCookie(user_credentials, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //    responce.Cookies.Add(new HttpCookie(_session_id, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
        //}

        //public static void SetAuth(string auth_token)
        //{
        //    var responce = HttpContext.Current.Response;

        //    responce.Cookies.Add(new HttpCookie(CookieAwareClient.TMP_AUTH_TOKEN, auth_token) { Expires = DateTime.Now.AddHours(1) });
        //}

       


        //public static UserDetails GetCurrentUser()
        //{

        //    var userCookies = HttpContext.Current.Request.Cookies;
        //    if (userCookies.AllKeys.Contains(user_credentials) && userCookies.AllKeys.Contains(_session_id))
        //    {
        //        var user = new UserDetails()
        //        {
        //            SessionCookies = new CookieContainer()
        //        };

        //        user.SessionCookies.Add(new Cookie(userCookies[user_credentials].Name, userCookies[user_credentials].Value, "/", user.Host));
        //        user.SessionCookies.Add(new Cookie(userCookies[_session_id].Name, userCookies[_session_id].Value, "/", user.Host));
        //        user.Email = userCookies[cloudemail].Value;
        //        return user;
        //    }
        //    else
        //    {
        //        return null;
        //    }

        //}


        /// <summary>
        /// get current user from cookies
        /// </summary>
        /// <returns></returns>
        public static UserDetails GetCurrentUser()
        {

            UserDetails user = new UserDetails();

            var userCookies = HttpContext.Current.Request.Cookies;
            if (userCookies.AllKeys.Contains(CookieAwareClient.TmpAuthToken) && !string.IsNullOrEmpty(userCookies[CookieAwareClient.TmpAuthToken].Value))
            {
                user = new UserDetails()
                {
                    AuthToken = userCookies[CookieAwareClient.TmpAuthToken].Value,
                    SessionCookies = new CookieContainer()
                };
            }
            if (userCookies.AllKeys.Contains(CookieAwareClient.user_credentials) && userCookies.AllKeys.Contains(CookieAwareClient._session_id))
            {
                user = new UserDetails()
                {
                    SessionCookies = new CookieContainer()
                };
                user.SessionCookies.Add(new Cookie(userCookies[CookieAwareClient.user_credentials].Name, userCookies[CookieAwareClient.user_credentials].Value, "/", user.Host));
                user.SessionCookies.Add(new Cookie(userCookies[CookieAwareClient._session_id].Name, userCookies[CookieAwareClient._session_id].Value, "/", user.Host));
            }
            return user;
        }

        public static void Logout()
        {
            //PlatformService.Logout();//TODO
          //  RemoveAuth();
            Update(null);
        }

        /// <summary>
        /// update cookies for current user
        /// </summary>
        /// <param name="user"></param>
        public static void Update(UserDetails user)
        {
            var responce = HttpContext.Current.Response;
            if (user == null || string.IsNullOrEmpty(user.AuthToken))
            {
                responce.Cookies.Add(new HttpCookie(CookieAwareClient.TmpAuthToken, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
            }
            else
            {
                if (responce.Cookies[CookieAwareClient.TmpAuthToken] == null || !string.Equals(responce.Cookies[CookieAwareClient.TmpAuthToken].Value, user.AuthToken))
                {
                    responce.Cookies.Add(new HttpCookie(CookieAwareClient.TmpAuthToken, user.AuthToken) { Expires = DateTime.Now.AddMinutes(55) });
                }
            }
            CookieCollection cookies= null;
            if (user != null &&user.SessionCookies!=null)
            {
                cookies=user.SessionCookies.GetCookies(PlatformService.HostWithSchema);
            }
            if (!HasCookie(cookies, CookieAwareClient.user_credentials) || !HasCookie(cookies, CookieAwareClient._session_id))
            {
                responce.Cookies.Add(new HttpCookie(CookieAwareClient.cloudemail, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
                responce.Cookies.Add(new HttpCookie(CookieAwareClient.user_credentials, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
                responce.Cookies.Add(new HttpCookie(CookieAwareClient._session_id, string.Empty) { Expires = DateTime.Now.AddDays(-10) });
            }
            else
            {
                responce.Cookies.Add(new HttpCookie(CookieAwareClient.cloudemail, user.Email));
                responce.Cookies.Add(new HttpCookie(CookieAwareClient.user_credentials, cookies[CookieAwareClient.user_credentials].Value));
                responce.Cookies.Add(new HttpCookie(CookieAwareClient._session_id, cookies[CookieAwareClient._session_id].Value));
            }
        }

        static bool HasCookie(CookieCollection col, string cookieName)
        {
            return col!=null&&col[cookieName] != null && !string.IsNullOrEmpty(col[cookieName].Value);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Progress/VMs/ProgressItemVm.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Text;
using Workshare.Components.Views.Common;

namespace Workshare.Components.Views.Progress.VMs
{
    public  class ProgressItemVm:BasePropertyChanged<ProgressItemVm>
    {
        public string Title { set; get; }
        public ObservableCollection<TargetItemVm> TargetItems { set; get; }
    

        public StateEnum State { set; get; }

        public ProgressItemVm()
        {
            TargetItems = new ObservableCollection<TargetItemVm>();        
        }

        public string Name { get; set; }

        public string TargetItemsToolTip
        {
            get
            {
                var itemsText = "Items:";
                foreach (var targetItemVm in TargetItems)
                {
                    itemsText += Environment.NewLine + targetItemVm.Name;
                }
                return itemsText;
            }
        }
    }

    public enum StateEnum
    {
        Loading,
        Success,
        Error
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/WorkshareIntegration.cs
﻿using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Linq;
using System.Net;
using Workshare.Integration;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;
using Workshare.Integration.Interfaces;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.OpenText.Integration
{
    public class WorkshareIntegration : WSIntegrationBase
    {

        public WorkshareIntegration(IAuthProvider authProvider)
            : base(authProvider,null)
        {
        }

        //protected override List<int> AddNewFileToFolder(IDMSFolder folder, UserDetails user, SyncOptions options, OperationContext context, ItemsErrorsCollection errorlist, List<FileDetails> filesOnCloud, List<int> localFiles)
        //{
        //    List<int> addedFiles = new List<int>();
        //    var processedFiles = folder.GetSendDataInfo();
        //    foreach (var fileID in filesOnCloud.Select(x => x.Id).Except(localFiles))
        //    {
        //        if (!processedFiles.Contains(fileID))
        //        {
        //            SafeFuncCall(errorlist, folder, new ExceptionListSignal() { IsAll = true, IsWeb = true, FileError = true }, Operations.Sync, () =>
        //            {
        //                FileDetails cloudFile = filesOnCloud.Where(x => x.Id == fileID).First();
        //                PlatformService.GetVersionDetails(user, cloudFile);
        //                cloudFile.Data = PlatformService.DownloadFile(user, fileID);
        //                IDMSFile newFile = folder.AddFile(cloudFile,null);
        //                if (newFile != null)
        //                {
        //                    newFile.Description = cloudFile.FriendlyName;
        //                    newFile.AddHistory("",RES.STR_HISTORY_ADDFILETOFOLDER, Operations.Sync);
        //                }
        //                addedFiles.Add(cloudFile.Id);
        //            });
        //        }
        //    }
        //    return addedFiles;
        //}

        //protected override void UpdateLocalFileName(IDMSFile localFile, FileDetails wsFile)
        //{
        //    localFile.UpdateDisplayName(wsFile.FriendlyName);
        //}

        //protected override void LocalFileNoMatter_wsFileWasChanged_KeepBothFiles(UserDetails user, IDMSFile localFile, FileDetails wsFile, OperationContext context, ISyncInfo syncInfo, ConflictVersionOptions SyncVerOption)
        //{
        //    if (localFile.ParentFolder != null)
        //    {
        //        // add new copy of the file to OpenText
        //        wsFile.Data = PlatformService.DownloadFile(user, wsFile.Id);
        //        bool newFileIsAdded = false;
        //        IDMSFile newFile = ((IDMSFolder)localFile.ParentFolder).AddFile(wsFile,out newFileIsAdded,null/*, true*/);// NOTE: display Profile dialog hire.. 
        //        if (newFileIsAdded)
        //        {
        //            if (newFile != null)
        //            {
        //                newFile.AddHistory("", string.Format(RES.STR_HISTORY_SAVEDFROM, localFile.Name), Operations.Sync);
        //            }

        //            UpdateLocalFileName(localFile, wsFile);
        //            localFile.AddHistory("", string.Format(RES.STR_HISTORY_SAVEDNEW, newFile.Name), Operations.Sync);

        //            // if local file was changed then we check in changes, otherwise we discard check out for file
        //            if (localFile.WasUpdatedAfterSend(syncInfo))
        //            {
        //                localFile.OnAfterSync(context);
        //            }
        //            else
        //            {
        //                localFile.UpdateSyncInfo(null, true, null,null);
        //            }

        //        }
        //    }
        //}

    }

}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/ActionStrategy/CeaseCollaborationStrategy.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Properties;
using Workshare.Integration.WsProxies;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Integration.Processor.Strategies.ActionStrategy
{
    public class CeaseCollaborationStrategy : ActionStrategy
    {
        readonly WsProxy _wsProxy;
        readonly IAuthProvider _auth;
        readonly DmsWorkerBase _dmsWorker;
        readonly SyncInfoService _syncInfoService;

        public CeaseCollaborationStrategy(WsProxy wsProxy, IAuthProvider auth, DmsWorkerBase dmsWorker, SyncInfoService syncInfoService)
            : base(syncInfoService)
        {
            this._wsProxy = wsProxy;
            this._auth = auth;
            this._dmsWorker = dmsWorker;
            this._syncInfoService = syncInfoService;
        }

        public override ProcessResult Process(Maps.FileMap fileMap, ItemMapActivityAction action)
        {
            try
            {
                CeaseCollaborationAction _action = action as CeaseCollaborationAction;

                if (fileMap.HasRemote())
                {
                    _syncInfoService.GetSyncInfo(fileMap);
                    if (_action.ImportAction == CeaseCollaborationImportType.WithComments)
                    {
                        ImportAsNewFile(fileMap.WsFile, fileMap.LocalFile.ParentFolder, fileMap.LocalFile, true);
                    }
                    else if (_action.ImportAction == CeaseCollaborationImportType.WithoutComments)
                    {
                        ImportAsNewFile(fileMap.WsFile, fileMap.LocalFile.ParentFolder, fileMap.LocalFile, false);
                    }

                    if (_action.FileAction == CeaseCollaborationType.Delete)
                    {
                        WsUser wsUser = _auth.GetCurrentWSUser2();
                        _wsProxy.DeleteFile(wsUser, fileMap.WsFile.Id);
                        fileMap.LocalFile.AddHistory(string.Empty, string.Format(RES.STR_HISTORY_ITEMDELETED, wsUser.UserName), Operations.Deleted);
                    }
                }

                _dmsWorker.UnlockIfNotEdited(fileMap.LocalFile);
                _syncInfoService.BreakLink(fileMap.LocalFile);

                return ProcessResult.Processed;
            }
            catch (WebException ex)
            {
                if (ex.IsCloudFolderAccessDenied())
                {
                    throw new CloudFolderAccessDenied(Resources.STR_UNABLE_SYNC, Resources.STR_UNABLESYNCFILE_TEXT, ex);
                }
                throw;
            }
        }

        public override ProcessResult Process(Maps.FolderMap folderMap, ItemMapActivityAction action)
        {
            try
            {
                CeaseCollaborationAction _action = action as CeaseCollaborationAction;

                if (folderMap.HasRemote())
                {
                    if (_action.FileAction == CeaseCollaborationType.Delete)
                    {
                        _wsProxy.DeleteFolder(_auth.GetCurrentWSUser2(), folderMap.WsFolder.Id);
                    }
                }

                _syncInfoService.BreakLink(folderMap.LocalFolder);
                return ProcessResult.Processed;
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode(HttpStatusCode.Forbidden))
                {
                    throw new CloudFolderAccessDenied(Resources.STR_UNABLE_SYNC, Resources.STR_UNABLESYNCFILE_TEXT, ex);
                }
                throw;
            }
        }

        private IDMSFile ImportAsNewFile(WsFile wsFile, IDMSFolder dmsFolder, IDMSFile basedOnFile, bool withComments)
        {
            var versionsToCreate = new List<CreateversionInfo>();

            foreach (var ver in wsFile.Versions.OrderBy(x => x.Version).ToArray())
            {
                var activitiesForCurrentVersion = new List<Activity>();

                versionsToCreate.Add(new CreateversionInfo
                {
                    Activities = activitiesForCurrentVersion,
                    file = wsFile,
                    version = ver,
                    FriendlyName = wsFile.FriendlyName,
                    FilePath = withComments ? ver.DownloadFileVersionInPdfWithComment((string)wsFile.DownloadPassword) : ver.DownloadFileVersionInPdf()
                });
            }

            var options = new NewFileOptions()
            {
                WsFile = wsFile,
                ParentFolder = dmsFolder,
                BasedOnFile = basedOnFile,
                VersionList = versionsToCreate
            };

            _dmsWorker.CanImportNewFileOrThrow(options);

            _dmsWorker.ImportNewFile(options);

            return options.CreatedFile;
        }


    }
}
<file_sep>/OpenText/src/Workshare.OpenText.Setup.CustomAction/CustomActions.cs
﻿using Microsoft.Deployment.WindowsInstaller;
using System;
using System.Reflection;

namespace Workshare.OpenText
{
    public class CustomActions
    {
         private static ActionResult ExecuteAction(Func<ActionResult> action, string methodName, Session session)
        {
#if MESSAGES
            MessageBox.Show(string.Format("Method {0} STARTED", methodName));
#endif
            session.Log(string.Format("Method {0} STARTED", methodName));
            try
            {

                
                return action();
            }
            catch (Exception ex)
            {
#if MESSAGES
                MessageBox.Show(ex.ToString(), string.Format("{0} : {1}", methodName, ex.Message));
#endif
                session.Log(string.Format("Method {0} caused Exception\n{1}\n{2}", methodName, ex.Message, ex.ToString()));
            }
            finally
            {
                session.Log(string.Format("Method {0} FINISHED", methodName));
            }
            return ActionResult.Failure;
        }


        [CustomAction]
        public static ActionResult RegisterMenusAction(Session session)
        {
            return ExecuteAction(() =>
                 {
                     Registering.RegisterMenus();
                     return ActionResult.Success;
                 }, MethodBase.GetCurrentMethod().Name, session);
        }

        [CustomAction]
        public static ActionResult UnRegisterMenusAction(Session session)
        {
            return ExecuteAction(() =>
            {
                //Registering.UnRegisterMenus();
                return ActionResult.Success;
            }, MethodBase.GetCurrentMethod().Name, session);
        }

    }

}
<file_sep>/WSComponents/src/WSIntegration/WsProxies/WsFile.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using WorksharePlatform;

namespace Workshare.Integration.WsProxies
{

    /// <summary>
    /// Should load data on demand from server 
    /// </summary>
    public class WsFile
    {
        public FileDetails file;
        UserDetails user;

        public WsFile(FileDetails file, UserDetails user)
        {
            if (file == null) throw new ArgumentNullException("file");
            if (user == null) throw new ArgumentNullException("user");
            this.file = file;
            this.user=user;
        }

        public int FolderId { get { return file.FolderId; } }
        public int Id { get { return file.Id; } }

        public string RemoteUrl { get { return file.RemoteUrl; } }

        public object DownloadPassword { get { return file.DownloadPassword; } }

        public string FriendlyName { get { return file.FriendlyName; } }

        public string Name { get { return file.Name; } }

        public WsUser Creator { get { return new WsUser(file.Creator); } }
        public DateTime CreatedAt { get { return file.CreatedAt; } }

        public DateTime UpdateDate { get { return file.UpdateDate; } }

        IEnumerable<WsVersion> _Versions;
        public IEnumerable<WsVersion> Versions
        {
            get
            {
                if(_Versions==null)
                {
                    _Versions=PlatformService.GetVersionDetails(user,file).Select(a=>new WsVersion(a,user));
                }
                return _Versions;
            }

            internal set
            {
                _Versions = value;
            }
        }

        public WsVersion CurrentVersion
        {
            get
            {
                var versions = Versions;
                var maxVersionId = versions.Max(p => p.Version);
                var res= versions.First(p => p.Version == maxVersionId);
                file.CurrentVersion = res.version;
                return res;
            }
        }

        public bool IsDeleted {
            get { return file.IsDeleted; }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/SettingsStorage/SettingsStorage.cs
﻿using Microsoft.Win32;
using Workshare.Components.WSLogger;

namespace Workshare.Integration.SettingsStorage
{
    public class SettingsStorage
    {
        private const string RegKey = @"Software\Workshare\IManage\Settings";

        public void SaveOption(string name, string value)
        {
            Logger.WriteTrace(string.Format("Saving {0}={1}", name, value));
            using (var reg=Registry.CurrentUser.CreateSubKey(RegKey))
            {
                if (reg != null) reg.SetValue(name,value);
            }    
        }

        public string GetString(string name, string defaultvalue=null)
        {
            using (var reg = Registry.CurrentUser.OpenSubKey(RegKey))
            {
                if (reg != null)
                {
                    return reg.GetValue(name) as string;
                }
            }
            return defaultvalue;
        }

        public void SaveOption(string name, int value)
        {
            Logger.WriteTrace(string.Format("Saving {0}={1}", name, value));
            using (var reg = Registry.CurrentUser.CreateSubKey(RegKey))
            {
                if (reg != null) reg.SetValue(name, value,RegistryValueKind.DWord);
            }    
        }

        public int GetInt(string name, int defaultvalue = 0)
        {
            using (var reg = Registry.CurrentUser.OpenSubKey(RegKey))
            {
                if (reg != null)
                {
                    return (int) reg.GetValue(name, defaultvalue);
                }
            }
            return defaultvalue;
        }
    }
}
<file_sep>/OpenText/src/Workshare.OpenText/Presenter/ModulePresenter.cs
﻿using Workshare.Components;
using Workshare.Components.Interfaces;
using Workshare.Components.Presenter;

namespace Workshare.OpenText.Presenter
{
    public class ModulePresenter :ModulePresenterBase
    {
        public ModulePresenter(IModuleView view) : base(view)
        {
        }

        public override void OnSyncItemsClicked(SyncItemsClickedArgs args)
        {
            throw new System.NotImplementedException();
        }
    }

}
<file_sep>/WSComponents/src/WSComponents/Common/CheckInDialogResult.cs
﻿using Workshare.Integration.Enums;

namespace Workshare.Components.Concrete
{
    public class CheckinDlgResult
    {
        public bool ApplyToAll { set; get; }
        public ConflictOptions option { set; get; }
        public ConflictVersionOptions versions { get; set; }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/FileMap.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Maps
{
    public class FileMap : ItemMap
    {
        public IDMSFile LocalFile { set; get; }

        public WsFile WsFile { set; get; }

        /// <summary>
        /// If files was send by itself to other folder then its parent then it will have this property set to actually container of it.
        /// </summary>
        public FolderMap IndirectParent { set; get; }


        public override void Apply(ItemMapVisitor visitor)
        {
            if (visitor.VisitEnter(this))
            {
                foreach (var item in this.Maps)
                {
                    item.Apply(visitor);
                }
                visitor.Visit(this);
            }
            visitor.VisitLeave(this);
        }

        public static string GetMapId(FileMap map)
        {
            if (map.LocalFile == null)
            {
                return map.WsFile == null ? string.Format("localfile:{0};wsfile:{1}", -1, -1) : string.Format("localfile:{0};wsfile:{1}", -1, map.WsFile.Id);
            }
            if (map.WsFile == null)
            {
                return string.Format("localfile:{0};wsfile:{1}", map.LocalFile.ID, -1);
            }
            return string.Format("localfile:{0};wsfile:{1}", map.LocalFile.ID, map.WsFile.Id);
        }

        public override string GetId()
        {
            return  GetMapId(this);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/ConflictResolver/ConflictResolverViewModel.cs
﻿using System;
using System.Windows.Input;
using System.Windows.Media;
using Workshare.Components.Concrete;
using Workshare.Components.Views.Common;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using RES = Workshare.Components.Properties.Resources;
using RES_INT = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Views.ConflictResolver
{
    class ConflictResolverViewModel : OwnViewModel
    {

        public ICommand ReplaceCommand { set; get; }
        public ICommand KeepBothCommand { set; get; }
        public ICommand CancelCommand { set; get; }

        public ConflictResolverViewModel()
        {
            WsData = new ConflictItemDataViewModel(RES_INT.STR_CONFLICT_DLG_WORKSHAREFILE_TITLE,new ConflictItemData()
                {
                    Date=DateTime.Now,
                    Modifier="ModifierValue",
                    Name="testDoc.docx"
                });
            ManData = new ConflictItemDataViewModel("Custom DMS",new ConflictItemData()
            {
                Date = DateTime.Now,
                Modifier = "Man ModifierValue",
                Name = "Man testDoc.docx"
            });
        }



        public ConflictResolverViewModel(ConflictItemData wsFile, ConflictItemData localFile, string DMSTitle)
        {
            WsData = new ConflictItemDataViewModel(RES_INT.STR_CONFLICT_DLG_WORKSHAREFILE_TITLE, wsFile);
            ManData = new ConflictItemDataViewModel(DMSTitle, localFile);

            CancelCommand = new RelayCommand((p) =>
            {
                Close(ConflictOptions.None, false);
            });

            ReplaceCommand = new RelayCommand((p) =>
            {
                Close(ConflictOptions.Replace, true);
            });

            KeepBothCommand = new RelayCommand((p) =>
            {
                Close(ConflictOptions.KeepBoth, true);
            });
        }

        void Close(ConflictOptions result, bool? dialogResult)
        {
            Result = result;
            RaiseClose(dialogResult);
        }

        public ConflictOptions Result { set; get; }

        public ConflictItemDataViewModel WsData { set; get; }
        public ConflictItemDataViewModel ManData { set; get; }

        ImageSource m_ArrowImage = null;
        public ImageSource ArrowImage
        {
            get
            {
                if (m_ArrowImage == null)
                {
                    m_ArrowImage = Utils.Convert(RES.conflict_arrow, System.Drawing.Imaging.ImageFormat.Png);
                }
                return m_ArrowImage;
            }
        }
    }

    class ConflictItemDataViewModel
    {
        ConflictItemData m_Data;

        public ConflictItemDataViewModel(string title, ConflictItemData data)
        {
            m_Data = data;
            this.Title = title;
        }

        public string Title { get; private set; }
        public string Name { get { return m_Data.Name; } }
        public string Modifier { get { return m_Data.Modifier; } }
        public string Date { get { return m_Data.Date.ToString(); } }
    }

}
<file_sep>/SharePoint/src/WorksharePointCloud/Features/WorkshareCloudIntegration/WorkshareCloudIntegration.EventReceiver.cs
using System;
using System.Runtime.InteropServices;
using System.Security.Permissions;
using Microsoft.SharePoint;
using Microsoft.SharePoint.Security;
using WorkshareCloud.Common;
using System.Linq;
using WorkshareCloud.Common.Receivers;
namespace WorkshareCloud.Features.WorkshareCloudIntegration
{
    /// <summary>
    /// This class handles events raised during feature activation, deactivation, installation, uninstallation, and upgrade.
    /// </summary>
    /// <remarks>
    /// The GUID attached to this class may be used during packaging and should not be modified.
    /// </remarks>

    [Guid("ebd7b255-328c-4217-8495-f37b42ef6d4c")]
    public class WorkshareCloudIntegrationEventReceiver : SPFeatureReceiver
    {
        // Uncomment the method below to handle the event raised after a feature has been activated.

        public override void FeatureActivated(SPFeatureReceiverProperties properties)
        {
            WorkshareCloud.Common.Logging.Logger.WriteTrace("Feature Activated", Microsoft.SharePoint.Administration.TraceSeverity.Verbose, Common.Logging.Category.CloudService);
        }




        public override void FeatureDeactivating(SPFeatureReceiverProperties properties)
        {
            var FieldName = CloudPathFieldValue.CloudField;
            using (SPWeb v = (SPWeb)properties.Feature.Parent)
            {
                SPList l;

                for (int i = 0; i < v.Lists.Count; i++)
                {
                    try
                    {
                        l = v.Lists[i];
                        if (l is SPDocumentLibrary && l.Hidden == false)
                        {

                            if (l.Fields.ContainsField(FieldName))
                            {

                                l.Fields.Delete(FieldName);
                                l.Update();

                            }

                            for (int j = 0; j < l.Views.Count; j++)
                            {

                                try
                                {
                                    var view = l.Views[j];
                                    if (view.ViewFields.Exists(FieldName))
                                    {
                                        view.ViewFields.Delete(FieldName);
                                        // view.XslLink = "";
                                        view.Update();

                                    }
                                }
                                catch { }
                            }

                            l.EventReceivers.OfType<SPEventReceiverDefinition>().Where(p => string.Equals(p.Class, typeof(WorkshareReceiver).FullName)).ToList().ForEach(receiver => receiver.Delete());

                        }
                    }

                    catch { }

                }
            };
        }


        // Uncomment the method below to handle the event raised after a feature has been installed.

        //public override void FeatureInstalled(SPFeatureReceiverProperties properties)
        //{
        //}


        // Uncomment the method below to handle the event raised before a feature is uninstalled.

        //public override void FeatureUninstalling(SPFeatureReceiverProperties properties)
        //{
        //}

        // Uncomment the method below to handle the event raised when a feature is upgrading.

        //public override void FeatureUpgrading(SPFeatureReceiverProperties properties, string upgradeActionName, System.Collections.Generic.IDictionary<string, string> parameters)
        //{
        //}
    }
}
<file_sep>/WSComponents/src/WSComponents/Exceptions/FileNotUpdatedException.cs
﻿using System;
using Workshare.Integration.Exceptions;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Exceptions
{
    public class FileNotUpdatedException : BaseException
    {
        public FileNotUpdatedException(string reasonMessage)
            : base(RES.STR_UNABLE_SYNC, reasonMessage)
        {
        }

        public FileNotUpdatedException(string reasonMessage, Exception inner)
            : base(RES.STR_UNABLE_SYNC, string.Format(RES.STR_FILE_CANNOT_BE_UPDATED, reasonMessage), inner)
        {
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Contrete/ManFile.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Runtime.InteropServices;
using System.Text;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components.Exceptions;
using Workshare.Components.Helpers;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.WsProxies;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.IManage.Contrete
{
    class ManFile : BaseDMSFile, IDMSFile
    {
        internal IManDocument m_document = null;
        IManFolder m_Folder = null;
        IManDocumentType newdoctype = null;
        bool wasAlreadyCheckedOut = false;
        bool m_bNeedToCleanTemp = false;
        string m_sTempCheckOutPath = "";

        public IDMSFile GetLatest()
        {
            try
            {
                m_document.Refresh();
            }
            catch(Exception ex)
            {
                Logger.Write(ex, Severity.Verbose);
                throw new OfflineException();
            }

            var l = m_document.LatestVersion;
            return new ManFile(l, m_Folder);
        }

        public ManFile(IManDocument doc)
        {
            m_document = doc;
        }

        public ManFile(IManDocument doc, IManFolder folder)
            : this(doc)
        {
            m_Folder = folder;
        }

        public void RelateDocument(IDMSFile file, string comments)
        {
            var manFile = (ManFile)file;
            m_document.RelatedDocuments.AddRelation(manFile.m_document.Number, comments);
        }

        public IDMSItemID ID
        {
            get { return new ManItemID(m_document); }
        }

        public void RemoveTempFileIfNeed()
        {
            if (m_bNeedToCleanTemp && !string.IsNullOrEmpty(m_sTempCheckOutPath))
            {
                if (File.Exists(m_sTempCheckOutPath))
                    File.Delete(m_sTempCheckOutPath);

                m_bNeedToCleanTemp = false;
                m_sTempCheckOutPath = string.Empty;
            }
        }

        public DateTime? CheckoutTime
        {
            get
            {
                try
                {
                    if (m_document.CheckedOut)
                    {
                        return m_document.CheckoutTime;
                    }
                    else
                    {
                        return null;
                    }
                }
                catch (Exception ex)
                {
                    Logger.Write(ex, Severity.Verbose);
                    return null;
                }
            }
            set{}
        }

        string _name = null;
        public string Name
        {
            get
            {
                if (_name == null)
                {
                    _name = (string.IsNullOrEmpty(m_document.LatestVersion.Name)) ? m_document.LatestVersion.Description : m_document.LatestVersion.Name;
                    string ext = FileUtils.GetExtension(_name);
                    string iManExt = "."+m_document.LatestVersion.Extension.ToLower();
                    if (string.IsNullOrEmpty(ext) || string.Compare(ext.ToLower(), iManExt.ToLower(), StringComparison.InvariantCultureIgnoreCase) != 0)
                    {
                        _name = _name + iManExt;
                    }

                }
                return _name;
            }
            set
            {
            }
        }

        public bool DoesUserHavePermissions(imAccessRight permissions)
        {
            return (m_document.EffectiveAccess & permissions) == permissions;
        }

        public bool DoesUserHavePermissions(Workshare.Integration.Enums.Permissions permissions)
        {
            switch (permissions)
            {
                case Workshare.Integration.Enums.Permissions.EditItem: return (m_document.EffectiveAccess & imAccessRight.imRightReadWrite) == imAccessRight.imRightReadWrite;
            }
            return true;
        }

        public bool CheckedOutToUser
        {
            get
            {
                var user = m_document.InUseBy;
                if (user != null)
                {
                    return user.Name == m_document.Database.Session.UserID;
                }
                return false;
            }
        }

        public string CheckoutPath { get { return m_document.CheckoutPath; } }

        public bool CheckedOut
        {
            get { return m_document.CheckedOut; }
        }

        public IDmsVersion AddVersion(string filePath, FileDetails file, List<Activity> activities, string versionFriendlyName = null, bool checkInVersion = false, bool keepLocalState = false)
        {
            Logger.Write("ADD VERSION: Start Add version", Severity.Information);
            string tmp_filename = (file.CurrentVersion.Name.Length < 15) ? file.CurrentVersion.Name : FileUtils.GetFileNameWithoutExtension(file.CurrentVersion.Name).Substring(0, 8) + "." + FileUtils.GetExtension(file.CurrentVersion.Name);
            bool wasCheckedOut = true;
            if (!m_document.CheckedOut)
            {
                m_document.CheckOut(Path.GetTempFileName(), imCheckOutOptions.imReplaceExistingFile, DateTime.Now.AddDays(INFINITY_DAYS), "Workshare adding new versions");
                wasCheckedOut = false;
            }
            var oldCheckOutPath = m_document.CheckoutPath;
            var oldCheckOutComment = m_document.CheckoutComment;

            if ((newdoctype = m_document.Database.GetDocumentTypeFromPath(filePath)) == null)
            {
                if (m_document.Type != null)
                {
                    newdoctype = m_document.Type;
                }
                else
                {
                    Logger.Write("ADD VERSION: Cannot get new doc type", Severity.Error);
                    throw new FileNotUpdatedException(string.Format(Properties.Resources.STR_CANNOT_ADD_NEW_FILE_WRONG_TYPE_ERROR_F, file.Name));
                }
            }

            UpdateDocTypeIfNeed();

            Logger.Write("ADD VERSION: Try check in with result", Severity.Information);

            file.FilePath = Path.GetTempPath() + tmp_filename;
            File.Copy(filePath, file.FilePath, true);
            FileUtils.SafeDelete(filePath);

            IManCheckinResult res = m_document.CheckInWithResults(file.FilePath, imCheckinDisposition.imCheckinNewVersion, imCheckinOptions.imDontKeepCheckedOut);

            if (!res.Succeeded)
            {
                var resErr = new StringBuilder();
                resErr.AppendFormat("ErrorCode : {0}. ErrorMessage: {1}", res.ErrorCode, res.ErrorMessage);
 
                foreach (IManProfileError manProfileError in res.ErrorList)
                {
                    resErr.Append(Environment.NewLine);
                    resErr.AppendFormat("{0} : {1}", manProfileError.AttribID,  manProfileError.Description);
                }
                Logger.Write("ManFile::AddVersion(): CheckInWithResults return error: " + resErr, Severity.Information);

                throw new FileCannotBeCheckedInException(res.ErrorMessage);
            }

            var checkedInVersion = res.Result;

            //add history to current version
            if (activities != null)
            {
                var last = activities.LastOrDefault(p => p.Noun == "Comment");

                foreach (var activity in activities)
                {
                    if (activity.Noun == "Comment" && activity != last)
                        continue;

                    var comment = activity.GetComment();

                    if (!string.IsNullOrEmpty(comment))
                        res.Result.HistoryList.Add(activity.HistoryModify ? imHistEvent.imHistoryModify : imHistEvent.imHistoryView, 0, 0, RES.STR_WORKSHARE_TITLE, comment, activity.FolderName, string.Empty, string.Empty);
                }
            }

            res.Result.HistoryList.Add(imHistEvent.imHistoryEchoSync, 0, 0, RES.STR_WORKSHARE_TITLE, string.Format(RES.STR_HISTORY_ITEMSYNC, DateTime.Now.ToString(Activity.TimeFormat)), Environment.MachineName, string.Empty, string.Empty);
            if (versionFriendlyName != null)
            {
                res.Result.Description = versionFriendlyName;
            }
            res.Result.Update();

            var addedver = new ManVersion(new ManFile(res.Result, m_Folder));

            if (!checkedInVersion.CheckedOut && wasCheckedOut)
            {
                var tmp = Path.GetTempFileName();//Path.GetTempPath() + tmp_filename;
                checkedInVersion.CheckOut(tmp, imCheckOutOptions.imReplaceExistingFile, DateTime.Now.AddDays(INFINITY_DAYS), oldCheckOutComment);
                var fi = new FileInfo(tmp);
                // somehow that's date set incorect by imanage, but we need that to further use
                fi.LastWriteTime = addedver.EditTime;
                fi.LastAccessTime = addedver.EditTime;

                if (keepLocalState)
                {
                    checkedInVersion.CheckoutPath = oldCheckOutPath;
                    checkedInVersion.Update();
                    FileUtils.SafeDelete(tmp);
                }
            }

            FileUtils.SafeDelete(oldCheckOutPath);

            return addedver;
        }

        public bool WasUpdatedAfterSend2(bool useForceRequest = true)
        {
            this.m_document.Refresh();
            var syncInfo = Application.iManInstance.Module.Resolve<SyncInfoService>().GetSyncInfo(this, useForceRequest);
            if (syncInfo == null) return false;
            long oldModified;
            if (long.TryParse(syncInfo.Modified, out oldModified))
            {
                return (EditDate.Ticks > long.Parse((syncInfo).Modified));    
            }
            return false;
        }

        public bool IsLocalFileWasEdited()
        {
            try
            {
                if (CheckedOut)
                {
                    if (!string.IsNullOrEmpty(CheckoutPath) && File.Exists(CheckoutPath))
                    {
                        var fi = new FileInfo(CheckoutPath);
                        return fi.LastWriteTime != Modified;
                    }
                }
                return false;
            }
            catch
            {
                return false;
            }
        }

        public IDmsVersion CheckInFileEx(bool keepCheckOut, imCheckinDisposition checkinDisposition)
        {
            if (CheckedOut)
            {
                string checkoutpath = CheckoutPath;
                var oldCheckOutComment = m_document.CheckoutComment;
                IManCheckinResult res = m_document.CheckInWithResults(checkoutpath, checkinDisposition, imCheckinOptions.imDontKeepCheckedOut);

                if (!res.Succeeded)
                {
                    var resErr = new StringBuilder();
                    resErr.AppendFormat("ErrorCode : {0}. ErrorMessage: {1}", res.ErrorCode, res.ErrorMessage);

                    foreach (IManProfileError manProfileError in res.ErrorList)
                    {
                        resErr.Append(Environment.NewLine);
                        resErr.AppendFormat("{0} : {1}", manProfileError.AttribID, manProfileError.Description);
                    }
                    Logger.Write("ManFile::AddVersion(): CheckInWithResults return error: " + resErr, Severity.Information);

                    throw new FileCannotBeCheckedInException(res.ErrorMessage);
                }

                var checkedInVersion = res.Result;

                var addedver = new ManVersion(new ManFile(res.Result, m_Folder));

                if (keepCheckOut)
                {
                    var tmp = Path.GetTempFileName();
                    checkedInVersion.CheckOut(tmp, imCheckOutOptions.imReplaceExistingFile, DateTime.Now.AddDays(INFINITY_DAYS), oldCheckOutComment);
                    var fi = new FileInfo(tmp);
                    // somehow that's date set incorect by imanage, but we need that to further use
                    fi.LastWriteTime = addedver.EditTime;
                    fi.LastAccessTime = addedver.EditTime;
                    //checkedInVersion.Update();
                }
                return addedver;
            }
            else
            {
                return null;
            }
        }

        public IDmsVersion CheckInFile(bool keepCheckOut)
        {
            return CheckInFileEx(keepCheckOut, imCheckinDisposition.imCheckinNewVersion);
        }

        public bool IsCheckedOutFileExists()
        {
            if (m_document.CheckedOut && !string.IsNullOrEmpty(m_document.CheckoutPath))
            {
                return File.Exists(m_document.CheckoutPath);
            }
            else
            {
                return true;
            }
        }

        public DateTime EditDate
        { 
            get 
            {
                if (CheckedOut)
                {
                    string localfilepath = string.Empty;
                    try
                    {
                        localfilepath = m_document.CheckoutPath;
                        var localfile = new FileInfo(localfilepath);
                        return localfile.LastWriteTime;
                    }
                    catch (IOException ex)
                    {
                        Logger.Write("Failded to access to checkouted file: " + localfilepath, Severity.Error);
                        throw new FileNotFoundException(ex.Message, ex);
                    }
                }
                else
                {
                    return Modified;
                }
            }
        }

        public string GetFilePath()
        {
            string localCopy = string.Empty;
            try
            {
                if (CheckedOut)
                {
                   localCopy = m_document.CheckoutPath;
                }
                else
                {
                    localCopy = Path.GetTempFileName();
                    Logger.Write("Trying to get copy of a file: " + localCopy, Severity.Information);
                    m_document.GetCopy(localCopy, imGetCopyOptions.imNativeFormat);
                    Logger.Write("Succeded: " + localCopy, Severity.Information);
                }
                return localCopy;
            }
            catch (IOException ex)
            {
                Logger.Write("Failded to access to checkouted file: " + localCopy, Severity.Error);
                throw new LocalFileNotFound();
            }
            catch (Exception ex)
            { 
                Logger.Write("Error due getting of copy: " + localCopy, Severity.CriticalError);
                throw;
            }
        }

        public string DisplayName
        {
            get
            {
                return FileUtils.GetFileNameWithoutExtension(Name);
            }
            set
            {
            }
        }

        public IDMSFolder ParentFolder
        {
            get
            {
                if (m_Folder == null && ParentFolders.Count == 1)
                {
                   return ParentFolders[0];
                }

                if (m_Folder != null)
                {
                    return new ManFolder(m_Folder);
                }
                return null;
            }
        }

        public string Modifier
        {
            get
            {
                if (m_document.Author != null)
                {
                    return m_document.Author.Name;
                }
                return string.Empty;
            }
        }

        public DateTime Modified
        {
            get 
            {
                try
                {
                    var dateedit = (DateTime)m_document.GetAttributeValueByID(imProfileAttributeID.imProfileEditDate);
                    var timeedit = (DateTime)m_document.GetAttributeValueByID(imProfileAttributeID.imProfileEditTime);
                    var Edit = new DateTime(dateedit.Year, dateedit.Month, dateedit.Day, timeedit.Hour, timeedit.Minute, timeedit.Second, timeedit.Millisecond);
                    return Edit;
                }
                catch (Exception ex)
                {
                    return m_document.LatestVersion.AccessTime;
                }
            }
        }

        const int INFINITY_DAYS = 10000;

        public void OnBeforeSending(OperationContext context)
        {
            if (!CheckedOut)
            {
                GetFileToCheckout();
                if (context.CheckOutOption != Workshare.Integration.Enums.CheckOutOptions.CheckOut)
                {
                    m_bNeedToCleanTemp = true;
                    m_sTempCheckOutPath = CheckoutPath;
                }
            }
            else if (!CheckedOutToUser)
            {
                throw new FileCheckoutedToAnotherUser(Workshare.Integration.Operations.Send);
            }
            else
            {
                wasAlreadyCheckedOut = true;
            }
        }

        public void OnAfterSending(OperationContext context)
        {
            if (context.CheckOutOption == Workshare.Integration.Enums.CheckOutOptions.DontCheckOut && !wasAlreadyCheckedOut)
            {
                DiscardCheckout();
            }
            RemoveTempFileIfNeed();
        }
        
        public void OnSendError(object args, Exception ex)
        {
            Logger.Write(ex, Severity.Error);
            if (!wasAlreadyCheckedOut)
            {
                m_document.UnlockContent();
            }
        }

        private void UpdateDocTypeIfNeed()
        {
            if (newdoctype!=null && newdoctype.Name != m_document.Type.Name)
            {
                Logger.Write("Update doc type", Severity.Information);
                m_document.SetAttributeByID(imProfileAttributeID.imProfileType, newdoctype);
            }
        }

        public void DiscardCheckout(bool deleteCheckOutFile = false)
        {
            if (!this.IsCheckedOutToOtherUser())
            {
                if (m_document.CheckedOut)
                {
                    bool res;
                    if (m_document.LatestVersion.CheckedOut)
                    {
                        res = m_document.LatestVersion.UnlockContent();
                        if (!res)
                        {
                            throw new FileUnlockFailedException();
                        }
                        m_document.LatestVersion.Update();
                    }

                    m_document.Refresh();
                    if (m_document.CheckedOut)
                    {
                        res = m_document.UnlockContent();
                        if (!res)
                        {
                            throw new FileUnlockFailedException();
                        }
                        m_document.Update();
                    }

                    if (deleteCheckOutFile)
                        FileUtils.SafeDelete(m_document.CheckoutPath);

                }
            }
        }

        public List<IDMSFolder> ParentFolders
        {
            get
            {
                var res = new List<IDMSFolder>();
                foreach (IManFolder folder in m_document.Folders)
                {
                    res.Add(new ManFolder(folder));
                }
                return res;
            }
        }

        private ManFile DisplayImportDialog(WorksharePlatform.FileDetails file)
        {
            var dlg = Application.Instance.Module.Resolve<ImportDialog>();
            dlg.Initialize(null, file.FilePath, file.FriendlyName ?? file.Name, m_document.Database);
            dlg.ShowDialog();
            return dlg.AddedFile;
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, List<Activity> actnivities, IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool updateSyncInfoForVersion = true)
        {
            var a = true;

            return AddFile(file, out a, actnivities,versionIdsToSkip, useProfileDialog, SyncVerOption, StartVersion,updateSyncInfoForVersion);
        }

        SyncInfoService GetService()
        {
            return Application.Instance.Module.Resolve<SyncInfoService>();
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, out bool added, List<Activity> actnivities,IEnumerable<string> versionIdsToSkip , bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool updateSyncInfoForVersions = true)
        {
            Logger.Write("Adding document to folder", Severity.Trace);
            added = false;
            try
            {
                //actnivities = PlatformService.GetFileActivitiesImanage(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.FolderId, file.Id);

                if (SyncVerOption == ConflictVersionOptions.All)
                {
                    file.DeleteFile();
                    file.FilePath = PlatformService.DownloadFileVersion(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.Id, StartVersion);
                }
                else
                {
                    var firstVersionToImport =
                        file.Versions.OrderBy(a => a.Version)
                            .LastOrDefault(a => !ManFile.ShouldSkip(versionIdsToSkip, a)) ?? file.CurrentVersion;

                    file.DeleteFile();
                    file.FilePath =
                        PlatformService.DownloadFileVersion(Application.iManInstance.AuthProvider.GetCurrentWSUser(),
                            file.Id, firstVersionToImport.Version);
                }

                ManFile createdFile;

                if (useProfileDialog)
                {
                    createdFile= DisplayImportDialog(file);
                    added = createdFile!=null;
                    if (createdFile != null && updateSyncInfoForVersions)
                    {
                        var version = SyncVerOption == ConflictVersionOptions.All ? file.Versions.FirstOrDefault(v => v.Version == StartVersion) : file.Versions.OrderBy(a => a.Version).LastOrDefault();
                        if (version != null)
                        {
                           GetService().UpdateSyncInfo(createdFile.GetVersions().First(),new ActionContext(Workshare.Integration.Processor.Services.ActionType.Import)
                           {
                               WsVersion = new WsVersion(version, null)
                           });
                        }
                    }
                }
                else
                {
                    IManDocument doc = m_document.Database.CreateDocument();
                    IManUser oUser = m_document.Database.GetUser(m_document.Database.Session.UserID);

                    var oDocClasses = m_document.Database.SearchDocumentClasses("", imSearchAttributeType.imSearchBoth, true);
                    var oDocClass = (oDocClasses.Contains("DOC")) ? oDocClasses.ItemByName("DOC") : oDocClasses.ItemByIndex(0);
                    var doctype = doc.Database.GetDocumentTypeFromPath(file.FilePath);
                    if (doctype == null)
                    {
                        throw new FileNotCreatedException(string.Format(Properties.Resources.STR_CANNOT_ADD_NEW_FILE_WRONG_TYPE_ERROR_F, file.FriendlyName));
                    }
                    doc.SetAttributeByID(imProfileAttributeID.imProfileType, doctype);
                    doc.SetAttributeByID(imProfileAttributeID.imProfileClass, oDocClass);
                    doc.SetAttributeByID(imProfileAttributeID.imProfileAuthor, oUser);
                    doc.SetAttributeByID(imProfileAttributeID.imProfileDescription, FileUtils.GetFileNameWithoutExtension(file.FriendlyName));
                    doc.SetAttributeByID(imProfileAttributeID.imProfileOperator, oUser);
                    Logger.Write("Trying to upload a file into DMS: " + file.FilePath, Severity.Information);

                    var Results = doc.CheckInWithResults(file.FilePath, imCheckinDisposition.imCheckinNewDocument, imCheckinOptions.imDontKeepCheckedOut);
                    if (!Results.Succeeded)
                    {
                        var resErr = new StringBuilder();
                        resErr.AppendFormat("ErrorCode : {0}. ErrorMessage : {1}", Results.ErrorCode, Results.ErrorMessage);

                        foreach (IManProfileError manProfileError in Results.ErrorList)
                        {
                            resErr.Append(Environment.NewLine);
                            resErr.AppendFormat("AttribID : {0}. Description : {1}", manProfileError.AttribID, manProfileError.Description);
                        }
                        Logger.Write("CheckInWithResults return error: " + resErr.ToString(), Severity.Information);

                        throw new FileNotCreatedException(Results.ErrorMessage);
                    }
                    Logger.Write("Trying to upload a file into DMS: Succeded " + file.FilePath, Severity.Information);
                    added = true;
                    createdFile = new ManFile(doc, m_Folder);
                }

                if (createdFile != null)
                {
                    if (SyncVerOption == ConflictVersionOptions.All)
                    {
                        if (!createdFile.CheckedOut)
                        {
                            createdFile.GetFileToCheckout();
                        }

                        /// TODO: REMOVE THAT IN FUTURE
                        if (StartVersion == 2)
                        {
                            createdFile.AddHistories(actnivities.Where(x => x.CurrentVersion == 1).ToList());
                        }
                        createdFile.AddHistories(actnivities.Where(x => x.CurrentVersion == StartVersion).ToList());

                        foreach (var ver in file.Versions.Where(x => x.Version > StartVersion && !ShouldSkip(versionIdsToSkip, x)).OrderBy(x => x.Version).ToArray())
                        {
                            file.FilePath = PlatformService.DownloadFileVersion(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.Id, ver.Version);
                            var version = createdFile.AddVersion(file.FilePath, file, actnivities.Where(x => x.CurrentVersion == ver.Version).ToList());
                            if (updateSyncInfoForVersions)
                            {
                                GetService().UpdateSyncInfo(version, new ActionContext(Workshare.Integration.Processor.Services.ActionType.Import)
                                {
                                    WsVersion = new WsVersion(ver, null)
                                });
                            }
                        }
                    }
                    else if (SyncVerOption == ConflictVersionOptions.Latest)
                    {
                        var versionsIdsToAdd =
                            file.Versions.Where(x => x.Version >= StartVersion).Select(x => x.Version).ToArray();
                        createdFile.AddHistories(actnivities.Where(act=>versionsIdsToAdd.Contains(act.CurrentVersion)).ToList());
                    }
                }
                return createdFile;
            }
            catch (FileNotCreatedException)
            {
                throw;
            }
            catch (Exception ex)
            {
                throw new FileNotCreatedException(ex.Message, ex);
            }
        }


        static public bool ShouldSkip(IEnumerable<string> list,FileVersionDetails verDetails )
        {
            if (list == null) return false;
            return list.Any(a => string.Equals(a, verDetails.Id.ToString()));
        }

        private imHistEvent GetHistEventByOperation(Workshare.Integration.Operations operation)
        {
            switch (operation)
            {
                case Workshare.Integration.Operations.Send:
                    return imHistEvent.imHistoryExport;
                case Workshare.Integration.Operations.Sync:
                    return imHistEvent.imHistoryEchoSync;
                case Workshare.Integration.Operations.Deleted:
                    return imHistEvent.imHistoryDelete;
                default:
                    throw new CannotAddHistoryException("Operation is not correct");
            }
        }

        public void AddHistory(string eventName, string eventComment, Workshare.Integration.Operations operation)
        {
            if(this.IsCheckedOutToOtherUser())
            {
                throw new FileCheckoutedToAnotherUser(operation, GetCheckoutUser());
            }

            m_document.HistoryList.Add(GetHistEventByOperation(operation), 0, 0, RES.STR_WORKSHARE_TITLE, eventComment, Environment.MachineName, eventName, string.Empty);
            
            var res = m_document.UpdateWithResults();
            if (!res.Succeeded)
            {
                throw new CannotAddHistoryException(res.ErrorList.ItemByIndex(0).Description);
            }
        }

        public void AddHistories(List<Activity> activities)
        {
            try
            {
                if (activities == null)
                    throw new CannotAddHistoryException("activity list is empty");

                var last = activities.LastOrDefault(p => p.Noun == "Comment");


                foreach (var activity in activities)
                {
                    if (activity.Noun == "Comment" && activity != last)
                        continue;

                    var comment = activity.GetComment();

                    //if (activity.Noun != "Member" && activity.CurrentVersion != version)
                    //continue;

                    if (!string.IsNullOrEmpty(comment))
                        m_document.HistoryList.Add(
                            activity.HistoryModify ? imHistEvent.imHistoryModify : imHistEvent.imHistoryView,
                            0, 0, RES.STR_WORKSHARE_TITLE, comment, activity.FolderName, string.Empty, string.Empty);
                }

                var res = m_document.UpdateWithResults();
                if (!res.Succeeded)
                {
                    throw new CannotAddHistoryException(res.ErrorList.ItemByIndex(0).Description);
                }
            }
            catch (COMException ex)
            {
                if (ex.ErrorCode ==-2147221199) //Document in use
                {
                    throw new FileCheckoutedToAnotherUser(GetCheckoutUser());
                }
                throw;
            }
        }

        public void GetFileToCheckout()
        {
            string filename = Path.GetTempFileName();
            m_document.CheckOut(filename, imCheckOutOptions.imReplaceExistingFile, DateTime.Now.AddDays(INFINITY_DAYS), string.Empty);
            var fi = new FileInfo(filename);
            // somehow that's date set incorect by imanage, but we need that to further use
            fi.LastWriteTime = Modified;
            fi.LastAccessTime = Modified;
        }

        public override string ToString()
        {
            return string.Format("File with ID={0}, Name={1}", ID, DisplayName);
        }

        public IDMSFolder RootFolder()
        {
            return new ManFolder(m_document.Database.Root);
        }



        public IEnumerable<IDmsVersion> GetVersions()
        {
            var res = new List<IDmsVersion>();
            m_document.Refresh();
            var latest=m_document.LatestVersion;
            var versions = latest.Versions;
            versions.Refresh();
            
            foreach (IManDocument doc in versions)
            {
                res.Add(new ManVersion(new ManFile(doc,m_Folder)));
            }

            return res;
        }
        public int DMSId
        {
            get
            {
                return m_document.Number;
            }
        }

        internal string GetCheckoutUser()
        {
            var user = m_document.InUseBy;
            if (user != null)
            {
                return user.Name;
            }
            return string.Empty;
        }

        internal string GetCurrentCheckedInFile()
        {
            var localCopy = Path.GetTempFileName();
            m_document.GetCopy(localCopy, imGetCopyOptions.imNativeFormat);
            return localCopy;
        }

        public bool IsFileLocked()
        {
            if (CheckedOut)
            {
                return FileUtils.IsFileLocked(CheckoutPath);
            }
            return false;
        }

        internal void Refresh()
        {
            m_document.Refresh();
        }

        public string DMSItemKey
        {
            get { return (m_document == null) ? "" : Application.iManInstance.ServerKey + ":!DatabaseName:" + m_document.Database.Name + ":!Document:" + this.DMSId; }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Interfaces/Logger/Logger.cs
﻿using System;
using System.Diagnostics;
using Microsoft.Win32;

namespace Workshare.Components.WSLogger
{

    //TODO better place for logger
    public enum Severity
    {
        Trace,
        Warning,
        Information,
        Error,
        CriticalError,
        Verbose
    }
    public static class Logger
    {
        static SourceLevels GetLogSeverity()
        {
            try
            {
                using (var rekKey = Registry.CurrentUser.OpenSubKey(@"Software\Workshare"))
                {
                    if (rekKey != null)
                    {
                        var value = Convert.ToInt32(rekKey.GetValue("logging"));
                        if (Enum.IsDefined(typeof (SourceLevels), value))
                        {
                            var level = (SourceLevels) value;
                            return level;
                        }
                    }
                }

                return SourceLevels.Error;
            }
            catch (Exception)
            {
                return SourceLevels.Error;
            }
        }

        static  Listener _listener;
        static Logger()
        {
            WorkShareTrace = new TraceSource(TRACESOURCENAME) {Switch = {Level = GetLogSeverity()}};
            _listener = new Listener(WorkShareTrace);
        }
        public static readonly string LOGFILENAME = "WorkshareIntegration.log";
        static readonly string TRACESOURCENAME = "WS";
        static private readonly TraceSource WorkShareTrace;
        static TraceEventType SeverityRemap(Severity severity)
        {
            switch (severity)
            {
                case Severity.CriticalError: return TraceEventType.Critical;
                case Severity.Error: return TraceEventType.Error;
                case Severity.Information: return TraceEventType.Information;
                case Severity.Trace: return TraceEventType.Resume;
                case Severity.Verbose: return TraceEventType.Verbose;
                case Severity.Warning: return TraceEventType.Warning;
                default: return TraceEventType.Verbose;
            }
        }
        static string MessageRemap(string message)
        {
            return DateTime.Now + " " + message;
        }
        static string MessageRemap(Exception message)
        {
            return DateTime.Now + " " + message.ToString();
        }
        static string MessageRemap(string message, Exception ex)
        {
            return DateTime.Now + " " + message + " " + ex.ToString();
        }

        #region WriteMethods
        public static void Write(string message, Severity severity)
        {
            WorkShareTrace.TraceEvent(SeverityRemap(severity), (int)severity, MessageRemap(message));
            WorkShareTrace.Flush();
        }
        public static void Write(Exception exception, Severity severity)
        {
            WorkShareTrace.TraceEvent(SeverityRemap(severity), (int)severity, MessageRemap(exception));
            WorkShareTrace.Flush();
        }
        public static void Write(string message, Exception exception, Severity severity)
        {
            WorkShareTrace.TraceEvent(SeverityRemap(severity), (int)severity, MessageRemap(message, exception));
            WorkShareTrace.Flush();
        }

        public static void WriteError(string message, Exception exception)
        {
            WorkShareTrace.TraceEvent(SeverityRemap(Severity.Error), (int)Severity.Error, MessageRemap(message, exception));
            WorkShareTrace.Flush();
        }

        public static void WriteTrace(string message)
        {
            WorkShareTrace.TraceEvent(SeverityRemap(Severity.Trace), (int)Severity.Trace, message);
            WorkShareTrace.Flush();
        }

        public static void WriteError(Exception exception)
        {
            try
            {
                WorkShareTrace.TraceEvent(SeverityRemap(Severity.Error), (int)Severity.Error, MessageRemap("", exception));
                WorkShareTrace.Flush();
            }
            catch (Exception )
            {
            }
            
        }

        #endregion

        public static void WriteWarning(string p)
        {
            try
            {
                WorkShareTrace.TraceEvent(SeverityRemap(Severity.Warning), (int)Severity.Warning, p);
                WorkShareTrace.Flush();
            }
            catch (Exception)
            {
            }
        }
    }
    public class Listener
    {
        public Listener(TraceSource listenSource)
        {
            if (instance == null)
            {
                instance = new TextWriterTraceListener(Path);
                instance.Name = "Workshare Logging Listener";
            }
            if (!listenSource.Listeners.Contains(instance))
            {
                listenSource.Listeners.Add(instance);
            }
        }

        readonly TextWriterTraceListener instance = null;
        static string _Path;
        public static string Path
        {
            get
            {
                if (_Path == null)
                {
                    _Path = System.IO.Path.GetTempPath() + "\\" + Logger.LOGFILENAME;
                }
                return _Path;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/FolderDetails.cs
﻿using System;
using System.Collections.Generic;

namespace WorksharePlatform
{
    public class FolderDetails
    {
        private int _id;
        public FolderDetails()
        {
            Permissions = new Permissions();
        }
        
        public int Id
        {
            get { return _id; }
            set
            {
                _id = value;
                Permissions.FolderId = _id;
            }
        }

        public int Ancestry { get; set; }
        public string Name { get; set; }
        public string Description { get; set; }
        public int ParentId { get; set; }
        public bool NotifyOwner { get; set; }
        public DateTime? ExpiresAt { get; set; }
        public int ChildFoldersCounter { get; set; }
        public int FileCounter { get; set; }
        public Permissions Permissions { get; set; }
        public UserDetails Creator { get; set; }
        public UserDetails Owner { get; set; }
        public bool IsDeleted { get; set; }
        public string Url { get; set; }
        public override string ToString()
        {
            return string.Format("Folder ID={0}, Name={1}", Id, Name);
        }



        public int MemberCount { get; set; }
    }

    public class FolderMembers
    {
        public List<UserDetails> Members { get; set; }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Strategies/ScanStrategy.cs
﻿using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.WsProxies;

namespace Workshare.IManage.Strategies
{
    class ScanStrategy : Workshare.Integration.Processor.Strategies.ScanStrategy
    {
        public ScanStrategy(WsProxy wsProxy, IAuthProvider auth, DmsWorkerBase dmsWorker,SyncInfoService syncInfoService):base(wsProxy,auth,syncInfoService)
        {
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CheckOutDialog/ContentConverter.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Data;

namespace Workshare.Components.Views.CheckOutDialog
{
    public class ContentConverter:IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            var filename = value as string;
            if (string.IsNullOrEmpty(filename))
            {
                return Properties.Resources.CHECKOUT_TEXT_IF_DOCUMENTS;
            }
            else
            {
                return string.Format(Properties.Resources.CHECKOUT_TEXT_IF_DOCUMENT, filename);
            }
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Common/DMSAuthProvider.cs
﻿using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;
using WorksharePlatform;

namespace Workshare.Components.Common
{
    public class DMSAuthProvider:IAuthProvider
    {
        public const string DeviceCredential = CookieAwareClient.device_credential;

        public UserDetails CheckIfAuth()
        {
            var user = GetCurrentWSUser();
            if (user == null)
                throw new CloudUnAuthorized();
            return user;
        }

        private UserDetails _currentUser;

        public UserDetails GetCurrentWSUser()
        {
            return _currentUser ?? (_currentUser = new UserDetails());
        }

        public void SetCurrentUser(UserDetails user)
        {
            _currentUser = user;
        }


        public WsUser GetCurrentWSUser2()
        {
            var u = GetCurrentWSUser();
            if (u != null)
            {
                PlatformService.RefreshUserIfNeeded(u);
            }
            return u == null ? null : new WsUser(u);
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/UserControls/WsSplitButton.xaml.cs
﻿using System;
using System.ComponentModel;
using System.Linq;
using System.Windows;
using System.Windows.Controls;
using Workshare.Components.Common;
using Workshare.Integration;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Services;
using WorksharePlatform;

namespace Workshare.Components.Views.TrueSyncDialog.UserControls
{
    /// <summary>
    /// Interaction logic for WsSplitButton.xaml
    /// </summary>
    public partial class WsSplitButton : UserControl
    {
        private BackgroundWorker breakLinkWorker = new BackgroundWorker();

        public WsSplitButton()
        {
            InitializeComponent();
            breakLinkWorker.DoWork += breakLinkWorker_DoWork;
        }

        private void BtnImport_OnClick(object sender, RoutedEventArgs e)
        {
            var parent = ((Panel)(((Button)sender).Parent)).FindName("MenuImport");
            if (parent != null && ((Menu)parent).Items.Count > 0)
            {
                var item = (MenuItem)((Menu)parent).ItemContainerGenerator.ContainerFromItem(((Menu)parent).Items[0]);
                if (item == null) return;

                if (item.Role == MenuItemRole.TopLevelHeader)
                {
                    item.IsSubmenuOpen = true;
                }
                else if (item.Role == MenuItemRole.TopLevelItem)
                {
                    if (item.Command != null)
                    {
                        item.Command.Execute(item.CommandParameter);
                    }
                }
            }
            else if(parent!=null)
            {
                ImportFileActivityVm importFileActivityVm = ((Menu)parent).DataContext as ImportFileActivityVm;
                if (importFileActivityVm != null && importFileActivityVm.State == ImportFileActivityState.Scanned && importFileActivityVm.Changes.Any(c => c.Type == ChangeType.RemoteDeleted))
                {
                    ImportFileActivity importFileActivity = importFileActivityVm.data as ImportFileActivity;
                    if (importFileActivity != null)
                    {
                        importFileActivityVm.State = ImportFileActivityState.DeletingLink;
                        while (!breakLinkWorker.IsBusy)
                        {
                            breakLinkWorker.RunWorkerAsync(importFileActivityVm);
                            break;
                        }
                    }
                }
            }
        }

        private void breakLinkWorker_DoWork(object sender, DoWorkEventArgs e)
        {
            ImportFileActivityVm importFileActivityVm = e.Argument as ImportFileActivityVm;
            if (importFileActivityVm != null)
            {
                ImportFileActivity importFileActivity = importFileActivityVm.data as ImportFileActivity;
                if (importFileActivity != null)
                {
                    try
                    {
                        var syncInfo = WSApplication.Instance.Module.Resolve<SyncInfoService>();
                        importFileActivity.DmsFile.AddHistory("FileDeletedOrMoved", "Synced from Workshare on " + DateTime.Now.ToString(Activity.TimeFormat) + ". File has been deleted or moved", Operations.Sync);
                        syncInfo.BreakLink(importFileActivity.DmsFile);
                        importFileActivityVm.State = ImportFileActivityState.LinkIsDeleted;
                    }
                    catch (Exception ex)
                    {
                        if (ex is FileCheckoutedToAnotherUser)
                        {
                            importFileActivityVm.State = ImportFileActivityState.CheckedOutToAnother;
                            importFileActivity.CheckedOutTo = ((FileCheckoutedToAnotherUser)ex).UserName;
                        }
                        else
                        {
                            importFileActivityVm.State = ImportFileActivityState.Error;
                            importFileActivity.Error = ex;
                        }
                    }
                }
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/Ext.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Runtime.Remoting.Messaging;
using System.Text;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Integration.Processor.Maps
{
    public static class Ext
    {
        public static ISyncInfo GetSyncInfo(this SyncInfoService dmsWorker, FileMap map, bool ForceRequest = true)
        {
            return (map == null || map.LocalFile == null) ? null : dmsWorker.GetSyncInfo(map.LocalFile, ForceRequest);
        }

        public static ISyncInfo GetSyncInfo(this SyncInfoService dmsWorker, FolderMap map, bool ForceRequest = true)
        {
            return (map == null || map.LocalFolder == null) ? null : dmsWorker.GetSyncInfo(map.LocalFolder, ForceRequest);
        }

        public static IEnumerable<int> GetSendData(this FolderMap map, SyncInfoService syncService, bool ForceRequest = true)
        {
            return (map.LocalFolder == null) ? new int[0] : syncService.GetSendData(map.LocalFolder, ForceRequest) ?? new int[0];
        }

        public static IEnumerable<int> GetSendData(this SyncInfoService syncService, FolderMap map, bool ForceRequest = true)
        {
            return (map.LocalFolder == null) ? new int[0] : syncService.GetSendData(map.LocalFolder, ForceRequest) ?? new int[0];
        }

        public static int? GetWsId(this FileMap map)
        {
            return map == null || map.WsFile == null ? (int?)null : map.WsFile.Id;
        }

        public static string GetLocalId(this FileMap map)
        {
            return map == null || map.LocalFile == null ? null : map.LocalFile.DMSId.ToString();
        }

        public static string GetLocalId(this FolderMap map)
        {
            return map == null || map.LocalFolder == null ? null : map.LocalFolder.DMSId.ToString();
        }

        public static int? GetWsId(this FolderMap map)
        {
            return map == null || map.WsFolder == null ? (int?)null : map.WsFolder.Id;
        }

        public static VersionMap GetLatestLocalVersionNotUploadedToWs(this FileMap fileMap)
        {
            return fileMap.Maps.OfType<VersionMap>()
                .Where(a => a.LocalVersion!=null && a.WsVersion==null)
                .OrderByDescending(a => a.LocalVersion.Number)
                .FirstOrDefault();
        }

        public static bool ContainsChildWsVersion(this FileMap map, int wsId)
        {
            return map.Maps.OfType<VersionMap>()
                .Any(p => p.WsVersion != null && p.WsVersion.Id == wsId);
        }

        public static List<ItemException> GetItemErrorsList(List<ItemMap> errors)
        {
            var errorsList = new List<ItemException>();
            foreach (var ex in errors)
            {
                var folderMap = ex as FolderMap;
                var fileMap = ex as FileMap;
                if (folderMap != null)
                {
                    errorsList.Add(new ItemException
                    {
                        Error = folderMap.LocalFolder == null
                            ? ((ex.Error is BaseException)
                                ? ex.Error
                                : new BaseException(string.Empty, ex.Error.Message, ex.Error))
                            : ((ex.Error is BaseException)
                                ? ex.Error
                                : new BaseException(folderMap.LocalFolder.Name, ex.Error.Message, ex.Error)),
                        Item = folderMap.LocalFolder
                    });
                }
                else if (fileMap != null)
                {
                    errorsList.Add(new ItemException
                    {
                        Error = fileMap.LocalFile == null
                            ? ((ex.Error is BaseException)
                                ? ex.Error
                                : new BaseException(string.Empty, ex.Error.Message, ex.Error))
                            : ((ex.Error is BaseException)
                                ? ex.Error
                                : new BaseException(fileMap.LocalFile.Name, ex.Error.Message, ex.Error)),
                        Item = fileMap.LocalFile
                    });
                }
                else
                {
                    errorsList.Add(new ItemException
                    {
                        Error = ex.Error
                    });
                }
            }
            return errorsList;
        }

        public static bool HasLocal(this FolderMap map)
        {
            if (map == null) return false;
            return map.LocalFolder != null;
        }

        public static bool HasRemote(this FolderMap map)
        {
            if (map == null) return false;
            return map.WsFolder != null && !map.WsFolder.IsDeleted;
        }

        public static bool HasLocal(this FileMap map)
        {
            if (map == null) return false;
            return map.LocalFile != null;
        }

        public static bool HasRemote(this FileMap map)
        {
            if (map == null) return false;
            return map.WsFile != null && !map.WsFile.IsDeleted;
        }

        public static bool HasRemote(this VersionMap map)
        {
            if (map == null) return false;
            return map.WsVersion != null;
        }

        public static bool HasLocal(this VersionMap map)
        {
            if (map == null) return false;
            return map.LocalVersion != null;
        }

        public static FolderMap GetActualParent(this FileMap map)
        {
            if (map == null) return null;
            return map.IndirectParent ?? map.Parent as FolderMap;
        }

        public static FolderMap GetLocalParent(this FileMap map)
        {
            var res = map.Parent as FolderMap;
            if (res == null && map.HasLocal())
            {
                res = new FolderMap
                {
                    LocalFolder = map.LocalFile.ParentFolder,
                    ProcessState = ProcessState.Scanned
                };
            }
            return res;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/SelectFolder/SelectFolderForm.cs
﻿using System;
using System.Diagnostics;
using System.Reflection;
using System.Runtime.InteropServices;
using System.Security.Permissions;
using System.Timers;
using System.Windows.Forms;
using System.Windows.Threading;
using mshtml;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using RES = Workshare.Components.Properties.Resources;
using Workshare.Components.WSLogger;
using Microsoft.Win32;

namespace Workshare.Components.Views.SelectFolder
{
    public partial class SelectFolderForm : Form
    {
        [DllImport("urlmon.dll", CharSet = CharSet.Ansi)]
        private static extern int UrlMkSetSessionOption(int dwOption, string pBuffer, int dwBufferLength, int dwReserved);
        const int URLMON_OPTION_USERAGENT = 0x10000001;

        JSCallback callbacks = new JSCallback();
        readonly string DialogRelUri = "home/dialogs.sdif?caller=imanage&extcall=hello";
        public int SelectedFolderId { private set; get; }
        Uri DialogUri
        {
            get
            {
                return new Uri(WSApplication.Instance.Server.ToString() + DialogRelUri);
            }
        }

        public void HideScriptErrors(WebBrowser wb, bool hide)
        {
            try
            {
                var fiComWebBrowser = typeof(WebBrowser).GetField("webBrowser1", BindingFlags.Instance | BindingFlags.NonPublic);
                if (fiComWebBrowser == null) return;
                var objComWebBrowser = fiComWebBrowser.GetValue(wb);
                if (objComWebBrowser == null)
                {
                    wb.Navigated += (o, s) => HideScriptErrors(wb, hide); //In case we are to early
                    return;
                }
                objComWebBrowser.GetType().InvokeMember("Silent", BindingFlags.SetProperty, null, objComWebBrowser, new object[] { hide });
            }
            catch (Exception ex)
            {
                Logger.Write(ex, Severity.Error);
            }
        }

        public SelectFolderForm()
        {
            SelectedFolderId = -1;
            InitializeComponent();
            this.Width = 594;
            this.Height = 510;
            this.StartPosition = FormStartPosition.CenterParent;
            this.Load += SelectFolderView_Loaded;
            this.AutoScroll = false;
            this.Disposed += SelectFolderForm_Disposed;
            webBrowser1.ScrollBarsEnabled = false;
            webBrowser1.Navigated += webBrowser_Navigated;
            callbacks.OnCancel += callbacks_OnCancel;
            callbacks.OnOk += callbacks_OnOk;
            webBrowser1.ObjectForScripting = callbacks;
            webBrowser1.ScriptErrorsSuppressed = true;
            //webBrowser1.NavigateError += webBrowser1_NavigateError;
            webBrowser1.Navigated += new WebBrowserNavigatedEventHandler(
                (object sender, WebBrowserNavigatedEventArgs args) =>
                    {
                        Action<HtmlDocument> blockAlerts = (HtmlDocument d) =>
                        {
                            HtmlElement h = d.GetElementsByTagName("head")[0];
                            HtmlElement s = d.CreateElement("script");
                            IHTMLScriptElement e = (IHTMLScriptElement)s.DomElement;
                            e.text = "window.alert=function(){};";
                            h.AppendChild(s);
                        };
                        WebBrowser b = sender as WebBrowser;
                        blockAlerts(b.Document);
                        for (int i = 0; i < b.Document.Window.Frames.Count; i++)
                            try { blockAlerts(b.Document.Window.Frames[i].Document); }
                            catch (Exception) { };
                    });
            ChangeUserAgent();

        }

        void webBrowser1_NavigateError(object sender, NewWebBrowser.WebBrowserNavigateErrorEventArgs e)
        {
            MessageBox.Show(e.StatusCode.ToString());
        }

        public void ChangeUserAgent()
        {
            string ua = @"User-Agent:Mozilla/4.0 (compatible; MSIE 8.0)";
            UrlMkSetSessionOption(URLMON_OPTION_USERAGENT, ua, ua.Length, 0);
        }

        void SelectFolderForm_Disposed(object sender, EventArgs e)
        {
          webBrowser1.Dispose();
        }
        void m_closeTimer_Elapsed(object sender, ElapsedEventArgs e)
        {
            Logger.Write("Inside m_closeTimer_Elapsed", Severity.Information);
            Dispatcher.CurrentDispatcher.BeginInvoke(new Action(() =>
            {
                Logger.Write("Inside Dispatcher", Severity.Information);
                this.DialogResult = System.Windows.Forms.DialogResult.OK;
                this.Close();
                Logger.Write("ThisClose Executed", Severity.Information);
            }));
        }
        void callbacks_OnOk(int obj)
        {
            try
            {
                Logger.Write("Inside Callback_OnOk", Severity.Verbose);
                this.SelectedFolderId = obj;
                this.Close();
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }

        bool? Res;

        void callbacks_OnCancel()
        {
            try
            {
                this.Close();
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
            }
        }
        void webBrowser_Navigated(object sender, WebBrowserNavigatedEventArgs e)
        {
            var doc = webBrowser1.Document;
            
            var str =Authentication.CookieReader.Reader.GetCookie(DialogUri.ToString());
            if (!str.Contains(DMSAuthProvider.DeviceCredential))
            {
                this.SelectedFolderId = -10;
                this.Close();
            }
 
            if (doc != null)
            {
                var head = doc.GetElementsByTagName("head")[0]; // Head is one and only element as a rule, so no problems here...
                if (head == null)
                {
                    Logger.Write("Html Document Head is null in SelectFolderForm", Severity.CriticalError);
                    return;
                }
                var script = doc.CreateElement("script");
                var scrElement = (IHTMLScriptElement)script.DomElement;
                scrElement.text = RES.injectedJS.Replace("\r", "").Replace("\n", "").Replace("\t", "");
                head.AppendChild(script);

                doc.InvokeScript("init");
            }
            pbLoader.Visible = false;
        }

        void SelectFolderView_Loaded(object sender, EventArgs e)
        {
            Logger.WriteTrace(string.Format("Web browser control version: {0}", webBrowser1.Version));
            if (webBrowser1.Version.Major <= ModuleViewBase.IE8MAJORVERSION )
            {
                webBrowser1.Navigate(DialogUri, null, null, @"User-Agent:Mozilla/4.0 (compatible; MSIE 8.0)");
            }
            else
            {
                webBrowser1.Navigate(DialogUri);
            }
        }

        private void btn_Refresh_Click(object sender, System.Windows.RoutedEventArgs e)
        {
            webBrowser1.Refresh();
        }

        private void btn_Dlg_Click(object sender, System.Windows.RoutedEventArgs e)
        {
            webBrowser1.Navigate(DialogUri);
        }

        private void btn_Home_Click(object sender, System.Windows.RoutedEventArgs e)
        {
            webBrowser1.Navigate(WSApplication.Instance.Server);
        }

        private void btn_Url_Click(object sender, System.Windows.RoutedEventArgs e)
        {

        }

        private void btn_Test_Click(object sender, System.Windows.RoutedEventArgs e)
        {
        }
    }

    [PermissionSet(SecurityAction.Demand, Name = "FullTrust")]
    [System.Runtime.InteropServices.ComVisibleAttribute(true)]
    public class JSCallback
    {
        public event Action OnCancel;
        public event Action<int> OnOk;
        public void onCancel()
        {
            if (OnCancel != null)
            {
                OnCancel();
            }
        }

        public void onOk(int folder_id)
        {
            if (OnOk != null)
            {
                OnOk(folder_id);
            }
        }

        public void jsLogger(string msg)
        { 
            var regKey = Registry.CurrentUser.OpenSubKey(@"Software\Workshare");
            if (regKey != null)
            {
                string logFromWeb = regKey.GetValue("UseWebLog") as string;
                if (!string.IsNullOrEmpty(logFromWeb) && logFromWeb == "1")
                {
                    Logger.Write("WEB LOG: " + msg, Severity.Information);
                }
            }
        }
    }

}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Contrete/ManVersion.cs
﻿using System;
using Workshare.Integration;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.Services;

namespace Workshare.IManage.Contrete
{
    internal class ManVersion : BaseDmsVersion, IDmsVersion
    {
        public string Id { set; get; }

        public int Number
        {
            get
            {
                return doc.m_document.Version;
            }
        }

        public object ID {
            get
            {
                return doc.ID;
            }
            set
            {
                
            }
        }

        private ManFile doc;

        public ManVersion(ManFile doc)
        {
            this.doc = doc;
            Id = doc.m_document.ObjectID;
        }


        public IDMSFile GetLatestFile()
        {
            return doc.GetLatest();
        }

        public string Name
        {
            get
            {
                return doc.Name;
            }
        }

        public bool WasChangedAfterSend2(bool useForcerequest = true)
        {
            var syncInfo = Application.iManInstance.Module.Resolve<SyncInfoService>().GetSyncInfo(this, useForcerequest);
            if (syncInfo == null) return false;
            return doc.EditDate.Ticks.ToString() != syncInfo.DmsEditTime;
        }

        public string DisplayName
        {
            get { return doc.DisplayName; }
        }

        internal string GetCurrentCheckedInFile()
        {
            return doc.GetCurrentCheckedInFile();
        }

        public DateTime EditTime
        {
            get
            {
                return doc.Modified;
            }
        }

        public void AddHistory(string eventName, string coment, Operations operation)
        {
            doc.AddHistory(eventName, coment, operation);
        }

        public IDMSFile AsFile()
        {
            return doc;
        }
    }
}

<file_sep>/SharePoint/src/WorksharePointCloud/Layouts/WorkshareCloud/WorkshareCloudService.aspx.cs
﻿using System;
using Microsoft.SharePoint;
using Microsoft.SharePoint.WebControls;
using System.Web;
using System.Threading;
using System.IO;
using System.Web.Services;
using System.Web.Script.Serialization;
using System.Web.Script.Services;
using WorksharePlatform;
using WorkshareCloud.Common;
using System.Net;
using System.Collections.Generic;

namespace WorkshareCloud.Layouts.WorkshareCloud
{
    public partial class WorkshareCloudService : LayoutsPageBase
    {

        protected void Page_Load(object sender, EventArgs e)
        {

        }

        [WebMethod]
        [ScriptMethod(ResponseFormat = ResponseFormat.Json)]
        public static object Send()
        {
            return Execute(() =>
                {
                    var user = CloudAuthenication.GetCurrentUser();
                    try
                    {
                        string data = string.Empty;
                        var sendInfos = Deserialize<SendItemInformations>(HttpContext.Current, out data);
                        if (sendInfos != null && sendInfos.infos != null)
                        {
                            WorkshareIntegration.Instance.SendItems(sendInfos.infos, user);
                        }
                        else
                        {
                            throw new BadRequest(data);
                        }
                        return string.Empty;

                    }
                    finally
                    {
                        CloudAuthenication.Update(user);
                    }
                });
        }

        static object Execute(Func<object> action)
        {
            try
            {
                return action();
            }
            catch (ListProcessException ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.InternalServerError;
                return new ErrorInfo(ErrorCode.ListItemSyncError, ex.Message, ex.ToJSON());
            }
            catch (BadRequest ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.BadRequest;
                return new ErrorInfo(ex);
            }

            catch (ItemNotFound ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.NotFound;
                return new ErrorInfo(ex);
            }
            catch (CloudUnAuthorized)
            {
                CloudAuthenication.Logout();
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.ServiceUnavailable;
                return new ErrorInfo(ErrorCode.CloudUnAuth);
            }
            catch (OfflineException ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.ServiceUnavailable;
                return new ErrorInfo(ex);
            }
            catch (FileCheckoutedToAnotherUser)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.MethodNotAllowed;
                return new ErrorInfo(ErrorCode.FileCheckedOut);
            }
            catch (UnauthorizedAccessException ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.Forbidden;
                return new ErrorInfo(ex);
            }
            catch (CloudFolderAccessDenied)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.Forbidden;
                return new ErrorInfo(ErrorCode.CloudItemIsForbidden);
            }
            catch (AlreadySentException ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.MethodNotAllowed;
                return new ErrorInfo(ex);
            }
            catch (CloudFolderNotFound)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.NotFound;
                return new ErrorInfo(ErrorCode.CloudFolderNotFound);
            }
            catch (CloudFileNotFound)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.NotFound;
                return new ErrorInfo(ErrorCode.CloudFileNotFound);
            }
            catch (CloudFieldNotFound)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.NotFound;
                return new ErrorInfo(ErrorCode.CloudFieldNotFound);
            }
            catch (Exception ex)
            {
                HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.InternalServerError;
                return new ErrorInfo(ex);
            }
        }

        [WebMethod]
        [ScriptMethod(ResponseFormat = ResponseFormat.Json)]
        public static object Sync()
        {
            return Execute(() =>
                {
                    var user = CloudAuthenication.GetCurrentUser();
                    try
                    {
                        var data=string.Empty;
                        var syncInfos = Deserialize<SyncItemInformations>(HttpContext.Current, out data);
                        if (syncInfos.infos != null)
                        {
                            foreach (var syncInfo in syncInfos.infos)
                            {
                                Guid ListGuid;

                                if (syncInfo != null && Extensions.GuidTryParse(syncInfo.listGuid, out ListGuid))
                                {
                                    WorkshareIntegration.Instance.SyncItems(syncInfos.infos, user);
                                }
                                else
                                {
                                    throw new BadRequest(data);
                                }
                            }
                        }
                        return string.Empty;
                    }
                    finally
                    {
                        CloudAuthenication.Update(user);
                    }
                });
        }
        [WebMethod]
        [ScriptMethod(ResponseFormat=ResponseFormat.Json)]
        public static object Update()
        {
            return Execute(() =>
                {
                    string data = string.Empty;
                    var sendInfo = Deserialize<SendItemInformation>(HttpContext.Current, out data);
                    Guid ListGuid;

                    if (Extensions.GuidTryParse(sendInfo.listGuid, out ListGuid))
                    {
                        WorkshareIntegration.Instance.EnsureListInitialized(SPContext.Current.Web.Lists[ListGuid]);
                        return "";
                    }
                    else
                    {
                        throw new BadRequest(string.Format("ListGuid={0}",sendInfo.listGuid));
                    }
                });
        }

        [WebMethod]
        [ScriptMethod(ResponseFormat = ResponseFormat.Json)]
        public static object DialogSettings()
        {
            return Execute(() =>
            {
                try
                {
                    var res = PlatformService.GetDialogSettings(new UserDetails());

                    return new
                    {
                        dialog_create_folder_height = res.dialog_create_folder_height,
                        dialog_create_folder_width = res.dialog_create_folder_width,
                        dialog_login_height = res.dialog_login_height,
                        dialog_login_width = res.dialog_login_width,
                        dialog_select_folder_height = res.dialog_select_folder_height,
                        dialog_select_folder_width = res.dialog_select_folder_width
                    };
                }
                finally
                {
                    PlatformService._Host = null;
                }
            });
        }

        [WebMethod]
        public static object Login(string email, string password)
        {
            return Execute(() =>
                {
                    if (string.IsNullOrEmpty(email) || string.IsNullOrEmpty(password))
                    {
                        HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.ServiceUnavailable;
                        return new ErrorInfo(ErrorCode.WrongCredentials);
                    }
                    try
                    {
                        CloudAuthenication.Login(new UserDetails()
                        {
                            Email = email,
                            Password = <PASSWORD>
                        });
                        return string.Empty;
                    }
                    catch (WebException ex)
                    {
                        HttpWebResponse res = (HttpWebResponse)ex.Response;
                        if (res.StatusCode == HttpStatusCode.NotFound || (int)res.StatusCode == 422)//422 - entity is unprocessible
                        {
                            HttpContext.Current.Response.StatusCode = (int)HttpStatusCode.ServiceUnavailable;
                            return new ErrorInfo(ErrorCode.WrongCredentials);
                        }
                        else throw;
                    }
                });
        }

        [WebMethod]
        public static object Logout()
        {
            return Execute(() =>
            {
                CloudAuthenication.Logout();
                return string.Empty;
            });
        }


        static T Deserialize<T>(HttpContext context, out string data)
        {
            data = string.Empty;
            try
            {
                context.Request.InputStream.Position = 0;
                using (var reader = new StreamReader(context.Request.InputStream, context.Request.ContentEncoding))
                {
                    data = reader.ReadToEnd();
                    return new JavaScriptSerializer().Deserialize<T>(data);
                }
            }
            catch
            {
                return default(T);
            }
        }

    }

     public class ErrorInfo
    {
         public ErrorInfo(ErrorCode error)
         {
             code = (int)error;
             switch (error)
             {
                 case ErrorCode.General: description =   Common.Properties.Resources.STR_ERROR_HAPPEN; break;
                 case ErrorCode.WrongCredentials: description = Common.Properties.Resources.STR_WRONGAUTH_CAPTION; break;
                 case ErrorCode.CloudUnAuth: description = Common.Properties.Resources.STR_WRONGAUTH_CAPTION; break;
                 case ErrorCode.CloudFileNotFound: description = Common.Properties.Resources.STR_CLOUDFILENOTFOUND; break;
                 case ErrorCode.CloudFolderNotFound: description = Common.Properties.Resources.STR_CLOUDFOLDERNOTFOUND; break;
                 case ErrorCode.CloudItemIsForbidden: description = Common.Properties.Resources.STR_UNABLESENDITEM_TEXT; break;
                 case ErrorCode.FileCheckedOut: description = Common.Properties.Resources.STR_FILEISCHECKEDOUTBYANOTHERUSER_TEXT; break;
                 case ErrorCode.CloudFieldNotFound: description = Common.Properties.Resources.STR_VIEWNOTINITIALIZED_TEXT; break;
                 case ErrorCode.ItemNotFound: description = Common.Properties.Resources.STR_LOCALFILENOTFOUND_TEXT; break;
                 default: description = Common.Properties.Resources.STR_ERROR; break;
             }
         }

         public ErrorInfo(Exception ex):this(ErrorCode.General,string.IsNullOrEmpty(ex.Message)?ex.GetType().Name:ex.Message)
         {
         }

        public ErrorInfo(ErrorCode error, string text)
        {
            code = (int)error;
            description = text;
        }

        public ErrorInfo(ErrorCode error, string text, object data)
            : this(error, text)
        {
            this.data = data;
        }

        public int code { get; private set; }
        public string description { get; private set; }
        public object data { get; private set; }
    }

    public static class HttpExt
    {
        public static void WriteObj(this HttpResponse response, object obj)
        {
            using (var writer = new StreamWriter(response.OutputStream))
            {
                writer.Write(new JavaScriptSerializer().Serialize(obj));
            }
        }

        public static void WriteErrorAndEndRequest(this HttpResponse response, ErrorCode error)
        {
            response.ClearContent();
            response.WriteObj(new ErrorInfo(error));
        }
    }

    public enum ErrorCode
    {
        General=1,
        ListItemSyncError = 5,
        CloudUnAuth=100,
        WrongCredentials=200,
        FileCheckedOut=300,
        CloudItemIsForbidden=403,
        CloudFileNotFound=404,
        CloudFolderNotFound=405,
        CloudItemNotFound=406,
        FileConflict = 503,
        SPFileNewer = 502,
        CloudFieldNotFound=506,
        ItemNotFound = 310
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/IManageModule.cs
﻿using Microsoft.Practices.Unity;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Services;
using Workshare.IManage.Integration;
using Workshare.IManage.Strategies;
using Workshare.IManage.Views;
using Workshare.Integration;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.IManage
{
    class IManageModule : WsIntegrationModule
    {
        protected override void Initialize()
        {
            base.Initialize();
            this.Container.RegisterInstance<ModuleBase>(this);
            this.Container.RegisterType<Workshare.Components.Views.Common.CommandInvoker>();
            this.Container.RegisterType<DmsWorkerBase, DmsWorker>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<IAuthProvider, DMSAuthProvider>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<IModuleView, ModuleView>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<IWSIntegration, WorkshareIntegration>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<DiscardedService, DiscardedService>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<SyncInfoService, SyncInfoService>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<WebDataStorageService, WebDataStorageService>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<IWSIntegration, WorkshareIntegration>(new ContainerControlledLifetimeManager());
            this.Container.RegisterType<ErrorReporterService>(new ContainerControlledLifetimeManager());

            this.Container.RegisterType<Workshare.Integration.Processor.Strategies.ActionStrategy.ImportStrategy>();
            this.Container.RegisterType<Workshare.Integration.Processor.Strategies.ActionStrategy.UploadStrategy>();
            this.Container.RegisterType<Workshare.Integration.Processor.Strategies.DmsScanStrategyBase, Workshare.IManage.Strategies.ScanStrategy>();
            this.Container.RegisterType<Workshare.Integration.Processor.Strategies.DmsProcessStrategyBase, Workshare.IManage.Strategies.ProcessStrategy>();
            this.Container.RegisterType<Workshare.IManage.Contrete.ImportDialog>();
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/MapController.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Processor.Changes.Visitors;

namespace Workshare.Integration.Processor.Maps
{
    public class MapController
    {
        public ItemMap FindMapById(ItemMap rootElement, string id)
        {
            var finder = new MapFinder(id);
            rootElement.Apply(finder);
            return finder.Result;
        }

        public FolderMap GetFirstParentLinkedWithExistedOnWs(ItemMap rootElement, string mapId)
        {
            var map = FindMapById(rootElement,mapId);
            if (map == null) return null;
            if (map is FileMap)
            {
                var fileMap = (FileMap) map;
                if (fileMap.IndirectParent != null)
                {
                    return fileMap.IndirectParent;
                }
            }
            var currentMap = map;
            while (currentMap!=null)
            {
                var folderMap = currentMap as FolderMap;
                if (folderMap.HasRemote() && folderMap.HasLocal())
                {
                    return folderMap;
                }
                currentMap = currentMap.Parent;
            }
            return null;
        }
    }
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/CloudFieldValue.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;
using WorksharePlatform;

namespace WorkshareCloud.Common
{
    public class CloudPathFieldValue
    {
        public readonly static string CloudField = "CloudPath";

        const char SEPARATOR = '/';

        public int ItemId { get; private set; }
        public int ParentFolderId { get; private set; }
        public int VersionId { get; private set; }
        public long ItemModifiedBy { get; private set; }

        CloudPathFieldValue()
        {
            ItemId = -1;
            ParentFolderId = -1;
            VersionId = -1;
            ItemModifiedBy = -1;
        }

        public CloudPathFieldValue(FileDetails value, SPListItem item)
            : this()
        {
            var fileDetailes = (FileDetails)value;
            ItemId = fileDetailes.CurrentVersion.FileId;
            ParentFolderId = fileDetailes.FolderId;
            if (fileDetailes.CurrentVersion != null)
            {
                VersionId = fileDetailes.CurrentVersion.Id;
            }
            var DateModify = (DateTime)item[SPBuiltInFieldId.Modified];
            ItemModifiedBy = DateModify.Ticks;
        }

        public CloudPathFieldValue(FolderDetails value, SPListItem item)
            : this()
        {
            var folderDetailes = (FolderDetails)value;
            ParentFolderId = folderDetailes.ParentId;
            ItemId = folderDetailes.Id;
            var DateModify = (DateTime)item[SPBuiltInFieldId.Modified];
            ItemModifiedBy = DateModify.Ticks;
        }

        public CloudPathFieldValue(string value)
            : this()
        {
            if (!string.IsNullOrEmpty(value))
            {
                var parts = value.Split(SEPARATOR);
                ParentFolderId = Int32.Parse(parts[0]);
                ItemId = Int32.Parse(parts[1]);
                VersionId = Int32.Parse(parts[2]);
                ItemModifiedBy =long.Parse(parts[3]);
            }
        }
        public static CloudPathFieldValue Empty
        {
            get
            {
                return new CloudPathFieldValue();
            }
        }

        public override string ToString()
        {
            if (HasValue)
            {
                return string.Format("{1}{0}{2}{0}{3}{0}{4}", SEPARATOR, ParentFolderId, ItemId, VersionId, ItemModifiedBy);
            }
            else
            {
                return string.Empty;
            }
        }

        public bool HasValue { get { return (ItemId > -1 && VersionId > -1) || ParentFolderId > -1; } }
    }
}
<file_sep>/OpenText/README.md
OTIntegration
=============

OTIntegration
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/TrueSyncDialogWindow.xaml.cs
﻿using System;
using System.Collections.Generic;
using System.Windows;
using System.Windows.Controls;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.TrueSyncDialog
{
    /// <summary>
    /// Interaction logic for TrueSyncDialogWindow.xaml
    /// </summary>
    public partial class TrueSyncDialogWindow
    {
        public TrueSyncDialogWindow()
        {
            InitializeComponent();
        }

        private readonly TrueSyncDialogViewModel _vm;
        private readonly IModuleView _view;

        public TrueSyncDialogWindow(ModuleBase module, CommandInvoker commandInvoker, IEnumerable<IDMSItem> items, IModuleView view)
        {
            InitializeComponent();
            _view = view;

            DataContextChanged += TrueSyncDialogWindow_DataContextChanged;

            DataContext = _vm = new TrueSyncDialogViewModel(module, commandInvoker, items, view);
            Loaded += TrueSyncDialogWindow_Loaded;
            Closed += TrueSyncDialogWindow_Closed;    
        }

        void TrueSyncDialogWindow_DataContextChanged(object sender, DependencyPropertyChangedEventArgs e)
        {
            var model = e.NewValue as TrueSyncDialogViewModel;
            if (model != null)
            {
                var vm = model;
                vm.ScanCompleted += vm_ScanCompleted;
            }
        }

        void vm_ScanCompleted(object sender, EventArgs e)
        {
            if (importActive.HasItems)
            {
                SyncTab.IsSelected = true;
            }
            else if (uploadActive.HasItems)
            {
                SendTab.IsSelected = true;
            }
        }

        void TrueSyncDialogWindow_Closed(object sender, EventArgs e)
        {
            _view.TopWindow = IntPtr.Zero;
            _view.SuppressProgressDialog(false);
        }

        void TrueSyncDialogWindow_Loaded(object sender, RoutedEventArgs e)
        {
            _view.SuppressProgressDialog(true);
            if (_vm != null)
            {
                if (_vm.RescanCommand.CanExecute(""))
                {
                    _vm.RescanCommand.Execute("");
                }

                Title = string.Format("{0}{1}{2}", FindResource("RES_TITLE_BAR_PART_1"), _vm.WorkspaceName, FindResource("RES_TITLE_BAR_PART_2"));
            }
            var handle=new System.Windows.Interop.WindowInteropHelper(this).Handle;
            _view.TopWindow = handle;

            if (AsDropDown)
            {
                Focusable = false;
                WindowStartupLocation = WindowStartupLocation.Manual;
                WindowStyle = WindowStyle.None;
                bar.Visibility = Visibility.Visible;
                UpdateLocation();
                Deactivated += TrueSyncDialogWindow_Deactivated;
                Closing += TrueSyncDialogWindow_Closing;
                SizeChanged += DropDownTrueSyncDialogWindow_SizeChanged;
            }
            this.KeepPositionOnResizing = !AsDropDown;
        }

        void DropDownTrueSyncDialogWindow_SizeChanged(object sender, SizeChangedEventArgs e)
        {
            UpdateLocation();
        }

        void UpdateLocation()
        {
            int taskBarYVirtualOffset = 50;
            var left = ButtonLeft + ButtonWidth - ActualWidth;
            var top = ButtonTop + ButtonHeight;

            left = (left >= 0) ? left : 0;
            left = (left + ActualWidth > SystemParameters.PrimaryScreenWidth) ? SystemParameters.VirtualScreenWidth - ActualWidth : left;

            top = (top >= 0) ? top : 0;
            top = ((top + (int)ActualHeight) >= SystemParameters.PrimaryScreenHeight - taskBarYVirtualOffset) ? (int)SystemParameters.VirtualScreenHeight - (int)ActualHeight - taskBarYVirtualOffset : top;

            Left = left;
            Top = top;
        }

        void TrueSyncDialogWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
        {
            Deactivated -= TrueSyncDialogWindow_Deactivated;
        }

        void TrueSyncDialogWindow_Deactivated(object sender, EventArgs e)
        {
            Close();
        }

        private void ImportSwitchButton_Click(object sender, RoutedEventArgs e)
        {
            SwitchDiscarded(importActive, importDiscarded, btnImportSwitch);
        }

        void SwitchDiscarded(Control activeConterol, Control discardedControl, Button switchButton)
        {
            if (activeConterol.Visibility == Visibility.Visible)
            {
                activeConterol.Visibility = Visibility.Collapsed;
                discardedControl.Visibility = Visibility.Visible;
                switchButton.Content = "View current activities";
                if (activeConterol == uploadActive) _vm.IsShowUploadDiscarded = true;
                else _vm.IsShowImportDiscarded = true;
            }
            else
            {
                activeConterol.Visibility = Visibility.Visible;
                discardedControl.Visibility = Visibility.Collapsed;
                if (activeConterol == uploadActive) _vm.IsShowUploadDiscarded = false;
                else _vm.IsShowImportDiscarded = false;                

                switchButton.Content = "View discarded activities";
            }
        }

        private void UploadSwitch_Click(object sender, RoutedEventArgs e)
        {
            SwitchDiscarded(uploadActive, uploadDiscarded, btnUploadSwitch);
        }

        public int ButtonLeft { get; set; }
        public int ButtonTop { get; set; }
        public bool AsDropDown { get; set; }
        public int ButtonWidth { get; set; }
        public int ButtonHeight { get; set; }

        public IEnumerable<FileMapActivity> ItemsToSkip
        {
            get { return _vm.ItemsToSkip; }
        }

        private void OwnWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
        {
            _vm.OnViewClosing();
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Views/ModuleView.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Net;
using System.Runtime.InteropServices;
using System.Threading;
using Com.Interwoven.WorkSite.iManage;
using CSOfficeRibbonAccessibility;
using Microsoft.Office.Core;
using Workshare.Components;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Presenter;
using Workshare.Components.Properties;
using Workshare.Components.Views;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.TrueSyncDialog;
using Workshare.Components.Views.TrueSyncUploadFilesDialog;
using Workshare.Components.WSLogger;
using Workshare.IManage.Contrete;
using Workshare.IManage.Presenter;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.WsProxies;

namespace Workshare.IManage.Views
{
    public class ModuleView: ModuleViewBase
    {
        ModuleBase _module;
        readonly WsProxy _wsProxy;

        public ModuleView(ModuleBase module, IWSIntegration integration)
            : base(integration)
        {
            _module = module;
            ActivieWindowHandle = Process.GetCurrentProcess().MainWindowHandle;
            _wsProxy = new WsProxy();
        }

        public virtual void OnTrueSyncItemsClicked(SyncItemsClickedArgs args, bool fromRibbon = false)
        {
            ((ModulePresenter)m_presenter).OnSyncItemsClicked(args, fromRibbon);
        }

        override public ModulePresenterBase CreatePresenter(IWSIntegration integration)
        {
            return new ModulePresenter(this);
        }

        int CHILDID_SELF = 0;

        TrueSyncDialogWindow dlg = null;

        internal void ShowTrueSyncDialog(CommandInvoker commandInvoker, IEnumerable<IDMSItem> items, Action<bool?, IEnumerable<FileMapActivity>> closed, bool fromRibbon)
        {
            if (dlg != null)
            {
                dlg.Close();
                dlg = null;
                return;
            }
            dlg = new TrueSyncDialogWindow(_module, commandInvoker, items, this);
          
            bool asDropDown=true;
            int left = 0, top = 0, width = 0, height = 0;
            if (fromRibbon)
            {
                try
                {
                    var topW = MSAAHelper.GetAccessibleObjectFromHandle(Process.GetCurrentProcess().MainWindowHandle);
                    var list = new List<IAccessible>();
                    IAccessible rre = MSAAHelper.GetAccessibleObjectByNameAndRole(topW, new System.Text.RegularExpressions.Regex("^Sync"), "push button", true);
                    if (rre == null)
                    {
                        Thread.Sleep(100);
                        rre = MSAAHelper.GetAccessibleObjectByNameAndRole(topW, new System.Text.RegularExpressions.Regex("^Sync"), "push button", true);
                    }                    

                    rre.accLocation(out left, out top, out width, out height, CHILDID_SELF);

                    Marshal.ReleaseComObject(topW);
                }
                catch (Exception ex)
                {
                    Logger.Write(ex, Severity.Error);
                    asDropDown = false;
                }
            }
            else
            {
                asDropDown = false;
            }

            dlg.Closed += (s, e) =>
            {
                if (closed != null)
                {
                    closed(((OwnWindow)s).OwnDialogResult, dlg.ItemsToSkip);
                }
                dlg = null;
            };

            if (asDropDown)
            {
                dlg.ButtonLeft = left ;
                dlg.ButtonTop = top ;
                dlg.ButtonWidth = width;
                dlg.ButtonHeight= height;
                dlg.AsDropDown = true;
                dlg.Show();
             
            }
            else
            {
                SetMainAsParent(dlg);
                dlg.AsDropDown = false;
                dlg.ShowDialog();
            }
        }

        private bool CheckDocModDuringLastAccess(ManFile doc)
        {
            if (!(DateTime.Compare(doc.m_document.AccessTime, doc.Modified) < 0))
            {
                TimeSpan interval = doc.m_document.AccessTime - doc.Modified;
                return (interval.CompareTo(new TimeSpan(0, 0, 2)) < 0);
            }
            return false;
        }

        private bool LocalFileWasChanged(ManFile doc)
        {
            if (!string.IsNullOrEmpty(doc.CheckoutPath))
            {
                // for checked out documents EditDate returns lastWriteTime for local file
                return DateTime.Compare(doc.EditDate, doc.Modified) == 0;
            }
            else
            {
                return false;
            }
        }

        public override void ShowFileSyncDialog(object file, EventOperation operation, string command)
        {   
            var act = new Action(() =>
            {
                if (file is IManDocument)
                {
                    Logger.Write("Start ShowFileSyncDialog", Severity.Information);
                    var doc = new ManFile(file as IManDocument);
                    var curversion = new ManFile(doc.m_document.Versions.ItemByIndex(doc.m_document.Version) as IManDocument);
                    var lastversionDoc = new ManFile(doc.m_document.Versions.ItemByIndex(doc.m_document.Versions.Count) as IManDocument);
                    var flds = doc.ParentFolders;
                    Logger.Write("Get required variables", Severity.Information);

                    if (!Application.iManInstance.Presenter.LoginIfNeeded())
                    {
                        return;
                    }

                    if (flds != null && flds.Any(i => IsFolderExist(i)))
                    {
                        Logger.Write("If at least one folder has been sent to Workshare", Severity.Information);
                        if (Application.iManInstance.Presenter.LoginIfNeeded())
                        {
                            var dlg = WSApplication.Instance.Module.Resolve<TrueSyncUploadFilesDialog>();

                            SetMainAsParent(dlg);

                            doc.Refresh();
                            dlg.Initiailize(doc);
                            Logger.Write("Show dialog", Severity.Information);
                            dlg.ShowDialog();
                        }
                    }
                    else
                    {
                        if (flds[0].ParentFolder != null)
                        {
                            Logger.Write("If noone parent folder has been sent to Workshare", Severity.Information);
                            var cFolder = GetSyncFolder(flds[0].ParentFolder);

                            if (cFolder != null)
                            {
                                if (Application.iManInstance.Presenter.LoginIfNeeded())
                                {
                                    if (operation == EventOperation.MoveFolder)
                                    {
                                        if (!IsFolderExist(cFolder)) return;
                                    }
                                    else
                                    {
                                        if (!IsFolderExist(flds[0].ParentFolder)) return;
                                    }

                                    var dlg = WSApplication.Instance.Module.Resolve<TrueSyncUploadFilesDialog>();

                                    SetMainAsParent(dlg);

                                    dlg.Initiailize(doc);
                                    dlg.ShowDialog();
                                }
                            }
                        }
                    }
                }
            });
            
            ExecuteInAppropriateThread(act);
        }

        private bool IsFolderExist(IDMSFolder folder)
        {
            try
            {
                if (folder != null)
                {
                    var sis = Application.iManInstance.Module.Resolve<SyncInfoService>();
                    var syncInfo = sis.GetSyncInfo(folder, false);
                    if (syncInfo != null)
                    {
                        return Workshare.Integration.WsProxies.WsProxy.IsFolderExist(WSApplication.Instance.AuthProvider.GetCurrentWSUser2(), syncInfo.ItemId);
                    }
                    else
                    {
                        return false;
                    }
                }
                else
                {
                    return false;
                }
            }
            catch (WebException ex)
            {
                if (ex.IsCloudFolderAccessDenied())
                    return true;
                else
                    throw;
            }
        }

        public IDMSFolder GetSyncFolder(IDMSFolder fld)
        {
            IDMSFolder folder = fld;

            if (folder != null)
            {
                if (Application.iManInstance.Module.Resolve<SyncInfoService>().GetSyncInfo(folder) != null)
                {
                    return folder;
                }
                return GetSyncFolder(folder.ParentFolder);
            }

            return null;
        }
    }

}
<file_sep>/WSComponents/src/WSIntegration/SyncInfo/Factory.cs
﻿using Workshare.Integration.Interfaces;

namespace Workshare.Integration.SyncInfo
{
    class Factory:ISyncInfoFactory
    {
        public ISyncInfo CreateFileInfo()
        {
            return new FileSyncInfo();
        }

        public ISyncInfo CreateFolderInfo()
        {
            return new FolderSyncInfo();
        }

        public IVersionSyncInfo CreateVersionInfo()
        {
            return  new VersionInfo();
        }

        public ISendDataInfo CreateSendDataInfo()
        {
            return new SendDataInfo();
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshate.HookEvents/HookMoveContentsCmd.cs
﻿using System;
using System.Collections;
using System.Diagnostics;
using System.Runtime.InteropServices;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.Worksite.iManExt2;
using Workshare.Components.Interfaces;
using Workshare.Components.WSLogger;

namespace Workshare.HookEvents
{
    [ClassInterface(ClassInterfaceType.None)]
    [Guid("44B80FA0-1E93-45D3-8A56-C2E03D83DA8E")]
    [ComVisible(true)]
    public class HookMoveContentsCmd : ICommand, Com.Interwoven.Worksite.iManExt2._ICommandEvents_Event
    {
        IManMoveContentsCmd cmd;

        bool isCancel = true;

        public HookMoveContentsCmd()
        {
            cmd = new IManMoveContentsCmd();
            cmd.OnCancel += cmd_OnCancel;
            cmd.OnInitDialog += cmd_OnInitDialog;
            cmd.PostOnOK += cmd_PostOnOK;
            cmd.PreOnOK += cmd_PreOnOK;
        }

        public int Accelerator
        {
            get
            {
                return cmd.Accelerator;
            }
            set
            {
                cmd.Accelerator = value;
            }
        }

        public object Bitmap
        {
            get
            {
                return cmd.Bitmap;
            }
            set
            {
                cmd.Bitmap = value;
            }
        }

        public ContextItems Context
        {
            get
            {
                return cmd.Context;
            }
        }

        public void Execute()
        {
            cmd.Execute();
            if (!isCancel)
            {
                try
                {
                    ProcessIManageEvents.ProcessEvent(Context, EventOperation.MoveFile, "HookMoveContentsCmd -> Execute");
                }
                catch (Exception exc)
                {
                    Logger.Write(exc, Severity.Error);
                }
            }
        }

        public string HelpFile
        {
            get
            {
                return cmd.HelpFile;
            }
            set
            {
                cmd.HelpFile = value;
            }
        }

        public int HelpID
        {
            get
            {
                return cmd.HelpID;
            }
            set
            {
                cmd.HelpID = value;
            }
        }

        public string HelpText
        {
            get
            {
                return cmd.HelpText;
            }
            set
            {
                cmd.HelpText = value;
            }
        }

        public void Initialize(ContextItems Context)
        {
            cmd.Initialize(Context);
        }

        public string MenuText
        {
            get
            {
                return cmd.MenuText;
            }
            set
            {
                cmd.MenuText = value;
            }
        }

        public string Name
        {
            get
            {
                return cmd.Name;
            }
            set
            {
                cmd.Name = value;
            }
        }

        public int Options
        {
            get
            {
                return cmd.Options;
            }
            set
            {
                cmd.Options = value;
            }
        }

        public int Status
        {
            get
            {
                return cmd.Status;
            }
            set
            {
                cmd.Status = value;
            }
        }

        public Commands SubCommands
        {
            get
            {
                return cmd.SubCommands;
            }
            set
            {
                cmd.SubCommands = value;
            }
        }

        public string Title
        {
            get
            {
                return cmd.Title;
            }
            set
            {
                cmd.Title = value;
            }
        }

        public CommandType Type
        {
            get
            {
                return cmd.Type;
            }
            set
            {
                cmd.Type = value;
            }
        }

        public void Update()
        {
            cmd.Update();
        }

        void cmd_PreOnOK(object pMyInterface)
        {
            isCancel = false;
            if (PreOnOK != null)
            {
                PreOnOK(pMyInterface);
            }
        }

        void cmd_PostOnOK(object pMyInterface)
        {
            if (PostOnOK != null)
            {
                PostOnOK(pMyInterface);
            }
        }

        void cmd_OnInitDialog(object pMyInterface)
        {
            if (OnInitDialog != null)
            {
                OnInitDialog(pMyInterface);
            }
        }

        void cmd_OnCancel(object pMyInterface)
        {
            isCancel = true;
            if (OnCancel != null)
            {
                OnCancel(pMyInterface);
            }
        }

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_OnCancelEventHandler OnCancel;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_OnInitDialogEventHandler OnInitDialog;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_PostOnOKEventHandler PostOnOK;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_PreOnOKEventHandler PreOnOK;

    }
}
<file_sep>/WSComponents/src/WSComponents/Interfaces/IModulePresenter.cs
﻿using System.Collections.Generic;
using Workshare.Components.Common;
using Workshare.Components.Views.Common;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using WorksharePlatform;

namespace Workshare.Components.Interfaces
{
    public interface IModulePresenter
    {
        bool IsAnyItemInProgress();
        void OnSendItemsClicked(SendItemsClickedArgs args);
        void OnSyncItemsClicked(SyncItemsClickedArgs args);
        void OnCollaborationItemsClicked(CollaborationItemsClickedArgs args);
        WorkUnit GetSendCommand(IEnumerable<IDMSItem> items, IEnumerable<FileMapActivity> itemsToSkip, int destFolderId, CheckOutOptions option);
        bool LoginIfNeeded();
        DialogSettings GetCurrentDialogSettings(UserDetails user);
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Services/DmsWorkerBase.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;
using WorksharePlatform;

namespace Workshare.Integration.Processor.Strategies
{
    public abstract class DmsWorkerBase
    {
        public abstract void ImportNewFile(NewFileOptions options);

        public abstract void ImportNewVersion(NewVersionsOptions options);

        public abstract void RelateDocument(IDMSFile mainFile, IDMSFile relatedFile, string p);

        public abstract IDMSFolder CreateSubFolder(IDMSFolder folder, NewFolderOptions options);

        /// <summary>
        /// Returns name with extension of file
        /// </summary>
        /// <param name="dmsVersion"></param>
        /// <returns></returns>
        public abstract string GetName(IDMSFile iDMSFile);

        public abstract string GetFilePath(IDMSFile iDMSFile);

        public abstract string GetFilePath(IDmsVersion dmsVersion);

        /// <summary>
        /// Returns name with extension of version
        /// </summary>
        /// <param name="dmsVersion"></param>
        /// <returns></returns>
        public abstract string GetName(IDmsVersion dmsVersion);

        /// <summary>
        /// Returns friendly name (without extension ) of version
        /// </summary>
        /// <param name="dmsVersion"></param>
        /// <returns></returns>
        public abstract string GetFriendlyName(IDmsVersion dmsVersion);

        /// <summary>
        /// Returns friendly name for _folder
        /// </summary>
        /// <param name="dmsVersion"></param>
        /// <returns></returns>
        public abstract string GetFriendlyName(IDMSFolder folder);

        public abstract DateTime GetEditTime(IDmsVersion dmsVersion);
        public abstract DateTime GetEditTime(IDMSFile dmsFile);

        public abstract IEnumerable<BaseDMSItem> GetParents(BaseDMSFile item);

        public abstract string GetFriendlyName(IDMSFile iDMSFile);

        public abstract void CanImportNewVersionOrThrow(IDMSFile dmsFile);

        public abstract void CanImportNewFileOrThrow(NewFileOptions options);

        public abstract void AddHistory(IDmsVersion dmsVersion, string eventName, string comment, Operations operation);

        public abstract void CanUpdateFileOrThrow(IDMSFile localFile, Operations operation);

        public abstract void CanUpdateFolderOrThrow(IDMSFolder localFolder);

        public abstract void CanUpdateVersionOrThrow(IDmsVersion localVersion, Operations operation);

        public abstract void UnlockIfNotEdited(IDMSFile localFile);
    }

    public class NewFolderOptions
    {
        public WsFolder WsFolder { set; get; }
    }

    public class NewFileOptions
    {
        public WsFile WsFile { set; get; }
        public IDMSFolder ParentFolder { set; get; }
        public IDMSFile BasedOnFile { set; get; }
        public IDMSFile CreatedFile { set; get; }
        public IEnumerable<CreateversionInfo> VersionList { set; get; }
    }

    public class NewVersionsOptions
    {
        public WsFile WsFile { set; get; }
        public IDMSFile File { set; get; }
        public IEnumerable<CreateversionInfo> VersionList { set; get; }
    }

    public class CreateversionInfo
    {
        public string FriendlyName;
        public string FilePath;
        public IEnumerable<Activity> Activities;
        public WsFile file;
        public WsVersion version;
        public IDmsVersion createdVersion;
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Visitors/UploadActivityFinder.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Integration.Processor.Changes.Visitors
{
    class UploadActivityFinder : ItemMapVisitor
    {
        public IEnumerable<string> ActivitiesToUpdate = null;

        readonly DiscardedService _discardedService;
        readonly ChangesDetector _detector;
        private readonly DmsWorkerBase _dmsWorker;
        public UploadActivityFinder(DiscardedService discardedService, ChangesDetector detector, DmsWorkerBase dmsWorker)
        {
            this._discardedService = discardedService;
            
            _detector = detector;
            _dmsWorker = dmsWorker;
            _options=new ActivityFinder.Options();
        }


        public List<UploadFileActivity> FoundedActivities = new List<UploadFileActivity>();

        private ActivityFinder.Options _options;
        public ActivityFinder.Options Options
        {
            get
            {
                return _options;
            }
            set
            {
                _options = value ?? new ActivityFinder.Options();
            }
        }

        public override bool VisitEnter(FileMap fileMap)
        {
            return true;
        }


        public void UpdateState(UploadFileActivity activity, FileMap fileMap)
        {
            if (fileMap.ProcessState == ProcessState.Error)
            {
                if (fileMap.Error is FileCheckoutedToAnotherUser)
                {
                    activity.State = UploadFileActivityState.CheckedOutToAnother;
                    activity.CheckedOutTo = ((FileCheckoutedToAnotherUser)fileMap.Error).UserName;
                }
                else if (fileMap.Error is CheckedOutOnAnotherMachine)
                {
                    activity.State = UploadFileActivityState.CheckedOutOnAnotherMachine;
                    activity.CheckOutMachine = ((CheckedOutOnAnotherMachine)fileMap.Error).MachineName;
                }
                else if (fileMap.Error.IsCloudFolderAccessDenied())
                {
                    activity.State = UploadFileActivityState.NoAccessOnWorkshare;
                }
                else
                {
                    activity.State = UploadFileActivityState.Error;
                    activity.Error = fileMap.Error;
                }
            }
            else if (fileMap.ProcessState == ProcessState.Processed)
            {
                if (activity.State == UploadFileActivityState.Uploading)
                {
                    activity.State = UploadFileActivityState.Uploaded;
                }
            }
            else if (fileMap.ProcessState == ProcessState.Scanned)
            {
                activity.State = UploadFileActivityState.Scanned;
            }
            else if (fileMap.ProcessState == ProcessState.Cancelled)
            {
                activity.State = UploadFileActivityState.Scanned;
            }
        }

        public override void Visit(FileMap fileMap)
        {
            var existed = FoundedActivities.FirstOrDefault(a => a.MapId == fileMap.Id);
            if (existed != null && Options.DoNotUpdate) return;
            var uploadFileActivity = existed ?? new UploadFileActivity();
            _detector.opt = new DetectorOptions() { UseForceRequest = _options.UseForceRequest };
            _discardedService.options = new DiscardedServiceOptions() { UseForceRequest = _options.UseForceRequest };
            try
            {
                if (ActivitiesToUpdate == null || ActivitiesToUpdate.Contains(uploadFileActivity.Id))
                {
                    uploadFileActivity.Refresh(fileMap, _dmsWorker);

                    uploadFileActivity.ClearChanges();

                    UpdateState(uploadFileActivity, fileMap);

                    _detector.AddFolderSharedIfDetected(uploadFileActivity, fileMap);

                    _detector.AddLastUnSentOrChangedVersionIfDetected(uploadFileActivity, fileMap);

                    uploadFileActivity.IsDiscarded = _discardedService.IsDiscarded(uploadFileActivity);

                    this.RefreshAction(uploadFileActivity);
                }

                if (!FoundedActivities.Contains(uploadFileActivity) && ShouldDetectActivity(uploadFileActivity))
                {
                    FoundedActivities.Add(uploadFileActivity);
                }
            }
            catch (Exception ex)
            {
                uploadFileActivity.Error = ex;
                uploadFileActivity.State = UploadFileActivityState.Error;
            }
        }

        public virtual bool ShouldDetectActivity(UploadFileActivity activity)
        {
            return true;
        }

        private void RefreshAction(UploadFileActivity activity)
        {
            activity.Actions = new List<ItemMapActivityAction>();
            if (activity.State == UploadFileActivityState.Error
                || activity.State == UploadFileActivityState.Uploaded
                || activity.State == UploadFileActivityState.Uploading)
            {
                //if we uploaded file by discarded activity we need to remove this activity from list of discarded activities on WDS
                //otherwise - if user delete the file from workshare the 'true sync' dialog will show upload activity as discarded
                if (activity.IsDiscarded == false && activity.State == UploadFileActivityState.Uploaded)
                {
                    UploadFileActivity oldDiscardedActivity = new UploadFileActivity() { WsId = "-1", DmsFileId = activity.DmsFileId, Type = activity.Type };
                    if (_discardedService.IsDiscarded(oldDiscardedActivity))
                        _discardedService.Remove(oldDiscardedActivity);
                }

                return;
            }

            var versionToUpload = activity.Changes.FirstOrDefault(a => a.Type == ChangeType.NotSentVersion || a.Type == ChangeType.VersionChangedAfterSend);

            if (versionToUpload!=null)
            {
                var upload = new UploadDocumentAction(activity, "Upload");
                upload.VersionIds.Add(versionToUpload.LocalVersionId);
                activity.Actions.Add(upload);
            }
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Contrete/ManFolder.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Web.Script.Serialization;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components.Common;
using Workshare.Components.Concrete;
using Workshare.Components.Exceptions;
using Workshare.Components.WSLogger;
using Workshare.Integration.SyncInfo;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.WsProxies;
using WorksharePlatform;
using ActionType = Workshare.Integration.Processor.Services.ActionType;
using Permissions = Workshare.Integration.Enums.Permissions;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.IManage.Contrete
{
    class ManFolder : BaseDMSFolder, IDMSFolder
    {
        internal IManFolder m_folder;
        public ManFolder(IManFolder folder)
        {
            m_folder = folder;
            InitializeName();
        }

        private void InitializeName()
        {
            _name = m_folder.Name ?? null;
        }

        private ManFile DisplayImportDialog(WorksharePlatform.FileDetails file)
        {
            var dlg = Application.Instance.Module.Resolve<ImportDialog>();
            dlg.Initialize(this, file.FilePath, file.FriendlyName ?? file.Name, m_folder.Database);
            dlg.ShowDialog();
            return dlg.AddedFile;
        }

        public IDMSFolder RootFolder()
        {
            return new ManFolder(m_folder.Database.Root);
        }

        public IDMSFile AddFile(WorksharePlatform.FileDetails file, List<Activity> actnivities,IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool updateSyncInfoForVersions = true)
        {
            var a = true;

            return AddFile(file, out a, actnivities, versionIdsToSkip,useProfileDialog, SyncVerOption, StartVersion,updateSyncInfoForVersions);
        }

        //this method should be avoided to use 
        public IDMSFile AddFile(WorksharePlatform.FileDetails file, out bool added, List<Activity> actnivities, IEnumerable<string> versionIdsToSkip, bool useProfileDialog = false, ConflictVersionOptions SyncVerOption = ConflictVersionOptions.Latest, int StartVersion = 2, bool updateSyncInfoForVersions = true)
        {
            Logger.Write("Adding document to folder", Severity.Trace);
            added = false;
            try
            {
                //var actnivities = PlatformService.GetFileActivitiesImanage(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.FolderId, file.Id);

                if (SyncVerOption == ConflictVersionOptions.All)
                {
                    file.DeleteFile();
                    file.FilePath = PlatformService.DownloadFileVersion(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.Id, StartVersion);
                }
                else
                {
                    var firstVersionToImport =
                        file.Versions.OrderBy(a => a.Version)
                            .LastOrDefault(a => !ManFile.ShouldSkip(versionIdsToSkip, a)) ?? file.CurrentVersion;

                    file.DeleteFile();
                    file.FilePath = PlatformService.DownloadFileVersion(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.Id, firstVersionToImport.Version);
                }

                var createdFile = DisplayImportDialog(file);
                added = createdFile != null;
                if (updateSyncInfoForVersions && added)
                {
                    var version = SyncVerOption == ConflictVersionOptions.All ? file.Versions.FirstOrDefault(v => v.Version == StartVersion) : file.Versions.OrderBy(a=>a.Version).LastOrDefault();
                    if (version != null)
                    {
                            
                        GetService().UpdateSyncInfo(createdFile.GetVersions().First(),
                            new ActionContext(ActionType.Import)
                            {
                                WsVersion = new WsVersion(version, null)
                            });
                    }
                }

                if (createdFile != null)
                {
                    if (SyncVerOption == ConflictVersionOptions.All)
                    {
                        if (!createdFile.CheckedOut)
                        {
                            createdFile.GetFileToCheckout();
                        }

                        /// TODO: REMOVE THAT IN FUTURE
                        if (StartVersion == 2)
                        {
                            createdFile.AddHistories(actnivities.Where(x => x.CurrentVersion == 1).ToList());
                        }
                        createdFile.AddHistories(actnivities.Where(x => x.CurrentVersion == StartVersion).ToList());

                        foreach (var ver in file.Versions.Where(x => x.Version > StartVersion && !ManFile.ShouldSkip(versionIdsToSkip,x)).OrderBy(x => x.Version).ToArray())
                        {
                            file.DeleteFile();
                            file.FilePath = PlatformService.DownloadFileVersion(Application.iManInstance.AuthProvider.GetCurrentWSUser(), file.Id, ver.Version);

                            var veriosn = (ManVersion)createdFile.GetLatest().AddVersion(file.FilePath, file, actnivities.Where(x => x.CurrentVersion == ver.Version).ToList());
                            if (updateSyncInfoForVersions)
                            {                                
                                GetService().UpdateSyncInfo(veriosn,new ActionContext(ActionType.Import)
                                {
                                    WsVersion = new WsVersion(ver, null)
                                });
                                //veriosn.UpdateSyncInfo2(new WsVersion(ver,null));
                            }
                        }
                    }
                    else if (SyncVerOption == ConflictVersionOptions.Latest)
                    {
                        createdFile.AddHistories(actnivities);
                    }
                    return createdFile.GetLatest();
                }
                else 
                {
                    return null;
                }
                
            }
            catch (FileNotCreatedException)
            {
                throw;
            }
            catch (Exception ex)
            {
                throw new FileNotCreatedException(ex.Message, ex);
            }
        }

        public IDMSFolder AddSubFolder(WorksharePlatform.FolderDetails cloudFolder)
        {
            try
            {
                if (cloudFolder == null) throw new ArgumentNullException("cloudFolder");
                var objDocFolders = (IManDocumentFolders)m_folder.SubFolders;
                var objDocFolder = objDocFolders.AddNewDocumentFolderInheriting(cloudFolder.Name, "");

                //Get location of folder in Workspace layout
                objDocFolder.Location.Cell = "column0";
                objDocFolder.Location.Order = 1;

                var createdFolder = new ManFolder(objDocFolder);
             //   createdFolder.UpdateSyncInfo(cloudFolder, true);
                GetService().UpdateSyncInfo(createdFolder,new ActionContext(ActionType.Import)
                {
                    WsFolder = new WsFolder(cloudFolder,null)
                });
                m_folder.Refresh();
                return createdFolder;
            }
            catch (Exception ex)
            {
                throw new FolderNotCreatedException(string.Format(RES.STR_CANNOT_ADD_NEW_FOLDER_ERROR_F, cloudFolder.Name, ex.Message));
            }
        }

        public BaseDMSFolder AddSubFolder2(string name)
        {
            var objDocFolders = (IManDocumentFolders)m_folder.SubFolders;
            var objDocFolder = objDocFolders.AddNewDocumentFolderInheriting(name, string.Empty);
            return new ManFolder(objDocFolder);
        }

        public bool IsDeleted 
        {
            get
            { 
                try
                {
                    int id = this.m_folder.FolderID;
                    return false;
                }
                catch
                {
                    return true;
                }
            }
        }

        public bool WasUpdatedAfterSend(ISyncInfo synhInfo)
        {
            return false;
        }

        public bool WasUpdatedAfterSend2(bool useForceRequest = true)
        {
            return false;
        }

        public IDMSItemID ID
        {
            get { return new ManItemID(m_folder); }
        }

        public int DMSId
        {
            get 
            {
                return m_folder.FolderID;
            }
        }

        string _name = null;
        public string Name
        {
            get
            {
                if (string.IsNullOrEmpty(_name))
                {
                    InitializeName();
                }
                return _name;
            }
            set
            {
            }
        }
        public string Description
        {
            get
            {
                return m_folder.Description;
            }
            set
            {
            }
        }

        public bool DoesUserHavePermissions(imAccessRight permissions)
        {
            return (m_folder.EffectiveAccess & permissions) == permissions;
        }

        private bool IsSpecialFolder()
        {
            return (m_folder!=null && m_folder.Parent == null && (m_folder.ObjectID.ToLower().Contains("rootfavoritesfolder") || m_folder.ObjectID.ToLower().Contains("subscriptionfolder"))) ? true : false;
        }

        public bool DoesUserHavePermissions(Permissions permissions)
        {
            if (m_folder == null || m_folder.FolderID < 0 || IsSpecialFolder() || (m_folder.Workspace!=null && m_folder.Workspace.FolderID == m_folder.FolderID) )
            {
                return false;
            }
            else
            {
                switch (permissions)
                {
                    case Permissions.EditItem: return (m_folder.EffectiveAccess & imAccessRight.imRightReadWrite) == imAccessRight.imRightReadWrite;
                }
                return true;
            }
        }

        public bool CheckedOutToUser
        {
            get { return true; }
        }

        public bool CheckedOut
        {
            get { return true; }
        }


        public string DisplayName
        {
            get
            {
                return m_folder.Name;
            }
            set
            {
            }
        }

        public IEnumerable<IDMSFolder> SubFolders
        {
            get
            {
                var list = new List<IDMSFolder>();
                foreach (IManFolder subFolder in m_folder.SubFolders)
                {
                    list.Add(new ManFolder(subFolder));
                }
                return list;
            }
            set
            {
            }
        }

        public IEnumerable<IDMSFile> Files
        {
            get
            {
                var list = new List<IDMSFile>();
                foreach (object content in m_folder.Contents)
                {
                    if (content is IManDocument)
                    {
                        list.Add(new ManFile((IManDocument)content, m_folder));
                    }
                }
                return list;
            }
            set
            {
            }
        }

        public IDMSFolder ParentFolder
        {
            get
            {
                if (m_folder.Parent != null)
                {
                    return new ManFolder(m_folder.Parent);
                }
                return null;
            }
        }


        public void OnBeforeSending(OperationContext context)
        {
        }

        private SyncInfoService GetService()
        {
            return WSApplication.Instance.Module.Resolve<SyncInfoService>();
        }

        public void OnSendError(object args, Exception e)
        {
            
        }

        public void UpdateDisplayName(string name)
        {
            
        }

        public void OnAfterAdd(OperationContext args)
        {
            
        }


        public void OnAfterSending(OperationContext context)
        {

        }


        public void OnBeforeSync(OperationContext args)
        {
        }


        public void AddHistory(string eventName, string eventComment, Workshare.Integration.Operations operation)
        {
        }

        public void AddHistories(List<Activity> activities)
        {
        }

        public override string ToString()
        {
            return string.Format("Folder with ID={0}, Name={1}", ID, DisplayName);
        }

        internal bool HasRightToAddNewFiles()
        {
            return true;
        }

        public string DMSItemKey
        {
            get { return m_folder == null ? "" : Application.iManInstance.ServerKey +":!DatabaseName:"+ m_folder.Database.Name + ":!Folder:" + this.DMSId.ToString(); }
        }
    }

}
<file_sep>/WSComponents/src/WSComponents/Common/WorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Text;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Common
{
    public enum WorkStatus
    {
        Unknown,
        Pending,
        Success,
        Processing,
        Error
    }

    public class WorkUnit : BasePropertyChanged<WorkUnit>, IWorkUnit
    {
        public event EventHandler<WorkUnitErrorEventArgs> OnError;

        protected WorkUnit(IModuleView view)
        {
            _view = view;
            TargetItems = new TargetItem[0];
            this.Name = "Work unit";
        }


        protected readonly IModuleView _view;

        public virtual void Execute()
        {
        }

        private WorkStatus _status;

        public virtual WorkStatus Status
        {
            get { return _status; }
            set
            {
                if (_status != value)
                {
                    _status = value;
                    PropertyHasChanged(p => p.Status);
                    PropertyHasChanged(p => p.StatusDescription);
                }
            }

        }

        public string Name
        {
            get; protected set;
        }

        public TargetItem[] TargetItems
        {
            get; protected set;
        }

        private string _statusDescription;

        public string StatusDescription
        {
            get
            {
                return _statusDescription;
            }
            set
            {
                if (_statusDescription != value)
                {
                    _statusDescription = value;
                    PropertyHasChanged(p => p.StatusDescription);
                }
            }
        }

        protected void ExecuteIntegration(Action action)
        {
            try
            {
                try
                {
                    action();
                }
                catch (Exception ex)
                {
                    if (OnError != null)
                    {
                        var args = new WorkUnitErrorEventArgs(this, ex);
                        OnError(this, args);
                        if (!args.Handled) throw;
                    }
                }
            }
            catch (MultiItemsException ex)
            {
                if (ex.errorList.AsQueryble().Any(p => p.Error is CloudUnAuthorized))
                {
                    WSApplication.Instance.AuthProvider.SetCurrentUser(null);
                }
                var sb = new StringBuilder();
                ex.errorList.AsQueryble()
                    .ToList()
                    .ForEach(p => sb.AppendLine(p.Item != null ? p.Item.DisplayName + " : " : "" + p.Error.Message));
                _view.ShowError(sb.ToString());
            }
            catch (CloudUnAuthorized ex)
            {
                WSApplication.Instance.AuthProvider.SetCurrentUser(null);
                _view.ShowError(ex.Message);
            }
            catch (Exception ex)
            {
                _view.ShowError(ex.Message);
            }
        }


        public virtual void OnAdded()
        {
        }


        public string ItemName
        {
            get; set;
        }
    }

    public class WorkUnitErrorEventArgs : EventArgs
    {
        public WorkUnitErrorEventArgs(IWorkUnit unit, Exception error)
        {
            Error = error;
            WorkUnit = unit;
        }

        public Exception Error { get; private set; }
        private IWorkUnit WorkUnit { get; set; }
        public bool Handled { set; get; }
    }

    public class TrueSynhWorkUnit : WorkUnit
    {
        private readonly IEnumerable<IDMSItem> _items = new List<IDMSItem>();

        public TrueSynhWorkUnit(IModuleView view, IEnumerable<SyncItemInformation> items)
            : base(view)
        {
            Name = RES.STR_WORK_STATUS_SYNCHRONIZATION_TEXT;
            _items = items.Where(e => e.item != null).Select(a => a.item);
            TargetItems = _items.Where(s => s != null).Select(f => new TargetItem(f.ID.ToString())
            {
                Name = f.Name
            }).ToArray();
            var itemsText = "Files:";
            _items.ToList().ForEach(p => itemsText += Environment.NewLine + p.DisplayName);
            StatusDescription = string.Format(itemsText);
        }

        private bool ShouldBeProcessed(ImportFileActivity activity)
        {
            return activity.Changes.Any(a => a.Type == ChangeType.BothChanged
                                             || a.Type == ChangeType.RemoteAdded
                                             || a.Type == ChangeType.RemoteChanged);
        }

        public override void Execute()
        {
            try
            {
                var processor = WSApplication.Instance.Module.Resolve<Processor>();
                SummaryProcessResult scanResult = processor.DirectScanFile(_items.OfType<BaseDMSFile>());
                if (scanResult == null) return;
                var activityFinder = WSApplication.Instance.Module.Resolve<ActivityFinder>();
                var activities = activityFinder.GetImportActivities(scanResult, null);
                var errors = activityFinder.GetErrors(scanResult);
                if (errors.Any())
                {
                    string errMsg = string.Empty;
                    List<string> listMsg = new List<string>();

                    errors.ForEach(e => 
                        {
                            string msg;
                            if (!string.IsNullOrEmpty(errMsg))
                                errMsg += Environment.NewLine;

                            if (e.Error is WebException && (e.Error as WebException).IsStatusCode(HttpStatusCode.Forbidden))
                                msg = RES.STR_YOU_DONT_HAVE_PERMISSION + activities.First(a => a.MapId.Equals(e.Id, StringComparison.OrdinalIgnoreCase)).Filename;
                            else
                                msg = e.Error.Message;

                            if (!listMsg.Contains(msg))
                            {
                                errMsg += msg;
                                listMsg.Add(msg);
                            }
                        });

                    _view.ShowError(new BaseException(RES.STR_UNABLESYNC_CAPTION, errMsg));
                }
                else
                {
                    var activitiesToProcess =
                        activities
                            .Where(ShouldBeProcessed)
                            .Where(a => a.GetAllAvailableActions().Any())
                            .ToList();
                    var deletedFiles =
                        activities.Where(a => a.Changes.Any(c => c.Type == ChangeType.RemoteDeleted)).ToList();
                    if (deletedFiles.Any())
                    {
                        _view.ShowErrors(deletedFiles.Select(a => new ItemException()
                        {
                            Item = a.DmsFile,
                            Error = new CloudFileNotFound(Integration.Properties.Resources.STR_UNABLE_SYNC)
                        }));
                        var syncInfo = WSApplication.Instance.Module.Resolve<SyncInfoService>();
                        foreach (var deletedFile in deletedFiles)
                        {
                            deletedFile.DmsFile.AddHistory("FileDeletedOrMoved", "Synced from Workshare on " + DateTime.Now.ToString(Activity.TimeFormat) + ". File has been deleted or moved", Operations.Sync);
                            syncInfo.BreakLink(deletedFile.DmsFile);
                        }
                    }
                    if (activitiesToProcess.Any())
                    {
                        var actions = _view.SelectActions(activitiesToProcess);
                        var processOptions = new ProcessOptions();
                        processOptions.ActionsToApply.AddRange(actions.OfType<ItemMapActivityAction>());
                        scanResult = processor.Process(scanResult, processOptions);
                        activityFinder.UpdateImportActivities(scanResult, activitiesToProcess);
                        var processErrors = activitiesToProcess.Where(a => a.InKindOfErrorState()).ToList();
                        if (processErrors.Any())
                        {
                            _view.ShowErrors(
                                processErrors.ConvertAll(
                                    e => new ItemException {Error = e.Error ?? new Exception(e.State.ToString()), Item = e.DmsFile}));
                        }
                    }
                }
            }

            catch (Exception ex)
            {
                Logger.WriteError(ex);
                _view.ShowError(ex.Message);
            }
        }
    }

    public class SendWorkUnit : WorkUnit
    {
        private readonly IEnumerable<IDMSItem> _mItems = new List<IDMSItem>();
        private readonly int _mDestinationFolderId = -1;
        private readonly CheckOutOptions _mCheckOutOption;

        public SendWorkUnit(IModuleView view, IEnumerable<IDMSItem> items, int destFolderId, CheckOutOptions option)
            : base(view)
        {
            _mItems = items;
            _mDestinationFolderId = destFolderId;
            _mCheckOutOption = option;
            Name = RES.STR_WORK_STATUS_SENDING_TEXT;
            TargetItems = items.Select(a => new TargetItem(a.ID.ToString())
            {
                Name = a.Name
            }).ToArray();

            var itemsText = "Files:" + Environment.NewLine;
            _mItems.ToList().ForEach(p => itemsText += p.DisplayName + Environment.NewLine);
            var val = StatusDescription;
            this.StatusDescription = string.Format(val + Environment.NewLine + itemsText);

        }

        public override void Execute()
        {
            ExecuteIntegration(() =>
            {
                var operationContext = new OperationContext(_mCheckOutOption);
                try
                {
                    Logger.Write("SendWorkUnit::Execute START", Severity.Information);
                    WSApplication.Instance.Integration.SendItems(_mItems,
                        new FolderDetails {Id = _mDestinationFolderId}, operationContext);
                }
                catch (MultiItemsException)
                {
                    throw;
                }
                catch (Exception ex)
                {
                    var itemCollection = new ItemsErrorsCollection(operationContext);
                    _mItems.ToList().ForEach(localItem => itemCollection.Add(localItem, ex));
                    itemCollection.Check();
                    throw;
                }
            });
        }
    }
}


<file_sep>/WSComponents/src/WSIntegration/Processor/Services/DiscardedService.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using System.Threading;
using System.Web.Script.Serialization;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Services
{
    public class DiscardedService
    {
        #region Nested Types
        class DataEntry
        {
            public string Id { set; get; }
            public long WsDateTick { set; get; }
            public long LocalEditDateTick { set; get; }
        }

        class DataEnties : IWebDataStorageData
        {
            List<DataEntry> _entries = new List<DataEntry>();

            public string DataType
            {
                get
                {
                    return "DMSUserCache";
                }
                set
                {
                }
            }

            public List<DataEntry> Entries
            {
                get { return _entries; }
                set { _entries = value; }
            }
        }

        #endregion
        
        private IAuthProvider _auth = null;
        private const string Delimiter = "|||";
        WebDataStorageService _wdsService;
        public DiscardedServiceOptions options;
        DataEnties _entries = new DataEnties();

        public DiscardedService(IAuthProvider auth_provider, WebDataStorageService wdsService)
        {
            _auth = auth_provider;
            _wdsService = wdsService;
            options = new DiscardedServiceOptions() { UseForceRequest = false };
            GetCahce();
        }

        void UpdateCahce()
        {
            try
            {
                var s_z = new JavaScriptSerializer();
                string _data = s_z.Serialize(_entries);
                _wdsService.AddUserData(_entries.DataType, _data, DateTime.MinValue);
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error during write cahce data to Web data storage", ex);
                //throw;
            }
        }

        void GetCahce()
        {
            try
            {
                var s_z = new JavaScriptSerializer();
                string _data = _wdsService.GetUsertData(_entries.DataType, DateTime.MinValue, options.UseForceRequest);
                
                if (!string.IsNullOrEmpty(_data))
                {
                    _data = _data.Replace("/Date(", "\\/Date(").Replace("/\"", "\\/\"");
                    _entries = s_z.Deserialize<DataEnties>(_data);
                }
                
            }
            catch (Exception ex)
            {
                Logger.WriteError("Error during get cahce data to Web data storage", ex);
                //throw;
            }
        }

        void RemoveLocally(FileMapActivity item)
        {
            var s = new DataEntry
            {
                Id = GetIdForActivity(item)
            };
            
            _entries.Entries.RemoveAll(p => Compare(s, p));
        }

        bool Compare(DataEntry item1, DataEntry item2)
        {
            return item1.Id == item2.Id;
        }

        string CreateCacheItem(DataEntry item)
        {
            return string.Format("{1}{0}{2}{0}{3}{4}", Delimiter, item.Id, item.WsDateTick, item.LocalEditDateTick, Environment.NewLine);
        }

        DataEntry AddLocally(FileMapActivity item)
        {
            var s = new DataEntry
            {
                Id = GetIdForActivity(item),
                WsDateTick = item.WsLastUpdateDate.Ticks,
                LocalEditDateTick = item.LocalEditTime.Ticks
            };
            _entries.Entries.Add(s);
            return s;
        }

        public bool IsDiscarded(FileMapActivity item)
        {
            var Id = GetIdForActivity(item);
            var entry = _entries.Entries.LastOrDefault(a => a.Id == Id);

            if (entry == null)
            {
                return false;
            }
            return item.WsLastUpdateDate.Ticks <= entry.WsDateTick && item.LocalEditTime.Ticks <= entry.LocalEditDateTick;
        }

        public void Add(FileMapActivity item)
        {
            var s = AddLocally(item);
            UpdateCahce();
        }

        public void Remove(FileMapActivity item)
        {
            RemoveLocally(item);
            UpdateCahce();
        }

        public void Refresh()
        {
            Logger.WriteTrace(string.Format("Refresing Discarded service."));
            GetCahce();
        }

        private string GetIdForActivity(FileMapActivity item)
        {
            //if you change forming of Id don't forget to change deleting discarded activity in UploadActivityFinder.RefreshAction
            return string.Format("{0}---{1}---{2}", item.WsId, item.DmsFileId, item.Type);
        }
    }

    public class DiscardedServiceOptions
    {
        public bool UseForceRequest { get; set; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/VMs/DocumentActionVm.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes.Activities;

namespace Workshare.Components.Views.TrueSyncDialog.VMs
{
    public class DocumentActionVM
    {
        public string Title { get { return action.Title; } }
        public ItemMapActivityAction action;
        public IItemMapActivityVm activityVm;
        public IEnumerable<DocumentActionVM> Actions
        {
            get
            {
                return action.Actions.Select(p => new DocumentActionVM(p, activityVm)).ToList();
            }
        }
        public DocumentActionVM(ItemMapActivityAction a, IItemMapActivityVm vm)
        {
            this.action = a;
            this.activityVm = vm;
        }

        public bool CanExecute()
        {
            return ((FileMapActivity) activityVm.data).CanExecute(action);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Strategies/DmsProcessStrategyBase.cs
﻿using System.Collections.Generic;
using Workshare.Integration.Processor.Maps;

namespace Workshare.Integration.Processor.Strategies
{
    public abstract class DmsProcessStrategyBase
    {
        public abstract ProcessResult Process(FileMap fileMap, DmsProcessOptions dmsProcessOptions);

        public abstract ProcessResult Process(FolderMap foldermap, DmsProcessOptions dmsProcessOptions);
    }

    public class ProcessResult
    {
        public static ProcessResult Processed = new ProcessResult(ProcessState.Processed);
        public static ProcessResult Cancelled = new ProcessResult(ProcessState.Cancelled);

        public ProcessResult(ProcessState result)
        {
            this.Result = result;
        }
        public ProcessState Result { private set; get; }
    }

    public class DmsProcessOptions
    {
        public DmsProcessOptions(IEnumerable<ItemMapActivityAction>  actions)
        {
            Actions = actions ?? new List<ItemMapActivityAction>();
        }
        public IEnumerable<ItemMapActivityAction> Actions { private set; get; }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/WorkUnits/ScanWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Runtime.InteropServices;
using System.Threading;
using System.Windows.Forms.VisualStyles;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.DmsItems;
using Workshare.Integration.Processor.DmsItems.Visitors;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using RES = Workshare.Integration.Properties.Resources;
namespace Workshare.Components.Views.TrueSyncDialog.WorkUnits
{
    public class ScanWorkUnit : WorkUnit
    {
        private readonly List<IDMSItem> _items;
        private readonly TrueSyncDialogViewModel _vm;
        private readonly bool _loadingMore;
        private readonly Thread _scanThread;

        public ScanWorkUnit(IModuleView view, IEnumerable<IDMSItem> items, TrueSyncDialogViewModel vm, Thread scanThread, 
            bool loadingMore = false)
            : base(view)
        {
            if (view == null) throw new ArgumentNullException("view");
            if (items == null) throw new ArgumentNullException("items");
            if (vm == null) throw new ArgumentNullException("vm");
            _items = items.ToList();
            _vm = vm;
            _loadingMore = loadingMore;
            Name = "Scanning";
            TargetItems = _items.Select(a => new TargetItem(a.ID.ToString())
            {
                Name = a.Name
            }).ToArray();
            StatusDescription = "Scanning...";

            _scanThread = scanThread = new Thread(new ThreadStart(Scan));
        }


        public override void OnAdded()
        {
            _vm.State = !_loadingMore
                ? TrueSyncDialogViewModel.StateEnum.Scanning
                : TrueSyncDialogViewModel.StateEnum.LoadingMore;
            base.OnAdded();
        }

        public override void Execute()
        {
            try
            {
                _scanThread.Start();
            }
            catch (Exception ex)
            {
                _view.ShowError(ex);
            }
        }

        private void Scan()
        {
            Logger.WriteTrace(string.Format("ScanWorkUnit.Execute. loadingMode={0}; itemsPerPage={1}", _loadingMore, _vm.ItemsPerPage));
            _vm.Module.Resolve<DiscardedService>().Refresh();
            var processor = _vm.Module.Resolve<Processor>();
            var existedActivities = _vm.AllActivities.Select(a => a.data).ToList();

            SummaryProcessResult scanMaps;
            var scanOptions = new ScanOptions(_vm.CancellationToken)
            {
                ItemsPerPage = _vm.ItemsPerPage
            };
            var itemToScan = _items.OfType<BaseDMSFolder>().First();
            if (!_loadingMore)
            {
                var itemsDetector = new ItemsDetector(_vm.Module.Resolve<ActivityFinder>(), _vm);
                scanMaps = processor.ScanFirstPage(itemToScan, scanOptions, itemsDetector);
            }
            else
            {
                scanMaps = processor.ScanNextPage(itemToScan, scanOptions, _vm.ScanResult);
            }

            var adapter = _vm.Module.Resolve<ActivityFinder>();
            var activities = adapter.GetAllActivities(scanMaps, existedActivities.OfType<FileMapActivity>().ToList());

            while (activities.OfType<ImportFileActivity>().Where(p => p.Changes.Any(x => x.Type == ChangeType.RemoteAdded))
                .All(p => p.IsDiscarded) && scanMaps.Iterator != null && scanMaps.Iterator.HasMore)
            {
                scanMaps = processor.ScanNextPage(itemToScan, scanOptions, scanMaps);
                activities = adapter.GetAllActivities(scanMaps, activities);
            }

            var errors = adapter.GetErrors(scanMaps);

            _vm.OnCompleted(errors, activities, scanMaps);
        }
    }

    class ItemsDetector : IItemsDetector
    {
        private readonly ActivityFinder _finder;
        private readonly TrueSyncDialogViewModel _vm;

        public ItemsDetector(ActivityFinder finder, TrueSyncDialogViewModel vm)
        {
            _finder = finder;
            _vm = vm;
        }

        public int GetCurrentItemsCount(DMSVisitor visitor)
        {
            var v = (ScanVisitor) visitor;
            var existedActivities = _vm.AllActivities.Select(a => a.data).ToList();
            return _finder.GetAllActivities(v.Result, existedActivities.OfType<FileMapActivity>()).Count(a => a.InKindOfErrorState() || a.InKindOfProceeedState() || TrueSyncDialogViewModel.FilterActivities(a));
        }
    }
}
<file_sep>/SharePoint/src/WorksharePointCloud/Layouts/WorkshareCloud/Scripts/WorkshareCore.js
﻿////RESOURCES

var RES = {
    STR_PROMPT_TO_CHANGE_LOCATION: "Some operations are in progress. Do you really want to leave page?",
    STR_ALERT_TEXT_SENDING: "Sending...",
    STR_ALERT_TEXT_SYNHRONIZATION: "Synchronization...",
    STR_ALERT_TEXT_UPDATING_LIST: "Updating...",
    STR_ALERT_TEXT_COMPLETED: "Completed",

    STR_MENUITEM_CAPTION_UPDATELIST: "Update view to work with Workshare",
    STR_MENUITEM_CAPTION_SEND_TO_WORKSHARE: "Send to Workshare",
    STR_MENUITEM_CAPTION_SYNHRONIZE: "Sync from Workshare",

    STR_MESSAGE_ERROR: "Something went wrong: ",
    STR_SUCCESSFULLY_LOGINED: "Successfully logged in to Workshare",

    STR_MESSAGE_NOT_ENOUGHT_PERMISSIONS: "You don't have permission to perform this action",
    INT_MENUOPTION_UPDATE_VIEW: 0,
    INT_MENUOPTION_SEND_TO_WS: 1,
    INT_MENUOPTION_SYNC_FROM_WS: 2,
    ERROR_WORKSHARE_FEILD_NOT_FOUND: "cannot find hidden input",
    ERROR_NO_ITEM_SELECTED: "Please select the checkbox to the left of the file/folder and try again.",
    ERROR_OTHER_OPERATION_IN_PROGRESS: "Other operation is being executed. Please wait...",

    CANNOT_BE_RESENT: "Cannot be sent back to Workshare.\n",
    CAN_BE_RESENT: "Can be sent back to Workshare.\n",
    PARENT_FOLDER_DELETED: "Parent folder is deleted",
    COOKIE_USER_CREDENTIALS: "user_credentials",
    COOKIE_SESSION_ID: "_session_id",
    COOKIE_AUTH_TOKEN: "tmp_auth_token",

    CONFLICT_REPLACE: 1,
    CONFLICT_KEEP_BOTH: 2,
    CONFLICT_NONE: 0,
    STR_CONFLICT_HEADER: "Replace with older file?",
    STR_CONFLICT_DESCRIPTION_DESTINATION_NEWER: "The file being synced from Workshare appears to be an older file",
    STR_CONFLICT_DESCRIPTION_SOURCE_NEWER: "The file source location appears to contain a newer instance of the file",
    STR_CONFLICT_FILE: "File :",
    STR_CONFLICT_DATE: "Date :",
    STR_CONFLICT_MODIFIER: "Modified by :",
    STR_CONFLICT_DLGTITLE: "Resolve conflict",
    STR_CONFLICT_REPLACEBUTTON_TEXT: "Replace File",
    STR_CONFLICT_KEEPBOTHBUTTON_TEXT: "Keep Both Files",
    STR_CONFLICT_CANCELBUTTON_TEXT: "Cancel",
    STR_CONFLICT_SHAREPOINT_TITLE: "SharePoint",
    STR_CONFLICT_WORKSHARE_TITLE: "Workshare",
    STR_ERROR_WORKSHARE_TITLE: "Workshare",
    STR_CANNOT_CONNECT_TO_SP_SERVICE: "Cannot establish connection with the Workshare Service on SharePoint"
};

var WSContext =
{
    //WS_SERVER: "https://dev.workshare.com/",
    //WS_SERVER: "https://my.workshare.com/",
    WS_SERVER: "https://qa.workshare.com/",
    WS_DIALOG_RELATIVE: "home/dialogs.sdif",
    LOGIN_DIALOG_RELATIVE: "login"
}

var ERRORCODE = {
    ItemListErrors: 5,
    CluudUnAuth: 100,
    ItemNotFound: 406,
    SyncConflict: 503
};

var HTTP_CODES =
    {
        SERVICE_UNAVAILABLE: 503
    };

//item class
function SPItem(itemID, type) {
    this.id = itemID;
    this.FSObjType = type;
};

//Data for one-request  sending
function SendItemsInfo(folderId, items, listGuid) {
    this.items = items
    this.folderId = folderId;
    this.listGuid = listGuid;
};

function SyncItemInfo(item, conflictOption) {
    this.item = item;
    this.conflictOption = conflictOption;
}

//Data for one-request  synchronization
function SyncItemsInfo(items, listGuid) {
    this.items = items
    this.listGuid = listGuid;
};

//SP CLOUD SERVICE

function SendItemToFolder(sendItemsInfos, success, error) {
    ExecuteWSPCloudMehod("Send", { infos: sendItemsInfos },
        function (return_data, textStatus) {
            if (success !== undefined) {
                success(return_data, textStatus);
            }
        },
       function (xhr, textStatus, errorThrown) {
           if (error !== undefined) {
               error(xhr, textStatus, errorThrown);
           }
           else {
               defaultErrorHandler(xhr, textStatus, errorThrown);
           }
       }, RES.STR_ALERT_TEXT_SENDING, RES.STR_ALERT_TEXT_COMPLETED);
};

function Login(email, pass, success, error) {
    ExecuteWSPCloudMehod("Login", { email: email, password: <PASSWORD> },
        function (return_data, textStatus) {
            if (success !== undefined) {
                success();
            }
        },
       function (xhr, textStatus, errorThrown) {
           if (error !== undefined) {
               error(xhr, textStatus, errorThrown);
           }
           else {
               defaultErrorHandler(xhr, textStatus, errorThrown);
           }
       }, RES.STR_ALERT_TEXT_SENDING, RES.STR_ALERT_TEXT_COMPLETED);
};

function Logout(success) {
    ExecuteWSPCloudMehod("Logout", {},
        function (return_data, textStatus) {
            success();
        },
       defaultErrorHandler, RES.STR_ALERT_TEXT_SENDING, RES.STR_ALERT_TEXT_COMPLETED);
};

function SyncItem(syncItemsInfos, success, error) {
    ExecuteWSPCloudMehod("Sync", { infos: syncItemsInfos },
        function (return_data, textStatus) {
            if (success !== undefined) {
                success();
            }
            return;
        },
        function (xhr, textStatus, errorThrown) {
            if (error !== undefined) {
                error(xhr, textStatus, errorThrown);
            }
            else {
                defaultErrorHandler(xhr, textStatus, errorThrown);
            }

        }, RES.STR_ALERT_TEXT_SYNHRONIZATION, RES.STR_ALERT_TEXT_COMPLETED);
};

function updateView(listGuid, success) {
    ExecuteWSPCloudMehod("Update", { items: [], folderId: -1, listGuid: listGuid },
        function (return_data, textStatus) {
            if (success !== undefined) {
                success(return_data, textStatus);
            }
        },
       defaultErrorHandler, RES.STR_ALERT_TEXT_UPDATING_LIST, RES.STR_ALERT_TEXT_COMPLETED);
};

var OperationsContext = {

    inProgress: 0,
    operationName: "",

    operationStarted: function (opName) {
        this.operationName = opName;
        this.inProgress++;
    },

    operationFinished: function () {
        this.operationName = "";
        this.inProgress--;
    },

    anyLiveOperation: function () {
        return this.inProgress > 0;
    }
};

function DialogsSettings(l_w, l_h, ch_w, ch_h, cr_w, cr_h) {
    this.l_w = l_w;
    this.l_h = l_h;
    this.ch_w = ch_w;
    this.ch_h = ch_h;
    this.cr_w = cr_w;
    this.cr_h = cr_h;
}

var defaultDialogSettings = new DialogsSettings(1026, 728, 596, 514, 596, 514);
var cachedSettings=null;
function GetDialogSettings(callback) {
    if(cachedSettings)
    {
        return callback(cachedSettings);
    }
    else
    {
        ExecuteOrDelayUntilScriptLoaded(function () {
            ExecuteOrDelayUntilScriptLoaded(function () {
                $.ajax({
                    type: "POST",
                    url: getUrl("WorkshareCloudService.aspx") + "/" + "DialogSettings",
                    contentType: "application/json; charset=utf-8",
                    dataType: "json",
                    data: JSON.stringify({}),
                    success: function (res, textStatus) {
                        var dlgSettings = new DialogsSettings(res.d.dialog_login_width, res.d.dialog_login_height, res.d.dialog_select_folder_width, res.d.dialog_select_folder_height, res.d.dialog_create_folder_width, res.d.dialog_create_folder_height);
                        cachedSettings=dlgSettings;
                        callback(dlgSettings);
                    },
                    error: function (xhr, textStatus, errorThrown) {
                        callback(defaultDialogSettings);
                    }
                });
            }, "sp.js");
        }, "core.js");
    }
}

function ExecuteWSPCloudMehod(method, data, onSucces, onError, onStartText, onSuccessText) {
    ExecuteOrDelayUntilScriptLoaded(function () {
        ExecuteOrDelayUntilScriptLoaded(function () {
            try {
                OperationsContext.operationStarted(method);
                var notificationId = SP.UI.Notify.addNotification(onStartText, true);
                $.ajax({
                    type: "POST",
                    url: getUrl("WorkshareCloudService.aspx") + "/" + method,
                    contentType: "application/json; charset=utf-8",
                    dataType: "json",
                    data: JSON.stringify(data),
                    success: function (return_data, textStatus) {
                        OperationsContext.operationFinished();
                        SP.UI.Notify.removeNotification(notificationId);
                        SP.UI.Notify.addNotification(onSuccessText, false);
                        onSucces(return_data, textStatus);
                        return;
                    },
                    error: function (xhr, textStatus, errorThrown) {
                        OperationsContext.operationFinished();
                        SP.UI.Notify.removeNotification(notificationId);
                        if (xhr.readyState == 4) {
                            var errorInfo = getErrorInfo(xhr);
                            if (errorInfo != null) {
                                if (errorInfo.code == 403 || errorInfo.code == 404 || errorInfo.code == 5) {
                                    //defaultErrorHandler(xhr, textStatus, errorThrown);
                                    //not display error notification
                                }
                                else {
                                    SP.UI.Notify.addNotification(errorInfo.description, false);
                                }
                            }
                            else {
                                SP.UI.Notify.addNotification(errorThrown, false);
                            }
                            if (onError) {
                                onError(xhr, textStatus, errorThrown);
                            }
                            else {
                                defaultErrorHandler(xhr, textStatus, errorThrown);
                            }
                        }
                        return;
                    }
                });
            }
            catch (err) {
                OperationsContext.operationFinished();
                alert(err);
            }
        }, "sp.js");
    }, "core.js");
};

function getCurrentItem() {
    return new SPItem(currentItemID, 0);
};

///  DIALOGS
function closeDialog(result, data) {
    ExecuteOrDelayUntilScriptLoaded(function () {
        if (result) {
            SP.UI.ModalDialog.commonModalDialogClose(SP.UI.DialogResult.OK, data);
        }
        else {
            SP.UI.ModalDialog.commonModalDialogClose(SP.UI.DialogResult.cancel, data);
        }
    }, "sp.js");
};

function getDlgSizes(settings) {
    if(settings)
    {
        return {
            width: settings.ch_w,
            height: settings.ch_h
        }
    }
    else
    {
        return {
            width: 594,
            height: 512
        };
    }
};

function getFrameSize(dlgSize) {
    return {
        width: dlgSize.width,
        height: dlgSize.height
    };
};

function setSizes(dlg, iframe, settings) {
    var dlgSize = getDlgSizes(settings);
    var frameSize = getFrameSize(dlgSize);

    if (dlg) {
        dlg.css("height", dlgSize.height + "px").css("width", dlgSize.width + "px");
        dlg.parent().css("height", dlgSize.height + "px").css("width", dlgSize.width + "px");
    }
    if (iframe) {
        iframe.css("height", frameSize.height + "px").css("width", frameSize.width + "px");
    }
}

function showDialog(src, callback, jq) {
    GetDialogSettings(function (settings) {
        function receiver(e) {
            if (window.removeEventListener) {
                window.removeEventListener("message", receiver, false);
            }
            else {
                window.detachEvent("onmessage", receiver);
            }
            dialogClosed(GetDialogResult(e.data));
        }


        if (jq) {
            if (window.addEventListener) {
                window.addEventListener("message", receiver, false);
            }
            else {
                window.attachEvent("onmessage", receiver);
            }

            var dlgSize = getDlgSizes(settings);
            var dlg = $("<div></div>");
            var frm = $("<iframe scrolling='no'></iframe>").attr("src", src).css("border", "none");
            dlg.append(frm);

            dlg.dialog({
                buttons: {},
                resizable: false,
                height: dlgSize.height,
                width: dlgSize.width,
                position: "center",
                modal: true,
                open: function (event, ui) {
                    //hide close button.
                    $(this).css("overflow", "hidden");
                    $(this).parent().css("overflow", "hidden");
                    $(this).parent().addClass("selectfolder-dialog");
                    $(this).parent().find('.ui-dialog-titlebar-close:first').hide();
                    $(this).parent().find('.ui-dialog-titlebar').hide();
                    setSizes(dlg, frm, settings);
                }
            });

            function dialogClosed(data) {
                dlg.dialog("close");
                dlg.remove();
                if (callback) {
                    callback(data);
                }
            }
        }
        else {
            //ie has problems with iframe to qa.workshare.com 
            //we can set 	<meta http-equiv="X-UA-Compatible" content="IE=9"/> on SharePoint master page, then dialog will work, but...
            var res = window.showModalDialog(src, null, "dialogHeight:700px,dialogWidth:700px,center:yes,status:no");
            // var res = window.showModalDialog(src, null, "dialogHeight:1000,dialogWidth:1000,center:yes,status:no");
            if (callback) {
                callback(GetDialogResult(res));
            };

        }
    });
}

var isIE = (function () {
    var div = document.createElement('div');
    div.innerHTML = '<!--[if IE]><i></i><![endif]-->';
    return (div.getElementsByTagName('i').length === 1);
}());


function GetDialogResult(data) {
    try {
        var res = $.parseJSON(data);
        if (res) {
            return res;
        }
        else {
            return data;
        }
    }
    catch (err) {
        //alert("Cannot parse dialog result");
        return data;
    }
}

function showSelectFolderDialog(items, initialFolderId, callback) {
    var params = "?caller=sharepoint&extcall=hello";
    var src = WSContext.WS_SERVER + WSContext.WS_DIALOG_RELATIVE + params;
    showDialog(src, callback, true);
};

function redirectToLogin() {
    var params = "?claim_token_url=" + encodeURIComponent(window.location).replace("%2520", "%20") + "&reuse_session=1";
    var src = WSContext.WS_SERVER + WSContext.LOGIN_DIALOG_RELATIVE + params;
    window.location = src;
}

function showResolveDlgRec(index, conflictedItems, callback) {
    if (index < 0) {
        callback(conflictedItems);
    }
    else {
        showResolveDlgInternal(conflictedItems[index], function (result) {
            if (result) {
                if (result.cancel) {
                    conflictedItems.splice(index, 1);
                }
                else if (result.action) {
                    conflictedItems[index].item.conflictOption = result.action;
                }
                else {
                    conflictedItems[index].item.conflictOption = RES.CONFLICT_NONE;
                }
            }
            showResolveDlgRec(index - 1, conflictedItems, callback);
        });
       
    }
}

function onDialogOpened(dlg) {
    dlg.parent().find('.ui-dialog-titlebar:first').prepend($("<img/>").addClass("ws-worksharelogo").attr("src", getUrl("/Images/Workshare.ico")));
}

function getConflictedVersHtml(title, info) {
    return $("<table cellpadding=\"4px\" cellspacing=\"3px\"></table>")
        .append($("<tr></tr>")
            .append($("<td></td>")
                .append($("<img/>").attr("title", name).attr("src", getUrl("FileIcon.ashx?size=40&filename=" + info.name))))
            .append($("<td></td>")
                .append($("<div></div>").addClass("SourceName")
                    .append($("<b></b>").html(title)))
                .append($("<div></div>").addClass("FileDetail").append($("<span></span>")
                    .append($("<b></b>").html(RES.STR_CONFLICT_FILE))).append($("<span></span>").html(info.name).attr("title", info.name)))
                .append($("<div></div>").addClass("FileDetail").append($("<span></span>")
                    .append($("<b></b>").html(RES.STR_CONFLICT_DATE))).append($("<span></span>").html(info.modified)))
                .append($("<div></div>").addClass("FileDetail").append($("<span></span>")
                    .append($("<b></b>").html(RES.STR_CONFLICT_MODIFIER))).append($("<span></span>").html(info.modifier).attr("title", info.modifier)))));
}

function getContentHtml(conflictedItem) {
    return $("<div></div>").addClass("ui_extend_file_conflict")
        .append($('<div></div>').addClass("conflictdlg-headertext")
            .append($("<h2></h2>").html(RES.STR_CONFLICT_HEADER)))
        .append($('<div></div>').addClass("conflictdlg-descriptiontext")
            .append($("<p></p>").html(RES.STR_CONFLICT_DESCRIPTION_DESTINATION_NEWER)))
        .append($('<div></div>').addClass("conflictdlg-fileInfo").append(getConflictedVersHtml(RES.STR_CONFLICT_WORKSHARE_TITLE, conflictedItem.wsInfo)))
        .append($('<div></div>').addClass("conflictdlg-arrow").append($("<img/>").attr("src", getUrl("Images/conflict-arrow.png"))))
        .append($('<div></div>').addClass("conflictdlg-fileInfo").append(getConflictedVersHtml(RES.STR_CONFLICT_SHAREPOINT_TITLE, conflictedItem.spInfo)));
}

function showResolveDlgInternal(item, callback) {
    var dlg = getContentHtml(item).attr("title", RES.STR_CONFLICT_WORKSHARE_TITLE);
    var buttons = {};
    buttons[RES.STR_CONFLICT_REPLACEBUTTON_TEXT] = function () { dlg.result = { action: RES.CONFLICT_REPLACE }; dlg.dialog("close"); };
    buttons[RES.STR_CONFLICT_KEEPBOTHBUTTON_TEXT] = function () { dlg.result = { action: RES.CONFLICT_KEEP_BOTH }; dlg.dialog("close"); };
    buttons[RES.STR_CONFLICT_CANCELBUTTON_TEXT] = function () { dlg.dialog("close"); };

    dlg.dialog({
        buttons: buttons, modal: true, width: 590, resizable: false,
        close: function () {
            if (dlg.result) {
                callback(dlg.result);
            }
            else {
                callback({ cancel: "true" });
            }
        },
        open: function () {
            $(this).parent().find(".ui-dialog-buttonset button:first-child").addClass("bluebutton");
            onDialogOpened($(this));
        }
        
    });
}

function showResolveDlg(conflictedItems, callback) {
    showResolveDlgRec(conflictedItems.length - 1, conflictedItems, callback);
}

function getErrorCode(xhr) {
    try {
        return getErrorInfo(xhr).code;
    }
    catch (err) {
        return null;
    }
};

function getErrorInfo(xhr) {
    try {
        var errorInfo = $.parseJSON(xhr.responseText);
        if (errorInfo.d.code !== undefined && errorInfo.d.description !== undefined) {
            return { code: errorInfo.d.code, description: errorInfo.d.description, data: errorInfo.d.data };
        }
        else {
            return null;
        }
    }
    catch (err) {
        return null;
    }
}

function defaultErrorHandler(xhr, textStatus, errorThrown) {
    try {
        var errorInfo = getErrorInfo(xhr);
        if (errorInfo) {
            switch (errorInfo.code) {
                default: showError(errorInfo); break;
            }
        }
        else {
            if (xhr.status == HTTP_CODES.SERVICE_UNAVAILABLE) {
                alert(RES.STR_CANNOT_CONNECT_TO_SP_SERVICE);
            }
            else {
                alert(textStatus);
            }
        }
    }
    catch (err) {
        alert('Status: ' + textStatus + '\nDesc: ' + errorThrown + '\nData: ' + xhr.responseText);
    }
};

function showError(errorInfo) {
    switch (errorInfo.code) {
        case 1: alert("ErrorCode : " + errorInfo.code + "\nDescription : " + errorInfo.description); break;
        default: alert(errorInfo.description);
    }
};



function handleException(err) {
    alert(RES.STR_MESSAGE_ERROR + err);
};

function getUrl(worksharelativeurl) {
    return SP.Utilities.Utility.getLayoutsPageUrl("WorkshareCloud/" + worksharelativeurl);
};


function RunSelectedMethod(runParam) {
    $.cookie("last_function", null, { path: '/' });
    if (runParam) {
        if (runParam.selectedFunctID == 0) {
            showSelectFolderDialog(runParam.items, 0, Function.createDelegate({ items: runParam.items, listGuid: runParam.listGUID }, selectFolderCallback));
        }
        else {
            SyncFromWorkshare(runParam.items, runParam.listGUID);
        }
    }
}

function EnsureUserLogin(runParam) {
    var fst = $.cookie("tmp_auth_token");
    var sid = $.cookie(RES.COOKIE_SESSION_ID);
    var crd = $.cookie(RES.COOKIE_USER_CREDENTIALS);

    $.cookie("tmp_auth_token", null, { path: '/' });
    $.cookie(RES.COOKIE_SESSION_ID, null, { path: '/' });
    $.cookie(RES.COOKIE_USER_CREDENTIALS, null, { path: '/' });

    //if ((fst != null) && (fst.length > 0) || (sid != null) && (crd != null)) {
    //    return true;
    //}
    //else {

    var funct = JSON.stringify(runParam);
    $.cookie("last_function", funct, { path: '/' });
    redirectToLogin();
    //}
};

var QueryString = function () {
    // This function is anonymous, is executed immediately and 
    // the return value is assigned to QueryString!
    var query_string = {};
    var query = window.location.search.substring(1);
    var vars = query.split("&");
    for (var i = 0; i < vars.length; i++) {
        var pair = vars[i].split("=");
        query_string[pair[0]] = pair[1];
    }
    return query_string;
}();


function checkSelectedMethod() {
    var param = $.cookie("last_function");
    if (param != null && $.cookie(RES.COOKIE_AUTH_TOKEN) != null) {
        var last_function_param = $.parseJSON(param);
        RunSelectedMethod(last_function_param);
    }

};

function eraseCookie(name) {
    var date = new Date();
    date.setTime(date.getTime() + (days * 24 * 60 * 60 * 1000));
    var expires = "; expires=" + date.toGMTString();
    document.cookie = escape(name) + "=" + escape("") + expires + "; path=/";
};
<file_sep>/WSComponents/src/WSCloudService.Tests/PlatformServiceTests.cs
﻿using System;
using System.Net;
using NUnit.Framework;
using WorksharePlatform;

namespace WorkshareCloud.ServiceProxy.Tests
{
    [TestFixture]
    public class PlatformServiceTests
    {
        [TestFixtureSetUp]
        public void Initialize()
        {
            ServicePointManager.DefaultConnectionLimit = int.MaxValue;
        }

        public void UploadFileToFolderWothDifferentPermisions(bool canAddnewVersion=true)
        {
            using (var user1 = new UserContext(TestUtils.USER1, TestUtils.USER1_PASS))
            {
                var newFolder = WS.CreateFolder(user1, new Permisions()
                    {
                        CanAddVersions = canAddnewVersion
                    }, new[] { TestUtils.USER2 });
                try
                {
                    using (var user2 = new UserContext(TestUtils.USER2, TestUtils.USER2_PASS))
                    {
                        var file = WS.GetTestFile();
                        file.FolderId = newFolder.Id;
                        PlatformService.UploadFile(user2, file);
                        Assert.IsNotNull(file.CurrentVersion);
                        Assert.IsTrue(file.CurrentVersion.FileId > 0);
                    }
                }
                finally
                {
                    PlatformService.DeleteFolder(user1, newFolder.Id);
                }
            }
        }

        public void UploadFileTest(string filename)
        {
            using (var user1 = new UserContext(TestUtils.USER1, TestUtils.USER1_PASS))
            {
                var file = WS.GetTestFile();
                try
                {

                    file.FolderId = 0;
                    file.Name = filename;
                    PlatformService.UploadFile(user1, file);
                    Assert.IsNotNull(file.CurrentVersion);
                    Assert.IsTrue(file.CurrentVersion.FileId > 0);
                }
                finally
                {
                    if (file.CurrentVersion != null)
                    {
                        //TODO - deletefile
                    }
                }
            }
        }

        [Test]
        public void UploadFileToFolderWithDisabledAddNewVersion_Bug11217()
        {
            UploadFileToFolderWothDifferentPermisions(canAddnewVersion:false);
        }

        [Test]
        public void UploadFileToFolderWithFullPermisions()
        {
            UploadFileToFolderWothDifferentPermisions(canAddnewVersion: true);
        }

//        [Test]
        public void UploadFileWithLongName()//bug 11223
        {
            UploadFileTest(new String('a', 254) + ".docx");
        }

        [Test]
        public void UploadNormalFile()
        {
            UploadFileTest("testdoc1.docx");
        }

        [Test]
        public void TestDialogSetting()
        {
            PlatformService.Host = "dev.workshare.com";
            var res = PlatformService.GetDialogSettings(new UserDetails());
            Assert.IsTrue(res.dialog_select_folder_width > 0);
            Assert.IsTrue(res.dialog_select_folder_height > 0);
            Assert.IsTrue(res.dialog_login_width > 0);
            Assert.IsTrue(res.dialog_login_height > 0);
            Assert.IsTrue(res.dialog_create_folder_width > 0);
            Assert.IsTrue(res.dialog_create_folder_height > 0);
        }
    }
}
<file_sep>/iManageIntegration/Src/Workshate.HookEvents/HookNewImportCmd.cs
﻿using System;
using System.Diagnostics;
using System.Runtime.InteropServices;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.Worksite.iManExt2;
using Workshare.Components.Interfaces;

namespace Workshare.HookEvents
{
    [ClassInterface(ClassInterfaceType.None)]
    [Guid("315C27E3-EEE9-46AE-B37B-37B0B24B19B2")]
    [ComVisible(true)]
    public class HookNewImportCmd : ICommand, Com.Interwoven.Worksite.iManExt2._ICommandEvents_Event
    {
        NewImportCmd cmd;
        bool isCancel = true;

        public HookNewImportCmd()
        {
            cmd = new NewImportCmd();
            cmd.OnCancel += cmd_OnCancel;
            cmd.OnInitDialog += cmd_OnInitDialog;
            cmd.PostOnOK += cmd_PostOnOK;
            cmd.PreOnOK += cmd_PreOnOK;
        }

        public int Accelerator
        {
            get
            {
                return cmd.Accelerator;
            }
            set
            {
                cmd.Accelerator = value;
            }
        }

        public object Bitmap
        {
            get
            {
                return cmd.Bitmap;
            }
            set
            {
                cmd.Bitmap = value;
            }
        }

        public ContextItems Context
        {
            get
            {
                return cmd.Context;
            }
        }

        private void ProcessImportEvent()
        {
            var docs = ProcessIManageEvents.GetImportedDocuments(Context);
            if (docs.Count != 0)
            {
                if (docs.Count == 1)
                {
                    object doc = docs[0];
                    ProcessIManageEvents.LastImportedDocNumber = ((Com.Interwoven.WorkSite.iManage.IManDocument)doc).Number;
                }

                //Context.OfType<object>().ToList().ForEach(p => Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                ProcessIManageEvents.ProcessEvent(docs, EventOperation.AddNewDoc, "HookNewImportCmd");

            }
            else
            {
                Workshare.Components.WSLogger.Logger.Write("ImportedDocuments list is empty. No document to add", Components.WSLogger.Severity.Information);
            }
        }

        public void Execute()
        {
            cmd.Execute();
            if (!isCancel)
            {
                try
                {
                    ProcessImportEvent();
                }
                catch (Exception ex)
                {
                    Workshare.Components.WSLogger.Logger.WriteError(ex);
                }
            }
            else
            {
                try
                {
                    //when user drag&drop several files the DeskSite/FileSite with new updates shows NewProfileDlg only once (for the first file)
                    object duplicateProfileFromDoc = ProcessIManageEvents.GetCmdContextItemValueByName(cmd.Context, "IManExt.Import.DuplicateProfileFromDoc");
                    object noCmdUI = ProcessIManageEvents.GetCmdContextItemValueByName(cmd.Context, "IManExt.OpenCmd.NoCmdUI");
                    if (duplicateProfileFromDoc != null && noCmdUI != null && Convert.ToBoolean(noCmdUI) == true)
                    {
                        ProcessImportEvent();
                    }
                }
                catch (Exception ex)
                {
                    Workshare.Components.WSLogger.Logger.WriteError(ex);
                }
            }
        }

        public string HelpFile
        {
            get
            {
                return cmd.HelpFile;
            }
            set
            {
                cmd.HelpFile = value;
            }
        }

        public int HelpID
        {
            get
            {
                return cmd.HelpID;
            }
            set
            {
                cmd.HelpID = value;
            }
        }

        public string HelpText
        {
            get
            {
                return cmd.HelpText;
            }
            set
            {
                cmd.HelpText = value;
            }
        }

        ContextItems ctx;
        public void Initialize(ContextItems Context)
        {
            cmd.Initialize(Context);
        }

        public string MenuText
        {
            get
            {
                return cmd.MenuText;
            }
            set
            {
                cmd.MenuText = value;
            }
        }

        public string Name
        {
            get
            {
                return cmd.Name;
            }
            set
            {
                cmd.Name = value;
            }
        }

        public int Options
        {
            get
            {
                return cmd.Options;
            }
            set
            {
                cmd.Options = value;
            }
        }

        public int Status
        {
            get
            {
                return cmd.Status;
            }
            set
            {
                cmd.Status = value;
            }
        }

        public Commands SubCommands
        {
            get
            {
                return cmd.SubCommands;
            }
            set
            {
                cmd.SubCommands = value;
            }
        }

        public string Title
        {
            get
            {
                return cmd.Title;
            }
            set
            {
                cmd.Title = value;
            }
        }

        public CommandType Type
        {
            get
            {
                return cmd.Type;
            }
            set
            {
                cmd.Type = value;
            }
        }

        public void Update()
        {
            cmd.Update();
        }

        void cmd_PreOnOK(object pMyInterface)
        {
            isCancel = false;
            if (PreOnOK != null)
            {
                PreOnOK(pMyInterface);
            }
        }

        void cmd_PostOnOK(object pMyInterface)
        {
            if (PostOnOK != null)
            {
                PostOnOK(pMyInterface);
            }
        }

        void cmd_OnInitDialog(object pMyInterface)
        {
            if (OnInitDialog != null)
            {
                OnInitDialog(pMyInterface);
            }
        }

        void cmd_OnCancel(object pMyInterface)
        {
            isCancel = true;
            if (OnCancel != null)
            {
                OnCancel(pMyInterface);
            }
        }

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_OnCancelEventHandler OnCancel;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_OnInitDialogEventHandler OnInitDialog;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_PostOnOKEventHandler PostOnOK;

        public event Com.Interwoven.Worksite.iManExt2._ICommandEvents_PreOnOKEventHandler PreOnOK;
    }
}
<file_sep>/WSComponents/src/WSIntegration/WSIntegration.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Net;
using System.Runtime.InteropServices;
using Workshare.Components.Helpers;
using Workshare.Components.WSLogger;
using Workshare.Integration.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Extensions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.WsProxies;
using WorksharePlatform;
using RES = Workshare.Integration.Properties.Resources;

namespace Workshare.Integration
{
    public enum Operations
    {
        Send,
        Sync,
        Deleted
    };

    public class WSIntegrationBase : IWSIntegration
    {
        private readonly IAuthProvider _authProvider;
        private readonly SyncInfoService _syncService;

        protected WSIntegrationBase(IAuthProvider authProvider, SyncInfoService syncService)
        {
            ServicePointManager.DefaultConnectionLimit = int.MaxValue;//TODO remove this line. fix problem with multiple files uploading
            this._syncService = syncService;
            _authProvider = authProvider;
        }


        public void SendItems(IEnumerable<IDMSItem> localItems, FolderDetails folder, OperationContext args)
        {
            SendItems(localItems.ToList(), folder.Id, args);
        }

        private void SendItems(List<IDMSItem> localItems, int folderId, OperationContext context)
        {
            using (var errorlist = new ItemsErrorsCollection(context))
            {
                try
                {
                    var user = _authProvider.CheckIfAuth();
                    SafeFuncCall(errorlist, null,
                        new ExceptionListSignal {IsAll = true, IsList = true, FolderError = true}, Operations.Send,
                        () =>
                        {
                            if (CheckFolderExistsWhenSendOrThrow(user, folderId) && localItems.Any())
                            {
                                foreach (IDMSItem item in localItems)
                                {

                                    if (item is IDMSFolder)
                                    {
                                        SafeFuncCall(errorlist, item,
                                            new ExceptionListSignal() {IsAll = true, IsList = true, FolderError = true},
                                            Operations.Send, () =>
                                            {
                                                SendFolder((IDMSFolder) item, folderId, user, context, null);
                                            });
                                    }
                                    else if (item is IDMSFile)
                                    {
                                        SafeFuncCall(errorlist, item,
                                            new ExceptionListSignal() {IsAll = true, IsList = true, FileError = true},
                                            Operations.Send, () =>
                                            {
                                                SendFile((IDMSFile) item, folderId, user, context);
                                            });
                                    }

                                }

                                errorlist.Check();
                            }
                        });
                }
                catch (CloudFolderNotFound ex)
                {
                    SafeFuncCall(errorlist, null, new ExceptionListSignal() {IsAll = true, IsList = true},
                        Operations.Send, () =>
                        {
                            if (localItems.Any())
                            {
                                var user = _authProvider.CheckIfAuth();
                                foreach (IDMSItem item in localItems)
                                {
                                    SafeFuncCall(errorlist, item,
                                        new ExceptionListSignal() {IsAll = true, IsList = true}, Operations.Send, () =>
                                        {
                                            if (item is IDMSFolder)
                                            {
                                                //TODO remove    SyncFolder((IDMSFolder)item, user, new SyncOptions(ConflictVersionOptions.None),context, true);
                                            }
                                            else if (item is IDMSFile)
                                            {
                                                _syncService.BreakLink((IDMSFile) item);
                                                //((IDMSFile)item).UpdateSyncInfo(null, true, null,null);
                                            }
                                        });
                                }
                            }
                        });
                    errorlist.Clear();
                    errorlist.Add((IDMSItem) null, ex);
                    errorlist.Check();
                }
            }
        }

        protected bool CheckFolderExistsWhenSendOrThrow(UserDetails user, int itemID, int parentFolderID = -1)
        {
            try
            {
                if (!PlatformService.IsFolderExists(user, itemID, parentFolderID))
                {
                    throw new CloudFolderNotFound(RES.STR_UNABLE_SEND);
                }
                return true;
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode((HttpStatusCode) 403))
                {
                    throw new CloudFolderAccessDenied(RES.STR_UNABLE_SEND, RES.STR_UNABLESENDITEM_TEXT, ex);
                }
                else if (ex.Status == WebExceptionStatus.ConnectFailure)
                {
                    throw new OfflineException(ex);
                }
                else
                {
                    throw;
                }
            }
        }

        private int UploadFileToWorkshareCloud(IDMSFile file, int folderId, UserDetails user, OperationContext context)
        {
            var fileDetailes = new FileDetails
            {
                Name = WsUtils.RemoveInvalidSymbolsFromFileName(file.Name),
                FriendlyName =
                    WsUtils.RemoveInvalidSymbolsFromFileName(((string.IsNullOrEmpty(file.DisplayName))
                        ? FileUtils.GetFileNameWithoutExtension(file.Name)
                        : file.DisplayName)),
                FilePath = file.GetFilePath(),
                FolderId = folderId
            };
            try
            {
                CheckFolderExistsWhenSendOrThrow(user, folderId);
                PlatformService.UploadFile3(user, fileDetailes);
                CheckFolderExistsWhenSendOrThrow(user, folderId);
                _syncService.UpdateSyncInfo(file.GetVersions().OrderByDescending(a => a.Number).FirstOrDefault(),
                    new ActionContext(ActionType.Upload)
                    {
                        WsVersion = new WsVersion(fileDetailes.CurrentVersion, user)
                    });
                _syncService.UpdateSyncInfo(file, new ActionContext(ActionType.Upload)
                {
                    WsFile = new WsFile(fileDetailes, user)
                });

                return fileDetailes.CurrentVersion.FileId;
            }
            catch (WebException ex)
            {
                if (ex.IsStatusCode((HttpStatusCode) 422))
                {
                    throw new CannotProcessItemException();
                }
                else if (ex.IsStatusCode((HttpStatusCode) 403))
                {
                    throw new CloudFolderAccessDenied(RES.STR_UNABLE_SEND, RES.STR_UNABLESENDFILE_TEXT, ex);
                }
                else if (ex.Status == WebExceptionStatus.ConnectFailure || ex.Status == WebExceptionStatus.NameResolutionFailure || ex.Status == WebExceptionStatus.ConnectionClosed)
                {
                    throw new OfflineException(ex);
                }
                else
                {
                    Logger.Write(ex, Severity.Error);
                    throw;
                }
            }
        }

        private int SendFile(IDMSFile localfile, int folderId, UserDetails user, OperationContext context)
        {
            localfile.CheckPermissionkOrThrow(Enums.Permissions.EditItem);
            localfile.OnBeforeSending(context);

            if (context.CheckOutOption == CheckOutOptions.CheckOut)
            {
                localfile.CheckNotCheckeOutToOtherUserOrThrow(Operations.Send);
            }

            try
            {
                var fileId = UploadFileToWorkshareCloud(localfile, folderId, user, context);
                if (fileId > 0)
                {
                    localfile.AddHistory(string.Empty,
                        string.Format(RES.STR_HISTORY_ITEMSEND, DateTime.Now.ToString(Activity.TimeFormat)),
                        Operations.Send);
                }
                localfile.OnAfterSending(context);
                return fileId;
            }
            catch (Exception ex)
            {
                if (!(ex is OfflineException))
                    localfile.OnSendError(context, ex);
                throw;
            }
        }

        private int SendFolder(IDMSFolder folder, int parentFolderId, UserDetails user, OperationContext context,
            List<int> parentChildren)
        {
            int newFolderID = -1;
            using (var errorlist = new ItemsErrorsCollection(context))
            {
                var sentItems = new List<int>();
                SafeFuncCall(errorlist, folder, new ExceptionListSignal {IsWeb = true, FolderError = true},
                    Operations.Send, () =>
                    {
                        folder.OnBeforeSending(context);
                        FolderDetails newFolder;
                        try
                        {
                            newFolder = PlatformService.CreateFolder(user, folder.Name, folder.Name, parentFolderId);
                        }
                        catch (WebException ex)
                        {
                            if (ex.IsStatusCode((HttpStatusCode) 403))
                            {
                                throw new CloudFolderAccessDenied(RES.STR_UNABLE_SEND, RES.STR_UNANBESENDFOLDER_TEXT, ex);
                            }
                            throw;
                        }
                        _syncService.UpdateSyncInfo(folder, new ActionContext(ActionType.Upload)
                        {
                            WsFolder = new WsFolder(newFolder, user)
                        });
                        //folder.UpdateSyncInfo(newFolder, true);
                        folder.AddHistory(string.Empty,
                            string.Format(RES.STR_HISTORY_ITEMSEND, DateTime.Now.ToString(Activity.TimeFormat)),
                            Operations.Send);
                        if (parentChildren != null)
                        {
                            parentChildren.Add(newFolder.Id);
                        }

                        foreach (IDMSFolder item in folder.SubFolders)
                        {
                            SafeFuncCall(errorlist, item,
                                new ExceptionListSignal {IsAll = true, IsList = true, FolderError = true},
                                Operations.Send, () =>
                                {
                                    var si = _syncService.GetSyncInfo(item);
                                    if (si == null)
                                    {
                                        SendFolder(item, newFolder.Id, user, context, sentItems);
                                    }
                                    else
                                    {
                                        sentItems.Add(si.ItemId);
                                        throw new FolderAlreadySentException();
                                    }
                                });
                        }

                        //Task 22006. GroupBy used to select only latest version when worksite shows all versions in Document view. 
                        foreach (IDMSFile file in folder.Files.GroupBy(x => x.DMSId).Select(x => x.First().GetLatest()))
                        {

                            SafeFuncCall(errorlist, file,
                                new ExceptionListSignal()
                                {
                                    IsAll = true,
                                    IsList = true,
                                    IsWeb = true,
                                    FolderError = true
                                }, Operations.Send, () =>
                                {
                                    var si = _syncService.GetSyncInfo(file);
                                    if (si == null)
                                    {
                                        sentItems.Add(SendFile(file, newFolder.Id, user, context));
                                    }
                                    else
                                    {
                                        sentItems.Add(si.ItemId);
                                        throw new FileAlreadySentException();
                                    }
                                });

                        }
                        _syncService.UpdateSendDataInfo(folder, sentItems);
                        newFolderID = newFolder.Id;
                    });
            }
            return newFolderID;
        }

        private static void ReThrowException(Exception ex, Operations operate)
        {
            if (ex is COMException)
            {
                Logger.WriteError("COMException in ReThrowException", ex);
                if (ex.IsConnectionError())
                    throw new OfflineException();
                else
                {
                    Logger.WriteError("ReThrowException catch COMException :", ex);
                    throw new DMSItemNotFound((operate == Operations.Send) ? RES.STR_UNABLESEND_CAPTION : RES.STR_UNABLESYNC_CAPTION, RES.STR_DMSFOLDER_REMOVED);
                }
            }

            if (ex is WebException)
            {
                if(ex.IsUnauthorized())
                {
                    throw new CloudUnAuthorized(ex);
                }
                else
                {
                    throw new OfflineException(ex);
                }
            }
            else if (ex is UnauthorizedAccessException)
            {
                throw new CloudUnAuthorized(ex); // DMSUnAuthorizedException(ex); imanage
            }

            Logger.WriteError("ReThrowException catch exception : ", ex);
            throw ex;
        }

        protected class ExceptionListSignal
        {
            public bool IsList = false;
            public bool IsWeb = false;
            public bool IsAll = false;
            public bool FolderError = false;
            public bool FileError = false;
        }

        protected void SafeFuncCall(ItemsErrorsCollection errorlist, IDMSItem item, ExceptionListSignal flags,
            Operations operate, Action func)
        {
            try
            {
                try
                {
                    func();
                }
                catch (Exception ex)
                {
                    ReThrowException(ex, operate);
                }
            }
            catch (Exception ex)
            {
                Trace.TraceError(ForTrace(ex));

                if (flags.IsList && ex is MultiItemsException)
                {
                    if (errorlist != null)
                    {
                        if (!errorlist.Equals(((MultiItemsException) ex).errorList))
                        {
                            errorlist.AddRange(((MultiItemsException) ex).errorList);
                        }
                    }
                    return;
                }

                if (flags.FolderError && ex is CloudFolderNotFound)
                {
                    throw;
                }

                if (ex is DMSUnAuthorizedException)
                {
                    throw;
                }

                if (ex is CloudUnAuthorized)
                {
                    throw;
                }

                if (flags.IsWeb && ex is WebException)
                {
                    if (flags.FileError && ((WebException) ex).IsStatusCode((HttpStatusCode) 403))
                    {
                        throw new CloudFolderAccessDenied(RES.STR_UNABLE_SYNC, RES.STR_UNABLESYNCFILE_TEXT, ex);
                    }

                    if (errorlist != null && item != null)
                    {
                        errorlist.Add(item, ex);
                        return;
                    }
                    else
                    {
                        throw;
                    }
                }

                if (flags.IsAll)
                {
                    if (errorlist != null && item != null)
                    {
                        errorlist.Add(item, ex);
                    }
                    else
                    {
                        throw;
                    }
                }
                else
                {
                    throw;
                }
            }
        }

        private string ForTrace(Exception ex)
        {
            return string.Format("{0}", ex);
        }

    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Common/OwnWindow.cs
﻿using System;
using System.Drawing.Imaging;
using System.Runtime.InteropServices;
using System.Windows;
using System.Windows.Input;
using System.Windows.Interop;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Threading;
using Workshare.Components.Interfaces;
using Workshare.Components.WSLogger;

namespace Workshare.Components.Views.Common
{
    public class OwnWindow:Window
    {
        public OwnWindow()
        {
            DataContextChanged += OwnWindow_DataContextChanged;
            this.Loaded += OwnWindow_Loaded;
            this.Closing += OwnWindow_Closing;
            var ibd = new IconBitmapDecoder(new Uri(@"pack://application:,,/WSComponents;component/Resources/Workshare_48x48.ico", UriKind.RelativeOrAbsolute),
                    BitmapCreateOptions.None, BitmapCacheOption.Default);
            this.Icon = ibd.Frames[0];
        }

        [DllImport("user32.dll")]
        static extern bool EnableWindow(IntPtr hWnd, bool bEnable);

        bool _ownerDisabled;

        void OwnWindow_Closing(object sender, System.ComponentModel.CancelEventArgs e)
        {
            if (_ownerDisabled)
            {
                EnableWindow(new WindowInteropHelper(this).Owner, true);
            }
        }

        void OwnWindow_Loaded(object sender, RoutedEventArgs e)
        {
            if (DisableOwner)
            {
                _ownerDisabled = !EnableWindow(new WindowInteropHelper(this).Owner, false);
            }
        }

        void OwnWindow_DataContextChanged(object sender, DependencyPropertyChangedEventArgs e)
        {
            var old = e.OldValue;
            if (old is ICloseRequester)
            {
                ((ICloseRequester)old).CloseRequested -= OwnWindow_CloseRequested;
            }

            var @new = e.NewValue;
            if (@new is ICloseRequester)
            {
                ((ICloseRequester)@new).CloseRequested += OwnWindow_CloseRequested;
            }
        }
        public bool? OwnDialogResult { set; get; }
        void OwnWindow_CloseRequested(bool? obj)
        {
            try
            {
                this.OwnDialogResult = obj;
                if (!IsLoaded)
                {
                    return;
                }
                if (ComponentDispatcher.IsThreadModal)
                {
                    this.DialogResult = obj;
                }
                this.Close();
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);
            }
            
        }

        protected bool KeepPositionOnResizing;

        protected override void OnRenderSizeChanged(SizeChangedInfo sizeInfo)
        {
            base.OnRenderSizeChanged(sizeInfo);
            if (KeepPositionOnResizing)
            {
                if (sizeInfo.HeightChanged)
                {
                    var newTop=Top-(sizeInfo.NewSize.Height - sizeInfo.PreviousSize.Height)/2;
                    Top = newTop > 0 ? newTop : 0;
                }
            }
        }

        protected void OnTitleMouseDown(object sender, MouseButtonEventArgs e)
        {
            if (e.ChangedButton == MouseButton.Left)
            {
                this.DragMove();
            }
        }

        public bool DisableOwner { get; set; }
    }

    public class OwnViewModel : OwnViewModel<OwnViewModel>
    {
    }

    public class OwnViewModel<T> : BasePropertyChanged<T>, ICloseRequester
    {
        public event Action<bool?> CloseRequested;

        public Dispatcher Dispatcher { private set; get; }

        public OwnViewModel()
        {
            this.Dispatcher = Dispatcher.CurrentDispatcher;
        }

        internal void RaiseClose(bool? result)
        {
            if (CloseRequested != null)
            {
                CloseRequested(result);
            }
        }

        ImageSource _footerImage;
        public ImageSource FooterImage
        {
            get
            {
                if (_footerImage == null)
                {
                    _footerImage = Utils.Convert(Properties.Resources.bottombar, ImageFormat.Png);
                }
                return _footerImage;
            }
        }

        ImageSource _titleImage;
        public ImageSource TitleImage
        {
            get
            {
                if (_titleImage == null)
                {
                    _titleImage = Utils.Convert(Properties.Resources.toptitlebar, ImageFormat.Png);
                }
                return _titleImage;
            }
        }
        ImageSource _closeImage;
        public ImageSource CloseImage
        {
            get
            {
                if (_closeImage == null)
                {
                    _closeImage = Utils.Convert(Properties.Resources.closebutton, ImageFormat.Png);
                }
                return _closeImage;
            }
        }

        ImageSource _brandImage;
        public ImageSource BrandImage
        {
            get
            {
                if (_brandImage == null)
                {
                    _brandImage = Utils.ToImageSource(Properties.Resources.Workshare_48x48);
                }
                return _brandImage;
            }
        }

        ImageSource _closeImageHover;
        public ImageSource CloseImageHover
        {
            get
            {
                if (_closeImageHover == null)
                {
                    _closeImageHover = Utils.Convert(Properties.Resources.closebutton_mouseover, ImageFormat.Png);
                }
                return _closeImageHover;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/WSServer.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;

namespace WorksharePlatform
{
    public class WSServer
    {
        public WSServer()
        { }

        public string ServerUrl { get; set; }
        public string QuesryString { get; set; }
        public string ctype { get; set; }
        public string token { get; set; } 
    }
}
<file_sep>/WSComponents/src/Framework4Adapter/IAsposePdfAdapter.cs
﻿using System.Collections.Generic;
using System.Runtime.InteropServices;
using WorksharePlatform;

namespace Framework4Adapter
{
    [ComVisible(true)]
    [Guid("CB5612CE-5D3C-4DEA-8E15-261F09F82649")]
    public interface IAsposePdfAdapter
    {
        byte[] AddCommentInData(byte[] data, List<FileComment> comments);
    }
}
<file_sep>/WSComponents/src/WSCloudService/DialogSettings.cs
﻿namespace WorksharePlatform
{
    public class DialogSettings
    {
        public int dialog_login_width { get; set; }
        public int dialog_login_height { get; set; }
        public int dialog_select_folder_width { get; set; }
        public int dialog_select_folder_height { get; set; }
        public int dialog_create_folder_width { get; set; }
        public int dialog_create_folder_height { get; set; }
    }
}
<file_sep>/SharePoint/src/WorkshareCloud.Common/Receivers/WorkshareReceiver.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;
using WorksharePlatform;

namespace WorkshareCloud.Common.Receivers
{
    public class WorkshareReceiver : SPItemEventReceiver
    {

        public override void ItemAdding(SPItemEventProperties properties)
        {
            EventFiringEnabled = false;
            try
            {
                properties.AfterProperties[CloudPathFieldValue.CloudField] = string.Empty;
            }
            catch (Exception ex)
            {
                Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.Unexpected, Logging.Category.Default);
            }
            finally
            {
                EventFiringEnabled = true;
            }
            //base.ItemAdding(properties);
        }

        public override void ItemUncheckedOut(SPItemEventProperties properties)
        {
            EventFiringEnabled = false;
            try
            {
                WorkshareIntegration.Instance.ClearFolderSyncDataIfNeed(properties.ListItem.File.ParentFolder.Item);
            }
            catch (Exception ex)
            {
                Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.Unexpected, Logging.Category.Default);
            }
            finally
            {
                EventFiringEnabled = true;
            }
        }

        public override void ItemCheckedIn(SPItemEventProperties properties)
        {
            EventFiringEnabled = false;
            try
            {
                WorkshareIntegration.Instance.ClearFolderSyncDataIfNeed(properties.ListItem.File.ParentFolder.Item);
            }
            catch (Exception ex)
            {
                Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.Unexpected, Logging.Category.Default);
            }
            finally
            {
                EventFiringEnabled = true;
            }
        }

        public override void ItemCheckingIn(SPItemEventProperties properties)
        {
            EventFiringEnabled = false;
            try
            {
                properties.AfterProperties.ChangedProperties.ClearCloudValue();
            }
            catch (Exception ex)
            {
                Logging.Logger.WriteTrace(ex, Microsoft.SharePoint.Administration.TraceSeverity.Unexpected, Logging.Category.Default);
            }
            finally
            {
                EventFiringEnabled = true;
            }
        }
    }
}
<file_sep>/WSComponents/src/WSCloudService/FileDetails.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using Workshare.Components.Helpers;

namespace WorksharePlatform
{
    public class FileDetails
    {
        public const long ChunkSize = 5242880; //5MB

        public int Id { get; set; }
        public string Name { get; set; }
        public string FriendlyName { get; set; }

        public string FriendlyNameWithExtension
        {
            get
            {
                return FileUtils.ChangeExtension(FriendlyName, FileUtils.GetExtension(Name));
            }
        }

        public int FolderId { get; set; }

        public static long GetFileSizeByFilePath(string filePath)
        {
            FileInfo fi = new FileInfo(filePath);
            return fi.Length;
        }

        public string FilePath { get; set; }

        public string RemoteUrl { get; set; }
        public string DownloadPassword { get; set; }

        public bool IsChunkingRequired
        {
            get
            {
                if (CurrentVersion != null && CurrentVersion.Size > 0)
                {
                    //this case is used during downloading the file
                    return (CurrentVersion.Size > FileDetails.ChunkSize);
                }
                else
                {
                    //this case is used during uploading the file
                    return (GetFileSizeByFilePath(FilePath) > FileDetails.ChunkSize);
                }
            }
        }

        public bool IsChunkingRequiredForUpload
        {
            get
            {
                return (GetFileSizeByFilePath(FilePath) > FileDetails.ChunkSize);
            }
        }

        public bool IsDeleted { get; set; }
        public FileVersionDetails CurrentVersion { get; set; }
        public MultiPartDetails CurrentPart { get; set; }
        public UserDetails Creator { get; set; }
        public UserDetails Updater { get; set; }
        public List<FileVersionDetails> Versions { get; set; }

        public override string ToString()
        {
            return string.Format("WsFile ID={0}, Name={1}", Id, Name);
        }

        public DateTime UpdateDate { get; set; }

        public DateTime CreatedAt { get; set; }

        public int VersionNumber { get; set; }

        public void DeleteFile()
        {
            if (!string.IsNullOrEmpty(FilePath))
                File.Delete(FilePath);
        }

    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Contrete/ManItemID.cs
﻿using System;
using System.Collections.Generic;
using System.Text;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Integration.Interfaces;

namespace Workshare.IManage.Contrete
{
    class ManItemID : IDMSItemID
    {
        string obj_ID;
        public ManItemID(IManObject doc)
        {
            if (doc.HasObjectID)
            {
                obj_ID = doc.ObjectID;
            }
            else
            {
                throw new ArgumentException("doc");
            }
        }

        public bool EqualTo(IDMSItemID obj)
        {
            if (obj is ManItemID)
            {
                return ((ManItemID)obj).obj_ID == this.obj_ID;
            }
            return false;
        }

        public override string ToString()
        {
            return obj_ID;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Common/RelayCommand.cs
﻿using System;
using System.Windows.Input;

namespace Workshare.Components.Views.Common
{
    public class RelayCommand:ICommand
    {
        Action<object> _execute;
        Predicate<object> _canExecute;

        public RelayCommand(Action<object> execute)
        {
            _execute = execute;
        }

        public RelayCommand(Predicate<object> canExecute, Action<object> execute)
        {
            _execute = execute;
            _canExecute = canExecute;
        }

        public bool CanExecute(object parameter)
        {
            if (_canExecute != null)
            {
                return _canExecute(parameter);;
            }
            else
            {
                return true;
            }
        }

        public event EventHandler CanExecuteChanged;

        public void Execute(object parameter)
        {
            if (_execute != null)
            {
                _execute(parameter);
            }
        }

        public void RaiseCanExecutechanged()
        {
            if (CanExecuteChanged != null)
            {
                CanExecuteChanged(this, EventArgs.Empty);
            }
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Common/SyncItemInformation.cs
﻿using Workshare.Integration.Enums;
using Workshare.Integration.Interfaces;
using WorksharePlatform;

namespace Workshare.Integration.Common
{
    public class SyncItemInformation
    {
        public IDMSItem item;
        public FileDetails wsItem;
        public ConflictOptions syncOption;
        public ConflictVersionOptions verOptions;
        public bool AddOnlyNewFiles;//if sync _folder then only new files should be added

        public SyncItemInformation(IDMSItem _item, ConflictOptions _option, ConflictVersionOptions _verOptions)
        {
            item = _item;
            syncOption = _option;
            verOptions = _verOptions;
            wsItem = null;
        }

        public SyncItemInformation(FileDetails _wsitem, IDMSItem _item,  ConflictOptions _option, ConflictVersionOptions _verOptions)
        {
            wsItem = _wsitem;
            syncOption = _option;
            verOptions = _verOptions;
            item = _item;
        }

        public SyncItemInformation CopyFor(IDMSItem item)
        {
            return new SyncItemInformation(item, syncOption, verOptions);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/VersionMap.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Maps
{
    public class VersionMap : ItemMap
    {
        public IDmsVersion LocalVersion { set; get; }
        public WsVersion WsVersion { set; get; }

        public override void Apply(ItemMapVisitor visitor)
        {
            visitor.Visit(this);
        }

        public override string GetId()
        {
            return GetMapId(this);
        }

        public static string GetMapId(VersionMap map)
        {
            if (map.LocalVersion == null)
            {
                return map.WsVersion == null ? string.Format("localversion:{0};wsversion:{1}", -1, -1) : string.Format("localversion:{0};wsversion:{1}", -1, map.WsVersion.Id);
            }
            if (map.WsVersion == null)
            {
                return string.Format("localversion:{0};wsversion:{1}", map.LocalVersion.Id, -1);
            }
            return string.Format("localversion:{0};wsversion:{1}", map.LocalVersion.Id, map.WsVersion.Id);
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Common/OperationContext.cs
﻿using Workshare.Integration.Enums;


namespace Workshare.Integration.Common
{
    public class OperationContext
    {
        public CheckOutOptions CheckOutOption { get; private set; }

        private OperationContext()
        {
        }

        public OperationContext(CheckOutOptions option)
            : this()
        {
            CheckOutOption = option;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Helpers/ProcessUtils.cs
﻿using System;
using System.Collections.Generic;
using System.Diagnostics;
using System.Linq;
using System.Text;
using Workshare.Components.WSLogger;

namespace Workshare.Components.Helpers
{
    public static class ProcessUtils
    {
        public static void StartProcess(string str)
        {
            if (!string.IsNullOrEmpty(str))
            {
                try
                {
                    Process.Start(str);
                }
                catch (Exception ex)
                {
                    Logger.Write(ex, Severity.Error);
                    Debug.Assert(false, "Cannot navigate");
                }
            }
        }
    }
}
<file_sep>/SharePoint/src/WorksharePointCloud/CloudPathField.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Microsoft.SharePoint;

namespace WorkshareCloud
{
    public class CloudPathField : SPFieldMultiLineText
    {
        public CloudPathField(SPFieldCollection fields, string fName)
            : base(fields, fName) { }
        public CloudPathField(SPFieldCollection fields,
                       string tName, string dName)
            : base(fields, tName, dName) { }

        public override string GetFieldValueAsHtml(object value)
        {
            var val = value as string;
            var onWorkshare = !string.IsNullOrEmpty(val);
            return string.Format("<input type=\"hidden\" value=\"{0}\" name=\"onWorkshare\" itemId=\"{1}\"/>", onWorkshare ? "true" : "false", "");
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Activities/FileMapActivity.cs
﻿using System;
using System.Collections.Generic;
using System.IO;
using System.Linq;
using Workshare.Components.Helpers;
using System.Security;
using Microsoft.Win32;
using Workshare.Components.WSLogger;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Strategies;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Changes.Activities
{
    public abstract class FileMapActivity : ItemMapActivity
    {
        public static void Update(FileMapActivity activity, FileMap map)
        {
           
        }

        protected bool AnyAvailableActions()
        {
            return Actions != null && Actions.Any() && Actions.All(p => p.Actions.Any());
        }

        public void Refresh(FileMap map, DmsWorkerBase dmsWorker) //TODO review using of DMS Worker
        {
            base.Refresh(map);
            WsFile = map.WsFile;
            DmsFile = map.LocalFile;

            var wsFilename = (WsFile != null) ? WsFile.FriendlyName + FileUtils.GetExtension(WsFile.Name) : null;
            var localFilename = (DmsFile != null) ? DmsFile.Name : null;

            Filename = localFilename ?? wsFilename;

            ViewOnlineUrl = GetUrlOnWorkshare(map);

            WsId = (WsFile == null) ? "-1" : WsFile.Id.ToString();
            DmsId = (DmsFile == null) ? "-1" : DmsFile.ID.ToString();
            DmsFileId = (DmsFile == null) ? "-1" : DmsFile.DMSId.ToString();

            WsLastUpdateDate = (WsFile != null) ? WsFile.UpdateDate : DateTime.MinValue;
            LocalEditTime = (DmsFile != null) ? dmsWorker.GetEditTime(DmsFile) : DateTime.MinValue;
        }


        public string Filename { set; get; }
        public string ViewOnlineUrl { set; get; }
        public string WsId { set; get; }
        public string DmsId { set; get; }

        /// <summary>
        /// Dms file ID without the version information
        /// </summary>
        public string DmsFileId { get; set; }

        public WsFile WsFile { set; get; }
        public IDMSFile DmsFile { set; get; }

        public bool IsLinked { set; get; } //TODO: Think about better solution here.  

        public string CheckedOutTo { get; set; }
        public string CheckOutMachine { get; set; }

        public DateTime WsLastUpdateDate { get; set; }
        public DateTime LocalEditTime { get; set; }

        /// <summary>
        /// Determine if default browser is Internet Explorer 8
        /// </summary>
        /// <param name="uriScheme">Uri scheme (http, https etc.)</param>
        /// <returns>true - default browser is Internet Explorer 8, otherwise - false</returns>
        static bool DefaultBrowserIsIE8(string uriScheme)
        {
            bool ret = false;

            try
            {
                using (RegistryKey defaultBrowserRegKey = Registry.CurrentUser.OpenSubKey(String.Format(@"Software\Microsoft\Windows\Shell\Associations\UrlAssociations\{0}\UserChoice", uriScheme)))
                {
                    bool defaultBrowserIsIE = false;
                    if (defaultBrowserRegKey != null)
                    {
                        if (Convert.ToString(defaultBrowserRegKey.GetValue("Progid")).ToUpper().Equals(String.Format("IE.{0}", uriScheme.ToUpper()), StringComparison.Ordinal))
                            defaultBrowserIsIE = true;
                    }
                    else
                    {
                        using (RegistryKey defaultBrowserPathRegKey = Registry.ClassesRoot.OpenSubKey(String.Format(@"{0}\shell\open\command", uriScheme)))
                        {
                            if (defaultBrowserPathRegKey != null)
                            {
                                if (Convert.ToString(defaultBrowserPathRegKey.GetValue(null)).ToLower().Contains("iexplore.exe"))
                                    defaultBrowserIsIE = true;
                            }
                        }
                    }

                    if (defaultBrowserIsIE)
                    {
                        using (RegistryKey ieRegKey = Registry.LocalMachine.OpenSubKey(@"Software\Microsoft\Internet Explorer"))
                        {
                            if (ieRegKey != null)
                            {
                                if (Convert.ToString(ieRegKey.GetValue("Version")).StartsWith("8.", StringComparison.Ordinal))
                                    ret = true;
                            }
                        }
                    }
                }
            }
            catch (Exception exc)
            {
                Logger.Write(exc, Severity.Warning);
            }

            return ret;
        }

        static string GetUrlOnWorkshare(FileMap filemap)
        {
            string wsUrl = string.Empty;
            try
            {
                if (filemap.WsFile != null)
                {
                    if (!string.IsNullOrEmpty(filemap.WsFile.RemoteUrl))
                    {
                        var uri = new Uri(filemap.WsFile.RemoteUrl);

                        //If IE is used as default browser and we use Process.Start(url) with url like http(s)://.../d/...
                        //it sends HTTP-request with Accept header */* and service sends HTTP-response with 401 status code
                        //in case of IE8 we should insert # before d/ to avoid this problem
                        //Note: We use this 'fix' because we don't have access to service source code
                        string urlPartD = (DefaultBrowserIsIE8(uri.Scheme) ? @"/#d/" : @"/d/");

                        wsUrl = string.Format("{0}://{1}{2}{3}", uri.Scheme, uri.Host, urlPartD, filemap.WsFile.DownloadPassword);
                    }
                }
                return wsUrl;
            }
            catch (Exception)
            {
                return string.Empty;
            }

        }

        public List<ItemMapActivityAction> Actions { get; set; }

        readonly List<FileActivityChange> _changes = new List<FileActivityChange>();
        public IEnumerable<FileActivityChange> Changes { get { return _changes; } }

        public bool HasChange(ChangeType changeType)
        {
            return Changes.Any(a => a.Type == changeType);
        }

        public void AddChange(FileActivityChange change)
        {
            change.Parent = this;
            _changes.Add(change);
        }

        public Exception Error { get; set; }

        public void ClearChanges()
        {
            _changes.Clear();
        }

        public virtual bool CanExecute(ItemMapActivityAction action)
        {
            return true;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncUploadFilesDialog/VMs/TrueSyncFilesScanDialogVm.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.Diagnostics;
using System.Linq;
using System.Windows.Input;
using Workshare.Components.Helpers;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.TrueSyncDialog;
using Workshare.Components.Views.TrueSyncDialog.VMs;
using Workshare.Components.Views.TrueSyncUploadFilesDialog.WorkUnits;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Components.Views.TrueSyncUploadFilesDialog.VMs
{
    public class TrueSyncFilesScanDialogVm : OwnViewModel<TrueSyncFilesScanDialogVm>
    {
        public enum StateEnum
        {
            Default,
            Loading,
            Error,
            NoInSyncedFolder,
            NoChangesDetected,
            NoAccessOnWorkshare
        }

        public bool ActivityToDisplay(UploadFileActivity activity)
        {
            return activity.Changes
                .Any(a => a.Type == ChangeType.VersionChangedAfterSend
                          || a.Type == ChangeType.NotSentVersion);
        }

        private StateEnum _state;

        public StateEnum State
        {
            get
            {
                return _state;
            }

            set
            {
                if (_state != value)
                {
                    _state = value;
                    this.PropertyHasChanged(a => a.State);
                }
            }
        }

        public ModuleBase Module { get; set; }
        public ObservableCollection<ParentScan> ParentScans { set; get; }

        #region Commands
        public RelayCommand ProcessActivityCommand { get; set; }
        public ICommand DiscardChangesCommand { get; set; }
        public ICommand CloseCommand { set; get; }
        public ICommand RescanCommand { get; set; }
        public ICommand UploadAllCommand { get; set; }
        public ICommand ViewOnlineCommand { get; set; }
        #endregion

        public string WorkspaceName { get; set; }

        string _fileName;
        public string FileName
        {
            get
            {
                return _fileName;
            }
            set
            {
                if (_fileName != null)
                {
                    _fileName = value;
                    this.PropertyHasChanged(p => p.FileName);
                }
            }
        }

        internal IModuleView View;
        private readonly DmsWorkerBase _dmsWorker;
        private readonly CommandInvoker _invoker;
        public  IDMSFile File { set; get; }

        public TrueSyncFilesScanDialogVm()
        {
            ParentScans = new ObservableCollection<ParentScan>();
            var parentScan = new ParentScan
            {
                Activities = new ObservableCollection<FileUploadActivityVm>()
            };
            var upDumme = new UploadFileActivity
            {
                State = UploadFileActivityState.Error,
                Error = new Integration.Exceptions.CheckedOutOnAnotherMachine("Us4er1"),
                Filename = "dummy3.doc"
            };
            parentScan.Activities.Add(new FileUploadActivityVm(upDumme));
            ParentScans.Add(parentScan);
        }

        public TrueSyncFilesScanDialogVm(ModuleBase module, CommandInvoker invoker)
        {
            ParentScans=new ObservableCollection<ParentScan>();
            Module = module;            
            View = module.Resolve<IModuleView>();
            _dmsWorker = module.Resolve<DmsWorkerBase>();
            this._invoker = invoker;

            CloseCommand = new RelayCommand(c => RaiseClose(false));

            ProcessActivityCommand = new RelayCommand( p =>
            {
                var action = p as DocumentActionVM;
                if (action != null && !action.Actions.Any())
                {
                    ExecuteDocumentAction(new[] {action});
                }
            });

            RescanCommand = new RelayCommand( p =>
            {
                var unit = new ScanWorkUnit(this, _dmsWorker);
                invoker.AddToQueue(unit);
            });

            DiscardChangesCommand = new RelayCommand(p =>
            {
                var service = module.Resolve<DiscardedService>();
                var item = p as IItemMapActivityVm;

                if (item != null && ((UploadFileActivityVm)p)._data.State != UploadFileActivityState.Uploading)
                {
                    service.Add(item.data as FileMapActivity);
                    item.IsDiscarded = true;
                    RaiseClose(true);
                }
            });

            this.ViewOnlineCommand = new RelayCommand(p =>
            {
                var item = p as IFileActivityBaseVm;
                if (item != null)
                {
                    ProcessUtils.StartProcess(item.ViewOnlineUrl);
                }
            });
        }

        public void Initialize(IDMSFile file)
        {
            File = file;
        }

        internal void ExecuteDocumentAction(IEnumerable<DocumentActionVM> actions)
        {
            var actionsCanBeExecuted = actions.Where(a => a.CanExecute()).ToList();
            if (actionsCanBeExecuted.Any())
            {
                var processWorkUnit = new ProcessWorkUnit(this, actionsCanBeExecuted);
                _invoker.AddToQueue(processWorkUnit);
            }
        }

        private Exception _error;
        public Exception Error {
            get { return _error; }
            set
            {
                if (_error != value)
                {
                    _error = value;
                    this.PropertyHasChanged(a=>a.Error);
                }
            }
        }

        private bool _isSharedExternally;
        public bool IsSharedExternally
        {
            set
            {
                if (_isSharedExternally != value)
                {
                    _isSharedExternally = value;
                    PropertyHasChanged(a => a.IsSharedExternally);
                }
            }
            get
            {
                return _isSharedExternally;
            }
        }
    }

  
}
<file_sep>/WSComponents/src/WSIntegration/Processor/DmsItems/BaseDmsVersion.cs
﻿
namespace Workshare.Integration.Processor.DmsItems
{
    public class BaseDmsVersion : BaseDMSItem
    {
        //public override void Apply(DMSVisitor visitor)
        //{
        //    visitor.Visit(this);
        //}
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/TrueSyncDialog/VMs/TrueSyncDialogViewModel.cs
﻿using System;
using System.Collections.Generic;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Linq;
using System.Windows.Data;
using System.Windows.Input;
using System.Windows.Threading;
using Workshare.Components.Helpers;
using Workshare.Components.Interfaces;
using Workshare.Components.Views.Common;
using Workshare.Components.Views.TrueSyncDialog.WorkUnits;
using Workshare.Integration.Common;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Modularity;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes;
using Workshare.Integration.Processor.Changes.Activities;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.Processor.Services;
using Workshare.Integration.SettingsStorage;
using Workshare.Integration.WsProxies;
using WorksharePlatform;

namespace Workshare.Components.Views.TrueSyncDialog.VMs
{
    public class TrueSyncDialogViewModel : OwnViewModel<TrueSyncDialogViewModel>
    {
        readonly Dispatcher _dispatcher;
        readonly IEnumerable<IDMSItem> _items;
        readonly IModuleView _view;
        private readonly SyncInfoService _syncInfoService;
        private System.Threading.Thread _scanThread;

        internal SummaryProcessResult ScanResult;

        public Guid Id { get; private set; }
        public ModuleBase Module { get; set; }
        // public enum StateEnum { Default, Scanning, NetError, NoFilesToSync, AllFilesAreSynced, RootFolderDeleted, Forbidden }
        public enum StateEnum { Default, Scanning, NetError, NoFilesToSync, AllFilesAreSynced, RootFolderDeleted, Forbidden,
            LoadingMore
        }

        private const int DefaultItemsPerPage = 50;
        public int ItemsPerPage = DefaultItemsPerPage ;

        public event EventHandler ScanCompleted;

        internal OwnCancellationTokenSource CancellationToken=new OwnCancellationTokenSource();

        StateEnum _state;
        public StateEnum State
        {
            get { return _state; }
            set
            {
                if (_state != value)
                {
                    _state = value;

                    PropertyHasChanged(p => p.State);
                }
            }
        }

        private bool _IsShowImportDiscarded = false;
        public bool IsShowImportDiscarded
        {
            get { return _IsShowImportDiscarded; }
            set
            {
                if (_IsShowImportDiscarded != value)
                {
                    _IsShowImportDiscarded = value;
                    UpdateButtonsState();
                }
            }
        }

        private bool _IsShowUploadDiscarded = false;
        public bool IsShowUploadDiscarded
        {
            get { return _IsShowUploadDiscarded; }
            set
            {
                if (_IsShowUploadDiscarded != value)
                {
                    _IsShowUploadDiscarded = value;
                    UpdateButtonsState();
                }
            }
        }

        public string WorkspaceName
        {
            get;set;
        }

        public bool IsViewClosed { get; private set; }

        public void OnViewClosing()
        {
            IsViewClosed = true;

            var import =
                AllActivities.OfType<ImportFileActivityVm>()
                    .Select(a => a._data)
                    .Where(d => (d.InKindOfErrorState() || d.InKindOfProceeedState()))
                    .OfType<FileMapActivity>().ToList();

            var upload =
                AllActivities.OfType<UploadFileActivityVm>()
                    .Select(a => a._data)
                    .Where(d => (d.InKindOfErrorState() || d.InKindOfProceeedState()))
                    .OfType<FileMapActivity>()
                    .ToList();

            import.AddRange(upload);
            ItemsToSkip = import;
            CancellationToken.Cancel();
            if (_scanThread != null) _scanThread.Abort();
        }

        public TrueSyncDialogViewModel()
        {
            
            Id = Guid.NewGuid();
            var dummy = new ImportFileActivity {Filename = "dummy1.doc"};
            new[]{
                new FileActivityChange
                {
                    Type=ChangeType.LocalChanged
                },
                new FileActivityChange
                {
                    Type=ChangeType.NamesDiffer
                },
                  new FileActivityChange
                  {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.FolderSharedWithOthers,
                    OtherMemebersCount = 12,
                    FolderSharedBy = new WsUser(new UserDetails
                    {
                      UserName  = "Vitaly"
                    })
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                }
            }.ToList().ForEach(dummy.AddChange);

            var dummy2 = new ImportFileActivity
            {
                Filename = "dummy2asdjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjjj.doc"
            };
            new[]{
                new FileActivityChange
                {
                    Type=ChangeType.BothChanged
                }
            }.ToList().ForEach(dummy2.AddChange);

            var dummy3 = new ImportFileActivity();
            dummy2.State = ImportFileActivityState.Error;
            dummy2.Error = new CheckedOutOnAnotherMachine("Us4er1");
            dummy3.Filename = "dummy3.doc";
            new[]{
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.BothChanged,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                },
                new FileActivityChange
                {
                    Type=ChangeType.Uploaded,
                }
            }.ToList().ForEach(dummy3.AddChange);

            var upDumme = new UploadFileActivity
            {
                Error = new CheckedOutOnAnotherMachine("Us4er1"),
                State = UploadFileActivityState.Error,
                Filename = "dummy3.doc"
            };

            AllActivities = new ObservableCollection<IItemMapActivityVm>
            {
                new ImportFileActivityVm(dummy),
                new ImportFileActivityVm(dummy2),
                new ImportFileActivityVm(dummy3),
                new ImportFileActivityVm(dummy),
                new UploadFileActivityVm(upDumme),
            };

            ImportActiveItems = new CollectionViewSource { Source = AllActivities }.View;

            ImportActiveItems.Filter = a => (a is ImportFileActivityVm) && FilterActivities(a) && !((ImportFileActivityVm)a)._data.IsDiscarded;

            UploadActiveItems = new CollectionViewSource { Source = AllActivities }.View;
            UploadActiveItems.Filter = a => (a is UploadFileActivityVm) && FilterActivities(a) && !((UploadFileActivityVm)a)._data.IsDiscarded;

            ItemsToSkip = new List<FileMapActivity>();
        }

        public TrueSyncDialogViewModel(ModuleBase module, CommandInvoker invoker, IEnumerable<IDMSItem> items,IModuleView view)
        {
            Id = Guid.NewGuid();
            Module = module;
            _items = items.ToList();
            _view = view;
            _dispatcher = Dispatcher.CurrentDispatcher;
            
            _syncInfoService = module.Resolve<SyncInfoService>();
            ItemsToSkip = new LinkedList<FileMapActivity>();
            var settingsStorage = module.Resolve<SettingsStorage>();
            ItemsPerPage = settingsStorage.GetInt(SettingsOptions.PagingSizeInTrueSync, DefaultItemsPerPage);
            ItemsPerPage = (ItemsPerPage > 0) ? ItemsPerPage : DefaultItemsPerPage;

            
            AllActivities = new ObservableCollection<IItemMapActivityVm>();

            ImportActiveItems = new CollectionViewSource {Source = AllActivities}.View;
            ImportActiveItems.Filter =
                a => (a is ImportFileActivityVm) && FilterActivities(a) && !((ImportFileActivityVm) a)._data.IsDiscarded;

            ImportDiscardedItems = new CollectionViewSource {Source = AllActivities}.View;
            ImportDiscardedItems.Filter =
                a => (a is ImportFileActivityVm) && FilterActivities(a) && ((ImportFileActivityVm) a)._data.IsDiscarded;

            UploadActiveItems = new CollectionViewSource {Source = AllActivities}.View;
            UploadActiveItems.Filter =
                a => (a is UploadFileActivityVm) && FilterActivities(a) && !((UploadFileActivityVm)a)._data.IsDiscarded && !((UploadFileActivityVm)a)._data.DmsFile.CheckedOut;

            UploadDiscardedItems = new CollectionViewSource {Source = AllActivities}.View;
            UploadDiscardedItems.Filter =
                a => (a is UploadFileActivityVm) && FilterActivities(a) && ((UploadFileActivityVm) a)._data.IsDiscarded;

            CloseCommand = new RelayCommand(c => RaiseClose(false));

            this.WorkspaceName = _items.Select(p => p.Name).FirstOrDefault() ?? "Unknown";

            this.ProcessActivityCommand = new RelayCommand(p =>
            {
                var action = p as DocumentActionVM;
                if (action != null && action.CanExecute())
                {
                    var u = new ProcessWorkUnit(Module, this._view, new[] {action}, this);
                    invoker.AddToQueue(u);
                }
            });

            this.RescanCommand = new RelayCommand(p =>
            {
                var unit = new ScanWorkUnit(this._view, this._items, this, _scanThread);
                invoker.AddToQueue(unit);
            });

            LoadMoreCommand = new RelayCommand(p =>
            {
                var unit = new ScanWorkUnit(this._view, this._items, this, _scanThread, true);
                invoker.AddToQueue(unit);
            });

            this.ImportAllCommand = new RelayCommand(p =>
            {
                RaiseClose(false);
                var activities = ImportActiveItems.OfType<ImportFileActivityVm>().ToList();
                var actionsToExecute =
                    GetAcitionsToImportAll(
                        activities.Select(a => a._data)
                            .Where(
                                a =>
                                    !a.InKindOfErrorState() && !a.InKindOfProceeedState() &&
                                    !a.InKindOfProcessingState())
                            .ToList());
                
                foreach (var item in actionsToExecute)
                {
                    ProcessActivityCommand.Execute(new DocumentActionVM(item,
                        activities.First(a => a.Id == item.ActivityId)));
                }
            });

            this.BreakLinksForRootCommand = new RelayCommand(p =>
            {
                var breakWorkUnit = new BreakFolderLinkWorkUnit(this, view);
                breakWorkUnit.Execute();
                this.RaiseClose(true); //strat old sync process
            });

            this.UploadAllCommand = new RelayCommand(p =>
            {
                foreach (var item in UploadActiveItems.OfType<UploadFileActivityVm>())
                {
                    if (item.State == UploadFileActivityState.Scanned)
                    {
                        ProcessActivityCommand.Execute(item.Actions.FirstOrDefault());
                    }
                }

                RaiseClose(false);
            });

            this.DiscardChangesCommand = new RelayCommand(p =>
            {
                var service = module.Resolve<DiscardedService>();
                var item = p as IItemMapActivityVm;

                if (item != null)
                {
                    service.Add(item.data as FileMapActivity);
                    item.IsDiscarded = true;


                    if (item is ImportFileActivityVm)
                    {
                        ImportActiveItems.Refresh();
                        ImportDiscardedItems.Refresh();
                    }
                    else
                    {
                        UploadActiveItems.Refresh();
                        UploadDiscardedItems.Refresh();
                    }

                    if (!HasActiveImportItems && !HasActiveUploadItems)
                    {
                        State = StateEnum.AllFilesAreSynced;
                    }
                    UpdateButtonsState();
                }
            });

            this.ViewOnlineCommand = new RelayCommand(p =>
            {
                var item = p as IFileActivityBaseVm;
                if (item != null)
                {
                    ProcessUtils.StartProcess(item.ViewOnlineUrl);
                }
            });



            this.ViewDiscardedCommand = new RelayCommand(p =>
            {
                this.State = StateEnum.Default;
            });

            this.ViewOnlineWorkspaceCommand = new RelayCommand(param =>
            {
                if (ScanResult != null)
                {
                    var url =
                        ScanResult.Maps.OfType<FolderMap>()
                            .Where(p => p.WsFolder != null)
                            .Select(p => p.WsFolder.Url)
                            .FirstOrDefault();
                    return !string.IsNullOrEmpty(url);
                }
                return false;
            },
                param =>
                {
                    if (ScanResult != null)
                    {
                        var url =
                            ScanResult.Maps.OfType<FolderMap>()
                                .Where(p => p.WsFolder != null)
                                .Select(p => p.WsFolder.Url)
                                .FirstOrDefault();
                        ProcessUtils.StartProcess(url);
                    }
                });

        }

        private IEnumerable<ImportDocumentAction> GetAcitionsToImportAll(List<ImportFileActivity> importActivities)
        {
            return _view.SelectActions(importActivities);
        }

        private void UpdateButtonsState()
        {
            PropertyHasChanged(a => a.ImportAllButtonVisible);
            PropertyHasChanged(a => a.UploadAllButtonVisible);
        }

        public bool ImportAllButtonVisible
        {
            get
            {
                if (IsShowImportDiscarded) return false;
                else return HasActiveImportItems;
            }
        }

        public bool UploadAllButtonVisible
        {
            get
            {
                if (IsShowUploadDiscarded) return false;
                else return HasActiveUploadItems;
            }
        }

        public bool HasActiveImportItems
        {
            get
            {
                return ImportActiveItems.OfType<object>().Any(); //TODO look for better line
            }
        }
        public bool HasActiveUploadItems
        {
            get
            {
                return UploadActiveItems.OfType<object>().Any(); //TODO look for better line
            }
        }

        bool OnlyNotSentImportItems()
        {
            var importActivities = AllActivities.OfType<ImportFileActivityVm>().ToList();
            var uploadActivities = AllActivities.OfType<UploadFileActivityVm>().ToList();
            return (importActivities.All(a => a._data.Changes.Any(p => p.Type == ChangeType.NotSent)) || !importActivities.Any())
                && (uploadActivities.All(a => !a._data.Changes.Any()) || !uploadActivities.Any());
        }

        public ObservableCollection<IItemMapActivityVm> AllActivities { private set; get; }
        public IEnumerable<FileMapActivity> ItemsToSkip { get; set; }

        public ICollectionView ImportActiveItems { set; get; }
        public ICollectionView UploadActiveItems { set; get; }
        public ICollectionView ImportDiscardedItems { set; get; }
        public ICollectionView UploadDiscardedItems { set; get; }

        public IItemMapActivityVm CreateVm(object a)
        {
            var data = a as ImportFileActivity;
            if (data != null)
            {
                return new ImportFileActivityVm(data);
            }
            var activity = a as UploadFileActivity;
            return activity != null ? new UploadFileActivityVm(activity) : null;
        }

        public bool HasMore
        {
            get
            {
                var res = ScanResult;
                var iterator = (res == null) ? null : res.Iterator;
                return iterator != null && iterator.HasMore;
            }
        }

        private void RemoveDeletedActivitiesIfNeed(List<FileMapActivity> activities)
        {
            var deletedActivities = activities.Where(a => a is ImportFileActivity && (a as ImportFileActivity).State == ImportFileActivityState.Scanned && a.Changes.Any(c => c.Type == ChangeType.RemoteDeleted)).ToList();
            if (deletedActivities.Count > 0)
            {
                var uploadedActivities = activities.Where(a => a is UploadFileActivity && (a as UploadFileActivity).State == UploadFileActivityState.Uploaded).ToList();
                if (uploadedActivities.Count > 0)
                {
                    var deletedActivitiesToHide = uploadedActivities.Join(deletedActivities, u => u.MapId, d => d.MapId, (u, d) => d).ToList();
                    deletedActivitiesToHide.ForEach(d => activities.Remove(d));

                    var deletedDiscardedActivities = deletedActivitiesToHide.Where(a => a.IsDiscarded).ToList();
                    deletedDiscardedActivities.ForEach(a =>
                    {
                        var fileMapActivity = a as FileMapActivity;
                        if (fileMapActivity != null)
                        {
                            var service = Module.Resolve<DiscardedService>();
                            service.Remove(fileMapActivity);
                        }
                    });
                }
            }
        }

        public void OnCompleted(List<ItemMap> errors, IEnumerable<FileMapActivity> newActivities, SummaryProcessResult scanresult)
        {
            // pass here processedIds. After get errors from newActivities, and save errors to (global?) list

            var newScanCompleed = this.ScanResult != scanresult;
            ScanResult = scanresult;

            var newActivitiesList = newActivities.ToList();

            RemoveDeletedActivitiesIfNeed(newActivitiesList);

            var itemsToUpdate = AllActivities.Where(a => newActivitiesList.Any(c => c == a.data)).ToList();
            var pairsToUpdate = itemsToUpdate.Select(p => new KeyValuePair<IItemMapActivityVm, ItemMapActivity>(p, newActivitiesList.First(a => a == p.data))).ToList();
            var itemsToDelete = AllActivities.Except(itemsToUpdate).ToList();
            var itemsToAdd = newActivitiesList.Where(c => AllActivities.All(p => p.data != c)).Select(CreateVm).Where(a => a != null).ToList();      
            
            System.Net.WebException ex;
            this._dispatcher.Invoke(new Action(() =>
            {
                foreach (var i in itemsToAdd)
                {
                    AllActivities.Add(i);
                }
                foreach (var i in itemsToDelete)
                {
                    AllActivities.Remove(i);
                }
                foreach (var i in pairsToUpdate)
                {
                    i.Key.PropertyChangedAll();
                }
                Exception exception = null;
                
                if (errors.Any(p => p.Error.IsConnectionError()))
                {
                    this.State = StateEnum.NetError;
                }
                else if (errors.Any(p => p.Error.IsUnauthorized()))
                {
                    this.State = StateEnum.Forbidden;
                }
                /*else if (this.ScanResult.Maps.First<ItemMap>().Maps.Any(x => { exception = x.Error; return x.ProcessState == ProcessState.Error; }) &&
                    (ex = exception as System.Net.WebException) != null && ex.IsStatusCode((System.Net.HttpStatusCode)403))*/
                else if ((this.ScanResult.Maps.All((x => { return x.ProcessState == ProcessState.Error && x.Error != null && x.Error is System.Net.WebException && (x.Error as System.Net.WebException).IsStatusCode((System.Net.HttpStatusCode)403); })) || 
                    (this.ScanResult.Maps.First<ItemMap>().Maps.All(x => { return x.ProcessState == ProcessState.Error && x.Error != null && x.Error is System.Net.WebException && (x.Error as System.Net.WebException).IsStatusCode((System.Net.HttpStatusCode)403);}))))
                {
                    this.State = StateEnum.Forbidden;
                }
                else if (RootFolderDeletedOnWs())
                {
                    this.State = StateEnum.RootFolderDeleted;
                }
                else if (OnlyNotSentImportItems())
                {
                    this.State = StateEnum.NoFilesToSync;
                }
                else if (!HasActiveImportItems && !HasActiveUploadItems && !HasMore)
                {
                    this.State = StateEnum.AllFilesAreSynced;
                }
                else
                {
                    this.State = StateEnum.Default;                   
                }

                this.PropertyHasChanged(a => a.HasMore);

                if (newScanCompleed && ScanCompleted != null)
                {
                    ScanCompleted(this, EventArgs.Empty);
                }

                this.ViewOnlineWorkspaceCommand.RaiseCanExecutechanged();

                UpdateButtonsState();
            }));
        }

        private bool RootFolderDeletedOnWs()
        {
            var folder = ScanResult.Maps.OfType<FolderMap>();
            return folder.All(f => !f.HasRemote()&&f.ProcessState==ProcessState.Scanned &&  _syncInfoService.IsLinked(f.LocalFolder));
        }

        public static bool FilterActivities(object activity)
        {
            var importActivity = activity as ImportFileActivity;
            var vm = activity as ImportFileActivityVm;
            if (vm != null)
            {
                importActivity = vm._data;
            }

            if (importActivity != null)
            {
                if (importActivity.InKindOfProceeedState() || importActivity.InKindOfErrorState())
                {
                    return importActivity.IsLinked;
                }

                var allowedTypesToShow = new[] { 
                                                    ChangeType.BothChanged, 
                                                    ChangeType.RemoteAdded, 
                                                    ChangeType.RemoteChanged, 
                                                    ChangeType.RemoteDeleted
                                                };

                return importActivity.Changes.Any(a => allowedTypesToShow.Contains(a.Type));
            }
            var uploadActivity = activity as UploadFileActivity;
            var activityVm = activity as UploadFileActivityVm;
            if (activityVm != null)
            {
                uploadActivity = activityVm._data;
            }

            if (uploadActivity != null)
            {
                if (uploadActivity.InKindOfProceeedState() || uploadActivity.InKindOfErrorState())
                {
                    return true;
                }

                var allowedTypesToShow = new[] { 
                    ChangeType.NotSentVersion,
                    ChangeType.VersionChangedAfterSend
                };

                return uploadActivity.Changes.Any(a => allowedTypesToShow.Contains(a.Type));
            }
            return true;
        }

        #region Commands
        public ICommand ImportAllCommand { get; set; }
        public ICommand BreakLinksForRootCommand { get; set; }

        public RelayCommand ProcessActivityCommand { get; set; }

        public ICommand DiscardChangesCommand { get; set; }
        public ICommand CloseCommand { set; get; }
        public ICommand ViewOnlineCommand { get; set; }
        public ICommand ViewDiscardedCommand { get; set; }
        public ICommand RescanCommand { get; set; }
        public RelayCommand ViewOnlineWorkspaceCommand { set; get; }
        public RelayCommand LoadMoreCommand { set; get; }
        public ICommand UploadAllCommand { get; set; }
        #endregion

    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Command.cs
﻿using System;
using System.Collections;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Windows.Forms;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components.Common;
using Workshare.Components.WSLogger;
using Workshare.IManage.Contrete;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Services;

namespace Workshare.IManage
{
    public enum iManType {FileSite, DeskSite};

    public abstract class Command : ICommand, ICommand2
    {

        readonly string GETSELECTEDITEMS = "SelectedIManObjects";
        readonly string GETSELECTEDFOLDER = "SelectedFolderObject";
        readonly string GETDMS = "IManDMS";
        readonly string GETDESTINATIONOBJECT = "IManDestinationObject";

        internal SyncInfoService syncService = Application.iManInstance.Module.Resolve<SyncInfoService>();

        public virtual int Accelerator
        {
            get
            {
                return 0;
            }
            set
            {
            }
        }

        void SafeCOMCall(Action call)
        {
            try
            {
                call();
            }
            catch (System.Runtime.InteropServices.COMException comException)
            {
                Logger.WriteError((Exception)comException);
                if (comException.ErrorCode == -2147221399 || comException.ErrorCode == -2147221402 || comException.ErrorCode == -2147221503)
                {
                    WSApplication.Instance.View.ShowError((Workshare.Integration.Exceptions.BaseException)new Workshare.Integration.Exceptions.OfflineException());
                }
                else
                {
                    Logger.WriteError(comException);

#if DEBUG
                    MessageBox.Show(comException.ToString(), "FIX ME PLEASE!!!!..");
#else
                MessageBox.Show(string.Format("Unexpected error during command execution occured:\n{0}\n Please try again and if error is persisted contact support.",comException.Message),"Unexpected error");
#endif
                }
            }
            catch (Exception ex)
            {
                Logger.WriteError(ex);

#if DEBUG
                MessageBox.Show(ex.ToString(), "FIX ME PLEASE!!!!...");
#else
                if (ex is BaseException)
                {
                    WSApplication.Instance.View.ShowError(ex);
                }
                else
                {
                    MessageBox.Show(string.Format("Unexpected error during command execution occured:\n{0}\n Please try again and if error is persisted contact support.", ex.Message), "Unexpected error");
                }
#endif
            }
        }

        public virtual object Bitmap
        {
            get
            {
                return null;
            }
            set
            {
            }
        }

        ContextItems m_Context = null;
        public virtual ContextItems Context
        {
            get
            {
                return m_Context;
            }
        }

        public virtual void ExecuteAction()
        {
            if (!Application.iManInstance.Presenter.LoginIfNeeded())
            {
                return;
            }
        }

        public void Execute()
        {
            SafeCOMCall(() =>
                {
                    ExecuteAction();
                });
        }

        public virtual string HelpFile
        {
            get
            {
                return string.Empty;
            }
            set
            {
            }
        }

        public virtual int HelpID
        {
            get
            {
                return 0;
            }
            set
            {
            }
        }

        public virtual string HelpText
        {
            get
            {
                return "HelpText";
            }
            set
            {
            }
        }

        public virtual void InitializeAction(ContextItems Context)
        {

        }

        public void Initialize(ContextItems Context)
        {
            SafeCOMCall(() =>
                {
                    m_Context = Context;
                    InitializeAction(m_Context);

                });
        }

        public virtual string MenuText
        {
            get
            {
                return "MenuText";
            }
            set
            {
            }
        }

        public virtual string Name
        {
            get
            {
                return "Name";
            }
            set
            {

            }
        }

        public virtual int Options
        {
            get
            {
                return 0;
            }
            set
            {
            }
        }

        public virtual int Status
        {
            get
            {
                //Context.OfType<object>().ToList().ForEach(p => System.Diagnostics.Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                return (int)((!Application.iManInstance.Presenter.IsAnyItemInProgress() && IsAnyServerAvailable()) ? CommandStatus.nrActiveCommand : CommandStatus.nrGrayedCommand);
            }
            set
            {
                
            }
        }

        public virtual Commands SubCommands
        {
            get
            {
                return null;
            }
            set
            {

            }
        }

        public virtual string Title
        {
            get
            {
                return "Title";
            }
            set
            {
            }
        }

        public virtual CommandType Type
        {
            get
            {
                return CommandType.nrStandardCommand;
            }
            set
            {
            }
        }

        public virtual void UpdateAction()
        {
        }

        public void Update()
        {
            SafeCOMCall(() =>
                {
                    UpdateAction();
                });
        }

        #region privates

        protected bool IsAnyServerAvailable()
        {
            try
            {
                var dms = Context.Item(GETDMS) as IManDMS;
                return dms != null && dms.Sessions != null && dms.Sessions.Count > 0;
            }
            catch
            { }
            //var ns = Context.Item("NRTSessions") as NRTSessions;
            return false;
        }

        protected virtual List<IDMSItem> GetContextItems()
        {
            var selectedItems = new List<IDMSItem>();
            var items = GetSelectedItemsInContext();

            if (items != null)
            {
                var contextFolder = GetContextFolder();

                if (string.IsNullOrEmpty(WSApplication.Instance.ServerKey))
                {
                    WSApplication.Instance.ServerKey = SetServerKey(contextFolder);
                }


                foreach (object item in items)
                {
                    if (item is IManFolder)
                    {
                        var manFolder = new ManFolder((IManFolder)item);
                        selectedItems.Add(manFolder);
                        
                    }
                    else if (item is IManDocument)
                    {
                        if (contextFolder != null)
                        {
                            selectedItems.Add(new ManFile((IManDocument) item, contextFolder).GetLatest());
                        }
                        else
                        {
                            selectedItems.Add(new ManFile((IManDocument)item).GetLatest());
                        }
                    }
                }
            }
            return selectedItems;
        }

        private string SetServerKey(IManFolder _folder)
        {
            try
            {
                var session = (_folder == null)? Context.Item("SelectedIManSession") as IManSession:_folder.Database.Session;
                var nrtdms = session.DMS.ObjectID;
                IPAddress server_ip;
                var ipAddres = "!server:";

                if (IPAddress.TryParse(session.ServerName, out server_ip))
                {
                    ipAddres += session.ServerName.Replace(".", "_");
                }
                else
                {
                    ipAddres += GetServerIp(session.ServerName);
                }

                return nrtdms + ipAddres;
            }
            catch
            {
                return "";
            }
        }

        private string GetServerIp(string hostname)
        {
            IPHostEntry entry = Dns.GetHostEntry(hostname);
            return entry.AddressList.FirstOrDefault().ToString().Replace(".","_");
        }

        protected iManType GetClientType()
        {
            string applicationName = "DeskSite";
            try
            {
                IManDMS _dms = Context.Item(GETDMS) as IManDMS;
                applicationName = _dms.ApplicationName;
            }
            catch (Exception ex)
            {
                Logger.Write(ex, Severity.Warning);
            }
            if (string.Compare(applicationName, "FileSite", StringComparison.InvariantCultureIgnoreCase) == 0)
            {
                return iManType.FileSite;
            }
            else
            {
                return iManType.DeskSite;
            }
        }

        protected IManFolder GetContextFolder()
        {
            try
            {
                return Context.Item(GETSELECTEDFOLDER) as IManFolder;
            }
            catch (Exception ex)
            {
                return null;
            }
        }

        protected List<IDMSFolder> GetSelectedFolders()
        {
            try
            {
                var folder = Context.Item(GETSELECTEDFOLDER) as IManFolder;
                if (folder != null)
                {
                    if (string.IsNullOrEmpty(WSApplication.Instance.ServerKey))
                    {
                        WSApplication.Instance.ServerKey = SetServerKey(folder);
                    }
                    return new List<IDMSFolder> { new ManFolder(folder) };
                }
            }
            catch (ArgumentException ex)
            {
                Logger.WriteWarning(ex.Message);
                
            }
            return new List<IDMSFolder>();
        }

        protected IEnumerable GetSelectedItemsInContext()
        {
            if (GetClientType() == iManType.DeskSite)
            {
                try
                {
                    //Context.OfType<object>().ToList().ForEach(p => Trace.TraceInformation((p.GetType().InvokeMember("Name", System.Reflection.BindingFlags.GetProperty, null, p, new object[0]) ?? "-").ToString()));
                    //Trace.TraceInformation("Current folder is = " + ((IManFolder)Context.Item("SelectedFolderObject")).Name);
                    return Context.Item(GETSELECTEDITEMS) as IEnumerable ?? new object[0];

                }
                catch (ArgumentException ex)
                {
                    try
                    {
                        Update();
                        var folder = Context.Item(GETSELECTEDFOLDER) as IManFolder;
                        if (folder != null)
                        {
                            return new object[] { folder };
                        }
                    }
                    catch (ArgumentException)
                    {
                    }

                } // not selected items in the context
            }
            else // if it's filesite
            {
                bool folderObject = false;
                try
                {
                    if (Context != null)
                    {
                        IManFolder obj = Context.Item(GETDESTINATIONOBJECT) as IManFolder;
                        if (obj != null)
                        {
                            folderObject = true;
                        }
                    }

                }
                catch
                {
                    folderObject = false;
                }

                if (folderObject)
                {
                    var folder = Context.Item(GETDESTINATIONOBJECT) as IManFolder;
                    return new object[] { folder };
                }
                else
                {
                    IEnumerable obj = null;
                    try
                    {
                        obj = Context.Item(GETSELECTEDITEMS) as IEnumerable;
                    }
                    catch
                    {
                        /*Application.iManInstance.View.ShowErrors(new List<Workshare.Integration.Exceptions.ItemException>() { new Workshare.Integration.Exceptions.ItemException() 
                        { Item = null, Error = new Workshare.Integration.Exceptions.DMSUnAuthorizedException() } });*/
                    }
                    return obj;
                }

            }
            return new object[0];
        }


        #endregion

        public virtual object LargeBitmap
        {
            get { return Bitmap; }
            set { }
        }

        public string TextLabel
        {
            get { return Title; }
            set { }
        }

        public void ShowError(BaseException ex, IDMSItem item)
        {
            Logger.WriteError(ex);
            Application.iManInstance.View.ShowErrors(new List<ItemException>()
                {
                    new ItemException()
                    {
                        Item = item,
                        Error = ex
                    }
                });
        }

        public void ShowErrors(BaseException ex, List<IDMSItem> items)
        {
            Logger.WriteError(ex);
            Application.iManInstance.View.ShowErrors(items.ConvertAll(i => new ItemException() { Item = i, Error = ex }));
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/Common/BasePropertyChanged.cs
﻿using System;
using System.ComponentModel;
using System.Linq.Expressions;

namespace Workshare.Components.Views.Common
{
    public abstract class BasePropertyChanged<T>
          : INotifyPropertyChanged
    {
        #region Property Change Event

        public event PropertyChangedEventHandler PropertyChanged;

        public void PropertyHasChanged(string propertyName, string method = "Blank")
        {
            var handler = PropertyChanged;
            if (handler != null)
            {
                handler(this, new PropertyChangedEventArgs(propertyName));
            }
        }

        public void PropertyChangedAll()
        {
            PropertyHasChanged(string.Empty);
        }

        public virtual void PropertyHasChanged(Expression<Func<T, object>> property)
        {
            if (property == null)
            {
                return;
            }

            var memberExp = property.Body as MemberExpression;

            if (memberExp == null)
            {
                var ur = property.Body as UnaryExpression;
                if (ur != null)
                {
                    memberExp = ur.Operand as MemberExpression;
                    if (memberExp == null)
                    {
                        return;
                    }
                }
                else
                {
                    return;
                }
            }
            PropertyHasChanged(memberExp.Member.Name, memberExp.Member.ReflectedType.Name);
        }

        #endregion
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/Contrete/ImportDialog.cs
﻿using System;
using System.IO;
using Com.Interwoven.Worksite.iManExt;
using Com.Interwoven.WorkSite.iManage;
using Workshare.Components.WSLogger;

namespace Workshare.IManage.Contrete
{
    class ImportDialog
    {
        ManFolder _folder;
        string _filePath = string.Empty;
        IManDatabase _datebase;
        string _name;
        public void Initialize(ManFolder parentFolder, string filePath, string name, IManDatabase datebase)
        {
            this._folder = parentFolder;
            this._filePath = filePath;
            this._name = name;
            this._datebase = datebase;
        }

        public ManFile AddedFile { set; get; }

        public void ShowDialog()
        {
            Logger.WriteTrace("Displaying import dialog.");
            Components.Presenter.ModulePresenterBase.InvokeInSTAThreadIfNeed(() =>
            {
                try
                {
                    var added = false;
                    var importCmd = new ImportCmdClass();
                    importCmd._ICommandEvents_Event_OnInitDialog += objDlg =>
                    {
                        var dlg = objDlg as NewProfileDlg;
                        if (dlg != null)
                        {
                            // commited through the task 16976
                            //var oDocClasses = m_folder.Database.SearchDocumentClasses("", imSearchAttributeType.imSearchBoth, true);
                            //var oDocClass = (oDocClasses.Contains("DOC")) ? oDocClasses.ItemByName("DOC") : null;

                            dlg.SetAttributeValueByID(AttributeID.nrDescription, _name, true);
                            //dlg.SetAttributeValueByID(AttributeID.nrClass, oDocClass, true);
                            dlg.SetAttributeValueByID(AttributeID.nrAuthor, _datebase.Session.UserID, true);
                        }
                    };

                    importCmd.PostOnOK += o =>
                    {
                        Logger.Write("PostOk event", Severity.Trace);
                        added = true;
                    };

                    var contextItems = new ContextItems
                    {
                        {"ParentWindow", (int) Application.iManInstance.View.ActivieWindowHandle},
                        {"DestinationObject", (_folder != null) ? (object) _folder.m_folder : _datebase},
                        {"IManExt.Import.FileName", _filePath},
                        {"IManExt.OpenCmd.NoCmdUI", false},
                        {"IManExt.NewProfile.ProfileNoUI", false},
                        {"IManExt.Import.KeepCheckedOut", CheckinOptions.nrDontKeepCheckedOut}
                    };

                    importCmd.Initialize(contextItems);
                    importCmd.Update();

                    if (importCmd.Status == (int)CommandStatus.nrActiveCommand)
                    {
                        Logger.Write("Executing import cmd", Severity.Trace);
                        IManDocument doc = null;

                        using (HooksDisabler.Create())
                        {
                            importCmd.Execute();
                        }

                        var brefresh = (bool)contextItems.Item("IManExt.Refresh");
                        if (brefresh)
                        {
                            //Succeeded in importing a document to WorkSite
                            doc = (IManDocument)contextItems.Item("ImportedDocument");
                        }
                        if (added)
                        {
                            AddedFile = new ManFile(doc, _folder == null ? null : _folder.m_folder);
                        }
                    }
                    else
                    {
                        throw new Exception("You cannot import file.");
                    }
                }
                finally
                {
                    try
                    {
                        File.Delete(_filePath);
                    }
                    catch (Exception e)
                    {
                        Logger.Write(e, Severity.Error);
                    }
                }
            });
        }
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Changes/Activities/ActivityExts.cs
﻿using System.Collections.Generic;
using System.Linq;
using Workshare.Integration.Exceptions;

namespace Workshare.Integration.Processor.Changes.Activities
{
    public static class ActivityExts
    {
        public static string AsString(this IEnumerable<FileActivityChange> change)
        {
            var res = string.Empty;
            change.ToList().ForEach(a => res += a.Type + ",");
            return res;
        }

        public static IEnumerable<ItemMapActivityAction> GetAllActions(IEnumerable<ItemMapActivityAction> activityVm)
        {
            var res = new List<ItemMapActivityAction>();

            foreach (var documentAction in activityVm.OfType<ItemMapActivityAction>())
            {
                if (documentAction.Actions != null && documentAction.Actions.Any())
                {
                    res.AddRange(GetAllActions(documentAction.Actions.ToList()));
                }
                else if(!(documentAction is ItemMapActivityActionGroup))
                {
                    res.Add(documentAction);
                }
            }

            return res.Distinct().ToList();
        }

        public static IEnumerable<ItemMapActivityAction> GetAllAvailableActions(this FileMapActivity activity)
        {
            if(activity.Actions==null)return new List<ItemMapActivityAction>();
            return GetAllActions(activity.Actions);
        }

      

    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Services/WebDataStorageService.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Net;
using System.Text;
using Workshare.Components.WSLogger;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.WsProxies;

namespace Workshare.Integration.Processor.Services
{

    class CacheDataObject
    {
        public string Data { get; set; }
        public DateTime AddDate { get; set; }
        public DateTime ObjectDate { get; set; }
    }

    public class WebDataStorageService
    {
        private static int AllowedTimeSpan = 3000;
        Dictionary<string, object> _Acc_cache = new Dictionary<string, object>();
        Dictionary<string, object> _User_cache = new Dictionary<string, object>();

        IAuthProvider _auth;
        WsProxy _proxy;

        WsUser User
        {
            get
            {
                return (_auth == null) ? null : _auth.GetCurrentWSUser2();
            }
        }

        public WebDataStorageService(IAuthProvider auth, WsProxy proxy)
        {
            _auth = auth;
            _proxy = proxy;
        }

        #region Work with account data  
        void UpdateAccountCache(string _key, CacheDataObject _data)
        {
            if (_Acc_cache.ContainsKey(_key))
            {
                _Acc_cache[_key] = _data;
            }
            else
            {
                _Acc_cache.Add(_key, _data);
            }
        }

        public void AddAccountData(string _key, string _data, DateTime objectUpdateDate)
        {
            var cdo = new CacheDataObject()
            {
                Data = _data,
                AddDate = DateTime.Now,
                ObjectDate = objectUpdateDate
            };

            _proxy.AddAccountDataToWDS(User, _key, _data);
            UpdateAccountCache(_key, cdo);
        }

        public void DeleteAccountData(string _key)
        {
            _proxy.DeleteAccountDataOnWDS(User, _key);
            UpdateAccountCache(_key, null);
        }

        public string GetAccountData(string _key, DateTime objectUpdateDate, bool ForceRequest = true)
        {
            if (_Acc_cache.ContainsKey(_key))
            {
                var cdo = _Acc_cache[_key] as CacheDataObject;
                if (cdo == null && !ForceRequest)
                {
                    return null;
                }
                else
                {
                    if (cdo != null)
                    {
                        TimeSpan ts = DateTime.Now - cdo.AddDate;
                        if ((ts.TotalMilliseconds <= AllowedTimeSpan || !ForceRequest) && (objectUpdateDate != DateTime.MinValue && objectUpdateDate == cdo.ObjectDate))
                        {
                            return (cdo == null) ? null : cdo.Data;
                        }
                    }
                }
            }

            string _data = GetDataFromWDS(_proxy.GetAccountDataFromWDS, User, _key);

            var ncdo = new CacheDataObject()
            {
                Data = _data,
                AddDate = DateTime.Now,
                ObjectDate = objectUpdateDate
            };
            UpdateAccountCache(_key, ncdo);
            return _data;
        }
        #endregion 

        #region Work with user data

        void UpdateUserCache(string _key, CacheDataObject _data)
        {
            if (_User_cache.ContainsKey(_key))
            {
                _User_cache[_key] = _data;
            }
            else
            {
                _User_cache.Add(_key, _data);
            }
        }

        public void AddUserData(string _key, string _data, DateTime objectUpdateDate)
        {
            var cdo = new CacheDataObject()
            {
                Data = _data,
                AddDate = DateTime.Now,
                ObjectDate = objectUpdateDate
            };

            _proxy.AddUserDataToWDS(User, _key, _data);
            UpdateUserCache(_key, cdo);
        }

        public void DeleteUserData(string _key)
        {
            _proxy.DeleteUserDataOnWDS(User, _key);
            UpdateUserCache(_key, null);
        }

        public string GetUsertData(string _key, DateTime objectUpdateDate, bool ForceRequest = true)
        {
            if (_User_cache.ContainsKey(_key) && !ForceRequest)
            {
                var cdo = _User_cache[_key] as CacheDataObject;
                if (cdo == null && !ForceRequest)
                {
                    return null;
                }
                else
                {
                    if (cdo != null)
                    {
                        TimeSpan ts = DateTime.Now - cdo.AddDate;
                        if (ts.TotalMilliseconds <= AllowedTimeSpan || !ForceRequest)
                        {
                            return (cdo == null) ? null : cdo.Data;
                        }
                    }
                }
            }

            var _data = GetDataFromWDS(_proxy.GetUserDataFromWDS, User, _key);//_proxy.GetUserDataFromWDS(User, _key);

            var ncdo = new CacheDataObject()
            {
                Data = _data,
                AddDate = DateTime.Now,
                ObjectDate = objectUpdateDate
            };
            UpdateUserCache(_key, ncdo);
            return _data;
            
        }
        #endregion

        #region Start scan for all items
        #endregion

        #region Support methods
        string GetDataFromWDS(Func<WsUser, string, string> funct, WsUser _user, string _key)
        {
            byte counter = 0;
            while (counter < 3)
            {
                try
                {
                    var _data = funct(_user, _key);
                    return _data;
                }
                catch (WebException e)
                {
                    if (e.Response != null && e.Response is HttpWebResponse &&
                        ((HttpWebResponse)e.Response).StatusCode == HttpStatusCode.NotFound)
                    {
                        return null;
                    }
                    else if (e.Status == WebExceptionStatus.Timeout ||
                        (e.Response != null && e.Response is HttpWebResponse &&
                        (((HttpWebResponse)e.Response).StatusCode == HttpStatusCode.RequestTimeout || (((HttpWebResponse)e.Response).StatusCode == HttpStatusCode.GatewayTimeout))))
                    {
                        counter++;
                        Logger.Write("Try to get data from WDS, attempt - " + (counter + 1).ToString(), e, Severity.Error);
                    }
                    else
                    {
                        if (e.IsConnectionError())
                            throw new OfflineException();
                        else
                            throw new CannotGetDataFromServer();
                    }
                }
                catch (UnauthorizedAccessException)
                {
                    throw;
                }
                catch (Exception ex)
                {
                    Logger.Write("Critical exeption during recieve data from WDS ", ex, Severity.Error);
                    throw new CannotGetDataFromServer();
                }
            }

            if (counter > 2)
            {
                throw new CannotGetDataFromServer();
            }
            return null;
        }
        #endregion
    }
}
<file_sep>/WSComponents/src/WSIntegration/Processor/Maps/MapAnylizer.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Workshare.Components.WSLogger;
using Workshare.Integration;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor.Strategies;

namespace Workshare.Integration.Processor.Maps
{
    public class MapAnylizer
    {
        public IAuthProvider _auth;
        private readonly DmsWorkerBase _dmsWorker;

        public MapAnylizer(IAuthProvider auth, DmsWorkerBase dmsWorker)
        {
            _auth = auth;
            _dmsWorker = dmsWorker;
        }
        
        public bool IsFolderSharedWithExternalUsers(FolderMap map)
        {
            if (map == null) return false;
            var wsFolder = map.WsFolder;
            if (wsFolder == null) return false;
            var user = _auth.GetCurrentWSUser2();
            if (user == null) return false;
            var members = wsFolder.Members;
            var otherUsers = members.GetWithoutCurrentUser(user);
            if (user.InPrivateDomain)
            {
                var currentUserDomain = user.Domain;
                Logger.WriteTrace(string.Format("User in private domain. Domain={0}; Email={1}; UserName={2}", currentUserDomain, user.Email, user.UserName));

                var accountUsers = WorksharePlatform.PlatformService.GetAccountUsersData(user._user);
                return otherUsers.Any(m => !accountUsers.Any(u => m.Email.Equals(u.Email, StringComparison.OrdinalIgnoreCase)));
            }
            else
            {
                Logger.WriteTrace(string.Format("User in public domain. Domain={0}; Email={1}; UserName={2}", user.Domain, user.Email, user.UserName));
                return otherUsers.Any();
            }

        }

        public string GetName(ItemMap itemMap)
        {
            if (itemMap is FolderMap)
            {
                var foldermap = (FolderMap) itemMap;
                if (foldermap.LocalFolder != null)
                {
                    return _dmsWorker.GetFriendlyName(foldermap.LocalFolder);
                }
                else if (foldermap.WsFolder != null)
                {
                    return foldermap.WsFolder.Name;
                }
            }
            else if (itemMap is FileMap)
            {
                var fileMap = (FileMap)itemMap;
                if (fileMap.LocalFile != null)
                {
                    return _dmsWorker.GetFriendlyName(fileMap.LocalFile);
                }
                else if (fileMap.WsFile != null)
                {
                    return fileMap.WsFile.Name;
                }
            }

            return itemMap.Id;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Interfaces/IModuleView.cs
﻿using System;
using System.Collections.Generic;
using Workshare.Components.Presenter;
using Workshare.Components.Views.Common;
using Workshare.Integration.Enums;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Changes.Activities;
using WorksharePlatform;

namespace Workshare.Components.Interfaces
{
    public enum EventOperation { UpdateCurrent, AddNewVersion, AddNewDoc, DeclareAsRecord, MoveFile, MoveFolder }

    public interface IModuleView
    {
        IModulePresenter m_presenter { get; set; }
        IntPtr ActivieWindowHandle { get; set; }
        
        void ShowErrors(IEnumerable<ItemException> errors);
        void ShowError(Exception ex);
        void ShowError(string message);
        void ShowError(BaseException ex);
        void OnSendItemsClicked(SendItemsClickedArgs args);
        void OnSynchItemsClicked(SyncItemsClickedArgs args);
        void OnCollaborationItemsClicked(CollaborationItemsClickedArgs args);
        void ShowProgressWindow(CommandInvoker invoker);
        bool ShowLogin(out UserDetails user, DialogSettings settings);
        int ShowSelectFolder(DialogSettings settings);
        CheckOutOptions ShowCheckOutDialogIfNeed(SendItemsClickedArgs args);
        ModulePresenterBase CreatePresenter(IWSIntegration integration);
        IntPtr TopWindow { set; get; }
        void ShowFileSyncDialog(object file, EventOperation operation, string command);
        void SuppressProgressDialog(bool p);
        List<ImportDocumentAction> SelectActions(List<ImportFileActivity> importActivities);
    }
}
<file_sep>/WSComponents/src/WSIntegration/Enums/Permissions.cs
﻿namespace Workshare.Integration.Enums
{
    public enum Permissions
    {
        EditItem=1
    }
}
<file_sep>/iManageIntegration/Src/Workshare.IManage/HooksDisabler.cs
﻿using System;

namespace Workshare.IManage
{
    public class HooksDisabler:IDisposable
    {
        public static bool DisableHooks;
        public static HooksDisabler Create()
        {
            return new HooksDisabler();
        }

        private readonly bool _previousValue;
        protected HooksDisabler()
        {
            _previousValue =DisableHooks;
            DisableHooks = true;
        }

        public void Dispose()
        {
            DisableHooks = _previousValue;
        }
    }
}
<file_sep>/WSComponents/src/WSComponents/Views/CeaseCollaborationDialog/WorkUnits/ProcessWorkUnit.cs
﻿using System;
using System.Collections.Generic;
using System.Linq;
using Workshare.Components.Common;
using Workshare.Components.Interfaces;
using Workshare.Integration.Exceptions;
using Workshare.Integration.Interfaces;
using Workshare.Integration.Processor;
using Workshare.Integration.Processor.Maps;
using Workshare.Integration.WsProxies;
using RES_CMP = Workshare.Components.Properties.Resources;
using RES_INT = Workshare.Integration.Properties.Resources;

namespace Workshare.Components.Views.CeaseCollaborationDialog.WorkUnits
{
    class ProcessWorkUnit : WorkUnit
    {
        private IEnumerable<IDMSItem> _items;
        private CeaseCollaborationDialogViewModel _vm;

        private CeaseCollaborationImportType _importAction;
        private CeaseCollaborationType _fileAction;

        private List<int> DeletedWsFolder;

        public ProcessWorkUnit(IModuleView view, IEnumerable<IDMSItem> items, CeaseCollaborationDialogViewModel vm)
            : base(view)
        {
            _vm = vm;
            _items = items;
            this.Name = "Closing collaboration";
            TargetItems = _items.Select(f => new TargetItem(f.ID.ToString()) { Name = f.Name }).ToArray();

            _importAction = _vm.ImportAction;
            _fileAction = _vm.FileAction;
        }

        public override void Execute()
        {
            try
            {
                var scanResult = _vm.ScanResult;
                var processor = _vm.Module.Resolve<Processor>();
                var processOptions = new ProcessOptions();

                var visitor = _vm.Module.Resolve<GetCeaseCollaborationActionsVisitor>();
                visitor.Initialize(_importAction, _fileAction);
                scanResult.Apply(visitor);

                processOptions.ActionsToApply.AddRange(visitor.Result);
    
                scanResult = processor.Process(scanResult, processOptions);

                var adapter = _vm.Module.Resolve<Workshare.Integration.Processor.Changes.ActivityFinder>();
                var errors = adapter.GetErrors(scanResult);

                if (errors.Any(p => p.Error.IsConnectionError()))
                {
                    throw new OfflineException();
                } 
                else if(errors.Any(p => p.Error.IsConnectionTimeOutError()))
                {
                    throw new OfflineException(RES_INT.STR_CONNECTION_ERROR_TEXT_TIMEOUT, errors.Where(p => p.Error.IsConnectionTimeOutError()).Select(p => p.Error).FirstOrDefault());
                }
                else
                {
                    if (_vm.CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.RemoteDeleted].Count > 0)
                    {
                        List<ItemException> itemExceptions = new List<ItemException>();

                        _vm.CeaseCollaborationCloseSpaceErrorFiles[CeaseCollaborationCloseSpaceError.RemoteDeleted].ForEach(i =>
                        {
                            itemExceptions.Add(new ItemException() { Item = i.LocalFile, Error = new BaseException(RES_CMP.STR_UNABLE_TO_CLOSE_COLLABORATION_SPACE, RES_INT.STR_CLOUDFILENOTFOUND) });
                        });

                        _view.ShowErrors(itemExceptions);
                    }
                }

                FinalizeCeaseCollaboration();
            }
            catch (Exception ex)
            {
                _view.ShowError(ex);
            }
        }

        private void FinalizeCeaseCollaboration()
        {
            var scanResult = _vm.ScanResult;
            DeletedWsFolder = new List<int>();
            var fileMaps = scanResult.Maps.OfType<FileMap>();

            if (_fileAction == CeaseCollaborationType.Delete && fileMaps.Any())
            {
                var _wsProxy = _vm.Module.Resolve<Workshare.Integration.WsProxies.WsProxy>();
                var _auth = _vm.Module.Resolve<IAuthProvider>();
                WsUser user = _auth.GetCurrentWSUser2();

                var dmsFolders = _items.Select(f => f.ParentFolder).GroupBy(f => f.DMSId).Select(f => f.First());

                foreach (var dmsFolder in dmsFolders)
                {
                    var dmsParent = dmsFolder;
                    var usingFolder = dmsParent;
                    var syncInfoService = _vm.Module.Resolve<Workshare.Integration.Processor.Services.SyncInfoService>();

                    while (dmsParent != null)
                    {
                        var syncInfo = syncInfoService.GetSyncInfo(dmsParent);
                        if (syncInfo == null) break;

                        var wsFolder = _wsProxy.TryGetFolder(user, syncInfo.ItemId);
                        if (wsFolder != null && !wsFolder.Files.Any() && FinalizeWsSubFolders(wsFolder.SubFolders))
                        {
                            _wsProxy.DeleteFolder(user, wsFolder.Id);
                            FinalizeLocalSubFolders(dmsParent.SubFolders, usingFolder);
                            syncInfoService.BreakLink(dmsParent);
                        }
                        else break;

                        usingFolder = dmsParent;
                        dmsParent = dmsParent.ParentFolder;
                    }
                }
            }
        }

        private bool FinalizeWsSubFolders(IEnumerable<WsFolder> wsSubFolders)
        {
            var isEmpty = true;
            var user = _vm.Module.Resolve<IAuthProvider>().GetCurrentWSUser2();
            var wsProxy = _vm.Module.Resolve<WsProxy>();

            foreach (var subFolder in wsSubFolders)
            {
                if (subFolder.Files.Any()) return false;
                isEmpty = FinalizeWsSubFolders(subFolder.SubFolders);
                if (isEmpty)
                {
                    wsProxy.DeleteFolder(user, subFolder.Id);
                    DeletedWsFolder.Add(subFolder.Id);
                }
            }
            return isEmpty;
        }

        private void FinalizeLocalSubFolders(IEnumerable<IDMSFolder> subFolders, IDMSFolder usingFolder)
        {
            var syncInfoService = _vm.Module.Resolve<Workshare.Integration.Processor.Services.SyncInfoService>();

            foreach (var subFolder in subFolders.Where(f => !f.ID.EqualTo(usingFolder.ID)))
            {
                FinalizeLocalSubFolders(subFolder.SubFolders, usingFolder);

                var syncInfo = syncInfoService.GetSyncInfo(subFolder);
                if (syncInfo != null && DeletedWsFolder.Contains(syncInfo.ItemId))
                {
                    syncInfoService.BreakLink(subFolder);
                }
            }
        }
    }
}
