diff --git a/src/OutlookAddin.UI/ViewModels/SettingsViewModel.cs b/src/OutlookAddin.UI/ViewModels/SettingsViewModel.cs index 031edd4..7ac8530 100644 --- a/src/OutlookAddin.UI/ViewModels/SettingsViewModel.cs +++ b/src/OutlookAddin.UI/ViewModels/SettingsViewModel.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.Collections.ObjectModel; +using System.Linq; using System.Net.Http; using System.Threading.Tasks; using System.Windows.Media; @@ -178,18 +179,61 @@ namespace MarcusLaw.OutlookAddin.UI.ViewModels } var deployment = System.Deployment.Application.ApplicationDeployment.CurrentDeployment; - var info = await Task.Run(() => deployment.CheckForDetailedUpdate(false)).ConfigureAwait(true); - if (!info.UpdateAvailable) + var currentVersion = deployment.CurrentVersion; + var manifestUri = deployment.UpdateLocation; + + // ApplicationDeployment.CheckForDetailedUpdate triggers a + // TrustManager re-evaluation which throws TrustNotGranted + // inside a hosted VSTO process even when the publisher and + // permissions are unchanged. Bypass it by fetching the + // deployment manifest directly and reading the version. + Version? availableVersion = null; + try { - UpdateStatusBrush = SuccessBrush; - UpdateStatus = "אתה על הגרסה האחרונה (" + deployment.CurrentVersion + ")."; + availableVersion = await Task.Run(() => FetchManifestVersion(manifestUri)).ConfigureAwait(true); + } + catch (Exception fetchEx) + { + _logger.Warning(fetchEx, "CheckForUpdate: manifest fetch failed"); + UpdateStatusBrush = ErrorBrush; + UpdateStatus = "שגיאה בבדיקת השרת: " + fetchEx.Message; return; } - UpdateStatus = $"זמינה גרסה {info.AvailableVersion} — מוריד…"; - var result = await Task.Run(() => deployment.Update()).ConfigureAwait(true); - UpdateStatusBrush = SuccessBrush; - UpdateStatus = $"הותקנה גרסה {info.AvailableVersion}. סגור ופתח את Outlook כדי לטעון אותה."; + if (availableVersion == null) + { + UpdateStatusBrush = ErrorBrush; + UpdateStatus = "לא ניתן לקרוא את גרסת השרת מ-" + manifestUri; + return; + } + + if (availableVersion <= currentVersion) + { + UpdateStatusBrush = SuccessBrush; + UpdateStatus = "אתה על הגרסה האחרונה (" + currentVersion + ")."; + return; + } + + // VSTO add-ins cannot be updated programmatically from inside + // a running Outlook — ApplicationDeployment.Update() throws. + // Open the .vsto URL via the shell; Windows hands it to + // VSTOInstaller.exe which installs the update correctly. + try + { + System.Diagnostics.Process.Start(new System.Diagnostics.ProcessStartInfo(manifestUri.ToString()) + { + UseShellExecute = true + }); + UpdateStatusBrush = SuccessBrush; + UpdateStatus = $"זמינה גרסה {availableVersion} — אשר את ההתקנה בחלון שנפתח, ואז סגור ופתח את Outlook."; + } + catch (Exception launchEx) + { + _logger.Warning(launchEx, "CheckForUpdate: shell launch of installer URL failed"); + UpdateStatusBrush = ErrorBrush; + UpdateStatus = $"זמינה גרסה {availableVersion} אבל לא הצלחנו לפתוח את חלון ההתקנה. גש ידנית ל-{manifestUri}"; + } + return; } catch (System.Deployment.Application.DeploymentDownloadException ex) { @@ -215,6 +259,33 @@ namespace MarcusLaw.OutlookAddin.UI.ViewModels } } + /// + /// Reads the top-level <assemblyIdentity> version from the + /// .vsto deployment manifest at . + /// Returns null if the document doesn't look like a deployment + /// manifest. Runs on a worker thread (synchronous HTTP). + /// + private static Version? FetchManifestVersion(Uri manifestUri) + { + // The .vsto manifest is small (≈6KB). Keep this synchronous — + // no point pulling in HttpClient and its lifecycle just for one + // GET. WebRequest works fine on .NET FW 4.8 and through proxies. + var req = System.Net.WebRequest.Create(manifestUri); + req.Timeout = 10_000; + using (var response = req.GetResponse()) + using (var stream = response.GetResponseStream()) + { + var doc = System.Xml.Linq.XDocument.Load(stream); + System.Xml.Linq.XNamespace asmv1 = "urn:schemas-microsoft-com:asm.v1"; + var identity = doc.Root? + .Elements() + .FirstOrDefault(e => e.Name.LocalName == "assemblyIdentity" && e.Name.Namespace == asmv1); + var versionAttr = identity?.Attribute("version")?.Value; + if (string.IsNullOrWhiteSpace(versionAttr)) return null; + return Version.TryParse(versionAttr, out var v) ? v : null; + } + } + private bool CanCheckForUpdate() => !IsCheckingForUpdate; partial void OnIsCheckingForUpdateChanged(bool value) diff --git a/src/OutlookAddin/OutlookAddin.csproj b/src/OutlookAddin/OutlookAddin.csproj index d02b71d..f988aad 100644 --- a/src/OutlookAddin/OutlookAddin.csproj +++ b/src/OutlookAddin/OutlookAddin.csproj @@ -36,7 +36,7 @@ C:\Users\Chaim\source\repos\OutlookAddin\Publish\ https://gitea.dev.marcus-law.co.il/espocrm-extensions/OutlookAddin/raw/branch/main/Publish/ en - 1.2.2.0 + 1.2.3.0 false true 7 diff --git a/src/OutlookAddin/Properties/AssemblyInfo.cs b/src/OutlookAddin/Properties/AssemblyInfo.cs index 3db4c4b..2ae3427 100644 --- a/src/OutlookAddin/Properties/AssemblyInfo.cs +++ b/src/OutlookAddin/Properties/AssemblyInfo.cs @@ -33,6 +33,6 @@ using System.Security; // You can specify all the values or you can default the Build and Revision Numbers // by using the '*' as shown below: // [assembly: AssemblyVersion("1.0.*")] -[assembly: AssemblyVersion("1.2.2.0")] -[assembly: AssemblyFileVersion("1.2.2.0")] +[assembly: AssemblyVersion("1.2.3.0")] +[assembly: AssemblyFileVersion("1.2.3.0")]