Exiting While Loop - mysql

I am trying to read values from a MySql database and check whether the id that needs to be updated, already exists in database or not. I have been able to make everything else in the program work except the part of checking database. Here is some of my code:
public void updateStatement() throws SQLException{
try
{
connnectDatabse();
}
catch (ClassNotFoundException e)
{
System.out.println("Could not connect to database..");
}
System.out.println("How many entries would you like to update?");
kb=new Scanner(System.in);
int numEntries = kb.nextInt();
int counter =0;
String newName=null, newDepartment =null;
int newSalary=0, newId =0;
int counterValues =0;
while(counterValues != numEntries){
System.out.println("Please enter 5 to view current entries in database\n");
selectStatement();
int idToUpdate =0;
boolean idVerify =false;
//Check if the user id exists in database or not
while(!(idVerify)){
System.out.println("\nPlease enter the ID of the record to update");
idToUpdate = kb.nextInt();
idFoundInDatabase(idArrayList, idToUpdate);
}
System.out.println("Please choose the number of column to update from below options.\n1.ID\n2.Name\n3.Salary\n4.Department");
int columnToUpdate = kb.nextInt();
switch(columnToUpdate){
case 1:
System.out.println("What will be the new id value for the selected ID?");
newId = kb.nextInt();
query = "update employee set ID = ? where ID = ?";
break;
case 2:
System.out.println("What will be the new name for the selected ID?");
newName = kb.next();
query = "update employee set Name = ? where ID = ?";
break;
case 3:
System.out.println("What will be the new salary for the selected ID?");
newSalary = kb.nextInt();
query = "update employee set Salary = ? where ID = ?";
break;
case 4:
System.out.println("What will be the new department for the selected ID?");
newDepartment = kb.next();
query = "update employee set Department = ? where ID = ?";
break;
default:
System.out.println("Correct option not chosen");
}
PreparedStatement st = conn.prepareStatement(query);
if(columnToUpdate ==1){
st.setInt(1, newId);
st.setInt(2, idToUpdate);
}
else if(columnToUpdate ==2){
st.setString(1, newName);
st.setInt(2, idToUpdate);
}
else if(columnToUpdate ==3){
st.setInt(1, newSalary);
st.setInt(2, idToUpdate);
}
else{
st.setString(1, newDepartment);
st.setInt(2, idToUpdate);
}
//execute the prepared statement
st.executeUpdate();
System.out.println("Record successfully updated..");
counterValues++;
}
}
//Code that I am unable to exit. This is
a separate method outside of updateStatement() method.
ArrayList contains the list of ids that are already in the database. ArrayList has been populated successfully.
public boolean idFoundInDatabase(ArrayList<String> arrayList, int id){
boolean validId = false;
while(validId == true){
String idRead = String.valueOf(id);
for (int i=0; i<arrayList.size(); i++){
String elementRead =arrayList.get(i);
if(elementRead.equals(idRead)){
validId = true;
break;
}
else{
validId= false;
}
}
}
return validId;
}
}
If required I am also posting the lines of code where I get the result set to make the array list of ids.
while(result.next()){
String id =result.getString("ID");
idArrayList.add(id);
if(choice == 1 || choice == 2 || choice == 3 || choice == 4){
resultIs = result.getString(columnName);
System.out.println(resultIs);
}
else{
System.out.println(result.getString("ID")+"\t"+result.getString("Name")+
"\t"+result.getString("Salary")+"\t"+result.getString("Department") );
}
}
Problem is exiting the above idFoundInDatabase method. It identifies if the id which user wants to update is in the database or not. On finding even the correct id which exists in the database, it just keeps on reading the values in array list, instead of going to return statement. Am I also doing something wrong where I call this method? Any help will be appreciated. Have been stuck on it for almost a day now. Have done debugging many many times. I am doing this just to get acquainted with jdbc and parameterized queries, so that I can follow the similar thing in a bigger project.Any help is appreciated. Thank You.

A few things:
Your while loop inside of idFoundInDatabase() is not necessary - one simple iteration through the for loop over arrayList is enough.
You are returning a boolean value from that function, but your calling method does not capture and use it, so idVerify is never being changed from false to true, so your input loop repeats forever.
All you need to do sort that out is change idFoundInDatabase(idArrayList, idToUpdate); to idVerify = idFoundInDatabase(idArrayList, idToUpdate); and then your input loop should successfully terminate when a valid id is found.

Related

How to Parse the Text file in SSIS

Iam new to SSIS , Iam facing the below issue while parsing a text file which contains the below sample data
Below is the requirement
-> Need to Capture the number after IH1(454756567) and insert into one column as
InvoiceNumber
-> Need to insert the data between ABCD1234 to ABCD2345 into another column as
TotalRecord .
Many thanks for the help .
ABCD1234
IH1 454756567 686575634
IP2 HJKY TXRT
IBG 23455GHK
ABCD2345
IH1 689343256 686575634
IP2 HJKY TXRT
IBG 23455GHK
ABCD5678
This is the script component to process the entire file. You need to create your output and they are currently being processed as strings.
This assumes your file format is consistent. If you don't have 2 columns in IH1 and IP2 ALL the time. I would recommend a for loop from 1 to len -1 to process. And send the records to their own output.
public string recordID = String.Empty;
public override void CreateNewOutputRows()
{
string filePath = ""; //put your filepath here
using (System.IO.StreamReader sr = new System.IO.StreamReader(filePath))
{
while (!sr.EndOfStream)
{
string line = sr.ReadLine();
if (line.Substring(0, 4) == "ABCD") //Anything that identifies the start of a new record
// line.Split(' ').Length == 1 also meets your criteria.
{
recordID = line;
Output0Buffer.AddRow();
Output0Buffer.RecordID = line;
}
string[] cols = line.Split(' ');
switch (cols[0])
{
case "IH1":
Output0Buffer.InvoiceNumber = cols[1];
Output0Buffer.WhatEverTheSecondColumnIs = cols[2];
break;
case "IP2":
Output0Buffer.ThisRow = cols[1];
Output0Buffer.ThisRow2 = cols[2];
break;
case "IBG":
Output0Buffer.Whatever = cols[1];
break;
}
}
}
}
You'll need to do this in a script component.

MySQL Query crashes my program even when in try statement

It errors out when the record couldn't be found Cannot read property 'id' of undefined
How can I keep it from crashing out and handle "undefined"?
let blacklisted = false;
let conStr = "SELECT * FROM `blacklist` WHERE `id` = '"+message.author.id+"'";
con.query(conStr, function(error, result, field) {
console.log(result[0].id);
if(result[0].id){
console.log("Van")
blacklisted = false;
}
});
if (message.author.id !== "397487086522990602" && blacklisted){/*Actual Code*/}
I believe you should add proper checks. Try catch is basically for connection/ query execution related failure not for if data not returned.
So just add check if result[0] exists.
Hence folowing code should serve your purpose:
let blacklisted = false;
let conStr = "SELECT * FROM `blacklist` WHERE `id` = '"+message.author.id+"'";
con.query(conStr, function(error, result, field) {
if(result[0] && result[0].id){ // add check for result[0]
console.log("Van")
blacklisted = false;
}
});
if (message.author.id !== "397487086522990602" && blacklisted){/*Actual Code*/}

In MVC, pass complex query and view model to session?

I have a view model:
public class UserCollectionView
{
public CardCollection CardCollections { get; set; }
public Card Cards { get; set; }
}
I have a List View Controller:
public ActionResult ViewCollection(int? page)
{
var userid = (int)WebSecurity.CurrentUserId;
var pageNumber = page ?? 1;
int pageSize = 5;
ViewBag.OnePageOfCards = pageNumber;
if (Session["CardCollection"] != null)
{
var paging = Session["CardCollection"].ToString.();
return View(paging.ToPagedList(pageNumber, pageSize));
}
var viewModel = from c in db.Cards
join j in db.CardCollections on c.CardID equals j.CardID
where (j.NumberofCopies > 0) && (j.UserID == userid)
orderby c.Title
select new UserCollectionView { Cards = c, CardCollections = j };
Session["CardCollection"] = viewModel;
return View(viewModel.ToPagedList(pageNumber, pageSize));
I am trying to use the PagedList to add paging to the results. I have been able to do this when I am not using a query that returns data from 2 databases in a single view. As shown here
My end result looks something like this:
Cards.SeveralColumns CardCollections.ColumnA CardCollections.ColumnB
Row 1 Data from Cards Table A from CardCollections B from CardCollections
Row 2 Data from Cards Table A from CardCollections B from CardCollections
Row 3 Data from Cards Table A from CardCollections B from CardCollections
And so on... I get an error
The ObjectContext instance has been disposed and can no longer be used for operations that require a connection.
I have tried variations of SQL statements but can't get it to fit with my view model. In SQL Management Studio this brings back the correct results
Select * from Cards Inner Join CardCollections On Cards.CardID = CardCollections.CardID where CardCollections.UserID = 1 and CardCollections.NumberofCopies > 0;
I need a way to pass the query in session so the paging will operate correctly. Any advice is appreciated. :)
Short answer is, you can't. The model needs to be a snapshot of the content and therefore you can't pass an open query across the boundary (either as a hand-off to a session or to the client directly).
What you're seeing is the disposal of the context beyond it's initial use (where you assemble var viewmodel).
With that said, you can cache the results (to save overhead) if querying the data is an expensive operation. Basically, you'd store the entire collection (or at least a large subset of the collection) in the session/memorycache (which can then be manipulated into a paged list). Something to the effect of:
public ActionResult ViewCollection(int? page)
{
var userId = (int) WebSecurity.CurrentUserId;
var pageNumber = page ?? 1;
var pageSize = 5;
ViewBag.OnePageOfCards = pageNumber;
var cacheKey = String.Format("ViewCollection[{0}]", userId);
var entities = GetOrCreateCacheItem<IEnumerable<UserCollectionView>>(cacheKey, () => {
var query = (from c in db.Cards
join j in db.CardCollections on c.CardID equals j.CardID
where (j.NumberofCopies > 0) && (j.UserID == userid)
orderby c.Title
select new UserCollectionView { Cards = c, CardCollections = j }
)
.ToList(); // Force fetch from Db so we can cache
});
return View(entities.ToPagedList(pageNumber, pageSize));
}
// To give an example of a cache provider; Feel free to change this,
// abstract it out, etc.
private T GetOrCreateCacheItem<T>(string cacheKey, Func<T> getItem)
{
T cacheItem = MemoryCache.Default.Get(cacheKey) as T;
if (cacheItem == null)
{
cacheItem = getItem();
var cacheExpiry = DateTime.Now.AddMinutes(5);
MemoryCache.Default.Add(cacheKey, cacheItem, cacheExpiry);
}
return cacheItem;
}
It turns out that I didn't need to pass the query at all. If I let it run through it works fine without the session. I am not really sure why this works but my search query has to be passed. Maybe it is because I am using a viewmodel to perform the query. I will experiment and post if I find anything. Currently the working code is:
public ActionResult ViewCollection(int? page)
{
var userid = (int)WebSecurity.CurrentUserId;
var pageNumber = page ?? 1;
int pageSize = 5;
ViewBag.OnePageOfCards = pageNumber;
ViewBag.Rarity_ID = new SelectList(db.Rarities, "RarityID", "Title");
ViewBag.MainType_ID = new SelectList(db.MainTypes, "MainTypeID", "Title");
ViewBag.CardSet_ID = new SelectList(db.CardSets, "CardSetID", "Title");
ViewBag.SubType_ID = new SelectList(db.SubTypes, "SubTypeID", "Title");
var viewModel = from c in db.Cards
join j in db.CardCollections on c.CardID equals j.CardID
where (j.NumberofCopies > 0) && (j.UserID == userid)
orderby c.Title
select new UserCollectionView { Cards = c, CardCollections = j };
return View(viewModel.ToPagedList(pageNumber, pageSize));

Node.JS String encoding issues

I'm writing a sort of interface between a TCP Chat server and an SQL Server, and while working on a part where a user submits a value and is assigned a named pulled from a row in this DB with this value. When querying this DB with a value from a telnet shell, I can't get any results from the DB. But I can when I perform the same query in adminer/MySQL # BASH etc...
My thoughts are that it has come down to an encoding issue. Being rather noobish to node, I don't really know what to do. I do have a pretty good experience with JavaScript, just not node.
Code
function setCliNameOrKick(client, key){
key = String(key).replace(/\n\r\b\\\s/gi, "");
var q = "SELECT username FROM webusers WHERE lic = \'"+String(key).toString()+"\'; --";
console.log(key);
query(q);
cli.query(q, function cb(e, r, f){
if(client != null){
console.log(r);
if(r.length >= 1){
client.name = r['username'];
}else{
client.stream.end();
}
}else{
console.log("Was Passed A Null Client!");
}
});
}
That comes from the DB query tool
It takes input from a string sent by the client on connect, alongside an object representing the client
stream.addListener("data", function(data){
if(client.name == null){
data = String(data).replace(new RegExp("[\n]+", "g"), "");
cNameBuff = cNameBuff + data;
if(cNameBuff.length > 1){ //Min Length
//client.name = cNameB;
db.set(client, cNameBuff);
onAuth(client);
}
return;
}
data = String(data);
if(data.length >= 2){
srv.procChat(client, data);
}
});

Entity Framework SaveChanges function won't commit my changes

I have an initial selection which I place into list. I use the list to loop through each record and where it meets certain criteria I run trough a series of inserts, deletes and updates. Finally call the SaveChanges() method to commit changes.
The code runs through without raising an exception but no changes reflect in the database. I have been searching the web with no luck.
I'm using VS2008 with SQL2008 backend.
Please help?
using (SMSEntities db = new SMSEntities())
{
try
{
//Get SMS's to send from Inbox
List<Inbox> tmpInbox = (from c in db.Inboxes where c.Status != "NEW" && c.Status != "SUCCESS" select c).ToList();// new { Inbox.InboxID, Inbox.StatusTrackingID, Inbox.Status, Inbox.NoOfAttempts, Inbox.CellNo, Inbox.SourceCellNo, Inbox.Header, Inbox.Message, Inbox.MessageDate, Inbox.AccountID, Inbox.LastAttemptDate }).ToList();
foreach (Inbox tmpInboxIndex in tmpInbox)
{
bool success = false;
//Check status here
string SentStatus = CheckSMSSentToProvider(tmpInboxIndex.StatusTrackingID);
// Define a transaction scope for the operations.
using (TransactionScope transaction = new TransactionScope())
{
try
{
if ((SentStatus == "DELIVERED") || (SentStatus == "NOTFOUND") || (SentStatus == "DELETED") || (SentStatus == "REJECTED") || (SentStatus == "UNDELIVERED"))
{
//Insert the Log row
Log newLog = new Log();
newLog.InboxID = tmpInboxIndex.InboxID;
newLog.CellNo = tmpInboxIndex.CellNo;
newLog.SourceCellNo = tmpInboxIndex.SourceCellNo;
newLog.Message = tmpInboxIndex.Message;
newLog.Header = tmpInboxIndex.Header;
newLog.MessageDate = tmpInboxIndex.MessageDate;
newLog.AccountID = tmpInboxIndex.AccountID;
newLog.ProcessedDate = DateTime.Now;
newLog.Status = tmpInboxIndex.Status;
newLog.StatusTrackingID = tmpInboxIndex.StatusTrackingID;
newLog.NoOfAttempts = tmpInboxIndex.NoOfAttempts;
newLog.LastAttemptDate = tmpInboxIndex.LastAttemptDate;
db.Logs.AddObject(newLog);
//Delete the Inbox row
if (tmpInbox != null)
{
var deleteInbox = (from c in db.Inboxes where c.InboxID == tmpInboxIndex.InboxID select c).FirstOrDefault();
if (deleteInbox != null)
{
db.DeleteObject(deleteInbox);
//db.SaveChanges(SaveOptions.DetectChangesBeforeSave);
}
}
}
else
{
//Update inbox status
var tmpUpdateInbox = (from c in db.Inboxes where c.InboxID == tmpInboxIndex.InboxID select c).FirstOrDefault();
tmpUpdateInbox.Status = SentStatus;
tmpUpdateInbox.NoOfAttempts = tmpInboxIndex.NoOfAttempts + 1;
tmpUpdateInbox.LastAttemptDate = DateTime.Now;
//db.SaveChanges(SaveOptions.DetectChangesBeforeSave);
}
// Mark the transaction as complete.
transaction.Complete();
success = true;
//break;
}
catch (Exception ex)
{
// Handle errors and deadlocks here and retry if needed.
// Allow an UpdateException to pass through and
// retry, otherwise stop the execution.
if (ex.GetType() != typeof(UpdateException))
{
Console.WriteLine("An error occured. "
+ "The operation cannot be retried."
+ ex.Message);
break;
}
// If we get to this point, the operation will be retried.
}
}
if (success)
{
// Reset the context since the operation succeeded.
//db.AcceptAllChanges();
db.SaveChanges();
}
}
// Dispose the object context.
db.Dispose();
}
catch (Exception exp)
{
throw new Exception("ERROR - " + exp.Message.ToString(), exp);
}
}
return true;
Regards,
GPR.
Are you using a local database file? You may be looking for changes in the wrong place. By default, when the program starts, VS copies the database file into the debug or release folder. Then the program runs and changes are made, and saved, to the file in the debug or release folder. The program ends, and when you look at the database in your source folder it looks the same. You can change the connection string in the app.config to use an absolute path to avoid this.
See http://blogs.msdn.com/b/smartclientdata/archive/2005/08/26/456886.aspx for more info
The TransactionScope is useless if you do not put the call to SaveChanges into it.
Either move the call to SaveChanges into it or remove the TransactionScope completely.