Example #1
0
        string BuildDesktopShortcut([NotNull] SnapOsShortcutDescription shortcutDescription, string description)
        {
            if (shortcutDescription == null)
            {
                throw new ArgumentNullException(nameof(shortcutDescription));
            }

            var workingDirectory = Filesystem.PathGetDirectoryName(shortcutDescription.ExeAbsolutePath);

            switch (DistroType)
            {
            case SnapOsDistroType.Ubuntu:
                return($@"[Desktop Entry]
Encoding=UTF-8
Version={shortcutDescription.SnapApp.Version}
Type=Application
Terminal=false
Exec=bash -c 'cd ""{workingDirectory}"" && LD_LIBRARY_PATH=. {shortcutDescription.ExeAbsolutePath}'
Icon={shortcutDescription.IconAbsolutePath}
Name={shortcutDescription.SnapApp.Id}
Comment={description}");

            default:
                return(null);
            }
        }
Example #2
0
 public Task CreateShortcutsForExecutableAsync(SnapOsShortcutDescription shortcutDescription, ILog logger = null,
                                               CancellationToken cancellationToken = default)
 {
     return(OsImpl.CreateShortcutsForExecutableAsync(shortcutDescription, logger, cancellationToken));
 }
Example #3
0
        public async Task CreateShortcutsForExecutableAsync(SnapOsShortcutDescription shortcutDescription, ILog logger = null, CancellationToken cancellationToken = default)
        {
            if (shortcutDescription == null)
            {
                throw new ArgumentNullException(nameof(shortcutDescription));
            }
            var exeName = Filesystem.PathGetFileName(shortcutDescription.ExeAbsolutePath);

            if (Username == null)
            {
                _logger?.Error($"Unable to create shortcut because username is null. Executable: {exeName}");
                return;
            }

            logger?.Info($"Creating shortcuts for executable: {shortcutDescription.ExeAbsolutePath}");

            var autoStartEnabled = shortcutDescription.ShortcutLocations.HasFlag(SnapShortcutLocation.Startup);
            var desktopEnabled   = shortcutDescription.ShortcutLocations.HasFlag(SnapShortcutLocation.Desktop);
            var startMenuEnabled = shortcutDescription.ShortcutLocations.HasFlag(SnapShortcutLocation.StartMenu);

            var desktopShortcutUtf8Content = BuildDesktopShortcut(shortcutDescription, shortcutDescription.NuspecReader.GetDescription());

            if (desktopShortcutUtf8Content == null)
            {
                _logger?.Warn(
                    $"Unknown error while building desktop shortcut for exe: {exeName}. Distro: {DistroType}. Maybe unsupported distro?");
                return;
            }

            var applicationsDirectoryAbsolutePath = Filesystem.PathCombine($"/home/{Username}", ".local/share/applications");
            var autoStartDirectoryAbsolutePath    = Filesystem.PathCombine($"/home/{Username}", ".config/autostart");

            var autoStartShortcutAbsolutePath = Filesystem.PathCombine(autoStartDirectoryAbsolutePath, $"{exeName}.desktop");
            var desktopShortcutAbsolutePath   = Filesystem.PathCombine(applicationsDirectoryAbsolutePath, $"{exeName}.desktop");

            if (startMenuEnabled)
            {
                _logger?.Warn("Creating start menu shortcuts is not supported on this OS.");
            }

            if (autoStartEnabled)
            {
                if (Filesystem.DirectoryCreateIfNotExists(autoStartDirectoryAbsolutePath))
                {
                    _logger?.Info($"Created autostart directory: {autoStartDirectoryAbsolutePath}");
                }

                if (Filesystem.FileDeleteIfExists(autoStartShortcutAbsolutePath))
                {
                    _logger?.Info($"Deleted existing auto start shortcut: {autoStartShortcutAbsolutePath}");
                }

                _logger?.Info($"Creating autostart shortcut: {autoStartShortcutAbsolutePath}. " +
                              $"Absolute path: {shortcutDescription.ExeAbsolutePath}.");

                await Filesystem.FileWriteUtf8StringAsync(desktopShortcutUtf8Content,
                                                          autoStartShortcutAbsolutePath, cancellationToken);

                _logger?.Info($"Attempting to mark shortcut as trusted: {autoStartShortcutAbsolutePath}.");
                var trustedSuccess = await OsProcessManager.ChmodExecuteAsync(autoStartShortcutAbsolutePath, cancellationToken);

                _logger?.Info($"Shortcut marked as trusted: {(trustedSuccess ? "yes" : "no")}");
            }

            if (desktopEnabled)
            {
                if (!Filesystem.DirectoryExists(applicationsDirectoryAbsolutePath))
                {
                    _logger?.Error($"Applications directory does not exist. Desktop shortcut will not be created. Path: {applicationsDirectoryAbsolutePath}");
                    goto next;
                }

                if (Filesystem.FileDeleteIfExists(desktopShortcutAbsolutePath))
                {
                    _logger?.Info($"Deleted existing shortcut: {desktopShortcutAbsolutePath}");
                }

                _logger?.Info($"Creating desktop shortcut: {desktopShortcutAbsolutePath}. " +
                              $"Auto startup: {autoStartEnabled}. " +
                              $"Absolute path: {shortcutDescription.ExeAbsolutePath}.");

                await Filesystem.FileWriteUtf8StringAsync(desktopShortcutUtf8Content,
                                                          desktopShortcutAbsolutePath, cancellationToken);

                _logger?.Info($"Attempting to mark shortcut as trusted: {desktopShortcutAbsolutePath}.");
                var trustedSuccess = await OsProcessManager.ChmodExecuteAsync(desktopShortcutAbsolutePath, cancellationToken);

                _logger?.Info($"Shortcut marked as trusted: {(trustedSuccess ? "yes" : "no")}");
            }

            next :;
        }
Example #4
0
        async Task InvokePostInstall(SnapApp snapApp, NuspecReader nuspecReader,
                                     string baseDirectory, string appDirectory, SemanticVersion currentVersion,
                                     bool isInitialInstall, ILog logger = null, CancellationToken cancellationToken = default)
        {
            var chmod = !RuntimeInformation.IsOSPlatform(OSPlatform.Windows);

            var coreRunExeAbsolutePath = _snapOs.Filesystem
                                         .PathCombine(baseDirectory, _snapEmbeddedResources.GetCoreRunExeFilenameForSnapApp(snapApp));
            var mainExeAbsolutePath = _snapOs.Filesystem
                                      .PathCombine(appDirectory, _snapEmbeddedResources.GetCoreRunExeFilenameForSnapApp(snapApp));
            var iconAbsolutePath = !RuntimeInformation.IsOSPlatform(OSPlatform.Windows) && snapApp.Target.Icon != null?
                                   _snapOs.Filesystem.PathCombine(appDirectory, snapApp.Target.Icon) : null;

            var snapChannel = snapApp.GetCurrentChannelOrThrow();

            logger?.Debug($"{nameof(coreRunExeAbsolutePath)}: {coreRunExeAbsolutePath}");
            logger?.Debug($"{nameof(mainExeAbsolutePath)}: {mainExeAbsolutePath}");
            logger?.Debug($"{nameof(iconAbsolutePath)}: {iconAbsolutePath}");

            async Task ChmodAsync(string exePath)
            {
                if (exePath == null)
                {
                    throw new ArgumentNullException(nameof(exePath));
                }
                logger?.Info($"Attempting to change file permission for executable: {exePath}.");
                var chmodSuccess = await _snapOs.ProcessManager.ChmodExecuteAsync(exePath, cancellationToken);

                logger?.Info($"Permissions changed successfully: {(chmodSuccess ? "true" : "false")}.");
            }

            if (chmod)
            {
                await ChmodAsync(coreRunExeAbsolutePath);
                await ChmodAsync(mainExeAbsolutePath);
            }

            var coreRunExeFilename = _snapOs.Filesystem.PathGetFileName(coreRunExeAbsolutePath);

            if (!snapApp.Target.Shortcuts.Any())
            {
                logger?.Warn("This application does not specify any shortcut locations.");
            }
            else
            {
                var shortcutLocations = snapApp.Target.Shortcuts.First();
                snapApp.Target.Shortcuts.Skip(1).ForEach(x => shortcutLocations |= x);
                logger?.Info($"Shortcuts will be created in the following locations: {string.Join(", ", shortcutLocations)}");
                try
                {
                    var shortcutDescription = new SnapOsShortcutDescription
                    {
                        SnapApp           = snapApp,
                        UpdateOnly        = isInitialInstall == false,
                        NuspecReader      = nuspecReader,
                        ShortcutLocations = shortcutLocations,
                        ExeAbsolutePath   = coreRunExeAbsolutePath,
                        IconAbsolutePath  = iconAbsolutePath
                    };

                    await _snapOs.CreateShortcutsForExecutableAsync(shortcutDescription, logger, cancellationToken);
                }
                catch (Exception e)
                {
                    logger?.ErrorException($"Exception thrown while creating shortcut for exe: {coreRunExeFilename}", e);
                }
            }

            var snapAppDllAbsolutePath = _snapOs.Filesystem.PathCombine(appDirectory, SnapConstants.SnapAppDllFilename);

            try
            {
                logger?.Info($"Updating {snapAppDllAbsolutePath}. Current channel is: {snapChannel.Name}.");

                using var snapAppDllAssemblyDefinition = _snapAppWriter.BuildSnapAppAssembly(snapApp);
                using var snapAPpDllDestinationStream  = _snapOs.Filesystem.FileWrite(snapAppDllAbsolutePath);
                snapAppDllAssemblyDefinition.Write(snapAPpDllDestinationStream);
            }
            catch (Exception e)
            {
                logger?.ErrorException($"Unknown error updating {snapAppDllAbsolutePath}", e);
            }

            var allSnapAwareApps = new List <string>
            {
                mainExeAbsolutePath
            }.Select(x =>
            {
                var installOrUpdateTxt = isInitialInstall ? "--snapx-installed" : "--snapx-updated";
                return(new ProcessStartInfoBuilder(x)
                       .Add(installOrUpdateTxt)
                       .Add(currentVersion.ToNormalizedString()));
            })
            .ToList();

            await InvokeSnapApps(allSnapAwareApps, TimeSpan.FromSeconds(15), isInitialInstall, currentVersion, logger, cancellationToken);
        }