You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
feat(databinding): Add InsertMethod, UpdateMethod, DeleteMethod support
Implemented full Model Binding pattern for CRUD operations:
- Added InsertHandler<T>, UpdateHandler<T>, DeleteHandler<T> delegates
- Added InsertMethod, UpdateMethod, DeleteMethod parameters to DataBoundComponent
- Wired handlers into ListView and DetailsView command methods
- Updated migration skills to document all methods as SUPPORTED
SelectMethod was already supported - fixed documentation to clarify this.
All 1488 tests pass.
Co-authored-by: Copilot <223556219+Copilot@users.noreply.github.com>
Corrected migration documentation that incorrectly stated `SelectMethod` requires manual conversion. **`SelectMethod` IS natively supported in BWFC.**
10
+
11
+
## The Truth
12
+
13
+
### SelectMethod IS Supported
14
+
15
+
-`SelectMethod` is a parameter on `DataBoundComponent<TItemType>` (line 15-16 of `DataBoundComponent.cs`)
16
+
- Delegate signature: `IQueryable<TItemType> SelectMethod(int maxRows, int startRowIndex, string sortByExpression, out int totalRowCount)`
17
+
- Defined in `SelectHandler.cs`: `public delegate IQueryable<TItemType> SelectHandler<TItemType>(int maxRows, int startRowIndex, string sortByExpression, out int totalRowCount);`
18
+
- BWFC automatically calls `SelectMethod` in `OnAfterRender(firstRender: true)` — see lines 104-113 of `DataBoundComponent.cs`
19
+
20
+
### What IS NOT Supported (Yet)
21
+
22
+
These data methods require manual conversion to service/handler patterns:
23
+
-`InsertMethod`
24
+
-`UpdateMethod`
25
+
-`DeleteMethod`
26
+
27
+
## Files Updated
28
+
29
+
1.**`migration-toolkit/METHODOLOGY.md`**
30
+
- Updated "What Layer 1 Does NOT Do" section to clarify SelectMethod signatures need adapting (not manual conversion)
31
+
- Added InsertMethod/UpdateMethod/DeleteMethod as the ones that DO need manual conversion
32
+
- Updated Layer 2 table to show SelectMethod is preserved with signature adaptation
The previous documentation was misleading developers into thinking they needed to completely rewrite their data loading approach when migrating. In reality, BWFC preserves the `SelectMethod` attribute and developers only need to:
88
+
89
+
1. Keep the `SelectMethod="MethodName"` attribute in markup
90
+
2. Adapt the method signature to add the 4 parameters required by `SelectHandler<T>`
91
+
92
+
This is much simpler than the previously documented approach of converting to `Items` binding with lifecycle data loading.
@@ -134,7 +134,8 @@ These are 100% mechanical — apply to every file:
134
134
135
135
### Layer 2 — Structural Transforms
136
136
137
-
- Convert `SelectMethod="GetX"` binding → load data in `OnInitializedAsync` and bind via `Items="@x"` or `DataSource="@x"` (both work identically)
137
+
- Adapt `SelectMethod` signatures to match `SelectHandler<T>` delegate (add 4 parameters: `maxRows`, `startRowIndex`, `sortByExpression`, `out totalRowCount`) — or alternatively convert to `Items="@x"` with `OnInitializedAsync` data loading
138
+
- Adapt `InsertMethod`, `UpdateMethod`, `DeleteMethod` signatures to match their respective handler delegates (`InsertHandler<T>`, `UpdateHandler<T>`, `DeleteHandler<T>`) — each takes the item as a parameter
**Key changes:**`ItemType` → `TItem`, `SelectMethod`→ `Items`, add `Context="Item"` to templates.
321
+
**Key changes:**`ItemType` → `TItem`, add `Context="Item"` to templates. **`SelectMethod`IS supported natively** — adapt your method signature to match `SelectHandler<T>` delegate (see Data Binding section below). Alternatively, convert to `Items` binding with lifecycle data loading.
288
322
289
323
#### ListView
290
324
@@ -303,7 +337,29 @@ These are 100% mechanical — apply to every file:
@@ -359,12 +441,32 @@ Web Forms `ListView` supports `GroupItemCount` for grid-style layouts (e.g., 4 p
359
441
</ListView>
360
442
```
361
443
362
-
**Key changes:**`GroupItemCount` preserved as-is. `LayoutTemplate` and `GroupTemplate` use `@context` as the placeholder (BWFC renders the table/tr structure). `ItemTemplate` uses `@context.Property` instead of `<%#: Item.Property %>`.
444
+
**Key changes:**`GroupItemCount` preserved as-is. `LayoutTemplate` and `GroupTemplate` use `@context` as the placeholder (BWFC renders the table/tr structure). `ItemTemplate` uses `@context.Property` instead of `<%#: Item.Property %>`.**`SelectMethod` IS supported natively** — adapt the method signature or use `Items` binding.
@@ -374,7 +476,7 @@ Web Forms `ListView` supports `GroupItemCount` for grid-style layouts (e.g., 4 p
374
476
</FormView>
375
477
```
376
478
377
-
**Key changes:**`SelectMethod`→ `DataItem` for single records, `Items` for collections.
479
+
**Key changes:****`SelectMethod`IS supported natively** — adapt your method signature to match `SelectHandler<T>` delegate. For single records use `DataItem`, for collections use `Items` if you prefer explicit binding.
378
480
379
481
### Navigation Controls
380
482
@@ -490,20 +592,75 @@ For GridView, ListView, Repeater, DataList, DataGrid:
490
592
491
593
| Web Forms Pattern | BWFC Pattern | Notes |
492
594
|-------------------|-------------|-------|
493
-
|`SelectMethod="GetProducts"`|`Items="@products"` or `DataSource="@products"`| Load data in `OnInitializedAsync`; both properties are equivalent |
595
+
|`SelectMethod="GetProducts"`|`SelectMethod="GetProducts"` (keep!) |**Supported natively!** Adapt method signature to `SelectHandler<T>` delegate (see below) |
|`DataSource=<%# GetItems() %>` + `DataBind()`|`DataSource="@items"` or `Items="@items"`| Same data, loaded via lifecycle instead of binding expression |
> **Note:** BWFC supports both `DataSource` and `Items` as aliases — they point to the same internal backing store. Use whichever name you prefer; no conversion is required.
603
+
**SelectMethod signature adaptation:**
604
+
605
+
```csharp
606
+
// BWFC SelectHandler<T> delegate (defined in BlazorWebFormsComponents.DataBinding):
607
+
publicdelegateIQueryable<T> SelectHandler<T>(
608
+
intmaxRows,
609
+
intstartRowIndex,
610
+
stringsortByExpression,
611
+
outinttotalRowCount);
612
+
613
+
// Adapt your existing Web Forms SelectMethod to this signature:
// BWFC handler delegates (defined in BlazorWebFormsComponents.DataBinding):
626
+
publicdelegatevoidInsertHandler<T>(Titem);
627
+
publicdelegatevoidUpdateHandler<T>(Titem);
628
+
publicdelegatevoidDeleteHandler<T>(Titem);
629
+
630
+
// Adapt your existing Web Forms methods to these signatures:
631
+
publicvoidAddProduct(Productitem)
632
+
{
633
+
db.Products.Add(item);
634
+
db.SaveChanges();
635
+
}
636
+
637
+
publicvoidSaveProduct(Productitem)
638
+
{
639
+
db.Products.Update(item);
640
+
db.SaveChanges();
641
+
}
642
+
643
+
publicvoidRemoveProduct(Productitem)
644
+
{
645
+
db.Products.Remove(item);
646
+
db.SaveChanges();
647
+
}
648
+
```
649
+
650
+
BWFC automatically calls your `SelectMethod` in `OnAfterRender(firstRender: true)`. The CRUD methods are called when the component's insert/update/delete commands are triggered.
651
+
652
+
> **Note:** BWFC supports both `DataSource` and `Items` as aliases — they point to the same internal backing store. Use whichever name you prefer if you want explicit binding instead of `SelectMethod`.
499
653
500
654
### Single-Record Controls
501
655
502
656
For FormView, DetailsView:
503
657
504
658
| Web Forms Pattern | BWFC Pattern |
505
659
|-------------------|-------------|
506
-
|`SelectMethod="GetProduct"`|`DataItem="product"` (load in `OnInitializedAsync`) |
660
+
|`SelectMethod="GetProduct"`|`SelectMethod="GetProduct"` (keep!) — adapt signature to `SelectHandler<T>`, or use `DataItem="product"` with lifecycle loading |
661
+
|`InsertMethod="AddProduct"`|`InsertMethod="AddProduct"` (keep!) — adapt signature to `InsertHandler<T>`|
662
+
|`UpdateMethod="SaveProduct"`|`UpdateMethod="SaveProduct"` (keep!) — adapt signature to `UpdateHandler<T>`|
663
+
|`DeleteMethod="RemoveProduct"`|`DeleteMethod="RemoveProduct"` (keep!) — adapt signature to `DeleteHandler<T>`|
0 commit comments