Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Fix unexpected error when a recipe performs package_id erasure and is used as a compatibility candidate #16575

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

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
6 changes: 5 additions & 1 deletion conans/client/graph/graph_binaries.py
Original file line number Diff line number Diff line change
Expand Up @@ -134,9 +134,13 @@ def _compatible_found(pkg_id, compatible_pkg):
f"compatible package '{pkg_id}': {diff}")
# So they are available in package_info() method
conanfile.info = compatible_pkg # Redefine current

# TODO: Improve this interface
# The package_id method might have modified the settings to erase information,
# ensure we allow those new values
conanfile.settings = conanfile.settings.copy_conaninfo_settings()
conanfile.settings.update_values(compatible_pkg.settings.values_list)
# Trick to allow mutating the options (they were freeze=True)
# TODO: Improve this interface
conanfile.options = conanfile.options.copy_conaninfo_options()
conanfile.options.update_options(compatible_pkg.options)

Expand Down
4 changes: 2 additions & 2 deletions conans/model/settings.py
Original file line number Diff line number Diff line change
Expand Up @@ -61,9 +61,9 @@ def copy_conaninfo_settings(self):
""" deepcopy, recursive
This function adds "ANY" to lists, to allow the ``package_id()`` method to modify some of
values, but not all, just the "final" values without subsettings.
We cannot let usres manipulate to random strings
We cannot let users manipulate to random strings
things that contain subsettings like ``compiler``, because that would leave the thing
in a undefined state, with some now inconsistent subsettings, that cannot be accessed
in an undefined state, with some now inconsistent subsettings, that cannot be accessed
anymore. So with this change the options are:
- If you need more "binary-compatible" descriptions of a compiler, lets say like
"gcc_or_clang", then you need to add that string to settings.yml. And add the subsettings
Expand Down
31 changes: 31 additions & 0 deletions test/integration/package_id/compatible_test.py
Original file line number Diff line number Diff line change
Expand Up @@ -401,6 +401,37 @@ def package_id(self):
c.run("install --requires=pdfium/2020.9 -pr=myprofile -s build_type=Debug")
assert "missing. Using compatible package" in c.out

def test_compatibility_erase_package_id(self):
c = TestClient()
conanfile = textwrap.dedent("""
from conan import ConanFile

class PdfiumConan(ConanFile):
name = "diligent-core"
version = "1.0"
settings = "compiler"
options = {"foo": ["no"]}

def package_id(self):
self.info.settings.compiler.runtime = "foobar"
AbrilRBS marked this conversation as resolved.
Show resolved Hide resolved
self.info.options.foo = "yes"
""")
profile = textwrap.dedent("""
[settings]
os = Windows
compiler=msvc
compiler.version=192
compiler.runtime=dynamic
build_type=Release
arch=x86_64
""")
c.save({"conanfile.py": conanfile,
"myprofile": profile})

c.run("create . -pr:a=myprofile -s compiler.cppstd=20")
c.run("install --requires=diligent-core/1.0 -pr:a=myprofile -s compiler.cppstd=17")
assert "ERROR: Invalid setting 'foobar' is not a valid 'settings.compiler.runtime' value." not in c.out

def test_compatibility_msvc_and_cppstd(self):
"""msvc 194 would not find compatible packages built with same version but different cppstd
due to an issue in the msvc fallback compatibility rule."""
Expand Down