Documentation
¶
Overview ¶
Django like (django-filter, DRF) queryparam filters to SQL parser.
Supported features:
- IN and NOT IN for list (or not) of get parameters: `.../path?column__in=1&column__in=2&column__in=3“
- exact equality and inequality (using not_in): `.../path?column__not_in=1 = column <> 1`
- LIKE using __like operator: col1__like=foo = `LOWER(col1) LIKE CONCAT('%', foo, '%')`
Planned features:
- support for operators: BETWEEN, IS NULL, gt, gte, lt, lte, not
- OR support
- ordering support (parentheses in resulting SQL)
Example ¶
package main
import (
"fmt"
"net/url"
naivequeryfilters "github.com/Wayodeni/go-naive-queryfilters"
)
func main() {
var whitelist = naivequeryfilters.AllowedColumns{
"col1": func(s string) string { return "table_name.col1" },
"col2": func(s string) string { return s },
}
filter, invalidParams, err := naivequeryfilters.Build(whitelist, url.Values{
"col1__in": []string{"1", "2"},
"col2__not_in": []string{"1"},
"col3": []string{"val"},
})
if err != nil {
panic(err)
}
if len(invalidParams) != 0 {
fmt.Printf("passed invalid column names in get parameters: %s\n", invalidParams)
}
fmt.Printf("SQL query filters part for WHERE clause: '%s'\nSQL query placeholder values: %v", filter.SqlFilters, filter.PlaceholderValues)
}
Output: passed invalid column names in get parameters: map[col3:[val]] SQL query filters part for WHERE clause: 'table_name.col1 IN (?,?) AND col2 <> ?' SQL query placeholder values: [1 2 1]
Index ¶
Examples ¶
Constants ¶
const ( OPERATOR_SEPARATOR = "__" OPERATOR_IN = "in" OPERATOR_NOT_IN = "not_in" OPERATOR_LIKE = "like" )
These constants define operator names in get parameters keys. E.g. ".../path?column__not_in=val" == fmt.Sprintf(".../path?column%s%s=val", OPERATOR_SEPARATOR, OPERATOR_NOT_IN)
const ( QUERY_TOKEN_IN = "IN" QUERY_TOKEN_NOT_IN = "NOT IN" QUERY_TOKEN_EQUALS = "=" QUERY_TOKEN_NOT_EQUALS = "<>" QUERY_TOKEN_LIKE = "LIKE" )
These constants define SQL query tokens in which operators will be transformed.
Variables ¶
var OPERATORS = map[string]string{ OPERATOR_IN: QUERY_TOKEN_IN, OPERATOR_NOT_IN: QUERY_TOKEN_NOT_IN, OPERATOR_LIKE: QUERY_TOKEN_LIKE, }
This map stores "<get param operator>: <sql query token equivalent>" pairs.
Functions ¶
This section is empty.
Types ¶
type AllowedColumns ¶
Map storing "<db column name>: <db column name changing function>".
Matching every column name to function which will optionally return transformed (or completely new) name instead of passed. Primarily used for transforming of aliases like this: "SELECT table.col_name AS new_col_name" into column names like this: "table_name.column_name" to be used in resulting SQL query.
We need that because inside SQL we can't use column aliases inside WHERE conditions: https://stackoverflow.com/questions/13031013/how-do-i-use-alias-in-where-clause
type ErrWrongOperator ¶
This error is thrown when wrong operator is passed in param name. e.g. col__not_listed_op.
func (ErrWrongOperator) Error ¶
func (e ErrWrongOperator) Error() string
type ErrWrongQueryParamName ¶
type ErrWrongQueryParamName struct {
ParamName string
}
This error is returned when query parameter with wrong key passed. e.g col__name__like.
func (ErrWrongQueryParamName) Error ¶
func (e ErrWrongQueryParamName) Error() string
type Filter ¶
type Filter struct {
// This field contains resulting SQL filters for WHERE part e.g. `col1 IN (?,?,?) AND col2 = ?`.
SqlFilters string
// List of placeholder values for SQL query.
PlaceholderValues []interface{}
}
Struct holding SQL filtering query with placeholders and placeholder values.
func Build ¶
func Build(filterAllowedColumnNames AllowedColumns, getParams url.Values) (Filter, url.Values, error)
Main library function. Accept whitelist of db table column names with get parameters extracted from url. Returns Filter with SQL query string and placeholder values, wrong column names passed in getParams and error.