Poor Man's Type Checking in Arguments and Returns
Please, disregard the branch name 😮💨
Changes
Add optional type checking to argument declarations
argument :jarl, type: Chiquito
argument :torpedo, type: Array, default: nil
Add optional type checking to returned values
returns MyClass, nullable: true
returns MyCollection, of: Item, nullable: true, allow_nils: false
Notes
Made them optional, since they're not the main purpose of the library, but happy to cut a 3.0.0 branch with breaking changes.
See each commit's README entries for more examples
class UserByPermissionsQuery
include Injectable
argument(:permission, type: Permission)
dependency(:base_relation) { User.all }
returns(ActiveRecord::Associations::CollectionProxy, of: User, nullable: false, allow_nils: false)
def call
base_relation.includes(:permissions).where(permissions: { id: permission.id })
end
end
About Collection validations
I've got a bit of a mess there. Not really sure I should check for Enumerable, or just responds_to?(:each) is enough?
Maybe having an optional enumerates_with: key is cool to indicate which method is used to iterate the collection (default :each)?
returns MyCollection, of: Item, enumerates_with: :each, nullable: false, allow_nils: false
Not a review, but to answer some of your questions:
Made them optional, since they're not the main purpose of the library, but happy to cut a 3.0.0 branch with breaking changes.
My idea originally was for it to be opt-in, since it has a runtime performance hit (not sure how much, but it's doing more work than before), and not everyone wants/likes strong typing.
I've got a bit of a mess there. Not really sure I should check for Enumerable, or just responds_to?(:each) is enough?
Maybe having an optional enumerates_with: key is cool to indicate which method is used to iterate the collection (default :each)?
I thought you'd do a collection.all? { it.is_a? type }. In Enumerable those are still defined in terms of :each, so I think it's a fair assumption. Still, I would assume that if someones uses of: that they're passing a collection and I would assume :each. I'd start simple and add complexity as you need it, so I'd personally keep : enumerates_with in the back burner.
@iovis WDYT?