示例#1
0
        public void UploadToWebonary(UploadToWebonaryModel model, IUploadToWebonaryView view)
        {
            view.UpdateStatus(xWorksStrings.ksUploadingToWebonary);
            view.SetStatusCondition(WebonaryStatusCondition.None);

            if (string.IsNullOrEmpty(model.SiteName))
            {
                view.UpdateStatus(xWorksStrings.ksErrorNoSiteName);
                view.SetStatusCondition(WebonaryStatusCondition.Error);
                return;
            }

            if (string.IsNullOrEmpty(model.UserName))
            {
                view.UpdateStatus(xWorksStrings.ksErrorNoUsername);
                view.SetStatusCondition(WebonaryStatusCondition.Error);
                return;
            }

            if (string.IsNullOrEmpty(model.Password))
            {
                view.UpdateStatus(xWorksStrings.ksErrorNoPassword);
                view.SetStatusCondition(WebonaryStatusCondition.Error);
                return;
            }

            if (string.IsNullOrEmpty(model.SelectedPublication))
            {
                view.UpdateStatus(xWorksStrings.ksErrorNoPublication);
                view.SetStatusCondition(WebonaryStatusCondition.Error);
                return;
            }

            if (string.IsNullOrEmpty(model.SelectedConfiguration))
            {
                view.UpdateStatus(xWorksStrings.ksErrorNoConfiguration);
                view.SetStatusCondition(WebonaryStatusCondition.Error);
                return;
            }

            var tempDirectoryToCompress = Path.Combine(Path.GetTempPath(), Path.GetRandomFileName());
            var zipBasename             = UploadFilename(model, view);

            if (zipBasename == null)
            {
                return;
            }
            var zipFileToUpload = Path.Combine(Path.GetTempPath(), zipBasename);

            Directory.CreateDirectory(tempDirectoryToCompress);
            ExportDictionaryContent(tempDirectoryToCompress, model, view);
            ExportReversalContent(tempDirectoryToCompress, model, view);
            ExportOtherFilesContent(tempDirectoryToCompress, model, view);
            CompressExportedFiles(tempDirectoryToCompress, zipFileToUpload, view);
            UploadToWebonary(zipFileToUpload, model, view);
        }
示例#2
0
        /// <summary>
        /// Filename of zip file to upload to webonary, based on a particular model.
        /// If there are any characters that might cause a problem, null is returned.
        /// </summary>
        internal static string UploadFilename(UploadToWebonaryModel basedOnModel, IUploadToWebonaryView view)
        {
            if (basedOnModel == null)
            {
                throw new ArgumentNullException(nameof(basedOnModel));
            }
            if (string.IsNullOrEmpty(basedOnModel.SiteName))
            {
                throw new ArgumentException(nameof(basedOnModel));
            }
            var disallowedCharacters = MiscUtils.GetInvalidProjectNameChars(MiscUtils.FilenameFilterStrength.kFilterProjName) + "_ $.%";

            if (basedOnModel.SiteName.IndexOfAny(disallowedCharacters.ToCharArray()) >= 0)
            {
                view.UpdateStatus(xWorksStrings.ksErrorInvalidCharacters);
                view.SetStatusCondition(WebonaryStatusCondition.Error);
                return(null);
            }
            return(basedOnModel.SiteName + ".zip");
        }
示例#3
0
        internal void UploadToWebonary(string zipFileToUpload, UploadToWebonaryModel model, IUploadToWebonaryView view)
        {
            if (zipFileToUpload == null)
            {
                throw new ArgumentNullException("zipFileToUpload");
            }
            if (model == null)
            {
                throw new ArgumentNullException("model");
            }
            if (view == null)
            {
                throw new ArgumentNullException("view");
            }

            view.UpdateStatus(xWorksStrings.ksConnectingToWebonary);
            var targetURI = DestinationURI(model.SiteName);

            using (var client = CreateWebClient())
            {
                var credentials = string.Format("{0}:{1}", model.UserName, model.Password);
                client.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(new UTF8Encoding().GetBytes(credentials)));
                client.Headers.Add("user-agent", string.Format("FieldWorks Language Explorer v.{0}", Assembly.GetExecutingAssembly().GetName().Version));
                client.Headers[HttpRequestHeader.Accept] = "*/*";

                byte[] response = null;
                try
                {
                    response = client.UploadFileToWebonary(targetURI, zipFileToUpload);
                }
                catch (WebonaryClient.WebonaryException e)
                {
                    if (e.StatusCode == HttpStatusCode.Redirect)
                    {
                        view.UpdateStatus(xWorksStrings.ksErrorWebonarySiteName);
                    }
                    else
                    {
                        view.UpdateStatus(string.Format(xWorksStrings.ksErrorCannotConnectToWebonary,
                                                        Environment.NewLine, e.StatusCode, e.Message));
                    }
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                    return;
                }
                var responseText = Encoding.ASCII.GetString(response);

                if (client.ResponseStatusCode == HttpStatusCode.Found)
                {
                    view.UpdateStatus(xWorksStrings.ksErrorWebonarySiteName);
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }
                else if (responseText.Contains("Upload successful"))
                {
                    if (!responseText.Contains("error"))
                    {
                        view.UpdateStatus(xWorksStrings.ksWebonaryUploadSuccessful);
                        view.SetStatusCondition(WebonaryStatusCondition.Success);
                        return;
                    }

                    view.UpdateStatus(xWorksStrings.ksWebonaryUploadSuccessfulErrorProcessing);
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }

                if (responseText.Contains("Wrong username or password"))
                {
                    view.UpdateStatus(xWorksStrings.ksErrorUsernameOrPassword);
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }
                else if (responseText.Contains("User doesn't have permission to import data"))
                {
                    view.UpdateStatus(xWorksStrings.ksErrorUserDoesntHavePermissionToImportData);
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }
                else                 // Unknown error, display the server response, but cut it off at 100 characters
                {
                    view.UpdateStatus(string.Format("{0}{1}{2}{1}", xWorksStrings.ksResponseFromServer, Environment.NewLine,
                                                    responseText.Substring(0, Math.Min(100, responseText.Length))));
                }
            }
        }
示例#4
0
 /// <summary>
 /// Exports the reversal xhtml and css for the reversals that the user had selected in the dialog
 /// </summary>
 private void ExportReversalContent(string tempDirectoryToCompress, UploadToWebonaryModel model, IUploadToWebonaryView webonaryView)
 {
     if (model.Reversals == null)
     {
         return;
     }
     foreach (var reversal in model.SelectedReversals)
     {
         var revWsRFC5646 = model.Reversals.Where(prop => prop.Value.Label == reversal).Select(prop => prop.Value.WritingSystem).FirstOrDefault();
         webonaryView.UpdateStatus(string.Format(xWorksStrings.ExportingReversalsToWebonary, reversal));
         var reversalWs = m_cache.LangProject.AnalysisWritingSystems.FirstOrDefault(ws => ws.LanguageTag == revWsRFC5646);
         // The reversalWs should always match the RFC5646 of one of the AnalysisWritingSystems, this exception is for future programming errors
         if (reversalWs == null)
         {
             throw new ApplicationException(string.Format("Could not locate reversal writing system for {0}", reversal));
         }
         var xhtmlPath     = Path.Combine(tempDirectoryToCompress, string.Format("reversal_{0}.xhtml", reversalWs.IcuLocale));
         var configuration = model.Reversals[reversal];
         m_exportService.ExportReversalContent(xhtmlPath, revWsRFC5646, configuration);
         webonaryView.UpdateStatus(xWorksStrings.ExportingReversalsToWebonaryCompleted);
     }
 }
示例#5
0
 /// <summary>
 /// This method will recurse into a directory and add files into the zip file with their relative path
 /// to the original dirToCompress.
 /// </summary>
 private static void RecursivelyAddFilesToZip(ZipFile zipFile, string dirToCompress, string dirInZip, IUploadToWebonaryView webonaryView)
 {
     foreach (var file in Directory.EnumerateFiles(dirToCompress))
     {
         if (!IsSupportedWebonaryFile(file))
         {
             webonaryView.UpdateStatus(string.Format(xWorksStrings.ksExcludingXXFormatUnsupported,
                                                     Path.GetFileName(file), Path.GetExtension(file)));
             continue;
         }
         zipFile.AddFile(file, dirInZip);
         webonaryView.UpdateStatus(Path.GetFileName(file));
     }
     foreach (var dir in Directory.EnumerateDirectories(dirToCompress))
     {
         RecursivelyAddFilesToZip(zipFile, dir, Path.Combine(dirInZip, Path.GetFileName(dir.TrimEnd(Path.DirectorySeparatorChar))), webonaryView);
     }
 }
示例#6
0
 internal static void CompressExportedFiles(string tempDirectoryToCompress, string zipFileToUpload, IUploadToWebonaryView webonaryView)
 {
     webonaryView.UpdateStatus(xWorksStrings.BeginCompressingDataForWebonary);
     using (var zipFile = new ZipFile(Encoding.UTF8))
     {
         RecursivelyAddFilesToZip(zipFile, tempDirectoryToCompress, "", webonaryView);
         zipFile.Save(zipFileToUpload);
     }
     webonaryView.UpdateStatus(xWorksStrings.FinishedCompressingDataForWebonary);
 }
示例#7
0
        /// <summary>
        /// Exports the dictionary xhtml and css for the publication and configuration that the user had selected in the dialog.
        /// </summary>
        private void ExportDictionaryContent(string tempDirectoryToCompress, UploadToWebonaryModel model, IUploadToWebonaryView webonaryView)
        {
            webonaryView.UpdateStatus(String.Format(xWorksStrings.ExportingEntriesToWebonary, model.SelectedPublication, model.SelectedConfiguration));
            var xhtmlPath     = Path.Combine(tempDirectoryToCompress, "configured.xhtml");
            var configuration = model.Configurations[model.SelectedConfiguration];

            m_exportService.ExportDictionaryContent(xhtmlPath, configuration);
            webonaryView.UpdateStatus(xWorksStrings.ExportingEntriesToWebonaryCompleted);
        }
示例#8
0
        internal void UploadToWebonary(string zipFileToUpload, UploadToWebonaryModel model, IUploadToWebonaryView view)
        {
            if (zipFileToUpload == null)
            {
                throw new ArgumentNullException("zipFileToUpload");
            }
            if (model == null)
            {
                throw new ArgumentNullException("model");
            }
            if (view == null)
            {
                throw new ArgumentNullException("view");
            }

            view.UpdateStatus("Connecting to Webonary.");
            var targetURI = DestinationURI(model.SiteName);

            using (var client = CreateWebClient())
            {
                var credentials = string.Format("{0}:{1}", model.UserName, model.Password);
                client.Headers.Add("Authorization", "Basic " + Convert.ToBase64String(new UTF8Encoding().GetBytes(credentials)));
                client.Headers.Add("user-agent", string.Format("FieldWorks Language Explorer v.{0}", Assembly.GetExecutingAssembly().GetName().Version));
                client.Headers[HttpRequestHeader.Accept] = "*/*";

                byte[] response = null;
                try
                {
                    response = client.UploadFileToWebonary(targetURI, zipFileToUpload);
                }
                catch (WebonaryClient.WebonaryException e)
                {
                    if (e.StatusCode == HttpStatusCode.Redirect)
                    {
                        view.UpdateStatus("Error: There has been an error accessing webonary. Is your sitename correct?");
                    }
                    else
                    {
                        const string errorMessage = "Unable to connect to Webonary.  Please check your username and password and your Internet connection.";
                        view.UpdateStatus(string.Format("An error occurred uploading your data: {0}{1}{2}:{3}",
                                                        errorMessage, Environment.NewLine, e.StatusCode, e.Message));
                    }
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                    return;
                }
                var responseText = Encoding.ASCII.GetString(response);

                if (client.ResponseStatusCode == HttpStatusCode.Found)
                {
                    view.UpdateStatus("Error: There has been an error accessing webonary. Is your sitename correct?");
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }
                else if (responseText.Contains("Upload successful"))
                {
                    if (!responseText.Contains("error"))
                    {
                        view.UpdateStatus("Upload successful. " +
                                          "Preparing your data for publication. " +
                                          "This may take several minutes to a few hours depending on the size of your dictionary. " +
                                          "You will receive an email when the process is complete. " +
                                          "You can examine the progress on the admin page of your Webonary site. " +
                                          "You may now safely close this dialog.");
                        view.SetStatusCondition(WebonaryStatusCondition.Success);
                        return;
                    }

                    view.UpdateStatus("The upload was successful; however, there were errors processing your data.");
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }

                if (responseText.Contains("Wrong username or password"))
                {
                    view.UpdateStatus("Error: Wrong username or password");
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }
                else if (responseText.Contains("User doesn't have permission to import data"))
                {
                    view.UpdateStatus("Error: User doesn't have permission to import data");
                    view.SetStatusCondition(WebonaryStatusCondition.Error);
                }
                else                 // Unknown error, display the server response, but cut it off at 100 characters
                {
                    view.UpdateStatus(string.Format("Response from server:{0}{1}{0}", Environment.NewLine,
                                                    responseText.Substring(0, Math.Min(100, responseText.Length))));
                }
            }
        }