Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Add copy buttons to all
 blocks\n(function() {\n function addCopyButtons() {\n document.querySelectorAll('pre code').forEach(function(codeBlock) {\n if (codeBlock.parentElement.hasAttribute('data-copy-added')) return;\n codeBlock.parentElement.setAttribute('data-copy-added', 'true');\n \n var btn = document.createElement('button');\n btn.textContent = 'Copy';\n btn.style.cssText = 'position:absolute;top:4px;right:4px;padding:2px 8px;font-size:11px;background:#4ecdc4;border:none;border-radius:4px;color:#1a1a2e;cursor:pointer;opacity:0.7;transition:opacity 0.2s;';\n btn.onmouseover = function() { this.style.opacity = '1'; };\n btn.onmouseout = function() { this.style.opacity = '0.7'; };\n btn.onclick = function() {\n navigator.clipboard.writeText(codeBlock.textContent).then(function() {\n btn.textContent = 'Copied!';\n setTimeout(function() { btn.textContent = 'Copy'; }, 1500);\n });\n };\n codeBlock.parentElement.style.position = 'relative';\n codeBlock.parentElement.appendChild(btn);\n });\n }\n \n addCopyButtons();\n \n // Re-run on dynamic content\n var observer = new MutationObserver(addCopyButtons);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Add Copy Buttons to Code Blocks");
}
} catch(__e) { console.warn('[Userscript:Add Copy Buttons to Code Blocks]', __e); }
})();
(function(){
try {
var __m = "github.com";
var __re = new RegExp('^' + "github\\.com" + '
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Force GitHub README to respect dark mode\n(function() {\n var style = document.createElement('style');\n style.textContent = '\n .markdown-body {\n color-scheme: dark light;\n }\n .markdown-body pre { background: #161b22 !important; }\n .markdown-body code { background: rgba(110, 118, 129, 0.4) !important; }\n .markdown-body table th, .markdown-body table td { border-color: #30363d !important; }\n .markdown-body img { background: #0d1117; }\n .markdown-body blockquote { border-left-color: #8b949e; }\n .markdown-body hr { border-color: #30363d; }\n ';\n document.head.appendChild(style);\n})();", "GitHub Dark Mode README Fix"); } } catch(__e) { console.warn('[Userscript:GitHub Dark Mode README Fix]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Highlight search terms from Google/DuckDuckGo/Bing referrer\n(function() {\n var ref = document.referrer;\n var terms = [];\n \n if (ref.includes('google.com') || ref.includes('duckduckgo.com') || ref.includes('bing.com')) {\n var url = new URL(ref);\n var q = url.searchParams.get('q') || url.searchParams.get('p');\n if (q) {\n terms = q.split(/\\s+/).filter(function(t) { return t.length > 2; });\n }\n }\n \n if (terms.length === 0) return;\n \n var style = document.createElement('style');\n style.textContent = '.userscript-highlight { background: #fbbf24; color: #1a1a2e; padding: 1px 3px; border-radius: 2px; }';\n document.head.appendChild(style);\n \n function highlight(node) {\n if (node.nodeType === 3) { // text node\n var text = node.textContent;\n var found = false;\n terms.forEach(function(term) {\n var regex = new RegExp('(' + term.replace(/[.*+?^${}()|[\\]\\\\]/g, '\\\\') + ')', 'gi');\n if (regex.test(text)) {\n found = true;\n var frag = document.createDocumentFragment();\n var parts = text.split(regex);\n parts.forEach(function(part, i) {\n if (i % 2 === 0) {\n frag.appendChild(document.createTextNode(part));\n } else {\n var span = document.createElement('span');\n span.className = 'userscript-highlight';\n span.textContent = part;\n frag.appendChild(span);\n }\n });\n node.parentNode.replaceChild(frag, node);\n }\n });\n } else if (node.nodeType === 1 && node.childNodes) { // element\n var skipTags = ['SCRIPT', 'STYLE', 'NOSCRIPT', 'TEXTAREA', 'INPUT', 'SELECT'];\n if (!skipTags.includes(node.tagName)) {\n Array.from(node.childNodes).forEach(highlight);\n }\n }\n }\n \n highlight(document.body);\n \n // Re-highlight on dynamic content\n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1 || node.nodeType === 3) highlight(node);\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Highlight Search Terms"); } } catch(__e) { console.warn('[Userscript:Highlight Search Terms]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Strip utm_, fbclid, gclid, etc. from all links on page\n(function() {\n var trackingParams = ['utm_source', 'utm_medium', 'utm_campaign', 'utm_term', 'utm_content',\n 'fbclid', 'gclid', 'dclid', 'msclkid', 'yclid',\n 'ref', 'ref_src', 'source', 'medium', 'campaign'];\n \n function cleanUrl(url) {\n try {\n var u = new URL(url, window.location.origin);\n var changed = false;\n trackingParams.forEach(function(p) {\n if (u.searchParams.has(p)) {\n u.searchParams.delete(p);\n changed = true;\n }\n });\n return changed ? u.toString() : url;\n } catch (e) {\n return url;\n }\n }\n \n function cleanLinks() {\n document.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n \n cleanLinks();\n \n var observer = new MutationObserver(function(mutations) {\n mutations.forEach(function(m) {\n m.addedNodes.forEach(function(node) {\n if (node.nodeType === 1) {\n if (node.tagName === 'A') cleanLinks();\n node.querySelectorAll('a[href]').forEach(function(a) {\n var clean = cleanUrl(a.href);\n if (clean !== a.href) a.href = clean;\n });\n }\n });\n });\n });\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "Remove Tracking Parameters from Links"); } } catch(__e) { console.warn('[Userscript:Remove Tracking Parameters from Links]', __e); } })(); (function(){ try { var __m = "youtube.com"; var __re = new RegExp('^' + "youtube\\.com" + '
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Auto-enable theater mode on YouTube\n(function() {\n function tryTheater() {\n var btn = document.querySelector('button[aria-label=\"Theater mode\"], ytd-player #player button[title=\"Theater mode\"]');\n if (btn && !btn.classList.contains('activated')) {\n btn.click();\n }\n }\n \n // Try immediately\n tryTheater();\n \n // Try after navigation (SPA)\n var lastUrl = location.href;\n setInterval(function() {\n if (location.href !== lastUrl) {\n lastUrl = location.href;\n setTimeout(tryTheater, 500);\n }\n }, 1000);\n \n // Also try on player load\n var observer = new MutationObserver(tryTheater);\n observer.observe(document.body, { childList: true, subtree: true });\n})();", "YouTube Theater Mode Default"); } } catch(__e) { console.warn('[Userscript:YouTube Theater Mode Default]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Remove or un-stick sticky/fixed headers that block content\n(function() {\n function unstick() {\n document.querySelectorAll('header, nav, [role=\"banner\"], .header, .navbar, .sticky, .fixed-top, [style*=\"position: fixed\"], [style*=\"position:sticky\"]').forEach(function(el) {\n if (el.style.position === 'fixed' || el.style.position === 'sticky' || \n getComputedStyle(el).position === 'fixed' || getComputedStyle(el).position === 'sticky') {\n el.style.position = 'static';\n el.style.top = 'auto';\n el.style.zIndex = 'auto';\n }\n });\n }\n \n unstick();\n \n var observer = new MutationObserver(unstick);\n observer.observe(document.body, { childList: true, subtree: true, attributes: true, attributeFilter: ['style', 'class'] });\n})();", "Kill Sticky Headers"); } } catch(__e) { console.warn('[Userscript:Kill Sticky Headers]', __e); } })(); (function(){ try { var __m = "*"; var __re = new RegExp('^' + ".*" + '
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer
, 'i'); if (__m === '*' || __re.test(location.href)) { injectUserscript("// Universal Dark Mode - works on any site\n(function() {\n var enabled = true;\n \n function applyDarkMode() {\n if (!enabled) return;\n \n // Create style element if it doesn't exist\n var style = document.getElementById('universal-dark-mode-style');\n if (!style) {\n style = document.createElement('style');\n style.id = 'universal-dark-mode-style';\n document.head.appendChild(style);\n }\n \n // Dark mode CSS - inverts colors but preserves images/video\n style.textContent = '\n /* Invert everything except media */\n html {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #1a1a2e !important;\n }\n \n /* Restore images, videos, iframes, canvas */\n img, video, iframe, canvas, svg, picture, [style*=\"background-image\"] {\n filter: invert(1) hue-rotate(180deg) !important;\n }\n \n /* Preserve specific elements that should not be inverted */\n .no-dark-mode, .no-dark-mode *,\n [data-theme=\"light\"], [data-theme=\"light\"],\n .ace_editor, .ace_editor *,\n .CodeMirror, .CodeMirror *,\n .monaco-editor, .monaco-editor *,\n .markdown-body pre, .markdown-body pre *,\n .highlight, .highlight *,\n pre code, pre code * {\n filter: none !important;\n }\n \n /* Fix common UI elements */\n .modal, .popup, .dropdown-menu, .tooltip, .popover {\n filter: invert(1) hue-rotate(180deg) !important;\n background: #2d2d44 !important;\n border-color: #444 !important;\n }\n \n /* Scrollbars */\n ::-webkit-scrollbar { background: #1a1a2e !important; }\n ::-webkit-scrollbar-thumb { background: #444 !important; }\n ::-webkit-scrollbar-thumb:hover { background: #555 !important; }\n \n /* Selection */\n ::selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ::-moz-selection { background: #4ecdc4 !important; color: #1a1a2e !important; }\n ';\n }\n \n function removeDarkMode() {\n var style = document.getElementById('universal-dark-mode-style');\n if (style) style.remove();\n }\n \n // Toggle with Alt+Shift+D\n document.addEventListener('keydown', function(e) {\n if (e.altKey && e.shiftKey && e.key === 'D') {\n e.preventDefault();\n enabled = !enabled;\n if (enabled) {\n applyDarkMode();\n console.log('[Universal Dark Mode] Enabled');\n } else {\n removeDarkMode();\n console.log('[Universal Dark Mode] Disabled');\n }\n }\n });\n \n // Apply on load\n applyDarkMode();\n \n // Re-apply on dynamic content\n var observer = new MutationObserver(function(mutations) {\n if (enabled && !document.getElementById('universal-dark-mode-style')) {\n applyDarkMode();\n }\n });\n observer.observe(document.head, { childList: true });\n \n console.log('[Universal Dark Mode] Loaded - Press Alt+Shift+D to toggle');\n})();", "Universal Dark Mode"); } } catch(__e) { console.warn('[Userscript:Universal Dark Mode]', __e); } })(); })();
Skip to content

Stokes/Elasticity using biharmonic/Laplace - #162

Open
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2
Open

Stokes/Elasticity using biharmonic/Laplace#162
isuruf wants to merge 2 commits into
inducer:mainfrom
isuruf:stokes_biharmonic2

Conversation

@isuruf

@isurufisuruf commented Jun 27, 2022

Copy link
Copy Markdown
Collaborator
  • Point sumpy back to main

Comment threadsetup.py Outdated
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 4 times, most recently from 95a898d to acc5ae0CompareJune 27, 2022 21:26
@alexfikl

Copy link
Copy Markdown
Collaborator

@isuruf I've been using #29 for my stuff. Should I switch to this? Does it contain any fixes or is it just a clean squash on top of main?

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@alexfikl, this PR has only parts of #29 so that it is easier to review. I'm not sure if this PR has all the features that you need. Probably not.

Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I think it'd be good to have CalculusPatch tests to ensure that PDE rediual for Stokes and elasticity is zero.

Copy link
Copy Markdown
CollaboratorAuthor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a test to check the stokes PDE in a9931e5 and elasticity in bb31471

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Added a bunch of nitpicks to pytential.symbolic.stokes (mostly based on how I've been using the new stuff). Many are ignorable, so feel free!

The main thing that bothered me while going through it was the nu_sym everywhere. It feels like that should be handled in elasticity so the user never gets a chance to pass nu_sym=3 from the Stokes wrappers.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, @alexfikl, this is ready for another round of reviews.

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch more nitpicks in pde.system_utils this time around :D

This is looking very cool!

Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/typing.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

That's technically not testing the Stokes potential, it's testing pytential-computed derivatives thereof.

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
@@ -0,0 +1,166 @@
__copyright__ = "Copyright (C) 2021 Isuru Fernando"

Copy link
Copy Markdown
Owner

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull the docs of this into like an "internals" chapter? internals.rst?

Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/mappers.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py
@isuruf
isurufforce-pushed the stokes_biharmonic2 branch 2 times, most recently from f7b661d to d34f787CompareNovember 23, 2022 15:06
@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

This is ready for another round of reviews

@alexfiklalexfikl left a comment

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Left a bunch of nitpicks while reading this again. I don't think any of them are stoppers of any sort, so go for it when you and @inducer are done! 🚀

Also, thanks for all this Stokes performance work! It's been immensely helpful in the past two-ish years!

Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadtest/test_pde_system_utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threaddoc/symbolic.rst Outdated
Comment threadpytential/symbolic/dof_desc.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/utils.py Outdated
Comment threadpytential/symbolic/elasticity.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py Outdated
Comment threadtest/test_stokes.py
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
Comment threadpytential/symbolic/pde/system_utils.py Outdated
@inducer

Copy link
Copy Markdown
Owner

Unsubscribing... @-mention or request review once it's ready for a look or needs attention.

@isuruf

Copy link
Copy Markdown
CollaboratorAuthor

@inducer, ready for a review

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from a9f21ed to 3443fa6CompareFebruary 13, 2026 14:43

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR expands pytential’s symbolic Stokes/elasticity support by introducing alternative kernel representations (naive/Laplace/biharmonic) and adding infrastructure to rewrite IntG expressions in terms of a chosen base kernel, along with tests and docs updates.

Changes:

  • Add new symbolic elasticity wrappers and refactor symbolic Stokes wrappers/operators to support multiple representation methods.
  • Introduce pytential.symbolic.pde.system_utils to rewrite layer-potential expressions (including target-to-source transformation handling) and add unit tests for these transformations.
  • Add/adjust tests for new utilities (LU solve helper) and update convergence/robustness checks.

Reviewed changes

Copilot reviewed 14 out of 14 changed files in this pull request and generated 6 comments.

Show a summary per file
FileDescription
pytential/symbolic/elasticity.pyNew elasticity wrapper framework (naive/Laplace/biharmonic) shared with Stokes.
pytential/symbolic/stokes.pyMajor refactor of Stokes wrappers/operators to use the new wrapper framework and support method dispatch.
pytential/symbolic/pde/system_utils.pyNew machinery for rewriting IntG expressions using a chosen base kernel and derivative relations.
pytential/utils.pyAdds symbolic utilities (chop, forward/back substitution, LU solve helper).
pytential/symbolic/mappers.pyExtends flattening behavior to rewrite IntG densities/kernel args when flattening.
pytential/symbolic/primitives.pyAdjusts Kernel imports/usage to avoid import-time issues and keep ambient_dim inference working.
pytential/qbx/__init__.pyRelaxes density type check to allow scalar densities (but current implementation has a runtime issue).
test/test_tools.pyAdds a unit test for solve_from_lu.
test/test_stokes.pyExpands Stokes tests to cover multiple methods/nu values and adds PDE-based verification tests.
test/test_pde_system_utils.pyNew tests for target->source transformation and base-kernel rewriting utilities.
test/test_linalg_skeletonization.pyMakes a zero-comparison more robust via tolerance.
doc/symbolic.rstDocuments new elasticity module and system-utils rewriting utilities.
doc/conf.pyAdds Sphinx intersphinx mapping for ExpressionKernel.
pyproject.tomlAdds mis to typos dictionary.

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py Outdated
Comment threadpytential/symbolic/stokes.py
Comment threadpytential/qbx/__init__.py Outdated
Comment threadpytential/utils.py
Comment on lines +594 to +601
try:
L, U, perm = sym_mat.LUdecomposition()
except RewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed = True

if not sp.USE_SYMENGINE and all(expr == 0 for expr in U[-1, :]):

CopilotAIFeb 19, 2026

Copy link

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The LUdecomposition() call is wrapped in except RewriteFailedError, but LUdecomposition will not raise RewriteFailedError here (and rank-deficient errors from symengine/sympy are different exception types). As written, rank-deficiency will escape the retry logic and crash. Catch the actual exceptions raised by LUdecomposition (or a broader exception type) and mark failed=True so the retry path is exercised.

Suggested change
try:
L, U, perm=sym_mat.LUdecomposition()
exceptRewriteFailedError:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
ifnotsp.USE_SYMENGINEandall(expr==0forexprinU[-1, :]):
L=U=perm=None
try:
L, U, perm=sym_mat.LUdecomposition()
exceptException:
# symengine throws an error when rank deficient
# and sympy returns U with last row zero
failed=True
if (notfailed
andnotsp.USE_SYMENGINE
andall(expr==0forexprinU[-1, :])):

Copilot uses AI. Check for mistakes.

Copy link
Copy Markdown
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This seems fair. The logic in _get_base_kernel_matrix_lu_factorization seems incomplete, but I'm not quite sure what to do there..

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 51787b9 to e4bc444CompareFebruary 21, 2026 19:05
@alexfikl

alexfikl commented Feb 21, 2026

Copy link
Copy Markdown
Collaborator

Spent a bit more time debugging those errors, mainly in test_elasticity_pde. For future reference:

  • pytest.param(3, "Laplace", 0.5, False) is failing, but pytest.param(3, "Laplace", 0.5, True) is passing just fine (first uses the Stokeslet/single-layer and the second uses the Stresslet/double-layer).
  • All the logic for these two cases is in StressletWrapperTornberg.apply_single_and_double_layer and it does not use anything from system_utils.
  • The "pytential" and CalculusPatch versions agree, so all the derivatives are taken correctly.
  • I couldn't fine any differences in stokes.py from some older version (that I think worked just fine): https://github.com/inducer/pytential/blob/88cb6ca94d610612518bd577ed0f1e736223bea4/pytential/symbolic/stokes.py.
  • The test checks both $\Delta u - p$ and $\nabla \cdot u$. The first one is zero order, but the divergence is "converging" to first order, so likely something wrong in the velocity part (?). Also the $x$ component seems to converge to second-order-ish when setting $\mu = 3$..

EDIT:

  • pytest.param(3, "Naive", 0.5, False, marks=pytest.mark.slowtest) seems to be failing pretty much the same as the Laplace version with $\mu = 3$.

@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 2 times, most recently from 193c1c7 to ffedab7CompareFebruary 22, 2026 13:51
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 5 times, most recently from 820ebf0 to 3b22ec6CompareMarch 16, 2026 15:29
@alexfikl
alexfikl requested a review from CopilotMarch 16, 2026 17:22

CopilotAI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

Copilot reviewed 13 out of 13 changed files in this pull request and generated 2 comments.


💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment threadpytential/utils.py Outdated
Comment threadtest/test_stokes.py Outdated
@alexfikl
alexfiklforce-pushed the stokes_biharmonic2 branch 3 times, most recently from 03f9e12 to 947e841CompareMarch 16, 2026 18:16
@alexfikl

Copy link
Copy Markdown
Collaborator

@inducer This should be passing now (at least it passed once) and is otherwise in a pretty good state. 😁

@alexfiklalexfikl mentioned this pull request May 8, 2026
4 tasks
isurufand others added 2 commits May 8, 2026 10:14
Sign up for freeto join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

4 participants

@isuruf@alexfikl@inducer