Hoy le toca el turno a un código de estado HTTP que no es nada habitual: HTTP 416 (Range Not Satisfiable). Este resultado se obtiene cuando la solicitud de un rango, especificado en el encabezado Range
, indica un valor que no puede ser satisfecho por el servidor, quizás porque son inválidos o porque superan el tamaño del recurso.
Ahí van los enlaces recopilados durante la semana pasada. Espero que os resulten interesantes. :-)
Por si te lo perdiste...
- Rutado dinámico en ASP.NET Core 3 MVC
José María Aguilar - Funciones locales en C# 7
José María Aguilar
.NET Core / .NET
- C# 9.0 – Specification: Partial Methods
Jorge Serrano - Algunas particularidades respecto a la inicialización y validación en setters
Jorge Serrano - Modelo de actores con Akka.Net – II
Joaquín García - MediatR 9.0 Released
Jimmy Bogard - .NET 5: Exploring System.Net.Http.Json namespace
Anthony Giretti - Tidy up your HttpClient usage
Josef Ottosson - 6 Best Practices to Keep a .NET Application's Memory Healthy
Michael Shpilt - Creating a dotnet new Project Template
Rick Strahl - Creating a .NET Core Global Tool
John Smith - Generate INotifyPropertyChanged implementation for MVVM pattern
Kazuki Ota - .NET Internals: System.Threading.Channels - UnboundedChannel (Part 1) - Steve Gordon
Steve Gordon - Changing Serilog Minimum level without application restart on .NET Framework and Core
Niels Swimberghe - Introducing C# 9: Covariant returns
Anthony Giretti - C# in Simple Terms - Code Blocks, Basic Statements, and Loops
Matthew Jones - Calculate the Moon Phase With C#
Khalid Abuhakmeh
<NumberList Count="10" />
Desde el punto de vista del componente <NumberList>
, la recepción de este parámetro es trivial, simplemente indicando el atributo [Parameter]
en su propiedad pública Count
:<ul>
@for (int i = 0; i < Count; i++)
{
<li>@i</li>
}
</ul>
@code {
[Parameter]
public int Count { get; set; }
}
Este mecanismo va bien si queremos pasar el parámetro a un componente específico mediante atributos, pero puede haber ocasiones en las que nos interesa pasar parámetros a todos los componentes que se encuentren por debajo en la estructura jerárquica sin tener que ir pasándolos de uno en uno. Esto puede ser especialmente útil si, como en el diagrama, existen varios niveles de componentes en los que deseamos tener acceso a la misma información.¡Bienvenidos a los cascading values and parameters, o valores y parámetros en cascada!
Probablemente os habréis topado algúna vez con el error HTTP 415 "Unsupported Media Type" mientras hacéis pruebas de APIs. Este código se reserva para que el servidor indique al otro extremo que los datos enviados en la petición no se encuentran en un formato soportado (por ejemplo, hemos enviado datos XML cuando sólo se soportan JSON, o algo similar). El servidor puede determinar la falta de soporte examinando los encabezados Content-Type
o Content-Encoding
, así como el propio cuerpo de la petición.
Y ahora, van los enlaces recopilados durante la semana pasada. Espero que os resulten interesantes. :-)
Por si te lo perdiste...
- Cómo modificar la convención de nombrado de controladores en ASP.NET Core MVC
José María Aguilar - Publicación self-contained y single-file en .NET Core
José María Aguilar
.NET Core / .NET
- C# 9.0 – Specification: Init-only Setters & Pattern Matching Enhancements & Target Typing & Target-Typed Conditional Expressions & Target-Typed Conditional Expressions & Covariant Returns
Jorge Serrano (¡Vaya serie, amigo! :)) - Introducing DotNet.SystemCollections.Analyzers
Kevin Avignon - IConfiguration does not contain a definition for GetValue
Paul Michaels - Don't Let Your .NET Applications Fail: Resiliency with Polly
Dmitrij Kovaliov - EnsureSuccessStatusCode as an assertion
Mark Seemann - A Subtle Gotcha with Azure Deployment Slots and ASP.NET Core
Phil Haack - A simple pattern for using System.CommandLine with dependency injection
Carmel Eve - C# in Simple Terms - Primitive Types, Literals, and Nullables
Matthew Jones - Automatic factory with Microsoft.Extensions.DependencyInjection and Castle DynamicProxy
Thomas Levesque - .NET 5.0 App Trimming and Potential for Future Progress
Patrick Smacchia - ArrayPool vs MemoryPool—minimizing allocations in AIS.NET
Ian Griffiths - Getting rid of array bound checks, ref-returns and .NET 5
Konrad Kokosa - Streamline .NET Dependency Management with NuGet Meta Packages
James Dawson - ILogger and Null Object Pattern
Christian Findlay - .NET Framework Connection Pool Limits and the new Azure SDK for .NET
Pavel Krymets - Programmable text (and JSON) formatting for Serilog
Nicholas Blumhardt - Using Hangfire and MediatR as a Message Dispatcher
Derek Comartin - Serialize Interface Instances With System.Text.Json
Khalid Abuhakmeh - How to use .NET module initializers in a concrete real use case
Daniel Cazzulino - C# in Simple Terms - Casting, Conversion, and Parsing
Matthew Jones - Creating C# Enums from a SQL Database using T4 Text Templates
Matthew Jones
Como sabemos, al acceder por primera vez a una aplicación Blazor WebAssembly, durante unos segundos aparecerá en el navegador el mensaje "Loading...", indicando que se están descargando los recursos necesarios para que funcione la aplicación.
Vimos también en su momento que este mensaje puede ser modificado a nuestro antojo para sustituirlo por algo más apropiado, como un espectacular spinner:
Sin embargo, si el navegador desde el que estamos accediendo es un vetusto Internet Explorer u otro sin soporte para Blazor WebAssembly, el mensaje de carga se mostrará indefinidamente en el navegador. No se mostrarán errores, ni siquiera por la consola, por lo que el usuario se quedará esperando sin saber que, en realidad, la aplicación no cargará jamás.
Lo que vamos a ver en este post es cómo detectar este escenario e informar al usuario de que para acceder a la aplicación debe usar un browser más moderno.
El código de respuesta HTTP 414, "URI Too Long", se reserva para indicar al cliente que la URI indicada en la petición es demasiado extensa. Esto puede darse en varios escenarios, pero quizás uno de os más frecuentes es cuando se produce un bucle infinito de redirecciones a páginas, cuyos parámetros van aumentando en cada iteración (por ejemplo, el clásico /login?returnUrl=/login
).
Aprovecho para recordaros que el próximo miércoles 30 de septiembre a las 18:30 (CEST, hora peninsular española) estaré con los amigos de SevillaDotNet tomándome un café virtual y hablando de desarrollo web, Blazor, el blog y todo lo que surja ;) Podéis usar este enlace para inscribiros gratuitamente y asistir online.
También está disponible la grabación del evento online de CampusMVP del pasado martes 22, donde José Manuel Alarcón y un servidor charlamos sobre Blazor un buen rato: ¿Qué es Blazor? ¿Qué me aporta? Lo que necesitas saber sobre Blazor.
Y ahora, van los enlaces recopilados durante la semana pasada. Espero que os resulten interesantes. :-)
Por si te lo perdiste...
- Adivina, adivinanza: ¿por qué no compila este código?
José María Aguilar - Cómo documentar y generar código cliente de nuestras APIs utilizando Swagger/OpenAPI
José María Aguilar
.NET Core / .NET
- C# 9.0 – Specification: Records & Top-Level Statements
Jorge Serrano - Hacer un FeedReader fácilmente en .NET Core 3.1
Jorge Serrano - Announcing more ways, we’re making app development easier on Windows
Kevin Gallo - Injecting services into Serilog filters, enrichers, and sinks
Nicholas Blumhardt - Building amazing cross-platform solutions for iOS, Android and Windows
Nick Randolph - Comparing .NET Mocking Libraries
Dan Clarke - PEM Loading in .NET Core and .NET 5
Scott Brady - How to generate code using Roslyn source generators in real world scenarios
Daniel Cazzulino - Responding to Phone Calls using Twilio and C#
Jamie Maguire - Using LINQ Expressions In C#
Munib Butt - Moving work Out-of-Process using Brighter and RabbitMQ
Derek Comartin - Automating .NET Security Updates
Muhammad Rehan Saeed - Deploying a .NET desktop application using MSIX
Gérald Barré - C# 8.0 nullable references and serialization
Ian Griffiths - NET Core Releases and Support
Jamshed Damkewala - C# in Simple Terms - The Type System
Matthew Jones - Zero Installer, Zero MSIX, Zero Packaging with .NET Single File Apps
Nick Randolph
Pero para entender su utilidad, creo que lo mejor es comenzar por un ejemplo de componente simple como el siguiente, que se encarga de mostrar una colección de objetos
Friend
formateados de una manera determinada:@* File: ItemList.razor *@
@{
var count = 1;
foreach (var item in Items)
{
<div class="counter">Item #@(count++)</div>
<div class="item">
@ChildContent(item)
</div>
}
}
@code
{
[Parameter]
public IEnumerable<Friend> Items { get; set; }
[Parameter]
public RenderFragment<Friend> ChildContent { get; set; }
}
Fijaos que estamos utilizando un RenderFragment
tipado. Si no sabes muy bien lo que es esto, puedes echarle un vistazo al post Componentes con cuerpo en Blazor.
Como hemos podido comprobar, lo único que hace el componente <ItemList>
es recorrer la colección de amigos disponible en la propiedad Items
y, por cada elemento, mostrar un contador que va incrementándose en cada iteración, renderizando el RenderFragment<Friend>
con el ítem actual.<ItemList>
podría ser utilizado desde cualquier otro componente, por ejemplo, de la siguiente manera:<h1>My friends</h1>
<ItemList Items="@Friends">
<p>@context.Name is @context.Age years old</p>
</ItemList>
@code {
public Friend[] Friends { get; set; }
protected override void OnInitialized()
{
Friends = new[] {
new Friend() {Name = "John", Age = 32},
new Friend() {Name = "Peter", Age = 23},
new Friend() {Name = "Ally", Age = 31}
};
}
}
Si ejecutamos un código como el anterior, podremos que ver todo es correcto: la lista de amigos se muestra correctamente. Bueno, todo es correcto, excepto cuando nos preguntamos si este mismo componente podría servir para otros tipos de objeto distintos a Friend
.Esto lo hemos vivido ya antes, muchos años atrás, cuando aún no existían los tipos genéricos en C# y .NET. Porque lo que realmente nos interesaría para lograr una mayor reutilización de código es que el componente
<ItemList>
fuera genérico y pudiera aplicarse a cualquier tipo de datos.