Skip to content

Commit

Permalink
Improve error message unsupported attribute for bridges
Browse files Browse the repository at this point in the history
  • Loading branch information
blegat authored and odow committed Oct 29, 2023
1 parent cab3440 commit a379199
Show file tree
Hide file tree
Showing 2 changed files with 34 additions and 20 deletions.
33 changes: 18 additions & 15 deletions src/Bridges/bridge.jl
Original file line number Diff line number Diff line change
Expand Up @@ -119,6 +119,18 @@ function MOI.supports(
return false
end

function _attribute_error_message(attr, bridge, action)
return "Bridge of type `$(nameof(typeof(bridge)))` does not support " *
"$action the attribute `$attr`. If you encountered this error " *
"unexpectedly, it probably means your model has been " *
"reformulated using the bridge, and you are attempting to query " *
"an attribute that we haven't implemented yet for this bridge. " *
"Please open an issue at https://github.com/jump-dev/MathOptInterface.jl/issues/new " *
"and provide a reproducible example explaining what you were " *
"trying to do."
end


"""
function MOI.get(
model::MOI.ModelLike,
Expand All @@ -134,18 +146,8 @@ function MOI.get(
attr::MOI.AbstractConstraintAttribute,
bridge::AbstractBridge,
)
return throw(
ArgumentError(
"Bridge of type `$(typeof(bridge))` does not support accessing " *
"the attribute `$attr`. If you encountered this error " *
"unexpectedly, it probably means your model has been " *
"reformulated using the bridge, and you are attempting to query " *
"an attribute that we haven't implemented yet for this bridge. " *
"Please open an issue at https://github.com/jump-dev/MathOptInterface.jl/issues/new " *
"and provide a reproducible example explaining what you were " *
"trying to do.",
),
)
message = _attribute_error_message(attr, bridge, "accessing")
return throw(ArgumentError(message))
end

function MOI.get(
Expand Down Expand Up @@ -173,12 +175,13 @@ function MOI.set(
model::MOI.ModelLike,
attr::MOI.AbstractConstraintAttribute,
bridge::AbstractBridge,
value,
_,
)
message = _attribute_error_message(attr, bridge, "setting a value for")
if MOI.is_copyable(attr) && !MOI.supports(model, attr, typeof(bridge))
throw(MOI.UnsupportedAttribute(attr))
throw(MOI.UnsupportedAttribute(attr, message))
else
throw(MOI.SetAttributeNotAllowed(attr))
throw(MOI.SetAttributeNotAllowed(attr, message))
end
end

Expand Down
21 changes: 16 additions & 5 deletions test/Bridges/bridge_optimizer.jl
Original file line number Diff line number Diff line change
Expand Up @@ -218,7 +218,13 @@ MOI.Utilities.@model(
(MOI.VectorAffineFunction, MOI.VectorQuadraticFunction)
)

function unsupported_constraint_attribute()
struct AttributeNotAllowed <: MOI.AbstractConstraintAttribute end

function MOI.supports(::MOI.ModelLike, ::AttributeNotAllowed, ::Type{<:MOI.Bridges.Constraint.SplitIntervalBridge})
return true
end

function test_unsupported_constraint_attribute()
mock = MOI.Utilities.MockOptimizer(NoIntervalModel{Float64}())
bridged_mock = MOI.Bridges.Constraint.LessToGreater{Float64}(
MOI.Bridges.Constraint.SplitInterval{Float64}(mock),
Expand All @@ -231,22 +237,27 @@ function unsupported_constraint_attribute()
MOI.LessThan{Float64},
}
attr = MOI.Test.UnknownConstraintAttribute()
err = ArgumentError(
"Bridge of type `$(bridge)` does not support accessing " *
message(action) =
"Bridge of type `$(nameof(bridge))` does not support $action " *
"the attribute `$attr`. If you encountered this error " *
"unexpectedly, it probably means your model has been " *
"reformulated using the bridge, and you are attempting to query " *
"an attribute that we haven't implemented yet for this bridge. " *
"Please open an issue at https://github.com/jump-dev/MathOptInterface.jl/issues/new " *
"and provide a reproducible example explaining what you were " *
"trying to do.",
)
"trying to do."
x = MOI.add_variable(bridged_mock)
ci = MOI.add_constraint(bridged_mock, x, MOI.Interval(0.0, 1.0))
@test !MOI.Bridges.is_bridged(bridged_mock, ci)
@test MOI.Bridges.is_bridged(bridged_mock.model, ci)
@test !MOI.supports(bridged_mock, attr, typeof(ci))
err = ArgumentError(message("accessing"))
@test_throws err MOI.get(bridged_mock, attr, ci)
err = MOI.UnsupportedAttribute(attr, message("setting a value for"))
@test_throws err MOI.set(bridged_mock, attr, ci, 1)
attr = AttributeNotAllowed()
err = MOI.SetAttributeNotAllowed(attr, message("setting a value for"))
@test_throws err MOI.set(bridged_mock, attr, ci, 1)
return
end

Expand Down

0 comments on commit a379199

Please sign in to comment.