Some questions regarding JS extensions

To discuss development of addons / skins / customization of MediaMonkey.

Moderators: jiri, drakinite, Addon Administrators

Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Some questions regarding JS extensions

Post by Christoph »

Hey,
at first, thanks for this great reboot of MediaMonkey. Basing it largely on web technology is a very nice way to simplify addon development and get it in line with other tools based on frameworks like Electron. :) Were there any reasons to not base it on Electron?

While getting my hands dirty working on some scripts I stumbled upon the following things. Maybe there already are solutions I'm missing.

1. Is there any builtin way for escaping strings for use in a sqlite query? Methods like

Code: Select all

getTracklist()
only accept a single query parameter. So if for example the query includes some user input it needs to be escaped to be handled securely. Currently I'm doing the escaping on my own, however usually database adapters provide some ways for this.
2. Are there any TypeScript definitions available or planned? This would enhance the developer experience.
3. Is there any way with

Code: Select all

QueryResults
to retrieve all field names returned by the query? At the moment I explicitly pick the fields by name and map them in an object.

Code: Select all

QueryResults.fields
allows accessing the values by index but also doesn't provide a way to retrieve the column names.
4.

Code: Select all

window.prompt()
doesn't seem to focus the input field by default. Can this be changed?

Thanks in advance!
PetrCBR
Posts: 1763
Joined: Tue Mar 07, 2006 5:31 pm
Location: Czech
Contact:

Re: Some questions regarding JS extensions

Post by PetrCBR »

re electron) we do not want to be dependant on any 3rd party framework
re 3) you can use QueryResults.names ... it will return string list
re 4) will check
How to make a debuglog - step 4b: viewtopic.php?f=30&t=86643
Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Re: Some questions regarding JS extensions

Post by Christoph »

Thanks for the response.

Regarding 3)
Thanks. That worked:

Code: Select all

QueryResult.names.forEach((column) => console.log(column.toString()));
Is this considered a stable public API as it isn't documented here? https://www.mediamonkey.com/webhelp/MM5 ... sults.html
drakinite
Posts: 965
Joined: Tue May 12, 2020 10:06 am
Contact:

Re: Some questions regarding JS extensions

Post by drakinite »

2) I actually did start work on a .d.ts file a while ago, which contained globally accessible methods and such. If it'd be helpful to you, like to help your IDE with auto code completion and what not, I can continue on it and we could possibly release it with the code.
Image
Student electrical-computer engineer, web programmer, part-time MediaMonkey developer, full-time MediaMonkey enthusiast
I uploaded many addons to MM's addon page, but not all of those were created by me. "By drakinite, Submitted by drakinite" means I made it on my own time. "By Ventis Media, Inc., Submitted by drakinite" means it may have been made by me or another MediaMonkey developer, so instead of crediting/thanking me, please thank the team. You can still ask me for support on any of our addons.
Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Re: Some questions regarding JS extensions

Post by Christoph »

drakinite wrote: Sun Apr 11, 2021 2:38 pm 2) I actually did start work on a .d.ts file a while ago, which contained globally accessible methods and such. If it'd be helpful to you, like to help your IDE with auto code completion and what not, I can continue on it and we could possibly release it with the code.
Thanks for the offer. :) If there's a general demand for it and/or the definitions can be produced automatically from your dev workflow, then sure, that would be awesome. However if it would be just for me then maybe it's too much work?

For my simple project I created the definitions I needed but they barely scratch the surface of the whole MM5 API. So for my purposes I'm fine with creating the needed definitions as I go.

An answer to 1) would be appreciated - especially for other developers, as this would encourage safe(r) addon development. :)
drakinite
Posts: 965
Joined: Tue May 12, 2020 10:06 am
Contact:

Re: Some questions regarding JS extensions

Post by drakinite »

Yep - I'm checking with Ludek for a definitive answer on number 1, but my guess is that the answer is no. I'm not sure if there are any database calls that are done by direct input from the user.
And if the user inputs any malicious sql-escaping stuff, I could be wrong, but the worst that can happen is having their own database corrupted (which they should probably be backing up anyways, just in case).

As for MediaMonkeyServer, that is a project that needs more security in its sql statements. (I'm in the process of switching all sql queries in MMS to prepared statements; though I don't believe the MM5 db currently uses prepared statements.)
Image
Student electrical-computer engineer, web programmer, part-time MediaMonkey developer, full-time MediaMonkey enthusiast
I uploaded many addons to MM's addon page, but not all of those were created by me. "By drakinite, Submitted by drakinite" means I made it on my own time. "By Ventis Media, Inc., Submitted by drakinite" means it may have been made by me or another MediaMonkey developer, so instead of crediting/thanking me, please thank the team. You can still ask me for support on any of our addons.
Ludek
Posts: 4945
Joined: Fri Mar 09, 2007 9:00 am

Re: Some questions regarding JS extensions

Post by Ludek »

Re 1) and escaping in getTracklist()
Can you please give me a concrete example of what you need to manually escape now? Do you mean the double-ampersands ?
Ideally the escaped and unescaped example.

Thanks!
Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Re: Some questions regarding JS extensions

Post by Christoph »

Thanks to you both for your answers and your support.

Let's take this query as an example:

Code: Select all

SELECT * FROM Songs WHERE SongTitle LIKE '%a%'
The expression %a% may be taken from a search input. Because it's encapsulated with single quotes, entering a search expression like %a'% breaks the query and leads to an injection:

Code: Select all

SELECT * FROM Songs WHERE SongTitle LIKE '%a'%'
So SQlite requires escaping the single quote by adding an additional single quote:

Code: Select all

SELECT * FROM Songs WHERE SongTitle LIKE '%a''%'
It's the same when using double quotes for encapsulating and contained double quotes:

Code: Select all

SELECT * FROM Songs WHERE SongTitle LIKE "%a""%"
Maybe there are other chars that need escaping.

So based on the string encapsulation the specific quote character needs to be escaped.

For easy use I've created a small tagged template that handles escaping. It's used like this:

Code: Select all

app.db.getTracklist(Sql.query`SELECT * FROM Songs WHERE SongTitle LIKE ${searchString}`, -1);
Because it's a tagged template it automatically separates template expressions which then get escaped correctly.

Inserting unescaped values works by using a special wrapper method:

Code: Select all

app.db.getTracklist(Sql.query`SELECT * FROM Songs ORDER BY ${Sql.raw(sorting)}`, -1);
It also supports arrays for things like IN searches:

Code: Select all

app.db.getTracklist(Sql.query`SELECT * FROM Songs WHERE IDSong IN (${songIds})`, -1);
If you're interested I can send you the .ts file but please don't take it as bulletproof.

Regarding possible damage:
Yeah, I don't know what may happen in a worst case. I think a common scenario would be a failing script in case somebody uses single/double quotes in a search. Damaging a users database could be a worst case scenario, yes.

Being a web developer myself I'm quite sensitive to these things so sorry if I'm a bit too harsh about this. :)
Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Re: Some questions regarding JS extensions

Post by Christoph »

The MM5 search bars may be affected by this (build 2330)

Imagine a song with title aaa'aaa.
Searching for aaa'aaa returns the song which is correct.

However if the song title is aaa"aaa I can't find it by looking for aaa"aaa.
On the other hand searching for aaa'aaa or a'a'a'a'a'a also returns the song. Maybe because of some normalization that strips single quotes?
So maybe the search string is encapsulated with double quotes which leads to double quotes breaking the search.
Ludek
Posts: 4945
Joined: Fri Mar 09, 2007 9:00 am

Re: Some questions regarding JS extensions

Post by Ludek »

Yes, we internaly use doubleQuotes() function when constructing queries, we always use just ampressand as the quote char and for all input values doubles the ampersands by using this function. But as we currently construct 99% of the queries in the native Delphi part (compiled MME.exe code) then it is not available in JS.
Nevertheless we could add some function for doubling ampersands to utils.js (there are already similar utility functions)
Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Re: Some questions regarding JS extensions

Post by Christoph »

Yeah, a utility method and hint in the docs could help for these cases, thanks. :)
Did you mean double quote (") instead of ampersand (&) as your quoting character?
Ludek
Posts: 4945
Joined: Fri Mar 09, 2007 9:00 am

Re: Some questions regarding JS extensions

Post by Ludek »

Yes, substitution of ampersand --> apostrophe :-)

Sorry, probably a little bit overworked these times, but will get back to you soon! ;-)
Christoph
Posts: 243
Joined: Fri Jan 25, 2008 12:43 pm

Re: Some questions regarding JS extensions

Post by Christoph »

Thanks, take your time. :)
Post Reply