licos-dev-cli 0.2.21__tar.gz → 0.3.1__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/PKG-INFO +2 -2
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/pyproject.toml +3 -3
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/src/licos_dev_cli/main.py +87 -8
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/tests/test_credit_check.py +26 -0
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/.gitignore +0 -0
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/src/licos_dev_cli/__init__.py +0 -0
- {licos_dev_cli-0.2.21 → licos_dev_cli-0.3.1}/tests/test_cli_output_paths.py +0 -0
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: licos-dev-cli
|
|
3
|
-
Version: 0.
|
|
3
|
+
Version: 0.3.1
|
|
4
4
|
Summary: LICOS Dev CLI - generate files and call model capabilities
|
|
5
5
|
Requires-Python: >=3.10
|
|
6
6
|
Requires-Dist: click>=8.1
|
|
7
|
-
Requires-Dist: licos-dev-sdk>=0.
|
|
7
|
+
Requires-Dist: licos-dev-sdk>=0.3.1
|
|
@@ -1,14 +1,14 @@
|
|
|
1
1
|
[build-system]
|
|
2
|
-
requires = ["hatchling"]
|
|
2
|
+
requires = ["hatchling>=1.27,<1.31"]
|
|
3
3
|
build-backend = "hatchling.build"
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "licos-dev-cli"
|
|
7
|
-
version = "0.
|
|
7
|
+
version = "0.3.1"
|
|
8
8
|
description = "LICOS Dev CLI - generate files and call model capabilities"
|
|
9
9
|
requires-python = ">=3.10"
|
|
10
10
|
dependencies = [
|
|
11
|
-
"licos-dev-sdk>=0.
|
|
11
|
+
"licos-dev-sdk>=0.3.1",
|
|
12
12
|
"click>=8.1",
|
|
13
13
|
]
|
|
14
14
|
|
|
@@ -123,14 +123,63 @@ def credit_check(estimated_points, resource_type, resource_code, request_id):
|
|
|
123
123
|
@click.option("-o", "--output-dir", default=None, help="Output directory")
|
|
124
124
|
@click.option("--format", "content_type", default="markdown", help="Content type: markdown|html")
|
|
125
125
|
@click.option("--page-size", default="A4", help="Page size: A4|LETTER")
|
|
126
|
-
|
|
126
|
+
@click.option("--theme", default="formal-blue", help="Theme: formal-blue|business|neutral")
|
|
127
|
+
@click.option("--title", default=None, help="Document title")
|
|
128
|
+
@click.option("--margin", default="20mm", help="Page margin CSS length, e.g. 20mm")
|
|
129
|
+
def pdf(input_path, content, filename, output_dir, content_type, page_size, theme, title, margin):
|
|
127
130
|
"""Generate PDF from Markdown or HTML."""
|
|
128
131
|
from licos_dev_sdk import create_pdf
|
|
129
132
|
text = _read_input(input_path, content)
|
|
130
|
-
path = create_pdf(
|
|
133
|
+
path = create_pdf(
|
|
134
|
+
text,
|
|
135
|
+
filename,
|
|
136
|
+
content_type=content_type,
|
|
137
|
+
output_dir=output_dir,
|
|
138
|
+
page_size=page_size,
|
|
139
|
+
theme=theme,
|
|
140
|
+
title=title,
|
|
141
|
+
margin=margin,
|
|
142
|
+
)
|
|
131
143
|
_echo_path(path)
|
|
132
144
|
|
|
133
145
|
|
|
146
|
+
@cli.command("pdf-inspect")
|
|
147
|
+
@click.option("-f", "--file", "file_path", required=True, type=click.Path(exists=True, dir_okay=False))
|
|
148
|
+
@click.option("--min-pages", type=click.IntRange(min=1), default=None)
|
|
149
|
+
@click.option("--max-pages", type=click.IntRange(min=1), default=None)
|
|
150
|
+
@click.option(
|
|
151
|
+
"--sparse-text-threshold",
|
|
152
|
+
type=click.IntRange(min=0),
|
|
153
|
+
default=300,
|
|
154
|
+
show_default=True,
|
|
155
|
+
help="Flag non-cover pages with fewer extracted text characters; 0 disables the check.",
|
|
156
|
+
)
|
|
157
|
+
@click.option("--allow-sparse-cover/--check-sparse-cover", default=True, show_default=True)
|
|
158
|
+
@click.option("--check-orphan-headings/--allow-orphan-headings", default=True, show_default=True)
|
|
159
|
+
def pdf_inspect(
|
|
160
|
+
file_path,
|
|
161
|
+
min_pages,
|
|
162
|
+
max_pages,
|
|
163
|
+
sparse_text_threshold,
|
|
164
|
+
allow_sparse_cover,
|
|
165
|
+
check_orphan_headings,
|
|
166
|
+
):
|
|
167
|
+
"""Inspect PDF structure, page density, and requested page-count limits."""
|
|
168
|
+
from licos_dev_sdk import inspect_pdf
|
|
169
|
+
|
|
170
|
+
report = inspect_pdf(
|
|
171
|
+
file_path,
|
|
172
|
+
min_pages=min_pages,
|
|
173
|
+
max_pages=max_pages,
|
|
174
|
+
sparse_text_threshold=sparse_text_threshold,
|
|
175
|
+
allow_sparse_cover=allow_sparse_cover,
|
|
176
|
+
check_orphan_headings=check_orphan_headings,
|
|
177
|
+
)
|
|
178
|
+
click.echo(json.dumps(report, ensure_ascii=False, indent=2))
|
|
179
|
+
if not report["quality_passed"]:
|
|
180
|
+
raise click.exceptions.Exit(2)
|
|
181
|
+
|
|
182
|
+
|
|
134
183
|
# ── DOCX ─────────────────────────────────────────────────────────────────────
|
|
135
184
|
|
|
136
185
|
@cli.command()
|
|
@@ -139,13 +188,31 @@ def pdf(input_path, content, filename, output_dir, content_type, page_size):
|
|
|
139
188
|
@click.option("-f", "--filename", required=True)
|
|
140
189
|
@click.option("-o", "--output-dir", default=None)
|
|
141
190
|
@click.option("--format", "content_type", default="markdown")
|
|
142
|
-
@click.option("--font", default="
|
|
191
|
+
@click.option("--font", default="Microsoft YaHei")
|
|
143
192
|
@click.option("--font-size", default=11, type=int)
|
|
144
|
-
|
|
193
|
+
@click.option("--theme", default="formal-blue", help="Theme: formal-blue|business|neutral")
|
|
194
|
+
@click.option("--title", default=None, help="Document title used when content has no H1")
|
|
195
|
+
@click.option("--header", default=None, help="Header text")
|
|
196
|
+
@click.option("--footer", default=None, help="Footer text placed before the page number")
|
|
197
|
+
@click.option("--toc/--no-toc", default=False, help="Insert an updatable Word table of contents")
|
|
198
|
+
def docx(input_path, content, filename, output_dir, content_type, font, font_size, theme, title, header, footer, toc):
|
|
145
199
|
"""Generate DOCX from Markdown or HTML."""
|
|
146
200
|
from licos_dev_sdk import create_docx
|
|
147
201
|
text = _read_input(input_path, content)
|
|
148
|
-
path = create_docx(
|
|
202
|
+
path = create_docx(
|
|
203
|
+
text,
|
|
204
|
+
filename,
|
|
205
|
+
content_type=content_type,
|
|
206
|
+
output_dir=output_dir,
|
|
207
|
+
font_name=font,
|
|
208
|
+
font_size=font_size,
|
|
209
|
+
theme=theme,
|
|
210
|
+
title=title,
|
|
211
|
+
header=header,
|
|
212
|
+
footer=footer,
|
|
213
|
+
include_toc=toc,
|
|
214
|
+
asset_base_path=str(Path(input_path).resolve().parent) if input_path else None,
|
|
215
|
+
)
|
|
149
216
|
_echo_path(path)
|
|
150
217
|
|
|
151
218
|
|
|
@@ -174,11 +241,12 @@ def docx_template(template_path, input_path, data_content, filename, output_dir)
|
|
|
174
241
|
@click.option("-o", "--output-dir", default=None)
|
|
175
242
|
@click.option("--sheet-name", default="Sheet1")
|
|
176
243
|
@click.option("--header-color", default="4472C4")
|
|
177
|
-
|
|
244
|
+
@click.option("--theme", default="professional-blue", help="Theme: professional-blue|business|neutral")
|
|
245
|
+
def xlsx(input_path, content, filename, output_dir, sheet_name, header_color, theme):
|
|
178
246
|
"""Generate XLSX from JSON data."""
|
|
179
247
|
from licos_dev_sdk import create_xlsx
|
|
180
248
|
data = _read_json(input_path, content)
|
|
181
|
-
path = create_xlsx(data, filename, output_dir=output_dir, sheet_name=sheet_name, header_color=header_color)
|
|
249
|
+
path = create_xlsx(data, filename, output_dir=output_dir, sheet_name=sheet_name, header_color=header_color, theme=theme)
|
|
182
250
|
_echo_path(path)
|
|
183
251
|
|
|
184
252
|
|
|
@@ -190,7 +258,8 @@ def xlsx(input_path, content, filename, output_dir, sheet_name, header_color):
|
|
|
190
258
|
@click.option("--header-color", default="4472C4")
|
|
191
259
|
@click.option("--freeze-header/--no-freeze-header", default=True)
|
|
192
260
|
@click.option("--autofilter/--no-autofilter", default=True)
|
|
193
|
-
|
|
261
|
+
@click.option("--theme", default="professional-blue", help="Theme: professional-blue|business|neutral")
|
|
262
|
+
def xlsx_workbook(input_path, content, filename, output_dir, header_color, freeze_header, autofilter, theme):
|
|
194
263
|
"""Generate multi-sheet XLSX from JSON workbook data."""
|
|
195
264
|
from licos_dev_sdk import create_xlsx_workbook
|
|
196
265
|
data = _read_json(input_path, content)
|
|
@@ -201,10 +270,20 @@ def xlsx_workbook(input_path, content, filename, output_dir, header_color, freez
|
|
|
201
270
|
header_color=header_color,
|
|
202
271
|
freeze_header=freeze_header,
|
|
203
272
|
autofilter=autofilter,
|
|
273
|
+
theme=theme,
|
|
204
274
|
)
|
|
205
275
|
_echo_path(path)
|
|
206
276
|
|
|
207
277
|
|
|
278
|
+
@cli.command("xlsx-inspect")
|
|
279
|
+
@click.option("-f", "--file", "file_path", required=True, type=click.Path(exists=True, dir_okay=False))
|
|
280
|
+
def xlsx_inspect(file_path):
|
|
281
|
+
"""Inspect generated XLSX formulas, charts, formatting, and validation features."""
|
|
282
|
+
from licos_dev_sdk import inspect_xlsx
|
|
283
|
+
|
|
284
|
+
click.echo(json.dumps(inspect_xlsx(file_path), ensure_ascii=False, indent=2))
|
|
285
|
+
|
|
286
|
+
|
|
208
287
|
# ── CSV ──────────────────────────────────────────────────────────────────────
|
|
209
288
|
|
|
210
289
|
@cli.command()
|
|
@@ -1,6 +1,7 @@
|
|
|
1
1
|
from __future__ import annotations
|
|
2
2
|
|
|
3
3
|
import json
|
|
4
|
+
from pathlib import Path
|
|
4
5
|
from unittest import mock
|
|
5
6
|
|
|
6
7
|
from click.testing import CliRunner
|
|
@@ -37,3 +38,28 @@ def test_credit_check_forwards_structured_options() -> None:
|
|
|
37
38
|
resource_code="IMAGE_GENERATE",
|
|
38
39
|
request_id="request-1",
|
|
39
40
|
)
|
|
41
|
+
|
|
42
|
+
|
|
43
|
+
def test_docx_uses_input_directory_as_asset_base_path(tmp_path: Path) -> None:
|
|
44
|
+
source_dir = tmp_path / "source"
|
|
45
|
+
source_dir.mkdir()
|
|
46
|
+
input_path = source_dir / "report.html"
|
|
47
|
+
input_path.write_text('<img src="chart.png">', encoding="utf-8")
|
|
48
|
+
|
|
49
|
+
with mock.patch(
|
|
50
|
+
"licos_dev_sdk.create_docx",
|
|
51
|
+
return_value=str(tmp_path / "report.docx"),
|
|
52
|
+
) as create:
|
|
53
|
+
result = CliRunner().invoke(
|
|
54
|
+
cli,
|
|
55
|
+
[
|
|
56
|
+
"docx",
|
|
57
|
+
"--input",
|
|
58
|
+
str(input_path),
|
|
59
|
+
"--filename",
|
|
60
|
+
"report.docx",
|
|
61
|
+
],
|
|
62
|
+
)
|
|
63
|
+
|
|
64
|
+
assert result.exit_code == 0
|
|
65
|
+
assert create.call_args.kwargs["asset_base_path"] == str(source_dir.resolve())
|
|
File without changes
|
|
File without changes
|
|
File without changes
|