From 6c61fd05c2868e5505d72ffa989b0b4a6a3c649d Mon Sep 17 00:00:00 2001 From: ChrisRackauckas Date: Mon, 29 Sep 2025 02:29:50 -0400 Subject: [PATCH 1/2] Add error message when NLopt AUGLAG algorithms are used without local_method MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Fixes #1020 NLopt's AUGLAG algorithms require a local optimization method to be specified. Previously, using them without a local_method would result in undefined behavior (returning wrong results like [0.0, 0.0] with Inf objective). This commit adds a clear error message when AUGLAG algorithms are used without specifying a local_method parameter, helping users understand the correct usage. Changes: - Add check in __map_optimizer_args! to detect AUGLAG algorithms without local_method - Provide helpful error message with usage example - Add test cases to verify the error is thrown correctly 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- lib/OptimizationNLopt/src/OptimizationNLopt.jl | 9 +++++++++ lib/OptimizationNLopt/test/runtests.jl | 4 ++++ 2 files changed, 13 insertions(+) diff --git a/lib/OptimizationNLopt/src/OptimizationNLopt.jl b/lib/OptimizationNLopt/src/OptimizationNLopt.jl index 31f7642a9..46f8465e9 100644 --- a/lib/OptimizationNLopt/src/OptimizationNLopt.jl +++ b/lib/OptimizationNLopt/src/OptimizationNLopt.jl @@ -68,6 +68,15 @@ function __map_optimizer_args!(cache::OptimizationCache, opt::NLopt.Opt; local_maxtime::Union{Number, Nothing} = nothing, local_options::Union{NamedTuple, Nothing} = nothing, kwargs...) + + # Check if AUGLAG algorithm requires local_method + alg_str = string(opt.algorithm) + if occursin("AUGLAG", alg_str) && local_method === nothing + error("NLopt.$(opt.algorithm) requires a local optimization method. " * + "Please specify a local_method, e.g., solve(prob, NLopt.$(opt.algorithm)(); " * + "local_method = NLopt.LN_NELDERMEAD())") + end + if local_method !== nothing if isa(local_method, NLopt.Opt) if ndims(local_method) != length(cache.u0) diff --git a/lib/OptimizationNLopt/test/runtests.jl b/lib/OptimizationNLopt/test/runtests.jl index f295e80ab..44898bc56 100644 --- a/lib/OptimizationNLopt/test/runtests.jl +++ b/lib/OptimizationNLopt/test/runtests.jl @@ -149,6 +149,10 @@ using Test, Random # @test sol.retcode == ReturnCode.Success @test 10 * sol.objective < l1 + # Test that AUGLAG without local_method throws an error + @test_throws ErrorException solve(prob, NLopt.LN_AUGLAG()) + @test_throws ErrorException solve(prob, NLopt.LD_AUGLAG()) + function con2_c(res, x, p) res .= [x[1]^2 + x[2]^2 - 1.0, x[2] * sin(x[1]) - x[1] - 2.0] end From 37f8492afcccfe38f407b5291177b9d879365fac Mon Sep 17 00:00:00 2001 From: ChrisRackauckas Date: Mon, 29 Sep 2025 02:37:41 -0400 Subject: [PATCH 2/2] Use direct type comparison for AUGLAG check instead of string matching MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Per review feedback, updated the AUGLAG algorithm check to directly compare against the specific algorithm types (NLopt.LN_AUGLAG, NLopt.LD_AUGLAG, NLopt.AUGLAG) rather than using string pattern matching. This is cleaner and more maintainable. 🤖 Generated with [Claude Code](https://claude.com/claude-code) Co-Authored-By: Claude --- lib/OptimizationNLopt/src/OptimizationNLopt.jl | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/lib/OptimizationNLopt/src/OptimizationNLopt.jl b/lib/OptimizationNLopt/src/OptimizationNLopt.jl index 46f8465e9..3803cc46f 100644 --- a/lib/OptimizationNLopt/src/OptimizationNLopt.jl +++ b/lib/OptimizationNLopt/src/OptimizationNLopt.jl @@ -70,8 +70,7 @@ function __map_optimizer_args!(cache::OptimizationCache, opt::NLopt.Opt; kwargs...) # Check if AUGLAG algorithm requires local_method - alg_str = string(opt.algorithm) - if occursin("AUGLAG", alg_str) && local_method === nothing + if opt.algorithm ∈ (NLopt.LN_AUGLAG, NLopt.LD_AUGLAG, NLopt.AUGLAG) && local_method === nothing error("NLopt.$(opt.algorithm) requires a local optimization method. " * "Please specify a local_method, e.g., solve(prob, NLopt.$(opt.algorithm)(); " * "local_method = NLopt.LN_NELDERMEAD())")