Skip to content

Conversation

@shuoweil
Copy link
Contributor

@shuoweil shuoweil commented Dec 4, 2025

This PR introduces the single column display for anywidget mode.

A screenshot of single index column display is here: screen/6VLA4Nk68TsYczV

Fixes #<459515995> 🦕

@shuoweil shuoweil requested a review from tswast December 4, 2025 18:22
@shuoweil shuoweil self-assigned this Dec 4, 2025
@shuoweil shuoweil requested review from a team as code owners December 4, 2025 18:22
@review-notebook-app
Copy link

Check out this pull request on  ReviewNB

See visual diffs & provide feedback on Jupyter Notebooks.


Powered by ReviewNB

@product-auto-label product-auto-label bot added size: l Pull request size is large. api: bigquery Issues related to the googleapis/python-bigquery-dataframes API. labels Dec 4, 2025
@shuoweil shuoweil marked this pull request as draft December 4, 2025 20:49
@shuoweil shuoweil removed the request for review from tswast December 4, 2025 21:16
@shuoweil shuoweil marked this pull request as ready for review December 4, 2025 21:16
@shuoweil shuoweil requested a review from tswast December 4, 2025 21:17
@shuoweil shuoweil changed the title feat: Display index column in anywidget mode feat: Display custom single index column in anywidget mode Dec 4, 2025
page_data = cached_data.iloc[start:end].copy()

# Handle index display
if page_data.index.name is not None:
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Would it be possible to check len(df.index.names) != 0 on the original BigFrames DataFrame instead? Most of the time the no-name index is going to be the default range index, but not always.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actually, it looks like df.index.names won't work in partial ordering mode.

@validations.requires_index

I'll try to figure out the correct alternative and report back.

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

df._block.has_index

Copy link
Contributor Author

@shuoweil shuoweil Dec 12, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Thanks again for the excellent feedback, @tswast. Your suggestion to use df._block.has_index was precisely what was needed to avoid the expensive index materialization on the full BigFrames DataFrame.

I've implemented the change to use self._dataframe._block.has_index. However, I found that an additional check was needed to fully resolve the issue and pass test_widget_with_default_index_should_display_row_column.

The full condition I've used is:
if self._dataframe._block.has_index and page_data.index.name is not None:

To clarify the inclusion of page_data.index.name is not None: this part of the check is performed on the small, local pandas page_data slice. It's a cheap operation because page_data is already in memory. Its purpose is to correctly handle the display formatting in all scenarios.

Specifically, while self._dataframe._block.has_index correctly tells us if a custom index exists on the BigFrames DataFrame, that index might still be an unnamed default (like a RangeIndex). In such cases, page_data.index.name would be None.

The combined check ensures that we only display a named custom index when both conditions are met:

  1. A custom index has been defined on the BigFrames DataFrame (self._dataframe._block.has_index).
  2. That index actually has a name (page_data.index.name is not None) to use as a header.

Otherwise, it correctly falls back to displaying the generic "Row" column. This makes the overall index display logic robust and accurate, reflecting the user's intent without triggering expensive BigQuery operations.

Let me know if this approach looks good to you.

@shuoweil shuoweil requested a review from tswast December 12, 2025 20:27
Comment on lines 300 to 302
if self._dataframe._block.has_index and page_data.index.name is not None:
# Custom named index - include it with its actual name
page_data.insert(0, page_data.index.name, page_data.index)
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Let's display the real index values, even if the index has no name.

Suggested change
if self._dataframe._block.has_index and page_data.index.name is not None:
# Custom named index - include it with its actual name
page_data.insert(0, page_data.index.name, page_data.index)
if self._dataframe._block.has_index:
index_name = page_data.index.name
page_data.insert(0, index_name if index_name is not None else "", page_data.index)

Copy link
Contributor Author

@shuoweil shuoweil Dec 12, 2025

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

testcase is updated accordingly

@shuoweil shuoweil requested a review from tswast December 12, 2025 21:56
page_data = cached_data.iloc[start:end].copy()

# Handle index display
# TODO(b/332316283): Add tests for custom multiindex
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Looks like this bug ID is incorrect. Maybe this is the correct one?

Suggested change
# TODO(b/332316283): Add tests for custom multiindex
# TODO(b/459515995): Add tests for custom multiindex

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

actually, I plan to use this one b/438181139

Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Are these changes intended? Maybe you missed my note about opting out of airlock in chat? I've also added instructions to our internal contributing docs.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I definitely should not include this noxfile change. I moidfy the noxfile file locally to run nox. I will revert this file change.

assert "row_4" not in html # Verify it respects max_rows


# TODO(b/332316283): Add tests for custom multiindex
Copy link
Collaborator

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Bug ID looks incorrect here, too.

Suggested change
# TODO(b/332316283): Add tests for custom multiindex
# TODO(b/459515995): Add tests for custom multiindex

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I would like to use b/438181139

@shuoweil shuoweil requested a review from tswast December 12, 2025 22:19
@shuoweil shuoweil merged commit f271962 into main Dec 12, 2025
20 of 25 checks passed
@shuoweil shuoweil deleted the shuowei-anywidget-single-index branch December 12, 2025 22:54
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

api: bigquery Issues related to the googleapis/python-bigquery-dataframes API. size: l Pull request size is large.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants