Wie erhalte ich den Pfad der Assembly, in der sich der Code befindet?

781

Gibt es eine Möglichkeit, den Pfad für die Assembly abzurufen, in der sich der aktuelle Code befindet? Ich möchte nicht den Pfad der aufrufenden Assembly, sondern nur den, der den Code enthält.

Grundsätzlich muss mein Unit-Test einige XML-Testdateien lesen, die sich relativ zur DLL befinden. Ich möchte, dass der Pfad immer korrekt aufgelöst wird, unabhängig davon, ob die Test-DLL von TestDriven.NET, der MbUnit-GUI oder etwas anderem ausgeführt wird.

Bearbeiten : Die Leute scheinen falsch zu verstehen, was ich frage.

Meine Testbibliothek befindet sich beispielsweise in

C: \ projects \ myapplication \ daotests \ bin \ Debug \ daotests.dll

und ich möchte diesen Weg bekommen:

C: \ projects \ myapplication \ daotests \ bin \ Debug \

Die drei Vorschläge, die ich bisher gemacht habe, scheitern, wenn ich von der MbUnit Gui renne:

  • Environment.CurrentDirectory gibt c: \ Programme \ MbUnit

  • System.Reflection.Assembly.GetAssembly(typeof(DaoTests)).Location gibt C: \ Dokumente und Einstellungen \ george \ Lokale Einstellungen \ Temp \ .... \ DaoTests.dll

  • System.Reflection.Assembly.GetExecutingAssembly().Location gibt das gleiche wie das vorherige.

George Mauer
quelle
102
Dies ist Ihre Lösung: var dir = AppDomain.CurrentDomain.BaseDirectory;
Jalal El-Shaer
7
Dies sollte die akzeptierte Lösung sein. AppDomain.CurrentDomain.BaseDirectory ist der richtige Ansatz.
aBetterGamer
2
Ich bin hierher gekommen, um nach einer Lösung für ein Nuget-Paket zu suchen, um eine JSON-Datei aus ihrem pacakge-Verzeichnis zu lesen. Wenn ein Nuget-Paket ausgeführt wird, zeigt "AppDomain.CurrentDomain.BaseDirectory" auf das Verzeichnis der laufenden Projekte und nicht auf das Verzeichnis des Nuget-Pakets. Keines davon scheint korrekt auf das Nuget-Paketverzeichnis abzuzielen.
Lucas
@Lucas nein, würde es nicht, weil es nicht darum ging, worum es bei dieser Frage ging (tatsächlich gab es Nuget nicht, als sie gestellt wurde) - zögern Sie nicht, eine neue Frage zu stellen und mich dort anzupingen, aber das kann ich Ihnen jetzt sagen es ist in den meisten Fällen unmöglich. Bei den meisten Projekten befindet sich das Nuget-Verzeichnis packagesneben der SLN-Datei. ABER wenn Sie Dinge kompilieren und verteilen, gibt es keine sln-Datei und kein Paketverzeichnis. Während der Kompilierung werden die benötigten Dinge (aber nicht alles) in das bin-Verzeichnis kopiert. Am besten kopieren Sie die gewünschte Datei mit einem Postbuild-Skript.
George Mauer

Antworten:

1036

Ich habe die folgende Eigenschaft definiert, da wir diese häufig in Unit-Tests verwenden.

public static string AssemblyDirectory
{
    get
    {
        string codeBase = Assembly.GetExecutingAssembly().CodeBase;
        UriBuilder uri = new UriBuilder(codeBase);
        string path = Uri.UnescapeDataString(uri.Path);
        return Path.GetDirectoryName(path);
    }
}

Die Assembly.LocationEigenschaft liefert manchmal einige lustige Ergebnisse, wenn Sie NUnit verwenden (wo Assemblys aus einem temporären Ordner ausgeführt werden). Daher bevorzuge ich die Verwendung, CodeBasedie Ihnen den Pfad im URI-Format gibt, dann UriBuild.UnescapeDataStringden File://am Anfang entfernt und GetDirectoryNamein das normale Windows-Format ändert .

John Sibly
quelle
29
Dies ist ein Problem, auf das ich gestoßen bin. Wenn Ihr Verzeichnisname lautet: c: \ My% 20Directory, gibt Uri.UnescapeDataString Folgendes zurück: c: \ My Directory Dies bedeutet, dass File.Exists ("c: \ My Directory \ MyFile.txt" ") gibt false zurück, da der richtige Pfad tatsächlich" c: \ My% 20Directory \ MyFile.txt "ist. Ich bin darauf gestoßen, da unsere SVN-Pfade Leerzeichen enthalten und beim Auschecken die Leerzeichen codiert werden.
Reihe1
5
Seien Sie vorsichtig, wenn Sie dies verwenden, um File.Exist () zu überprüfen, da diese Methode im UNC-Pfad false zurückgibt. Verwenden Sie stattdessen die Antwort von @ Keith.
AZ.
3
Wusste nicht, dass Sie statisch vor die Öffentlichkeit stellen können. Gut zu wissen und ich denke, ich bevorzuge die Lesbarkeit
Valamas
5
Hinweis: Dies funktioniert nicht mit Netzwerkstandorten (z. B. \\ REMOT_EPC \ Folder)
Muxa
5
Dies funktioniert auch nicht, wenn das Verzeichnis die Nummernzeichen '#' enthält. Nummernschilder sind in Verzeichnis- und Dateinamen in Windows zulässig.
Huemac
321

Hilft das?

//get the full location of the assembly with DaoTests in it
string fullPath = System.Reflection.Assembly.GetAssembly(typeof(DaoTests)).Location;

//get the folder that's in
string theDirectory = Path.GetDirectoryName( fullPath );
Keith
quelle
siehe meine Bearbeitung, nicht wahr, ist das etwas Seltsames daran, wie MbUnit Dinge macht?
George Mauer
3
Stellen Sie die XML-Dateien so ein, dass sie Inhalt sind, mit der DLL kopiert werden oder Ressourcen aus der DLL gelesen werden.
Keith
22
Oder einfachtypeof(DaoTests).Assembly
SLaks
4
@SLaks @JohnySkovdal @Keith: Hey Leute, benutzt Assembly.GetExecutingAssembly(). Es "ruft die Assembly ab, die den Code enthält, der gerade ausgeführt wird" (aus der Methodenbeschreibung). Ich verwende dies in meinem AddIn " EntitiesToDTOs ". Ein echtes Beispiel finden Sie unter AssemblyHelper.cs .
Kzfabi
4
Hatte ein Problem mit dem Beitrag von @John Silby, da er nicht für UNC-Pfade funktioniert ... zB \\ Server \ Folder \ File.ext. Dieser hat den Trick gemacht. +1
Blueberry
312

So einfach ist das:

var dir = AppDomain.CurrentDomain.BaseDirectory;
Jalal El-Shaer
quelle
11
Dies sollte die akzeptierte Lösung sein. AppDomain.CurrentDomain.BaseDirectory ist der richtige Ansatz.
aBetterGamer
5
Vielen Dank, dass Sie mich darauf aufmerksam gemacht haben. Ich bin mir nicht sicher, ob dies zu dem Zeitpunkt verfügbar war, als ich die Frage gestellt habe, aber jetzt.
George Mauer
120
Nein, das ist falsch. Dies gibt den Pfad des ORIGINAL ENTRY POINT zurück, nicht den aktuell ausgeführten Code. Wenn Sie eine Assembly manuell von einem anderen Pfad geladen haben oder wenn sie von GAC geladen wurde, wird das falsche Ergebnis zurückgegeben. Diese Antwort ist richtig: stackoverflow.com/a/283917/243557 Noch schneller Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location).
Nathanchere
9
Eigentlich funktioniert dies nicht in Webanwendungen, aber soweit ich festgestellt habe, sollte die folgende Erweiterung für jede Art von Anwendung funktionieren:AppDomain.CurrentDomain.RelativeSearchPath ?? AppDomain.CurrentDomain.BaseDirectory
Ilya Chernomordik
4
Dies eignet sich hervorragend für Komponententests, wenn Sie nur den ursprünglichen Bin-Pfad Ihrer Testbaugruppe abrufen möchten (z. B. um zusätzliche Datendateien in Unterordnern zu erreichen). Die Testbaugruppe ist der Einstiegspunkt Ihres Codes.
MarioDS
68

Wie Johns Antwort, jedoch eine etwas weniger ausführliche Erweiterungsmethode.

public static string GetDirectoryPath(this Assembly assembly)
{
    string filePath = new Uri(assembly.CodeBase).LocalPath;
    return Path.GetDirectoryName(filePath);            
}

Jetzt können Sie tun:

var localDir = Assembly.GetExecutingAssembly().GetDirectoryPath();

oder wenn Sie es vorziehen:

var localDir = typeof(DaoTests).Assembly.GetDirectoryPath();
Sneal
quelle
6
Meinten Sie assemblystatt Assembly.GetExecutingAssembly()?
Dude Pascalou
3
Wie Dude betont, haben Sie ein Argument übergeben und es nicht verwendet.
Chris Moschini
4
Diese Antwort ist für die vorliegende Frage einfach falsch. Eine modifizierte Version dieser Antwort kann Ihnen den Pfad einer bestimmten Assembly geben. Hier suchen wir jedoch speziell nach der ausführenden Assembly, sodass das Übergeben einer Assembly keinen Sinn ergibt. Eine Erweiterungsmethode ist das falsche Werkzeug für den Job.
Edward Brey
46

Die einzige Lösung, die bei der Verwendung von CodeBase- und UNC-Netzwerkfreigaben für mich funktioniert hat, war:

System.IO.Path.GetDirectoryName(new System.Uri(System.Reflection.Assembly.GetExecutingAssembly().CodeBase).LocalPath);

Es funktioniert auch mit normalen URIs.

Ignacio Soler Garcia
quelle
5
Dies sollte die akzeptierte Antwort sein. Es ist wirklich ärgerlich, dass die Standardcodebasis die UNC-Freigaben nicht korrekt verarbeitet.
Daniel Gilbert
Dies kommt zum Absturz, wenn der Ordner Leerzeichen enthält und Gott weiß, welche anderen Zeichen ...
MarioDS
1
Ich habe dies häufig verwendet und ein Szenario gefunden, in dem es fehlschlägt: Wenn diese Codezeile selbst Teil eines NuGet-Pakets ist, das dann von einer Anwendung verwendet wird! Auch wir können dieses Szenario unterstützen , indem sie ersetzt GetExecutingAssembly()durch GetCallingAssembly().
Timo
@ Timo: Haben Sie überprüft, ob diese Änderung Nebenwirkungen hat? Wenn ja, bearbeiten Sie bitte die Antwort, um das Update einzuschließen.
Ignacio Soler Garcia
@IgnacioSolerGarcia Leider muss ich berichten, dass es nur eine Schicht tief funktioniert hat, dh es schlägt fehl, wenn das NuGet-Paket von einem anderen NuGet-Paket aufgerufen wurde! Ich benutze dies jetzt (aus einem Kommentar auf dieser Seite von Chernomordik) : AppDomain.CurrentDomain.RelativeSearchPath ?? AppDomain.CurrentDomain.BaseDirectory. Der erste Teil ist für Webanwendungen und der zweite für andere Anwendungen.
Timo
32

Dies sollte funktionieren, es sei denn, die Assembly ist schattenkopiert :

string path = System.Reflection.Assembly.GetExecutingAssembly().Location
Jodonnell
quelle
14

Was ist damit:

System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);
huseyint
quelle
11

Ich vermute, dass das eigentliche Problem hier darin besteht, dass Ihr Testläufer Ihre Baugruppe an einen anderen Ort kopiert. Zur Laufzeit gibt es keine Möglichkeit festzustellen, woher die Assembly kopiert wurde, aber Sie können wahrscheinlich einen Schalter umlegen, um dem Testläufer mitzuteilen, dass die Assembly von ihrem Standort aus ausgeführt und nicht in ein Schattenverzeichnis kopiert werden soll.

Ein solcher Schalter ist natürlich wahrscheinlich für jeden Testläufer unterschiedlich.

Haben Sie darüber nachgedacht, Ihre XML-Daten als Ressourcen in Ihre Testassembly einzubetten?

Curt Hagenlocher
quelle
+1 für den Hinweis auf das Problem beim Kopieren von Schatten. Es ist jedoch tatsächlich möglich, den ursprünglichen Ort aus dem zu bestimmen Assembly.CodeBase.
tm1
11
AppDomain.CurrentDomain.BaseDirectory

funktioniert mit MbUnit GUI.

user368021
quelle
Dies funktionierte hervorragend zum Schreiben einer Datei relativ zum Stammverzeichnis in einer asp.net-Web-App
Philip Pittle
Ich habe festgestellt, dass dieser im Allgemeinen am besten funktioniert. Wählen Sie es aus, wenn Sie sich nicht sicher sind.
Erik Bergstedt
10

Ich glaube, das würde für jede Art von Anwendung funktionieren:

AppDomain.CurrentDomain.RelativeSearchPath ?? AppDomain.CurrentDomain.BaseDirectory
Ilya Chernomordik
quelle
1
Meine Experimente zeigen, dass dies die narrensicherste Antwort ist, die nicht nur Web- und Konsolenanwendungen abdeckt, sondern auch Aufrufe von Komponententests und NuGet-Paketen (verschachtelt auf jeder Rekursionsstufe).
Timo
8

Soweit ich das beurteilen kann, haben die meisten anderen Antworten einige Probleme.

Der richtige Weg, dies für eine festplattenbasierte (im Gegensatz zu webbasierten), nicht GACed-Assembly zu tun, besteht darin, die CodeBaseEigenschaft der aktuell ausgeführten Assembly zu verwenden .

Dies gibt eine URL ( file://) zurück. Anstatt mit der Manipulation von Strings herumzuspielen oder UnescapeDataStringkann dies mit minimalem Aufwand konvertiert werden, indem die LocalPathEigenschaft von genutzt wird Uri.

var codeBaseUrl = Assembly.GetExecutingAssembly().CodeBase;
var filePathToCodeBase = new Uri(codeBaseUrl).LocalPath;
var directoryPath = Path.GetDirectoryName(filePathToCodeBase);
Spender
quelle
1
Funktioniert nicht, wenn der Pfad enthält #( EscapedCodeBasefunktioniert, aber EscapedCodeBase funktioniert nicht, wenn der Pfad z. B. %20wörtlich enthält (was eine zulässige Zeichenfolge in einem Windows-Pfad ist)
Martin Ba
Wenn wir diesen Code in einem NuGet-Paket haben möchten, können wir dieses Szenario durch Ersetzen GetExecutingAssembly()durch beheben GetCallingAssembly().
Timo
8

Wie wäre es damit ...

string ThisdllDirectory = System.IO.Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);

Dann hacken Sie einfach ab, was Sie nicht brauchen

David C Fuchs
quelle
7
var assembly = System.Reflection.Assembly.GetExecutingAssembly();
var assemblyPath = assembly.GetFiles()[0].Name;
var assemblyDir = System.IO.Path.GetDirectoryName(assemblyPath);
Mark Cidade
quelle
7

Hier ist ein VB.NET-Port von John Siblys Code. Visual Basic unterscheidet nicht zwischen Groß- und Kleinschreibung, daher kollidierten einige seiner Variablennamen mit Typnamen.

Public Shared ReadOnly Property AssemblyDirectory() As String
    Get
        Dim codeBase As String = Assembly.GetExecutingAssembly().CodeBase
        Dim uriBuilder As New UriBuilder(codeBase)
        Dim assemblyPath As String = Uri.UnescapeDataString(uriBuilder.Path)
        Return Path.GetDirectoryName(assemblyPath)
    End Get
End Property
Mike Schall
quelle
6

In all den Jahren hat niemand diesen tatsächlich erwähnt. Ein Trick, den ich aus dem großartigen ApprovalTests-Projekt gelernt habe . Der Trick besteht darin, dass Sie die Debugging-Informationen in der Assembly verwenden, um das ursprüngliche Verzeichnis zu finden.

Dies funktioniert weder im RELEASE-Modus noch bei aktivierten Optimierungen oder auf einem anderen Computer als dem, auf dem er kompiliert wurde.

Dadurch erhalten Sie jedoch Pfade, die sich auf den Speicherort der Quellcodedatei beziehen , aus der Sie sie aufrufen

public static class PathUtilities
{
    public static string GetAdjacentFile(string relativePath)
    {
        return GetDirectoryForCaller(1) + relativePath;
    }
    public static string GetDirectoryForCaller()
    {
        return GetDirectoryForCaller(1);
    }


    public static string GetDirectoryForCaller(int callerStackDepth)
    {
        var stackFrame = new StackTrace(true).GetFrame(callerStackDepth + 1);
        return GetDirectoryForStackFrame(stackFrame);
    }

    public static string GetDirectoryForStackFrame(StackFrame stackFrame)
    {
        return new FileInfo(stackFrame.GetFileName()).Directory.FullName + Path.DirectorySeparatorChar;
    }
}
George Mauer
quelle
5

Das aktuelle Verzeichnis, in dem Sie existieren.

Environment.CurrentDirectory;  // This is the current directory of your application

Wenn Sie die XML-Datei mit Build kopieren, sollten Sie sie finden.

oder

System.Reflection.Assembly assembly = System.Reflection.Assembly.GetAssembly(typeof(SomeObject));

// The location of the Assembly
assembly.Location;
David Basarab
quelle
Dies ist problematisch, wenn die Baugruppe im Schatten kopiert wurde .
Spender
+1520! Environment.CurrentDirectoryfunktioniert, wenn Sie Reflection in der MSBuild-Taskklasse verwenden, in der sich die ausführende Assembly in GAC befindet und sich Ihr Code an einer anderen Stelle befindet.
Vulkanischer Rabe
4
Im Allgemeinen sagt CurrentDirectory nicht, wo sich Ihre ausführbaren Dateien befinden. Dafür wird es nicht verwendet. Es ist einfach häufig derselbe Ort, an dem sich die ausführbaren Dateien befinden, sodass viele Programmierer den Unterschied nicht verstehen. Dann verursachen sie Probleme für einige der Endbenutzer, die erwartet haben, dass die Anwendung die ordnungsgemäße Verwendung von CurrentDirectory versteht.
Bent Tranberg
5

Ich habe Assembly.CodeBase anstelle von Location verwendet:

Assembly a;
a = Assembly.GetAssembly(typeof(DaoTests));
string s = a.CodeBase.ToUpper(); // file:///c:/path/name.dll
Assert.AreEqual(true, s.StartsWith("FILE://"), "CodeBase is " + s);
s = s.Substring(7, s.LastIndexOf('/') - 7); // 7 = "file://"
while (s.StartsWith("/")) {
    s = s.Substring(1, s.Length - 1);
}
s = s.Replace("/", "\\");

Es hat funktioniert, aber ich bin nicht mehr sicher, ob es 100% korrekt ist. Auf der Seite unter http://blogs.msdn.com/suzcook/archive/2003/06/26/assembly-codebase-vs-assembly-location.aspx heißt es:

"Die CodeBase ist eine URL zu dem Ort, an dem die Datei gefunden wurde, während der Speicherort der Pfad ist, in den sie tatsächlich geladen wurde. Wenn die Assembly beispielsweise aus dem Internet heruntergeladen wurde, beginnt ihre CodeBase möglicherweise mit" http: // ". , aber sein Speicherort kann mit "C: \" beginnen. Wenn die Datei im Schatten kopiert wurde, ist der Speicherort der Pfad zur Kopie der Datei im Schattenkopierverzeichnis. Es ist auch gut zu wissen, dass die CodeBase nicht garantiert ist Wird für Assemblys im GAC festgelegt. Der Speicherort wird jedoch immer für Assemblys festgelegt, die von der Festplatte geladen werden. "

Möglicherweise möchten Sie CodeBase anstelle von Location verwenden.

Dan Gibson
quelle
1
@Kiquenet: So viel Code nur zum Konvertieren eines URI in einen Pfad. Sicher könnte es verbessert werden. Schauen Sie sich die Antwort von Mike Schall oder SoMoS an. Sie sollten nicht versuchen, URIs auf Zeichenfolgenebene zu konvertieren, sondern die geeigneten Objekte verwenden. OK, es ist auch umständlich, dass Assembly.CodeBase anstelle eines geeigneteren Objekts wie URI oder FileInfo eine Zeichenfolge zurückgibt.
Sieben
2

Sie können den Bin-Pfad über AppDomain.CurrentDomain.RelativeSearchPath abrufen

Fass es zusammen
quelle
2

Alle vorgeschlagenen Antworten funktionieren, wenn der Entwickler den Code so ändern kann, dass er das erforderliche Snippet enthält. Wenn Sie dies jedoch tun möchten, ohne Code zu ändern, können Sie den Prozess-Explorer verwenden.

Es werden alle ausführenden DLLs auf dem System aufgelistet. Möglicherweise müssen Sie die Prozess-ID Ihrer laufenden Anwendung ermitteln. Dies ist jedoch normalerweise nicht allzu schwierig.

Ich habe eine vollständige Beschreibung geschrieben, wie dies für eine DLL in II funktioniert - http://nodogmablog.bryanhogan.net/2016/09/locating-and-checking-an-executing-dll-on-a-running-web -Server/

Bryan
quelle
Beachten Sie, dass der Code im Artikel erstens ziemlich IIS-zentriert ist und zweitens (glaube ich) alle aktuell geladenen DLLs enthält, nicht die, die gleichzeitig ausgeführt werden.
George Mauer
Das angegebene Beispiel bezieht sich auf iis, aber die gleichen Schritte gelten, wenn die DLL in einem Prozess außerhalb von iis ausgeführt wird. Es geht nur darum, die Prozess-ID zu identifizieren. Ich werde den Artikel aktualisieren, um das zu bemerken. Danke für den Vorschlag.
Bryan
2

In einer Windows Form App können Sie einfach verwenden Application.StartupPath

Für DLLs und Konsolen-Apps ist der Code jedoch viel schwerer zu merken ...

string slash = Path.DirectorySeparatorChar.ToString();
string root = Path.GetDirectoryName(System.Reflection.Assembly.GetExecutingAssembly().Location);

root += slash;
string settingsIni = root + "settings.ini"
Shane J.
quelle
1
string path = Path.GetDirectoryName(typeof(DaoTests).Module.FullyQualifiedName);
Jesse C. Slicer
quelle
1

Sie erhalten ein falsches Verzeichnis, wenn ein Pfad das Symbol '#' enthält. Daher verwende ich eine Modifikation der Antwort von John Sibly, nämlich die Kombination UriBuilder.Path und UriBuilder.Fragment:

public static string AssemblyDirectory
{
    get
    {
        string codeBase = Assembly.GetExecutingAssembly().CodeBase;
        UriBuilder uri = new UriBuilder(codeBase);
        //modification of the John Sibly answer    
        string path = Uri.UnescapeDataString(uri.Path.Replace("/", "\\") + 
          uri.Fragment.Replace("/", "\\"));
        return Path.GetDirectoryName(path);
     }
}
Fedor Shihantsov
quelle
0

Das habe ich mir ausgedacht. Zwischen Webprojekten Unit-Tests (Nunit und Resharper Test Runner) ; Ich fand das funktionierte für mich.

Ich habe nach Code gesucht, um festzustellen, in welcher Konfiguration sich der Build befindet Debug/Release/CustomName. Leider die #if DEBUG. Also wenn jemand das verbessern kann !

Fühlen Sie sich frei zu bearbeiten und zu verbessern.

App-Ordner abrufen . Nützlich für Web-Roots, Unittests, um den Ordner mit Testdateien abzurufen.

public static string AppPath
{
    get
    {
        DirectoryInfo appPath = new DirectoryInfo(AppDomain.CurrentDomain.BaseDirectory);

        while (appPath.FullName.Contains(@"\bin\", StringComparison.CurrentCultureIgnoreCase)
                || appPath.FullName.EndsWith(@"\bin", StringComparison.CurrentCultureIgnoreCase))
        {
            appPath = appPath.Parent;
        }
        return appPath.FullName;
    }
}

Bin-Ordner abrufen : Nützlich zum Ausführen von Assemblys mithilfe von Reflection. Wenn Dateien aufgrund von Build-Eigenschaften dorthin kopiert werden.

public static string BinPath
{
    get
    {
        string binPath = AppDomain.CurrentDomain.BaseDirectory;

        if (!binPath.Contains(@"\bin\", StringComparison.CurrentCultureIgnoreCase)
            && !binPath.EndsWith(@"\bin", StringComparison.CurrentCultureIgnoreCase))
        {
            binPath = Path.Combine(binPath, "bin");
            //-- Please improve this if there is a better way
            //-- Also note that apps like webapps do not have a debug or release folder. So we would just return bin.
#if DEBUG
            if (Directory.Exists(Path.Combine(binPath, "Debug"))) 
                        binPath = Path.Combine(binPath, "Debug");
#else
            if (Directory.Exists(Path.Combine(binPath, "Release"))) 
                        binPath = Path.Combine(binPath, "Release");
#endif
        }
            return binPath;
    }
}
Valamas
quelle
0

Das sollte funktionieren:

ExeConfigurationFileMap fileMap = new ExeConfigurationFileMap();
Assembly asm = Assembly.GetCallingAssembly();
String path = Path.GetDirectoryName(new Uri(asm.EscapedCodeBase).LocalPath);

string strLog4NetConfigPath = System.IO.Path.Combine(path, "log4net.config");

Ich verwende dies, um DLL-Dateibibliotheken zusammen mit einigen Konfigurationsdateien bereitzustellen (dies dient zur Verwendung von log4net aus der DLL-Datei heraus).

mmmmmm
quelle
Wofür wird fileMaphier verwendet?
George Mauer
0

Ich finde meine Lösung ausreichend, um den Standort abzurufen.

var executingAssembly = new FileInfo((Assembly.GetExecutingAssembly().Location)).Directory.FullName;
Tez Wingfield
quelle
Dies ist bereits eine der am besten bewerteten Antworten und wird in der Frage ausdrücklich als etwas erwähnt, das in dieser Situation nicht funktioniert.
George Mauer
Entschuldigung muss das verpasst haben! Offensichtlich habe ich nicht gründlich durchgelesen.
Tez Wingfield
0

Ich habe das gleiche Verhalten NUnitin der Vergangenheit. Standardmäßig NUnitkopiert Ihre Assembly in das temporäre Verzeichnis. Sie können dieses Verhalten in den NUnitEinstellungen ändern :

Geben Sie hier die Bildbeschreibung ein

Vielleicht TestDriven.NETund MbUnitGUI haben die gleichen Einstellungen.

Andrey Bushman
quelle
-3

Ich benutze dies, um den Pfad zum Bin-Verzeichnis zu erhalten:

var i = Environment.CurrentDirectory.LastIndexOf(@"\");
var path = Environment.CurrentDirectory.Substring(0,i); 

Sie erhalten dieses Ergebnis:

"c: \ Benutzer \ Ricooley \ Dokumente \ Visual Studio 2010 \ Projekte \ Windows_Test_Project \ Windows_Test_Project \ bin"

rcooley56
quelle
6
Ich sehe keinen Grund, Path.getDirectoryName hier zu vermeiden
Max Keller
@MaxKeller Wenn Sie keine Gründe sehen, heißt das nicht, dass es richtig ist. Diese alternative Methode von Path.GetDirectoryName ist zehnmal schneller.
Ruslan Veselov
-3

Internetanwendung?

Server.MapPath("~/MyDir/MyFile.ext")
user2009677
quelle
2
@christiandev Dies ist eine Antwort, aber es scheint vielleicht eine Antwort auf die falsche Frage zu sein. Aus der Frage geht ziemlich klar hervor, dass dies keine Webanwendung ist, sondern eine Assembly, die mit MbUnit ausgeführt wird. Abgesehen davon ist die Antwort aufgrund des Kopierens von Asp.Net-Schatten immer noch nicht richtig (obwohl es möglicherweise das ist, wonach jemand sucht, der auf dieser Frage landet).
George Mauer