)]}'
{
  "commit": "389431bba6f9a4b46b6cf15dd9cd24a1f52f6e16",
  "tree": "01361600b1d97cd8ec14a38f44d10351feb7081b",
  "parents": [
    "5a8f6c4acd4190421e58f5ecc6f099f1ce406cb8"
  ],
  "author": {
    "name": "Richard Levasseur",
    "email": "rlevasseur@google.com",
    "time": "Thu Mar 13 16:25:06 2025 -0700"
  },
  "committer": {
    "name": "GitHub",
    "email": "noreply@github.com",
    "time": "Thu Mar 13 23:25:06 2025 +0000"
  },
  "message": "refactor: API for deriving customized versions of the base rules (#2610)\n\nThis implements a \"builder style\" API to allow arbitrary modification of\nrule, attr, etc\nobjects used when defining a rule. The net effect is users are able to\nuse the base\ndefinition for our rules, but define their own with the modifications\nthey need, without\nhaving to copy/paste portions our implementation, load private files, or\npatch source.\n\nThe basic way it works is a mutable object (\"builder\") holds the args\nand state that would\nbe used to create the immutable Bazel object. When `build()` is called,\nthe immutable\nBazel object (e.g. `attr.string()`) is created. Builders are implemented\nfor most objects\nand their settings (rule, attrs, and supporting objects).\n\nThis design is necessary because of three Bazel behaviors:\n* attr etc objects are immutable, which means we must keep our own state\n* attr etc objects aren\u0027t inspectable, which means we must store the\narguments for\n  creating the immutable objects.\n* Starlark objects are frozen after initial bzl file evaluation, which\nmeans creation\n  of any mutable object must be done at the point of use.\n\nThe resulting API resembles the builder APIs common in other languages:\n\n```\nr \u003d create_py_binary_rule_builder()\nr.attrs.get(\"srcs\").set_mandatory(True)\nr.attrs.get(\"deps\").aspects().append(my_aspect)\nmy_py_binary \u003d r.build()\n```\n\nMost objects are thin wrappers for managing a kwargs dict. As such, and\nbecause they\u0027re\nwrapping a foreign API, they aren\u0027t strict in enforcing their internal\nstate and the\nkwargs dict is publicly exposed as an escape hatch.\n\nAs of this PR, no public API for e.g. `create_py_binary_rule_builder()`\nis exposed. That\u0027ll come in a separate PR (to add public access points\nunder python/api).\n\nWork towards https://github.com/bazelbuild/rules_python/issues/1647",
  "tree_diff": [
    {
      "type": "modify",
      "old_id": "0c07002a012aefee17f4195aa7db31b69d6b4d4f",
      "old_mode": 33188,
      "old_path": "docs/BUILD.bazel",
      "new_id": "e19c22113f3495c2ceb980ff5f212c1e414fc1cd",
      "new_mode": 33188,
      "new_path": "docs/BUILD.bazel"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "0241947b430a0dd56eb4c5e7d39556d362c24a55",
      "new_mode": 33188,
      "new_path": "docs/_includes/field_kwargs_doc.md"
    },
    {
      "type": "modify",
      "old_id": "2928dab0683b55ab4c00509a32404e2a79565f1c",
      "old_mode": 33188,
      "old_path": "python/private/BUILD.bazel",
      "new_id": "b7e52a35aad74fcd7bf74b673ca78547a0b63c5f",
      "new_mode": 33188,
      "new_path": "python/private/BUILD.bazel"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "acd1d4039481eb372b8a142d45bf2764ef54dfc3",
      "new_mode": 33188,
      "new_path": "python/private/attr_builders.bzl"
    },
    {
      "type": "modify",
      "old_id": "e167482eb10634a23a5b5eb84a0764519bbfe8b3",
      "old_mode": 33188,
      "old_path": "python/private/attributes.bzl",
      "new_id": "b57e2754069d64655d8bd3f55b15fb5b0135b034",
      "new_mode": 33188,
      "new_path": "python/private/attributes.bzl"
    },
    {
      "type": "modify",
      "old_id": "bf5dbb8667e735e246982a82bd3cdcc747394b7f",
      "old_mode": 33188,
      "old_path": "python/private/builders.bzl",
      "new_id": "50aa3ed91aff1126ec7fdded5db0a110a5d269e2",
      "new_mode": 33188,
      "new_path": "python/private/builders.bzl"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "139084f79a603990a4590d8bb30cb34c6f102405",
      "new_mode": 33188,
      "new_path": "python/private/builders_util.bzl"
    },
    {
      "type": "modify",
      "old_id": "137f0d23f306c7b63275a3839b7a25cfd533fe58",
      "old_mode": 33188,
      "old_path": "python/private/common.bzl",
      "new_id": "48e2653ebbf97cd181f89f1aebfbb60169414986",
      "new_mode": 33188,
      "new_path": "python/private/common.bzl"
    },
    {
      "type": "modify",
      "old_id": "5b40f52198be35a40e4b3a535182d3b821883c9e",
      "old_mode": 33188,
      "old_path": "python/private/py_binary_rule.bzl",
      "new_id": "0e1912cf0c80128ae0b463accb50eed149850a60",
      "new_mode": 33188,
      "new_path": "python/private/py_binary_rule.bzl"
    },
    {
      "type": "modify",
      "old_id": "a2ccdc65f3dfa2c58ad606c75edfefa584fa9452",
      "old_mode": 33188,
      "old_path": "python/private/py_executable.bzl",
      "new_id": "f85f242bbaba932287a4a3ea552e1c167efbf3d9",
      "new_mode": 33188,
      "new_path": "python/private/py_executable.bzl"
    },
    {
      "type": "modify",
      "old_id": "350ea35aa6ba3e70aae49c46a6bbbcb43ee9160c",
      "old_mode": 33188,
      "old_path": "python/private/py_library.bzl",
      "new_id": "a774104dd2331cd31546f27a22360810d816850c",
      "new_mode": 33188,
      "new_path": "python/private/py_library.bzl"
    },
    {
      "type": "modify",
      "old_id": "8a8d6cf3803788a6c10b61445f908394f85821b1",
      "old_mode": 33188,
      "old_path": "python/private/py_library_rule.bzl",
      "new_id": "44382a76d6b4a6dfa1b9b42d8f2b78d530878143",
      "new_mode": 33188,
      "new_path": "python/private/py_library_rule.bzl"
    },
    {
      "type": "modify",
      "old_id": "5ce8161cf0653c59adae9d714cfaa3f54548a00a",
      "old_mode": 33188,
      "old_path": "python/private/py_runtime_rule.bzl",
      "new_id": "9407cac50ff1ae9e20eab892048d2a9b3862b9c8",
      "new_mode": 33188,
      "new_path": "python/private/py_runtime_rule.bzl"
    },
    {
      "type": "modify",
      "old_id": "6ad4fbddb815917b7edd01ae8a9888fc3a13a49a",
      "old_mode": 33188,
      "old_path": "python/private/py_test_rule.bzl",
      "new_id": "72e8bab805e6c1d58120ea166de83fd7ac121a76",
      "new_mode": 33188,
      "new_path": "python/private/py_test_rule.bzl"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "6d9fb3f964e30b40ba64985565a93be0250cbd3e",
      "new_mode": 33188,
      "new_path": "python/private/rule_builders.bzl"
    },
    {
      "type": "modify",
      "old_id": "969c77238603df59959d44167e0c9edde11dacaa",
      "old_mode": 33188,
      "old_path": "sphinxdocs/inventories/bazel_inventory.txt",
      "new_id": "dc11f02b5bcc2250e6ec9c1a602ba3b7481511bf",
      "new_mode": 33188,
      "new_path": "sphinxdocs/inventories/bazel_inventory.txt"
    },
    {
      "type": "modify",
      "old_id": "3ad0c3e80c46fd153d5f8d5d06eba86d7408cd0a",
      "old_mode": 33188,
      "old_path": "tests/builders/BUILD.bazel",
      "new_id": "f963cb0131ee8c49d3bf4c554d5a5609764c72d7",
      "new_mode": 33188,
      "new_path": "tests/builders/BUILD.bazel"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "58557cd6334a9f88c2fc3aa89629c7319c2b08e9",
      "new_mode": 33188,
      "new_path": "tests/builders/attr_builders_tests.bzl"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "9a91ceb062f7346784ab77bde3fe77aac060eb76",
      "new_mode": 33188,
      "new_path": "tests/builders/rule_builders_tests.bzl"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "cab5f800eca9733e23c3686da62df08333fb28fe",
      "new_mode": 33188,
      "new_path": "tests/support/empty_toolchain/BUILD.bazel"
    },
    {
      "type": "add",
      "old_id": "0000000000000000000000000000000000000000",
      "old_mode": 0,
      "old_path": "/dev/null",
      "new_id": "e2839283c71b44c7b4aa85394f7923f402926d7b",
      "new_mode": 33188,
      "new_path": "tests/support/empty_toolchain/empty.bzl"
    },
    {
      "type": "modify",
      "old_id": "d116f0403fd1c2b1e9f2b7ccab53af0f6ca67aa9",
      "old_mode": 33188,
      "old_path": "tests/support/sh_py_run_test.bzl",
      "new_id": "d1e3b8e9c8d64d33d1ae29878caa48124dda45d4",
      "new_mode": 33188,
      "new_path": "tests/support/sh_py_run_test.bzl"
    }
  ]
}
