In Visual Studio 2013, how do I minify Javascript and CSS in the post-build step? I'd like to have every single css and js file compress into a .min.js, or .min.css in the same folder.
I don't want to check in the minified files, but rather just have them generated post-build.
All solutions I found required using different filenames for the minimized versions, and a lot of extra work to switch between using the normal/minified versions.
Instead, I wanted the compressed JavaScript files to have the original names so I didn't have to change the references in my HTML markup. I could use the normal Javascript files in my development environment, then minimized versions would be automatically deployed when publishing.
I found a simple solution that does just that.
First, install Microsoft Ajax Minifier.
Then, in your Visual Studio project file, just before the closing </Project>
tag add the following :
<Import Project="$(MSBuildExtensionsPath)\Microsoft\Microsoft Ajax Minifier\ajaxmin.tasks" />
<Target Name="AfterBuild" Condition="'$(ConfigurationName)'=='Release'">
<ItemGroup>
<JS Include="**\*.js" Exclude="**\*.min.js;obj\**\*.*" />
<CSS Include="**\*.css" Exclude="**\*.min.css;obj\**\*.*" />
</ItemGroup>
<AjaxMin
JsSourceFiles="@(JS)" JsSourceExtensionPattern="\.js$" JsTargetExtension=".jsMIN"
CssSourceFiles="@(CSS)" CssSourceExtensionPattern="\.css$" CssTargetExtension=".cssMIN" />
</Target>
<PropertyGroup>
<CopyAllFilesToSingleFolderForPackageDependsOn>
CustomCollectFiles;
$(CopyAllFilesToSingleFolderForPackageDependsOn);
</CopyAllFilesToSingleFolderForPackageDependsOn>
</PropertyGroup>
<Target Name="CustomCollectFiles">
<ItemGroup>
<MinJS Include="**\*.jsMIN" />
<FilesForPackagingFromProject Include="%(MinJS.Identity)">
<DestinationRelativePath>%(RecursiveDir)%(Filename).js</DestinationRelativePath>
</FilesForPackagingFromProject>
<MinCSS Include="**\*.cssMIN" />
<FilesForPackagingFromProject Include="%(MinCSS.Identity)">
<DestinationRelativePath>%(RecursiveDir)%(Filename).css</DestinationRelativePath>
</FilesForPackagingFromProject>
</ItemGroup>
</Target>
What does the above code do? When you publish in Visual Studio, this code will find every .js
and .css
file in your source, and create a minified copy using the extension .jsMIN
and .cssMIN
. It will ignore files that are already minified. Then it will copy these minified files to the deployment folder, using the original file names.
Voilà! You just published minified JS/CSS files, while your original files stay intact on your development environment.
Optional:
Want Ajax Minifier to be packaged with your project? From the Ajax Minifier install folder, you can move AjaxMin.dll
and AjaxMinTask.dll
directly into your source directory. I put them in my App_Data
folder. Once they're somewhere in your source, in Visual Studio right-click them, select Include in Project
, and also change their Build Action
property to None
.
Then in the code I included above, change
<Import Project="$(MSBuildExtensionsPath)\Microsoft\Microsoft Ajax Minifier\ajaxmin.tasks" />
to
<UsingTask TaskName="AjaxMin" AssemblyFile="$(MSBuildProjectDirectory)\App_Data\AjaxMinTask.dll" />
Done.
A troubleshooting tip:
My main code above executes AfterBuild
and only when the configuration is Release
. That's so it will only run during a publish. If your configuration is named something else, or you want it to run in other circumstances, modify the code as needed.