5 ms·
Couldn't find anything on Ruby validations (drop me a link?) just something about the db ORM/engine. However, Clojure's specs indeed seem to be runtime checks.
by verttii 7y ago
Couldn't find anything on Ruby validations (drop me a link?) just something about the db ORM/engine.
However, Clojure's specs indeed seem to be runtime checks. Seems very different from a type system, really just packages functionalities for the primitives rather than having an expressive type system.
I may be understanding this wrong but I fail to see what's the added benefit of moving checks to runtime in contrast with the performance penalty it produces. Or maybe it's just an improvement to an otherwise dynamic language, like Erlang/Elixir has Dialyzer.
Seems to me it's more of a mechanism to handle the errors or produce code that handles inputs a static type system would prevent from being used in the first place.
- wellpast 7y agoRuntime checks are much, much more flexible (because they are ad hoc), more compose-able (they are written using the PL itself), _and_ more capable (you have the full breadth of the PL semantics). I could go on with concrete examples to demonstrate each of these merits but here is a big one: In a statically typed architecture you typically see a typed domain object (ADT) used -- eg, Person -- and you let the type itself "validate" (eg, Person.name, Person.age are non-null/required fields, etc). And wherever Person flows you are obligated to adhere to this form/validation requirements OR you must create a new type and map from/to these two types. This is already obviously a bad idea. In a dynamic language you can define specs universally (like you are obligated to in the static typing case) or you can define a spec for different scenarios and different functions. Let's say I have a process (sequence of function calls) that ultimately cleanses/normalizes a person's name (I'm making up a use case here). This code does not need age but in a statically typed system you will be passing around a Person object and all sources of data must "fill in" that age slot. Now there are a lot of responses from the statically typed people to this scenario [1] but if you follow them all down honestly, you will end up with a dynamic map to represent your entity and you will best be within a dynamic system like Clojure to optimally code and compose your code. [1] The only other response is to say who cares if I have to "fill in" age and to this person I say I feel sorry for the people six months, one year, etc that have to build on top of your code. Here's the Ruby link you asked for-- it's actually rails,b ut it ca be fully decopuled from ActiveRecord fwiw: https://guides.rubyonrails.org/active_record_validations.html https://guides.rubyonrails.org/active_record_validations.htm... (Spec is far more decoupled and designed for general use.)
- bam365 7y agoNot an expert on spec, but I suspect that there are a lot of data that are not representable with combinations of predicates: GADTs, rank-n types, existential types, type families, data families, and other more advanced type system features. Either way, the tradeoff is this: statically typed languages are guaranteed to be free of type errors, but no such guarantees can be made with runtime assertions. Whether or not you use a tool like spec to help you make those assertions, the fact that they happen at runtime prevents them from making any guarantees about type safety. Even if you use spec literally everywhere, as you suggest (and no one actually comes close to doing anyway), you are still not guaranteed of type safety. Dijkstra explains why: https://www.cs.utexas.edu/users/EWD/transcriptions/EWD03xx/EWD303.html https://www.cs.utexas.edu/users/EWD/transcriptions/EWD03xx/E...