Hyston blog
About • Archive • RSS

D3Signal: npgsql and dotnet

May 31, 2022

Intro

Recently I created a small application, that contain most of technology stack, that I’m using at work and/or learned recently: dotnet, react, mobx, d3js & signalR. So I decided to make small series of posts, in which I add some tips for each of these frameworks. I’ll update this list as soon as posts would be available.

Docker

Postgress is one of the famous db in the world of software development. Although my knowledge does not allow me do dig deep in differences between databases, I prefer to use postgress for my dotnet projects, because it require less resources than MsSQL and allow db migrations unlike SQLite. Simpliest way to install it would be, of course, official installer on local machine, but I prefer to use docker. This way it’s easier to support multiple versions, add plugins and throw away data, that is not needed. To run postgreSQL from docker:

docker run 
-e POSTGRES_USER=user 
-e POSTGRES_PASSWORD=pass 
-e POSTGRES_DB=d3signal_db 
-p 5432:5432 
-v db:/var/lib/postgresql/data 
-d 
postgres:14

-e flags used to set environment, especially user name, pass and db name, that would be used. -p is mapping container port to local port. In this case it’s the same, but if I run local Postgres in addition to one in docker, ports can be remapped to avoid confusion. The most interesting param here is -v, which creates docker volume db (if it’s not existed) and mounts it into container. When container would be stopped, this volume persisted and data can be saved this way between reboots.

Dotnet

There are many ways to connect dotnet to sql (as well as there are many types of dotnet application). I usually use EntityFramework and include same steps:

public interface ICirclesContext
{
    DbSet<Circle> Circles { get; }
    Task Save();
}

Name here is better to be pointed to application name, like MyAppContext. In this case the whole application is about circles 🙂 Implementation:

public class CirclesContext: DbContext, ICirclesContext
{
    public CirclesContext(DbContextOptions options) : base(options) { }

    public DbSet<Circle> Circles => Set<Circle>();

    public async Task Save() => await SaveChangesAsync();
}
var connectionString = builder.Configuration.GetConnectionString("db");
builder.Services.AddDbContext<CirclesContext>(ops => 
    ops.UseNpgsql(connectionString));
builder.Services.AddScoped<ICirclesContext>(p => p.GetService<CirclesContext>()!);

Of course, config file should contain connection string (although, in production it usually goes from environment variable where it appear by CI/CD pipeline):

{
  "ConnectionStrings": {
    "db": "Host=localhost;Username=user;Password=pass;Database=d3signal_db"
  }
}
app.Services
    .CreateScope()
    .ServiceProvider
    .GetService<CirclesContext>()?
    .Database
    .Migrate();

More about migrations and how to create them can be found in microsoft documentation


Without any other details about .net application type, these are simplest steps to add postgreSQL support to our application.


How to make gif?

February 15, 2022

I need to add new feature to my site - posts-links with simple commentary. I was going to write how to use ffmpeg to create amazing gifs, but guys from GIPHY already described everything that I know (and more!) here: How to make GIFs with FFMPEG
With combination of youtube-dl & ffmpeg the only limits are imagination and free time. I, as example, finaly created by myself this gif with medic from TF2, that I could not find anywhere.
medic


Dynamic

February 14, 2022

I’m writing on C# for 5 years now and keep finding things, that are not widely used, but they are exist already for a long time. Just recently I found the need of dynamic keyword. Usually new variables are defined with var or with value type directly:

Foo foo = new Foo();
var foo = new Foo();

These are actually two identical lines, compiler would define actual type on second lane from right-hand operator.

But what if type is unknown in compile type? I have met a problem, where actual type is created by external parameter - and there is no common interface that can be used to aggregate possible types. In these uncommon scenarios dynamic can be very handy.

Suppose, we have a three types:

public record TypeA(string A);
public record TypeB(string B);
public record TypeC(string C);

Then we can declare a function, which return any of this types by random:

dynamic GetRandomType(Random random) => random.Next(3) switch
{
    0 => new TypeA("a"),
    1 => new TypeB("b"),
    2 => new TypeC("c"),
    _ => throw new Exception("out of random range")
};

By making dynamic return type, we tell a compiler, that he should not care, which type it actually is. Problem here in that compiler agreed and skip any further compile-time checking:

var random = new Random();
var result = GetRandomType(random);
result.DoSomething(); // We would get runtime error here

A good thing is, that actual type is available in run time and overloading works even with dynamic type:

public class Foo
{
    public static void Do(TypeA obj) => Console.WriteLine($"Do a: {obj.A}");
    public static void Do(TypeB obj) => Console.WriteLine($"Do b: {obj.B}");
    public static void Do(TypeC obj) => Console.WriteLine($"Do c: {obj.C}");
}
Foo.Do(result); // correct function would be called, based on result type

This can be very handful for places, where actual behaviour is unknown beforehand. As example, I wrote a event parser, where each event contain a enum with event type and object payload. And for each actual event the payload would be a completely different DTO, as well as event handlers would have completely different behaviour.


Svelte

January 3, 2022

Most of current frontend frameworks are build upon making virtual DOM. All UI changes are applied to this structure, then it is getting compared to real DOM and only then framework adjust actual page. Just before Christmas, when there were not a lot of stuff to do, one collegue mentioned to me Svelte framework, that use different approach and I decided to give it a try.
TLDR: using virtual DOM is slow; All changes can be made manually, and code can be generated in compile-time. Svelte moves complexity from client browser realtime into dev machine compile time.
All code is written in html-like files with .svelte extension. On building (svelte-kit build) all code in <script> get compiled into javascript, <style> goes into css. I have not made any real comparisons with big projects, but for small hello worlds it loads really fast and generates a lot of "compiled" javascript code that became unreadable really fast.
For me, actually, the biggest benefit was a flat learning curve. This is component-based framework, that is really start with. I'm using react lately and I find that there are too much conventional boilerplate code. For example, here is hello-click-me-world example in svelte:

<script>
	let count = 0;

	function handleClick() {
		count += 1;
	}
</script>

<button on:click={handleClick}>
	Clicked {count} {count === 1 ? 'time' : 'times'}
</button>

Html can be enchanced with conditional statements and loops:

{#each values as value}
	<li>{value}</li>
{/each}

Input elements can be binded by attributes bind:value. Even regular variables can be "reactified" by adding $: before declaration.

<script>
	let count = 0;
	$: double = count * 2;
</script>

<button on:click={e => count += 1}>Click</button>
<p>{count}</p>
<p>{double}</p>

In this example after clicking button second label would not be updated without $: statement. As I understood, first label is getting updated anyway because it is already used in handler.
DOM gets updated on each assignment operator, not by anything else. So, if you need to update array, then use spread syntax: values = [...values, { name: newName }];

I think it is a nice framework to play around with, very easy to start, however, it's conventions were broken by moving to each major version and it's unclear (as with every new js-framework) how popular would it be and how many support will it get. May be it can be used for small dev-related project, where react or angular would be overkill.
And for my purposes I'll continue to explore react in my free time, since this seems to be the most popular frontend. Although typescript is very painfull and unfriendly after years of writing in C#.1


WWDC 2021 - Keynote

June 7, 2021

I was an apple fan for the last 5+ years and I’m always eager to watch their presentations. They always have marketing-driven demos, but in this year they outbullshitened themselves. Over the many California style stages and inspiring fake smiles it’s getting harder than ever to see actual features, that will help me personally in everyday life:

That’s actually all news that I really care about. iPad mulitasking and Playgrounds enchantments looks promising, but I am not active iPad user. Not every wwdc should be amazing (like last year was with widgets, app library and  silicone macs), today is a quiet one. With is good, I just wish that presentation were more actually inspiring and less from pinkish kindergarten world.


← Next Previous →