Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
37 changes: 29 additions & 8 deletions src/error.jl
Original file line number Diff line number Diff line change
Expand Up @@ -51,19 +51,40 @@ form).
function operation_name end

function Base.showerror(io::IO, err::NotAllowedError)
print(io, typeof(err), ": ", operation_name(err), " cannot be performed")
println(io, typeof(err), ":\n")
println(io, "## Cause\n")
print(io, operation_name(err), " cannot be performed")
m = message(err)
if Base.isempty(m)
print(io, ".")
if isempty(m)
println(io)
else
print(io, ": ", m)
println(io, " because:\n\n", m)
end
return print(
println(io)
print(
io,
" You may want to use a `CachingOptimizer` in `AUTOMATIC` mode",
" or you may need to call `reset_optimizer` before doing this",
" operation if the `CachingOptimizer` is in `MANUAL` mode.",
"""
## Fixing this error

An `MOI.NotAllowedError` error occurs when you have tried to do something that
is not implemented by the solver.

The most common way to fix this error is to wrap the optimizer in a
`MOI.Utilities.CachingOptimizer`.

For example, if you are using `JuMP.Model` or `JuMP.set_optimizer`, do:
```julia
model = JuMP.Model(optimizer; with_cache_type = Float64)
model = JuMP.GenericModel{T}(optimizer; with_cache_type = T)
JuMP.set_optimizer(model, optimizer; with_cache_type = Float64)
```
Similarly, if you are using `MOI.instantiate`, do:
```julia
model = MOI.instantiate(optimizer; with_cache_type = Float64)
```
""",
)
return
end

"""
Expand Down
3 changes: 2 additions & 1 deletion test/General/attributes.jl
Original file line number Diff line number Diff line change
Expand Up @@ -356,7 +356,8 @@ function test_submit_not_allowed()
@test MOI.SubmitNotAllowed(submit) == MOI.SubmitNotAllowed(submit, "")
err = MOI.SubmitNotAllowed(submit, "msg")
contents = sprint(showerror, err)
@test occursin("Submitting $submit cannot be performed: msg", contents)
@test occursin("Submitting $submit cannot be performed", contents)
@test occursin("msg", contents)
return
end

Expand Down
124 changes: 59 additions & 65 deletions test/General/errors.jl
Original file line number Diff line number Diff line change
Expand Up @@ -27,12 +27,10 @@ function test_errors_fallback_AddVariableNotAllowed()
try
MOI.add_variable(model)
catch err
@test sprint(showerror, err) ==
"MathOptInterface.AddVariableNotAllowed:" *
" Adding variables cannot be performed. You may want to use a" *
" `CachingOptimizer` in `AUTOMATIC` mode or you may need to call" *
" `reset_optimizer` before doing this operation if the" *
" `CachingOptimizer` is in `MANUAL` mode."
contents = sprint(showerror, err)
@test occursin("$(MOI.AddVariableNotAllowed)", contents)
@test occursin("Adding variables cannot be performed", contents)
@test occursin("## Fixing this error", contents)
end
@test_throws MOI.AddVariableNotAllowed MOI.add_variables(model, 2)
return
Expand Down Expand Up @@ -104,13 +102,14 @@ function test_errors_add_constraint()
try
MOI.add_constraint(model, vi, MOI.EqualTo(0.0))
catch err
@test sprint(showerror, err) ==
"$(MOI.AddConstraintNotAllowed{MOI.VariableIndex,MOI.EqualTo{Float64}}):" *
" Adding `$MOI.VariableIndex`-in-`$MOI.EqualTo{Float64}`" *
" constraints cannot be performed. You may want to use a" *
" `CachingOptimizer` in `AUTOMATIC` mode or you may need to call" *
" `reset_optimizer` before doing this operation if the" *
" `CachingOptimizer` is in `MANUAL` mode."
contents = sprint(showerror, err)
F, S = MOI.VariableIndex, MOI.EqualTo{Float64}
@test occursin("$(MOI.AddConstraintNotAllowed{F,S})", contents)
@test occursin(
"Adding `$F`-in-`$S` constraints cannot be performed",
contents,
)
@test occursin("## Fixing this error", contents)
end
@test_throws(
MOI.AddConstraintNotAllowed,
Expand Down Expand Up @@ -139,23 +138,19 @@ function test_errors_DeleteNotAllowed()
try
MOI.delete(model, vi)
catch err
@test sprint(showerror, err) ==
"$(MOI.DeleteNotAllowed{typeof(vi)}): Deleting the index $vi " *
"cannot be performed. You may want to use a `CachingOptimizer` " *
"in `AUTOMATIC` mode or you may need to call `reset_optimizer` " *
"before doing this operation if the `CachingOptimizer` is in " *
"`MANUAL` mode."
contents = sprint(showerror, err)
@test occursin("$(MOI.DeleteNotAllowed{typeof(vi)})", contents)
@test occursin("Deleting the index $vi cannot be performed", contents)
@test occursin("## Fixing this error", contents)
end
@test_throws MOI.DeleteNotAllowed{typeof(ci)} MOI.delete(model, ci)
try
MOI.delete(model, ci)
catch err
@test sprint(showerror, err) ==
"$(MOI.DeleteNotAllowed{typeof(ci)}): Deleting the index $ci " *
"cannot be performed. You may want to use a `CachingOptimizer` " *
"in `AUTOMATIC` mode or you may need to call `reset_optimizer` " *
"before doing this operation if the `CachingOptimizer` is in " *
"`MANUAL` mode."
contents = sprint(showerror, err)
@test occursin("$(MOI.DeleteNotAllowed{typeof(ci)})", contents)
@test occursin("Deleting the index $ci cannot be performed", contents)
@test occursin("## Fixing this error", contents)
end
return
end
Expand Down Expand Up @@ -244,14 +239,14 @@ function test_errors_ModifyNotAllowed_constraint()
change = MOI.ScalarConstantChange(1.0)
err = MOI.ModifyConstraintNotAllowed(ci, change)
@test_throws err MOI.modify(model, ci, change)
@test sprint(showerror, err) ==
"$(MOI.ModifyConstraintNotAllowed{MOI.VariableIndex,MOI.EqualTo{Float64},MOI.ScalarConstantChange{Float64}}):" *
" Modifying the constraints $(MOI.ConstraintIndex{MOI.VariableIndex,MOI.EqualTo{Float64}}(1))" *
" with MathOptInterface.ScalarConstantChange{Float64}(1.0) cannot" *
" be performed. You may want to use a `CachingOptimizer` in" *
" `AUTOMATIC` mode or you may need to call `reset_optimizer`" *
" before doing this operation if the `CachingOptimizer` is in" *
" `MANUAL` mode."
contents = sprint(showerror, err)
@test occursin("$(typeof(err)):", contents)
@test occursin(
"Modifying the constraints $ci with $change cannot be performed",
contents,
)
@test occursin("## Fixing this error", contents)
return
end

function test_errors_ModifyNotAllowed_objective()
Expand All @@ -260,13 +255,14 @@ function test_errors_ModifyNotAllowed_objective()
attr = MOI.ObjectiveFunction{MOI.VariableIndex}()
err = MOI.ModifyObjectiveNotAllowed(change)
@test_throws err MOI.modify(model, attr, change)
@test sprint(showerror, err) ==
"$(MOI.ModifyObjectiveNotAllowed{MOI.ScalarConstantChange{Float64}}):" *
" Modifying the objective function with $(MOI.ScalarConstantChange{Float64}(1.0))" *
" cannot be performed. You may want to use a `CachingOptimizer`" *
" in `AUTOMATIC` mode or you may need to call `reset_optimizer`" *
" before doing this operation if the `CachingOptimizer` is in" *
" `MANUAL` mode."
contents = sprint(showerror, err)
@test occursin("$(typeof(err)):", contents)
@test occursin(
"Modifying the objective function with $change cannot be performed",
contents,
)
@test occursin("## Fixing this error", contents)
return
end

function test_errors_show_SetAttributeNotAllowed()
Expand All @@ -276,26 +272,22 @@ function test_errors_show_SetAttributeNotAllowed()
@test sprint(showerror, MOI.UnsupportedAttribute(MOI.Name(), "Message")) ==
"$MOI.UnsupportedAttribute{$MOI.Name}:" *
" Attribute $MOI.Name() is not supported by the model: Message"
@test sprint(showerror, MOI.SetAttributeNotAllowed(MOI.Name())) ==
"$MOI.SetAttributeNotAllowed{$MOI.Name}:" *
" Setting attribute $MOI.Name() cannot be performed. You may want to use" *
" a `CachingOptimizer` in `AUTOMATIC` mode or you may need to call" *
" `reset_optimizer` before doing this operation if the" *
" `CachingOptimizer` is in `MANUAL` mode."
@test sprint(
showerror,
MOI.SetAttributeNotAllowed(MOI.Name(), "Message"),
) ==
"$MOI.SetAttributeNotAllowed{$MOI.Name}:" *
" Setting attribute $MOI.Name() cannot be performed: Message You may want" *
" to use a `CachingOptimizer` in `AUTOMATIC` mode or you may need to call" *
" `reset_optimizer` before doing this operation if the `CachingOptimizer`" *
" is in `MANUAL` mode." ==
"$MOI.SetAttributeNotAllowed{$MOI.Name}:" *
" Setting attribute $MOI.Name() cannot be performed: Message You may want" *
" to use a `CachingOptimizer` in `AUTOMATIC` mode or you may need to call" *
" `reset_optimizer` before doing this operation if the `CachingOptimizer`" *
" is in `MANUAL` mode."
contents = sprint(showerror, MOI.SetAttributeNotAllowed(MOI.Name()))
@test occursin("$MOI.SetAttributeNotAllowed{$MOI.Name}:", contents)
@test occursin(
"Setting attribute $(MOI.Name()) cannot be performed",
contents,
)
@test occursin("## Fixing this error", contents)
err = MOI.SetAttributeNotAllowed(MOI.Name(), "Message")
contents = sprint(showerror, err)
@test occursin("$(typeof(err))", contents)
@test occursin("Message", contents)
@test occursin(
"Setting attribute $(MOI.Name()) cannot be performed",
contents,
)
@test occursin("## Fixing this error", contents)
return
end

Expand Down Expand Up @@ -352,11 +344,13 @@ function test_get_fallback_error()
MOI.get(model, MOI.SolveTimeSec()),
)
err = MOI.GetAttributeNotAllowed(MOI.SolveTimeSec(), "")
@test sprint(showerror, err) ==
"$(typeof(err)): Getting attribute $(MOI.SolveTimeSec()) cannot be " *
"performed. You may want to use a `CachingOptimizer` in " *
"`AUTOMATIC` mode or you may need to call `reset_optimizer` before " *
"doing this operation if the `CachingOptimizer` is in `MANUAL` mode."
contents = sprint(showerror, err)
@test occursin("$(typeof(err)):", contents)
@test occursin(
"Getting attribute $(MOI.SolveTimeSec()) cannot be performed",
contents,
)
@test occursin("## Fixing this error", contents)
return
end

Expand Down
Loading