I never understood the use-case for these libraries, but I’ve seen a lot of them in my career.
First of all, it is not saving any typing, essentially providing oneliners replacing other onelines
list_products() # Repo.all(Products)
list_products(opts) # Repo.all(where(Products, ...))
list_products_paginated() # Repo.paginate(Products)
list_products_paginated(opts) # Repo.paginate(where(Products))
count_products() # Repo.aggregate(Products, :count)
count_products(opts) # Repo.aggregate(where(Products, ...), :count)
# Create operations
create_product(%{name: "Item"}) # Repo.insert(Product.changeset(...))
create_product!(%{name: "Item"}) # Repo.insert!(Product.changeset(...))
create_product() # Repo.insert(%Product{})
create_product!() # Repo.insert!(%Product{})
# Read operations
get_product(1) # Repo.get(Product, 1)
get_product!(1) # Repo.fetch!(Product, 1)
get_product(1, preload: [:items]) # Repo.get(Product, 1) |> Repo.preload()
get_product!(1, preload: [:items]) # Repo.fetch!(Product, 1) |> Repo.preload()
# Update operations
update_product(product, attrs) # Repo.update(Product.changeset(product, attrs))
update_product(product) # Update without new attributes (??????? why would anyone needs this)
change_product(product, attrs) # Product.changeset(product, attrs)
change_product(product) # Product.changeset(product, attrs)
# Delete operations
delete_product(product) # Product.delete(product)
delete_product!(product) # Product.delete!(product)
# Initialize operations
new_product() # %Product{}
new_product(attrs) # struct(Product, attrs)
new_product(attrs, opts) # ??????
Second, it makes it impossible to search for definition. When I will go to Product
module, I won’t be able to find what the list_products
function does, because I can’t see it
Third, every time I used this approach, it quickly became unmaintainable, because CRUD operations which just do plain CRUD are extremely rare, and most of them usually contain some business logic which is reflected in query (like, for example, product ownership checks, soft-deletion checks, category checks, normalized form preloading, etc.)
So every time I used one of these libraries, they became a huge frustration for me and other devs