Flex Database Select Statement doesnot respond - database

I am trying to retrieve data in flex database (AIR APPLICATION), below is code. everything is working properly except i am not able to retrieve data. ie.,when select statement is executed result handler is not called after execution
package
{
import flash.data.SQLConnection;
import flash.data.SQLMode;
import flash.data.SQLResult;
import flash.data.SQLSchemaResult;
import flash.data.SQLStatement;
import flash.data.SQLTableSchema;
import flash.errors.SQLError;
import flash.events.SQLErrorEvent;
import flash.events.SQLEvent;
import flash.events.TimerEvent;
import flash.filesystem.File;
import flash.utils.Timer;
import mx.core.FlexGlobals;
public class DB
{
public var conn:SQLConnection;
private var myTimer:Timer
private var selectStmt:SQLStatement;
private var insertStmt:SQLStatement;
public function DB()
{
conn = new SQLConnection();
var dbFile:File = File.applicationStorageDirectory.resolvePath("DBSample1.db");
try
{
conn.openAsync(dbFile);
myTimer = new Timer(1000, 1);
myTimer.addEventListener(TimerEvent.TIMER, timerHandler);
myTimer.start();
trace("the database was created successfully");
}
catch (error:SQLError)
{
trace("1 Error message:", error.message);
trace("Details:", error.details);
}
}
private function timerHandler(e:TimerEvent):void{
if(!doesTableExist(conn,"employee")){
createTable();
}
}
public function updateTrack():void{
insertStmt = new SQLStatement();
insertStmt.sqlConnection = conn;
var sql:String =
"INSERT INTO employee (name, tid) " +
"VALUES ('foo',2)";
insertStmt.text = sql;
insertStmt.addEventListener(SQLEvent.RESULT, insertResult);
insertStmt.addEventListener(SQLErrorEvent.ERROR, insertError);
insertStmt.execute();
}
public function getTracklist():void{
trace("excuting select");
selectStmt = new SQLStatement();
selectStmt.sqlConnection = conn;
selectStmt.text = "SELECT * FROM employee";
selectStmt.addEventListener(SQLEvent.RESULT, resultHandlernew);
selectStmt.addEventListener(SQLErrorEvent.ERROR, errorHandler);
selectStmt.execute();
}
private function resultHandlernew(e:SQLResult):void{
var result:SQLResult = selectStmt.getResult();
var numResults = result.data.length;
trace(numResults);
}
private function createTable():void{
var createStmt:SQLStatement = new SQLStatement();
createStmt.sqlConnection = conn;
var sql:String =
"CREATE TABLE IF NOT EXISTS employee (" +
" id INTEGER PRIMARY KEY AUTOINCREMENT, " +
" name TEXT, " +
" tid INTEGER " +
")";
createStmt.text = sql;
createStmt.addEventListener(SQLEvent.RESULT, createResult);
createStmt.addEventListener(SQLErrorEvent.ERROR, createError);
createStmt.execute();
}
function insertResult(event:SQLEvent):void
{
trace("INSERT statement succeeded");
var result:SQLResult = insertStmt.getResult();
var primaryKey:Number = result.lastInsertRowID;
trace("primaryKey:"+primaryKey);
getTracklist();
}
function insertError(event:SQLErrorEvent):void
{
trace("3 Error message:", event.error.message);
trace("Details:", event.error.details);
}
public function doesTableExist(connection:SQLConnection, tableName:String):Boolean
{
var r:Boolean;
try{
connection.loadSchema();
var schema:SQLSchemaResult = connection.getSchemaResult();
for each (var table:SQLTableSchema in schema.tables)
{
if (table.name.toLowerCase() == tableName.toLowerCase())
{
r= true;
}
}
r = false;
}catch(e){
r = false;
}
return r;
}
private function createResult(event:SQLEvent):void
{
trace("Table created");
updateTrack();
}
private function createError(event:SQLErrorEvent):void
{
trace("2 Error message:", event.error.message);
trace("Details:", event.error.details);
}
private function openHandler(event:SQLEvent):void
{
trace("the database opened successfully");
}
private function errorHandler(event:SQLErrorEvent):void
{
trace("3 Error message:", event.error.message);
trace("Details:", event.error.details);
}
}
}

Related

How to create a single store in objectbox flutter?

Flutter database objectbox error - " Unsupported operation: Cannot create multiple Store instances for the same directory in the same isolate. Please use a single Store, close() the previous instance before opening another one or attach to it in another isolate ". I am using objectbox as my app database.How can I solve this problem. Here is my code -
// First File
import 'package:flutter/material.dart';
import 'package:provider/provider.dart';
import '../objectbox.g.dart';
#Entity()
class MarkEvent {
int? id;
int habitId;
String dateTime;
MarkEvent({required this.dateTime, required this.habitId, this.id = 0});
}
class HabitDetailProvider with ChangeNotifier {
List<MarkEvent> marks = [];
Future<void> deleteMark(int id) async {
final index = marks.indexWhere((element) => element.id == id);
marks.removeAt(index);
var store = await openStore();
var box = store.box<MarkEvent>();
box.remove(id);
store.close();
// await DataBaseHelper.deleteEvent(id);
notifyListeners();
}
Future<void> addMark(MarkEvent mark) async {
marks.add(MarkEvent(dateTime: mark.dateTime, habitId: mark.habitId));
var store = await openStore();
var box = store.box<MarkEvent>();
box.put(mark);
store.close();
notifyListeners();
}
Future<void> fetchAndSetMarks() async {
var store = await openStore();
var box = store.box<MarkEvent>();
final markList = box.query().build().find();
store.close();
marks = markList
.map((e) => MarkEvent(dateTime: e.dateTime, habitId: e.habitId))
.toList();
notifyListeners();
}
}
// Another file
import 'package:flutter/material.dart';
import 'package:habit_app/objectbox.g.dart';
import '../model/habit_model.dart';
class HabitListNotifier with ChangeNotifier {
List<HabitModel> _habitList = [];
List<HabitModel> get Habit_List {
return [..._habitList];
}
Future<Store> get originalStore {
return openStore();
}
void addHabit(HabitModel habit) async {
HabitModel newHabit = HabitModel(
hour: habit.hour,
minutes: habit.minutes,
reminderHour: habit.reminderHour,
reminderMinute: habit.reminderMinute,
alarmId: habit.alarmId,
notificationText: habit.notificationText,
reason: habit.reason,
notificationId: habit.notificationId,
iconData: habit.iconData.toString(),
title: habit.title,
plan: habit.plan,
);
_habitList.add(newHabit);
var store = await originalStore;
var box = store.box<HabitModel>();
box.put(habit);
store.close();
notifyListeners();
}
void updateHabit(HabitModel newHabit) async {
final oldHabitIndex =
_habitList.indexWhere((habit) => habit.id == newHabit.id);
_habitList[oldHabitIndex] = newHabit;
var store = await originalStore;
var box = store.box<HabitModel>();
box.put(newHabit);
store.close();
notifyListeners();
}
Future<void> fetchAndSetHabits() async {
var store = await originalStore;
var box = store.box<HabitModel>();
var query = box.query().build();
_habitList = query.find();
store.close();
notifyListeners();
}
Future<void> deleteHabit(int id) async {
final existingHabit = _habitList.indexWhere((element) => element.id == id);
_habitList.removeAt(existingHabit);
var store = await originalStore;
var box = store.box<HabitModel>();
box.remove(id);
store.close();
notifyListeners();
}
}
// Another file
import 'package:flutter/material.dart';
import 'package:habit_app/providers/habit_provider.dart';
import 'package:provider/provider.dart';
import '../objectbox.g.dart';
class NoteModel {
int habitId;
int? id;
String dateTime;
String note;
NoteModel(
{required this.dateTime,
required this.habitId,
this.id = 0,
required this.note});
}
class Notes with ChangeNotifier {
List<NoteModel> notes = [];
List<NoteModel> get dupNoteList {
return notes;
}
Future<void> addNote(
NoteModel note, int habitId, BuildContext context) async {
notes.add(note);
var store = await Provider.of<HabitListNotifier>(context, listen: false)
.originalStore;
var box = store.box<NoteModel>();
box.put(note);
store.close();
fetchAndSetNotes(habitId);
notifyListeners();
}
Future<void> deleteNote(int id) async {
final index = notes.indexWhere((element) => element.id == id);
notes.removeAt(index);
var store = await openStore();
var box = store.box<NoteModel>();
box.remove(id);
store.close();
notifyListeners();
}
Future<void> updateNote(NoteModel newNote) async {
var store = await openStore();
var box = store.box<NoteModel>();
box.put(newNote);
store.close();
final oldNote = notes.indexWhere((habit) => habit.id == newNote.id);
notes[oldNote] = newNote;
notifyListeners();
}
Future<void> fetchAndSetNotes(int habitId) async {
var store = await openStore();
var box = store.box<NoteModel>();
var query = box.query().build();
final note = query.find();
store.close();
notes = note.where((notes) => notes.habitId == habitId).toList();
notifyListeners();
}
}
//Models file
import 'package:objectbox/objectbox.dart';
#Entity()
class NoteModel {
String habitId;
int? id;
String dateTime;
String note;
NoteModel({
required this.dateTime,
required this.habitId,
required this.note,
this.id = 0,
});
}
import 'dart:core';
import 'package:objectbox/objectbox.dart';
class ClockTime {
int? id;
int hour;
int minutes;
ClockTime(this.hour, this.minutes);
}
#Entity()
class HabitModel {
String title;
String reason;
String plan;
String iconData;
int? id;
int alarmId;
int notificationId;
String notificationText;
int hour;
int reminderHour;
int reminderMinute;
int minutes;
HabitModel({
required this.reason,
required this.notificationText,
required this.reminderHour,
required this.reminderMinute,
required this.notificationId,
required this.plan,
required this.alarmId,
required this.iconData,
required this.title,
this.id = 0,
required this.hour,
required this.minutes,
});
}

Can't recieve byte array using Retrofit 2 in Kotlin

I have a DTO class using Moshi that's supposed to send and recieve byte arrays[], but it only works when sending them, because when I recieve then I have this exception.
com.squareup.moshi.JsonDataException: Expected BEGIN_ARRAY but was STRING at path $[0].image
But im pretty sure that the type that the API returns is a byte array.
Here's the DTO class and API controller
#JsonClass(generateAdapter = true)
data class LocationImageDTO (
#Json(name="idLocationImage") val idLocationImage: Int,
#Json(name = "idLocation") val idLocation: Int?,
#Json(name="image") val image: ByteArray,
)
//This one is for recieving
public List<clsLocationImage> getList(int idLocation)
{
List<clsLocationImage> list = new List<clsLocationImage>();
clsLocationImage locationImage;
clsMyConnection connection = new clsMyConnection();
SqlCommand command = new SqlCommand
{
CommandText = "SELECT idLocationImage, idLocation, image FROM K0_MAP_LOCATION_IMAGES WHERE idLocation = #idLocation",
Connection = connection.getConnection()
};
command.Parameters.Add("#idLocation", System.Data.SqlDbType.Int).Value = idLocation;
SqlDataReader reader;
try
{
reader = command.ExecuteReader();
if (reader.HasRows)
{
while (reader.Read())
{
locationImage = new clsLocationImage();
locationImage.idLocationImage = (int)reader["idLocationImage"];
locationImage.idLocation = (int)reader["idLocation"];
locationImage.image = (byte[])reader["image"];
list.Add(locationImage);
}
}
}
catch (SqlException excepcion)
{
throw excepcion;
}
return list;
}
public List<clsLocationImage> getListDAL(int id)
{
return getList(id);
}
}
}
///This one is for sending
public int createLocationImage(clsLocationImage locationImage)
{
int filasAfectadas = 0;
clsMyConnection conexion = new clsMyConnection();
SqlCommand miComando = new SqlCommand
{
CommandText = "INSERT INTO K0_MAP_LOCATION_IMAGES(idLocation, image) VALUES (#idLocation, #image)",
Connection = conexion.getConnection()
};
miComando.Parameters.Add("#idLocation", System.Data.SqlDbType.Int).Value = locationImage.idLocation;
miComando.Parameters.Add("#image", System.Data.SqlDbType.VarBinary).Value = locationImage.image;
try
{
filasAfectadas = miComando.ExecuteNonQuery();
}
catch (SqlException excepcion)
{
throw excepcion;
}
return filasAfectadas;
}
}
}
You need to set an explicit JSON adapter to the Moshi Builder.
class CustomDateAdapter : JsonAdapter<Date>() {
private val dateFormat = SimpleDateFormat(SERVER_FORMAT, Locale.getDefault())
#FromJson
override fun fromJson(reader: JsonReader): Date? {
return try {
val dateAsString = reader.nextString()
synchronized(dateFormat) {
dateFormat.parse(dateAsString)
}
} catch (e: Exception) {
null
}
}
#ToJson
override fun toJson(writer: JsonWriter, value: Date?) {
if (value != null) {
synchronized(dateFormat) {
writer.value(value.toString())
}
}
}
companion object {
const val SERVER_FORMAT = ("yyyy-MM-dd'T'HH:mm") // define your server format here
}
}
And then you add it in the Moshi builder
private val moshiBuilder = Moshi.Builder().add(CustomDateAdapter())
private fun getRetrofit(): Retrofit =
Retrofit.Builder()
.baseUrl(MAPK0_API_BASE_URL)
.addConverterFactory(MoshiConverterFactory.create(moshiBuilder.build()))
//.client(getUnsafeOkHttpClient())
.build()
}

Execute Reader is not returning a result

Can you please help me see what is wrong with my code? If I run the stored procedure using the a parameter for Id, I get a result in SQL Server. But when I use the code below using the same value for Id, in my if(rdr.HasRows).. I get a false.
public Student Find(int key)
{
string connectionPath = ConnectionStrings.DbConnection;
Student student = null;
try
{
using(var sqlCon = new SqlConnection(connectionPath))
{
sqlCon.Open();
using(var cmd = new SqlCommand("Sp_FindStudent", sqlCon))
{
cmd.Parameters.AddWithValue("#Id", key);
using(var rdr = cmd.ExecuteReader(CommandBehavior.SingleResult))
{
if (rdr.HasRows)
{
while (rdr.Read())
{
student = new Student
{
Age = Convert.ToInt32(rdr["Age"]),
FirstName = rdr["FirstName"].ToString(),
LastName = rdr["LastName"].ToString(),
Gender = rdr["Gender"].ToString()
};
}
}
}
}
}
}
catch(Exception ex)
{
throw ex;
}
return student;
}
If I try to get all records, I don't get any problems:
public IEnumerable<Student> GetAll()
{
var studentList = new List<Student>();
try
{
string connectionPath = ConnectionStrings.DbConnection;
using(var sqlCon = new SqlConnection(connectionPath))
{
using(var cmd = new SqlCommand("Sp_GetStudents", sqlCon) { CommandType = CommandType.StoredProcedure})
{
sqlCon.Open();
using(var rdr = cmd.ExecuteReader(CommandBehavior.CloseConnection))
{
while (rdr.Read())
{
studentList.Add
(
new Student
{
Id = Convert.ToInt32(rdr["Id"]),
Age = Convert.ToInt32(rdr["Age"]),
FirstName = rdr["FirstName"].ToString(),
LastName = rdr["LastName"].ToString()
}
);
}
}
}
}
}
catch(Exception ex)
{
throw ex;
}
return studentList;
}
This is using asp.net core
Your code for Find lacks the definition that this is a stored procedure that you're calling.
If you look at your GetAll, you have:
using(var cmd = new SqlCommand("Sp_GetStudents", sqlCon) { CommandType = CommandType.StoredProcedure})
defining this SqlCommand to be a stored procedure - this setting is missing from your Find code:
using(var cmd = new SqlCommand("Sp_FindStudent", sqlCon))
I'm pretty sure it'll work if you add that:
using(var cmd = new SqlCommand("Sp_FindStudent", sqlCon) { CommandType = CommandType.StoredProcedure}))

SQL Server query in ADO.NET only returning one result

I'm learning asp.net mvc with ado.net, I've got this method in my repository class
public IEnumerable<int?> GetAllUniqueYears()
{
using (IDbConnection dbConnection = dbConnectionFactory.CreateConnection())
{
using (IDbCommand cmd = dbConnection.CreateCommand())
{
cmd.CommandText = "SELECT DISTINCT YEAR(DateAdded) As Year FROM GeoCounters";
cmd.CommandTimeout = 1000;
using (IDataReader reader = cmd.ExecuteReader())
{
if (!reader.Read())
{
yield return null;
}
else
{
yield return (int)reader["Year"];
}
}
}
}
}
When I load my view it's only got a single result, but when I run the query in SQL Server Management Studio there are 4 results
The controller action
public ActionResult Index()
{
HomeIndexViewModel model = new HomeIndexViewModel()
{
GeoCounterDefinitions = geodefrepo.GetAll()
.Select((x,y) => new SelectListItem
{
Text = x.Id + " " + x.FriendlyDesc,
Value = (y + 1).ToString()
}),
Years = geocounterrepo.GetAllUniqueYears()
.Select(x => new SelectListItem
{
Text = x.ToString(),
Value = x.ToString()
})
};
return View(model);
}
You need a while loop.
using (IDataReader reader = cmd.ExecuteReader())
{
while (reader.Read())
{
yield return (int)reader["Year"];
}
}

Dapper table valued parameter as a property?

I have a stored proc like this:
CREATE PROCEDURE [dbo].[Organisation_Insert]
#OrganisationXId uniqueidentifier
,#Enabled bit
,#Timezone nvarchar(50)
,#MinimumValue float
,#Rules ReminderRuleType READONLY ...
ReminderRuleType is a user defined type.
In my app I have this:
class OrganisationDTO
{
private readonly IOrganisationDocument _orgDoc;
public long OrganisationId { get { return _orgDoc.OrganisationId; } }
public Guid OrganisationXId { get { return _orgDoc.OrganisationXId; } }
public string TimeZone { get { return _orgDoc.TimeZone; } }
public bool Enabled { get { return _orgDoc.Enabled; } }
public decimal MinimumValue { get { return _orgDoc.MinimumValue; } }
public RuleTableValuedParameters Rules { get; private set; }
public OrganisationDTO(IOrganisationDocument orgDoc)
{
_orgDoc = orgDoc;
Rules = new RuleTableValuedParameters("#Rules", _orgDoc.Rules);
}
}
RuleTableValuedParameters implements SqlMapper.IDynamicParameters which has an AddParameters method.
When I execute the query, the #Rules parameter is never passed (using SQLProfiler). I can also see that AddParameters is never called.
Is this possible to do?
Thanks
Here's a simplified example based on your code that shows it working just fine; AddParameters is invoked correctly, and the values are conveyed to the stored procedure. As a side note: if you are using DataTable for your TVPs, the library supports that directly with no additional code needed.
public void SO29596645_TvpProperty()
{
try { connection.Execute("CREATE TYPE SO29596645_ReminderRuleType AS TABLE (id int NOT NULL)"); }
catch { }
connection.Execute(#"create proc #SO29596645_Proc (#Id int, #Rules SO29596645_ReminderRuleType READONLY)
as begin select #Id + ISNULL((select sum(id) from #Rules), 0); end");
var obj = new SO29596645_OrganisationDTO();
int val = connection.Query<int>("#SO29596645_Proc", obj.Rules, commandType: CommandType.StoredProcedure).Single();
// 4 + 9 + 7 = 20
val.IsEqualTo(20);
}
class SO29596645_RuleTableValuedParameters : Dapper.SqlMapper.IDynamicParameters {
private string parameterName;
public SO29596645_RuleTableValuedParameters(string parameterName)
{
this.parameterName = parameterName;
}
public void AddParameters(IDbCommand command, Dapper.SqlMapper.Identity identity)
{
Console.WriteLine("> AddParameters");
SqlCommand lazy = (SqlCommand)command;
lazy.Parameters.AddWithValue("Id", 7);
DataTable table = new DataTable {
Columns = {{"Id", typeof(int)}},
Rows = {{4}, {9}}
};
lazy.Parameters.AddWithValue("Rules", table);
Console.WriteLine("< AddParameters");
}
}
class SO29596645_OrganisationDTO
{
public SO29596645_RuleTableValuedParameters Rules { get; private set; }
public SO29596645_OrganisationDTO()
{
Rules = new SO29596645_RuleTableValuedParameters("#Rules");
}
}
Here's the full working DynamicParameter that I created:
public class OrganisationDynamicParameter : SqlMapper.IDynamicParameters
{
private readonly IOrganisation _orgModel;
public OrganisationDynamicParameter(IOrganisation orgModel)
{
_orgModel = orgModel;
}
public void AddParameters(IDbCommand command, SqlMapper.Identity identity)
{
SqlParameter p;
var sqlCommand = (SqlCommand)command;
sqlCommand.CommandType = CommandType.StoredProcedure;
p = sqlCommand.Parameters.Add("#OrganisationXId", SqlDbType.UniqueIdentifier);
p.Value = _orgModel.OrganisationXId;
p = sqlCommand.Parameters.Add("#Enabled", SqlDbType.Bit);
p.Value = _orgModel.Enabled;
p = sqlCommand.Parameters.Add("#Timezone", SqlDbType.NVarChar, 50);
p.Value = _orgModel.TimeZone;
p = sqlCommand.Parameters.Add("#MinimumValue", SqlDbType.Float);
p.Value = _orgModel.MinimumValue;
List<SqlDataRecord> ruleList = _orgModel.Rules.Select(MapRuleData).ToList();
if (ruleList.Count > 0)
{
p = sqlCommand.Parameters.Add("#Rules", SqlDbType.Structured);
p.Direction = ParameterDirection.Input;
p.TypeName = "ReminderRuleType";
p.Value = ruleList;
}
}
protected SqlDataRecord MapRuleData(IReminderRule value)
{
var rec = new SqlDataRecord(new[]
{
new SqlMetaData("RuleId", SqlDbType.BigInt),
new SqlMetaData("OrganisationId", SqlDbType.BigInt),
new SqlMetaData("Name", SqlDbType.NVarChar, 200),
new SqlMetaData("OffsetDays", SqlDbType.Int),
new SqlMetaData("SubjectTemplate", SqlDbType.NVarChar, -1),
new SqlMetaData("BodyTemplate", SqlDbType.NVarChar, -1)
});
rec.SetInt64(0, value.RuleId);
rec.SetInt64(1, value.OrganisationId);
rec.SetString(2, value.Name);
rec.SetInt32(3, value.OffsetDays);
rec.SetString(4, value.SubjectTemplate);
rec.SetString(5, value.BodyTemplate);
return rec;
}
}
I use this thusly:
public IOrganisation CreateOrganisation(IOrganisation organisation)
{
var dtoOrg = new OrganisationDynamicParameter(organisation);
return ExecuteSPReturningOrganisation("Organisation_Insert", dtoOrg);
}
protected IOrganisation ExecuteSPReturningOrganisation(string query, object parameters)
{
using (IDbConnection con = ConnectionFactory.CreateOpenConnection())
{
using (
SqlMapper.GridReader multi = con.QueryMultiple(query, parameters,
commandType: CommandType.StoredProcedure))
{
OrganisationModel org = multi.Read<OrganisationModel>().SingleOrDefault();
if (org != null)
{
org.Rules = multi.Read<ReminderRuleModel>().ToArray();
}
return org;
}
}
}
Cheers

Resources