I am trying to display the items in my list via the console and I'm not sure how to achieve that.
Data is added to a list from a SQL server with the following code:
List:
namespace SSIS_FileWatcher
{
public class WikiList //custom list
{
public string Source { get; set; }
}
}
Code to add data to list:
using System;
using System.Collections.Generic;
using System.Data.SqlClient;
using System.Text;
namespace SSIS_FileWatcher
{
public class getWikiData
{
public List<WikiList> Source()
{
using (SqlConnection connection = new SqlConnection(Helper.CnnVal("DEV-BRMSQL01")))
{
connection.Open();
SqlCommand sqlCommand = new SqlCommand("SELECT source FROM [REFERENCE].[KRI_METRIC_WIKI_AND_INGESTION_SCHEDULE] ", connection);
SqlDataReader reader = sqlCommand.ExecuteReader();
while (reader.Read())
{
List<WikiList> entries = new List<WikiList>();
while (reader.Read())
{
WikiList w = new WikiList();
w.Source = (string)reader["Source"];
//w.Metric_ID = (string)reader["Metric_ID"];
//w.name = (string)reader["name"];
entries.Add(w);
}
}
}
return List<WikiList>;
}
}
}
Main code:
using System;
using System.Collections.Generic;
using System.Linq;
using System.IO;
using System.Threading;
using System.Threading.Tasks;
using Microsoft.Extensions.Hosting;
using Microsoft.Extensions.Logging;
using System.Data.SqlClient;
using System.Data;
namespace SSIS_FileWatcher
{
public class Worker : BackgroundService
{
public string path = #"\\p1l-nas-02\EntTechBURM_DATA\PRD\";
private readonly ILogger<Worker> _logger;
public Worker(ILogger<Worker> logger)
{
_logger = logger;
}
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
while (!stoppingToken.IsCancellationRequested)
{
try
{
_logger.LogInformation("Worker running at: {time}", DateTimeOffset.Now);
//add code to display list in console
await Task.Delay(60*1000, stoppingToken);
}
catch (Exception ex)
{
Console.WriteLine($"Exception: {ex.Message}");
}
}
}
}
}
As you can see in the last code sample, I commented where I would like to show the results from my list. If anyone can show me how to do this, it would be much appreciated.
first of all, set the return type of getWikiData to List<WikiList>().
(this you have done after an edit)
Then after calling getWikiData.Source(), you can create a string list like so:
var wikis = new getWikiData().Source();
string str = String.Join("\r\n", wikis.Select(x => x.Source));
Console.WriteLine(str);
If you want to add a bullet like structure, this can be achieved this way:
var wikis = new getWikiData().Source();
if (wikis.Count > 0)
{
string str = "\t- " + String.Join("\r\n\t- ", wikis.Select(x => x.Source));
Console.WriteLine(str);
}
edit after your comment
I modified your method to work, beware that you renamed the method:
public List<WikiList> Source()
{
List<WikiList> entries = new List<WikiList>();
using (SqlConnection connection = new SqlConnection(Helper.CnnVal("DEV-BRMSQL01")))
{
connection.Open();
SqlCommand sqlCommand = new SqlCommand("SELECT source FROM [REFERENCE].[KRI_METRIC_WIKI_AND_INGESTION_SCHEDULE] ", connection);
SqlDataReader reader = sqlCommand.ExecuteReader();
while (reader.Read())
{
while (reader.Read())
{
WikiList w = new WikiList();
w.Source = (string)reader["Source"];
//w.Metric_ID = (string)reader["Metric_ID"];
//w.name = (string)reader["name"];
entries.Add(w);
}
}
}
return entries;
}
You could use the JavaScriptSerializer class (add reference to System.Web.Extensions):
using System.Web.Script.Serialization;
after that
var wikis = getWikiData();
var json = new JavaScriptSerializer().Serialize(wikis);
Console.WriteLine(json);
Also, you can use Newtonsoft
ref- https://www.newtonsoft.com/json
you don' t need WikiData class
public List<string> Source()
{
List<string> entries = new List<string>();
using (SqlConnection connection = new SqlConnection(Helper.CnnVal("DEV-BRMSQL01")))
{
...
while (reader.Read()) entries.Add(reader["Source"].ToString());
reader.Close();
}
return entries;
}
and how to display
var getWikiData= new getWikiData();
var source =getWikiData.Source();
Console.WriteLine(string.Join(Join("\n\r",source));
To provide an alternative method (Cedric's will work, but if there's lots of data it may look like nothing's happening in the console for a while; so you may desire to print each line as it's retrieved):
If so, you could tweak the class definition to:
public class WikiList //custom list
{
public string Source { get; set; }
public void WriteToConsole()
{
Console.WriteLine(Source);
}
}
Allowing getWikiData to change to:
public class getWikiData
{
public List<WikiData> Entries {get;set;}
public getWikiData()
{
using (SqlConnection connection = new SqlConnection(Helper.CnnVal("DEV-BRMSQL01")))
{
connection.Open();
SqlCommand sqlCommand = new SqlCommand("SELECT source FROM [REFERENCE].[KRI_METRIC_WIKI_AND_INGESTION_SCHEDULE] ", connection);
SqlDataReader reader = sqlCommand.ExecuteReader();
while (reader.Read())
{
Entries = new List<WikiList>();
WikiList w = new WikiList();
w.Source = (string)reader["Source"];
//w.Metric_ID = (string)reader["Metric_ID"];
//w.name = (string)reader["name"];
Entries.Add(w);
w.WriteToConsole();
}
}
}
}
Meaning you just call getWikiData in your worker method:
protected override async Task ExecuteAsync(CancellationToken stoppingToken)
{
while (!stoppingToken.IsCancellationRequested)
{
try
{
_logger.LogInformation("Worker running at: {time}", DateTimeOffset.Now);
getWikiData wikiData = new getWikiData();
await Task.Delay(60*1000, stoppingToken);
}
catch (Exception ex)
{
Console.WriteLine($"Exception: {ex.Message}");
}
}
}
Related
I need help with the project I am currently working on. Please bare with me, I'm not good at coding specially with c# this is my first attempt.
I have a button the will pull the data from webservice. Saving of data to database will be triggered with the same button. I have manage to display the string via tutorial and now stuck on saving I don't know where I went wrong it keeps on throwing error that **Value cannot be null ** I have provided that error message for your reference and the json output.
This is what I have so far
CIP.cs
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using RestSharp.Authenticators;
using System.IO;
using RestSharp;
using System.Text.Json;
using System.Data;
using System.Data.SqlClient;
using System.Configuration;
using System.Xml.Linq;
namespace SAPSO
{
class CIP
{
public class DetailOutput
{
public string NAME { get; set; }
public string ADD { get; set; }
public string GAP { get; set; }
public DateTime SDTE { get; set; }
public DateTime EDTE { get; set; }
}
RestClient client;
RestRequest request;
public CIP()
{
client = new RestClient(#"urlpath/");
client.Authenticator = new HttpBasicAuthenticator("user", "pass");
}
public List<DetailOutput>
GetDetailOutputs(DateTime start, DateTime end)
{
request = new RestRequest("sap/bc/zcip", Method.Get);
request.AddParameter("sap-client", "200");
request.AddParameter("start", "");
request.AddParameter("end", end.ToString("yyyyMMdd"));
var output = client.ExecuteAsync<List<DetailOutput>>(request);
var o = output.Result.Data;
return o;
}
public void ProcessOutput(DateTime start, DateTime end)
{
var output = GetDetailOutputs(start, end);
if (output.Count() < 1)
{
Console.WriteLine("Null");
}
else
{
Console.WriteLine(output.ToString());
}
var xmlPath = new XElement("CIPS",
from CIPPath in output
select new XElement("CIP",
new XElement("NAME", CIPPath.NAME),
new XElement("ADD", CIPPath.ADD),
new XElement("GAP", CIPPath.GAP),
new XElement("SDTE", CIPPath.SDTE),
new XElement("EDTE", CIPPath.EDTE)));
insertCIP(xmlPath.ToString(), "InsertDetail");
}
//insert to db
int insertCIP(string xml, string strdproc)
{
int row = 0;
try
{
using (SqlConnection con = new SqlConnection(ConfigurationManager.ConnectionStrings["db"].ConnectionString))
{
using(SqlCommand cmd = new SqlCommand(strdproc))
{
cmd.Connection = con;
cmd.CommandTimeout = 3000;
cmd.CommandType = CommandType.StoredProcedure;
cmd.Parameters.AddWithValue("#xmldata", xml);
con.Open();
row = cmd.ExecuteNonQuery();
con.Close();
}
}
}
catch(Exception ex)
{
Console.WriteLine(ex.Message);
}
return row;
}
}
}
This is my form1.cs
void m_oWorker_DoWork(object sender, DoWorkEventArgs e)
{
try
{
_backgroundWorkerThread = Thread.CurrentThread;
SAP svc = new SAP();
CIP cip = new CIP();
cip.ProcessOutput(dte_from.Value, dte_to.Value);
}
catch (ThreadAbortException)
{
e.Cancel = true;
m_oWorker.Dispose();
Thread.ResetAbort();
}
}
I use Microsoft sqlserver for my database.
Here is the sample output of the webservice:
[{"NAME":"FOLDERNME","ADD":"0000000376_0000000385","GAP":"GP\\ADVNAME\\ADVNME2, INC","SDTE ":"0000-00-00","EDTE ":"0000-00-00"}]
And this is the error I'm getting.
System.ArgumentNullException HResult=0x80004003 Message=Value
cannot be null. Parameter name: source Source=System.Core
StackTrace: at System.Linq.Enumerable.Count[TSource](IEnumerable`1
source) at SAPSO.CIP.ProcessOutput(DateTime start, DateTime end) in
C:\prjname\trunk\GET\SAPSO\CIP.cs:line 58 at
SAPSO.Form1.m_oWorker_DoWork(Object sender, DoWorkEventArgs e) in
C:\prjname\trunk\GET\SAPSO\Form1.cs:line 103 at
System.ComponentModel.BackgroundWorker.OnDoWork(DoWorkEventArgs e)
at System.ComponentModel.BackgroundWorker.WorkerThreadStart(Object
argument)
This exception was originally thrown at this call stack:
[External Code]
SAPSO.CIP.ProcessOutput(System.DateTime, System.DateTime) in CIP.cs
SAPSO.Form1.m_oWorker_DoWork(object, System.ComponentModel.DoWorkEventArgs) in Form1.cs
[External Code]
I'm developing a WinForms application in C# and I want to connect my access database to my application through the code in the class below, but the application.StartupPath does not point to the bin/debug folder which contains my application's executable instead it points to this C:program files x86/Microsoft Visual Studio/2019/Community/Common 7/IDE folder, my application files are not even in the C drive I don't know what is causing the problem.
here is my code:
enter code here
using System;
using System.Configuration;
using System.Data.OleDb;
using System.Windows.Forms;
namespace GradeApplicationForm.Models
{
public static class Connector
{
public static OleDbConnection Connect()
{
return new OleDbConnection($#"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=" + Application.StartupPath + #"grades.accdb");
}
}
}
using System.Collections.Generic;
using System.Linq;
using System.Data;
using Dapper;
using GradeApplicationForm.Models;
using System.Data.OleDb;
namespace GradeApplicationForm.DataAccess
{
class StudentDataAccess
{
public List<StudentsModel> getStudents()
{
using (OleDbConnection connection = Connector.Connect())
{
string sql = "SELECT * FROM tbl_StudentInfo";
var result = connection.Query<StudentsModel>(sql).ToList();
return result;
}
}
public bool InsertStudent(string Name, string Age,string Phone,string City,string Department,string UserId)
{
bool value;
using (OleDbConnection connection = Connector.Connect())
{
connection.Open();
List<StudentsModel> students = new List<StudentsModel>();
if (string.IsNullOrEmpty(Name) || string.IsNullOrEmpty(Age)||string.IsNullOrEmpty(Phone)|| string.IsNullOrEmpty(City))
{
value = false;
}
else
{
students.Add(new StudentsModel { Name = Name, Age= int.Parse(Age) ,Phone=Phone,City=City,Department=Department,UserId=int.Parse(UserId)});
connection.Execute("INSERT INTO [tbl_StudentInfo](Name,Age,Phone,City,Department,UserId) values(#Name,#Age,#Phone,#City,#Department,#UserId)", students);
value = true;
}
return value;
}
}
public bool DeleteStudent(int ID)
{
bool value;
using (OleDbConnection connection = Connector.Connect())
{
connection.Open();
List<StudentsModel> students = new List<StudentsModel>();
if (ID==0)
{
value = false;
}
else
{
students.Add(new StudentsModel { ID=ID});
connection.Execute("Delete From [tbl_StudentInfo] WHERE ID=#ID", students);
value = true;
}
return value;
}
}
}
}
and the error:
enter image description here
Rookie here needing help. I'm trying to build a prototype with the neo4j .NET driver using Bolt. My aim with the prototype is building multiple methods for creation and searches in the db, but only one method to connect to the db - here I'm continuously having problems. I've Googled all weekend for examples, tutorials and traversed through the documentation and now I need your help.
Programs.cs
using System;
using DTUneo4jConsoleApp.Db;
namespace DTUneo4jConsoleApp
{
public class Program
{
public static void Main(string[] args)
{
MyProperties something = new MyProperties();
neo4jdb session = new neo4jdb();
session.Run($"CREATE (a:Person {{name:'{something.Name}', title:'{something.Title}'}})");
var result = session.Run($"MATCH (a:Person) WHERE a.name = '{something.Name}' RETURN a.name AS name, a.title AS title");
foreach (var record in result)
{
Console.WriteLine($"{record["title"].As<string>()} {record["name"].As<string>()}");
}
Console.ReadKey();
}
}
public class MyProperties
{
public string Name { get; set; }
public string Title { get; set; }
}
}
db.cs
using Neo4j.Driver.V1;
namespace DTUneo4jConsoleApp.Db
{
public class neo4jdb
{
public static void Connection()
{
using (var driver = GraphDatabase.Driver("bolt://localhost", AuthTokens.Basic("user", "pass")))
using (var session = driver.Session())
{
}
}
}
}
When I instantiate the neo4jdb session = new neo4jdb(); I don't get i.e. the Run() method from the driver.
I hope someone can guide me in the right direction.
I am doing it like this:
public static List<IStatementResult> ExecuteCypher(List<Statement> statements)
{
List<IStatementResult> results = new List<IStatementResult>();
using (var driver = GraphDatabase.Driver("bolt://localhost", AuthTokens.Basic("user", "pass")))
{
using (var session = driver.Session())
{
using (var tx = session.BeginTransaction())
{
foreach (var statement in statements)
{
results.Add(tx.Run(statement));
}
tx.Success();
}
}
}
return results;
}
usage:
MyProperties something = new MyProperties();
var createCypher = new Statement($"CREATE (a:Person {{name:'{something.Name}', title:'{something.Title}'}})");
var matchCypher = new Statement($"MATCH (a:Person) WHERE a.name = '{something.Name}' RETURN a.name AS name, a.title AS title");
var statements = new List<Statement>();
statements.Add(createCypher);
statements.Add(matchCypher);
var results = ExecuteCypher(statements);
//you can now query result for each statement or
//your query your desired result
foreach (var record in results.Last())
{
Console.WriteLine($"{record["title"].As<string>()} {record["name"].As<string>()}");
}
In this way I can also create multiple records in a single transaction and get the result of all those as well.
Using SQLite, System.Data.SQLite and Dapper (in a Console Application; later Windows Service; high throughput); why "database is locked" is there anyway?
I even abstracted all calling to SQLite db in this method:
public static void LocalDbScope(Action<IDbConnection> action)
{
try
{
lock (DbLock)
{
using (var connection = Open(LocalStorageConnectionString))
{
action(connection);
}
}
}
catch (Exception xux)
{
ErrLog.Error(xux);
throw;
}
}
Turning on the memory-mapped option did not help either:
connection.Execute("PRAGMA wal_autocheckpoint=32; PRAGMA journal_size_limit = 2048;");
connection.Execute("PRAGMA mmap_size=" + GB);
And this is connection string:
var builder = new SQLiteConnectionStringBuilder
{
DataSource = storageDbFilePath,
FailIfMissing = false,
PageSize = 32 * KB,
CacheSize = 10 * MB,
ForeignKeys = false,
UseUTF16Encoding = false,
Pooling = true,
JournalMode = SQLiteJournalModeEnum.Wal,
SyncMode = SynchronizationModes.Normal,
DateTimeKind = DateTimeKind.Utc,
DateTimeFormat = SQLiteDateFormats.ISO8601,
DefaultIsolationLevel = IsolationLevel.ReadCommitted,
DefaultTimeout = (int)TimeSpan.FromMinutes(1).TotalMilliseconds
};
LocalStorageConnectionString = builder.ToString();
What am I missing here?
Note: When you google for "database is locked", all the top results (and whole first page) is about this problem in different programming languages and platforms. It seems there is something else about SQLite that I can not filter out of this picture.
As stated in my comment, I have NO idea what-so-ever, is going on without seeing more of your code.
Still, if you are not willing to change Dapper to Sqlite-net, below is a small non-blocking example, using your abstraction, which is not throwing any exceptions. Hope it helps you figure it out.
using System;
using System.Data;
using System.Data.SQLite;
using System.Linq;
using System.Threading;
using System.Threading.Tasks;
using Dapper;
namespace MyConsoleApplication
{
public class Program
{
static void Main(string[] args)
{
var test = new TestSQLite();
test.GoForIt();
}
}
public class Entity
{
public int Id { get; set; }
public string Content { get; set; }
}
public class TestSQLite
{
private const string ConnectionString = "Data Source=sqlitetest.sqlite";
private static readonly object DbLock = new object();
public void GoForIt()
{
CreateTable();
var random = new Random();
for (int i = 0; i < 100; i++)
{
if ( i % 2 != 0)
{
Task.Factory.StartNew(() => Thread.Sleep(random.Next(0, 200))).ContinueWith(other =>
LocalDbScope(action =>
{
var entity = new Entity {Content = "hoax"};
entity.Id = action.Query<int>(
#"insert into entity (content) values (#Content); select last_insert_rowid()",
entity).First();
var ids = action.Query<int>(#"select id from entity").ToList();
Console.WriteLine("Inserted id:{0}, all ids:[{1}]", entity.Id, string.Join(",", ids));
}));
}
else
{
Task.Factory.StartNew(() => Thread.Sleep(random.Next(200, 500))).ContinueWith(other =>
LocalDbScope(action =>
{
action.Execute(#"delete from entity");
Console.WriteLine("Deleted all entities");
}));
}
}
Console.ReadLine();
}
public static void LocalDbScope(Action<IDbConnection> action)
{
lock (DbLock)
{
using (var connection = new SQLiteConnection(ConnectionString))
action(connection);
}
}
private static void CreateTable()
{
using (IDbConnection c = new SQLiteConnection(ConnectionString))
{
c.Execute(#"drop table if exists entity");
c.Execute(#"create table entity (id integer primary key autoincrement, content varchar(100))");
}
}
}
}
I need to write a script which merges a list with a dictionary to create a third dictionary. I'm pretty new to programming and am struggling with the basics here.
So far I've created the following class which generates a list of dates. I have another class which generates a dictionary and I want to basically create a third dictionary which contains the dates and data which do not exist already in the first list.
Any ideas how I should do this? Thanks.
class StartList: IDisposable
{
private readonly string[] names = new[] { "name1", "name2", "name3"};
private SqlConnection conn;
private Dictionary<string, List<DateTime>> startData = new Dictionary<string, List<DateTime>>();
public StartList()
{
this.conn = new SqlConnection(ConfigurationManager.ConnectionStrings["NameCon"].ConnectionString);
this.conn.Open();
}
private void Dispose()
{
if (this.conn != null)
{
if (this.conn.State != ConnectionState.Closed)
{
try
{
this.conn.Close();
}
catch
{
}
}
this.conn.Dispose();
this.conn = null;
}
}
public void ImportStartData()
{
foreach (string name in this.names)
{
this.startData.Add(name, this.ImportStartData(name));
}
}
public List<DateTime> ImportStartData(string name)
{
List<DateTime> result = new List<DateTime>();
string sqlCommand = string.Format("SELECT * FROM {0}_Index ", name);
using (SqlCommand cmd = new SqlCommand(sqlCommand, this.conn))
{
cmd.CommandType = CommandType.Text;
using (SqlDataReader reader = cmd.ExecuteReader())
{
while (reader.Read())
{
result.Add(reader.GetDateTime(0));
}
}
}
return result;
}
}
First you need to modify the below code block
From:
public void ImportStartData()
{
foreach (string name in this.names)
{
this.names.Add(name, this.ImportStartData(name));
}
}
To:
public void ImportStartData()
{
foreach (string name in this.names)
{
if(!startData.ContainsKey(name)) //If this check is not done, then Dictionary will throw, duplicate key exception.
{
this.startData.Add(name, this.ImportStartData(name));
}
}
}
Anyway, the better approach would be, if possible first read the name as well as Date from database, possibly into a DataTable and then using LINQ/foreach loop, group the results by name.