How do I use Slick to call a stored procedure?
I want it to be type safe / injection safe. (ie, I don't want any SQL query strings in my code...)
According to the docs, Slick includes "Type-safe support of stored procedures" (http://slick.typesafe.com/doc/1.0.0/introduction.html)
But I do not see any example in the docs of how to do it.
That's a typo. It should read "Type-safe support of scalar database functions". At the moment you have to use plain SQL to call stored procedures.
Also see https://groups.google.com/forum/#!searchin/scalaquery/procedure/scalaquery/BUB2-ryR0bY/EFZGX663tRYJ
Related
My application uses the SQLalchemy ORM code exclusively to define the database schema. For the database, two uses cases exist. For the sake of simplicity, I'll call the first the "simple" use case, the second the "complex" use case.
Both use cases go through my application. Both use cases generate JSON data. However, the use cases differ on how the JSON data is queried later on; consequently, the reports that run on the database make use of the same application/library code, but construct different queries on the JSON attributes of the schema.
Now, the simple use case employs exclusively SQLite, while the complex use case relies on PostgreSQL exclusively. I would like to use JSONB on PostgreSQL, because all reports that run against the PostgreSQL database cast all JSON fields to JSONB. SQLite, however, does not have JSONB, obviously. Still, I would like to use the same ORM code in both cases.
How can I make SQLalchemy use JSONB when my code connects to a PostgreSQL database, but JSON in all other cases? I.e., can I change the facade of JSON for the PostgreSQL dialect?
As per the helpful people in the SQLalchemy forums, the definition is actually pretty simple:
Column(
"my_column",
sqlalchemy.JSON().with_variant(
sqlalchemy.dialects.postgresql.JSONB(),
"postgresql"
)
)
I am working on writing a Spring Java program accessing data from Athena, but I found that Athena JDBC driver does not support PreparedStatement, does anyone have idea about how to avoid SQL injection on Athena?
Update: I originally answered this question in 2018, and since then Athena now supports query parameters.
Below is my original answer:
You'll have to format your SQL query as a string before you prepare the query, and include variables by string concatenation.
In other words, welcome to PHP programming circa 2005! :-(
This puts the responsibility on you and your application code to ensure the variables are safe, and don't cause SQL injection vulnerabilities.
For example, you can cast variables to numeric data types before you interpolate them into your SQL.
Or you can create an allowlist when it's possible to declare a limited set of values that may be allowed. If you accept input, check it against the whitelist. If the input is not in the allowlist, don't use it as part of your SQL statement.
I recommend you give feedback to the AWS Athena project and ask them when they will provide support for SQL query parameters in their JDBC driver. Email them at Athena-feedback#amazon.com
See also this related question: AWS Athena JDBC PreparedStatement
Athena now has support for prepared statements (this was not the case when the question was asked).
That being said, prepared statements aren't the only way to guard against SQL injection attacks in Athena, and SQL injection attacks aren't as serious as they are in a database.
Athena is just a query engine, not a database. While dropping a table can be disruptive, tables are just metadata, and the data is not dropped along with it.
Athena's API does not allow multiple statements in the same execution, so you can't sneak a DROP TABLE foo into a statement without completely replacing the query.
Athena does not, by design, have any capability of deleting data. Athena has features that can create new data, such as CTAS, but it will refuse to write into an existing location and cannot overwrite existing data.
Currently, I have a PostGIS DB, and I have the basics working. However, I am inserting directly into the database using pg_query. I have been recommended to use pg_query_params to help prevent against SQL injections, but am unsure how to implement this. Below is a cut-down example of my current insert statement for a site location. How would I, for example, utilise pg_query_params with this example? I know I will have to implement further security, but it is a starting point.
EDIT: I was going to use the drupal form API but it gave me headaches. I realize that would do a lot of this stuff automatically.
$sql = "INSERT INTO sites_tbl (river_id ,sitename ,the_geom) VALUES ('$_POST[river_id]','$_POST[sitename]',st_geomfromtext('POINT($geomstring)',27700))";
$result = pg_query($sql);
Because you are using strings rather than parameters, your example is vulnerable to SQL injection. It's best to avoid pg_ functions. In your case there are two things you need to take into account:
Learn the Drupal API (considering you are using Drupal this would be the best for code consistency
or
Use stored procedures
Use a library like PDO or pg_query_params which takes care of parameterized queries
Normally you use stored procedures in addition to PDO, unfortunately sometimes this is not manageable because you have too much code. My advice is to use as much stored procedures as possible.
when trying to make this question, i got this one it is using Java, and in the answer it gave a Ruby example, and it seems that the injection happens only when using Json? because i've an expose where i'll try to compare between NoSQL and SQL and i was trying to said: be happy, nosql has no sql injection since it's not sql ...
can you please explain me:
how sql injection happens when using Python driver (pymongo).
how to avoid it.
the comparison using the old way sql injection using the comment in the login form.
There are a couple of concerns with injection in MongoDB:
$where JS injection - Building JavaScript functions from user input can result in a query that can behave differently to what you expect. JavaScript functions in general are not a responsible method to program MongoDB queries and it is highly recommended to not use them unless absolutely needed.
Operator injection - If you allow users to build (from the front) a $or or something they could easily manipulate this ability to change your queries. This of course does not apply if you just take data from a set of text fields and manually build a $or from that data.
JSON injection - Quite a few people recently have been trying to convert a full JSON document sent (saw this first in JAVA, ironically) from some client side source into a document for insertion into MongoDB. I shouldn't need to even go into why this is bad. A JSON value for a field is fine since, of course, MongoDB is BSON.
As #Burhan stated injection comes from none sanitized input. Fortunately for MongoDB it has object orientated querying.
The problem with SQL injection comes from the word "SQL". SQL is a querying language built up of strings. On the other hand MongoDB actually uses a BSON document to specify a query (an Object). If you keep to the basic common sense rules I gave you above you should never have a problem with an attack vector like:
SELECT * FROM tbl_user WHERE ='';DROP TABLE;
Also MongoDB only supports one operation per command atm (without using eval, don't ever do that though) so that wouldn't work anyway...
I should add that this does not apply to data validation only injection.
SQL injection has nothing to do with the database. It is a type of vulnerability that allows for execution of arbitrary SQL commands because the target system does not sanitize the SQL that is given to the SQL server.
It doesn't matter if you are on NoSQL or not. If you have a system running on mongodb (or couchdb, or XYZ db), and you provide a front end where users can enter records - and you don't correctly escape and sanitize the input coming from the front end; you are open to SQL injection.
I need to get a database connection through a firewall, and also limit what queries can be run. DBD::Proxy seems to be the perfect solution for this. However, I'm currently using DBIx::Class, and can't figure out how to hook them together.
In particular, DBD::Proxy doesn't take SQL; it takes particular named queries. But DBIx::Class doesn't seem to have a way to invoke those named queries.
This is inside a Catalyst-based webapp.
DBD::Proxy does take SQL. It allows for named queries as a convenience.
There is no convenient way to use DBIx::Class with DBD::Proxy named queries, since the purpose of the DBIx::Class Object-Relational Mapper (ORM) is to present an object-oriented view of SQL's Data Manipulation Language (DML) statements. The named query feature of DBD::Proxy is not a DML statement, so DBIx::Class does not have feature that suit your needs: passing a literal string directly to the prepare() function of your DBD::Proxy driver.
Some inconvenient ways:
Don't use DBIx::Class. Just do it in DBI. You could use Catalyst::Model::DBI, or plain DBI + catalyst::Model::Adaptor + your own model class.
Don't use named queries. This means that if you were planning to use named queries as a way to control access to the database, then you'll need to move the query authorization
logic into the code that makes the call to the database inside your controller or model, depending on how you built your application.