Абсолютный путь обратно к веб-относительному пути

Если мне удалось найти и проверить существование файла с помощью Server.MapPath, и теперь я хочу отправить пользователя непосредственно в этот файл, какой самый быстрый способ преобразовать этот абсолютный путь обратно в относительный веб-путь?

6.08.2008 08:34:13
6 ОТВЕТОВ
РЕШЕНИЕ

Возможно, это может сработать:

String RelativePath = AbsolutePath.Replace(Request.ServerVariables["APPL_PHYSICAL_PATH"], String.Empty);

Я использую C #, но может быть адаптирован к VB.

55
20.03.2018 14:18:12
@ GateKiller : обратите внимание, что если вы используете виртуальные каталоги IIS на своем веб-сайте, ваше решение может дать сбой, поскольку физический путь к приложению может отличаться от физического пути к файлу.
Costo 13.08.2008 01:09:43

Если вы использовали Server.MapPath, то у вас уже должен быть относительный веб-путь. Согласно документации MSDN , этот метод принимает одну переменную, путь , который является виртуальным путем веб-сервера. Поэтому, если вы смогли вызвать метод, у вас уже должен быть доступный относительный веб-путь.

2
6.08.2008 09:23:44
Это не обязательно верно - вызов MapPath мог быть выполнен другим методом и передан в / вызван из моего метода проверки файлов, или (в моем случае) построен из ряда различных элементов, одним из которых является мой каталог ресурсов (определенный как "~ / __ Ресурсы"). Очевидно, что направление пользователя по этому пути приведет к неожиданным результатам. Это также было бы полезно знать, потому что иногда абсолютный путь к файлу мог быть извлечен из базы данных без какой-либо другой контекстной информации.
tags2k 6.08.2008 09:00:42
@tagsk - я не знаю об этом. По тому, как метод определен, если строка, которую вы вводите в Server.MapPath, является допустимой и возвращает физический путь к серверу, то это должен был быть также действительный виртуальный путь, независимо от того, как вы его сгенерировали. Относительно использования тильды (~) в начале виртуального адреса см. Эту статью MSDN о путях веб-сайта ASP.NET:> ASP.NET включает веб-приложение> корневой оператор (~), который можно использовать> при указании путь на сервере> c
Yaakov Ellis♦ 6.08.2008 09:30:10
Яаков - Не так. Например, функция, которую я использую, берет корневой путь и IEnumerable<FileInfo>рекурсивно возвращает коллекцию. В моем веб-приложении я могу предоставить этот путь, разрешающий мой относительный путь к физическому, но когда я возвращаюсь к этому рекурсивному списку и хочу сопоставить их с относительными путями в моем приложении, у меня нет этой информации.
one.beat.consumer 14.06.2012 18:00:16

Не было бы неплохо иметь Server.RelativePath (путь) ?

ну, вам просто нужно расширить его ;-)

public static class ExtensionMethods
{
    public static string RelativePath(this HttpServerUtility srv, string path, HttpRequest context)
    {
        return path.Replace(context.ServerVariables["APPL_PHYSICAL_PATH"], "~/").Replace(@"\", "/");
    }
}

С этим вы можете просто позвонить

Server.RelativePath(path, Request);
37
24.10.2013 15:42:00
лучшей заменой для физического пути будет ~ /. path.Replace (context.ServerVariables ("APPL_PHYSICAL_PATH"), "~ /")
Josh Russo 12.07.2013 19:33:57

Я знаю, что это старый, но мне нужно было учитывать виртуальные каталоги (согласно комментарию @ Costo). Это, кажется, помогает:

static string RelativeFromAbsolutePath(string path)
{
    if(HttpContext.Current != null)
    {
        var request = HttpContext.Current.Request;
        var applicationPath = request.PhysicalApplicationPath;
        var virtualDir = request.ApplicationPath;
        virtualDir = virtualDir == "/" ? virtualDir : (virtualDir + "/");
        return path.Replace(applicationPath, virtualDir).Replace(@"\", "/");
    }

    throw new InvalidOperationException("We can only map an absolute back to a relative path if an HttpContext is available.");
}
13
7.02.2016 14:12:30

Мне нравится идея Каноаса. К сожалению, у меня не было «HttpContext.Current.Request» (BundleConfig.cs).

Я изменил метод так:

public static string RelativePath(this HttpServerUtility srv, string path)
{
     return path.Replace(HttpContext.Current.Server.MapPath("~/"), "~/").Replace(@"\", "/");
}
5
24.06.2015 08:19:45

Для ядра asp.net я написал вспомогательный класс, чтобы получить пути в обоих направлениях.

public class FilePathHelper
{
    private readonly IHostingEnvironment _env;
    public FilePathHelper(IHostingEnvironment env)
    {
        _env = env;
    }
    public string GetVirtualPath(string physicalPath)
    {
        if (physicalPath == null) throw new ArgumentException("physicalPath is null");
        if (!File.Exists(physicalPath)) throw new FileNotFoundException(physicalPath + " doesn't exists");
        var lastWord = _env.WebRootPath.Split("\\").Last();
        int relativePathIndex = physicalPath.IndexOf(lastWord) + lastWord.Length;
        var relativePath = physicalPath.Substring(relativePathIndex);
        return $"/{ relativePath.TrimStart('\\').Replace('\\', '/')}";
    }
    public string GetPhysicalPath(string relativepath)
    {
        if (relativepath == null) throw new ArgumentException("relativepath is null");
        var fileInfo = _env.WebRootFileProvider.GetFileInfo(relativepath);
        if (fileInfo.Exists) return fileInfo.PhysicalPath;
        else throw new FileNotFoundException("file doesn't exists");
    }

из контроллера или службы вставьте FilePathHelper и используйте:

var physicalPath = _fp.GetPhysicalPath("/img/banners/abro.png");

и наоборот

var virtualPath = _fp.GetVirtualPath(physicalPath);
0
19.12.2018 11:56:18