android.database.sqlite.SQLiteException: no such column: user_id (code 1 SQLITE_ERROR): - database

being an Android Studio beginner i tend to get lots and lots of tiny errors i cannot find out, please let me know what I am doing wrong because I've tried all the other answers somehow and it doesn't get better :)
public class DatabaseHelper extends SQLiteOpenHelper{
private static final int DATABASE_VERSION = 1;
private static final String DATABASE_NAME = "UserManager.db";
private static final String TABLE_USER = "user";
private static final String COLUMN_USER_ID= "user_id";
private static final String COLUMN_USER_NAME= "user_name";
private static final String COLUMN_USER_EMAIL= "user_email";
private static final String COLUMN_USER_PASSWORD= "user_password";
private String CREATE_USER_TABLE = "CREATE TABLE " + TABLE_USER + "(" +
COLUMN_USER_ID + " INTEGER PRIMARY KEY AUTOINCREMENT, "
+ COLUMN_USER_NAME + " TEXT," + COLUMN_USER_EMAIL + " TEXT," +
COLUMN_USER_PASSWORD + " TEXT" + ")";
private String DROP_USER_TABLE = " DROP TABLE IF EXISTS " + TABLE_USER;
public DatabaseHelper(Context context){
super(context, DATABASE_NAME,null, DATABASE_VERSION);
}
#Override
public void onCreate(SQLiteDatabase db){
db.execSQL(CREATE_USER_TABLE);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion){
db.execSQL(DROP_USER_TABLE);
onCreate(db);
}
public void addUser(User user){
SQLiteDatabase db= this.getWritableDatabase();
ContentValues values = new ContentValues();
values.put(COLUMN_USER_NAME, user.getName());
values.put(COLUMN_USER_EMAIL, user.getEmail());
values.put(COLUMN_USER_PASSWORD, user.getPassword());
db.insert(TABLE_USER,null, values);
db.close();
}
public boolean checkUser(String password, String email){
String[] columns = {
COLUMN_USER_ID
};
SQLiteDatabase db= this.getWritableDatabase();
String selection = COLUMN_USER_EMAIL + " = ? " + "AND "+ COLUMN_USER_PASSWORD+" =? ";
String[] selectionArgs = { email,password };
Cursor cursor = db.query(TABLE_USER,
columns,
selection,
selectionArgs,
null,
null,
null);
int cursorCount = cursor.getCount();
cursor.close();
db.close();
if(cursorCount > 0){
return true;
}
return false;
}
}
I know the logcat let me know this:
07-11 22:08:29.072 9071-9071/com.example.lavinia.sqllogin E/AndroidRuntime:
FATAL EXCEPTION: main
Process: com.example.lavinia.sqllogin, PID: 9071
android.database.sqlite.SQLiteException: no such column: user_id (code 1
SQLITE_ERROR): , while compiling: SELECT user_id FROM user WHERE user_email =
?AND user_password =?
And I can't find the wrong usage of user_id, I think I used it fine and the app will stop working after I Login myself. (the app has login and registration activities- and the registration works ok, but pressing the Login button in the Login.activity will make the app crash)
Thank you very much for you support :) If needed, I will provide with further code.

This issue is probably due to i tend to get lots and lots of tiny errors in conjunction with a common misconception regarding the onCreate method.
The onCreate method automatically runs only once when the database is and has actually been created. It does not run every time the App is run.
As such any changes (corrections included) to the structure (tables and columns) will not be applied if they are coded/actioned within the onCreate method.
When developing the easiest fix is to do one of the following 3:-
delete the App's data (deletes the database so onCreate will be called).
uninstall the App (deletes the database so onCreate will be called).
if the onUpgrade method will drop the table(s) and then call onCreate , to increase the database version number as passed as the 4th parameter to the SQLIteOpenHelper sub-class (aka the DatabaseHelper class).
After doing one of the above, rerun the App.
NOTE any existing data will be lost.
If data has to be retained then a fix is more complicated but would be based upon using ALTER TABLE statements.

Related

Null pointer exception when inserting data into Android SQLite Database

I'm just starting an Android Studio project and Ive created a small player database and I have been trying to add player details into the database. However each time the program crashes with a null pointer exception. A quick debgug suggests the problem is with the call to the OnClickListener in the OnCreate method. What changes need to be made to the code? Thanks
public class DatabaseHelper {
// Declare instance of DBHelper class, context and SQLiteDatabase
private DBHelper ourDbHelper;
private final Context ourContext;
private SQLiteDatabase myDb;
// Initialise the database and table names and version
private static final String DATABASE_NAME = "Club";
private static final String PLAYER_TABLE_NAME = "Players";
//Initialise the PLAYER_TABLE_NAME field names
private static final String PLAYER_ID = "player_id";
private static final String PLAYER_SURNAME = "player_surname";
private static final String PLAYER_FORENAME = "player_forename";
private static final String PLAYER_AGE = "player_age";
private static final String PLAYER_DOB = "player_dob";
private static class DBHelper extends SQLiteOpenHelper {
// This constructor takes the context, db name and db version as
parameters
// and applies them to the DBHelper class
public DBHelper(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
}
// This constructor takes context as parameter and assigns it to
variable
#Override
public void onCreate(SQLiteDatabase db) {
//Executes the following queries to create the Player Table
db.execSQL("CREATE TABLE " + PLAYER_TABLE_NAME + " (" + PLAYER_ID
+ " INTEGER PRIMARY KEY AUTOINCREMENT, "
+ PLAYER_FORENAME + "TEXT NOT NULL, " + PLAYER_SURNAME +
"TEXT NOT NULL, " +
PLAYER_AGE + " INTEGER NOT NULL, " + PLAYER_DOB + "DATE
NOT NULL );");
}//OnCreate
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int
newVersion) {
// if table is upgraded or already exists
db.execSQL("DROP TABLE IF EXISTS " + PLAYER_TABLE_NAME);
onCreate(db);
}//OnUpgrade
}//DBHelperClass
// Constructor takes a context as a parameter and assigns it to
ourContext
public DatabaseHelper (Context c){
ourContext = c;
}//constructor
// Open writable database and allow to be modified
public DatabaseHelper open() throws SQLException {
ourDbHelper = new DBHelper(ourContext);
myDb = ourDbHelper.getWritableDatabase();
return this;
}//open
//method to close the db to modification
public void close() {
ourDbHelper.close();
}//close
// method to create an entry to the Player table with player attributes as parameters
public long createEntry (String forename, String surname, String age, String dob){
//contentValues will hold the information to be added to the database
ContentValues contentValues = new ContentValues();
//Using put method, insert the parameters into the fields in the table
contentValues.put(PLAYER_FORENAME, forename);
contentValues.put(PLAYER_SURNAME, surname);
contentValues.put(PLAYER_AGE,age);
contentValues.put(PLAYER_DOB, String.valueOf(dob));
//insert the values into the player table
//assign to variable result to check if data added correctly
return myDb.insert(PLAYER_TABLE_NAME,null,contentValues);
}//createEntry
Here is the AddPlayer activity class
public class AddPlayer extends Activity implements View.OnClickListener {
//declare variables
Button confirmAdd;
EditText editSurname, editForename, editAge, editDOB;
#Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.add_player_activity);
//Initialise variables
editForename = (EditText) findViewById(R.id.editPlayerForename);
editSurname = (EditText) findViewById(R.id.editPlayerSurname);
editAge = (EditText) findViewById(R.id.editPlayerAge);
editDOB = (EditText) findViewById(R.id.editPlayerDOB);
confirmAdd = (Button) findViewById(R.id.addPlayerBtn);
//set onclicklisteners
confirmAdd.setOnClickListener(this);
}
#Override
public void onClick(View v) {
String forename = editForename.getText().toString();
String surname = editSurname.getText().toString();
String age = editAge.getText().toString();
String dob = editDOB.getText().toString();
DatabaseHelper myDb = new DatabaseHelper(AddPlayer.this);
myDb.open();
myDb.createEntry(forename, surname, age, dob);
Toast.makeText(AddPlayer.this, "Data Inserted", Toast.LENGTH_LONG).show();
}
Change this
DatabaseHelper myDb = new DatabaseHelper(AddPlayer.this);
myDb.open()
To
DatabaseHelper myDb = new DatabaseHelper(this.getContext());
myDb.open();

How to fix 'database.CursorIndexOutOfBoundsException: Index 0 requested, with a size of 0'?

I am setting up a database with Android SQLite for my weight_activity with a dialog. In that Activity I save the current weight and I want to request the saved value for the current weight when starting the activity to display it.
The Error I get is:
java.lang.RuntimeException: Unable to start activity ComponentInfo{com.example.thisfit/com.example.thisfit.Weight_Activity}: android.database.CursorIndexOutOfBoundsException: Index 0 requested, with a size of 0
Caused by: android.database.CursorIndexOutOfBoundsException: Index 0 requested, with a size of 0
at android.database.AbstractCursor.checkPosition(AbstractCursor.java:460)
This is the code that requests the current weight in my activity class
public void getCurrentWeightAsFloat() {
textView_currentWeight.setText(String.valueOf(weight_dbHandler.getCurrentWeight()));
} //public void getCurrentWeightAsFloat()
This is the whole database code. I post this because I don't know, if the problem could be in another section of the code and not just the method getCurrentWeight():
public class Weight_Database extends SQLiteOpenHelper {
//region Attributes
private static final String TAG = "weight_database";
private static final int DATABASE_VERSION = 1;
private static final String DATABASE_NAME = "weight_database.db";
private static final String TABLE_NAME = "weight_table";
private static final String COL1 = "ID";
private static final String COL2 = "Weight";
private static final String COL3 = "Date";
//endregion
//region Constructors
public Weight_Database(Context context) {
super(context, DATABASE_NAME, null, DATABASE_VERSION);
// SQLiteDatabase db = this.getWritableDatabase();
}
//endregion
//region Methods
#Override
public void onCreate(SQLiteDatabase db) {
String createTable = "CREATE TABLE " + TABLE_NAME
+ " (ID INTEGER PRIMARY KEY AUTOINCREMENT, "
+ COL2 + " FLOAT, "
+ COL3 + " DATE )";
db.execSQL(createTable);
}
#Override
public void onUpgrade(SQLiteDatabase db, int oldVersion, int newVersion) {
db.execSQL("DROP TABLE IF EXISTS " + TABLE_NAME);
onCreate(db);
}
public boolean addNewCurrentWeightAsFloat(float newCurrentWeightAsFloat){
SQLiteDatabase db = this.getWritableDatabase();
ContentValues contentValues = new ContentValues();
contentValues.put(COL2, newCurrentWeightAsFloat);
Log.d(TAG, "addWeight: Adding " + newCurrentWeightAsFloat + " to " + TABLE_NAME);
long result = db.insert(TABLE_NAME, null, contentValues);
//if date as inserted incorrectly it will return -1
if (result == -1){
return false;
} else {
return true;
}
} //public boolean addNewCurrentWeightAsFloat(String newCurrentWeightAsFloat)
public float getCurrentWeight(){
SQLiteDatabase db = this.getWritableDatabase();
String query = "SELECT Weight FROM " + TABLE_NAME + " ORDER BY ID DESC LIMIT 1";
Cursor data = db.rawQuery(query, null);
data.moveToFirst();
float currentWeightAsFloat = data.getFloat(data.getColumnIndex("content"));
return currentWeightAsFloat;
} //public float getCurrentWeight()
//Returns the whole table as a raw query
public Cursor getData(){
SQLiteDatabase db = this.getWritableDatabase();
String query = "SELECT * FROM " + TABLE_NAME;
Cursor data = db.rawQuery(query, null);
return data;
} //public Cursor getData()
//endregion
} //class Weight_Database
I expect to get the latest weight entered by selecting the ID DESCending with a Limit of 1.
I want to get this float of my current weight and display it in a textView afterwards.
Have a nice day and thanks in advance :)
Your table has no data.
You should check the return values of data.moveToFirst() and only try to call getFloat() on the cursor in case it returned true.

SQLite Database is not working after standalone build in Unity3D

I am trying to make a Standalone Application using SQLite in Unity3D,
I am getting a strange problem.
I created a database using sqliteadmin, and created a Table named Admin, having field: id, email, password.
I am able to Login using email and password but in Unity Edit Mode.
Its working fine but when i build it and then run it, its not working, I have no idea why?
Reference
Here is my code:
using UnityEngine;
using System.Collections;
using Mono.Data.Sqlite;
using System.Data;
using System;
using UnityEngine.UI;
public class DatabaseConnection : MonoBehaviour {
public Text em;
public Text pas;
public static int id;
public static string email ="";
public static string password="";
public static string wrong="Wrong Email/Password !!!";
public Text Wrong;
public GameObject loading;
private ButtonsController bc;
public GameObject loginPanel;
void Start () {
string conn = "URI=file:" + Application.dataPath + "/Database/TMDB.s3db";
IDbConnection dbconn;
dbconn = (IDbConnection)new SqliteConnection (conn);
dbconn.Open ();
IDbCommand dbcmd = dbconn.CreateCommand ();
string sqlQuery = "SELECT id, email, password " + "FROM Admin";
dbcmd.CommandText = sqlQuery;
IDataReader reader = dbcmd.ExecuteReader ();
while (reader.Read()) {
id = reader.GetInt32 (0);
email = reader.GetString(1);
password = reader.GetString(2);
}
reader.Close ();
reader = null;
dbcmd.Dispose ();
dbcmd = null;
dbconn.Close ();
dbconn = null;
loading.SetActive (false);
}
public void login()
{
if ((em.text == email) && (pas.text == password)) {
Debug.Log ("Success");
loading.SetActive (true);
loginPanel.SetActive(false);
Application.LoadLevel(1);
} else {
Debug.Log ("Error");
Wrong.text = wrong.ToString ();
}
}
}
Application.datapath is readonly.
What you need is Application.persistentDataPath
Checkout this link
http://answers.unity3d.com/questions/209108/when-to-use-persistentdatapath-versus-datapath.html
Create StreamingAssets folder into your Assets, and use this connection string:
string conn = "URI=file:" +
System.IO.Path.Combine(Application.streamingAssetsPath, "Database/TMDB.s3db");
Using streaming asset is necessary, it places files into the normal filesystem on the target machine to make them accessible via a pathname.
More info:
https://docs.unity3d.com/Manual/StreamingAssets.html
dude ,,, just check the files bro,,, after building the database is empty so go and replace the database file with the one u been working on with the same database name .

Insert CSV using Apex Batch Class Salesforce for OpportunityLineItem

I want to add a button to my opportunity header record that is called Insert Products. This will send the opportunity ID to a visualforce page which will have a select file button and an insert button that will loop through the CSV and insert the records to the related opportunity.
This is for non technical users so using Data loader is not an option.
I got this working using standard apex class however hit a limit when i load over 1,000 records (which would happen regularly).
I need to convert this to a batch process however am not sure how to do this.
Any one able to point me in the right direction? I understand a batch should have a start, execute and finish. However i am not sure where i should split the csv and where to read and load?
I found this link which i could not work out how to translate into my requirements: http://developer.financialforce.com/customizations/importing-large-csv-files-via-batch-apex/
Here is the code i have for the standard apex class which works.
public class importOppLinesController {
public List<OpportunityLineItem> oLiObj {get;set;}
public String recOppId {
get;
// *** setter is NOT being called ***
set {
recOppId = value;
System.debug('value: '+value);
}
}
public Blob csvFileBody{get;set;}
public string csvAsString{get;set;}
public String[] csvFileLines{get;set;}
public List<OpportunityLineItem> oppLine{get;set;}
public importOppLinesController(){
csvFileLines = new String[]{};
oppLine = New List<OpportunityLineItem>();
}
public void importCSVFile(){
PricebookEntry pbeId;
String unitPrice = '';
try{
csvAsString = csvFileBody.toString();
csvFileLines = csvAsString.split('\n');
for(Integer i=1;i<csvFileLines.size();i++){
OpportunityLineItem oLiObj = new OpportunityLineItem() ;
string[] csvRecordData = csvFileLines[i].split(',');
String pbeCode = csvRecordData[0];
pbeId = [SELECT Id FROM PricebookEntry WHERE ProductCode = :pbeCode AND Pricebook2Id = 'xxxx HardCodedValue xxxx'][0];
oLiObj.PricebookEntryId = pbeId.Id;
oLiObj.Quantity = Decimal.valueOf(csvRecordData[1]) ;
unitPrice = String.valueOf(csvRecordData[2]);
oLiObj.UnitPrice = Decimal.valueOf(unitPrice);
oLiObj.OpportunityId = 'recOppId';;
insert (oLiObj);
}
}
catch (Exception e)
{
ApexPages.Message errorMessage = new ApexPages.Message(ApexPages.severity.ERROR, e + ' - ' + unitPrice);
ApexPages.addMessage(errorMessage);
}
}
}
First problem that I can sense is that the insert DML statement is inside FOR-loop. Can you put the new "oLiObj" into a List that is declared before the FOR-loop starts and then try inserting the list after the FOR-loop ?
It should bring some more sanity in your code.

eBay API, get globalID from numerical Site ID

As the title says, I have the numerical Site ID, I need a way to get the corresponding GlobalId.
I know there are tables with matches
https://developer.ebay.com/DevZone/merchandising/docs/CallRef/Enums/GlobalIdList.html
https://developer.ebay.com/DevZone/merchandising/docs/Concepts/SiteIDToGlobalID.html
but I need a programmatic way to do it.
Your three options:
Hash Map implementation
import java.util.HashMap;
public class Mappings{
public static void main(String []args){
HashMap myMap = new HashMap<Integer, String>();
myMap.put(0, "EBAY-US");
myMap.put(2, "EBAY-ENCA");
myMap.put(3, "EBAY-GB");
myMap.put(15, "EBAY-AU");
//...
System.out.println("Given ID 15, it's corresponding Global ID is: " + myMap.get(15));
}
}
SQL Table implementation
//STEP 1. Import required packages
import java.sql.*;
public class JDBCExample {
// JDBC driver name and database URL
static final String JDBC_DRIVER = "com.mysql.jdbc.Driver";
static final String DB_URL = "jdbc:mysql://localhost/STUDENTS";
// Database credentials
static final String USER = "username";
static final String PASS = "password";
public static void main(String[] args) {
Connection conn = null;
Statement stmt = null;
try{
//STEP 2: Register JDBC driver
Class.forName("com.mysql.jdbc.Driver");
//STEP 3: Open a connection
System.out.println("Connecting to a selected database...");
conn = DriverManager.getConnection(DB_URL, USER, PASS);
System.out.println("Connected database successfully...");
//STEP 4: Execute a query
System.out.println("Inserting records into the table...");
stmt = conn.createStatement();
String sql = "INSERT INTO Mappings " +
"VALUES (0, 'EBAY-US')";
stmt.executeUpdate(sql);
sql = "INSERT INTO Mappings " +
"VALUES (2, 'EBAY-ENCA')";
stmt.executeUpdate(sql);
sql = "INSERT INTO Mappings " +
"VALUES (3, 'EBAY-GB')";
stmt.executeUpdate(sql);
sql = "INSERT INTO Mappings " +
"VALUES (15, 'EBAY-AU')";
stmt.executeUpdate(sql);
System.out.println("Inserted records into the table...");
sql = "SELECT siteID, globalID FROM Mappings";
ResultSet rs = stmt.executeQuery(sql);
//STEP 5: Extract data from result set
while(rs.next()){
//Retrieve by column name
int siteId = rs.getInt("siteID");
int globalId = rs.getInt("globalID");
//Display values
System.out.print("siteId: " + siteId);
System.out.print(", globalId: " + globalId);
}
rs.close();
}catch(SQLException se){
//Handle errors for JDBC
se.printStackTrace();
}catch(Exception e){
//Handle errors for Class.forName
e.printStackTrace();
}finally{
//finally block used to close resources
try{
if(stmt!=null)
conn.close();
}catch(SQLException se){
}// do nothing
try{
if(conn!=null)
conn.close();
}catch(SQLException se){
se.printStackTrace();
}//end finally try
}//end try
System.out.println("Goodbye!");
}//end main
}//end JDBCExample
Kimono implementation
If you don't want to have local storage for the Site ID <=> Global ID mappings, as mentioned in the techcrunch article, "Kimono Is A Smarter Web Scraper That Lets You “API-ify” The Web, No Code Required,":
With Kimono, the end goal is to simplify data extraction so that anyone can manage it.
Then Kimono’s learning algorithm will build a data model involving the items you’ve
selected.
As Kimono's website goes onto mention:
Turn websites into structured APIs from your browser in seconds.

Resources