Ecto: create tables

I’m new to Ecto and this is my second day of using it so please excuse me if I’m missing anything obvious.
How can I programmatically create tables using Ecto.
All the tutorials hint to use mix ecto.migrate which I’m able to use successfully if I use sqlite with a file. But I want something temporary, something like sqlite “in memory” database which cease to exist when application quits.
So whenever I start my application or execute mix test, I want the tables to be automatically created. I’ve already written migration scripts.

What I really want to do: I’m doing this as part of my homework where I have to show that I can send message to huge number of clients (simulating Twitter), so I don’t really want to save any data persistently. I don’t mind saving it but I’m guessing in memory database would be faster and since this is a homework problem the size of data isn’t very large.
I’m open to other solutions too, like Mnesia but I think since I need more CRUD operations using ecto+sqlite[1] would be better combination.

1: sqlite because I don’t want to depend on school computers to have PostgreSQL installed.

mix has a lot more options than mix ecto.migrate

$ mix --help | grep ecto
mix ecto               # Prints Ecto help information
mix ecto.create        # Creates the repository storage
mix ecto.drop          # Drops the repository storage
mix ecto.dump          # Dumps the repository database structure
mix ecto.gen.migration # Generates a new migration for the repo
mix ecto.gen.repo      # Generates a new repository
mix ecto.load          # Loads previously dumped database structure
mix ecto.migrate       # Runs the repository migrations
mix ecto.migrations    # Displays the repository migration status
mix ecto.rollback      # Rolls back the repository migrations
mix       # Creates a new Ecto project within an umbrella project

Maybe You are looking for mix ecto.create?

Please note You can pass MIX_ENV=test before each mix command… or prod.

Thinking of in memory datastore… You can use processes also, or ETS tables.

All these disappear when You plug the system off.

When I use mix, a new process is created, migration/creation of tables happen and then process dies, killing the temporary database. Subsequent calls to database from mix test fail.
I’m looking for something which I can trigger programmatically before any of my code executes.

Why have a database at all?

If you only need your data as long as the application runs, just put it into sume Agents or GenServers.

But to answer your question:

What you want to achieve is not easily doable. In theory the SQlite inmemory database sounds as if it were what you want, but it only persists as long as connections are open. So it will vanish after mix ecto.create has been run.

So you will need to do everything that mix ecto.create and mix ecto.migrate usually do in your applications startup phase.

So just accept the file beeing there and delete it after you don’t need it anymore, thats the most simple thing to do.

Maybe you can just use mix aliases to migrate your db before running tests and rollback those migrations afterwards. If your application did not create additional tables this should leave you with a clean db.

1 Like

Mix aliases sound like a good idea. You can also try mix do for a start, it lets you run multiple commands without restarting the process in-between.

If you used the default generators, your app should have a file like “test_helper.exs” that starts ExUnit. You could also try calling the Ecto.Migrator functions from that helper.