Skip to content
This repository was archived by the owner on Jun 25, 2020. It is now read-only.

New command : create new post #284

Merged
merged 7 commits into from
Dec 13, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
9 changes: 8 additions & 1 deletion src/Pretzel.Logic/Commands/CommandParameters.cs
Original file line number Diff line number Diff line change
Expand Up @@ -35,7 +35,8 @@ public CommandParameters([ImportMany] IEnumerable<IHaveCommandLineArgs> commandL
{ "nobrowser", "Do not launch a browser", v => LaunchBrowser = false },
{ "withproject", "Includes a layout VS Solution, to give intellisense when editing razor layout files", v => WithProject = (v!=null) },
{ "wiki", "Creates a wiki instead of a blog (razor template only)", v => Wiki = (v!=null) },
{ "cleantarget", "Delete the target directory (_site by default)", v => CleanTarget = true }
{ "cleantarget", "Delete the target directory (_site by default)", v => CleanTarget = true },
{ "n|newposttitle=", "The title of the new post (\"New post\" by default)", v => NewPostTitle = v }
};

// Allow extensions to register command line args
Expand Down Expand Up @@ -66,6 +67,8 @@ public CommandParameters([ImportMany] IEnumerable<IHaveCommandLineArgs> commandL

public string DestinationPath { get; private set; }

public string NewPostTitle { get; internal set; }

private decimal port;

public decimal Port
Expand All @@ -91,6 +94,10 @@ public void Parse(IEnumerable<string> arguments)
{
DestinationPath = fileSystem.Path.Combine(Path, DestinationPath);
}
if (string.IsNullOrEmpty(NewPostTitle))
{
NewPostTitle = "New post";
}
}

public void DetectFromDirectory(IDictionary<string, ISiteEngine> engines, SiteContext context)
Expand Down
1 change: 1 addition & 0 deletions src/Pretzel.Logic/Pretzel.Logic.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -168,6 +168,7 @@
<DesignTime>True</DesignTime>
<DependentUpon>Resources.resx</DependentUpon>
</Compile>
<Compile Include="Recipe\Ingredient.cs" />
<Compile Include="SanityCheck.cs" />
<Compile Include="Templating\Context\Category.cs" />
<Compile Include="Templating\Context\LinkHelper.cs" />
Expand Down
50 changes: 50 additions & 0 deletions src/Pretzel.Logic/Recipe/Ingredient.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
using System;
using System.IO.Abstractions;
using Pretzel.Logic.Extensibility.Extensions;
using Pretzel.Logic.Extensions;

namespace Pretzel.Logic.Recipe
{
public class Ingredient
{
private readonly string directory;

private readonly IFileSystem fileSystem;

private readonly string title;

private readonly bool withDrafts;

public Ingredient(IFileSystem fileSystem, string title, string directory, bool withDrafts)
{
this.fileSystem = fileSystem;
this.title = title;
this.directory = directory;
this.withDrafts = withDrafts;
}

public void Create()
{
var postPath = fileSystem.Path.Combine(directory, !this.withDrafts ? @"_posts" : @"_drafts");

var postName = string.Format("{0}-{1}.md", DateTime.Today.ToString("yyyy-MM-dd"), SlugifyFilter.Slugify(title));
var pageContents = string.Format("---\r\n layout: post \r\n title: {0}\r\n comments: true\r\n---\r\n", title);

if (!fileSystem.Directory.Exists(postPath))
{
Tracing.Info(string.Format("{0} folder not found", postPath));
return;
}

if (fileSystem.File.Exists(fileSystem.Path.Combine(postPath, postName)))
{
Tracing.Info(string.Format("The \"{0}\" file already exists", postName));
return;
}

fileSystem.File.WriteAllText(fileSystem.Path.Combine(postPath, postName), pageContents);

Tracing.Info(string.Format("Created the \"{0}\" post ({1})", title, postName));
}
}
}
41 changes: 41 additions & 0 deletions src/Pretzel.Tests/Commands/CommandParameterTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ public class CommandParameterTests
private const string ExpectedPort = "8000";
private const decimal ExpectedPortDecimal = 8000;
private const string ExpectedDestinationPath = @"D:\Code\Generated";
private const string ExpectedNewPostTitle = @"Post title";

private readonly IFileSystem FileSystem = new MockFileSystem();

Expand Down Expand Up @@ -236,6 +237,38 @@ public void LaunchBrowser_WhenNotSpecifyingCleanTarget_IsFalse()
Assert.False(subject.CleanTarget);
}

[Fact]
public void Parse_WhenSpecifyingNewPostTitleUsingShortParameter_MapsToPath()
{
var args = new List<string> { "--n", ExpectedNewPostTitle };
subject.Parse(args);
Assert.Equal(ExpectedNewPostTitle, subject.NewPostTitle);
}

[Fact]
public void Parse_WhenSpecifyingNewPostTitleUsingFullParameter_MapsToPath()
{
var args = new List<string> { "--newposttitle", ExpectedNewPostTitle };
subject.Parse(args);
Assert.Equal(ExpectedNewPostTitle, subject.NewPostTitle);
}

[Fact]
public void Parse_WhenSpecifyingNewPostTitleUsingShortParameterSingleDash_MapsToPath()
{
var args = new List<string> { "-n", ExpectedNewPostTitle };
subject.Parse(args);
Assert.Equal(ExpectedNewPostTitle, subject.NewPostTitle);
}

[Fact]
public void Parse_WhenSpecifyingNewPostTitleUsingFullParameterSingleDash_MapsToPath()
{
var args = new List<string> { "-newposttitle", ExpectedNewPostTitle };
subject.Parse(args);
Assert.Equal(ExpectedNewPostTitle, subject.NewPostTitle);
}

[Fact]
public void CommandParameters_WhenSpecifyingAllParameters_ResultIsCorrect()
{
Expand Down Expand Up @@ -410,5 +443,13 @@ public void Parse_WhenNoParametersSet_MapsDestinationPathTo_siteInCurrentDirecto
subject.Parse(args);
Assert.Equal(FileSystem.Path.Combine(subject.Path, "_site"), subject.DestinationPath);
}

[Fact]
public void Parse_WhenNoParametersSet_MapsNewPostTileToNewPost()
{
var args = new List<string>();
subject.Parse(args);
Assert.Equal("New post", subject.NewPostTitle);
}
}
}
1 change: 1 addition & 0 deletions src/Pretzel.Tests/Pretzel.Tests.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -106,6 +106,7 @@
<Compile Include="MockAssembly.cs" />
<Compile Include="PretzelContext.cs" />
<Compile Include="Properties\AssemblyInfo.cs" />
<Compile Include="Recipe\IngredientTests.cs" />
<Compile Include="Recipe\RecipeTests.cs" />
<Compile Include="Templating\Context\LinkHelperTest.cs" />
<Compile Include="Templating\Context\SiteContextGeneratorTests.cs" />
Expand Down
97 changes: 97 additions & 0 deletions src/Pretzel.Tests/Recipe/IngredientTests.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,97 @@
using NSubstitute;
using Pretzel.Logic.Extensibility;
using Pretzel.Logic.Extensibility.Extensions;
using Pretzel.Logic.Extensions;
using System;
using System.Collections.Generic;
using System.Globalization;
using System.IO;
using System.IO.Abstractions;
using System.IO.Abstractions.TestingHelpers;
using System.Linq;
using System.Text;
using System.Threading;
using Xunit;
using Xunit.Extensions;

namespace Pretzel.Tests.Recipe
{
public class IngredientTests
{
private MockFileSystem fileSystem = new MockFileSystem(new Dictionary<string, MockFileData>());
private const string BaseSite = @"c:\site\";
private const string PostsFolder = @"_posts";
private const string DraftsFolder = @"_drafts";

private readonly StringBuilder sb = new StringBuilder();
private readonly TextWriter writer;

public IngredientTests()
{
writer = new StringWriter(sb);
Tracing.Logger.SetWriter(writer);
Tracing.Logger.AddCategory(Tracing.Category.Info);
Tracing.Logger.AddCategory(Tracing.Category.Error);
Tracing.Logger.AddCategory(Tracing.Category.Debug);
}

[Fact]
public void Post_Is_Created()
{
fileSystem.Directory.CreateDirectory(BaseSite + PostsFolder);
var postTitle = "Post title";
var postName = string.Format("{0}-{1}.md", DateTime.Today.ToString("yyyy-MM-dd"), SlugifyFilter.Slugify(postTitle));

var ingredient = new Logic.Recipe.Ingredient(fileSystem, postTitle, BaseSite, false);
ingredient.Create();

Assert.True(fileSystem.File.Exists(fileSystem.Path.Combine(BaseSite + PostsFolder, postName)));
}

[Fact]
public void Post_Has_Correct_Content()
{
fileSystem.Directory.CreateDirectory(BaseSite + PostsFolder);
var postTitle = "Post title";
var expectedContent = string.Format("---\r\n layout: post \r\n title: {0}\r\n comments: true\r\n---\r\n", postTitle);
var postName = string.Format("{0}-{1}.md", DateTime.Today.ToString("yyyy-MM-dd"), SlugifyFilter.Slugify(postTitle));

var ingredient = new Logic.Recipe.Ingredient(fileSystem, "Post title", BaseSite, false);
ingredient.Create();

Assert.Equal(expectedContent, fileSystem.File.ReadAllText(fileSystem.Path.Combine(BaseSite + PostsFolder, postName)));
}

[Fact]
public void Post_Already_Exists()
{
fileSystem.Directory.CreateDirectory(BaseSite + PostsFolder);
var postTitle = "Post title";
var postName = string.Format("{0}-{1}.md", DateTime.Today.ToString("yyyy-MM-dd"), SlugifyFilter.Slugify(postTitle));

var ingredient = new Logic.Recipe.Ingredient(fileSystem, postTitle, BaseSite, false);
ingredient.Create();
ingredient.Create();

Assert.Contains(string.Format("The \"{0}\" file already exists", postName), writer.ToString());
}

[Fact]
public void Post_Folder_Not_Found()
{
var ingredient = new Logic.Recipe.Ingredient(fileSystem, string.Empty, BaseSite, false);
ingredient.Create();

Assert.Contains(string.Format(@"{0} folder not found", BaseSite + PostsFolder), writer.ToString());
}

[Fact]
public void Draft_Folder_Not_Found()
{
var ingredient = new Logic.Recipe.Ingredient(fileSystem, string.Empty, BaseSite, true);
ingredient.Create();

Assert.Contains(string.Format(@"{0} folder not found", BaseSite + DraftsFolder), writer.ToString());
}
}
}
41 changes: 41 additions & 0 deletions src/Pretzel/Commands/IngredientCommand.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
using Pretzel.Logic.Commands;
using Pretzel.Logic.Extensions;
using Pretzel.Logic.Recipe;
using System.Collections.Generic;
using System.ComponentModel.Composition;
using System.IO;
using System.IO.Abstractions;

namespace Pretzel.Commands
{
[PartCreationPolicy(CreationPolicy.Shared)]
[CommandInfo(CommandName = "ingredient")]
public sealed class IngredientCommand : ICommand
{
#pragma warning disable 649

[Import]
private IFileSystem fileSystem;

[Import]
private CommandParameters parameters;

#pragma warning restore 649

public void Execute(IEnumerable<string> arguments)
{
Tracing.Info("ingredient - create a new post");

parameters.Parse(arguments);

var ingredient = new Ingredient(fileSystem, parameters.NewPostTitle, parameters.Path, parameters.IncludeDrafts);
ingredient.Create();
}

public void WriteHelp(TextWriter writer)
{
writer.Write(" Create a new post\r\n");
parameters.WriteOptions(writer, "newposttitle", "drafts", "-s");
}
}
}
1 change: 1 addition & 0 deletions src/Pretzel/Pretzel.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,7 @@
<Compile Include="Commands\CommandInfoAttribute.cs" />
<Compile Include="Commands\HungryCommand.cs" />
<Compile Include="Commands\ImportCommand.cs" />
<Compile Include="Commands\IngredientCommand.cs" />
<Compile Include="Commands\RecipeCommand.cs" />
<Compile Include="Commands\ICommand.cs" />
<Compile Include="Commands\ICommandInfo.cs" />
Expand Down