Hacker News new | ask | show | jobs
by bastawhiz 2046 days ago
This article doesn't use the word "permission" or "validation", which is concerning.

The only mention of security hand waves away the idea of access control to a "thin back end". That's the whole point of this post! The details of this are critical!

> you can define an API that takes an SQL query from the client, runs it, and returns the results. This query can be run under a database user account that has only read access, that too only to the friends table. This can accommodate unforeseen uses, like getting the number of friends rather than the actual list. Or if there’s a search box where the user can filter his friends, you can do a LIKE query. Or you can limit the number of friends returned to how many will be displayed in the UI.

Without mentioning how this has been solved elsewhere, this is an incredibly reckless piece of advice. For one, it's nearly impossible to parse and check an arbitrary SQL query for malicious intent. Besides ensuring that queries that should read only read, you also need to make sure that queries aren't designed to intentionally DoS your DB.

And moreover, it now passes the responsibility of query performance to the FE engineer. Are appropriate indexes in place? Does the query make inappropriate JOINs?

And on top of all of that, schema changes now mean that you need to update your front end code. This means guaranteed hard downtime, because you can't control what JS folks are running in the browser.

There's a lot wrong with the ideas presented here.

3 comments

Author here.

> This article doesn't use the word "permission" or "validation"

The article talks about it multiple times: using a database user account with limited privledges, exposing some tables but not others, exposing read but not write access, giving users access only to data they own.

> it's nearly impossible to parse and check an arbitrary SQL query for malicious intent

Which is why the article doesn't propose trying to parse and check queries for malicious intent.

> it now passes the responsibility of query performance to the FE engineer. Are appropriate indexes in place? Does the query make inappropriate JOINs?

No, in the proposal, we have backend engineer(s) to advise and assist frontend engineers. Having appropriate indices and JOINs doesn't mean you have a layer that doesn't add business value. And when it does add value, write it!

> schema changes now mean that you need to update your front end code. This means guaranteed hard downtime, because you can't control what JS folks are running in the browser.

I don't know if I understood you, but you can just force a refresh in the browser.

> you also need to make sure that queries aren't designed to intentionally DoS your DB.

That's a valid point I didn't think of.

> There's a lot wrong with the ideas presented here.

It's hard to take your criticism seriously when many of your reactions are a result of your own misunderstanding of the proposal.

While I largely share your broader concerns,

> ensuring that queries that should read only read

seems to be the purview of the DBMS, setting appropriate account permissions. The bit you quoted said "a database user account that has only read access".

On MySQL, you can run SLEEP() or BENCHMARK() as a read-only user to your heart's content. You cannot restrict access to these functions, and letting the wide internets play with them will bring your server to its knees by clogging up all connections and hogging up its CPUs.
I wasn't contradicting the bits about DOS attacks, which remain very much a concern, even when no one is malicious.
Solution: Don't use MySQL
PostgreSQL's SQL is Turing-complete. Imagine the possibilities!
All rdbms have similar issues with built-in functions. Plus you can easily create pathological queries that do the same.
This assumes you only deal with non-sensitive data (e.g. user profiles).

Never mind that, how do you prevent denial of service attacks? I can run any allowed query on that database. Including 50 times cross join of the table I can read, sorted by random.

> This assumes you only deal with non-sensitive data (e.g. user profiles).

Not really. You can do row or column level permissions. Details very much depend on your DBMS.

> Never mind that, how do you prevent denial of service attacks?

I have no real answer, and I never suggested that I would. Denial of service attacks (deliberate or accidental) are one piece of the "broader concerns" that I very much share.

In theory, a sufficiently advanced DBMS might be able to assign users quotas, and if your users are stable that may be sufficient for some use cases, but I am skeptical.

Firebase was recommended in the post, which has built in security rules and auth.
Then the author should really search-and-replace every instance of "database" with "Firebase"; their advice doesn't work very well otherwise.
The article literally says "Instead, you can define an API that takes an SQL query from the client, runs it, and returns the results," so...