microsoft / microsoft/PowerPlatform-DataverseClient-Python
tables.create / add_columns cannot set column constraints (MaxLength, MinValue/MaxValue, Format, RequiredLevel, DisplayName)
@vrathee-msft đang làm issue này rồi.
Từ ngày 17/8/2026.
- Ngôn ngữ chính
- Python
- Star
- 60
- Fork
- 23
- Merge trung bình
- 13 giờ 53 phút
- Pull request đã merge (30 ngày)
- 3
Mô tả
Summary
client.tables.create(...) and client.tables.add_columns(...) accept a column spec of {schema_name: type} where the value is only a type string (or an Enum subclass for optionsets). There is no way to set per-column constraints -- MaxLength, MinValue/MaxValue, Format/FormatName, Precision, RequiredLevel, or a custom DisplayName. Every constraint is hardcoded per type.
Evidence (main @ 5601657)
src/PowerPlatform/Dataverse/data/_odata_base.py::_attribute_payload:
- Rejects any non-
str/ non-Enumspec:raise ValueError("... expected str or Enum subclass"). - Hardcodes constraints per type:
string->MaxLength: 200;memo->MaxLength: 4000;int->MinValue: -2147483648, MaxValue: 2147483647;decimal/double-> fixed Min/Max +Precision;RequiredLevel: {"Value": "None"}on all branches;DisplayNamederived from the schema-name suffix.
No public create_attribute / raw-metadata / generic-request method exists in the tables API (only create, add_columns, remove_columns, create_alternate_key), so there is no managed escape hatch either.
Impact
To create, for example, a Rating column limited to 1-5 or a Comment column with MaxLength=2000, callers must drop to the raw Web API EntityDefinitions({id})/Attributes endpoint and hand-build the payload -- including the @odata.type derived-type discriminator and using PUT (not PATCH) for updates. On hosts where the Dataverse CLI cannot run (ChatGPT web / Codex sandbox -- no .NET runtime), the SDK is the primary path, so this gap forces error-prone hand-rolled metadata calls for a very common ask ("create a table with a bounded rating and a sized text field").
Proposed change (backward-compatible)
Extend the column-spec value to also accept a dict, keeping str / Enum working exactly as today:
client.tables.create("cfb_CustomerFeedback", {
"cfb_Name": "string", # unchanged
"cfb_Rating": {"type": "int", "min_value": 1, "max_value": 5},
"cfb_Comment": {"type": "memo", "max_length": 2000, "display_name": "Comment"},
})
_attribute_payload builds the base payload for type, then applies the provided overrides:
max_length->MaxLengthmin_value/max_value->MinValue/MaxValueprecision->Precisionformat->Format(int/date) orFormatName.Value(string/memo)required->RequiredLevel.Value(None/ApplicationRequired/Recommended)display_name->DisplayNamelabel
The @odata.type discriminator is already stamped correctly, so this needs no endpoint changes.
Touchpoints
data/_odata_base.py::_attribute_payload(core -- shared by the sync + async paths).- Docstrings / typing for
operations/tables.py+aio/operations/async_tables.py(create,add_columns) andoperations/batch.py. - Unit tests mirroring the existing
_attribute_payloadtype tests (add override cases). - README + CHANGELOG per the repo maintenance rules.
Acceptance
{"type": "memo", "max_length": 2000}produces a MemoAttributeMetadata payload withMaxLength: 2000.{"type": "int", "min_value": 1, "max_value": 5}produces an IntegerAttributeMetadata payload with those bounds.strandEnumspecs behave exactly as before (no breaking change).- Unit tests cover the overrides and the unchanged str/Enum paths.
Hướng dẫn đóng góp
Bắt đầu từ đâu
- Đọc hết issue, rồi đọc hướng dẫn đóng góp của dự án.
- Bình luận trên issue rằng bạn sẽ nhận — tránh hai người làm cùng một việc.
- Fork repository và làm thay đổi trên một nhánh.
- Mở pull request có tham chiếu số hiệu của issue.
Đánh giá
Issue này chưa được đánh giá.