#Core Haxe
1 messages ยท Page 3 of 1
i thought it might have been a modern addition
but even haxe.json parses it correctly
INSERT INTO persons.person (personId,lastName,firstName,iconId,hourlyRate)
VALUES (1,'bob','tim',1,1);
this fails
(firstName is a json column)
this passes:
INSERT INTO persons.person (personId,lastName,firstName,iconId,hourlyRate)
VALUES (1,'bob','{}',1,1);
("tim" changed to "{}")
via db core or mysql gui?
gui
ok, this is alright though:
INSERT INTO persons.person (personId,lastName,firstName,iconId,hourlyRate)
VALUES (1,'bob','"tim"',1,1);
So that makes sense seeing as "tim" is valid json but tim (no quotes) isnt
this fails because 'tim' is invalid json
change tim to 711 and it will pass
if you want it to be valid change it to '"tim"'
yeah, i mentioned exactly this above ๐
ah yea
ok, so this:
return result.table.addAll([
Person(1, '711', 'Harrigan', 1, Bytes.ofString("this is ians contract document"), 111.222),
Person(2, '712', 'Barker', 3, null, 333.444),
Person(3, '713', 'Mallot', 2, null, 555.666),
Person(4, '714', 'Parker', 1, null, 777.888)
]);
and later this:
var record = result.data;
record.field("firstName", 777);
record.field("lastName", "HARRIGAN_MODIFIED");
record.field("hourlyRate", 999.123);
return result.table.update(query($personId = 1), record);
works fine
so i wonder if we are barking up the wrong tree here and its not that at all
i think you'll need to minimal repro it and see if it is that... like just a throw away app that opens the db and makes the update
is this nodejs btw?
yea
i'm struggling to parse the actual sql error tbh
it updates fine for me
i can't see what is problematic
sql errors are shit in general, especially as the error wont (for good reasons) include the values
if it were a problem with the json, i think you would get a CONSTRAINT FAILURE error
lets see if because the where is a string value... ๐
nope
this all works fine:
var record = result.data;
record.field("firstName", 777);
record.field("lastName", "HARRIGAN_MODIFIED");
record.field("hourlyRate", 999.123);
var lastName:Dynamic = "Harrigan";
return result.table.update(query($lastName = lastName), record);
which is about as close as i think i can get to your usage
UPDATE Person SET personId = ?, lastName = ?, firstName = ?, iconId = ?, contractDocument = ?, hourlyRate = ? WHERE (`Person`.`lastName` = ?);`
function test(field:String, value:Dynamic) {
var record = new Record();
record.field("firstName", value);
record.field("lastName", "HARRIGAN_MODIFIED");
record.field("hourlyRate", 999.123);
return result.table.update(query($firstName = field), record);
}
test('firstName', 7132);
this is pretty much exactly what I have locally
some differences
i think you'll need to minimal repro it outside of your actual app and see if that makes it make more sense
this end, it seems fine
can you try the above?
you're entering 777 directly in the record instead of having it as a dynamic
you're whereing on the last name instead of the first name
dont see how that would make a diff, but ill try
oh wait, nvm on the last name thing
yours is whering on an unrelated string field though
it's pretty much the only difference i can see between your testcase and my usecase
var record = result.data;
var value:Dynamic = 777;
record.field("firstName", value);
record.field("lastName", "HARRIGAN_MODIFIED");
record.field("hourlyRate", 999.123);
var lastName:Dynamic = "Harrigan";
return result.table.update(query($lastName = lastName), record);
all fine
i presume you are using latest everything?
i dont think ive fixed anything like this, but who knows
yeah just added the libs to hbot yesterday
so then, yeah, i guess your only remaning option is to minimal repro it... i cant see another way
shouldnt take long, few mins i would have thought
hmmm
query($lastName = lastName)
in my code I have query($lastName == lastName)
is this invalid?
oh ๐
nope, seems fine
yeah, its handled:
switch (op) {
case QOpEq: sb.add(" = ");
case QOpAssign: sb.add(" = ");
}
... so its not that... phew... was about to jump off the balcony
haha
i get the same error in a repro project
import db.DatabaseError;
import haxe.Timer;
import db.IDatabase;
import db.DatabaseFactory;
import db.Record;
import Query.*;
class Main {
var db:IDatabase;
static function main() {
new Main();
}
function new() {
db = DatabaseFactory.instance.createDatabase(DatabaseFactory.MYSQL, {
database: "haxe",
host: "",
user: "",
pass: ""
});
db.setProperty('autoReconnect', true);
db.setProperty('autoReconnectInterval', 5000);
db.setProperty('replayQueriesOnReconnection', true);
connect();
var timer = new Timer(500);
timer.run = () -> {};
}
function connect() {
db.connect().then(function(state) {
if (state.data) {
db.table('state').then((result) -> {
var record = new Record();
record.field("key", "next_roundup");
record.field("value", 730);
return result.table.update(query($key = "next_roundup"), record);
}).then(function(res) {
trace(res);
trace('success');
trace(res);
}, function(err) {
trace(err);
// trace(queryExprToSql(query));
// trace(value.debugString());
});
trace('Database connected');
} else {
trace('Database not connected');
}
},function err(err:DatabaseError) {
trace(err.call);
trace(err.message);
});
}
}
here's my db setup
forgot the table creation
lol
UPDATE state SET key = ?, value = ? WHERE (`state`.`key` = ?);
TestAll.hx:29: {
message : You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near 'key = ?, value =
? WHERE (`state`.`key` = ?)' at line 1,
call : update
๐ฅณ
fixed i think... just need to check some other stuff out first
yay
alright if you pull latest db-core and db-mysql... ... ... ?
ok, but that might be "on you" now, no? does your test app work now?
probably needed to be a string or something?
although seems odd... didnt need to be in the test app
btw, the original issue was nothing to do with json, or anything, its that the "key" column is a reserved word, so needed to be key
i get an empty message
lol
you know
I thought about that at some point
but just let it go as "that can't be it"
same issue would have happened for deleting
i defo have more normal uses for the mysql db
but being able to do something like this in mysql is pretty cool either way
it plays really nicely with haxe as well
for dbcore the readme says there's one-to-one and one-to-many
is many-to-many fine?
im not sure ive played with many to many relationships in db-core / entities
are LIKE queries supported with db-core?
I couldn't find a test for anything that looks like it
LIKE isnt supported in query dsl... not sure what the haxe syntax equiv could be
you could do an "internally reserved" keyword
$LIKE
but not sure how elegant that is
i wonder if $field % value would be alright?
its defo valid syntax, just dunno if its too esoteric
might be a bit extra but why not an enum?
query(LIKE('a%'));
i guess it isn't very universal
i just dont like "LIKE"... its very sql... and db-core isnt (supposed) to be sql
granted the only two plugins currently are sql, but i dont want to shoot myself in the foot
ahhh that makes sense
wildcard in itself does seem okay, but it might lack some flexibility
like, would i be able to do a%z or a___%
oh, i guess so
it would probably just look a bit odd
$field % a%z
i wonder if a whole new operation make sense "search" or something
that would mean you cant use "LIKE" in update / delete... but maybe thats ok? Seems dangerous / silly to do things like that anyway?
I think that's actually a good compromise
because you can still just perform an update or delete with the results of the search altogether
I agree it seems a bit odd, but I can also see a use case for these things
eg removing duplicates
yeah, i can defo see a use for "delete where like"
but at the same time, like you say, you could do that with the results of a search
im also not sure that "like" would map well to other non-sql things in the future (although "search" almost certainly would)
eg, i dont think you could do a "delete where like" on cassandra / solr / lucene (i could be wrong about that ofc)
so i guess a seach(fields:Array<String>, terms:Array<String>)? ๐ค
although how would that work with "(x like a or (y like b and z like c))"... hmm
could search accept an expression?
you mean a query expression? Like the other calls? Then we are back to "like" in the query dsl
maybe a new search dsl? But now its starting so sound over engineered / duplicated
ahhh, yeah
search(['x like a', 'or y like b'])
this would work fine, no?
maybe not
this type of stuff is complicated ๐
thats waaaaay too specific
@velvet lodge can I do a direct/inline mysql query with dbcore?
nope... i think we discussed it before and consindered adding a "raw" call... ... ?
The thing i dont like about it, is it encourages "just use raw" - though i suppose thats not my business
yeah, i vaguely remembered it as well, but discord search within threads sucks
its mostly to be able to cover queries that aren't supported in core as of yet
yeah, thats fair
i would still report them as usual, probably worth putting them up as github issues in general
right, you can use "raw" calls now on either ITable or IDatabase... both calls have the same signature (and work in the same way), and you have to "opt in" to allow it:
#if allow_raw
public function raw(data:String, values:Array<Any> = null):Promise<DatabaseResult<RecordSet>>;
#end
its not thoroughly tested, so let me know if you get any issues
(side note: "thoroughly" is a bitch of a word to spell - had to google it ๐ )
how do we use this?
i was expecting something like raw('select foo ...)
yeah, thats how you use it, on either ITable or IDatabase... where where you expecting to call "raw" from?
oh so data == query
what's values for?
thats if you want to use it as a prepared statment (which is safer), so you can do:
theDB.raw("select * from x where field = 'bob'")
or
theDB.raw("select * from x where field = ?", ["bob"])
ahhhh
yeah, i didnt want to call it query, because, well, it might not be a query in the future, and in general, i dont like this whole "raw" stuff anyway (hence the opt in)... but i can see the utility in it (to make up for core-db shortcomings... ... ... currently)
yeah, i figured its just a better way to handle things when you're busy
yeah, makes sense
i have no issues changing my code when the proper ways come along :)
exactly... it will (hopefully) be a "well, at least i can do stuff until a better method comes along"
hell yeah ๐
thanks!
not something i can be "happy" about as it highlights holes in core-db... but good its not a blocker anymore ๐
src/systems/DatabaseSystem.hx:322: SELECT * FROM
quotesWHERE title LIKE '%electr%';
src/systems/DatabaseSystem.hx:61: ceramic electron
๐
?
can search in any position of a string
its a luxury that firebase/nosql doesn't provide
when I insert into the db the column name is id
why does it become insertedId here ๐ค
_insertedId is something that comes from the db when you do an insert, yeah, but it shouldnt have overwritten anything
ahh
I was expecting the id field to come back as the id field
in the insert response
i dont think it returns that, unless it requeries it... afaik, the only thing you get back from an insert is the inserted id, i dont really understand why those other fields are there...
what is your call?
it's the primary key/auto increment field
yeah
so I just wanted to do stuff with the response and was confused when the id field had no value
just a standard insert, this is to do with the response from the insert
if you trace the response.data here: https://github.com/core-haxe/db-mysql/blob/main/src/db/mysql/MySqlTable.hx#L158
what do you get?
i think i would expect only { insertId: 487 }
all that said and done, there is a refreshSchema() call at the start, so technically it should be possible to find out what the primary key is and set that field...
db/mysql/MySqlTable.hx:159: {
fieldCount : 0,
affectedRows : 1,
insertId : 38,
info : ,
serverStatus : 2,
warningStatus : 0,
changedRows : 0
}
so yeah, it doesnt give you the id field name back either
nah, its the only field missing
seems a bit off
considering it does actually send the id
just with a different name ๐
i think thats usual tbh... ive never seen insert queries be like "this is the primary key name, and its value is 38"
possibly, it might legit be over a decade since i used mysql
i do like the idea of core-db working it out though... my concern is a) getting it wrong and b) adding overheard to inserts
it does seem fitting for core-db
the overhead issue, i'm not sure how that could be worked out
well, the call to refreshSchema is cached: https://github.com/core-haxe/db-mysql/blob/main/src/db/mysql/MySqlDatabase.hx#L136
so its might not be that much of an overheard, but what if the schema changes while things are running... like an ALTER table raw query or something?
i guess in that case, since you used "raw" you would have to manualy call clearCachedSchema
in this particular instance i'm not using raw
no no, i understand, im just saying if you alter table via raw then the cached schema will be out of date, but upon reflection i kinda think "thats a you problem for using raw alter table"... ... if you use addColumn / removeColumn (for example, which will create an alter table query) then it also clears the cached schema
if (res.data.hasField('_insertedId')) {
res.data.field('id', res.data.field('_insertedId'));
}```
simple workaround, just seemed like an oversight
well, the problem is knowing its "id"
ahhh, tbh, as long as there's some kind of asterisk somewhere that says "hey these are things to watch out with raw queries, and there may be some other things i've forgotten, its very diy land" etc etc
i think it should be okay
raw should, for the most part be considered "you're on your own"
i think if you use raw, you cant expect db-core to have any idea what you did
I would agree
can be just "nice" to post some things to look out for, but it should be considered anti db-core
and i don't think it should be considered as part of "core's inner workings"
at most just some note somewhere in the readme
I must say tho
having raw around is very comforting x)
its a good thing to have around, but im not a "fan" ๐
oh yay
thanks!
Hmm, when we do a delete operation
is the record we pass to it meant to be used as a kind of where operation
or are we meant to supply the full row?
ahah
okay, i think we have a bit of an unintuitive bug with delete then
If the operation fails, there's no clear way to figure out that the operation failed in the response data
for example, i purposely supplied a mismatching author_id here, so nothing got deleted from the table
but the response is the same as if something did get deleted
yeah, sounds like an oversight, ill check it tomorrow... dunno whats better though, returning null result or rejecting (throwing an error)
i feel like null result is the best idea, maybe with the property for throwing an exception
null or some bool sucess: true, success: false
i think error would be somewhat misleading
With core-http's server, is there a way to get the remote IP Address from the request?
try checking the headers
there may be some way to check the ip address via checking the source of the socket request
nothing in there
so i dont think it does, shouldnt be hard to add, although, ill have to have a quick check how you can get that info from "normal" haxe http
fyi @toxic stratus - im just writing the unit tests, but ive changed the DatabaseResult to include an "itemsAffected" var
(rather than success / failure prop)
yeah, it makes more sense really... so tests like this make sense:
function testBasicDelete_All(async:Async) {
db.table("Person").then(result -> {
return result.table.all();
}).then(result -> {
Assert.equals(4, result.data.length);
return result.table.findOne(query($personId = 1));
}).then(result -> {
Assert.equals(1, result.data.field("personId"));
Assert.equals("Ian", result.data.field("firstName"));
Assert.equals("Harrigan", result.data.field("lastName"));
Assert.equals(1, result.data.field("iconId"));
return result.table.deleteAll();
}).then(result -> {
Assert.equals(4, result.itemsAffected);
return result.table.findOne(query($personId = 1));
}).then(result -> {
Assert.isNull(result.data);
return result.table.all();
}).then(result -> {
Assert.equals(0, result.data.length);
async.done();
}, error -> {
trace("error", error);
});
}
function testBasicDelete_None(async:Async) {
db.table("Person").then(result -> {
return result.table.all();
}).then(result -> {
Assert.equals(4, result.data.length);
return result.table.deleteAll(query($personId = 1111));
}).then(result -> {
Assert.equals(0, result.itemsAffected);
return result.table.all();
}).then(result -> {
Assert.equals(4, result.data.length);
async.done();
}, error -> {
trace("error", error);
});
}
its quite a strong test validation tool in itself
with all the core-* libs i tend to unit tests to the nth degree (or try to at least): https://github.com/core-haxe/db-core/tree/main/tests/cases
i poke in there when looking to see if there's a feature i want to use now and then ๐
PITA is now i have to populate that itemsAffected in all the different routes possible - in just db-sqlite there are 3 routes (npm sqlite3, c++ libsqite3, shitty sys.db)
lol you should have a dbcore script that can just update the tables ๐
not sure it would work... its more like "add "changes" to SqliteResult", "expose sqlite3_changes call in libsqlite3", "populate chanages from extern call"...
not complex, but just alot of places
the unit tests help alot ofc.... let me know when ive missed something... which is often ๐
alright, thats in now... you'll need to pull pretty much everything
@uncut phoenix - httpRequest now contains remoteAddress property
eg:
httpServer.onRequest = (httpRequest, httpResponse) -> {
return new Promise((resolve, reject) -> {
trace(httpRequest.remoteAddress);
httpResponse.write("this is the response");
resolve(httpResponse);
});
};
hell yeah
^ Ah sorry forgot to respond, thanks so much!
by [ab]using the OpNegBits unary operator in haxe, we can now have "similar" (aka "LIKE" in sql) queries in the query ast in db-core, eg (from the unit tests):
function testBasicSimilar_WildCard_Multiple_Or_Nested(async:Async) {
db.table("Person").then(result -> {
return result.table.find(query(($firstName =~ "i*" || $firstName =~ "*b") || $firstName = "Jim"));
}).then(result -> {
Assert.equals(3, result.data.length);
Assert.equals("Ian", result.data[0].field("firstName"));
Assert.equals("Bob", result.data[1].field("firstName"));
Assert.equals("Jim", result.data[2].field("firstName"));
async.done();
}, error -> {
trace("error", error);
});
}
this will generate (assuming you are using a sql db-core db plugin):
(`Person`.`firstName` LIKE 'i%' OR `Person`.`firstName` LIKE '%b') OR `Person`.`firstName` = 'Jim'
@toxic stratus - what haxe target do you use mysql with?
just nodejs atm
I think one of core haxe's libs doesn't work on cpp so I'm mostly just using node
should all work, i have unit tests
but im going to migrate hxcpp to not use sys.db and use libmysqlclient externs (which past me wrote somehow)
heh, thats the core-haxe version, right?
but also, thats nothing to do with mysql
thats web sockets
yeah, but i said one of core-haxe libs doesn't work ๐
right, but it does work under nodejs?
yeah
good to know
need to look at core-haxe/ws soon actually as i need it
might not be using wss, just ws
ahhh
hell yeah
what target were you thinking about?
i'd like both nodejs/js and cpp available
they should all be available now (mysql)
but im going to remove the sys.db dep for hxcpp
nice, will I need to add any lib for cpp to work?
libmysqlclient (which i thought i would have to create, but ive actually already created it)
sorry, just reread, currently you wont have to, but after i remove the sys.db dep you will
that's cool
can't seem to find Mysql after updating db core stuff
I installed libmysqlclient
oooh
i thought libmysqlclient was a complete replacement for hx4compat
that fixed it ๐
lol
i'll post a pr I guess ๐
message : You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'keys
WHERE (? = ?) LIMIT 1' at line 1,
call : findOne
}
query is:
db.table(table).then((result) -> {
return result.table.findOne(query('aid' == 'idgoeshere'));
})
query($aid == 'idgoeshere')) has the same issue
SELECT * FROM keys
WHERE (`keys`.`aid` = ?) LIMIT 1;
hmm..
i wonder if its cause it is "just" keys
this query fails in heidi
changing
var sql = 'SELECT ${fieldList} FROM ${table.name}';
to
var sql = 'SELECT ${fieldList} FROM `${table.name}`';
in SqlUtils.hx:53, makes it work but that might breaks things else where
lemme know if you're cool with a PR for this change
thanks for this btw, merged - accidently left the import in (prolly testing something... no idea)... and so it pulled into the sys.db dep... nice catch ๐
So is libmysql work for you?
yeah, all names should be quoted, must have missed this one... whats the name of the table? Some reserved name i guess?
table name was keys
mebbe thats reserved in mysql... no idea
but yeah, if your fix fixes it, then defo PR please ๐
cools
i'm just out of sql for so long no idea if no quoting is relied on behaviour anywhere
unseen core-db issue? "Your sql will get worse since you dont need it anymore" ๐
yeah, there's a few other table names without backticks in here
i'll add those in
nice one
'${table.name}.
${tableColumn.name}
how should the back ticking be done here?
discords markdown is getting in the way here x)
`table`.`column`
feels like it yeah
might want to runt he UTs just to be sure, but pretty sure thats not the best way to handle these things
where is that code?
https://github.com/core-haxe/db-core/pull/5 here's the PR
will see what the tests come back as
they may fail in general though...
ah ๐
nodejs and neko should pass though by the looks of it
yup
can you change this one... this one was fine actually, i didnt understand the context... its an "AS"
ahhh okay
and this one: AS ${joinName}.${tableColumn.name}');
any of the "AS"'s
just two
rest seem fine... quite alot of them... nice catches
nice
tiny change, but ill make... it will take me longer to explain ๐
uh, wait, all the UTs broke locally, might be because of that change i wanted to make, two secs
nope, nothing to do with that change, was also backtick issues on db-core/mysql
unless you also fixed those?
nothing, dont worry... found some other issues
ahhh
should be fixed now... pull latest db-core / db-mysql to be sure
Hmm ... I think the change here cause problems https://github.com/core-haxe/db-core/commit/000f8535aea3ad68cd508e4cb3098569e690bee2
I had done this change before and https://github.com/core-haxe/db-core/commit/d5c4cbcc5ee7fe11efa017e016707dea8b1f713c ( the first done) I was concentrated on columns and no table names. But I remeber trying what !Billy did and not working
yeah, i fixed those now, but found some issues specific to mysql in the "addColumn" test
not sure if they just went under the radar or broke recently... no idea... sorted now and UTs pass locally
fyi, these are the commits to get UTs back to normal (locally):
Hmm, one error seems to be fixed but not the one
I have when launching the job-consumer this error. It was the kind of errors when I had when trying to fix the backtick issues
sqlite?
runs for me ๐
TestAddColumn also fails for me (sqlite)
yeah using sqlite.
I'm nearly sure for some reasons you can't have the backticks in the first part ${table.name}.${tableColumn.name} will try without backticks and see if it works
uts pass, just realised you had already made the same change i needed locally (i just hadnt pulled ๐ )
so are you saying with latest db-core, db-sqlite, everything, that exception occurs?
(latest as in "3 mins ago")
yes ๐ฆ
๐โโ๏ธ
i feel like something else is up then... or are you saying if you go back some commits then everything works?
hmm not sure anymore. I had two problems and one is fixed... and maybe the other is mine... ( hugs !Billy).
right, would be good at some point to isolate that... core-db should "just work"... if its a logic error (or whatever) in one of the job consumers... thats a totally seperate thing
the UTs certainly pass, but they are only as good as the coverage added by the author (me in this case)
lemme check entities real quick, but again, coverage is only as good as "it is" (though coverage on all these libs is pretty good i think)
(entities UTs pass - sqlite)
No it doesn't work ( suddenly I thought it didn't work in old versions but it was because of rabbit queues that I forgot to empty) .
Now I'll try with pseudo fix.
doesnt work if you go back some commits you mean?
rabbit queues that I forgot to empty
this is interesting in its own right, how did you poison your rabbitmq queues? (jeez, had to google how to spell "poison"... :/ )
what dbs do u support atm?
sqlite / mysql... postgres coming "soon" and "IndexedDB" as a "test of the abstraction"
cool i have a custom native sys.db.Postgres impl somewhere, maybe i could butcher that and contribute some code
sounds good, for sure... first we need a libpostgres (for hxcpp) but iirc i found it and it looks significantly more sane than libmysqlclient
the idea of core-db (not core-haxe in general), is we just stop thinking about "oh, which db"... i guess like haxeui, with the backends and such... im a masochist it seems ๐
i used the official dynamic libs via hxcpp i think
I'm in stupid mode... I don't know anymore anything ^^ Tell you in a moment when I'm sure what's happening
yeah, i remember looking for libpostgres and it was like libsqlite3... just "there"... libmysqlclient is verrrry different, its embedded in the mysql distro... which is mental
sounds weird
yeah, take your time... its saturday ๐ ... but there are multiple layers here, and in this context, the layer that is important is db-core... if job consumers are failing and your queues are being poisoned (<---- this fucking word!) then thats a totally different thing, but core-db, at its, erm, core... should function
its really odd... like you cant just extract "a dozen" cpp files and be done with it... you need the whole mysql source to get anything to work... which is a cluster fuck
so i went with the "precompiled lib" route
still need some macro magic on linux tbh to get where headers are etc... but its, effectively, "there"
which reminds me that i need to revist that... i set up a VM specifically for it, then went "all done!" (once the VM was setup)... ๐คฆโโ๏ธ
now i look, i wonder how "extractable" libpq is: https://github.com/postgres/postgres/tree/master/src/include/libpq - will find out - id ideally like to use the cpp source and have things statically linked...
Okay it works ^^
just about to start the "walk the doggos marathon" but, "everything" is working? Or just core-db (unrelated, but interestingly, i worked it out the other day and i walk 15-18km a day with the 5 dogs in their "groups")
core-db works. There's a bug in migrator, when you have migrator in the db that don't exist.
just about to start the "walk the doggos marathon" but, "everything" is working? Or just core-db (unrelated, but interestingly, i worked it out the other day and i walk 15-18km a day with the 5 dogs in their "groups")
Wow, that's plenty. how many walks do you do a day?
core-db works. There's a bug in migrator, when you have migrator in the db that don't exist.
fixable i assume / presume?
Wow, that's plenty. how many walks do you do a day?
3 "groups" (of two), twice a day, about 2-3km a walk
fixable i assume / presume?
Workaroundable for now.. but fixable I think ๐
cool
3 "groups" (of two), twice a day, about 2-3km a walk
So 3 to 4 hours of walk ?
each walk about 30-45 mins i would say, multiplied by 6 (per day)
speed varies on who were taking, if its the two 35kg ones, i cover more distance since they take me for a walk ๐
if its the 25kg ones, we tend to amble...
when its the tiny one... meh, maybe we dont make it 1km... not sure
You must be quite healthy, even with the smoking
And you still have room for another dog in your groups ๐
You must be quite healthy, even with the smoking
it offsets my smoking quite nicely, for sure
And you still have room for another dog in your groups
๐คซ divorces start this way ๐
Oh why, usually tiny dogs like to walk. He's a smeller?
just about to start the "walk the doggos marathon"
Oh have a nice walk!
he hates walking - hes terrified of everything - especially traffic - which we have to pass before we get to the country side
(in fact we havent taken him for a while because of that, and the fact he was crazy ill a while back so cant have any vaccinations etc)
hmmmm
for json field types in db-core
hm, nvm, i'm still not actually sure what's going on
lemme keep messing aronud
I think dce is killing a field but i'm explicitly mentioning it so i'm not sure why ๐ค
quality of life suggestion
when adding an internal id to a record, eg _insertedId, remove them so that I don't have to in my local code ๐
i think technically _insertedId isnt needed now... DatabaseResult has properties now for lastInsertedId and affectedRows that dont need to be in the data
ohhh nicee
yeah, i just need to update a few libs that are dependant on those data level props and get them to use the new result level property
hmm, for the websocket api
it would be nice that we have a unified state variable
I keep getting caught out by trying to send stuff down a connecting socket x)
i'm not sure what's going on because my connected var is true from the callback onOpen
maybe i've got a bug ๐ค
yes nvm, was a simple bug that was hidden away x)
Hmm, i get weird behaviour with websockets and the websocket server
instead of places where a string is expected, I am recieving a UInt8Array
socket server I guess I can understand as its still a pure nodejs api
but when I send out a string and parse it with a client WebSocket, StrMessage(content) is receiving a UInt8Array
@toxic stratus - i think you are using the auto reconnect / replay queries part of db-mysql, right?
Im thinking about making couple of tiny changes:
- reconnect will be true by default
- replay will be true by default
- when disconnection detected, it will immediately try and reconnect, not wait for
autoReconnectIntervalMSand then try -autoReconnectIntervalMSwill come into play if the first reconnection attempt failed
I think all of these will be fine for me
I see no obvious issues that would occur
ive already made the changes and tested locally, all fine
I just posted this to db-core
only issue is, i've literally never messed with custom iterators
so i'm not sure if there's a "better" way to implement it
@velvet lodge
but it works either way
whats the idea? To get the index and record out?
ya
key value iterator
for (index => value in set)
currently you can't get index
seems fine to me... not sure why you would need the index exactly, but no doubt very app specific
just needed the index for debugging purposes tbh
Does core http have a default timeout? Is there a way to turn this off?
I am trying to download a file, but it seems to be closing before it gets the file
i dont think it does, unless the underlying impl does... where are you running this? Browser? Got an example url?
try https://fonts.gstatic.com/s/opensans/v40/memSYaGs126MiZpBA-UvWbX2vVnXBbObj2OVZyOOSr4dVJWUgsiH0B4gaVc.ttf
i am just doing
client.get(variant.tff).then(r -> {
sys.io.File.saveBytes(fileName, r.body);
});
that's a nice url
try using a different target
@uncut phoenix its for debugging sake
Doesn't work with the python target
same with js, but I am getting the error:
/home/logo4poopers/Projects/haxe/CeramicFontGrabber/main.js:116
request.method = "GET";
^
TypeError: Cannot set properties of undefined (setting 'method')```
package;
import http.HttpClient;
class Main {
static function main() {
trace("started");
var client = new HttpClient();
var url = "https://fonts.gstatic.com/s/opensans/v40/memSYaGs126MiZpBA-UvWbX2vVnXBbObj2OVZyOOSr4dVJWUgsiH0B4gaVc.ttf";
client.get(url).then(r -> {
trace("got bytes");
sys.io.File.saveBytes("something.ttf", r.body);
});
}
}
--class-path src
--main Main
--js bin/main.js
--library hxnodejs
--library http
-D no-deprecation-warnings
--cmd node bin\main.js
Huh, that is what I am doing. Is there some issues relating to running client.get inside another callback?
doubtful, you'll have to send a failing sample app - its all fine this end
alright
Up to line 24 works fine, then it crashes
https://github.com/l0go/CeramicFontGrabber/blob/main/src/GrabCommand.hx
i can repro... its a kinda weird way of using promises tbh (i would chain them), but it doesnt really explain the error
the url is different, would that matter?
yeah, if i hardcode the url to the previous on (https://fonts.gstatic.com/s/opensans/v40/memSYaGs126MiZpBA-UvWbX2vVnXBbObj2OVZyOOSr4dVJWUgsiH0B4gaVc.ttf) then it all works fine
could be a redirect that is causing issues - http lib follows redirects, but maybe something is borked there
its not a redirect... its an http, so it should be fine
its such a weird error
something to do with the HttpRequest abstract

ok, its because variant.tff isnt a string (i think) so it doesnt hit the abstracts "fromString" function
oh, do i need to cast it first?
i mean, if you do "" + variant.tff it works, but i dont like it...
also, it is a string apparently
trace("----------------------------------", variant.ttf, Type.typeof(variant.ttf));
src/GrabCommand.hx:26: ----------------------------------, https://fonts.gstatic.com/s/roboto/v32/KFOkCnqEu92Fr1MmgVxIIzc.ttf, TClass({
__name__ : String
})
i think its a GC issue... i think the variant.tff is being cleaned up super fast... at least, thats all i cant think of
because this loop is going exit pretty fast, and "its done" (as i mentioned, its quite weird way to use promises)
would cleaning up the promises fix that?
i am not really that familiar with promises (obviously)
i just mean that this loop is firing off promises "into the wind"... and maybe by the time the request actually gets round to executing its cleared the mem... its a hunch but its defo possible with this nested promises is loops...
gimme a sec, ill show you how i would have chained it (and if the issue persists, ignore all of the above ๐ )
well, it wasnt what i thought ;/
if i do var s:String = variant.ttf; and the use "s" its all fine
but even though variant.ttf is apparently a string, the abstract doesnt think so
ah, hang on, ofc it wouldnt... abstracts are compile time
is .ttf an abstract over string or a straight string?
HttpRequest is an abstract
@:forward
@:forward.new
abstract HttpRequest(HttpRequestObject) {
@:from public static function fromString(s:String):HttpRequest {
return new HttpRequest(s);
}
}
but it makes perfect sense now... variant.tff is dynamic (at compile time), no way for the compiler to know its a string
ahh, yeah that makes sense
so yeah, you will need a cast or something like that to let the abstract know its a string
if its expected to be a string it should just be typed as one before hand
well, it can either be a string, or a HttpRequestObject so you can set headers, etc, etc (hence the abstract)
but yeah, it makes perfect sense now i think
so yeah @uncut phoenix - you'll need a cast to a Std.string... etc... but fwiw, this is the chaining code (that i dont think you technically need, but its better than firing promises off into the wind an not wait from them to complete):
var client = new http.HttpClient();
client.get(API_URL).then(r -> {
trace("GOT API RESULT");
var filtered = Fuzzaldrin.filter(r.bodyAsJson, values["family"], {key: "family", maxResults: 1});
if (filtered.length <= 0) {
Sys.println("Font family not found: " + values["family"]);
Sys.exit(-1);
}
sys.FileSystem.createDirectory(".tmp");
return client.get(API_URL + '/${filtered[0].id}');
}).then(r -> {
trace("GOT FILTERED LIST");
var promises = [];
for (variant in (r.bodyAsJson.variants : Array<Dynamic>)) {
var family = (variant.fontFamily : String).replace(" ", "").replace("'", "");
var fileName = '.tmp/${family}_${variant.fontWeight}_${styleFormat(variant.fontStyle)}.ttf';
trace("ADDING FONT TO LIST", variant.ttf + " => " + fileName);
promises.push(saveFont.bind(client, variant, fileName));
}
return PromiseUtils.runAll(promises);
}).then(_ -> {
trace("ALL DONE!");
}, error -> {
trace("error", error);
});
...
...
private function saveFont(client:http.HttpClient, variant:Dynamic, fileName:String):Promise<Bool> {
return new Promise((resolve, reject) -> {
trace("MAKING REQUEST", variant.ttf);
client.get((variant.ttf:String)).then(r -> {
trace("SAVED BYTES ", fileName, r.body.length);
sys.io.File.saveBytes(fileName, r.body);
resolve(true);
}, error -> {
reject(error);
});
});
}
is there a syntax in Query.query() for limit eg: table.query($uid == 'uid' limit 5)
i couldn't find a test for it
just seems like findOne exists etc
I mean in the query syntax itself
probably not, i just woke up not sure if the concept makes sense anymore lol
table.page(0, 5, query($uid == 'uid')) will create a limit query
.count will create a count(...) query
i also think a different name could be nice, well, another call that is a little clearer... "findFixed" or something
(but i dont like "fixed")
what's wrong with .limit?
table.limt(someQuery) doesnt make sense
table.results(query, 5) perhaps?
also, doesnt seem obvious
although, looking at "find" it could have a "maxResults:Null<Int> = null"... ... ?
page makes sense now that I look at it fully, but i just scanned the function names and didn't look at the params
i think im going to add maxResults also, i think its a useful function param
semantically, im not sure "page" always makes sense
yeah, other times is certainly useful, like when you are actually paging... so the "pageIndex" is nice there
but other times, i just want to find(someQuery, 5)
yeah, exactly
yeah, ill add it as an optional param to "find", and maybe "all"

np - its nice for my enitites2 lib also
MyEntity.findAll(10) for example
anoter thing i need to sort out is is sorting
possibly another param on find / all
Thanks so much! Ffinally having time to look at this. It seems like most of my threads crash tho... Seems like an issue within saveFont
i thought it might be smth to do with saveBytes, but commenting that out does the same thing
i am assuming it is smth on the core-http level then?
more like just a haxe interplay with dynamics
everything seems to be properly cast tho
what does your new code look like?
same as yours
is it trace "SAVED BYTES" or... ...
try return PromiseUtils.runSequentially(promises); , see if that makes a diff
this is a sys target, right? Smells like problems with http's internal thread handler
yeah, just interp target
guess i should try a different one huh
ah yeah, js works
tbf i might be the only interp user outside of macros lmao
yeah, i dont use interp... not sure if there are threading issues there in general
lemme try hxcpp just to be sure
HL is fine
hxcpp also fine
ive added a -D http_no_threads flag...
which will override even if the target is threaded
it does mean that it makes the http lib synchronous though ofc (even though the interface will still be promise based)
i actually think it might be that the default http impl in interp is not supposed to be threaded
could the query expression be "expanded"?
just an idea
query(expr, limit, sort)
i don't think that's too much of an imposition on the abstraction api, is it?
and they could just just be ignored paramaters
i dont think sort and limit should be part of the query
they arent in other db systems (like solr, etc)
it also means, if things dont have a sort in them (like, dunno, maybe browser db thing), you can just implement it as a post processing step
sort, limit and query should defo be seperate "things"
makes sense
i take it by this, there isn't an api exposed?
if not, mind if i expose reverse on recordset?
as a temp solution
Now I just get Unix.Unix_error(Unix.EBADF, "recv", "") but i'll use a diff target for now
fine by me
That sounds like the mbedtls issues that should be fixed on nightly.
Hello, I'm relying heavily on https://github.com/core-haxe/promises for my amqp library to reduce the callback hell necessary for establishing a connection, opening a channel and consuming a queue. I would love to push that library to haxelib but for that I would need promises pushed to haxelib. Is that possible? Also wasn't sure about it, so I created an issue for that
Asking because there were bugfixes made and thenshim has been archived in the meantime
hmmmm, yeah, i get the issue - i wasnt going to release any of these as haxelibs tbh - mainly because the names are too generic "http" for example - its also quite alot of burden to keep things up to date - i suppose i could make an exception for promises since its pretty standalone itself (ie, no other core-haxe deps i dont think)
i do wonder if there is a better way to handle it though... maybe you could just add its a git module or something and somehow package it with your haxelib? It doesnt change very often at all
At the moment I am referencing to the library via readme. Packaging it directly via submodule would be another possibility. But I am currently also investigating whether it is possible to add Support for void promises within the typedef
Problem with void is that the resolve callback ist typed as Void->Void which makes it Impossible to call it then since Haxe then expects a void Parameter
I don't think its intuitive
but I think you can do
function (_) {}
``` It'll pass
i could be remembering wrong there
but there was some trick you could do with tink promises for that
I am thankful we have raw queries in db-core x)
boooo - whats the query?
nothing complex
SELECT * FROM `$table` WHERE `$where` = \'$value\' ORDER BY `$column` DESC LIMIT 1
right, so sort
yeah, fair enough - i'd actually totally forgotten about all that sort and max results stuff above...
completely fine
useful additions though, for sure - as you say - raw is "alright" as a stop gap... but if you are using raw, as in this case, it indicates an api hole
Question about queries, is there a possibility to escape values like you do in PHP with mysqli_real_escape_string?
I am planning to use db-core or at least libmysqlclient for my private Project to get rid of libffi
if you are using the lower level libs, like libmysqlclient for example, then you probably need to escape things yourself (not sure if there is an exposed function for it in the externs, easy to add if not), if you are using the higher level libs, like db-core, then everything should be auto escaped for you automatically... when the sql is built care is taken for that type of stuff, even identifiers are backticked - and where possible, prepapred statements will be used
Ah good to know. Have to take a look at libmysqlclient to get it Work on Linux. At the moment the workflows are at least failing
ah, would defo be good to know if there are issues - it could just be that the UTs are failing because it can connect to a mysql instance (all that stuff is a PITA)...
in fact, actually, i know there arent issues - i know someone who is using it on linux without issues
I think the failing might be for a haxe version
possibly
haxebot uses db core and is running on Linux
Ah okay, then I have to take a deeper look
i would, ofc, suggest you use db-core (ie, the top level abstractions) as, imo (and ofc, im biased) they can save you alot of time, and you can flip db backends at will, etc... and depending on your use case, i would also possibly suggest entities2 (which is, i think, my fav lib, ever)
if I recall it might have to be with haxe < 4.3
Last time I tried libmysqlclient I had compile issues since it couldn't find mysql.h
ah, thats not the same thing then... and actually, now i think about it @old juniper is running on node too
so yeah, there still might be issues on *nix
Also tried to build a Haxe only MySQL connector but failed since it needs Public Key encryption which I didn't want to Dive into ๐
i mean, there isnt even anything except a build.windows here: https://github.com/core-haxe/libmysqlclient ... ... so that'll be why ๐
so yeah, will defo need some rejiggling
Will have a look at it. Want to get rid of the libffi connector I am using at the moment xD
yeah, externs ftw for sure
Hmm yeah running on node right now... but I think I was able to run nearly all tests ( maybe a heaps exception) on dbcore with mysql
oh yeah... valid point - i think i remember that... but how... there is no linux build xml
๐ค
did you maybe make changes and then not commit them?
That's absolutely possible... I think I change the code by hand to connect in db, like added a few lines somewhere...
yeah, i seem to remember that, and i think i remember a convo about needing a macro that builds the buildxml like hxwidgets does
ie, runs some processes to get bits that should be included etc
@velvet lodge what's the kind of api you'd want for sorting? something like this find(query:QueryExpr, sort:Direction, allowRelationships:Bool = true)?
I can take a shot at implementing it
at least for mysql backend
oh maybe its more involved than that, we'd need an option to specify a query expression i think ๐ค
yeah, dont worry, ill do it, i want "maxResults" also
no worries, just thought it was low hanging contribution fruit x)
thought about it for a bit and realised the abstraction adds quite a few things to consider
But escape of Strings would still be necessary to prevent MySQL injections or are you taking care of it in haxe?
in the case of core-db, yeah, its handled internally since it builds the sql queries (you dont write sql in core-db)
that's what I understood
But nevertheless strings need to be escaped by mysql real escape string to prevent sql injections
or am I missing something?
so, if memory serves, db-core builds up prepared type statements (select from x where field=?) then, it passes that down the stack, some plugins handle it natively (ie, using actual prepared staments) and others (like sys.db which doesnt support prepared statements) builds up the actual sql string and that escapes the values
it will replace the ?s with escaped version (_nativeConnection.escape)
nodejs uses the (official?) npm lib, which presumably handles the prepared statement automatically
i was looking for the hxcpp version, but it doesnt use prepared statements... though the commit is: remove sys.db dep for hxcpp (1st iteration - not using prepared stmts)
and indeed, that is not escaping things, but once it uses prepared statments it shouldnt matter
ok
will have a look at libmysqlclient to get it built with linux. Are you preferring to package the libraries with the repository or would it be okay to depend on installed libmysqlclient?
i think you'll need to use whats in the system, the locations can vary so i think we'll need a macro that will build up the @:buildXml dynamically based on system paths (hxWidgets does something similar, but its not a 5 min job)
Oh, found a way to compile it with linux
Extended the build.xml by following:
<section if="linux">
<files id="haxe">
<compilerflag value="-I${include_folder}" />
<compilerflag value="-I${include_folder}/include" />
</files>
<target id="haxe" tool="linker" toolid="exe">
<lib name="-lmysqlclient"/>
</target>
</section>
That works at least for haxe tests/common.hxml --class-path tests -cpp target/cpp
question is right now, why is the windows build also failing in github workflow
sadly I don't have a running windows instance
doesnt have a mysql to connect to
ah okay
then I'll prepare a pull request to extend build.xml by linux and rename it to Build.xml ๐
alot simpler than i thought... might be good to get, dunno, @old juniper to also test
Good look at it later this afternoon
Good evening, took some time to create the pull request but finally I created it and is ready to merge ๐
build worked on my local machine, don't know whether the github workflows are also executed on pull requests
yeah, saw both... will merge shortly.. thanks gents! ๐
in db-core and friends, could we remove dependencies from haxelib.json? I might be using it wrong, but haxelib freaks out when a package that doesn't' exist is added there
wdym
You already have db-core version git installed.
Updating db-core version git ...
db-core was updated
Library db-core current version is now git
Error: Failed with error: No such Project : promises
i'm using it through hmm, so maybe it is fine with normal haxelib
ahhh, i think it's better to have it there
otherwise it would fail with no error
I guess not at that point, but because I am using hmm I don't really have control on the order of installation
does hmm have a config file?
could try putting promises before db-core
yeah, but i think it gets reset each time you add something new to it
not sure if it is intended to be manually edited
it sorts alphabetically by default
is that an "hmm problem"? I mean, surely dependency resolution is important? I dont think the solution is "remove the depenendancy marker"
like, other haxelib.json's have dependencies, surely?
yeah, but they aren't git dependencies
ah
anything in dependencies is assumed to be on the haxelib repo
the problem is if you remove it form there, you have to manually -lib it in your hxml
or maybe you have to anyway ๐ค
i think thats a perfectly fine solution, if it works
because, yeah, it pulls them in automatically in vscode, which is useful (not just for building)
ie, no promises anywhere explicitly included
Lol, I forgot about your haxeui vscode theme. I can send a PR for extraparams later if it doesn't break anything
haxeui vscode theme?
isn't that the haxeui colorscheme?
dont think so... i built my own icon pack, thats about it
ah k, i was just looking at the icons
yeah, those are intellij icons... i just copy and pasted some icon pack and dropped those icons over the top for choice files
can we install from git via extraparams? 
no but you can do --library ...
so you'll still get an error etc... but, if it doesnt show up in vscode (as above) then its not good imo
i think it should / will
I no your no!
--L promises:git:https://github.com/core-haxe/promises
You can even specify a commit hash if you'd like
is that a thing?
Yea
pretty nice
... can you do that in a haxelib.json
but haxelib.json doesnt recognise that?
i didnt even know that was a thing... sounds useful for core-haxe, for sure
tried to move all of the libs into extraParams, but I am getting .haxelib/sqlite3/git/src/sqlite/impl/cpp/SqliteDatabase.hx:4: characters 8-21 : Type not found : sqlite.Sqlite
you'd need to specify the connector in your project - right?
did you move libmysqlite3 also?
no, i am just doing the stuff in my project rn. which worked fine before. here is the entire diff for that package
diff --git a/extraParams.hxml b/extraParams.hxml
new file mode 100644
index 0000000..d474ee8
--- /dev/null
+++ b/extraParams.hxml
@@ -0,0 +1,4 @@
+# Since core-haxe libraries aren't available on the haxelib repo, we import them here
+-L libsqlite3
+-L promises
+-L logging
diff --git a/haxelib.json b/haxelib.json
index 98f2811..5f402c3 100644
--- a/haxelib.json
+++ b/haxelib.json
@@ -8,13 +8,8 @@
"tags": [
],
"releasenote": "0.0.0",
- "dependencies": {
- "libsqlite3": "",
- "promises": "",
- "logging": ""
- },
"classPath": "src",
"name": "sqlite3",
"description": "",
"url": ""
-}
\ No newline at end of file
+}
this is the sqlite3 lib
oh right
https://haxe.org/manual/compiler-usage.html docs if you ever wanna come back to it
oh, how does that affect things?
actually, no, nvm, it should be fine... haxelib.json is still there, right?
ye
yep
weird, no idea
i wonder if haxelib does smth fancy
looks like libsqlite3 is where sqlite.Sqlite and what not are defined
yup
are haxelibs just an abstraction over -cp or do they have their own compilation step?
@frosty locust sorry for pinging, would you happen to have any knowledge in this domain of haxelib?
They're just an abstraction over -cp.
You can use haxelib path myLib to check the flags passed to the compiler.
Yeah, it's just -cp with a couple more compilation flags if the haxelib needs them
I managed to pack promises into my amqp library with some macro setting class path correctly
Some question about libmysqlclient: I would like to call real_escape_string, how do I do that / what do I've to do to add a wrapper
are you using libmysqlclient directly?
oh, i was going to say just use it from here: https://github.com/core-haxe/libmysqlclient/blob/main/src/mysql/MySqlClientConnection.hx
but it doesnt seem to be exposed
https://github.com/core-haxe/libmysqlclient/blob/main/src/mysql/RawMySqlClient.hx#L22-L23
externs are there, so really these should be exposed here: https://github.com/core-haxe/libmysqlclient/blob/main/src/mysql/MySqlClientConnection.hx
ok, will have a look at it.
I'm using libmysqlclient directly, yes
replaced my libffi library by libmysqlclient
just some question: Shouldn't to:RawPointer<cpp.Char> of type ConstCharStar?
In case it's correct, how do I pass a string variable in there
which function? depends if its supposed to be char* or const char*
ah okay
found something in the haxe channel from you regarding the real_escape_string ๐
Will play a bit around with that
What do you think about following code for exposing real_escape_string? Another question shall I also expose real_escape_string_quote?
public function real_escape_string(value:String):String {
if (_handle == null) {
throw new Exception("internal handle is null");
}
var len = NativeString.utf8Length(value) * 2 + 1;
var na = NativeArray.create(len);
var p = Pointer.arrayElem(na, 0);
RawMySqlClient.real_escape_string(_handle, p.raw, value, value.length);
return untyped __cpp__("{0}", p.raw);
}
return untyped cpp("{0}", p.raw); does that work?
looks like it works, still testing around
might want to try return new String(untyped cpp("{0}", p.raw)) or something like that, feels safer (could be wrong ofc)
also, as for exposing it, i would say that this function should be called "escapeString" and should be here: https://github.com/core-haxe/libmysqlclient/blob/main/src/mysql/MySqlClientConnection.hx ... ... ?
I put it already into MySqlClientConnection, but will rename it to escapeString
will try it with return new string ๐
i could be being over cautious, just not sure what is going to happen to that buffer, might get reclaimed or something
could do, wont hurt for it to be there
ok
ahm what about the return of real_escape_string and the quote one? In cpp it returns unsigned long, so shouldn't the return be Int64?
probably int will be fine? I mean, technically its not "right" but i doubt anyone is going to be using strings of that size
ok, just asking because of error handling
so how to check for error, when the api states Because mysql_real_escape_string() returns an unsigned value, you can check for -1 by comparing the return value to (unsigned long)-1 (or to (unsigned long)~0, which is equivalent).
would uint max value be fine
damn arch linux ๐
It's not finding mysql_real_escape_string_quote since the package is mariadb ๐
humm... have to see whether a check for existance of mysql_real_escape_string_quote is possible since it's mysql only ๐e
at least the mysql_escape_string expose is working ๐
do you want to stick to mysql or mariadb? Seems that linux distributions switched from mysql to mariadb which has a drop in replacement for libmysqlclient but removed a bunch of functions like mysql_real_escape_string_quote
i think the lowest common denominator, so imo, just drop mysql_real_escape_string_quote, it was a "nice to have" anyway, mysql_real_escape_string is probably enough... ?
okay, then I would go and remove the mysql_real_escape_string_quote in favor of mysql_real_escape_string
So, I made following modifications:
- Change return value of
real_escape_stringto cpp.Uint64 to be able to check for error - Added escapeString function which exposes real_escape_string
- Removed
real_escape_string_quotefrom RawMySqlClient
Will do a bunch of further tests with my project and then submit a pull request
Translated cpp code looks at the moment like this:
::String MySqlClientConnection_obj::escapeString(::String value){
HX_GC_STACKFRAME(&_hx_pos_63a675c029f1cf5e_88_escapeString)
HXLINE( 89) if (::hx::IsNull( this->_handle )) {
HXLINE( 90) HX_STACK_DO_THROW( :
:Exception_obj::_alloc( HX_CTX ,HX("internal handle is null",88,4f,70,9c),null(),null()));
}
HXLINE( 93) int len = ((_hx_utf8_length(value) * 2) + 1);
HXLINE( 95) ::Array< char > na = ::Array_obj< char >::__new(len);
HXLINE( 97) ::cpp::Pointer< char > p = ( (::cpp::Pointer< char >)(::cpp::Pointer_obj::arrayElem(na,0)) );
HXLINE( 99) MYSQL* result = this->_handle;
HXDLIN( 99) char* result1 = p->get_raw();
HXDLIN( 99) ::cpp::UInt64 result2 = ::mysql_real_escape_string(result,result1,value.utf8_str(),value.length);
HXLINE( 101) if ((result2 == ::hx::TCast< ::cpp::UInt64 >::cast(-1))) {
HXLINE( 102) HX_STACK_DO_THROW( :
:Exception_obj::_alloc( HX_CTX ,HX("mysql_real_escape_string failed!",0f,53,c1,d0),null(),null()));
}
HXLINE( 105) return ::String(p->get_constRaw());
}
which looks valid to me
yeah, me too
only thing which might be incompatible is uint64, because real_escape_string uses normally unsigned long
Have to see whether I can reflect that one
but generally it seems to work
got it ๐
Used UnsignedLong as return type ๐
have to test whether following c++ construct works:
unsigned long result2 = ::mysql_real_escape_string(result,result1,value.utf8_str(),value.length);
if (::hx::IsInstanceEq( result2,::hx::TCast< unsigned long >::cast(-1) )) {
HX_STACK_DO_THROW( :
:Exception_obj::_alloc( HX_CTX ,HX("mysql_real_escape_string failed!",0f,53,c1,d0),null(),null()));
}
looks much better with UnsignedLong return for real_escape_string and untyped __cpp__("unsigned long errorReturn = (unsigned long)-1"); ๐
First time working with exposing c++ externs, so sorry for the questions ๐
no bother, i didnt actually know about the UnsignedLong type on hxcpp tbh ๐
the UnsignedLong was existing in RawMysqlClient.hx
@:native("unsigned long")
extern class UnsignedLong {
}
it was used already for some other extern
hxcpp uses uint64 types which are cross platform
sadly libmysqlclient uses unsigned long, so I had to work around that a bit ๐
funny, now the github workflows are executing automatically
i think they will fail anyway because of mysql not being setup, its a todo list somewhere to sort
Shall I prepare a pull request for https://github.com/core-haxe/mysql/blob/main/src/mysql/impl/cpp/DatabaseConnection.hx so that it uses the new escapeString method?
or would that be the wrong place within prepareSQL
within sys there is an escape call for strings
seems sensible, eventually that file will move to prepared statements, but in the meantime, certainly seems safer / apprporiate
okay, then I'll fork and adjust it ๐
thanks! all very much appreciated ๐
do you have any possibility to test the new escape within mysql?
Since I'm using libmysqlclient directly and there are no tests I cannot test it
yeah, i should be able write UTs for it, the UTs work locally , just not as github actions
created a pull request that for cpp escapeString of _nativeConnection is used
sadly crypto of HaxeFoundation doesn't have a publicEncrypt method. In case it would be there I could have continued my haxe only mysql client ๐
tbh, i kinda feel like, for things like this, its usually better to delegate to an external lib... otherwise i think you are always playing catch up
I guess it depends
but yes a cpp mysql extension which is exactly what I need is much easier ๐
@velvet lodge @uncut phoenix @wide solstice We CAN add github dependencies via haxelib.json!
ooooo
"dependencies": {
"promises": "git:https://github.com/core-haxe/promises"
}
Also when I want to publish my package to haxelib? That is why I added promises as submodule with macro as source extending the class-path
thats pretty nice... i wonder if that will still show up the deps in vscode... @uncut phoenix - does that sort your hmm problem?
I haven't tried it with a uploading directly to haxelib
these libs arent on haxelib so thats wont be an issue
Also when I want to publish my package to haxelib?
no, for uploading to haxelib all dependencies need to be on haxelib too
ah, sorry, got what NB meant now, thought that was to me
so right, Barbaric-Tofu will still need his "copy" solution in place ๐
still useful for core haxe I guess tho
yeah, be interesting to know if that sorts logo's HMM issue
I am guessing it would. Iโll test it later
Does db-core have a syntax for is null or is not null ?
oh lol
literally the last commit (for tests)
any reason to not do it for logging and queues-core?
thanks for volunteering
lol
would be quite nice to be able to never need to manually type that url out again tho
yeah, i think if this works (as in vscode shows it correctly - which it probably will) then all core-haxe haxelib.jsons should do the same (which ill do at some point)
@velvet lodge mysql doesn't work on hxcpp
trying to run an application gives the following errors
libssl-3-x64.dll was not found
libcrypto-3-x64.dll was not found
test case is simple
import db.DatabaseFactory;
import db.IDatabase;
class Main {
static function main() {
var db:IDatabase = DatabaseFactory.instance.createDatabase(DatabaseFactory.MYSQL, {
database: "test",
host: "localhost",
user: "admin",
pass: "pass"
});
db.connect().then(function(resp) {
trace('connected');
}, (err) -> trace(err));
}
}
oh is this a thing?
i thought it would just work
i do have it somewhere but maybe not installed ๐ค
ahh, this was it - thanks!
i didnt actually know about the dep, but it makes sense its using ssl... just had it installed so never knew about it
i guess that means you'd need to distribute the .dlls with any app shipped? Not sure how i feel about that... would prefer to statically link it
yeah it's not very ideal
im sure openssl can be used from source and included in with libmysql
its a biggun though https://github.com/openssl/openssl
looks like it might be able to get away with crypto (https://github.com/openssl/openssl/tree/master/crypto) and ssl (https://github.com/openssl/openssl/tree/master/ssl) which seem simpler and possibly standlone
also not sure how to tell libmysql to not use dlls... but there is probably a call spec in the header file somewhere
i wouldn't statically link it on linux
its arguably not a great idea to statically link anything "security" like on any system
yeah, hashlink has faced issues with that
generally, i prefer statically link (on all OS's) but i think in this case, its a valid exception
it is big, defo... and, mysqlclientlib is precompiled too (ie, .lib, not source)
might be able to finagle a way to use a statically linked version of openssl, but given the context, i dont think its the right way to go
so better to just make the dependency known in the readme or something (i didnt even know about the dep, but makes perfect sense)
you could probably check for it at compile time and give a more in depth error
readme good enough for now lol
yeah, seems overkill when the readme can specify it, the error was pretty clear imo
libssl-3-x64.dll was not found
libcrypto-3-x64.dll was not found
yeah
yeah, i didn't even consider mysql being the issue
cause i saw the tests passing ๐
this broke my local build
--------------------------------------------------------------------------------
build: glint::analytics::client
--------------------------------------------------------------------------------
- executing haxe (html5.hxml)
Error: Error: Library promises version git is not installed
Error: Error: Library promises version git is not installed
yup, confirmed, its fine without it... sorry, reverting ๐
issue is that the dep specifies git and i use them as dev, so change is a no-go for me im afraid
yeah, i might look at (but not any time soon) publishing everything to haxelib but under things like core-haxe.http... it would mean -lib would have to change, but actually, -lib core-haxe.http is probably nicer really
I'm using
-lib haxeui-blank
--macro haxe.ui.macros.ExternGenerator.generate('src-externs')
--macro include('haxe.ui.components')
--macro include('haxe.ui.containers')
--macro include('haxe.ui.containers.dialogs')
--macro include('haxe.ui.containers.menus')
--macro include('haxe.ui.containers.properties')```
But when compiling against those externs I receive
```src-externs/haxe/ui/backend/ComponentBase.hx:8: characters 124-153 : Not enough type parameters for haxe.ui.core.IEventDispatcher```
Any thoughts?
might be a bug in the generator, i defo remember "hand fixing" a few little things
ah, thanks
For the record to fix after compile:
- change haxe.ui.backend.ComponentBase.hx line 8 by changing
extern class ComponentBase extends haxe.ui.backend.ComponentSurface implements haxe.ui.core.IComponentContainer implements haxe.ui.core.IEventDispatcher implements haxe.ui.core.IClonable<haxe.ui.backend.ComponentBase> {
to
extern class ComponentBase extends haxe.ui.backend.ComponentSurface implements haxe.ui.core.IComponentContainer implements haxe.ui.core.IEventDispatcher<haxe.ui.events.UIEvent> implements haxe.ui.core.IClonable<haxe.ui.backend.ComponentBase> { - copied haxe.ui.util.Color from git over extern
- copied haxe.ui.validators.Validators.hx from git over extern
Seems to work. Since I copied Color and Validators over extern there may be some file size increase but it was easiest
Nope. IDK. Stopping for now with
haxe.ui.containers.TabView is not a constructor ButtonsView ComponentMacros.hx:900
Sorry for the noise
Turns out the issue was a line in the xml I was loading. layout="vertical" was throwing issue.
<box width="100%" height="100%" layout="vertical" >
Anyways, it is working. Woohoo. Actually take up more file size, but there it is
https://haxeuitest.github.io/TestApp/html5/index.modular.html
How are you managing dependencies right now?
just with a hxml?
i might just use crobes' haxe gsm
i just read gsm as gasm ๐
yup, just an hxml
actually, im using a haven.xml file, but really that just generates an .hxml
nice... are you including the whole of haxeui in the module / client?
Below is the extern creator
https://github.com/haxeuitest/TestApp/blob/main/html5.GenerateExterns.hxml
This is the Host. Not sure I need the macros in that (tested locally it looks like I do). The DCE that is in here, add/removing had no effect besides smaller.
https://github.com/haxeuitest/TestApp/blob/main/html5.host.hxml
This is the Client. I just converted the box with layout vertical into vbox for now
https://github.com/haxeuitest/TestApp/blob/main/html5.hxml
You can see it working here https://haxeuitest.github.io/TestApp/html5/index.modular.html
the buttons, labels buttons are in the host
Cool ๐ Just curious why in core haxe and not in haxeui? Is it using some core haxe stuff?
Discussion was intended to focus on modular from core haxe which is outside of HaxeUI sphere.
So yeah, if you include all of haxeui in the modular host (https://github.com/haxeuitest/TestApp/blob/main/html5.host.hxml#L11-L15), then you wont see any particular size decrease - in fact, as you noticed, you may see a since increase since you are including everything. The idea would be to only include the classes you want in the modular host... I have some other ideas about including the externs in host and the concrete impls in modules (that would be loaded dynamically), i already do that for the "entities" in the glint application im writing, ie, the host has no clue about the the "enitites", and other modules use them via externs, but once the entities module is loaded, it provides the impls at runtime
(there is no reason why haxeui component impls - or anything really - couldnt work the same way)
makes sense. My main goal was to allow compile times to decrease. Reducing host would likely mean more compile times? Sounds good though. Defs nice for release.
Yo Ian, I have some info regarding websockets
i've managed to connect to a socket via wss
on native/hxcpp
I had to change this line from sleep(0) to sleep(0.1) https://github.com/core-haxe/websockets/blob/main/src/ws/impl/sys/WebSocket.hx#L148
it was completely blocking my app
that's the "only" thing I had to do really, so i'm not sure how valid that change is or complete, but for some reason ws isn't working and errors out with an error SSL - An invalid SSL record was received
even though it's meant to just be a local socket connection
hmmmm
its probably a valid change, but i think that stuff need work anyway, this is still "half ported"
just thought i'd mention it because i think this was on your todo list
not sure about the wss though, i would have expected it to "just fail"
import haxe.Json;
import ws.WebSocket;
class Main {
static function main() {
trace("Hello, world!");
var ws = new WebSocket('wss://stream.bybit.com/v5/public/spot');
ws.onopen = () -> {
trace('opened');
ws.send(Json.stringify({
req_id: "test", // optional
op: "subscribe",
args: ["kline.1.BTCUSDT"]
}));
}
ws.onerror = (errr) -> {
trace(errr);
}
ws.onmessage = (message) -> {
trace(message);
}
ws.onclose = () -> {
trace('socket closed');
}
}
}
``` here's a testcase if you want to visit it at some point
might require git hxcpp i'm not sure
it's also interesting to note, i only need to adjust the sleep for ceramic
https://github.com/core-haxe/websockets/blob/main/src/ws/impl/sys/WebSocket.hx#L66 - i dont know why that doesnt just throw this exception
ah, it probably screws with the MainLoop
here's my modded websockets file
ah, you removed the throw
makes one other change (removes the throw for not implemented)
but the throw was there because its not implemented / tested - so im not surprised it didnt work ๐
but it does work!
except it didnt right? It failed the SSL handshake
so, hang on, wss worked and ws failed an SSL handshake?
it's backwards ๐
yes!
very odd
i've got a local websocket server websockets one
afaik that requires a ws connection
right, ill have to play with this and get some UTs going
and this is ws, not wss?
try {
client = new WebSocket("ws://localhost:8124");
client.onopen = onOpen;
client.onerror = onError;
client.onmessage = onMessage;
} catch (e) {
trace(e);
}
yep!
very weird - maybe i screwed something up when i moved the file over, not sure
well, good that wss works i guess, thats one less thing...
maybe, the whole situation seems odd to begin with ๐
what lib are you using for your server?
same lib
Wait you are actually using core-haxe/websockets?
yeah
oh, hang on so you are using core-haxe/ws for server too... right...
not terribly important i don't think
tbf i would probably just use http if I knew better a few weeks ago
core-haxe one is still incomplete, i moved for a reason but i've been running it for so long i can't recall what it is now
hang on - there are no impls here...
yeah
ah, you are using the node server
still think there is something weird going on though... i still would have expected that to work with ws i think
https://github.com/core-haxe/websockets/blob/main/tests/cases/TestClientWithNativeNodeServer.hx some semi decent unit tests there thought ๐ฅณ
Ah, for this specific project an http server would have made more sense compared to a websocket one
right
it has just complicated things, nothing wrong with websockets for other stuff though
I wonder if the server is booting in wss mode by default
not sure, maybe... thought i use it in unit tests and its ws ther
i just ran the unit tests for hxcpp and they pass
and they use ws
actually all those haxe targets UTs pass (which is pretty cool actually)
very odd
i wonder if git hxcpp has broken something?
i'm pretty confused by the server here
how does the server unit test work when there's no implementation
i've shadow'd the module locally so that's why it works for me
oh no i haven't
the package structure is misleading x)
nodejs implementation is under ws/extern/nodejs
and your unit tests references the externs file instead of the impl file
lol
i never saw that
@velvet lodge could you run the tests there, i'd like to see if those pass ๐
Oh! I understand why normal ws fails
I'm trying to connect to through the ssl server
that pr will have the same issue i suspect
it uses a prebuilt nodejs server, not its own one (which as you say doesnt exist). I want "two sets" of UTs - 1 set against an external, 3rd party lib - nodejs in this (to verify compatibility) and another set against its own server impl
yes, all makes sense now
and i've got ws and wss running locally
now i need to figure out why db isn't working
i should really test things out more often on native ๐
debugging stuff over here is a pita
Memory exhausted.
try HXCPP_GC_BIG_BLOCKS.
this was a fun one
