Microsoft Web API: Como você faz um Server.MapPath?

239

Como a Microsoft Web API não é MVC , você não pode fazer algo assim:

var a = Request.MapPath("~");

nem isso

var b = Server.MapPath("~");

porque eles estão no System.Webespaço para nome, não no System.Web.Httpespaço para nome.

Então, como você descobre o caminho relativo do servidor na Web API ?
Eu costumava fazer algo assim no MVC :

var myFile = Request.MapPath("~/Content/pics/" + filename);

O que me daria o caminho absoluto no disco:

"C:\inetpub\wwwroot\myWebFolder\Content\pics\mypic.jpg"
Zachary Scott
fonte

Respostas:

469

Você pode usar HostingEnvironment.MapPath em qualquer contexto em que System.Webobjetos como HttpContext.Currentnão estejam disponíveis (por exemplo, também a partir de um método estático).

var mappedPath = System.Web.Hosting.HostingEnvironment.MapPath("~/SomePath");

Consulte também Qual é a diferença entre Server.MapPath e HostingEnvironment.MapPath?

StuartLC
fonte
1
Isso é bom, mas não há nenhuma maneira fácil de HostingEnvironment simulada uma vez que é uma instância de classe estática ... :-(
Josh G
6
Claro, mas em seu controlador ou em outra camada lógica que você deseja testar, você dependeria apenas de sua própria abstração, como IPathMapper(você provavelmente juntará isso com várias outras preocupações em uma interface maior de cinto de ferramentas / utilitário) com o método string MapPath(string virtualPath). Apenas a aplicação concreta para as suas WebApi IPathMappernecessidades de saber sobreSystem.Web.Hosting.HostingEnvironment
StuartLC
1
@JoshG - você pode abstrair o HostingEnvironment.MapPath via Func <string, string> GetWebPath = HostingEnvironment.MapPath e, em seguida, sobrescrever o GetWebPath no momento do teste com uma simulação.
Sean B
parece que este é tendo problemas com caminhos relativos como../images/
AaA
Está dando o caminho do controlador, então posso obter o caminho do serviço usando o "HostingEnvironment"?
Md Aslam
13
string root = HttpContext.Current.Server.MapPath("~/App_Data");
ArgeKumandan
fonte
16
Você não deseja usar o HttpContext.Current no WebAPI. E as APIs auto-hospedadas? Você não pode confiar no HttpContext.Current para estar lá. Também não é teste amigável.
Trevor de Koekkoek
2

Como um aparte daqueles que se deparam com isso, uma boa maneira de executar o nível de teste ao usar a chamada HostingEnvironment é se o acesso, digamos, ao compartilhamento UNC: \ example \ mapeado para ~ / example /, você pode executá-lo para se locomover Problemas do IIS-Express:

#if DEBUG
    var fs = new FileStream(@"\\example\file",FileMode.Open, FileAccess.Read);
#else
    var fs = new FileStream(HostingEnvironment.MapPath("~/example/file"), FileMode.Open, FileAccess.Read);
#endif

Acho isso útil caso você tenha direitos para testar localmente em um arquivo, mas precise do mapeamento do ambiente uma vez em produção.

Nathan Teague
fonte
Fyi, a HostingEnvironmentclasse está no System.Web.Hostingespaço para nome.
Dermot
2
Qual é a alternativa HostingEnvironment para o DNX core 5.0?
Rbdukkey 14/05
A nova classe Startup.cs agora Injeta uma Inicialização pública (IHostingEnvironment env) {} na construção, a propriedade desliza na minha mente, apenas fiz isso no outro dia. isso permite que você também controle um ambiente por instância e, usando as diretivas #if, crie um aplicativo que possa implantar entre camadas facilmente em vários ambientes.
Nathan Teague
1

Eu não posso dizer a partir do contexto que você fornece, mas se é algo que você só precisa fazer a inicialização do aplicativo, você ainda pode usar Server.MapPathem WebApiHttpApplication; por exemplo, em Application_Start().

Estou apenas respondendo sua pergunta direta; a já mencionada HostingEnvironment.MapPath()é provavelmente a solução preferida.

fita adesiva
fonte
0

Como Server.MapPath()não existe em uma API da Web (Soap ou REST), você precisará indicar o local em relação ao diretório inicial do contexto do servidor da Web. A maneira mais fácil de fazer isso é com:

string AppContext.BaseDirectory { get;}

Você pode usar isso para concatenar uma cadeia de caminho para mapear o caminho relativo para qualquer arquivo.
NOTA: os caminhos de string são \e não /são como no mvc.

Ex:

System.IO.File.Exists($"{**AppContext.BaseDirectory**}\\\\Content\\\\pics\\\\{filename}");

retorna true postulando que este é um caminho sonoro no seu exemplo

Convidado
fonte
-1

A resposta selecionada não funcionou no meu aplicativo de API da Web. Eu tive que usar

System.Web.HttpRuntime.AppDomainAppPath
Aproximação aproximação
fonte
1
Embora parece que esta é a única maneira que você pode obter o caminho para a sua aplicação WebAPI, este dá-lhe raiz do seu aplicativo, mas não se traduz caminhos relativos como ~\folderou ../images/para caminhos físicos
AaA
-1

Você pode tentar como:

var path = "~ / Image / test.png"; System.Web.Hosting.HostingEnvironment.MapPath (@ + path)

SANDIP G.PATIL
fonte