My project is a Web project for MVC4 and I am trying to add a controller after adding a connection string to the web.config folder, but every time i try to add it, i get the following message:
Unable to retrieve metadata for TestFFL14.Models.LivePlayers. Object Reference not set to an instance of an object
Here is the LivePlayers Model:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Data.Entity;
namespace TestFFL14.Models
{
public class LivePlayers
{
public int ID { get; set; }
public int Nid { get; set; }
public string Plyr { get; set; }
public string Team { get; set; }
public DateTime DateAdded { get; set; }
public DateTime DateUpdated { get; set; }
}
public class LivePlayersDBContext : DbContext
{
public DbSet<LivePlayers> Players { get; set; }
}
}
I am trying to use this connection string but not having any success:
<add name="LivePlayersDBContext" connectionString="Server=127.0.0.1;Port=5432;Database=testdb;User Id=pkioko;Password=stunner1" providerName="Npgsql" />
What am i doing wrong?
Try this.
Add below LivePlayersDBContext constructor with connectionstring name as parameter to base constructor
public class LivePlayersDBContext : DbContext
{
public LivePlayersDBContext ():base("LivePlayersDBContext")
{
}
public DbSet<LivePlayers> Players { get; set; }
}
Related
I have several classes in my real code but for this problem I will focus on the two at hand. I have a List class which contains a Name and Items. There is also a Group class which has a name and Items. The relationship used to be List -> Group (many) -> Items. The default for our data seemed to trend more toward List -> Items (many) -> Group where an item may, or may not, be grouped. To accomplish this I simply removed the ListId and navigational item from the Group class. I am able to load the Items just fine but whenever I try to access the Groups DbSet it gives me the following error:
Invalid column name 'List_ListId'.
Here is the code for the classes and the DbContext. I am using EF6 (not core). I have tried recreating the Group class, restarting Visual Studio, restarting SQL Server, and wiping the publish directory to make sure it is clean. Help?
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using System.Linq;
namespace MyProject.Database
{
[Table("dbo.Lists")]
public class List
{
[Key]
public int ListId { get; set; }
[Required]
public string Name { get; set; }
[Required]
public bool SortAsNumeric { get; set; }
public virtual List<ListItem> Items { get; set; }
}
}
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using System.Linq;
using System.Text;
namespace MyProject.Database
{
[Table("dbo.ListGroups")]
public class ListGroup
{
[Key]
public int ListGroupId { get; set; }
[Required]
public string Name { get; set; }
[Required]
public int OrderSequence { get; set; }
[NotMapped]
public List<ListItem> Items { get; set; }
public ListGroup()
{
this.Items = new List<ListItem>();
}
}
}
using System;
using System.Collections.Generic;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using System.Text;
namespace MyProject.Database
{
[Table("dbo.ListItems")]
public class ListItem
{
[Key]
public int ListItemId { get; set; }
[Required]
public string Label { get; set; }
[Required]
public string Value { get; set; }
public string Subtext { get; set; }
public string Icon { get; set; }
public string Thumbnail { get; set; }
public int OrderSequence { get; set; }
[NotMapped]
public bool Selected { get; set; }
public int ListId { get; set; }
public virtual List List { get; set; }
public int? ListGroupId { get; set; }
public virtual ListGroup Group { get; set; }
public virtual List<ListItemProperty> Properties { get; set; }
public ListItem()
{
this.OrderSequence = 1;
this.Selected = false;
this.Properties = new List<ListItemProperty>();
}
}
}
using System.Collections.Generic;
using System.Data.Entity;
using System.Linq;
using System.Web.Mvc;
namespace MyProject.Database
{
public class ListContext : DbContext
{
public ListContext() : base("MyConnectionString") {}
public virtual DbSet<List> Lists { get; set; }
public virtual DbSet<ListItem> Items { get; set; }
public virtual DbSet<ListGroup> Groups { get; set; }
public virtual DbSet<ListItemProperty> Properties { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
modelBuilder.Entity<List>()
.HasMany(l => l.Items)
.WithRequired(li => li.List)
.HasForeignKey<int>(li => li.ListId);
modelBuilder.Entity<ListItem>()
.HasMany(li => li.Properties)
.WithRequired(p => p.Item)
.HasForeignKey<int>(p => p.ListItemId);
}
}
}
NOTE: The following code is working. The problem comes when I attempt to access this.Groups in the context.
List MyList = Lists
.Where(x => x.Name == ListName)
.Include(x => x.Items.Select(i => i.Properties))
.SingleOrDefault();
I want to read some data from a JSON API in SSIS and write it to a table in SQL Server. I've solved the task using a 3rd party, but the solution isn't that elegant, so now I'm trying to script it myself in Visual Studio using SSIS's script component.
I've researched around the web for solutions, and ended with this result. So far, I'm fairly confident about what is going on, but I lack the final direction for this. I know I need to somehow map the output to the columns I've created in SSIS.
I guess I have to do something around CreateNewOutputRows(), but I'm not sure what. Can someone please help me out on this? Also, since this is more or less my first ever c# script, I would also appreciate it, if there's a way easier solution OR if it is in some way inappropriate etc.
First of all, the output from the API looks like this (API documentation here):
"data":[
{
"created_at":"2016-03-12 09:45:00",
"created_at_unix":1457772300,
"shop_name":"DK - Some name",
"location_id":1111,
"custom_location_id":"2222",
"custom_shop_id":"2222",
"shop_id":3333,
"count_in":"1",
"count_out":"1",
"timekey":3
}
The script I've got so far is
using System;
using System.Data;
using Microsoft.SqlServer.Dts.Pipeline.Wrapper;
using Microsoft.SqlServer.Dts.Runtime.Wrapper;
using System.Linq;
using System.Net;
using System.Collections.Generic;
using Newtonsoft.Json;
[Microsoft.SqlServer.Dts.Pipeline.SSISScriptComponentEntryPointAttribute]
public class ScriptMain : UserComponent
{
public static void Main()
{
//Test api
var url = "https://login.vemcount.com/api/fetch_data/?data={"api_key":"xxxxxxx","type":"company_id","id":"10","date_from":"2019-01-01 00:00","interval":"15min", "group_by":"shop_id"}";
var json = new WebClient().DownloadString(url);
var root = JsonConvert.DeserializeObject<RootObject>(json);
//Printing last record
Console.WriteLine(root.data.Last().created_at);
}
public class data
{
public string created_at { get; set; }
public int created_at_unix { get; set; }
public string shop_name { get; set; }
public int location_id { get; set; }
public string custom_location_id { get; set; }
public string custom_shop_id { get; set; }
public int shop_id { get; set; }
public string count_in { get; set; }
public string count_out { get; set; }
public int timekey { get; set; }
}
public class RootObject
{
public List<data> data { get; set; }
}
public override void CreateNewOutputRows()
{
}
}
You'll put all that code in CreateNewOutputRows().
First you have to manually add all the columns to the script component. In the example here I only added 2 columns:
The code goes in CreateNewOutPutRows(). I don't have Newtonsoft, just using the JavaScriptSerializer here to show a working example so you can see how to hook it up:
using System;
using System.Data;
using Microsoft.SqlServer.Dts.Pipeline.Wrapper;
using Microsoft.SqlServer.Dts.Runtime.Wrapper;
using System.Web.Script.Serialization;
using System.Collections.Generic;
[Microsoft.SqlServer.Dts.Pipeline.SSISScriptComponentEntryPointAttribute]
public class ScriptMain : UserComponent
{
public override void CreateNewOutputRows()
{
string json = #"{""data"":[{""created_at"":""2016-03-12 09:45:00"",""created_at_unix"":1457772300,""shop_name"":""DK - Some name"",""location_id"":1111,""custom_location_id"":""2222"",""custom_shop_id"":""2222"",""shop_id"":3333,""count_in"":""1"",""count_out"":""1"",""timekey"":3},{""created_at"":""2016-03-12 09:45:00"",""created_at_unix"":1457772300,""shop_name"":""test2"",""location_id"":1111,""custom_location_id"":""2222"",""custom_shop_id"":""2222"",""shop_id"":3333,""count_in"":""1"",""count_out"":""1"",""timekey"":3}]}";
RootObject Test = new JavaScriptSerializer().Deserialize<RootObject>(json);
/*
* This is where data gets added to the output buffer.
* After AddRow() you are basically mapping the column you manually added(on the left) to the data(on the right).
* using a foreach loop to loop through the deserialize json
*/
foreach (var item in Test.data)
{
Output0Buffer.AddRow();
Output0Buffer.createdat = item.created_at;
Output0Buffer.shopname = item.shop_name;
}
}
public class RootObject
{
public List<data> data { get; set; }
}
public class data
{
public string created_at { get; set; }
public int created_at_unix { get; set; }
public string shop_name { get; set; }
public int location_id { get; set; }
public string custom_location_id { get; set; }
public string custom_shop_id { get; set; }
public int shop_id { get; set; }
public string count_in { get; set; }
public string count_out { get; set; }
public int timekey { get; set; }
}
}
Then in this example, just using a record set destination and enabled data viewer so you can see the individuals rows come back out:
I have the following JSON string:
[
{
"name":"Test diagnosis",
"code":"324324",
"table":"EXAMPLE",
"addedby":"EDnurse",
"dateadded":3243243,
"qualifier":[
{
"name":"Qualifier",
"value":"Confirmed Diagnosis",
"code":"23434434",
"prefix":"[C] "
},
{
"name":"Left/Right",
"value":"Bilateral",
"code":"324343",
"suffix":" - Bilateral"
}
],
"prefix":"[C] ",
"suffix":" - Bilateral"
}
]
You can see that the Qualifier field in this JSON String is nested and has 2 objects.
I am working on a package that parses this JSON string using C# in SSIS. I can Parse the string with one object of qualifier, but when I add the second object (left/right), and attempt to turn the string into an array, I receive an error.
Without array (works with one Qualifier object):
Diagnosis diagnosis = js.Deserialize<Diagnosis>(reviewConverted);
With array (returns error stating that I cannot implicitly convert type diagnosis to type diagnosis ):
Diagnosis diagnosis = js.Deserialize<List<Diagnosis>>(reviewConverted);
I also use the following Class to define my diagnosis fields:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SC_8aae662509ae4bab8491323924579173
{
class Diagnosis
{
public string name { get; set; }
public string code { get; set; }
public string table { get; set; }
public string addedby { get; set; }
public string dateadded { get; set; }
public qualifier Qualifier { get; set; }
public string prefix { get; set; }
public string suffix { get; set; }
}
}
Here is my qualifier class:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
namespace SC_8aae662509ae4bab8491323924579173
{
class qualifier
{
public string name { get; set; }
public string value { get; set; }
public string code { get; set; }
public string prefix { get; set; }
}
}
As far as i can tell, based on what you're saying, 1 Diagnosis object, can contain multiple Qualifier objects. So what you need to do is the following:
First, change your Diagnosis class to have the following property:
public qualifier List<Qualifier> { get; set; }
instead of
public qualifier Qualifier { get; set; }
Also the following statement is what gives you an error:
Diagnosis diagnosis = js.Deserialize<List<Diagnosis>>(reviewConverted);
You are trying to store in a Diagnosis objext a List of Diagnosis object, which makes no sense of course.
Did you try like below?
class Diagnosis
{
public string name { get; set; }
public string code { get; set; }
public string table { get; set; }
public string addedby { get; set; }
public string dateadded { get; set; }
public List<Qualifier> qualifier { get; set; }
public string prefix { get; set; }
public string suffix { get; set; }
}
I'm writing an ASP.NET Web API right now and everything works just fine for 2 controllers. Now I try to do exactly the same as before but this time I get a weird error:
System.InvalidOperationException: "The entity type 'UserItem' requires a primary key to be defined."
Well then, why does UserItem needs a primary key when the others don't?
This is my UserItem class:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
namespace ModulApi.Models
{
public class UserItem
{
public int matrikelnr { get; set; }
public string studiengang { get; set; }
public string user_semester { get; set; }
public string user_max_klausur { get; set; }
//Not necessary Constructor. I try to fix the primary Key error.
public UserItem()
{
this.matrikelnr = 0;
this.studiengang = "";
this.user_max_klausur = "";
this.user_semester = "";
}
}
}
And my WORKING LoginItem class:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
namespace ModulApi.Models
{
public class LoginItem
{
public long Id { get; set; }
public string username { get; set; }
public string password { get; set; }
public string matrikelnr { get; set; }
public string email { get; set; }
public string email_verified { get; set; }
public LoginItem()
{
this.Id = 0;
this.username = "";
this.password = "";
this.matrikelnr = "";
this.email = "";
this.email_verified = "";
}
}
}
As you see, I got getter and setter set up, so the error can't be there.
Here is where the error occurs:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
using ModulApi.Models;
using ModulApi.DBConnectors;
// For more information on enabling Web API for empty projects, visit
https://go.microsoft.com/fwlink/?LinkID=397860
namespace ModulApi.Controllers
{
[Route("api/user")]
public class UserController : Controller
{
private readonly UserContext _context;
public UserController(UserContext context)
{
_context = context;
if (_context.UserItems.Count() == 0) <--- Error right here
{
getDataFromConnector(_context);
}
}
private void getDataFromConnector(UserContext context)
{
//Getting my Data from Database method
}
.
.
Well Since it is in a Context call, I'll attach UserContext as well, but again it is the same as in LoginContext, which works just fine.
UserContext:
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.EntityFrameworkCore;
namespace ModulApi.Models
{
public class UserContext : DbContext
{
public UserContext(DbContextOptions<UserContext> options) : base(options)
{
}
public DbSet<UserItem> UserItems { get; set; }
}
}
Has anyone a clue why I get this weird error? And why all other Controllers work fine which do exactly the same?
Entity Framework goes by convention. That means that if you have an object with a property named Id, it will assume that it is the Primary Key for the object. That's why your LoginItemclass works fine.
Your UserItem class has no such property, and therefor it can't figure out what to use as the primary key.
To fix this, affix the KeyAttribute to whatever your primary key is on your class. For example:
// Need to add the following using as well at the top of the file:
using System.ComponentModel.DataAnnotations;
public class UserItem
{
[Key]
public int matrikelnr { get; set; }
public string studiengang { get; set; }
public string user_semester { get; set; }
public string user_max_klausur { get; set; }
// ...
}
Your working LoginItem has:
public long Id { get; set; }
Properties called *id are detected and used as the primary key by convention. You need to explicitly set the [Key] attribute otherwise.
There are multiple was to resolve this.
1.Decorate matrikelnr as [Key]
public class UserItem
{
[Key]
public int matrikelnr { get; set; }
public string studiengang { get; set; }
public string user_semester { get; set; }
public string user_max_klausur { get; set; }
//Not necessary Constructor. I try to fix the primary Key error.
public UserItem()
{
this.matrikelnr = 0;
this.studiengang = "";
this.user_max_klausur = "";
this.user_semester = "";
}
}
2.Rename matrikelnr with matrikelnrId . With *Id , EF will consider it as PK.
public class UserItem
{
[Key]
public int matrikelnrId { get; set; }
public string studiengang { get; set; }
public string user_semester { get; set; }
public string user_max_klausur { get; set; }
//Not necessary Constructor. I try to fix the primary Key error.
public UserItem()
{
this.matrikelnrId = 0;
this.studiengang = "";
this.user_max_klausur = "";
this.user_semester = "";
}
}
Beacuse you register UserItem with DBContext, DBContext Bind this user item with SQL database Table with which it is necessary to set any primary key attribute in UserItem.
Try this , it will resolve your problem.
[Key]
public int matrikelnr { get; set; }
My question is how to make it possible to have a function that takes a string convert it to a class and than execute a linq query.
This is a simple example of how it should work:
// DBContext
DataView _db = new DataView();
public static void ... (){
Create("somedesc", "someabbr", "vwFunctieScheidingMetacom", "someiconstring");
}
// the function
public static void Create(string description, string abbrevition, string cn, string icon)
{
// cn is classname
// convert cn into a class
var class = Convert.Class(cn);
// Execute Linq query
_db.class.ToList<dynamic>();
}
This is my dbcontext:
public partial class DataView : DbContext
{
public DataView()
: base("name=DataView")
{
}
public virtual DbSet<vwFunctieScheidingMetacom> vwFunctieScheidingMetacom { get; set; }
protected override void OnModelCreating(DbModelBuilder modelBuilder)
{
}
}
Now there is only one model loaded, but in the future there will be more. these models will all be different and I want to make it as dynamic as possible.
I tried to use reflection but it didn't work yet, i have no idea where to start.
Any help would be appreciated.
update
This is one of the class that needs to be used dynamicly:
namespace Portal.ModelViews
{
using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
using System.Data.Entity.Spatial;
[Table("vwFunctieScheidingMetacom")]
public partial class vwFunctieScheidingMetacom
{
public int? PermissiesID1 { get; set; }
public int? PermissiesID2 { get; set; }
[StringLength(255)]
public string PermName1 { get; set; }
[StringLength(255)]
public string PermName2 { get; set; }
public string Omschrijving { get; set; }
public int? Prioriteit { get; set; }
[StringLength(50)]
public string Login { get; set; }
[Key]
[Column(Order = 0)]
[DatabaseGenerated(DatabaseGeneratedOption.None)]
public int FunctieScheidingID { get; set; }
[Key]
[Column(Order = 1)]
[StringLength(60)]
[DisplayName("ID")]
public string ID { get; set; }
}
}
Since you don't seem to like the answers so far I'll interpret your question differently. Put references to your classes in a dictionary.
Assuming your code defines a class Foo...
var clash = new Dictionary< string, Type>();
clash["Foo"] = Foo.GetType();
Populate this hash table with your strings and the types to which they resolve.