feat(Table): add SearchFormLocalizerOptions parameter#7769
Conversation
Reviewer's GuideAdds configurable, localized search-form text for Table search items and refines when advanced search is enabled, by introducing SearchFormLocalizerOptions, wiring it into Table search metadata generation, and updating localization wiring and samples. Sequence diagram for localized SearchFormItems generationsequenceDiagram
actor User
participant Page as RazorPage
participant Table as Table_TItem
participant Localizer as IStringLocalizer_SearchFormLocalizerOptions
participant Cols as ITableColumnCollection
participant Ext as IEditItemExtensions
User->>Page: Request page with Table
Page->>Table: Render Table
Table->>Table: Access SearchFormItems
alt SearchFormLocalizerOptions is null
Table->>Localizer: Get SelectAllText
Localizer-->>Table: localized SelectAllText
Table->>Localizer: Get BooleanAllText
Localizer-->>Table: localized BooleanAllText
Table->>Localizer: Get BooleanTrueText
Localizer-->>Table: localized BooleanTrueText
Table->>Localizer: Get BooleanFalseText
Localizer-->>Table: localized BooleanFalseText
Table->>Localizer: Get NumberStartValueLabelText
Localizer-->>Table: localized NumberStartValueLabelText
Table->>Localizer: Get NumberEndValueLabelText
Localizer-->>Table: localized NumberEndValueLabelText
Table->>Table: Create SearchFormLocalizerOptions instance
end
alt SearchItems provided
Table->>Table: Use SearchItems
else SearchItems not provided
Table->>Table: GetSearchColumns()
Table-->>Cols: request columns
Cols-->>Table: ITableColumn list
loop for each ITableColumn
Table->>Ext: ParseSearchItem(column, SearchFormLocalizerOptions)
Ext->>Ext: BuildSearchMetaData(column, SearchFormLocalizerOptions)
Ext-->>Table: ISearchItem with localized MetaData
end
end
Table-->>Page: Localized SearchFormItems
Page-->>User: Rendered search form with localized texts
Class diagram for SearchFormLocalizerOptions integration into Table searchclassDiagram
direction LR
class Table_TItem {
+bool ShowSearchButton
+bool ShowAdvancedSearch
+SearchMode SearchMode
+IEnumerable~ISearchItem~ SearchItems
+SearchFormLocalizerOptions~nullable~ SearchFormLocalizerOptions
+IEnumerable~ISearchItem~ SearchFormItems
+List~IFilterAction~ GetAdvanceSearches()
+IEnumerable~ITableColumn~ GetSearchColumns()
}
class SearchFormLocalizerOptions {
+string SelectAllText
+string BooleanAllText
+string BooleanTrueText
+string BooleanFalseText
+string NumberStartValueLabelText
+string NumberEndValueLabelText
}
class IStringLocalizer_SearchFormLocalizerOptions {
+string this[string name]
}
class ITableColumn {
+string GetFieldName()
+Type PropertyType
+Type GetRealType()
+string GetDisplayName()
+string GroupName
+int GroupOrder
+int Order
+ISearchFormItemMetaData SearchFormItemMetaData
}
class IEditItemExtensions {
+static ISearchItem ParseSearchItem(ITableColumn column, SearchFormLocalizerOptions options)
-static ISearchFormItemMetaData BuildSearchMetaData(ITableColumn column, SearchFormLocalizerOptions options)
}
class ISearchItem {
}
class SearchItem {
+SearchItem(string fieldName, Type propertyType, string displayName)
+string FieldName
+Type PropertyType
+string DisplayName
+string GroupName
+int GroupOrder
+int Order
+ISearchFormItemMetaData MetaData
}
class ISearchFormItemMetaData {
}
class SelectSearchMetaData {
+IEnumerable~SelectedItem~ Items
}
class NumberSearchMetaData {
+string StartValueLabelText
+string EndValueLabelText
+Type ValueType
}
class DateTimeRangeSearchMetaData {
}
class SelectedItem {
+string Value
+string Text
}
class IFilterAction {
}
class SearchMode {
<<enumeration>>
Top
Popup
None
}
Table_TItem --> IStringLocalizer_SearchFormLocalizerOptions : uses
Table_TItem --> SearchFormLocalizerOptions : has
Table_TItem --> ISearchItem : produces
Table_TItem --> ITableColumn : reads
IEditItemExtensions ..> ITableColumn : extends
IEditItemExtensions ..> SearchFormLocalizerOptions : uses
IEditItemExtensions --> ISearchFormItemMetaData : builds
SearchItem ..|> ISearchItem
SearchItem --> ISearchFormItemMetaData : has
SelectSearchMetaData ..|> ISearchFormItemMetaData
NumberSearchMetaData ..|> ISearchFormItemMetaData
DateTimeRangeSearchMetaData ..|> ISearchFormItemMetaData
SelectSearchMetaData --> SelectedItem : contains
Table_TItem --> IFilterAction : returns
Table_TItem --> SearchMode : configures advanced search
Flow diagram for when advanced search is enabledflowchart LR
A[Start] --> B[Check ShowAdvancedSearch]
B -->|false| Z[Advanced search disabled]
B -->|true| C[Check SearchMode]
C -->|not Popup| Z
C -->|Popup| D[Check CustomerSearchModel is null]
D -->|false| Z
D -->|true| E[Create default advanced search filters]
E --> F[Return List of IFilterAction]
F --> G[Advanced search popup available]
Z --> H[End]
G --> H
File-Level Changes
Assessment against linked issues
Possibly linked issues
Tips and commandsInteracting with Sourcery
Customizing Your ExperienceAccess your dashboard to:
Getting Help
|
There was a problem hiding this comment.
Hey - I've found 1 issue, and left some high level feedback:
- The
SearchFormItemsgetter now mutates theSearchFormLocalizerOptionsparameter and uses it as lazy initialization; consider moving this initialization intoOnInitParameters(where you already left a TODO-style comment) or another lifecycle method to avoid side effects in a property getter. - Changing
ITableColumnExtensions.ParseSearchItemandBuildSearchMetaDatato always require aSearchFormLocalizerOptionsargument is a breaking signature change; if possible, add an overload that preserves the previous parameter-less usage and routes to the new overload with default options.
Prompt for AI Agents
Please address the comments from this code review:
## Overall Comments
- The `SearchFormItems` getter now mutates the `SearchFormLocalizerOptions` parameter and uses it as lazy initialization; consider moving this initialization into `OnInitParameters` (where you already left a TODO-style comment) or another lifecycle method to avoid side effects in a property getter.
- Changing `ITableColumnExtensions.ParseSearchItem` and `BuildSearchMetaData` to always require a `SearchFormLocalizerOptions` argument is a breaking signature change; if possible, add an overload that preserves the previous parameter-less usage and routes to the new overload with default options.
## Individual Comments
### Comment 1
<location path="src/BootstrapBlazor/Components/Table/Table.razor.Search.cs" line_range="173" />
<code_context>
{
- // TODO: 增加多语言支持
- _searchItems ??= SearchItems ?? GetSearchColumns().Select(i => i.ParseSearchItem()).ToList();
+ if (SearchFormLocalizerOptions is null)
+ {
+ SearchFormLocalizerOptions = new SearchFormLocalizerOptions()
</code_context>
<issue_to_address>
**issue (complexity):** Consider refactoring the search form localization logic to separate parameter handling, default resolution, and caching, and to move initialization outside the property getter.
You can simplify this by separating:
* parameter input (`SearchFormLocalizerOptions?`)
* resolved, non-null options used internally
* search item caching
and by moving initialization out of the getter.
### 1. Keep `[Parameter]` but introduce a non-nullable backing field
```csharp
[Parameter]
public SearchFormLocalizerOptions? SearchFormLocalizerOptions { get; set; }
private SearchFormLocalizerOptions _effectiveSearchFormLocalizerOptions;
```
### 2. Initialize the effective options once (e.g. in `OnParametersSet`)
This avoids mutating the `[Parameter]` in the getter and removes the nullable+`.Value` complexity:
```csharp
protected override void OnParametersSet()
{
_effectiveSearchFormLocalizerOptions = SearchFormLocalizerOptions ?? new SearchFormLocalizerOptions
{
SelectAllText = SearchFormLocalizer[nameof(Components.SearchFormLocalizerOptions.SelectAllText)],
BooleanAllText = SearchFormLocalizer[nameof(Components.SearchFormLocalizerOptions.BooleanAllText)],
BooleanTrueText = SearchFormLocalizer[nameof(Components.SearchFormLocalizerOptions.BooleanTrueText)],
BooleanFalseText = SearchFormLocalizer[nameof(Components.SearchFormLocalizerOptions.BooleanFalseText)],
NumberStartValueLabelText = SearchFormLocalizer[nameof(Components.SearchFormLocalizerOptions.NumberStartValueLabelText)],
NumberEndValueLabelText = SearchFormLocalizer[nameof(Components.SearchFormLocalizerOptions.NumberEndValueLabelText)]
};
// If options influence search items, invalidate cache when they change
_searchItems = null;
base.OnParametersSet();
}
```
### 3. Make `SearchFormItems` only handle caching/building
No side effects, no nullable `.Value`:
```csharp
private IEnumerable<ISearchItem> SearchFormItems
{
get
{
_searchItems ??= SearchItems
?? GetSearchColumns()
.Select(i => i.ParseSearchItem(_effectiveSearchFormLocalizerOptions))
.ToList();
return _searchItems;
}
}
```
This keeps all current functionality (parameter override + localized defaults) while reducing complexity around parameter mutation, nullability, and getter side effects.
</issue_to_address>Help me be more useful! Please click 👍 or 👎 on each comment and I'll use the feedback to improve your reviews.
There was a problem hiding this comment.
Pull request overview
This PR introduces localization support for the Table search form’s auto-generated search item metadata (enum “All”, boolean values, number range labels), adds the corresponding localization resources, and updates related Table behavior/docs.
Changes:
- Added
SearchFormLocalizerOptionsand wired Table to provide localized default labels for generated search form items. - Updated
ITableColumn→ISearchItemconversion to accept localization options when building metadata. - Added new localization entries in both library and server locale JSON files; bumped package version.
Reviewed changes
Copilot reviewed 9 out of 10 changed files in this pull request and generated 4 comments.
Show a summary per file
| File | Description |
|---|---|
| src/BootstrapBlazor/Options/SearchFormLocalizerOptions.cs | New options type for search-form label localization. |
| src/BootstrapBlazor/Locales/zh.json | Adds localized strings for SearchFormLocalizerOptions. |
| src/BootstrapBlazor/Locales/en.json | Adds localized strings for SearchFormLocalizerOptions. |
| src/BootstrapBlazor/Extensions/ITableColumnExtensions.cs | Updates search-item generation to use localized option values. |
| src/BootstrapBlazor/Components/Table/Table.razor.Search.cs | Adds Table parameter + default options creation from localizer; changes advanced-search filter gating. |
| src/BootstrapBlazor/Components/Table/Table.razor.Localization.cs | Injects localizer for SearchFormLocalizerOptions. |
| src/BootstrapBlazor/Components/Table/Table.razor.cs | Version-related minor change; adds placeholder comment. |
| src/BootstrapBlazor/BootstrapBlazor.csproj | Bumps package version to 10.4.1-beta03. |
| src/BootstrapBlazor.Server/Locales/zh-CN.json | Adds/moves sample-page localized strings for SearchForm section. |
| src/BootstrapBlazor.Server/Locales/en-US.json | Adds/moves sample-page localized strings for SearchForm section. |
| src/BootstrapBlazor.Server/Components/Samples/Table/TablesSearch.razor | Formatting-only indentation change. |
💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.
Codecov Report✅ All modified and coverable lines are covered by tests. Additional details and impacted files@@ Coverage Diff @@
## main #7769 +/- ##
=======================================
Coverage 99.99% 99.99%
=======================================
Files 764 764
Lines 33933 33953 +20
Branches 4672 4673 +1
=======================================
+ Hits 33930 33951 +21
Misses 2 2
+ Partials 1 0 -1
Flags with carried forward coverage won't be shown. Click here to find out more. ☔ View full report in Codecov by Sentry. 🚀 New features to boost your workflow:
|
Link issues
fixes #7768
Summary By Copilot
Regression?
Risk
Verification
Packaging changes reviewed?
☑️ Self Check before Merge
Summary by Sourcery
Add configurable localization support for table search form UI and refine advanced search behavior.
New Features:
Enhancements:
Documentation: