summaryrefslogtreecommitdiff
path: root/django/db
diff options
context:
space:
mode:
authorMariusz Felisiak <felisiak.mariusz@gmail.com>2018-03-19 17:35:16 +0100
committerGitHub <noreply@github.com>2018-03-19 17:35:16 +0100
commitcede5111bbeea1f02a7d35941a4264c7ff95df0a (patch)
tree959f0785f3102ba84db7d4fcd96c17ae1baab479 /django/db
parent8d67c7cffdcd5fd0c5cb0b87cd699a05b461e58d (diff)
Refs #28643 -- Added LPad and RPad database functions.
Thanks Tim Graham for the review.
Diffstat (limited to 'django/db')
-rw-r--r--django/db/backends/sqlite3/base.py12
-rw-r--r--django/db/models/functions/__init__.py9
-rw-r--r--django/db/models/functions/text.py13
3 files changed, 30 insertions, 4 deletions
diff --git a/django/db/backends/sqlite3/base.py b/django/db/backends/sqlite3/base.py
index 996ec1e09b..3989028930 100644
--- a/django/db/backends/sqlite3/base.py
+++ b/django/db/backends/sqlite3/base.py
@@ -169,6 +169,8 @@ class DatabaseWrapper(BaseDatabaseWrapper):
conn.create_function("regexp", 2, _sqlite_regexp)
conn.create_function("django_format_dtdelta", 3, _sqlite_format_dtdelta)
conn.create_function("django_power", 2, _sqlite_power)
+ conn.create_function('LPAD', 3, _sqlite_lpad)
+ conn.create_function('RPAD', 3, _sqlite_rpad)
conn.execute('PRAGMA foreign_keys = ON')
return conn
@@ -467,5 +469,15 @@ def _sqlite_regexp(re_pattern, re_string):
return bool(re.search(re_pattern, str(re_string))) if re_string is not None else False
+def _sqlite_lpad(text, length, fill_text):
+ if len(text) >= length:
+ return text[:length]
+ return (fill_text * length)[:length - len(text)] + text
+
+
+def _sqlite_rpad(text, length, fill_text):
+ return (text + fill_text * length)[:length]
+
+
def _sqlite_power(x, y):
return x ** y
diff --git a/django/db/models/functions/__init__.py b/django/db/models/functions/__init__.py
index 5528be8c48..a0f5a9e8b2 100644
--- a/django/db/models/functions/__init__.py
+++ b/django/db/models/functions/__init__.py
@@ -6,8 +6,8 @@ from .datetime import (
TruncQuarter, TruncSecond, TruncTime, TruncWeek, TruncYear,
)
from .text import (
- Chr, Concat, ConcatPair, Left, Length, Lower, LTrim, Ord, Replace, Right,
- RTrim, StrIndex, Substr, Trim, Upper,
+ Chr, Concat, ConcatPair, Left, Length, Lower, LPad, LTrim, Ord, Replace,
+ Right, RPad, RTrim, StrIndex, Substr, Trim, Upper,
)
from .window import (
CumeDist, DenseRank, FirstValue, Lag, LastValue, Lead, NthValue, Ntile,
@@ -24,8 +24,9 @@ __all__ = [
'TruncMinute', 'TruncMonth', 'TruncQuarter', 'TruncSecond', 'TruncTime',
'TruncWeek', 'TruncYear',
# text
- 'Chr', 'Concat', 'ConcatPair', 'Left', 'Length', 'Lower', 'LTrim', 'Ord',
- 'Replace', 'Right', 'RTrim', 'StrIndex', 'Substr', 'Trim', 'Upper',
+ 'Chr', 'Concat', 'ConcatPair', 'Left', 'Length', 'Lower', 'LPad', 'LTrim',
+ 'Ord', 'Replace', 'Right', 'RPad', 'RTrim', 'StrIndex', 'Substr', 'Trim',
+ 'Upper',
# window
'CumeDist', 'DenseRank', 'FirstValue', 'Lag', 'LastValue', 'Lead',
'NthValue', 'Ntile', 'PercentRank', 'Rank', 'RowNumber',
diff --git a/django/db/models/functions/text.py b/django/db/models/functions/text.py
index 614522017f..c57545bc6a 100644
--- a/django/db/models/functions/text.py
+++ b/django/db/models/functions/text.py
@@ -110,6 +110,15 @@ class Lower(Transform):
lookup_name = 'lower'
+class LPad(Func):
+ function = 'LPAD'
+
+ def __init__(self, expression, length, fill_text=Value(' '), **extra):
+ if not hasattr(length, 'resolve_expression') and length < 0:
+ raise ValueError("'length' must be greater or equal to 0.")
+ super().__init__(expression, length, fill_text, **extra)
+
+
class LTrim(Transform):
function = 'LTRIM'
lookup_name = 'ltrim'
@@ -141,6 +150,10 @@ class Right(Left):
return Substr(self.source_expressions[0], self.source_expressions[1] * Value(-1))
+class RPad(LPad):
+ function = 'RPAD'
+
+
class RTrim(Transform):
function = 'RTRIM'
lookup_name = 'rtrim'