gcf-python 2.2.0__py3-none-any.whl → 2.2.1__py3-none-any.whl
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.
- gcf/__init__.py +2 -1
- gcf/decode_generic.py +19 -10
- gcf/generic.py +83 -33
- {gcf_python-2.2.0.dist-info → gcf_python-2.2.1.dist-info}/METADATA +7 -7
- {gcf_python-2.2.0.dist-info → gcf_python-2.2.1.dist-info}/RECORD +8 -8
- {gcf_python-2.2.0.dist-info → gcf_python-2.2.1.dist-info}/WHEEL +0 -0
- {gcf_python-2.2.0.dist-info → gcf_python-2.2.1.dist-info}/entry_points.txt +0 -0
- {gcf_python-2.2.0.dist-info → gcf_python-2.2.1.dist-info}/licenses/LICENSE +0 -0
gcf/__init__.py
CHANGED
|
@@ -38,7 +38,7 @@ from .constants import KIND_ABBREV, KIND_EXPAND
|
|
|
38
38
|
from .decode import DecodeError, decode
|
|
39
39
|
from .delta import encode_delta
|
|
40
40
|
from .encode import encode
|
|
41
|
-
from .generic import encode_generic
|
|
41
|
+
from .generic import encode_generic, GenericOptions
|
|
42
42
|
from .session import Session, encode_with_session
|
|
43
43
|
from .decode_generic import decode_generic
|
|
44
44
|
from .stream import StreamEncoder
|
|
@@ -62,6 +62,7 @@ __all__ = [
|
|
|
62
62
|
"encode",
|
|
63
63
|
"encode_delta",
|
|
64
64
|
"encode_generic",
|
|
65
|
+
"GenericOptions",
|
|
65
66
|
"encode_with_session",
|
|
66
67
|
]
|
|
67
68
|
|
gcf/decode_generic.py
CHANGED
|
@@ -360,6 +360,14 @@ def _parse_attachment(
|
|
|
360
360
|
arr, consumed = _parse_array_from_header(lines, line_idx, depth, after_name)
|
|
361
361
|
return name, arr, consumed, None
|
|
362
362
|
|
|
363
|
+
# Scalar: =value (field names containing ">" excluded from tabular columns).
|
|
364
|
+
if after_name.startswith("="):
|
|
365
|
+
val_str = after_name[1:]
|
|
366
|
+
parsed = parse_scalar(val_str, tabular_context=True)
|
|
367
|
+
if parsed is MISSING:
|
|
368
|
+
return name, None, 1, None
|
|
369
|
+
return name, parsed, 1, None
|
|
370
|
+
|
|
363
371
|
raise ValueError(f"invalid attachment form: {after_name}")
|
|
364
372
|
|
|
365
373
|
|
|
@@ -423,7 +431,11 @@ def _parse_tabular_body(
|
|
|
423
431
|
path_column_map: dict[str, list[str]] = {}
|
|
424
432
|
for f in fields:
|
|
425
433
|
if ">" in f:
|
|
426
|
-
|
|
434
|
+
parts = f.split(">")
|
|
435
|
+
# Only treat as a path column if all segments are non-empty.
|
|
436
|
+
# A literal key like ">" would split into ["", ""].
|
|
437
|
+
if all(p for p in parts):
|
|
438
|
+
path_column_map[f] = parts
|
|
427
439
|
|
|
428
440
|
# Track inline schemas and shared array schemas.
|
|
429
441
|
inline_schemas: dict[str, list[str]] = {}
|
|
@@ -506,10 +518,10 @@ def _parse_tabular_body(
|
|
|
506
518
|
all_att_fields = traditional_att_fields + inline_att_fields
|
|
507
519
|
attachment_values: dict[str, Any] = {}
|
|
508
520
|
|
|
509
|
-
if row_has_id
|
|
521
|
+
if row_has_id:
|
|
510
522
|
inline_idx = 0
|
|
511
523
|
|
|
512
|
-
while i < len(lines)
|
|
524
|
+
while i < len(lines):
|
|
513
525
|
a_line = lines[i]
|
|
514
526
|
a_content: str | None = None
|
|
515
527
|
if depth == 0 or a_line.startswith(ind):
|
|
@@ -601,13 +613,6 @@ def _parse_tabular_body(
|
|
|
601
613
|
if extra_name in attachment_values:
|
|
602
614
|
raise ValueError(f"duplicate_attachment: {extra_name}")
|
|
603
615
|
|
|
604
|
-
if not row_has_id or not all_att_fields:
|
|
605
|
-
att_indent = ind + " "
|
|
606
|
-
if i < len(lines) and lines[i].startswith(att_indent):
|
|
607
|
-
peek = lines[i][len(att_indent):]
|
|
608
|
-
if peek.startswith("."):
|
|
609
|
-
raise ValueError(f"orphan_attachment: {peek}")
|
|
610
|
-
|
|
611
616
|
row: dict[str, Any] = {}
|
|
612
617
|
for f in fields:
|
|
613
618
|
if f in missing_fields:
|
|
@@ -616,6 +621,10 @@ def _parse_tabular_body(
|
|
|
616
621
|
row[f] = cell_values[f]
|
|
617
622
|
elif f in attachment_values:
|
|
618
623
|
row[f] = attachment_values[f]
|
|
624
|
+
# Also add any orphan attachment values (fields excluded from column list, e.g. ">" fields).
|
|
625
|
+
for k, v in attachment_values.items():
|
|
626
|
+
if k not in row:
|
|
627
|
+
row[k] = v
|
|
619
628
|
# Unflatten path columns into nested objects.
|
|
620
629
|
if path_column_map:
|
|
621
630
|
nested = _unflatten_paths(path_column_map, flat_values, flat_absent)
|
gcf/generic.py
CHANGED
|
@@ -2,42 +2,55 @@
|
|
|
2
2
|
|
|
3
3
|
from __future__ import annotations
|
|
4
4
|
|
|
5
|
+
from dataclasses import dataclass
|
|
5
6
|
from typing import Any
|
|
6
7
|
|
|
7
8
|
from .scalar import format_scalar, format_key
|
|
8
9
|
|
|
9
10
|
|
|
10
|
-
|
|
11
|
+
@dataclass
|
|
12
|
+
class GenericOptions:
|
|
13
|
+
"""Options for controlling generic encoding behavior."""
|
|
14
|
+
no_flatten: bool = False
|
|
15
|
+
"""When True, disables promotion of fixed-shape nested objects to path
|
|
16
|
+
columns (e.g. "customer>name"). Nested objects use attachment syntax
|
|
17
|
+
instead. Set when targeting open-weight models that show lower
|
|
18
|
+
comprehension on flattened encoding."""
|
|
19
|
+
|
|
20
|
+
|
|
21
|
+
def encode_generic(data: Any, opts: GenericOptions | None = None) -> str:
|
|
22
|
+
if opts is None:
|
|
23
|
+
opts = GenericOptions()
|
|
11
24
|
out: list[str] = ["GCF profile=generic"]
|
|
12
|
-
_encode_root_value(data, out)
|
|
25
|
+
_encode_root_value(data, out, opts)
|
|
13
26
|
return "\n".join(out) + "\n"
|
|
14
27
|
|
|
15
28
|
|
|
16
|
-
def _encode_root_value(v: Any, out: list[str]) -> None:
|
|
29
|
+
def _encode_root_value(v: Any, out: list[str], opts: GenericOptions) -> None:
|
|
17
30
|
if v is None:
|
|
18
31
|
out.append("=-")
|
|
19
32
|
elif isinstance(v, dict):
|
|
20
|
-
_encode_object(v, out, 0)
|
|
33
|
+
_encode_object(v, out, 0, opts)
|
|
21
34
|
elif isinstance(v, list):
|
|
22
|
-
_encode_root_array(v, out)
|
|
35
|
+
_encode_root_array(v, out, opts)
|
|
23
36
|
else:
|
|
24
37
|
out.append(f"={format_scalar(v)}")
|
|
25
38
|
|
|
26
39
|
|
|
27
|
-
def _encode_object(d: dict, out: list[str], depth: int) -> None:
|
|
40
|
+
def _encode_object(d: dict, out: list[str], depth: int, opts: GenericOptions) -> None:
|
|
28
41
|
prefix = _indent(depth)
|
|
29
42
|
for key, value in d.items():
|
|
30
43
|
fk = format_key(key)
|
|
31
44
|
if isinstance(value, dict):
|
|
32
45
|
out.append(f"{prefix}## {fk}")
|
|
33
|
-
_encode_object(value, out, depth + 1)
|
|
46
|
+
_encode_object(value, out, depth + 1, opts)
|
|
34
47
|
elif isinstance(value, list):
|
|
35
|
-
_encode_named_array(fk, value, out, depth)
|
|
48
|
+
_encode_named_array(fk, value, out, depth, opts)
|
|
36
49
|
else:
|
|
37
50
|
out.append(f"{prefix}{fk}={format_scalar(value)}")
|
|
38
51
|
|
|
39
52
|
|
|
40
|
-
def _encode_root_array(arr: list, out: list[str]) -> None:
|
|
53
|
+
def _encode_root_array(arr: list, out: list[str], opts: GenericOptions) -> None:
|
|
41
54
|
if not arr:
|
|
42
55
|
out.append("## [0]")
|
|
43
56
|
return
|
|
@@ -47,12 +60,12 @@ def _encode_root_array(arr: list, out: list[str]) -> None:
|
|
|
47
60
|
return
|
|
48
61
|
fields = _tabular_fields(arr)
|
|
49
62
|
if fields is not None:
|
|
50
|
-
_encode_tabular("## ", arr, fields, out, 0)
|
|
63
|
+
_encode_tabular("## ", arr, fields, out, 0, opts)
|
|
51
64
|
return
|
|
52
|
-
_encode_expanded("## ", arr, out, 0)
|
|
65
|
+
_encode_expanded("## ", arr, out, 0, opts)
|
|
53
66
|
|
|
54
67
|
|
|
55
|
-
def _encode_named_array(name: str, arr: list, out: list[str], depth: int) -> None:
|
|
68
|
+
def _encode_named_array(name: str, arr: list, out: list[str], depth: int, opts: GenericOptions) -> None:
|
|
56
69
|
prefix = _indent(depth)
|
|
57
70
|
if not arr:
|
|
58
71
|
out.append(f"{prefix}## {name} [0]")
|
|
@@ -63,9 +76,9 @@ def _encode_named_array(name: str, arr: list, out: list[str], depth: int) -> Non
|
|
|
63
76
|
return
|
|
64
77
|
fields = _tabular_fields(arr)
|
|
65
78
|
if fields is not None:
|
|
66
|
-
_encode_tabular(f"{prefix}## {name} ", arr, fields, out, depth)
|
|
79
|
+
_encode_tabular(f"{prefix}## {name} ", arr, fields, out, depth, opts)
|
|
67
80
|
return
|
|
68
|
-
_encode_expanded(f"{prefix}## {name} ", arr, out, depth)
|
|
81
|
+
_encode_expanded(f"{prefix}## {name} ", arr, out, depth, opts)
|
|
69
82
|
|
|
70
83
|
|
|
71
84
|
def _tabular_fields(arr: list) -> list[str] | None:
|
|
@@ -152,6 +165,9 @@ def _analyze_flattenable(
|
|
|
152
165
|
arr: list[dict], field_name: str, parent_path: str
|
|
153
166
|
) -> list[dict] | None:
|
|
154
167
|
"""Analyze whether a field can be flattened. Returns list of leaf descriptors or None."""
|
|
168
|
+
# Field names containing ">" cannot be flattened (would create ambiguous paths).
|
|
169
|
+
if ">" in field_name:
|
|
170
|
+
return None
|
|
155
171
|
canonical_shape: dict[str, str] | None = None # key -> "scalar" | "nested"
|
|
156
172
|
|
|
157
173
|
for item in arr:
|
|
@@ -249,26 +265,39 @@ def _resolve_key_chain(item: Any, keys: list[str]) -> tuple[Any, bool]:
|
|
|
249
265
|
|
|
250
266
|
|
|
251
267
|
def _encode_tabular(
|
|
252
|
-
header_prefix: str, arr: list[dict], fields: list[str], out: list[str], depth: int
|
|
268
|
+
header_prefix: str, arr: list[dict], fields: list[str], out: list[str], depth: int, opts: GenericOptions
|
|
253
269
|
) -> None:
|
|
254
270
|
prefix = _indent(depth)
|
|
255
271
|
|
|
256
272
|
# Phase 0: Analyze fields for flattening.
|
|
257
273
|
flatten_map: dict[str, list[dict]] = {}
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
|
|
261
|
-
|
|
274
|
+
if not opts.no_flatten:
|
|
275
|
+
for f in fields:
|
|
276
|
+
leaves = _analyze_flattenable(arr, f, "")
|
|
277
|
+
if leaves and len(leaves) > 0:
|
|
278
|
+
flatten_map[f] = leaves
|
|
279
|
+
|
|
280
|
+
# Fields whose names contain ">" must not appear as tabular columns
|
|
281
|
+
# because the decoder would interpret them as flattened path columns.
|
|
282
|
+
# Track them for per-row attachment emission (spec rule 7.4.6.1.4).
|
|
283
|
+
gt_fields = {f for f in fields if f not in flatten_map and ">" in f}
|
|
262
284
|
|
|
263
285
|
# Build expanded column list.
|
|
264
286
|
columns: list[dict] = []
|
|
265
287
|
for f in fields:
|
|
288
|
+
if f in gt_fields:
|
|
289
|
+
continue
|
|
266
290
|
if f in flatten_map:
|
|
267
291
|
for leaf in flatten_map[f]:
|
|
268
292
|
columns.append({"header": format_key(leaf["path"]), "type": "flat", "field": f, "keys": leaf["keys"]})
|
|
269
293
|
else:
|
|
270
294
|
columns.append({"header": format_key(f), "type": "original", "field": f, "keys": []})
|
|
271
295
|
|
|
296
|
+
# If all fields were excluded (all contain ">"), fall back to expanded.
|
|
297
|
+
if not columns:
|
|
298
|
+
_encode_expanded(header_prefix, arr, out, depth, opts)
|
|
299
|
+
return
|
|
300
|
+
|
|
272
301
|
# Pre-compute inline schemas and shared array schemas (skip flattened fields).
|
|
273
302
|
inline_schemas: dict[str, list[str]] = {}
|
|
274
303
|
shared_arr_schemas: dict[str, list[str]] = {}
|
|
@@ -333,6 +362,15 @@ def _encode_tabular(
|
|
|
333
362
|
else:
|
|
334
363
|
cells.append(format_scalar(v, "|"))
|
|
335
364
|
|
|
365
|
+
# Emit fields with ">" in their names as per-row attachments.
|
|
366
|
+
for f in fields:
|
|
367
|
+
if f not in gt_fields:
|
|
368
|
+
continue
|
|
369
|
+
if f not in item:
|
|
370
|
+
continue
|
|
371
|
+
row_has_attachment = True
|
|
372
|
+
attachments.append((f, item[f], False, None))
|
|
373
|
+
|
|
336
374
|
row = "|".join(cells)
|
|
337
375
|
if row_has_attachment:
|
|
338
376
|
out.append(f"{prefix}@{i} {row}")
|
|
@@ -351,17 +389,25 @@ def _encode_tabular(
|
|
|
351
389
|
elif isinstance(att_val, list):
|
|
352
390
|
sas = shared_arr_schemas.get(att_name)
|
|
353
391
|
if sas and i > 0:
|
|
354
|
-
_encode_attachment_array_shared(prefix, fk, att_val, out, depth + 2, sas)
|
|
392
|
+
_encode_attachment_array_shared(prefix, fk, att_val, out, depth + 2, sas, opts)
|
|
355
393
|
else:
|
|
356
|
-
_encode_attachment_array(prefix, fk, att_val, out, depth + 2)
|
|
394
|
+
_encode_attachment_array(prefix, fk, att_val, out, depth + 2, opts)
|
|
357
395
|
elif isinstance(att_val, dict):
|
|
358
396
|
out.append(f"{prefix}.{fk} {{}}")
|
|
359
|
-
_encode_object(att_val, out, depth + 2)
|
|
397
|
+
_encode_object(att_val, out, depth + 2, opts)
|
|
398
|
+
else:
|
|
399
|
+
# Scalar attachment (e.g. field names containing ">").
|
|
400
|
+
if att_val is None:
|
|
401
|
+
out.append(f"{prefix}.{fk} =-")
|
|
402
|
+
else:
|
|
403
|
+
out.append(f"{prefix}.{fk} ={format_scalar(att_val)}")
|
|
360
404
|
|
|
361
405
|
|
|
362
406
|
def _encode_attachment_array(
|
|
363
|
-
att_prefix: str, fk: str, arr: list, out: list[str], depth: int
|
|
407
|
+
att_prefix: str, fk: str, arr: list, out: list[str], depth: int, opts: GenericOptions | None = None
|
|
364
408
|
) -> None:
|
|
409
|
+
if opts is None:
|
|
410
|
+
opts = GenericOptions()
|
|
365
411
|
if not arr:
|
|
366
412
|
out.append(f"{att_prefix}.{fk} [0]")
|
|
367
413
|
elif _all_primitives(arr):
|
|
@@ -370,13 +416,13 @@ def _encode_attachment_array(
|
|
|
370
416
|
else:
|
|
371
417
|
fields = _tabular_fields(arr)
|
|
372
418
|
if fields is not None:
|
|
373
|
-
_encode_tabular(f"{att_prefix}.{fk} ", arr, fields, out, depth)
|
|
419
|
+
_encode_tabular(f"{att_prefix}.{fk} ", arr, fields, out, depth, opts)
|
|
374
420
|
else:
|
|
375
|
-
_encode_expanded(f"{att_prefix}.{fk} ", arr, out, depth)
|
|
421
|
+
_encode_expanded(f"{att_prefix}.{fk} ", arr, out, depth, opts)
|
|
376
422
|
|
|
377
423
|
|
|
378
424
|
def _encode_attachment_array_shared(
|
|
379
|
-
att_prefix: str, fk: str, arr: list, out: list[str], depth: int, shared_fields: list[str]
|
|
425
|
+
att_prefix: str, fk: str, arr: list, out: list[str], depth: int, shared_fields: list[str], opts: GenericOptions | None = None
|
|
380
426
|
) -> None:
|
|
381
427
|
if not arr:
|
|
382
428
|
out.append(f"{att_prefix}.{fk} [0]")
|
|
@@ -403,25 +449,29 @@ def _encode_attachment_array_shared(
|
|
|
403
449
|
out.append(f"{prefix}{'|'.join(cells)}")
|
|
404
450
|
else:
|
|
405
451
|
# Fields don't match: fall back to full encoding.
|
|
406
|
-
_encode_attachment_array(att_prefix, fk, arr, out, depth)
|
|
452
|
+
_encode_attachment_array(att_prefix, fk, arr, out, depth, opts)
|
|
407
453
|
|
|
408
454
|
|
|
409
|
-
def _encode_expanded(header_prefix: str, arr: list, out: list[str], depth: int) -> None:
|
|
455
|
+
def _encode_expanded(header_prefix: str, arr: list, out: list[str], depth: int, opts: GenericOptions | None = None) -> None:
|
|
456
|
+
if opts is None:
|
|
457
|
+
opts = GenericOptions()
|
|
410
458
|
prefix = _indent(depth)
|
|
411
459
|
out.append(f"{header_prefix}[{len(arr)}]")
|
|
412
460
|
for i, item in enumerate(arr):
|
|
413
461
|
if isinstance(item, dict):
|
|
414
462
|
out.append(f"{prefix}@{i} {{}}")
|
|
415
|
-
_encode_object(item, out, depth + 1)
|
|
463
|
+
_encode_object(item, out, depth + 1, opts)
|
|
416
464
|
elif isinstance(item, list):
|
|
417
|
-
_encode_expanded_array_item(prefix, i, item, out, depth)
|
|
465
|
+
_encode_expanded_array_item(prefix, i, item, out, depth, opts)
|
|
418
466
|
else:
|
|
419
467
|
out.append(f"{prefix}@{i} ={format_scalar(item)}")
|
|
420
468
|
|
|
421
469
|
|
|
422
470
|
def _encode_expanded_array_item(
|
|
423
|
-
prefix: str, idx: int, arr: list, out: list[str], depth: int
|
|
471
|
+
prefix: str, idx: int, arr: list, out: list[str], depth: int, opts: GenericOptions | None = None
|
|
424
472
|
) -> None:
|
|
473
|
+
if opts is None:
|
|
474
|
+
opts = GenericOptions()
|
|
425
475
|
if not arr:
|
|
426
476
|
out.append(f"{prefix}@{idx} [0]")
|
|
427
477
|
elif _all_primitives(arr):
|
|
@@ -430,9 +480,9 @@ def _encode_expanded_array_item(
|
|
|
430
480
|
else:
|
|
431
481
|
fields = _tabular_fields(arr)
|
|
432
482
|
if fields is not None:
|
|
433
|
-
_encode_tabular(f"{prefix}@{idx} ", arr, fields, out, depth + 1)
|
|
483
|
+
_encode_tabular(f"{prefix}@{idx} ", arr, fields, out, depth + 1, opts)
|
|
434
484
|
else:
|
|
435
|
-
_encode_expanded(f"{prefix}@{idx} ", arr, out, depth + 1)
|
|
485
|
+
_encode_expanded(f"{prefix}@{idx} ", arr, out, depth + 1, opts)
|
|
436
486
|
|
|
437
487
|
|
|
438
488
|
def _all_primitives(arr: list) -> bool:
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
Metadata-Version: 2.4
|
|
2
2
|
Name: gcf-python
|
|
3
|
-
Version: 2.2.
|
|
4
|
-
Summary:
|
|
3
|
+
Version: 2.2.1
|
|
4
|
+
Summary: The AI-native wire format for structured data. 50-92% fewer tokens than JSON. 100% comprehension on every frontier model. Zero dependencies.
|
|
5
5
|
Project-URL: Homepage, https://github.com/blackwell-systems/gcf-python
|
|
6
6
|
Project-URL: Documentation, https://blackwell-systems.github.io/gcf/
|
|
7
7
|
Project-URL: Specification, https://github.com/blackwell-systems/gcf
|
|
@@ -32,7 +32,7 @@ Description-Content-Type: text/markdown
|
|
|
32
32
|
|
|
33
33
|
Python implementation of [GCF](https://gcformat.com/) — the most token-efficient wire format for LLMs. A drop-in alternative to JSON and TOON for any structured data.
|
|
34
34
|
|
|
35
|
-
**100% comprehension on every frontier model tested.
|
|
35
|
+
**100% comprehension on every frontier model tested. 29% fewer tokens than TOON, 56% fewer than JSON across 16 datasets. 91.2% on structurally complex code graphs (vs TOON 68.2%, JSON 53.4%). 2,400+ LLM evaluations. Zero training.**
|
|
36
36
|
|
|
37
37
|
Docs: [gcformat.com](https://gcformat.com/) · [Playground](https://gcformat.com/playground.html) · [GCF vs TOON](https://gcformat.com/guide/vs-toon.html)
|
|
38
38
|
|
|
@@ -206,16 +206,16 @@ Works on dicts, lists, and primitives. Lists of uniform dicts get tabular rows.
|
|
|
206
206
|
|
|
207
207
|
## Benchmarks
|
|
208
208
|
|
|
209
|
-
|
|
209
|
+
2,400+ LLM evaluations across 10 models, 3 providers, and 51 independent test runs.
|
|
210
210
|
|
|
211
211
|
| | GCF | TOON | JSON |
|
|
212
212
|
|---|---|---|---|
|
|
213
|
-
| **Comprehension** (23 runs, 10 models) | **
|
|
213
|
+
| **Comprehension** (23 runs, 10 models) | **91.2%** | 68.2% | 53.4% |
|
|
214
214
|
| **Generation** (28 runs, 9 models) | **5/5** | 1.0/5 | 5.0/5 |
|
|
215
215
|
| **Input tokens** (500 symbols) | **11,090** | 16,378 | 53,341 |
|
|
216
216
|
| **Output tokens** (100 symbols) | **5,976** | 8,937 | 16,121 |
|
|
217
217
|
|
|
218
|
-
GCF wins
|
|
218
|
+
GCF wins 15/16 datasets on the expanded [token efficiency benchmark](https://github.com/blackwell-systems/toon/tree/gcf-comparison). Full results: [gcformat.com/guide/benchmarks](https://gcformat.com/guide/benchmarks.html)
|
|
219
219
|
|
|
220
220
|
## Implementations
|
|
221
221
|
|
|
@@ -236,7 +236,7 @@ GCF wins 13/15 datasets on the expanded [token efficiency benchmark](https://git
|
|
|
236
236
|
|
|
237
237
|
**Zero runtime dependencies. Permanently.** All six implementations depend only on their language's standard library. No transitive dependencies. No supply chain risk. This is a permanent commitment: GCF will never take on external runtime dependencies. MIT licensed. All implementations support both generic profile (`encodeGeneric`) and graph profile (`encode`). CLI included in all 6 languages.
|
|
238
238
|
|
|
239
|
-
**Specification:** [SPEC v3.
|
|
239
|
+
**Specification:** [SPEC v3.2 Stable](https://github.com/blackwell-systems/gcf/blob/main/SPEC.md) with 173 conformance fixtures, 43,000,000,000+ lossless round-trips verified across 5 formats and 6 languages. All implementations at v2.2.0+ (Go v1.3.0). Cross-language 6x6 matrix verified.
|
|
240
240
|
|
|
241
241
|
## License
|
|
242
242
|
|
|
@@ -1,19 +1,19 @@
|
|
|
1
|
-
gcf/__init__.py,sha256=
|
|
1
|
+
gcf/__init__.py,sha256=AlIvWioau3i54BViE2rZsNuXCpQKD9tzwA7_jOKq2u4,1776
|
|
2
2
|
gcf/__main__.py,sha256=EpvBz1yc8H0D5OJ1zy2tYke-kRzvudKa4DEbfeW14ao,71
|
|
3
3
|
gcf/cli.py,sha256=UEe1CAZn-rKGNIo_ap8-oez3ucl6DSRbsdv6RDnzygY,5256
|
|
4
4
|
gcf/constants.py,sha256=cmZ8YJSOB0im_eyfN8v4UvrLpBC6Fuf4cfcKZGbutxY,638
|
|
5
5
|
gcf/decode.py,sha256=nD8bXYhoeHQQ3LCeAJQOAgFuob-V_6us4mcBYtL_bBc,5978
|
|
6
|
-
gcf/decode_generic.py,sha256=
|
|
6
|
+
gcf/decode_generic.py,sha256=ZlFZqwenOzCnvbJijKscb6aQHoHQ81qoHBkaalVbqqo,26381
|
|
7
7
|
gcf/delta.py,sha256=f90UC6zejXH-ujyU_OViWDCqnxLXk3i6Qion-RJGHY4,1670
|
|
8
8
|
gcf/encode.py,sha256=CcqMSNmojrQAAw2X3MNfw8YR6l4rNw9hWDqwmf846oA,2929
|
|
9
|
-
gcf/generic.py,sha256=
|
|
9
|
+
gcf/generic.py,sha256=I06-vcVtcCg38X6uaoTMy7ipWiIFLaBMgQpTtuGvg2o,17763
|
|
10
10
|
gcf/scalar.py,sha256=MZay-KIROvaFHet-g2-pBghahT1bf_5bxZjG4yTZkSo,9329
|
|
11
11
|
gcf/session.py,sha256=6-wytNGaBkgqH7uTar7ojUFYNwIMeEVAZhuV-s-upZM,4704
|
|
12
12
|
gcf/stream.py,sha256=1Kt_a2daKpYHlWP1lnDJ4g549pUt9rc-U0xbARbXRKQ,5174
|
|
13
13
|
gcf/stream_generic.py,sha256=RnqqiPSu5joJa-7e58QbbzSGfvxBICA587A3aArjZvE,3250
|
|
14
14
|
gcf/types.py,sha256=AWm-LQoSqLHAYtEjcAxWQZqJ4JXqNreLUKO2mJFgNMA,1465
|
|
15
|
-
gcf_python-2.2.
|
|
16
|
-
gcf_python-2.2.
|
|
17
|
-
gcf_python-2.2.
|
|
18
|
-
gcf_python-2.2.
|
|
19
|
-
gcf_python-2.2.
|
|
15
|
+
gcf_python-2.2.1.dist-info/METADATA,sha256=izqgkRxKLUVqw5_sZqcs50i9kMAP3NRZnY8EuBDLVt8,9802
|
|
16
|
+
gcf_python-2.2.1.dist-info/WHEEL,sha256=mffPy8wBnZQn2VnJUU5jE99KsxaSfiyMHV9Yt0aLVxs,87
|
|
17
|
+
gcf_python-2.2.1.dist-info/entry_points.txt,sha256=aFT6gqlkh8iGfM8cblE-LUMxHH08_v71IIoZtDdRIVA,37
|
|
18
|
+
gcf_python-2.2.1.dist-info/licenses/LICENSE,sha256=2Fit9wnaIe--RMSAgyQqxC5hfZTyZqn4fIdBtp9qPDw,1072
|
|
19
|
+
gcf_python-2.2.1.dist-info/RECORD,,
|
|
File without changes
|
|
File without changes
|
|
File without changes
|