Permalink
Browse files

Expand variables such as SolutionDir, ProjectDir in T4 assembly direc…

…tives.
  • Loading branch information...
1 parent 7954372 commit 0961c8fc51d9844313e92fb7ff38ee3ad4c00cbc @mrward mrward committed Sep 25, 2011
@@ -0,0 +1,12 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+
+namespace ICSharpCode.TextTemplating
+{
+ public interface ITextTemplatingStringParser
+ {
+ string GetValue(string propertyName);
+ }
+}
@@ -0,0 +1,13 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+
+namespace ICSharpCode.TextTemplating
+{
+ public interface ITextTemplatingVariables
+ {
+ string Expand(string name);
+ string GetValue(string name);
+ }
+}
@@ -2,6 +2,7 @@
// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
using System;
+using System.IO;
using ICSharpCode.SharpDevelop.Project;
namespace ICSharpCode.TextTemplating
@@ -10,22 +11,33 @@ public class TextTemplatingAssemblyResolver : ITextTemplatingAssemblyResolver
{
IProject project;
IAssemblyParserService assemblyParserService;
+ ITextTemplatingVariables templatingVariables;
public TextTemplatingAssemblyResolver(
IProject project,
- IAssemblyParserService assemblyParserService)
+ IAssemblyParserService assemblyParserService,
+ ITextTemplatingVariables templatingVariables)
{
this.project = project;
this.assemblyParserService = assemblyParserService;
+ this.templatingVariables = templatingVariables;
}
public TextTemplatingAssemblyResolver(IProject project)
- : this(project, new TextTemplatingAssemblyParserService())
+ : this(
+ project,
+ new TextTemplatingAssemblyParserService(),
+ new TextTemplatingVariables())
{
}
public string Resolve(string assemblyReference)
{
+ assemblyReference = ExpandVariables(assemblyReference);
+ if (Path.IsPathRooted(assemblyReference)) {
+ return assemblyReference;
+ }
+
string resolvedAssemblyFileName = ResolveAssemblyFromProject(assemblyReference);
if (resolvedAssemblyFileName == null) {
resolvedAssemblyFileName = ResolveAssemblyFromGac(assemblyReference);
@@ -36,6 +48,11 @@ public string Resolve(string assemblyReference)
return assemblyReference;
}
+ string ExpandVariables(string assemblyReference)
+ {
+ return templatingVariables.Expand(assemblyReference);
+ }
+
string ResolveAssemblyFromProject(string assemblyReference)
{
foreach (ReferenceProjectItem refProjectItem in project.GetItemsOfType(ItemType.Reference)) {
@@ -0,0 +1,27 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+using System.Linq;
+
+namespace ICSharpCode.TextTemplating
+{
+ public static class TextTemplatingDirectoryVariable
+ {
+ public static bool IsDirectoryVariable(string name)
+ {
+ return name.EndsWith("Dir", StringComparison.OrdinalIgnoreCase);
+ }
+
+ public static string AppendTrailingSlashIfMissing(string variableValue)
+ {
+ if (!String.IsNullOrEmpty(variableValue)) {
+ if (variableValue.Last() == '\\') {
+ return variableValue;
+ }
+ return variableValue + "\\";
+ }
+ return String.Empty;
+ }
+ }
+}
@@ -0,0 +1,16 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+using ICSharpCode.Core;
+
+namespace ICSharpCode.TextTemplating
+{
+ public class TextTemplatingStringParser : ITextTemplatingStringParser
+ {
+ public string GetValue(string propertyName)
+ {
+ return StringParser.GetValue(propertyName);
+ }
+ }
+}
@@ -0,0 +1,75 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+
+namespace ICSharpCode.TextTemplating
+{
+ public class TextTemplatingVariableLocation
+ {
+ public TextTemplatingVariableLocation()
+ : this(String.Empty, 0, 0)
+ {
+ }
+
+ public TextTemplatingVariableLocation(
+ string variableName,
+ int index,
+ int length)
+ {
+ this.VariableName = variableName;
+ this.Index = index;
+ this.Length = length;
+ }
+
+ public static TextTemplatingVariableLocation CreateFromString(
+ string text,
+ int unexpandedVariableStartIndex,
+ int unexpandedVariableEndIndex)
+ {
+ int variableNameStart = unexpandedVariableStartIndex + 2;
+ int unexpandedLength = unexpandedVariableEndIndex - unexpandedVariableStartIndex + 1;
+ string variableName = text.Substring(variableNameStart, unexpandedVariableEndIndex - variableNameStart);
+ return new TextTemplatingVariableLocation(variableName, unexpandedVariableStartIndex, unexpandedLength);
+ }
+
+ public string VariableName { get; set; }
+ public int Index { get; set; }
+ public int Length { get; set; }
+
+ public override bool Equals(object obj)
+ {
+ var rhs = obj as TextTemplatingVariableLocation;
+ if (rhs != null) {
+ return (VariableName == rhs.VariableName) &&
+ (Index == rhs.Index) &&
+ (Length == rhs.Length);
+ }
+ return false;
+ }
+
+ public override int GetHashCode()
+ {
+ return base.GetHashCode();
+ }
+
+ public override string ToString()
+ {
+ return String.Format(
+ "VariableName: {0}, Index: {1}, Length: {2}",
+ VariableName, Index, Length);
+ }
+
+ public static TextTemplatingVariableLocation FindVariable(string text, int startSearchIndex)
+ {
+ int start = text.IndexOf("$(", startSearchIndex);
+ if (start >= 0) {
+ int end = text.IndexOf(")", start);
+ if (end >= 0) {
+ return CreateFromString(text, start, end);
+ }
+ }
+ return null;
+ }
+ }
+}
@@ -0,0 +1,92 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+using System.Collections.Generic;
+using System.Linq;
+using System.Text;
+
+namespace ICSharpCode.TextTemplating
+{
+ public class TextTemplatingVariables : ITextTemplatingVariables
+ {
+ ITextTemplatingStringParser stringParser;
+
+ public TextTemplatingVariables()
+ : this(new TextTemplatingStringParser())
+ {
+ }
+
+ public TextTemplatingVariables(
+ ITextTemplatingStringParser stringParser)
+ {
+ this.stringParser = stringParser;
+ }
+
+ public string Expand(string name)
+ {
+ var variablesBuilder = new TextTemplatingVariablesStringBuilder(name, this);
+ foreach (TextTemplatingVariableLocation variableLocation in GetVariables(name)) {
+ variablesBuilder.AppendTextBeforeVariable(variableLocation);
+ variablesBuilder.AppendVariable(variableLocation);
+ }
+ variablesBuilder.AppendRemaining();
+ return variablesBuilder.ToString();
+ }
+
+ public IEnumerable<TextTemplatingVariableLocation> GetVariables(string text)
+ {
+ if (String.IsNullOrEmpty(text)) {
+ yield break;
+ }
+
+ int currentIndex = 0;
+ while (true) {
+ TextTemplatingVariableLocation variableLocation =
+ FindVariable(text, currentIndex);
+ if (variableLocation != null) {
+ currentIndex = variableLocation.Index + variableLocation.Length;
+ yield return variableLocation;
+ } else {
+ yield break;
+ }
+ }
+ }
+
+ TextTemplatingVariableLocation FindVariable(string text, int startIndex)
+ {
+ return TextTemplatingVariableLocation.FindVariable(text, startIndex);
+ }
+
+ public string GetValue(string name)
+ {
+ if (name == null) {
+ return String.Empty;
+ }
+
+ string variableValue = stringParser.GetValue(name);
+ if (IsDirectoryVariable(name)) {
+ return AppendTrailingSlashIfMissing(variableValue);
+ }
+ return GetEmptyStringIfNull(variableValue);
+ }
+
+ bool IsDirectoryVariable(string name)
+ {
+ return TextTemplatingDirectoryVariable.IsDirectoryVariable(name);
+ }
+
+ string AppendTrailingSlashIfMissing(string variableValue)
+ {
+ return TextTemplatingDirectoryVariable.AppendTrailingSlashIfMissing(variableValue);
+ }
+
+ string GetEmptyStringIfNull(string variableValue)
+ {
+ if (variableValue != null) {
+ return variableValue;
+ }
+ return String.Empty;
+ }
+ }
+}
@@ -0,0 +1,73 @@
+// Copyright (c) AlphaSierraPapa for the SharpDevelop Team (for details please see \doc\copyright.txt)
+// This code is distributed under the GNU LGPL (for details please see \doc\license.txt)
+
+using System;
+using System.Text;
+
+namespace ICSharpCode.TextTemplating
+{
+ public class TextTemplatingVariablesStringBuilder
+ {
+ StringBuilder variablesBuilder = new StringBuilder();
+ string unexpandedVariablesString;
+ ITextTemplatingVariables templatingVariables;
+ int currentIndex;
+
+ public TextTemplatingVariablesStringBuilder(
+ string unexpandedVariablesString,
+ ITextTemplatingVariables templatingVariables)
+ {
+ this.unexpandedVariablesString = unexpandedVariablesString;
+ this.templatingVariables = templatingVariables;
+ }
+
+ public void Append(string text)
+ {
+ variablesBuilder.Append(text);
+ }
+
+ public override string ToString()
+ {
+ return variablesBuilder.ToString();
+ }
+
+ public void AppendVariable(TextTemplatingVariableLocation variableLocation)
+ {
+ AppendVariableText(variableLocation);
+ UpdateCurrentIndex(variableLocation);
+ }
+
+ public void AppendTextBeforeVariable(TextTemplatingVariableLocation variableLocation)
+ {
+ string textBeforeVariable = unexpandedVariablesString.Substring(currentIndex, variableLocation.Index);
+ variablesBuilder.Append(textBeforeVariable);
+ }
+
+ void AppendVariableText(TextTemplatingVariableLocation variableLocation)
+ {
+ string variableValue = GetVariableValue(variableLocation);
+ variablesBuilder.Append(variableValue);
+ }
+
+ void UpdateCurrentIndex(TextTemplatingVariableLocation variableLocation)
+ {
+ currentIndex = variableLocation.Index + variableLocation.Length;
+ }
+
+ string GetVariableValue(TextTemplatingVariableLocation variableLocation)
+ {
+ return templatingVariables.GetValue(variableLocation.VariableName);
+ }
+
+ public void AppendRemaining()
+ {
+ string textNotAppended = GetTextNotAppended();
+ variablesBuilder.Append(textNotAppended);
+ }
+
+ string GetTextNotAppended()
+ {
+ return unexpandedVariablesString.Substring(currentIndex);
+ }
+ }
+}
@@ -60,6 +60,8 @@
<Compile Include="Src\ITextTemplatingFilePreprocessor.cs" />
<Compile Include="Src\ITextTemplatingHost.cs" />
<Compile Include="Src\ITextTemplatingFileGenerator.cs" />
+ <Compile Include="Src\ITextTemplatingStringParser.cs" />
+ <Compile Include="Src\ITextTemplatingVariables.cs" />
<Compile Include="Src\NamespaceHint.cs" />
<Compile Include="Src\TemplatingHostProcessTemplateError.cs" />
<Compile Include="Src\TextTemplatingAppDomain.cs" />
@@ -68,6 +70,7 @@
<Compile Include="Src\TextTemplatingAssemblyResolver.cs" />
<Compile Include="Src\TextTemplatingCustomTool.cs" />
<Compile Include="Src\TextTemplatingCustomToolContext.cs" />
+ <Compile Include="Src\TextTemplatingDirectoryVariable.cs" />
<Compile Include="Src\TextTemplatingFileGenerator.cs" />
<Compile Include="Src\TextTemplatingFileGeneratorCustomTool.cs" />
<Compile Include="Configuration\AssemblyInfo.cs" />
@@ -76,6 +79,10 @@
<Compile Include="Src\TextTemplatingFileProcessor.cs" />
<Compile Include="Src\TextTemplatingHost.cs" />
<Compile Include="Src\TextTemplatingReflectionProjectContent.cs" />
+ <Compile Include="Src\TextTemplatingStringParser.cs" />
+ <Compile Include="Src\TextTemplatingVariableLocation.cs" />
+ <Compile Include="Src\TextTemplatingVariables.cs" />
+ <Compile Include="Src\TextTemplatingVariablesStringBuilder.cs" />
</ItemGroup>
<ItemGroup>
<EmbeddedResource Include="Resources\TextTemplating.xshd" />
Oops, something went wrong.

0 comments on commit 0961c8f

Please sign in to comment.