Skip to content

Commit

Permalink
Merge branch 'main' into feat-css-inliner
Browse files Browse the repository at this point in the history
  • Loading branch information
rich-iannone committed Dec 10, 2024
2 parents b4b90a6 + 03e38ab commit d307803
Show file tree
Hide file tree
Showing 4 changed files with 46 additions and 16 deletions.
35 changes: 19 additions & 16 deletions great_tables/_formats.py
Original file line number Diff line number Diff line change
Expand Up @@ -34,7 +34,7 @@
to_list,
)
from ._text import _md_html, escape_pattern_str_latex
from ._utils import _str_detect, _str_replace
from ._utils import is_valid_http_schema, _str_detect, _str_replace
from ._utils_nanoplots import _generate_nanoplot

if TYPE_CHECKING:
Expand Down Expand Up @@ -3663,13 +3663,13 @@ def fmt_image(
To more easily insert graphics into body cells, we can use the `fmt_image()` method. This allows
for one or more images to be placed in the targeted cells. The cells need to contain some
reference to an image file, either: (1) complete http/https or local paths to the files; (2) the
file names, where a common path can be provided via `path=`; or (3) a fragment of the file name,
where the `file_pattern=` argument helps to compose the entire file name and `path=` provides
the path information. This should be expressly used on columns that contain *only* references to
image files (i.e., no image references as part of a larger block of text). Multiple images can
be included per cell by separating image references by commas. The `sep=` argument allows for a
common separator to be applied between images.
reference to an image file, either: (1) local paths to the files; (2) complete http/https to the
files; (3) the file names, where a common path can be provided via `path=`; or (4) a fragment of
the file name, where the `file_pattern=` argument helps to compose the entire file name and
`path=` provides the path information. This should be expressly used on columns that contain
*only* references to image files (i.e., no image references as part of a larger block of text).
Multiple images can be included per cell by separating image references by commas. The `sep=`
argument allows for a common separator to be applied between images.
Parameters
----------
Expand Down Expand Up @@ -3749,7 +3749,7 @@ def fmt_image(
if height is None and width is None:
height = "2em"

formatter = FmtImage(self._tbl_data, height, width, sep, str(path), file_pattern, encode)
formatter = FmtImage(self._tbl_data, height, width, sep, path, file_pattern, encode)
return fmt(
self,
fns=FormatFns(html=formatter.to_html, latex=formatter.to_latex, default=formatter.to_html),
Expand All @@ -3762,9 +3762,9 @@ def fmt_image(
class FmtImage:
dispatch_on: DataFrameLike | Agnostic = Agnostic()
height: str | int | None = None
width: str | None = None
width: str | int | None = None
sep: str = " "
path: str | None = None
path: str | Path | None = None
file_pattern: str = "{}"
encode: bool = True

Expand Down Expand Up @@ -3800,13 +3800,16 @@ def to_html(self, val: Any):

out: list[str] = []
for file in full_files:
# Case 1: from url
if self.path and (self.path.startswith("http://") or self.path.startswith("https://")):
norm_path = self.path.rstrip().removesuffix("/")
# Case 1: from url via `dispatch_on`
if self.path is None and is_valid_http_schema(file):
uri = file.rstrip().removesuffix("/")
# Case 2: from url via `path`
elif self.path is not None and is_valid_http_schema(str(self.path)):
norm_path = str(self.path).rstrip().removesuffix("/")
uri = f"{norm_path}/{file}"
# Case 2:
# Case 3:
else:
filename = (Path(self.path or "") / file).expanduser().absolute()
filename = str((Path(self.path or "") / file).expanduser().absolute())

if self.encode:
uri = self._get_image_uri(filename)
Expand Down
4 changes: 4 additions & 0 deletions great_tables/_utils.py
Original file line number Diff line number Diff line change
Expand Up @@ -281,3 +281,7 @@ def _migrate_unformatted_to_output(
# Define the type of `data` as `TblData` when doing so won't result in a circular import
def _get_visible_cells(data: TblData) -> list[tuple[str, int]]:
return [(col, row) for col in get_column_names(data) for row in range(n_rows(data))]


def is_valid_http_schema(url: str) -> bool:
return url.startswith("http://") or url.startswith("https://")
14 changes: 14 additions & 0 deletions tests/test_formats.py
Original file line number Diff line number Diff line change
Expand Up @@ -1734,6 +1734,20 @@ def test_fmt_flag_height():
assert column_vals_px == column_vals_num


@pytest.mark.parametrize(
"url", ["http://posit.co/", "http://posit.co", "https://posit.co/", "https://posit.co"]
)
def test_fmt_image_http(url: str):
formatter = FmtImage(encode=False, height=30)
res = formatter.to_html(url)
dst_img = '<img src="{}" style="height: 30px;vertical-align: middle;">'.format(
url.removesuffix("/")
)
dst = formatter.SPAN_TEMPLATE.format(dst_img)

assert strip_windows_drive(res) == dst


@pytest.mark.parametrize(
"src,dst",
[
Expand Down
9 changes: 9 additions & 0 deletions tests/test_utils.py
Original file line number Diff line number Diff line change
@@ -1,6 +1,7 @@
from collections.abc import Generator
import pytest


from great_tables import GT, exibble
from great_tables._tbl_data import is_na
from great_tables._utils import (
Expand All @@ -14,6 +15,7 @@
_migrate_unformatted_to_output,
OrderedSet,
_str_scalar_to_list,
is_valid_http_schema,
heading_has_subtitle,
heading_has_title,
seq_groups,
Expand Down Expand Up @@ -215,3 +217,10 @@ def test_migrate_unformatted_to_output_html():
)

assert is_na(migrated._body.body, migrated._body.body["char"].tolist()).tolist() == [True, True]


@pytest.mark.parametrize(
"url", ["http://posit.co/", "http://posit.co", "https://posit.co/", "https://posit.co"]
)
def test_is_valid_http_schema(url: str):
assert is_valid_http_schema(url)

0 comments on commit d307803

Please sign in to comment.