62

How can I find the location of my application's executable in WPF (C# or VB.Net)?

I've used this code with windows forms:

Application.ExecutablePath.ToString();

But with WPF I received this error from Visual Studio:

System.Window.Application does not contain a definition for ExecutablePath.

Blorgbeard
  • 101,031
  • 48
  • 228
  • 272
Shahin
  • 12,543
  • 39
  • 127
  • 205

8 Answers8

99

System.Reflection.Assembly.GetExecutingAssembly().Location should work.

Blorgbeard
  • 101,031
  • 48
  • 228
  • 272
  • 24
    This may not work properly all the times. It will get the executing assembly, not the application's executable. This means this won't work if running through a referenced DLL if you want the application's executable. – André Santaló Mar 09 '15 at 18:50
38

Several alternatives:

Directory.GetParent(Assembly.GetExecutingAssembly().Location)

System.AppDomain.CurrentDomain.BaseDirectory

Only in VB:

My.Application.Info.DirectoryPath
Konrad Rudolph
  • 530,221
  • 131
  • 937
  • 1,214
  • 2
    System.AppDomain.CurrentDomain.BaseDirectory returns current directory, not executable location, i.e. when run from outlook (sent as a link to \\server\folder\file.exe it will set BaseDirectory to user documents instead executable location – Jakub Pawlinski Nov 05 '15 at 09:23
22

this is useful for you: Application.ExecutablePath equals to:

Process.GetCurrentProcess().MainModule.FileName;
dexiang
  • 1,345
  • 16
  • 23
  • 6
    This is the only thing that worked perfect for me. The alternative - GetExecutingAssembly got me the dll instead of the exe (As mentioned above), and the use of Application.ExecutablePath is not available from where I coded. – Guy Jul 09 '19 at 11:10
11

The following is applicable in the recent versions of .NET Core:

System.Environment.ProcessPath

This returns the path of the executable that started the currently running process.

Salih Kavaf
  • 897
  • 9
  • 17
  • Why is this answer not being upvoted? This is recommended from a performance standpoint over Process.GetCurrentProcess().MainModule.FileName ( [CA1839](https://learn.microsoft.com/ja-jp/dotnet/fundamentals/code-analysis/quality-rules/ca1839) ). It also correctly returns the location of the exe, not the location of the dll. – mikm Jun 04 '22 at 06:25
  • [System.Environment.ProcessPath](https://learn.microsoft.com/en-us/dotnet/api/system.environment.processpath) is available in **.NET 6** or later. This is the best way now. – noobar Feb 28 '23 at 01:34
3

The executing assembly can be a DLL if the code is located in a library:

var executingAssembly = Assembly.GetExecutingAssembly(); //MyLibrary.dll
var callingAssembly = Assembly.GetCallingAssembly(); //MyLibrary.dll
var entryAssembly = Assembly.GetEntryAssembly(); //WpfApp.exe or MyLibrary.dll

So the best way I found is (C#) :

var wpfAssembly = (AppDomain.CurrentDomain
                .GetAssemblies()
                .Where(item => item.EntryPoint != null)
                .Select(item => 
                    new {item, applicationType = item.GetType(item.GetName().Name + ".App", false)})
                .Where(a => a.applicationType != null && typeof(System.Windows.Application)
                    .IsAssignableFrom(a.applicationType))
                    .Select(a => a.item))
            .FirstOrDefault();

So in your case, you can find location of the assembly :

var location = wpfAssembly.Location;
scrat789
  • 2,961
  • 3
  • 30
  • 26
  • Nice technique @scrat789. It gets to the regular .exe's assembly even when running in the debugger. None of that XXX.vshost.exe. – Bryan Knox Aug 15 '15 at 04:35
2

This is what I use. It works even in debugger.

using System.IO;
using System.Diagnostics;

public static string GetMyBinDirectory()
{
    return Path.GetDirectoryName(Process.GetCurrentProcess().MainModule.FileName);
}

It uses some powerfull classes, like Process and ProcessModule

marsh-wiggle
  • 2,508
  • 3
  • 35
  • 52
2

Environment.CurrentDirectory returns parent directory of exe file

mahdi b
  • 37
  • 3
0

Based on others answers, here's an example that shows how to remove the executable name from the path and combine the result with some subfolder and filename:

at my updated version of Hotspotizer (http://github.com/birbilis/Hotspotizer), I've just added support for loading a Gesture Collection file at startup, if found at Library\Default.hsjson, by using the following code:

const string GESTURE_COLLECTION_LIBRARY_PATH = "Library"
const string DEFAULT_GESTURE_COLLECTION = "Default.hsjson"

//...

LoadGestureCollection(
  Path.Combine(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location),
  GESTURE_COLLECTION_LIBRARY_PATH,
  DEFAULT_GESTURE_COLLECTION));
George Birbilis
  • 2,782
  • 2
  • 33
  • 35