# Trying to save MPS from raw solver and problems with MOI.RawSolver()

**URL:** https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515
**Category:** Optimization (Mathematical)
**Tags:** jump
**Created:** [April 3, 2021, 6:48pm UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515 "2021-04-03T18:48:10Z")
**Posts on this page:** 6
**Page:** 1

<div class="post-metadata">

### Author: ![Henrique\_Becker](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrique_becker/32/15443_2.png) [@Henrique\_Becker](https://discourse.julialang.org/u/Henrique_Becker)
#### Post date: [April 3, 2021, 6:48pm UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515/1 "2021-04-03T18:48:11Z")

</div>

I am having problems with [`JuMP.write_to_file`](https://jump.dev/JuMP.jl/dev/reference/models/#JuMP.write_to_file) which calls [`MOI.write_to_file`](https://jump.dev/MathOptInterface.jl/stable/apireference/#MathOptInterface.write_to_file). I had some problems using `Model` with no solver attached (because this calls the MOI function mentioned above and, at the moment, it seems a little memory-hungry and limited, not supporting `.rew` and the like), so I wanted to try having a solver attached (CPLEX or Gurobi), and using it to write the MPS and started writing an alternative to `JuMP.write_to_file` that tried to be native if possible, however I am hitting some problems.

My code is [here](https://github.com/henriquebecker91/GuillotineModels.jl/blob/native_save_model/src/SaveModel.jl#L33), the highlighted line emphasizes my current problem. Independently of the the model being a `direct_model` or a `Model`, I hit a `ERROR: OptimizeNotCalled()` for trying to get the `MOI.RawSolver()` from the model object to call the specific solver saving/writing method. I tried `MOI.attach_optimizer` when it is a `Model` (and has a `CachingOptimizer` underlying) but this had no effect.

---

<div class="post-metadata">

### Author: ![odow](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/odow/32/28685_2.png) [@odow](https://discourse.julialang.org/u/odow)
#### Post date: [April 4, 2021, 10:26pm UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515/2 "2021-04-04T22:26:04Z")

</div>

I guess you need something like:

```nohighlight
native_write(model::Model) = native_write(backend(model))
function native_write(model::MOI.Utilities.CachingOptimizer)
    MOI.Utilities.attach_optimizer(model)
    return native_write(model.optimizer)
end
native_write(model::MOI.Bridges.LazyBridgeOptimizer) = native_write(model.model)

function native_write(model::Gurobi.Optimizer)
    # ...
end
function native_write(model::CPLEX.Optimizer)
    # ...
end

```

---

<div class="post-metadata">

### Author: ![Henrique\_Becker](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrique_becker/32/15443_2.png) [@Henrique\_Becker](https://discourse.julialang.org/u/Henrique_Becker)
#### Post date: [April 5, 2021, 12:19am UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515/3 "2021-04-05T00:19:39Z")

</div>

Thank you very much odow, I thought about pinging you, but it is easter and I did not want to be a bother.

---

<div class="post-metadata">

### Author: ![Henrique\_Becker](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrique_becker/32/15443_2.png) [@Henrique\_Becker](https://discourse.julialang.org/u/Henrique_Becker)
#### Post date: [April 5, 2021, 3:23pm UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515/4 "2021-04-05T15:23:44Z")

</div>

Worked like a charm. I kept my old logic to be able to fallback to `JuMP.write_to_file` if the solver is not recognized by the module (i.e., nobody extended the right functions), so I used your idea to be able to get the raw solver from a `Model` or `direct_model` in [lines 22–33 of this file](https://github.com/henriquebecker91/GuillotineModels.jl/blob/24ff9f42ee71071dfb2dc433035e328c5299dc9b/src/SaveModel.jl#L22--L33).

Now I just need to check if `JuMP.read_from_file` is able to parse back the native MPS files, XD.

Do you think JuMP/MOI may want to have this functionality in the future? I did not open a issua/PR because I had no time to go through the approval process this time, but in the future I can port this feature to JuMP/MOI.

---

<div class="post-metadata">

### Author: ![Henrique\_Becker](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/henrique_becker/32/15443_2.png) [@Henrique\_Becker](https://discourse.julialang.org/u/Henrique_Becker)
#### Post date: [May 11, 2021, 2:02pm UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515/5 "2021-05-11T14:02:06Z")

</div>

Just a follow-up, @odow. My version of `write_to_file` has helped me in a way I did not foresee: debugging Gurobi.

I have found some strange behavior from Gurobi ([described in this small Github repo](https://github.com/henriquebecker91/GeneratorG2OPP/)). Basically, if I solve a model that I know to be feasible with three harmless parameters, Gurobi says it is unfeasible, but ditching any the three parameters (that are `Threads = 1`, `Method = 2`, and `Seed = 1`) will make Gurobi find a feasible solution. I sent [a message to the Gurobi forums](https://support.gurobi.com/hc/en-us/community/posts/360078019352-Bug-Model-gives-unfeasible-when-three-parameters-are-passed-but-feasible-if-any-is-removed-) and they [opened a request because of it](https://support.gurobi.com/hc/en-us/requests/17332).

The `JuMP.write_to_file` was unable to create an MPS that replicated this behavior: I had the problem running from Julia, but reading it from the MPS of `JuMP.write_to_file` did not trigger the same strange behavior. Only when I used my version of the `write_to_file` that uses Gurobi native machinery, I was able to put my hands on an MPS that replicated the strange behavior (and guaranteed that the problem was not some very strange bug within JuMP/MOI).

@odow, do you think it would be interesting to add a feature request to JuMP asking for a `native_write` or even a flag passed to `write_to_file` so it uses the native machinery available? The code I am using is [here](https://github.com/henriquebecker91/GuillotineModels.jl/blob/master/src/SaveModel.jl), I have little time on my hands right now (finding this bug has delayed me), but if the feature request is approved I can slowly dot it through the weekends.

---

<div class="post-metadata">

### Author: ![odow](https://sea2.discourse-cdn.com/julialang/user_avatar/discourse.julialang.org/odow/32/28685_2.png) [@odow](https://discourse.julialang.org/u/odow)
#### Post date: [May 11, 2021, 9:16pm UTC](https://discourse.julialang.org/t/trying-to-save-mps-from-raw-solver-and-problems-with-moi-rawsolver/58515/6 "2021-05-11T21:16:07Z")

</div>

I’m not in favor of `native_write`.

But what I am in favor of is better documenting how to call the solver APIs. See also [How to use feasRelax in Gurobi ? · Issue #407 · jump-dev/Gurobi.jl · GitHub](https://github.com/jump-dev/Gurobi.jl/issues/407).

We could also define `MOI.write_to_file(model::Gurobi.Optimizer, filename::String)` inside Gurobi.jl.

The next version of JuMP should include a way to get the Gurobi.Optimizer object, even if there are multiple cache in the way, which should make this easier.
