Search code examples
asp.net-mvcpostgresqlasp.net-coreasp.net-core-mvcnpgsql

Unable to query beyond a few rows with Npgsql.EntityFrameworkCore.PostgreSQL (3.1.4)


I'm in an .NET Core MVC 3.1 project, using Npgsql.EntityFrameWorkCore.PostgreSQL (3.1.4) and have configured the connection string to a remote postgreSQL DB server. I'm not using a DBContext because I need to write SQL queries. I have a regular action method inside HomeConroller:

public IActionResult Countries()
        {
            _logger.LogInformation("About to return countries...");
            return View(DataAccess.GetCountries);
        }

I get countries using

class DataAccess
    {
        public static List<Country> GetCountries
        {
            get {
                var connString = "connection string obscured";
                using var conn = new NpgsqlConnection(connString);
                conn.Open();
                var cmd = new NpgsqlCommand("SELECT name, capital, population FROM country", conn);
                List<Country> temp = new List<Country>();
                using (var reader = cmd.ExecuteReader())
                    while (reader.Read())
                    {
                        temp.Add(new Country(reader.GetString(0), reader.GetString(1), reader.GetInt32(2)));
                    }

                return temp;
            }
            set { }
        }
    }

The error is

An unhandled exception occurred while processing the request.
InvalidCastException: Column is null
Npgsql.NpgsqlDataReader.GetFieldValue<T>(int ordinal)

Stack Query Cookies Headers Routing
InvalidCastException: Column is null
Npgsql.NpgsqlDataReader.GetFieldValue<T>(int ordinal)
Npgsql.NpgsqlDataReader.GetString(int ordinal)
dblabb3mvccore.Data.DataAccess.get_GetCountries() in DataAccess.cs
+
                        temp.Add(new Country(reader.GetString(0), reader.GetString(1), reader.GetInt32(2)));
dblabb3mvccore.Controllers.HomeController.Countries() in HomeController.cs
+
            return View(DataAccess.GetCountries);
lambda_method(Closure , object , object[] )
Microsoft.Extensions.Internal.ObjectMethodExecutor.Execute(object target, object[] parameters)
Microsoft.AspNetCore.Mvc.Infrastructure.ActionMethodExecutor+SyncActionResultExecutor.Execute(IActionResultTypeMapper mapper, ObjectMethodExecutor executor, object controller, object[] arguments)
Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeActionMethodAsync()
Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(ref State next, ref Scope scope, ref object state, ref bool isCompleted)
Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeNextActionFilterAsync()
Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Rethrow(ActionExecutedContextSealed context)
Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.Next(ref State next, ref Scope scope, ref object state, ref bool isCompleted)
Microsoft.AspNetCore.Mvc.Infrastructure.ControllerActionInvoker.InvokeInnerFilterAsync()
Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeNextResourceFilter>g__Awaited|24_0(ResourceInvoker invoker, Task lastTask, State next, Scope scope, object state, bool isCompleted)
Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.Rethrow(ResourceExecutedContextSealed context)
Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.Next(ref State next, ref Scope scope, ref object state, ref bool isCompleted)
Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.InvokeFilterPipelineAsync()
Microsoft.AspNetCore.Mvc.Infrastructure.ResourceInvoker.<InvokeAsync>g__Awaited|17_0(ResourceInvoker invoker, Task task, IDisposable scope)
Microsoft.AspNetCore.Routing.EndpointMiddleware.<Invoke>g__AwaitRequestTask|6_0(Endpoint endpoint, Task requestTask, ILogger logger)
Microsoft.AspNetCore.Authorization.AuthorizationMiddleware.Invoke(HttpContext context)
Microsoft.AspNetCore.Diagnostics.DeveloperExceptionPageMiddleware.Invoke(HttpContext context)

Despite no columns being null in the DB.

However, it works if I change the SQL command to for example SELECT name, capital, population FROM country limit 20.

My Country.cs:

    public class Country
    {
        public Country(string name, string capital, int population)
        {
            Name = name;
            Capital = capital;
            Population = population;
        }

        public string Name { get; set; }
        public string Capital { get; set; }
        public int Population { get; set; }
    }

Countries.cshtml:

@model List<Country>
@{
    ViewData["Title"] = "Countries";
}
<h1>@ViewData["Title"]</h1>

<table class="table table-bordered table-striped">
    <thead>
    <tr>
        <th>Name</th>
        <th>Capital</th>
        <th>Population</th>
    </tr>
    </thead>
    <tbody>
    @foreach (var country in Model)
    {
        <tr>
            <td>@country.Name</td>
            <td>@country.Capital</td>
            <td>@country.Population</td>
        </tr>
    }
    </tbody>
</table>

Solution

  • Admittedly, there were null values in my DB.