using System;
using System.Collections;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Reflection;
using System.Threading;
namespace CC_Functions.Commandline
{
///
/// A class to provide basic parsing for program arguments
///
public class ArgsParse : IEnumerable
{
private readonly string[] _args;
///
/// Create a new instance based on the specified args
///
/// The inputted args. Should be a parameter of the main method
public ArgsParse(string[] args) => _args = args ?? throw new NullReferenceException();
///
/// Shadowed from the base args
///
/// The index in the base args
public string this[int i]
{
get => _args[i];
set => _args[i] = value;
}
///
/// Shadowed from the base args
///
/// An enumerator for the base args
IEnumerator IEnumerable.GetEnumerator() => ((IEnumerable)_args).GetEnumerator();
///
/// Shadowed from the base args
///
///
public IEnumerator GetEnumerator() => _args.GetEnumerator();
///
/// Gets the string specified for this key or null
///
/// The name of the parameter
public string? this[string i]
{
get
{
string? selected = null;
foreach (string s in _args)
if (s.TrimStart('-', '/').ToLower().StartsWith($"{i.ToLower()}:"))
selected = string.Join("", s.TrimStart('-', '/').Skip(i.Length + 1));
return selected;
}
}
///
/// Gets the string specified for this key or null
///
/// The name of the parameter
/// The value or null
public string? GetString(string i) => this[i];
///
/// Gets a boolean value with the specified name. Either specified as --i or --i:true
///
/// The name of the parameter
/// The value
public bool GetBool(string i) => _args.Any(s => s.ToLower().TrimStart('-', '/') == i.ToLower()) || bool.TryParse(this[i], out bool res) && res;
///
/// Gets an arg using a transformer specified by you. The value passed will be the same as this[i]
///
/// The name of the parameter
/// A null-safe function to convert a string to the expected type
/// The type to convert to
/// The converted value
public T Get(string i, Func func) => func(this[i]);
///
/// Uses reflection to call the Parse method on types providing it. Use Get() with a func param for other types
/// This will return null if the type is not found
///
/// The name of the parameter
/// The type to convert to
/// The converted value
public T Get(string i)
{
MethodInfo[] parse = typeof(T).GetMethods().Where(s => s.Name.ToLower() == "parse"
&& s.GetParameters().Length == 1
&& s.GetParameters()[0].ParameterType == typeof(string)
&& s.ReturnType == typeof(T)
&& !s.IsAbstract && !s.IsPrivate && s.IsStatic).ToArray();
if (parse.Length == 0)
throw new InvalidOperationException("Could not find a valid parse method");
string? v = this[i];
if (v == null)
return default;
return (T) parse[0].Invoke(null, new object[] {v});
}
}
}