Live data from Hacker News

C# 9 top-level programs and target-typed expressions

developers.redhat.com

91–100 of 188 posts

Re: C# 9 top-level programs and target-typed expressions

#91
I mean, top-level programs are nice, I guess? IMO it's more of a means of attracting non-.NET developers into the fold. I work in a .NET shop and we probably won't use this in our production code.

The benefit of target-typed expressions IMO is that it changes property syntax from:

public List Foos = new List();

to simply:

public List Foos = new();

It may seem subtle, but if you write C# you see this pattern constantly.

Honestly, these are the features in C#9 I'm least excited about. I'm much more excited about record types, init-only setters, not to mention the improved pattern-matching and type inference (no more casting nulls inside of ternary operators!).

Immutability in C# has classically been pretty cumbersome. I work on a payroll platform where we've managed to work around a lot of that, but we're excited to introduce record types and init-only setters in particular to help with some of the maintenance pain-points surrounding the elimination of side-effects from things like pay calculations.

Re: C# 9 top-level programs and target-typed expressions

#92

Earlier quoted context omitted.

You may want to keep an eye on CoreWCF: https://github.com/CoreWCF/CoreWCF Though as a heavy WCF user in the past, I'd suggest your best bet is simply to throw out all your binding configs, and build your own REST API or similar backend (gRPC support in .NET 5+ is something often also recommended if you want something more RPC-like and need/want a more binary-serializer like approach, though in 2021 I'd just use JSON…

Could you expand a little on that? How exactly does an REST API backed desktop/forms application look like in 2021, and how is the decoupling accomplished?

A lot of the decoupling is naturally accomplished by just not being backward compatible with previous WCF bindings and throwing out the whole mess.

The easiest place to start with is your data contracts. You may not have many depending on which side of the RPC/not-RPC boundary you were on, but it may be as simple as creating plain classes that implement those data contracts and then double checking that the Newtonsoft.Json (classic) or System.Text.Json (newer, sleeker) JSON serialization looks nice, deserializes just fine. Generally this work is pretty straightforward and sometimes you can just eliminate the data contract interfaces when you are done (you won't likely need them anywhere else and most of their WCF-specific annotations may just be clutter at that point) and replace them with references to the "POCO" data classes.

Some of your service contracts you might also want to explore moving more of the arguments from lists of arguments into simple data classes that serialize nicely to JSON.

Then at a high level it's a matter of writing client side class implementations of your service contracts and server-side "proxies" that then call your existing server-side physical implementation of your service contract.

At a high level from the client side:

- Open a connection to the recipient

- Send the JSON serialized data to an endpoint

- Wait for the response

- Deserialize the response and return it

That's basically all that the "bindings" are doing for you in a magic nutshell. You'll just be writing it directly "by hand". In the case of a "REST-like" it would be using something like System.Net.Http.HttpClient on the client side and the HTTP method and your URLs would likely reflect your "operation contracts" (the names of the individual methods on your service contract): `Task IMyServiceContract.GetItemDetails(int id)` to `http GET /api/item/details/{id}` for example type things. In general it's a lot of straightforward simple boiler plate to fill out for every interface method ("operation contract").

At a high level for the server side:

- Receive a connection

- Deserialize the data

- Call the appropriate service contract method

- Serialize and return the results

On the server side, for the simple "REST-like approach" you might want to build a simple ASP.NET (Core) host wrapper. These days you don't necessarily need the full weight of something like ASP.NET MVC and go do all the above steps with just what ASP.NET these days calls "Endpoint Routing".

Obviously complications come from figuring out your network topology shifts. Maybe you can't shift your "server" as easily to a real ASP.NET application hosted on a "real" HTTP server somewhere like IIS or Apache or whatever. In some of these cases you can find hints in your existing bindings. (Are you using MSMQ bindings? Use MSMQ or a modern direct replacement like Azure Storage Queues or redis instead of "REST-like" HttpClient and Server, for instance.) There are also ugly "duct tape" solutions such as ASP.NET's "Kestrel" web server can easily be hosted in other .NET processes, if it absolutely must remain an "ordinary" Windows Service or something crazy like that.

Once you prove that your "hand-written" clients and service endpoints work, you can generally just throw out most of WCF's binding gunk in your config files and all the attributes on your interfaces. A lot of your code shouldn't change that much in this whole process if it was already just calling the interfaces with again the big caveat being if you need to add Task now, as opposed to having already migrated to it years ago or even using the older uglier Begin/End Async pattern which you often can easily replace with Task).

Another option to possibly explore, depending on the nature of your ServiceContracts, how they are expected to feel ("real time?"), is to use SignalR rather than HTTP. (The basics are about the same: make sure everything serializes/deserializes JSON well and change your "operation contracts" to SignalR calls and event responses.) SignalR is also generally hosted on a webserver for negotiating match-making, but actual communications happen in "peer-to-peer" websockets generally after negotiations complete. Azure SignalR has some powerfully scalable hosted solutions, depending on your environment's tolerance for cloud-based tools.

Re: C# 9 top-level programs and target-typed expressions

#93

Can I just create a single .cs file somewhere, and execute it by typing its name? No Visual Studio solution/project shenanigans? That’s my dream. Top-level programs to eliminate boilerplate is a nice related step.

what do you mean by "execute it"? It's source, you need to compile it and get an executable out of it. This is not Python, an interpreter. But if you want an interpreter for C#, nobody's stopping you to write one.

Me, on the other hand, I want Python to become a compiled language. And to those who's going to reply with "PyPy/Cython/Nuitka" I have a question for them: -do show me a .dll from those!

Re: C# 9 top-level programs and target-typed expressions

#94
post #73

Earlier quoted context omitted.

They were created by the same person. https://en.m.wikipedia.org/wiki/Anders_Hejlsberg All the hate C# gets is because of balmer and gates, not for technical reasons

Are you sure? My personal reluctance to C# has been that it's not handy for the stuff I do that needs to run on Windows, Mac, and Linux, which is everything.

Anything in particular? .NET 5.0 (and therefore C#) runs beautifully on Windows, Mac and Linux (x64 or Arm)

Re: C# 9 top-level programs and target-typed expressions

#95
post #44

Earlier quoted context omitted.

Is it possible to create a single, stand-alone, self-contained .exe? (I'm fine with only building for a single platform - Mac/Win/Linux) Needing to run my programs (which show up as .dll's) using dotnet just feels weird (and it doesn't match my intuition for 'how programs are run' in Windows cmd/etc). I'd be fine with an .exe that's not self contained but at least I run it like a 'normal' exe. :)

You have to set up "dotnet publish" for the project that makes the executable. It then makes a stub loader "your program.exe" which looks and behaves normally. You can then make it "self contained", which bundles the assemblies for you and transparently unpacks them. You can have different publish profiles for the different targets.

.NET 5.0 can now create true single file that doesn't need any unpacking on first run (except on Windows where the Jit and GC dlls will live or be unpacked separately; but that should be resolved in .NET 6.0)

Re: C# 9 top-level programs and target-typed expressions

#96

I think that C# is underrated. Although TypeScript is my default language choice for most programming, C# / .NET is my choice for cases where: - high performance is important - or interop with native libraries is required (because C#'s DllImport attribute makes that super simple) Another benefit is that C# is syntactically similar to TypeScript (they were both designed by Anders Hejlsberg after all), so switching bet…

I agree it is an excellent language from an ergnomics point of view.

One problem I've found for proprietary programs is that C# stored basically your whole source code in the executable. I don't just mean it's easy to disassemble... it's really retained the source code, or at least a lot of metadata. Even the original local variable names are there! I wonder if anyone has any ideas to work around this?

Re: C# 9 top-level programs and target-typed expressions

#97

Can I just create a single .cs file somewhere, and execute it by typing its name? No Visual Studio solution/project shenanigans? That’s my dream. Top-level programs to eliminate boilerplate is a nice related step.

what do you mean by "execute it"? It's source, you need to compile it and get an executable out of it. This is not Python, an interpreter. But if you want an interpreter for C#, nobody's stopping you to write one. Me, on the other hand, I want Python to become a compiled language. And to those who's going to reply with "PyPy/Cython/Nuitka" I have a question for them: -do show me a .dll from those!

To give an example, in Swift, I can write a hello.swift with:

    #!/usr/bin/env swift

    print("Hello")
And after a chmod +x, it works. Granted, anyone who I distribute this to will need a swift compiler installed, but that’s to be expected (and similar for Python.)

Golang and other “compiled” languages have similar ways of making this work too.

Re: C# 9 top-level programs and target-typed expressions

#99
post #91

I mean, top-level programs are nice, I guess? IMO it's more of a means of attracting non-.NET developers into the fold. I work in a .NET shop and we probably won't use this in our production code. The benefit of target-typed expressions IMO is that it changes property syntax from: public List Foos = new List (); to simply: public List Foos = new(); It may seem subtle, but if you write C# you see this pattern constant…

top level is mostly going to be nice when teaching new programmers. You can just get on with hello world and now have to type all this boiler plate and explain why you have to. But yeah, for "real" programs it is probably irrelevant. But who knows, maybe we will find a use for it.

I am mostly excited about the sort-of option type getting rid of nulls option.

Re: C# 9 top-level programs and target-typed expressions

#100
> Top-level programs allow you to write the main method of your application without having to add a class with a static Main method

Riveting stuff happening in .Net land! Sarcasm aside, this seems like such a small, oddly-specific, once-off feature that its like...why bother? Any C# devs want to enlighten me here?

Post reply on HN