Skip to content

Commit

Permalink
style: File scoped namespaces and usings satements
Browse files Browse the repository at this point in the history
  • Loading branch information
alexmg committed Sep 12, 2024
1 parent 242ad1a commit fb05cbc
Show file tree
Hide file tree
Showing 7 changed files with 222 additions and 231 deletions.
71 changes: 35 additions & 36 deletions src/Moniker.Cli/Program.cs
Original file line number Diff line number Diff line change
@@ -1,43 +1,42 @@
using JetBrains.Annotations;
using McMaster.Extensions.CommandLineUtils;

namespace Moniker.Cli
namespace Moniker.Cli;

[Command(Name = "moniker", FullName = "moniker", Description = "Moniker command line interface")]
[VersionOptionFromMember(MemberName = nameof(GetVersion))]
internal class Program
{
[Command(Name = "moniker", FullName = "moniker", Description = "Moniker command line interface")]
[VersionOptionFromMember(MemberName = nameof(GetVersion))]
internal class Program
private readonly IConsole _console;

public Program(IConsole console) => _console = console;

[Option("-s|--style <STYLE>",
"The style of moniker to generate (Moniker or Moby)",
CommandOptionType.SingleValue)]
[UsedImplicitly]
public MonikerStyle MonikerStyle { get; } = MonikerStyle.Moniker;

[Option("-d|--delimiter <DELIMITER>",
"The delimiter to use between name parts such as adjective and noun",
CommandOptionType.SingleValue)]
[UsedImplicitly]
public string Delimiter { get; } = NameGenerator.DefaultDelimiter;

[UsedImplicitly]
public int OnExecute()
{
private readonly IConsole _console;

public Program(IConsole console) => _console = console;

[Option("-s|--style <STYLE>",
"The style of moniker to generate (Moniker or Moby)",
CommandOptionType.SingleValue)]
[UsedImplicitly]
public MonikerStyle MonikerStyle { get; } = MonikerStyle.Moniker;

[Option("-d|--delimiter <DELIMITER>",
"The delimiter to use between name parts such as adjective and noun",
CommandOptionType.SingleValue)]
[UsedImplicitly]
public string Delimiter { get; } = NameGenerator.DefaultDelimiter;

[UsedImplicitly]
public int OnExecute()
{
var moniker = NameGenerator.Generate(MonikerStyle, Delimiter);
_console.WriteLine(moniker);
return 0;
}

private static int Main(string[] args)
=> CommandLineApplication.Execute<Program>(args);

private static string? GetVersion() =>
(string?)typeof(Program).Assembly
.GetType("GitVersionInformation")!
.GetField("FullSemVer")!
.GetValue(null);
var moniker = NameGenerator.Generate(MonikerStyle, Delimiter);
_console.WriteLine(moniker);
return 0;
}

private static int Main(string[] args)
=> CommandLineApplication.Execute<Program>(args);

private static string? GetVersion() =>
(string?)typeof(Program).Assembly
.GetType("GitVersionInformation")!
.GetField("FullSemVer")!
.GetValue(null);
}
25 changes: 12 additions & 13 deletions src/Moniker/MonikerStyle.cs
Original file line number Diff line number Diff line change
@@ -1,18 +1,17 @@
namespace Moniker
namespace Moniker;

/// <summary>
/// Supported styles of random names to generate.
/// </summary>
public enum MonikerStyle
{
/// <summary>
/// Supported styles of random names to generate.
/// Names found in the technosophos/moniker project.
/// </summary>
public enum MonikerStyle
{
/// <summary>
/// Names found in the technosophos/moniker project.
/// </summary>
Moniker,
Moniker,

/// <summary>
/// Names found in the moby/moby project.
/// </summary>
Moby
}
/// <summary>
/// Names found in the moby/moby project.
/// </summary>
Moby
}
205 changes: 102 additions & 103 deletions src/Moniker/NameGenerator.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,128 +2,127 @@
using System.Diagnostics;
using System.Runtime.CompilerServices;

namespace Moniker
namespace Moniker;

/// <summary>
/// Generates fun random names that are readable and memorable.
/// </summary>
public static class NameGenerator
{
/// <summary>
/// Generates fun random names that are readable and memorable.
/// The default delimiter between adjective and noun.
/// </summary>
public const string DefaultDelimiter = "-";

/// <summary>
/// Generate a random name in the specified style.
/// </summary>
public static class NameGenerator
/// <param name="monikerStyle">The style of random name.</param>
/// <param name="delimiter">An optional delimiter to use between adjective and noun.</param>
/// <returns>The generated random name.</returns>
/// <exception cref="ArgumentOutOfRangeException"></exception>
public static string Generate(MonikerStyle monikerStyle, string delimiter = DefaultDelimiter)
{
/// <summary>
/// The default delimiter between adjective and noun.
/// </summary>
public const string DefaultDelimiter = "-";

/// <summary>
/// Generate a random name in the specified style.
/// </summary>
/// <param name="monikerStyle">The style of random name.</param>
/// <param name="delimiter">An optional delimiter to use between adjective and noun.</param>
/// <returns>The generated random name.</returns>
/// <exception cref="ArgumentOutOfRangeException"></exception>
public static string Generate(MonikerStyle monikerStyle, string delimiter = DefaultDelimiter)
{
ValidateDelimiterArgument(delimiter);
Generate(monikerStyle, out var adjective, out var noun);
return Join(adjective, delimiter, noun);
}
ValidateDelimiterArgument(delimiter);
Generate(monikerStyle, out var adjective, out var noun);
return Join(adjective, delimiter, noun);
}

/// <summary>
/// Generate a random name in the specified style.
/// </summary>
/// <param name="monikerStyle">The style of random name.</param>
/// <param name="adjective">The adjective part of the random name.</param>
/// <param name="noun">The noun part of the random name.</param>
/// <exception cref="ArgumentOutOfRangeException"></exception>
public static void Generate(MonikerStyle monikerStyle, out Chars adjective, out Chars noun)
/// <summary>
/// Generate a random name in the specified style.
/// </summary>
/// <param name="monikerStyle">The style of random name.</param>
/// <param name="adjective">The adjective part of the random name.</param>
/// <param name="noun">The noun part of the random name.</param>
/// <exception cref="ArgumentOutOfRangeException"></exception>
public static void Generate(MonikerStyle monikerStyle, out Chars adjective, out Chars noun)
{
switch (monikerStyle)
{
switch (monikerStyle)
{
case MonikerStyle.Moby: GenerateMoby(out adjective, out noun); break;
case MonikerStyle.Moniker: GenerateMoniker(out adjective, out noun); break;
default: throw new ArgumentOutOfRangeException(nameof(monikerStyle));
}
case MonikerStyle.Moby: GenerateMoby(out adjective, out noun); break;
case MonikerStyle.Moniker: GenerateMoniker(out adjective, out noun); break;
default: throw new ArgumentOutOfRangeException(nameof(monikerStyle));
}
}

/// <summary>
/// Generate a random name in the 'moniker' project style.
/// </summary>
/// <param name="delimiter">An optional delimiter to use between adjective and noun.</param>
/// <returns>The generated random name.</returns>
public static string GenerateMoniker(string delimiter = DefaultDelimiter)
{
ValidateDelimiterArgument(delimiter);
GenerateMoniker(out var adjective, out var noun);
return Join(adjective, delimiter, noun);
}
/// <summary>
/// Generate a random name in the 'moniker' project style.
/// </summary>
/// <param name="delimiter">An optional delimiter to use between adjective and noun.</param>
/// <returns>The generated random name.</returns>
public static string GenerateMoniker(string delimiter = DefaultDelimiter)
{
ValidateDelimiterArgument(delimiter);
GenerateMoniker(out var adjective, out var noun);
return Join(adjective, delimiter, noun);
}

/// <summary>
/// Generate a random name in the 'moniker' project style.
/// </summary>
/// <param name="adjective">The adjective part of the random name.</param>
/// <param name="noun">The noun part of the random name.</param>
public static void GenerateMoniker(out Chars adjective, out Chars noun)
=> BuildNamePair(MonikerDescriptors.Strings, out adjective, MonikerAnimals.Strings, out noun);

/// <summary>
/// Generate a random name in the 'moby' project style.
/// </summary>
/// <param name="delimiter">An optional delimiter to use between adjective and noun.</param>
/// <returns>The generated random name.</returns>
public static string GenerateMoby(string delimiter = DefaultDelimiter)
{
ValidateDelimiterArgument(delimiter);
GenerateMoby(out var adjective, out var noun);
return Join(adjective, delimiter, noun);
}
/// <summary>
/// Generate a random name in the 'moniker' project style.
/// </summary>
/// <param name="adjective">The adjective part of the random name.</param>
/// <param name="noun">The noun part of the random name.</param>
public static void GenerateMoniker(out Chars adjective, out Chars noun)
=> BuildNamePair(MonikerDescriptors.Strings, out adjective, MonikerAnimals.Strings, out noun);

/// <summary>
/// Generate a random name in the 'moby' project style.
/// </summary>
/// <returns>The generated random name.</returns>
public static void GenerateMoby(out Chars adjective, out Chars noun)
=> BuildNamePair(MobyAdjectives.Strings, out adjective, MobySurnames.Strings, out noun);
/// <summary>
/// Generate a random name in the 'moby' project style.
/// </summary>
/// <param name="delimiter">An optional delimiter to use between adjective and noun.</param>
/// <returns>The generated random name.</returns>
public static string GenerateMoby(string delimiter = DefaultDelimiter)
{
ValidateDelimiterArgument(delimiter);
GenerateMoby(out var adjective, out var noun);
return Join(adjective, delimiter, noun);
}

private static void ValidateDelimiterArgument(
string delimiter,
[CallerArgumentExpression(nameof(delimiter))] string? paramName = null)
{
if (string.IsNullOrEmpty(delimiter))
throw new ArgumentException("The delimiter must not be null or empty.", paramName);
}
/// <summary>
/// Generate a random name in the 'moby' project style.
/// </summary>
/// <returns>The generated random name.</returns>
public static void GenerateMoby(out Chars adjective, out Chars noun)
=> BuildNamePair(MobyAdjectives.Strings, out adjective, MobySurnames.Strings, out noun);

private static void BuildNamePair(
Utf8Strings adjectives, out Chars adjective,
Utf8Strings nouns, out Chars noun)
{
do
{
adjective = GetRandomEntry(adjectives);
noun = GetRandomEntry(nouns);
}
while (adjective.Equals("boring"u8) && noun.Equals("wozniak"u8)); // Steve Wozniak is not boring
}
private static void ValidateDelimiterArgument(
string delimiter,
[CallerArgumentExpression(nameof(delimiter))] string? paramName = null)
{
if (string.IsNullOrEmpty(delimiter))
throw new ArgumentException("The delimiter must not be null or empty.", paramName);
}

private static Chars GetRandomEntry(Utf8Strings entries)
private static void BuildNamePair(
Utf8Strings adjectives, out Chars adjective,
Utf8Strings nouns, out Chars noun)
{
do
{
var index = Random.Shared.Next(entries.Count);
return entries[index];
adjective = GetRandomEntry(adjectives);
noun = GetRandomEntry(nouns);
}
while (adjective.Equals("boring"u8) && noun.Equals("wozniak"u8)); // Steve Wozniak is not boring
}

private static string Join(Chars adjective, ReadOnlySpan<char> delimiter, Chars noun)
{
var length = adjective.Length + delimiter.Length + noun.Length;
var chars = length <= 64 ? stackalloc char[length] : new char[length];
private static Chars GetRandomEntry(Utf8Strings entries)
{
var index = Random.Shared.Next(entries.Count);
return entries[index];
}

var writeCount = adjective.Write(chars);
Debug.Assert(writeCount == adjective.Length);
private static string Join(Chars adjective, ReadOnlySpan<char> delimiter, Chars noun)
{
var length = adjective.Length + delimiter.Length + noun.Length;
var chars = length <= 64 ? stackalloc char[length] : new char[length];

delimiter.CopyTo(chars[adjective.Length..]);
var writeCount = adjective.Write(chars);
Debug.Assert(writeCount == adjective.Length);

writeCount = noun.Write(chars[(adjective.Length + delimiter.Length)..]);
Debug.Assert(writeCount == noun.Length);
delimiter.CopyTo(chars[adjective.Length..]);

return new(chars);
}
writeCount = noun.Write(chars[(adjective.Length + delimiter.Length)..]);
Debug.Assert(writeCount == noun.Length);

return new(chars);
}
}
7 changes: 2 additions & 5 deletions src/Moniker/Utf8Strings.cs
Original file line number Diff line number Diff line change
@@ -1,8 +1,5 @@
#nullable enable

using System;
using System;
using System.Diagnostics;
using System.Text;

namespace Moniker;

Expand Down Expand Up @@ -41,7 +38,7 @@ public ref struct Enumerator(Utf8Strings strings)
/// Behaviour is undefined if <see cref="MoveNext"/> has never been called or returned
/// <see langword="false"/>.
/// </remarks>
public Chars Current => _strings[_index];
public readonly Chars Current => _strings[_index];

public bool MoveNext()
{
Expand Down
4 changes: 2 additions & 2 deletions test/Moniker.Tests/CharsTests.cs
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
using System.Text;
using System;
using System;
using System.Linq;
using System.Text;
using FluentAssertions;
using Xunit;

Expand Down
Loading

0 comments on commit fb05cbc

Please sign in to comment.