logo lower layer
logo upper layer
logo text

Genfic Blog

ᚑᚌᚋᚐ

From NSwag To Built-In OpenAPI


With the .NET 9.0 release, and specifically ASP.NET Core 9.0, we got a built-in OpenAPI generator. No need to depend on Swashbuckle or NSwag anymore.

OpenAPI generation has been an issue for Ogma3 for quite some time now, and there was no silver bullet. Swashbuckle would have dodgy support for forms, NSwag would outright not support HEAD method, et cetera.

Thankfully, with the new, first-party support, all those issues should be a song of the past, leaving just one: migrating off NSwag. As it turns out, it was not that hard, and you can read the details below.

Read the full post

Fluent Validator for File Size With Client-side Validation


Fluent Validation is a great package for handling, well, validation. It ties in well with ASP.NET as well, providing client-side hits in the form of data-val attributes on your form inputs that can be used by whatever means of client-side validation you use, the jQuery thingamajig by default.

There’s but one problem, one thing that good ol’ attribute-based validators have over this package: the ease of creating custom client-side validators. Server-side? No issue at all, the docs guide you cleanly through the process. Client-side? That’s where issues begin.

In this post, however, we will make a file size validator that also works client-side. So sit back and enjoy.

Read the full post

Generic MediatR Handlers


Odd as it might be, I couldn’t find much information about it myself, so I thought I’ll share my findings instead. Perhaps it’ll be of help to those seeking answers in the future.

Creating a generic controller? Nothing could be easier, simply create a method with a signature like

1
private async Task<ActionResult> BlockContent<T>(PostData data) where T : BaseModel, IBlockableContent

and use it like you would any other generic method:

1
2
3
4
5
6
7
8
[HttpPost("story")]
public async Task<ActionResult> BlockStory(PostData data) => await BlockContent<Story>(data);

[HttpPost("chapter")]
public async Task<ActionResult> BlockChapter(PostData data) => await BlockContent<Chapter>(data);

[HttpPost("blogpost")]
public async Task<ActionResult> BlockBlogpost(PostData data) => await BlockContent<Blogpost>(data);

But how about using it with MediatR and the CQRS pattern..?

Read the full post

Gulp Shenanigans


Ogma3, the software on which Genfic is ran, uses Gulp to process all the SASS styles, Javascript scripts, all the Typescript, everything. While I did experiment with various bundlers — and I mean various, everything from Webpack through Parcel to Snowpack — it was always Gulp that fit the workflow the most.

It’s not perfect, however, does have its issues, and the documentation is fairly outdated at times. Because of that, many people see that it takes 5 seconds to process their SCSS styles and bounces right out. In this post, I hope to solve at least two issues.

Read the full post

Progressive Enhancement


Yeah, using Vue or custom elements in the frontend is cool they can greatly improve compartmentalization of code through the use of components, but what happens when the JS code just… doesn’t load. Be it the user blocking it, the browser bugging out, or the CDN dying, those things happen.

If a form relies on the fields being components, what happens? Does the form just not render, does it break in any other way? Yes, it does, and submission becomes impossible.

But it doesn’t have to.

Read the full post