Skip to content

Instantly share code, notes, and snippets.

View nickalbrecht's full-sized avatar

Nick Albrecht nickalbrecht

View GitHub Profile
@nickalbrecht
nickalbrecht / CombineFormattableStrings.cs
Created November 24, 2023 19:18
An extension method for use on a FormattableString to allow combining them, but keeping the output as a FormattableString, not string. I added this to allow passing it to EFCore, and let it handle parameterizing the command. Otherwise you have to do this yourself and call the RawSql variant of methods and pass in the parameters yourself. I'm not…
[GeneratedRegex(@"\{(\d+)\}")]
private static partial Regex FormattableStringArgumentRegex();
/// <summary>
/// Extension method for combining two <see cref="FormattableString"/>, and returning a new <see cref="FormattableString"/> with the combined arguments and format
/// </summary>
/// <remarks>Originally added to facilitate dynamically building up querystrings that EFCore would take and excute</remarks>
public static FormattableString Combine(this FormattableString baseFormattableString, FormattableString addingFormattableString)
{
var regex = FormattableStringArgumentRegex();
@nickalbrecht
nickalbrecht / EllipsizeString.cs
Created October 7, 2023 00:45
A method for truncating a long string using ellipse. You can prefer to truncate the end of the string, or cut a chunk out of the middle and keep the start and end of the string. It will also shift the cutoff point slightly to the closest space/punctuation for aesthetics
public enum EllipseStyle { End, Middle };
public static string EllipsizeString(this string text, int? maxLength, EllipseStyle ellipseStyle)
{
if(string.IsNullOrEmpty(text))
return null;
const string ellipsis = "...";
var preferredCharacters = new[] { ' ', ',', '.', ';', ':', '?', '!' };
string truncatedString = null;
@nickalbrecht
nickalbrecht / PrioritizedGroupsSelectListItemComparer.cs
Last active November 1, 2023 23:19
Custom Comparer<SelectListItem> implementation for use in ASPNETCore to handle prioritizing certain SelectListGroup to the top of the SELECT element before being passed to a View. NULL groups are put last, but the SelectListItem, with a NULL value is made first as I assume it's the "Pick One" place holder
public class PrioritizedGroupsSelectListItemComparer : Comparer<SelectListItem>
{
private readonly List<string> prioritizedGroupNames;
public PrioritizedGroupsSelectListItemComparer(params string[] prioritizedGroupNames)
{
this.prioritizedGroupNames = prioritizedGroupNames.ToList();
}
public PrioritizedGroupsSelectListItemComparer(IEnumerable<string> prioritizedGroupNames)
{
@nickalbrecht
nickalbrecht / SemVerAndDateIncrementing.yaml
Last active December 14, 2022 20:35
Versioning build in YAML using a combination of SemVer, and days since Jan 1, 2000
# I use the days since Jan 1, 2000 as part of my build number to mimic a behavior found with .NET Full Framework
# that would autoincrement the 4th piece of the version information based on this math. I started using it as a
# way to reverse enginer the build date at runtime. After switching to .NET Core,I lost this, and start using this
# logic to get that behavior back
# Example build numbers resulting from this...
# 7.0.featurebranch.1+7550
# 7.0.1+7550
# Inspiration for the versioning differently between branches
# https://medium.com/@ychetankumarsarma/build-versioning-in-azure-devops-pipelines-94b5a79f80a0
@nickalbrecht
nickalbrecht / CollectionItemTagHelper.cs
Last active July 3, 2020 00:31
Variation on my CollectionEditingHtmlExtensions gist to use TagHelper instead.
[HtmlTargetElement("CollectionItem")]
public class CollectionItemTagHelper : TagHelper
{
private readonly IHtmlHelper htmlHelper;
[ViewContext]
[HtmlAttributeNotBound]
public ViewContext ViewContext { get; set; }
public CollectionItemTagHelper(IHtmlHelper htmlHelper)
@nickalbrecht
nickalbrecht / CollectionEditingHtmlExtensions.cs
Last active July 3, 2020 00:31
Updated implementation of `BeginCollectionItem` to support nesting, not ignore the original `HtmlFieldPrefix`, and also provide overloads to let me decide the ID to use. Refactored to be a bit cleaner
public static class CollectionEditingHtmlExtensions
{
/// <summary>
/// Begins a collection item by inserting a hidden field for the index value
/// </summary>
/// <param name="collectionName">The name of the collection property that owns this item</param>
/// <param name="indexValue">The value of the index for the current item</param>
public static IDisposable BeginCollectionItem<TModel>(this IHtmlHelper<TModel> html, string collectionName, Guid indexValue)
{
return BeginCollectionItem(html, collectionName, indexValue == Guid.Empty ? null : indexValue.ToString(), html.ViewContext.Writer);
@nickalbrecht
nickalbrecht / A demo overriding Exceptional error list
Last active August 16, 2017 01:17
StackExchange.Exceptional - Custom Error List
Sample of some files I whipped up to try and demonstrate how to provide a
custom RazorPage to list errors recorded in StackExchange's Exceptional
@nickalbrecht
nickalbrecht / AspNetCore LinqPad Playground.cs
Last active April 26, 2024 03:30
Minimum code needed to run/experiment with functionality from an AspNetCore project
/*
References (F4 - Additional References - Add...)
~~~~~~~~~~~~~~~~~~~
<Your AspNetCore site assembly>
* Check Reference ASP.NET Core
Using (F4 - Additional Namespace Imports)
~~~~~~~~~~~~~~~~~~~
Microsoft.AspNetCore.Hosting
Microsoft.Extensions.Configuration
@nickalbrecht
nickalbrecht / CustomValidationAttributeAdapterProvider.cs
Last active December 7, 2023 21:45
Attribute to mark properties backed by primitive types or structs (int, DateTime, Guid, etc) as requiring a value other than their default value. `RequireNonDefaultAttribute` alone is enough for Server side validation. If you want to use this for client side as well, you'll need the other files too.
using System.ComponentModel.DataAnnotations;
using Microsoft.AspNetCore.Mvc.DataAnnotations;
using Microsoft.Extensions.Localization;
public class CustomValidationAttributeAdapterProvider : IValidationAttributeAdapterProvider
{
readonly IValidationAttributeAdapterProvider baseProvider = new ValidationAttributeAdapterProvider();
public IAttributeAdapter GetAttributeAdapter(ValidationAttribute attribute, IStringLocalizer stringLocalizer)
{
@nickalbrecht
nickalbrecht / EndpointBehavior.cs
Last active January 21, 2018 21:46
Series of functions and classes for using SSRS to run reports from inside an ASP.NET Core application
using System.ServiceModel.Channels;
using System.ServiceModel.Description;
using System.ServiceModel.Dispatcher;
internal class ReportingServicesEndpointBehavior : IEndpointBehavior
{
public void AddBindingParameters(ServiceEndpoint endpoint, BindingParameterCollection bindingParameters) { }
public void ApplyClientBehavior(ServiceEndpoint endpoint, ClientRuntime clientRuntime)
{