Visual Studio: Programmatically Create Project Items in project directory - c#

I am trying to create a project item programmatically. i have this code
string itemPath = currentSolution.GetProjectItemTemplate("ScreenTemplate.zip", "csproj");
currentSolution.Projects.Item(1).ProjectItems.AddFromTemplate(itemPath, name);
currentSolution.Projects.Item(1).Save();
But I would like to create the item in a specified directory inside the project (this creates the item in the root of the project). Is it possible? Thanks for help!

That's roughly how I add my cpp file, should be no different in your case.
The code will add the file under "SourceFiles\SomeFolder" in the project and also in the "Source Files" folder in the project view tree (it should be already there).
Project project = null; // you should get the project from the solution or as active project or somehow else
string fileName = "myFileName.cpp";
string fileRelativePath = "SourceFiles\\SomeFolder\\" + fileName;
// First see if the file is already there and delete it (to create an empty one)
string fileFullPath = Path.GetDirectoryName(project.FileName) + "\\" + fileRelativePath;
if (File.Exists(fileFullPath))
File.Delete(fileFullPath);
// m_applicationObject here is DTE2 or DTE2
string templatePath = (m_applicationObject.Solution as Solution2).ProjectItemsTemplatePath(project.Kind);
ProjectItem folderItem = project.ProjectItems.Item("Source Files");
ProjectItem myFileItem = folderItem.ProjectItems.AddFromTemplate(templatePath + "/newc++file.cpp", fileRelativePath);
Please don't expect the code to compile straight away and run - some checks for invalid state aren't performed here.

Related

Dynamic Paths for MStest Unit Test DataSource

I am using CSV files as datasource for my MSTest unit tests. I had the idea that I would generate dynamic file paths for the CSV file, store them in a variable and then pass the variable in ConnectionString of databasesource for the unit tests.
However, now I have learned that we cannot pass variable in Datasource Connection string. Any idea how can I make the file path dynamic as the unit test dll will be executed on different machines and a static path is not an option.
The CSV files are already added in the solution.
public string GetAbsolutePath(string relativePath)
{
string path = System.Reflection.Assembly.GetCallingAssembly().CodeBase;
int lastIndex = path.LastIndexOf("bin", StringComparison.OrdinalIgnoreCase);
string actualPath = path.Substring(0, lastIndex);
string projectPath = new Uri(actualPath).LocalPath;
string absolutePath = projectPath + relativePath;
return absolutePath;
}
The above code is for c# will run on any machine to reach file inside your project. this code will give your project folder path in "projectPath " variable even if you use different machines because it is generated with reference to your dll file. the only thing you need to do is pass relative path of folder or file you want to reach inside your project.
Note:- find bin folder in your project "projectPath" variable will give you path till that and then accordingly pass your relative path as a parameter. Please debug function to get a clear understanding.
Let me know if you need clarification

C#: opening a text file stored within the same project as the app

I managed to open a text file using an absolute path (in Visual Studio 2017) although if I change the location of my Solution folder the whole code would not work anymore as the actual physical path has changed and the code can not reference an existing location anymore.
I tried to create a text file within the same project and I would now like to open this file in my code, so if the location of the whole Solution changes the program can still work, would anyone be so kind to help me fix this issue?
I have also looked online for some different solution using code that references the current directory but I can't get my head around it as the current directory seems to be bin/debug and if I try to insert the file there the code doesn't recognize the location (also it doesn't look like a clean solution to me).
This is the code I am using so far in a WPF app, the whole purpose is to open the content of the text file containing countries listed line by line and to add them to a list box which will be displayed when a checkbox will be ticked.
private void listCountry_Initialized(object sender, EventArgs e)
{
listCountry.Visibility = Visibility.Hidden;
string path = "C:\\Users\\david\\source\\repos\\StudentRecord\\StudentRecordSystemMod\\StudentRecord\\country.txt";
if (File.Exists(path))
{
string[] myCountryFile = File.ReadAllLines(path);
foreach (var v in myCountryFile)
{
listCountry.Items.Add(v);
}
}
}
This is a great use case for OpenFileDialog Class.
Represents a common dialog box that allows a user to specify a filename for one or more files to open.
Here is the example of use, from the documentation.
// Configure open file dialog box
Microsoft.Win32.OpenFileDialog dlg = new Microsoft.Win32.OpenFileDialog();
dlg.FileName = "Document"; // Default file name
dlg.DefaultExt = ".txt"; // Default file extension
dlg.Filter = "Text documents (.txt)|*.txt"; // Filter files by extension
// Show open file dialog box
Nullable<bool> result = dlg.ShowDialog();
// Process open file dialog box results
if (result == true)
{
// Open document
string filename = dlg.FileName;
}
Assuming C:\\Users\\david\\source\\repos\\StudentRecord\\StudentRecordSystemMod\\ is your project, and StudentRecord\\country.txt is a project folder and file in your project - you need change "Copy to Output Directory" to be "Always Copy" or "Copy If Newer" and "Build Action" to "Content" for the file in your project.
As you can see from the screenshot above, the folder structure for this content is created as well.
Then change your path assignment to be something like the following:
string path = string.Join(#"\", Application.ExecutablePath, #"StudentRecord\country.txt");
Clean and simple, place the file you want to open next to where the executable is generated, remember the executable path changes depending to if your project is in Debug or Release build mode. Now set:
string path = "country.txt";
By only providing a filename, the file is looked for in the same folder as the executable. Just remember that when you move the executable you must also move the file to the same place, but if you move the entire project folder then you're already set.
However, if you want to keep your file in a fixed location regardless of where you have your executable and/or VS project files, then the simplest path for it is:
string path = "C:\\country.txt";
This is an absolute path, but it's quite simple and very robust to changes, you would have to change the drive letter to break it and if C: is where your operating system files are then you probably won't do that.
If you don't like to have your files around in your root, you can always have a path like this:
string path = "C:\\ProjectNameFiles\\country.txt";
Or if you prefer to maintain a hierarchy of projects then you can use:
string path = "C:\\MyProjectsFiles\\ProjectName\\country.txt";
With this, every project can have a directory for the files it needs to open. These are all absolute paths, but are notably simpler than the one you posted, and they have a more fixed and organized structure.

Get Project Root Directory Name in MVC 5

I can't seem to find an answer anywhere on how to get the name of the first folder of my project.
So for Example I have a BaseSite folder and inside that BaseSite folder is where my solution file sits, in there I have many projects. I need to retrive the "BaseSite" name and only that.
I have found various examples with AppDomain.CurrentDomain.GetData("DataDirectory").ToString(); but that gives you the full path and my folder name is buried in there.
Same with: Server.MapPath("~/App_Data/somedata.xml");
Please check. It will return the base directory.
var BaseDirectory = new DirectoryInfo(Server.MapPath("~")).Parent.Name;
And
new DirectoryInfo(Server.MapPath("~/App_Data/somedata.xml")).Parent.Name;
I hope this will help you.
//this path will return current project folder
string path = AppDomain.CurrentDomain.BaseDirectory;
DirectoryInfo info = new DirectoryInfo(AppDomain.CurrentDomain.BaseDirectory);
string infy = info.Parent.FullName; //this will give you the full path of project folder.
if you have to go one level up then add
info.Parent.Parent.FullName
And if you have to go one level down to subdirectory. Then use
DirectoryInfo[] directoryinfo = info.GetDirectories("SearchPattern or your subdirectory name");
string subdirectory = directoryinfo.FirstOrDefault().FullName;

Load a file from another project

I have two projects in my solution and project A has a reference to project B. Project A calls a function in project B that should load a document that is within Project B:
return XDocument.Load(#"Mock\myDoc.html");
The problem is that XDocument.Load is using the path from Project A (where there is no Mock\myDoc.html).
I have tried using
string curDir = Directory.GetCurrentDirectory();
var path = String.Format("file:///{0}/Mock/myDoc.html", curDir);
but this as well gives me a path to ProjectA\Mock\myDoc.html when instead it should be ProjectB\Mock\myDoc.html. What am I missing?
EDIT: "Copy to Output" for the file "myDoc.html" is set to "Copy always" and the file is available in the Output folder of Project B.
There is only one current working Directory for all of your code at runtime. You'll have to navigate up to the solution directory, then back down to the other Project.
string solutiondir = Directory.GetParent(
Directory.GetCurrentDirectory()).Parent.FullName;
// may need to go one directory higher for solution directory
return XDocument.Load(solutiondir + "\\" + ProjectBName + "\\Mock\\myDoc.html");
string str = Path.GetDirectoryName(Directory.GetParent(Directory.GetCurrentDirectory()).Parent.FullName) + "\\->ProjectName<-";
I think this idea can help you.
Temporarily update the application current directory:
string saveDir = Directory.GetCurrentDirectory();
Directory.SetCurrentDirectory("the_projectB_defaultDirectory");
ProjectBfunction() ;
Directory.SetCurrentDirectory(saveDir) ;
If your directory architecture permits it, you may deduce the projectB directory from ProjectA current directory or from the .exe directory (i.e. Application.StartupPath).

Save/retrieve a file in a project directory, not the output directory

I'm creating a simple .NET console application where I want to save a file in a folder that's part of the root project, like so: SolutionName.ProjectName\TestData\. I want to put test.xml into the TestData folder. However, when I go to save my XDocument, it saves it to SolutionName.ProjectName\bin\x86\Debug Console\test.xml.
What do I need to do to save or retrieve the file in a folder that is a child of project directory?
Your console application is, once compiled, not really related to your Visual Studio solution anymore. The best way is probably to simply 'feed' the output path to your application as an command line argument:
Public Sub Main(args as String())
' don't forget validation: handle situation where no or invalid arguments supplied
Dim outputFile = Path.Combine(args(0), "TestData", "test.xml")
End Sub
Now you can run your application like so:
myapp.exe Path\To\SolutionFolder
I've seen this before but never actually tried it out. Did a quick search and dug this up:
System.AppDomain.CurrentDomain.BaseDirectory
Give that a shot instead of Application.StartupPath for your console app.
You can use the System.IO namespace to get your directory relative to your exe:
var exeDirectory = Application.StartupPath;
var exeDirectoryInfo = new DirectoryInfo(exeDirectory);
var projectDirectoryInfo = exeDirectoryInfo.Parent.Parent.Parnet; // bin/x86/debug to project
var dataPath = Path.Combine(projectDirectoryInfo.FullName, "TestData");
var finalFilename = Path.Combine(dataPath, "test.xml");

Categories

Resources