lib/data_model/error.rb in data_model-0.4.0 vs lib/data_model/error.rb in data_model-0.5.0

- old
+ new

@@ -1,44 +1,48 @@ -# typed: strict - module DataModel - # Error is a class that holds errors. + # Error is a class that holds errors. Errors are a tuple of [name, ctx] + # - name is a symbol that identifies the error + # - ctx is contextual information about the error which can be used to build an error message + # + # The error object is a structured way to store, modify, and add errors in that intermediary format. + # To turn an error into a human readable message, use #to_messages, which delegates to a registry + # + # Base errors are errors that are related to the object as a whole, and not to any specific child + # Child errors are errors that are related to a specific child of the object, which may or may not apply depending on the type class Error - extend T::Sig include Errors - TErrorList = T.type_alias { T::Array[TError] } - TErrorMap = T.type_alias { T::Hash[Symbol, TErrorList] } - - sig { void } + # Create a new error Object + # @return [Error] the new error object def initialize - @base = T.let([], TErrorList) - @children = T.let({}, TErrorMap) + @base = [] + @children = {} end # errors related to the object as a whole - sig { returns(TErrorList) } + # @return [Array<Array(Symbol, untyped)>] the base errors def base return @base end # errors related children - sig { returns(TErrorMap) } + # @return [Hash{Symbol => Array<Array(Symbol, untyped)>}] the child errors def children return @children end # all errors - sig { returns(TErrorMap) } + # @return [Hash{Symbol => Array<Array(Symbol, untyped)>}] all errors def all return children.merge(base:) end alias to_h all # Returns true if any errors are present. - sig { params(blk: T.nilable(T.proc.params(error: TError).returns(T::Boolean))).returns(T::Boolean) } + # @param blk [Proc] an optional block to filter errors, takes an Array(Symbol, untyped) and returns boolean + # @return [Boolean] true if any errors are present def any?(&blk) if !blk return !@base.empty? || !@children.empty? end @@ -52,17 +56,20 @@ end return any end - sig { returns(T::Boolean) } + # Returns true if no errors are present. + # @return [Boolean] true if no errors are present def empty? !any? end # Add an error to the error list. - sig { params(err: TError, child: T.nilable(T.any(Symbol, T::Array[Symbol]))).void } + # @param err [Array(Symbol, untyped)] the error to add + # @param child [Symbol, Array(Symbol)] the child to add the error to. child can be an array of symbols to specify a path if nested + # @return [void] def add(err, child: nil) if child.is_a?(Array) child = child.join(".").to_sym end @@ -72,11 +79,14 @@ errs = child ? @children[child] ||= [] : @base errs.push(err) end - sig { params(name: Symbol, child: Error).void } + # Merge another error object into this one for child Errors + # @param name [Symbol] the name of the child + # @param child [Error] the child error object + # @return [void] def merge_child(name, child) if !child.any? return end @@ -85,10 +95,12 @@ add(error, child: [name, key]) end end end - sig { params(registry: Registry).returns(T::Hash[Symbol, T::Array[String]]) } + # Get human readable error messages from error tuples + # @param registry [Registry] the registry to use to get error messages + # @return [Hash{Symbol => Array[String]}] the error messages def to_messages(registry: Registry.instance) return registry.error_messages(self) end end end