···33import filepath
44import gleam/bool
55import gleam/erlang/atom
66+import gleam/int
67import gleam/io
78import gleam/list
89import gleam/regexp
···13141415/// An integration test for a specific postgres type.
1516///
1616-type TestType {
1717+type TestCase {
1818+ /// This tests squirrel on a fixed set of parametrised queries doing
1919+ /// insertions and selects. To do so it creates some Gleam code that uses
2020+ /// Gleam values as parameters to the query.
2121+ ///
1722 TestType(postgres_type: String, values: List(TestValue))
2323+2424+ /// This tests squirrel running a fixed query with no parameters. And it
2525+ /// checks the value you get back from the query to match the given
2626+ /// `expected_value`.
2727+ ///
2828+ TestQuery(query: String)
1829}
19302031/// How a tested value looks in gleam code when it is fed into a query or
···6273 TestType("float4", [TestValue("1.0")]),
6374 TestType("float8", [TestValue("1.0")]),
6475 TestType("numeric", [TestValue("1.0")]),
7676+ TestQuery("select 1::numeric"),
6577 // Uuid
6678 TestType("uuid", [TestValue("uuid.v7()")]),
6779 // Bytea
···134146}
135147136148fn run_integration_tests(
137137- values: List(TestType),
149149+ values: List(TestCase),
138150) -> Result(Result(String, #(Int, String)), simplifile.FileError) {
139151 let integration_test_project = filepath.join(".", "integration_test_project")
140152 let _ = simplifile.create_directory(integration_test_project)
···144156145157 scaffold_gleam_project(dir)
146158 let code = {
147147- use code, TestType(postgres_type, values) <- list.fold(values, "")
148148- let table_name = safe_name(postgres_type) <> "_table"
149149- create_database_table(table_name, postgres_type)
150150- let assertions =
151151- create_query_files_and_assertions(postgres_type, table_name, values, dir)
159159+ use code, test_case <- list.fold(values, "")
160160+ let assertions = setup_and_generate_code(for: test_case, in: dir)
152161 code <> "\n\n" <> assertions
153162 }
154163 write_main(code, to: dir)
155164 test_project(dir)
156165}
157166167167+fn setup_and_generate_code(for test_case: TestCase, in dir: String) -> String {
168168+ case test_case {
169169+ TestQuery(query:) -> create_query_files_and_assertions_for_query(query, dir)
170170+ TestType(postgres_type:, values:) -> {
171171+ let table_name = safe_name(postgres_type) <> "_table"
172172+ create_database_table(table_name, postgres_type)
173173+ create_query_files_and_assertions(postgres_type, table_name, values, dir)
174174+ }
175175+ }
176176+}
177177+158178fn create_database_table(table_name: String, postgres_type: String) -> Nil {
159179 let drop = "drop table if exists " <> table_name
160180 let create = "create table if not exists " <> table_name <> "(
···267287268288 string.join(assertions, with: "\n")
269289}
290290+291291+fn create_query_files_and_assertions_for_query(
292292+ query: String,
293293+ dir: String,
294294+) -> String {
295295+ let src_dir = filepath.join(dir, "src")
296296+ let sql_dir = filepath.join(src_dir, "sql")
297297+ let query_name = "query_" <> int.to_string(unique_integer())
298298+ let assert Ok(_) =
299299+ simplifile.write(query, to: filepath.join(sql_dir, query_name <> ".sql"))
300300+301301+ "let assert Ok(_) = sql.<query>(db)"
302302+ |> string.replace(each: "<query>", with: query_name)
303303+}
304304+305305+@external(erlang, "squirrel_ffi", "unique")
306306+fn unique_integer() -> Int
270307271308/// Writes the entry point of the Gleam project that will connect to the
272309/// database and run all the assertions testing the generated squirrel code.