@@ -1037,12 +1037,6 @@ defmodule Ecto.Adapters.SQLite3.Connection do
1037
1037
message: "join hints are not supported by SQLite3"
1038
1038
end
1039
1039
1040
- defp assert_valid_join ( % JoinExpr { source: { :values , _ , _ } } , query ) do
1041
- raise Ecto.QueryError ,
1042
- query: query ,
1043
- message: "SQLite3 adapter does not support values lists"
1044
- end
1045
-
1046
1040
defp assert_valid_join ( _join_expr , _query ) , do: :ok
1047
1041
1048
1042
defp join_on ( :cross , true , _sources , _query ) , do: [ ]
@@ -1368,8 +1362,8 @@ defmodule Ecto.Adapters.SQLite3.Connection do
1368
1362
|> parens_for_select
1369
1363
end
1370
1364
1371
- defp expr ( { :values , _ , _ } , _ , _query ) do
1372
- raise ArgumentError , "SQLite3 adapter does not support values lists"
1365
+ defp expr ( { :values , _ , [ types , _idx , num_rows ] } , _ , query ) do
1366
+ [ ?( , values_list ( types , num_rows , query ) , ?) ]
1373
1367
end
1374
1368
1375
1369
defp expr ( { :identifier , _ , [ literal ] } , _sources , _query ) do
@@ -1560,6 +1554,36 @@ defmodule Ecto.Adapters.SQLite3.Connection do
1560
1554
message: "unsupported expression #{ inspect ( expr ) } "
1561
1555
end
1562
1556
1557
+ defp values_list ( types , num_rows , query ) do
1558
+ col_names = Enum . map ( types , & elem ( & 1 , 0 ) ) |> Enum . join ( ", " )
1559
+ rows = :lists . seq ( 1 , num_rows , 1 )
1560
+
1561
+ [
1562
+ "WITH xxx(" ,
1563
+ col_names ,
1564
+ ") AS (VALUES " ,
1565
+ Enum . map_intersperse ( rows , ?, , fn _ ->
1566
+ [ ?( , values_expr ( types , query ) , ?) ]
1567
+ end ) ,
1568
+ ") SELECT * FROM xxx"
1569
+ ]
1570
+ end
1571
+
1572
+ defp values_expr ( types , _query ) do
1573
+ Enum . map_intersperse ( types , ?, , fn { _field , type } ->
1574
+ # TODO: cast?
1575
+ # ["CAST(", ??, " AS ", ecto_cast_to_db(type, query), ?)]
1576
+ ??
1577
+ end )
1578
+ end
1579
+
1580
+ # defp ecto_cast_to_db(:id, _query), do: "INTEGER"
1581
+ # defp ecto_cast_to_db(:integer, _query), do: "INTEGER"
1582
+ # defp ecto_cast_to_db(:string, _query), do: "char"
1583
+ # defp ecto_cast_to_db(:utc_datetime_usec, _query), do: "datetime(6)"
1584
+ # defp ecto_cast_to_db(:naive_datetime_usec, _query), do: "datetime(6)"
1585
+ # defp ecto_cast_to_db(_type, _query), do: "TEXT"
1586
+
1563
1587
def interval ( _ , "microsecond" , _sources ) do
1564
1588
raise ArgumentError ,
1565
1589
"SQLite does not support microsecond precision in datetime intervals"
@@ -1618,6 +1642,9 @@ defmodule Ecto.Adapters.SQLite3.Connection do
1618
1642
{ :fragment , _ , _ } ->
1619
1643
{ nil , as_prefix ++ [ ?f | Integer . to_string ( pos ) ] , nil }
1620
1644
1645
+ { :values , _ , _ } ->
1646
+ { nil , as_prefix ++ [ ?v | Integer . to_string ( pos ) ] , nil }
1647
+
1621
1648
{ table , schema , prefix } ->
1622
1649
name = as_prefix ++ [ create_alias ( table ) | Integer . to_string ( pos ) ]
1623
1650
{ quote_table ( prefix , table ) , name , schema }
0 commit comments