Repository: tobymao/sqlglot

Issue:
Teradata to Databricks transpilation issue
When working on Teradata to Databricks conversion i ran into a issue where a command like "Database databasename" which is equvalent to "USE Databasename" on Databricks side is not getting tranpiled correctly. The final output still shows the original command.


**Sample code** below
```
sql="""
	DATABASE tduser;
"""

try:
    new_query = sqlglot.transpile(sql, read='teradata', write='databricks', pretty=True)[0]
    print(new_query)
except sqlglot.errors.ParseError as error:
    print(traceback.format_exc())
    print(error.errors)
```
**Expected output:**
USE tduser

**Official Documentation**
https://docs.databricks.com/en/sql/language-manual/sql-ref-syntax-ddl-usedb.html


Discussion:

Patch:
diff --git a/sqlglot/dialects/teradata.py b/sqlglot/dialects/teradata.py
index 2be1a625..163cc137 100644
--- a/sqlglot/dialects/teradata.py
+++ b/sqlglot/dialects/teradata.py
@@ -95,6 +95,9 @@ class Teradata(Dialect):
 
         STATEMENT_PARSERS = {
             **parser.Parser.STATEMENT_PARSERS,
+            TokenType.DATABASE: lambda self: self.expression(
+                exp.Use, this=self._parse_table(schema=False)
+            ),
             TokenType.REPLACE: lambda self: self._parse_create(),
         }
 
@@ -165,6 +168,7 @@ class Teradata(Dialect):
             exp.Select: transforms.preprocess([transforms.eliminate_distinct_on]),
             exp.StrToDate: lambda self, e: f"CAST({self.sql(e, 'this')} AS DATE FORMAT {self.format_time(e)})",
             exp.ToChar: lambda self, e: self.function_fallback_sql(e),
+            exp.Use: lambda self, e: f"DATABASE {self.sql(e, 'this')}",
         }
 
         def partitionedbyproperty_sql(self, expression: exp.PartitionedByProperty) -> str:
diff --git a/sqlglot/parser.py b/sqlglot/parser.py
index 214998c7..f9f8bd4d 100644
--- a/sqlglot/parser.py
+++ b/sqlglot/parser.py
@@ -3154,12 +3154,12 @@ class Parser(metaclass=_Parser):
 
             if len(parts) == 2:
                 if unit:
-                    # this is not actually a unit, it's something else
+                    # This is not actually a unit, it's something else (e.g. a "window side")
                     unit = None
                     self._retreat(self._index - 1)
-                else:
-                    this = exp.Literal.string(parts[0])
-                    unit = self.expression(exp.Var, this=parts[1])
+
+                this = exp.Literal.string(parts[0])
+                unit = self.expression(exp.Var, this=parts[1])
 
         return self.expression(exp.Interval, this=this, unit=unit)
 
@@ -4151,7 +4151,7 @@ class Parser(metaclass=_Parser):
         key = self._parse_column()
         self._match_set((TokenType.COLON, TokenType.COMMA))
         self._match_text_seq("VALUE")
-        value = self._parse_column()
+        value = self._parse_bitwise()
 
         if not key and not value:
             return None


Test patch:
diff --git a/tests/dialects/test_oracle.py b/tests/dialects/test_oracle.py
index 27845ed7..01a9ca3a 100644
--- a/tests/dialects/test_oracle.py
+++ b/tests/dialects/test_oracle.py
@@ -6,6 +6,7 @@ class TestOracle(Validator):
     dialect = "oracle"
 
     def test_oracle(self):
+        self.validate_identity("SELECT JSON_OBJECT('name': first_name || ' ' || last_name) FROM t")
         self.validate_identity("COALESCE(c1, c2, c3)")
         self.validate_identity("SELECT * FROM TABLE(foo)")
         self.validate_identity("SELECT a$x#b")
diff --git a/tests/dialects/test_teradata.py b/tests/dialects/test_teradata.py
index 4d322419..32bdc719 100644
--- a/tests/dialects/test_teradata.py
+++ b/tests/dialects/test_teradata.py
@@ -4,6 +4,18 @@ from tests.dialects.test_dialect import Validator
 class TestTeradata(Validator):
     dialect = "teradata"
 
+    def test_teradata(self):
+        self.validate_all(
+            "DATABASE tduser",
+            read={
+                "databricks": "USE tduser",
+            },
+            write={
+                "databricks": "USE tduser",
+                "teradata": "DATABASE tduser",
+            },
+        )
+
     def test_translate(self):
         self.validate_all(
             "TRANSLATE(x USING LATIN_TO_UNICODE)",
diff --git a/tests/test_parser.py b/tests/test_parser.py
index a853a757..7135dd89 100644
--- a/tests/test_parser.py
+++ b/tests/test_parser.py
@@ -711,3 +711,11 @@ class TestParser(unittest.TestCase):
             parse_one("SELECT a, b ?? c ?? 'No Data' FROM z").sql(),
             "SELECT a, COALESCE(COALESCE(b, c), 'No Data') FROM z",
         )
+
+    def test_parse_intervals(self):
+        ast = parse_one(
+            "SELECT a FROM tbl WHERE a <= DATE '1998-12-01' - INTERVAL '71 days' GROUP BY b"
+        )
+
+        self.assertEqual(ast.find(exp.Interval).this.sql(), "'71'")
+        self.assertEqual(ast.find(exp.Interval).unit.assert_is(exp.Var).sql(), "days")