> ## Documentation Index
> Fetch the complete documentation index at: https://proto.evodesign.org/docs/llms.txt
> Use this file to discover all available pages before exploring further.

# LigandMPNN

> Released in 2023, LigandMPNN is an inverse-folding model that designs a sequence for a protein backbone while explicitly accounting for the non-protein atoms around it: small-molecule ligands, nucleotides, and metal ions. It extends ProteinMPNN, which ignores those atoms, and substantially improves sequence recovery for residues that contact ligands, nucleic acids, or metals, making it a model of choice for binding-site and cofactor-aware design. It can design sequences for a backbone and score how well a sequence fits a structure.

<div class="page-hero"><img class="page-hero-banner" src="https://proto-bio.github.io/proto-assets/images/tool/ligandmpnn/hero.png" alt="LigandMPNN" /><div class="tool-org-badges page-hero-badges"><a href="/docs/tools/organizations/institute-for-protein-design" class="tool-org-badge" style={{background: "#4b2e83"}} title="Institute for Protein Design"><img src="https://mintcdn.com/bio-pro/_UGa2jUMKeVPCbLk/assets/images/cached/6c4da2f317fc.png?fit=max&auto=format&n=_UGa2jUMKeVPCbLk&q=85&s=e0eec78648cb6cc4938f40ab18608b31" alt="" class="tool-org-badge-logo" width="200" height="200" data-path="assets/images/cached/6c4da2f317fc.png" /> IPD</a></div></div>

<Note>
  **License:** LigandMPNN is open source and free for academic and commercial use under an MIT license. Please refer to [the license](https://github.com/dauparas/LigandMPNN/blob/main/LICENSE) for full terms.
</Note>

<p class="entity-disclaimer">Proto is not affiliated with Institute for Protein Design. This toolkit is open source and builds on the implementation produced by this organization. Product names, logos, and trademarks are the property of their respective owners.</p>

<hr class="entity-rule" />

<input type="radio" name="tab-ligandmpnn" id="none-ligandmpnn" class="tab-radio-input" />

<input type="radio" name="tab-ligandmpnn" id="github-ligandmpnn" class="tab-radio-input" defaultChecked />

<input type="radio" name="tab-ligandmpnn" id="paper-ligandmpnn" class="tab-radio-input" />

<input type="radio" name="tab-ligandmpnn" id="cite-ligandmpnn" class="tab-radio-input" />

<input type="radio" name="tab-ligandmpnn" id="source-ligandmpnn" class="tab-radio-input" />

<input type="radio" name="tab-ligandmpnn" id="notebook-ligandmpnn" class="tab-radio-input" />

<input type="radio" name="tab-ligandmpnn" id="proto-ligandmpnn" class="tab-radio-input" />

<div class="tool-tab-bar">
  <span class="tool-tab-wrap"><label for="github-ligandmpnn" class="tool-tab tab-open badge-github"><svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0024 12c0-6.63-5.37-12-12-12z" /></svg> GitHub</label><label for="none-ligandmpnn" class="tool-tab tab-close badge-github"><svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0024 12c0-6.63-5.37-12-12-12z" /></svg> GitHub</label></span> <span class="tool-tab-wrap"><label for="paper-ligandmpnn" class="tool-tab tab-open badge-paper"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z" /><polyline points="14 2 14 8 20 8" /><line x1="16" y1="13" x2="8" y2="13" /><line x1="16" y1="17" x2="8" y2="17" /><polyline points="10 9 9 9 8 9" /></svg> Publication</label><label for="none-ligandmpnn" class="tool-tab tab-close badge-paper"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z" /><polyline points="14 2 14 8 20 8" /><line x1="16" y1="13" x2="8" y2="13" /><line x1="16" y1="17" x2="8" y2="17" /><polyline points="10 9 9 9 8 9" /></svg> Publication</label></span> <span class="tool-tab-wrap"><label for="cite-ligandmpnn" class="tool-tab tab-open badge-cite"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M3 21c3 0 7-1 7-8V5c0-1.25-.756-2.017-2-2H4c-1.25 0-2 .75-2 1.972V11c0 1.25.75 2 2 2 1 0 1 0 1 1v1c0 1-1 2-2 2s-1 .008-1 1.031V20c0 1 0 1 1 1z" /><path d="M15 21c3 0 7-1 7-8V5c0-1.25-.757-2.017-2-2h-4c-1.25 0-2 .75-2 1.972V11c0 1.25.75 2 2 2h.75c0 2.25.25 4-2.75 4v3c0 1 0 1 1 1z" /></svg> Cite</label><label for="none-ligandmpnn" class="tool-tab tab-close badge-cite"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M3 21c3 0 7-1 7-8V5c0-1.25-.756-2.017-2-2H4c-1.25 0-2 .75-2 1.972V11c0 1.25.75 2 2 2 1 0 1 0 1 1v1c0 1-1 2-2 2s-1 .008-1 1.031V20c0 1 0 1 1 1z" /><path d="M15 21c3 0 7-1 7-8V5c0-1.25-.757-2.017-2-2h-4c-1.25 0-2 .75-2 1.972V11c0 1.25.75 2 2 2h.75c0 2.25.25 4-2.75 4v3c0 1 0 1 1 1z" /></svg> Cite</label></span> <span class="tool-tab-wrap"><label for="source-ligandmpnn" class="tool-tab tab-open badge-source"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Tool Source</label><label for="none-ligandmpnn" class="tool-tab tab-close badge-source"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Tool Source</label></span> <span class="tool-tab-wrap"><label for="notebook-ligandmpnn" class="tool-tab tab-open badge-notebook"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M2 3h6a4 4 0 0 1 4 4v14a3 3 0 0 0-3-3H2z" /><path d="M22 3h-6a4 4 0 0 0-4 4v14a3 3 0 0 1 3-3h7z" /></svg> Open as Notebook</label><label for="none-ligandmpnn" class="tool-tab tab-close badge-notebook"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M2 3h6a4 4 0 0 1 4 4v14a3 3 0 0 0-3-3H2z" /><path d="M22 3h-6a4 4 0 0 0-4 4v14a3 3 0 0 1 3-3h7z" /></svg> Open as Notebook</label></span> <span class="tool-tab-wrap"><label for="proto-ligandmpnn" class="tool-tab tab-open badge-proto"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M13 2L3 14h9l-1 8 10-12h-9l1-8z" /></svg> Open on Proto</label><label for="none-ligandmpnn" class="tool-tab tab-close badge-proto"><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M13 2L3 14h9l-1 8 10-12h-9l1-8z" /></svg> Open on Proto</label></span>
</div>

<a href="https://github.com/dauparas/LigandMPNN" target="_blank" class="tab-panel github-panel" data-tab="github-ligandmpnn">
  <div class="gh-card-wrap">
    <img src="https://opengraph.githubassets.com/1/dauparas/LigandMPNN" class="gh-card-img img-fallback" alt="dauparas/LigandMPNN" />

    <div class="gh-card-fallback">
      <div class="gh-fallback-org"><svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0024 12c0-6.63-5.37-12-12-12z" /></svg> dauparas/LigandMPNN</div>
    </div>
  </div>

  <span class="panel-goto-btn gh-goto-btn"><span><svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0024 12c0-6.63-5.37-12-12-12z" /></svg> View repo</span></span>
</a>

<a href="https://doi.org/10.1038/s41592-025-02626-1" target="_blank" class="tab-panel paper-panel" data-tab="paper-ligandmpnn">
  <div class="paper-info">
    <div class="paper-title">Atomic context-conditioned protein sequence design using
    LigandMPNN</div>
    <div class="paper-meta">Justas Dauparas, Gyu Rie Lee, ... David Baker</div>
    <div class="paper-meta paper-venue">Nat. Methods (2025)</div>
  </div>

  <span class="panel-goto-btn pub-goto-btn"><span><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M14 2H6a2 2 0 0 0-2 2v16a2 2 0 0 0 2 2h12a2 2 0 0 0 2-2V8z" /><polyline points="14 2 14 8 20 8" /><line x1="16" y1="13" x2="8" y2="13" /><line x1="16" y1="17" x2="8" y2="17" /><polyline points="10 9 9 9 8 9" /></svg> Read paper</span></span>
</a>

<div class="tab-panel cite-panel" data-tab="cite-ligandmpnn">
  <div class="cite-code-wrap">
    ```bibtex theme={null}
    @ARTICLE{Dauparas2025-eg,
      title     = "Atomic context-conditioned protein sequence design using
                   {LigandMPNN}",
      author    = "Dauparas, Justas and Lee, Gyu Rie and Pecoraro, Robert and An,
                   Linna and Anishchenko, Ivan and Glasscock, Cameron and Baker,
                   David",
      journal   = "Nat. Methods",
      publisher = "Springer Science and Business Media LLC",
      volume    =  22,
      number    =  4,
      pages     = "717--723",
      doi       = "10.1038/s41592-025-02626-1",
      month     =  apr,
      year      =  2025,
      language  = "en"
    }
    ```
  </div>

  <span class="panel-goto-btn cite-copy-btn"><span><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M3 21c3 0 7-1 7-8V5c0-1.25-.756-2.017-2-2H4c-1.25 0-2 .75-2 1.972V11c0 1.25.75 2 2 2 1 0 1 0 1 1v1c0 1-1 2-2 2s-1 .008-1 1.031V20c0 1 0 1 1 1z" /><path d="M15 21c3 0 7-1 7-8V5c0-1.25-.757-2.017-2-2h-4c-1.25 0-2 .75-2 1.972V11c0 1.25.75 2 2 2h.75c0 2.25.25 4-2.75 4v3c0 1 0 1 1 1z" /></svg> Copy citation</span></span>
</div>

<a href="https://github.com/evo-design/proto-tools/tree/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn" target="_blank" class="tab-panel source-panel" data-tab="source-ligandmpnn">
  <div class="source-info">
    <img src="https://github.com/evo-design.png?size=40" class="source-avatar" width="36" height="36" />

    <span class="source-path">evo-design/proto-tools<span class="source-subpath">/proto\_tools/tools/inverse\_folding/ligandmpnn</span></span>
  </div>

  <span class="panel-goto-btn source-goto-btn"><span><svg width="14" height="14" viewBox="0 0 24 24" fill="currentColor"><path d="M12 0C5.37 0 0 5.37 0 12c0 5.31 3.435 9.795 8.205 11.385.6.105.825-.255.825-.57 0-.285-.015-1.23-.015-2.235-3.015.555-3.795-.735-4.035-1.41-.135-.345-.72-1.41-1.23-1.695-.42-.225-1.02-.78-.015-.795.945-.015 1.62.87 1.845 1.23 1.08 1.815 2.805 1.305 3.495.99.105-.78.42-1.305.765-1.605-2.67-.3-5.46-1.335-5.46-5.925 0-1.305.465-2.385 1.23-3.225-.12-.3-.54-1.53.12-3.18 0 0 1.005-.315 3.3 1.23.96-.27 1.98-.405 3-.405s2.04.135 3 .405c2.295-1.56 3.3-1.23 3.3-1.23.66 1.65.24 2.88.12 3.18.765.84 1.23 1.905 1.23 3.225 0 4.605-2.805 5.625-5.475 5.925.435.375.81 1.095.81 2.22 0 1.605-.015 2.895-.015 3.3 0 .315.225.69.825.57A12.02 12.02 0 0024 12c0-6.63-5.37-12-12-12z" /></svg> View source</span></span>
</a>

<a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/examples/example.ipynb" target="_blank" class="tab-panel notebook-panel" data-tab="notebook-ligandmpnn">
  <div class="notebook-info">
    <span class="notebook-icon">
      <svg width="40" height="40" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round">
        <path d="M2 3h6a4 4 0 0 1 4 4v14a3 3 0 0 0-3-3H2z" />

        <path d="M22 3h-6a4 4 0 0 0-4 4v14a3 3 0 0 1 3-3h7z" />
      </svg>
    </span>

    <span class="notebook-label">Open Notebook</span>
  </div>

  <span class="panel-goto-btn notebook-goto-btn"><span><svg width="14" height="14" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M2 3h6a4 4 0 0 1 4 4v14a3 3 0 0 0-3-3H2z" /><path d="M22 3h-6a4 4 0 0 0-4 4v14a3 3 0 0 1 3-3h7z" /></svg> Open notebook</span></span>
</a>

<div class="tab-panel proto-panel" data-tab="proto-ligandmpnn">
  <div class="proto-info">
    <div class="proto-cloud">
      <svg class="proto-cloud-bg" viewBox="0 0 640 512" xmlns="http://www.w3.org/2000/svg">
        <path d="M0 336c0 79.5 64.5 144 144 144H512c70.7 0 128-57.3 128-128c0-61.9-44-113.6-102.4-125.4c4.1-10.7 6.4-22.4 6.4-34.6c0-53-43-96-96-96c-19.7 0-38.1 6-53.3 16.2C367 64.2 315.3 32 256 32C167.6 32 96 103.6 96 192c0 2.7 .1 5.4 .2 8.1C40.2 219.8 0 273.2 0 336z" />
      </svg>

      <img noZoom src="https://mintcdn.com/bio-pro/KVh0EKV-IKblvXR8/assets/logo/evo-logo-light.svg?fit=max&auto=format&n=KVh0EKV-IKblvXR8&q=85&s=0cb66034ba45618505501aee6ea5f5c1" class="proto-panel-logo block dark:hidden" alt="Proto" width="198" height="151" data-path="assets/logo/evo-logo-light.svg" />

      <img noZoom src="https://mintcdn.com/bio-pro/KVh0EKV-IKblvXR8/assets/logo/evo-logo-dark.svg?fit=max&auto=format&n=KVh0EKV-IKblvXR8&q=85&s=2c9e23a14635e60384a434e220788f54" class="proto-panel-logo hidden dark:block" alt="Proto" width="198" height="151" data-path="assets/logo/evo-logo-dark.svg" />
    </div>
  </div>

  <div class="proto-actions">
    <a href="https://proto.evodesign.org/tools/ligandmpnn-sample" target="_blank" class="proto-action-btn"><span>LigandMPNN Sampling</span><svg width="13" height="13" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="7" y1="17" x2="17" y2="7" /><polyline points="7 7 17 7 17 17" /></svg></a>
    <a href="https://proto.evodesign.org/tools/ligandmpnn-score" target="_blank" class="proto-action-btn"><span>LigandMPNN Scoring</span><svg width="13" height="13" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><line x1="7" y1="17" x2="17" y2="7" /><polyline points="7 7 17 7 17 17" /></svg></a>
  </div>
</div>

<div class="entity-contributors"><span class="entity-contributors-label">Toolkit contributors</span><span class="entity-contributors-people"><a class="entity-contributor" href="https://github.com/bviggiano" target="_blank" rel="noopener" title="bviggiano: 48 commits"><img noZoom class="entity-contributor-avatar" src="https://avatars.githubusercontent.com/u/21143637?v=4&s=64" alt="" loading="lazy" /><span class="entity-contributor-login">bviggiano</span></a><a class="entity-contributor" href="https://github.com/dguo8412" target="_blank" rel="noopener" title="dguo8412: 27 commits"><img noZoom class="entity-contributor-avatar" src="https://avatars.githubusercontent.com/u/46211285?v=4&s=64" alt="" loading="lazy" /><span class="entity-contributor-login">dguo8412</span></a><a class="entity-contributor" href="https://github.com/brianhie" target="_blank" rel="noopener" title="brianhie: 6 commits"><img noZoom class="entity-contributor-avatar" src="https://avatars.githubusercontent.com/u/6365340?v=4&s=64" alt="" loading="lazy" /><span class="entity-contributor-login">brianhie</span></a><a class="entity-contributor" href="https://github.com/leba01" target="_blank" rel="noopener" title="leba01: 2 commits"><img noZoom class="entity-contributor-avatar" src="https://avatars.githubusercontent.com/u/124846286?v=4&s=64" alt="" loading="lazy" /><span class="entity-contributor-login">leba01</span></a></span></div>

| Function                  | Description                                     |                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                                            |
| ------------------------- | ----------------------------------------------- | -------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `run_ligandmpnn_sample()` | Sample protein sequences using LigandMPNN (GPU) | <a href="#api-run-ligandmpnn-sample" class="func-table-btn func-api-btn"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M4 19.5v-15A2.5 2.5 0 0 1 6.5 2H19a1 1 0 0 1 1 1v18a1 1 0 0 1-1 1H6.5a1 1 0 0 1 0-5H20" /></svg> Docs</a> <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/ligandmpnn_sample.py#L291" target="_blank" class="func-table-btn func-source-btn"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a> |
| `run_ligandmpnn_score()`  | Score protein sequences using LigandMPNN (GPU)  | <a href="#api-run-ligandmpnn-score" class="func-table-btn func-api-btn"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><path d="M4 19.5v-15A2.5 2.5 0 0 1 6.5 2H19a1 1 0 0 1 1 1v18a1 1 0 0 1-1 1H6.5a1 1 0 0 1 0-5H20" /></svg> Docs</a> <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/ligandmpnn_score.py#L132" target="_blank" class="func-table-btn func-source-btn"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>   |

## Background

LigandMPNN ([Dauparas et al., 2025](https://doi.org/10.1038/s41592-025-02626-1)) solves the inverse-folding problem for biomolecular assemblies: given a protein backbone together with the non-protein atoms around it, it predicts an amino-acid sequence compatible with that environment. It is a direct extension of ProteinMPNN, which sees only protein backbone atoms and is therefore blind to the bound ligands, nucleic acids, and metals that strongly shape which residues fit.

Internally, LigandMPNN keeps ProteinMPNN's message-passing design model and adds a second graph over the non-protein atoms. Residues and nearby ligand atoms exchange messages, and the model reads each atom's chemical element, which is what lets it reason about coordinating a metal or packing against a large or unusual ligand. It generates the sequence autoregressively and can also produce sidechain conformations so binding interactions can be inspected directly. On native backbones it recovers roughly 63% of the native residues that contact small molecules, 51% of those contacting nucleotides, and 78% of those coordinating metals.

The reference implementation is maintained by the [Institute for Protein Design](https://www.ipd.uw.edu/) at [dauparas/LigandMPNN](https://github.com/dauparas/LigandMPNN).

### Learning Resources

* [Introducing LigandMPNN](https://www.ipd.uw.edu/2025/03/introducing-ligandmpnn/) (Institute for Protein Design) - an accessible overview of what LigandMPNN adds over ProteinMPNN and when to use it.

## Tools

<a name="api-run-ligandmpnn-sample" />

<div class="tool-section-card tool-section-card--sample">
  ### LigandMPNN Sampling (`ligandmpnn-sample`)

  Designs new sequences for a backbone in the presence of its non-protein context. Each input structure is encoded once, with any ligand, nucleotide, or metal atoms included, and decoded into one or more candidate sequences with a perplexity and sequence recovery score.

  #### API Reference

  <div class="api-model-section api-input-section">
    <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/shared_data_models.py#L123" target="_blank" class="func-table-btn func-source-btn api-model-source"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>

    <Accordion title="Input: InverseFoldingInput">
      <ParamField path="inputs" type="List[InverseFoldingStructureInput]" required>
        Per-structure inputs, each containing a structure plus optional `chains_to_redesign` and `fixed_positions` selections.

        <Expandable title="InverseFoldingStructureInput">
          <ParamField path="chains_to_redesign" type="ChainSelection">
            Chains to redesign. `None` means redesign every chain in the structure. Accepts shorthand `"A"` or `["A", "B"]` at construction.
          </ParamField>

          <ParamField path="fixed_positions" type="ResidueSelection">
            Per-chain positions whose residue identity is held fixed during design (1-indexed). Accepts shorthand `{"A": [1, 2, 3]}` at construction.
          </ParamField>

          <ParamField path="structure" type="Structure" required>
            Protein structure. Accepts a file path, raw PDB/CIF content string, `Structure` object, or a dict in the shape produced by `Structure.model_dump(mode='json')`.
          </ParamField>
        </Expandable>
      </ParamField>
    </Accordion>
  </div>

  <div class="api-model-section api-config-section">
    <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/ligandmpnn_sample.py#L54" target="_blank" class="func-table-btn func-source-btn api-model-source"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>

    <Accordion title="Config: LigandMPNNSampleConfig">
      <ParamField path="model_type" type="enum" default="ligand_mpnn">
        LigandMPNN implementation. `ligand_mpnn` (default) is the Foundry implementation; `original` runs the original LigandMPNN code and weights, auto-provisioned on first use, and emits packed full-atom structures.

        Available options: `ligand_mpnn`, `original`
      </ParamField>

      <ParamField path="use_atom_context" type="boolean" default="True">
        Whether ligand-aware variants encode ligand atom context.
      </ParamField>

      <ParamField path="checkpoint_path" type="string">
        Optional explicit LigandMPNN checkpoint path.
      </ParamField>

      <ParamField path="use_side_chain_context" type="boolean" default="False">
        Whether to condition on fixed-residue sidechain atoms.
      </ParamField>

      <ParamField path="cutoff_for_score" type="number" default="8.0">
        Ligand-residue distance cutoff (Å) for the ligand-interface recovery score.
      </ParamField>

      <ParamField path="excluded_amino_acids" type="array">
        One-letter codes of amino acids to exclude.
      </ParamField>

      <ParamField path="sc_num_denoising_steps" type="integer" default="8">
        Side-chain denoising steps. Only used when model\_type is `original`.
      </ParamField>

      <ParamField path="sc_num_samples" type="integer" default="1">
        Side-chain packing samples. Only used when model\_type is `original`.
      </ParamField>

      <ParamField path="verbose" type="integer" default="0">
        Verbosity level (0=quiet, 1=info, 2=debug, 3=raw subprocess stderr). `True` is coerced to `1` and `False` to `0`.
      </ParamField>

      <ParamField path="device" type="string" default="cuda">
        Device to run the model on. Options include 'cuda' (NVIDIA GPU), 'cpu' (CPU execution), or specific GPU devices like 'cuda:0'. Defaults to 'cuda'.
      </ParamField>

      <ParamField path="timeout" type="integer" default="3600">
        Maximum execution time in seconds. `None` waits indefinitely.
      </ParamField>

      <ParamField path="seed" type="integer">
        Random seed to use for sampling.
      </ParamField>

      <ParamField path="num_sequences_per_structure" type="integer" default="1">
        Total number of sequences to generate per input structure.
      </ParamField>

      <ParamField path="batch_size" type="integer">
        Number of sequences to process simultaneously on GPU. Defaults to num\_sequences\_per\_structure.
      </ParamField>

      <ParamField path="temperature" type="number" default="0.1">
        Controls randomness in sampling from logits.
      </ParamField>
    </Accordion>
  </div>

  <div class="api-model-section api-output-section">
    <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/ligandmpnn_sample.py#L236" target="_blank" class="func-table-btn func-source-btn api-model-source"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>

    <Accordion title="Output: LigandMPNNSampleOutput">
      <ResponseField name="design_sets" type="List[LigandMPNNDesignSet]" required>
        One `LigandMPNNDesignSet` per input structure, in input order.

        <Expandable title="LigandMPNNDesignSet">
          <ResponseField name="complexes" type="List[LigandMPNNDesign]" required>
            The complexes generated for one input structure, each a complete multi-chain complex with recovery metrics.
          </ResponseField>
        </Expandable>
      </ResponseField>
    </Accordion>
  </div>

  #### Applications

  Use this to design or redesign binding sites, enzyme active sites, nucleic-acid-binding interfaces, and metal-coordination sites, where the identity of nearby non-protein atoms determines which residues work. It is the right choice over backbone-only ProteinMPNN whenever a ligand, cofactor, nucleic acid, or metal is part of the target.

  #### Usage Tips

  * **Keep `use_atom_context` enabled.** It defaults to `True` and is the whole point of LigandMPNN: it encodes the surrounding ligand, nucleotide, and metal atoms. Turning it off makes the model effectively ligand-blind, close to plain ProteinMPNN.
  * **Set `use_side_chain_context` to `True` to honor a fixed motif.** It conditions on the sidechain atoms of fixed residues, which helps when redesigning around a preserved catalytic or binding motif. It defaults to `False`.
  * **Set `model_type="original"` when you need packed full-atom outputs.** The default `ligand_mpnn` uses the Foundry implementation and emits redesigned-backbone structures. `original` instead runs the original LigandMPNN code and weights, so sampling returns sequence-consistent full-atom (packed) structures. The code and weights are auto-provisioned into the model cache on first use, so no manual setup is needed; advanced users can override the sequence checkpoint with `checkpoint_path`.
  * **`fixed_positions` is counted from 1, not 0**, to match biological residue selection conventions. Listed positions keep their input residue, and chains or atoms you do not redesign still act as context rather than being removed.

  <a name="api-run-ligandmpnn-score" />
</div>

<div class="tool-section-card tool-section-card--score">
  ### LigandMPNN Scoring (`ligandmpnn-score`)

  Evaluates how well existing sequences fit a structure and its non-protein context, returning log-likelihood-based metrics with optional per-position logits.

  #### API Reference

  <div class="api-model-section api-input-section">
    <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/ligandmpnn_score.py#L25" target="_blank" class="func-table-btn func-source-btn api-model-source"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>

    <Accordion title="Input: LigandMPNNScoringInput">
      <ParamField path="sequence_structure_pairs" type="List[SequenceStructurePair]" required>
        Sequence and structure pairs to score; each pair may carry per-pair `fixed_positions` excluded from the metrics.

        <Expandable title="SequenceStructurePair">
          <ParamField path="sequence" type="string" required>
            Protein sequence to score against the structure.
          </ParamField>

          <ParamField path="structure" type="Structure" required>
            Protein structure to score the sequence against.
          </ParamField>

          <ParamField path="fixed_positions" type="ResidueSelection">
            Per-chain 1-indexed positions excluded from the aggregate scoring metrics. Accepts `{"A": [1, 2]}`.
          </ParamField>
        </Expandable>
      </ParamField>
    </Accordion>
  </div>

  <div class="api-model-section api-config-section">
    <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/ligandmpnn_score.py#L42" target="_blank" class="func-table-btn func-source-btn api-model-source"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>

    <Accordion title="Config: LigandMPNNScoringConfig">
      <ParamField path="return_logits" type="boolean" default="False">
        Whether to include per-position logits.
      </ParamField>

      <ParamField path="scoring_mode" type="enum" default="single_aa">
        Single-position or autoregressive scoring mode.

        Available options: `single_aa`, `autoregressive`
      </ParamField>

      <ParamField path="model_type" type="enum" default="ligand_mpnn">
        LigandMPNN implementation. `ligand_mpnn` (default) is the Foundry implementation; `original` runs the original LigandMPNN code and weights, auto-provisioned on first use.

        Available options: `ligand_mpnn`, `original`
      </ParamField>

      <ParamField path="checkpoint_path" type="string">
        Optional explicit LigandMPNN checkpoint path.
      </ParamField>

      <ParamField path="use_atom_context" type="boolean" default="True">
        Whether ligand-aware variants encode ligand atom context.
      </ParamField>

      <ParamField path="use_side_chain_context" type="boolean" default="False">
        Whether to condition on fixed-residue sidechain atoms.
      </ParamField>

      <ParamField path="cutoff_for_score" type="number" default="8.0">
        Ligand-residue distance cutoff (Å).
      </ParamField>

      <ParamField path="verbose" type="integer" default="0">
        Verbosity level (0=quiet, 1=info, 2=debug, 3=raw subprocess stderr). `True` is coerced to `1` and `False` to `0`.
      </ParamField>

      <ParamField path="device" type="string" default="cuda">
        Device to run the model on.
      </ParamField>

      <ParamField path="timeout" type="integer" default="3600">
        Maximum execution time in seconds. `None` waits indefinitely.
      </ParamField>

      <ParamField path="seed" type="integer">
        Random seed. When set, tools run reproducibly up to small GPU float noise (see `BaseToolOutput.approx_equal`), and the seed participates in cache keys. When None, cacheable seed-sensitive tools skip cache until seeded.
      </ParamField>
    </Accordion>
  </div>

  <div class="api-model-section api-output-section">
    <a href="https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/shared_data_models.py#L458" target="_blank" class="func-table-btn func-source-btn api-model-source"><svg width="12" height="12" viewBox="0 0 24 24" fill="none" stroke="currentColor" stroke-width="2" stroke-linecap="round" stroke-linejoin="round"><polyline points="16 18 22 12 16 6" /><polyline points="8 6 2 12 8 18" /></svg> Source</a>

    <Accordion title="Output: InverseFoldingScoringOutput">
      <ResponseField name="scores" type="List[InverseFoldingScoringMetrics]" required>
        List of scoring outputs, one per input sequence-structure pair. Each entry is a `Metrics` subclass with scalar metrics (accessed via `score.perplexity` or `score["perplexity"]`) plus declared `logits` / `vocab` fields.

        <Expandable title="InverseFoldingScoringMetrics">
          <ResponseField name="logits" type="array">
            Per-position logits array `(seq_len, vocab_size)`. `None` unless the tool returns logits.
          </ResponseField>

          <ResponseField name="vocab" type="array">
            Token ordering for `logits`.
          </ResponseField>

          <ResponseField name="primary_metric" type="string">
            Name of the metric that best summarizes the result overall (e.g. `"avg_plddt"` for AlphaFold2). Used by downstream UI and reporting to pick a headline value.
          </ResponseField>

          <ResponseField name="metric_type" type="string">
            Concrete Metrics subclass tag; enables typed reconstruction after a serialization round-trip.
          </ResponseField>
        </Expandable>
      </ResponseField>

      **Metrics** (one set per `scores` item)

      | Metric               | Type  | Range | Availability |
      | -------------------- | ----- | ----- | ------------ |
      | `log_likelihood`     | float | ≤ 0.0 | always       |
      | `avg_log_likelihood` | float | ≤ 0.0 | always       |
      | `perplexity`         | float | ≥ 1.0 | always       |
    </Accordion>
  </div>

  #### Applications

  Use this to rank designs or assess mutations near ligands, nucleic acids, or metals, where backbone-only scoring would miss the very interactions that matter. Lower perplexity indicates a better fit to the structure and its bound environment.

  #### Usage Tips

  * **`scoring_mode` changes what the score means.** `single_aa` (the default) scores each position from its own conditional probability and is order-independent, which is what you usually want for ranking. `autoregressive` scores along one seed-determined decoding order, so it depends on the seed.
  * **`fixed_positions` excludes residues from the aggregate score.** Set it per (sequence, structure) input pair as a `{chain: [positions]}` selection counted from 1, not 0, to match biological residue selection conventions, so the score reflects only the residues you care about.
  * **`return_logits` (default `False`) has a size trade-off.** Enabling it adds a per-position logit array per sequence for residue-level analysis, which dominates output size and memory for long sequences, so leave it off unless you need it.
</div>

## Toolkit Notes

These apply to every LigandMPNN tool in this toolkit (`ligandmpnn-sample`, `ligandmpnn-score`).

* **A GPU is recommended.** LigandMPNN is a small message-passing model that also runs on CPU, but a GPU is much faster when designing or scoring many sequences.
* **The non-protein context must be in the input structure.** LigandMPNN only conditions on ligands, nucleotides, or metals that are present in the supplied structure; if they are absent, it behaves like backbone-only ProteinMPNN.

<Tip>
  **Example notebook:** See the [full working example](https://github.com/evo-design/proto-tools/blob/47e34afa5ea240a3b406e323dc38aa5dc85f223e/proto_tools/tools/inverse_folding/ligandmpnn/examples/example.ipynb) for a copy-paste-ready walkthrough.
</Tip>

## Infrastructure Guides

The following guides cover how to run tools efficiently and at scale.

<CardGroup cols={2}>
  <Card title="Tool Persistence" icon="repeat" href="/docs/tools/guides/tool-persistence">Keep a tool's model warm across calls instead of reloading it every invocation.</Card>
  <Card title="Device Management" icon="cpu" href="/docs/tools/guides/device-management">How GPUs are allocated to tools and how to target specific devices.</Card>
  <Card title="Parallel Execution" icon="layers" href="/docs/tools/guides/parallel-execution">Fan a batch of inputs out across multiple GPUs.</Card>
</CardGroup>
