Webiant Logo Webiant Logo
  1. No results found.

    Try your search with a different keyword or use * as a wildcard.

LocalizedUrlExtenstions.cs

using System.Net;
using Microsoft.AspNetCore.Http;
using Nop.Core.Domain.Localization;
using Nop.Core.Infrastructure;

namespace Nop.Services.Localization;

/// 
/// Represents extensions for localized URLs
/// 
public static class LocalizedUrlExtensions
{
    private static readonly char[] _separator = ['/', '?'];

    /// 
    /// Get a value indicating whether URL is localized (contains SEO code)
    /// 
    /// URL
    /// Application path base
    /// A value indicating whether passed URL is raw URL
    /// 
    /// A task that represents the asynchronous operation
    /// The task result contains true if passed URL contains SEO code; otherwise false. Language whose SEO code is in the URL if URL is localized
    /// 
    public static async Task<(bool IsLocalized, Language Language)> IsLocalizedUrlAsync(this string url, PathString pathBase, bool isRawPath)
    {
        if (string.IsNullOrEmpty(url))
            return (false, null);

        //remove application path from raw URL
        if (isRawPath)
            url = url.RemoveApplicationPathFromRawUrl(pathBase);

        //get first segment of passed URL
        var firstSegment = url.Split(_separator, StringSplitOptions.RemoveEmptyEntries).FirstOrDefault() ?? string.Empty;
        if (string.IsNullOrEmpty(firstSegment))
            return (false, null);

        //suppose that the first segment is the language code and try to get language
        var languageService = EngineContext.Current.Resolve();
        var language = (await languageService.GetAllLanguagesAsync())
            .FirstOrDefault(urlLanguage => urlLanguage.UniqueSeoCode.Equals(firstSegment, StringComparison.InvariantCultureIgnoreCase));

        //if language exists and published passed URL is localized
        return (language?.Published ?? false, language);
    }

    /// 
    /// Remove application path from raw URL
    /// 
    /// Raw URL
    /// Application path base
    /// Result
    public static string RemoveApplicationPathFromRawUrl(this string rawUrl, PathString pathBase)
    {
        new PathString(rawUrl).StartsWithSegments(pathBase, out var result);
        return WebUtility.UrlDecode(result);
    }

    /// 
    /// Remove language SEO code from URL
    /// 
    /// Raw URL
    /// Application path base
    /// A value indicating whether passed URL is raw URL
    /// URL without language SEO code
    public static string RemoveLanguageSeoCodeFromUrl(this string url, PathString pathBase, bool isRawPath)
    {
        if (string.IsNullOrEmpty(url))
            return url;

        //remove application path from raw URL
        if (isRawPath)
            url = url.RemoveApplicationPathFromRawUrl(pathBase);

        //get result URL
        url = url.TrimStart('/');
        var result = url.Contains('/') ? url[(url.IndexOf('/'))..] : string.Empty;

        //and add back application path to raw URL
        if (isRawPath)
            result = pathBase + result;

        return result;
    }

    /// 
    /// Add language SEO code to URL
    /// 
    /// Raw URL
    /// Application path base
    /// A value indicating whether passed URL is raw URL
    /// Language
    /// Result
    public static string AddLanguageSeoCodeToUrl(this string url, PathString pathBase, bool isRawPath, Language language)
    {
        ArgumentNullException.ThrowIfNull(language);

        //null validation is not required
        //if (string.IsNullOrEmpty(url))
        //    return url;

        //remove application path from raw URL
        if (isRawPath && !string.IsNullOrEmpty(url))
            url = url.RemoveApplicationPathFromRawUrl(pathBase);

        //add language code
        url = $"/{language.UniqueSeoCode}{url}";

        //and add back application path to raw URL
        if (isRawPath)
            url = pathBase + url;

        return url;
    }
}