dotted-notation 0.49.3__tar.gz → 0.49.4__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.
Files changed (48) hide show
  1. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/CHANGELOG.md +9 -0
  2. {dotted_notation-0.49.3/dotted_notation.egg-info → dotted_notation-0.49.4}/PKG-INFO +1 -1
  3. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/recursive.py +8 -5
  4. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/wrappers.py +6 -4
  5. {dotted_notation-0.49.3 → dotted_notation-0.49.4/dotted_notation.egg-info}/PKG-INFO +1 -1
  6. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/pyproject.toml +1 -1
  7. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/LICENSE +0 -0
  8. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/MANIFEST.in +0 -0
  9. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/README.md +0 -0
  10. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/__init__.py +0 -0
  11. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/__main__.py +0 -0
  12. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/access.pxd +0 -0
  13. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/access.py +0 -0
  14. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/api.py +0 -0
  15. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/base.pxd +0 -0
  16. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/base.py +0 -0
  17. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/cli/__init__.py +0 -0
  18. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/cli/_compat.py +0 -0
  19. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/cli/formats.py +0 -0
  20. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/cli/main.py +0 -0
  21. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/containers.py +0 -0
  22. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/engine.pxd +0 -0
  23. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/engine.py +0 -0
  24. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/filters.pxd +0 -0
  25. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/filters.py +0 -0
  26. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/grammar.py +0 -0
  27. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/groups.pxd +0 -0
  28. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/groups.py +0 -0
  29. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/matchers.pxd +0 -0
  30. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/matchers.py +0 -0
  31. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/native.py +0 -0
  32. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/predicates.py +0 -0
  33. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/recursive.pxd +0 -0
  34. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/results.py +0 -0
  35. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/sql/__init__.py +0 -0
  36. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/sql/core.py +0 -0
  37. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/sql/pg.py +0 -0
  38. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/transforms.py +0 -0
  39. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/utils.py +0 -0
  40. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/utypes.py +0 -0
  41. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted/wrappers.pxd +0 -0
  42. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted_notation.egg-info/SOURCES.txt +0 -0
  43. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted_notation.egg-info/dependency_links.txt +0 -0
  44. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted_notation.egg-info/entry_points.txt +0 -0
  45. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted_notation.egg-info/requires.txt +0 -0
  46. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/dotted_notation.egg-info/top_level.txt +0 -0
  47. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/setup.cfg +0 -0
  48. {dotted_notation-0.49.3 → dotted_notation-0.49.4}/setup.py +0 -0
@@ -3,6 +3,15 @@
3
3
  All notable changes to `dotted` are recorded here. Versions prior to
4
4
  the ones listed are omitted — browse git history for earlier entries.
5
5
 
6
+ ## [0.49.4]
7
+
8
+ ### Fixed
9
+ - `update` through `~` around a filtered or recursive op,
10
+ `[(~*&k=v#, +)]` or `~*a.x`, raised `TypeError` once something
11
+ matched (#65). It now keeps what the `~` matches as it is and, as
12
+ elsewhere, still updates the path after it: `[(~*&k=1#, +)].x`
13
+ updates `x` in the matching items.
14
+
6
15
  ## [0.49.3]
7
16
 
8
17
  ### Added
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: dotted_notation
3
- Version: 0.49.3
3
+ Version: 0.49.4
4
4
  Summary: Dotted notation for safe nested data traversal with optional chaining, pattern matching, and transforms
5
5
  Author-email: Frey Waid <logophage1@gmail.com>
6
6
  License-Expression: MIT
@@ -400,7 +400,7 @@ class Recursive(BaseOp):
400
400
  node[k] = v
401
401
  return node
402
402
 
403
- def _update_recursive(self, ops, node, val, has_defaults, _path, nop, depth=0, guard=None, seen=frozenset(), settings=base.SETTINGS):
403
+ def _update_recursive(self, ops, node, val, has_defaults, _path, nop, depth=0, guard=None, seen=frozenset(), settings=base.SETTINGS, nop_from_unwrap=False):
404
404
  node_id = id(node)
405
405
  if node_id in seen:
406
406
  return node
@@ -411,7 +411,8 @@ class Recursive(BaseOp):
411
411
 
412
412
  for acc, k, v in items:
413
413
  # Recurse first (bottom-up)
414
- v = self._update_recursive(ops, v, val, has_defaults, _path, nop, depth + 1, guard, seen, settings=settings)
414
+ v = self._update_recursive(ops, v, val, has_defaults, _path, nop, depth + 1, guard, seen, settings=settings,
415
+ nop_from_unwrap=nop_from_unwrap)
415
416
  node = self._assign(acc, node, k, v)
416
417
  if self.filters and not any(True for _ in self.filtered((v,), settings)):
417
418
  continue
@@ -421,13 +422,15 @@ class Recursive(BaseOp):
421
422
  if guard and not guard(v):
422
423
  continue
423
424
  if ops:
424
- node = self._assign(acc, node, k, engine.updates(ops, v, val, has_defaults, _path + [(self, k)], nop, settings=settings))
425
+ # a ~ on this op holds back only this op, not the ops after it
426
+ pass_nop = nop and not nop_from_unwrap
427
+ node = self._assign(acc, node, k, engine.updates(ops, v, val, has_defaults, _path + [(self, k)], pass_nop, settings=settings))
425
428
  elif not nop:
426
429
  node = self._assign(acc, node, k, val)
427
430
  return node
428
431
 
429
- def do_update(self, ops, node, val, has_defaults, _path, nop, settings=base.SETTINGS):
430
- return self._update_recursive(ops, node, val, has_defaults, _path, nop, settings=settings)
432
+ def do_update(self, ops, node, val, has_defaults, _path, nop, nop_from_unwrap=False, settings=base.SETTINGS):
433
+ return self._update_recursive(ops, node, val, has_defaults, _path, nop, settings=settings, nop_from_unwrap=nop_from_unwrap)
431
434
 
432
435
  def _remove_recursive(self, ops, node, val, nop, depth=0, guard=None, seen=frozenset(), settings=base.SETTINGS):
433
436
  node_id = id(node)
@@ -314,7 +314,7 @@ class TransformWrap(Wrap):
314
314
  val = self.apply(val, settings)
315
315
  except base.UnresolvedReference:
316
316
  return node
317
- return self.inner.do_update(ops, node, val, has_defaults, _path, nop, settings=settings)
317
+ return self.inner.do_update(ops, node, val, has_defaults, _path, nop, nop_from_unwrap=nop_from_unwrap, settings=settings)
318
318
 
319
319
  def do_remove(self, ops, node, val, nop, settings=base.SETTINGS):
320
320
  return self.inner.do_remove(ops, node, val, nop, settings=settings)
@@ -543,7 +543,8 @@ class ValueGuard(Wrap):
543
543
  nop = self._nop(nop)
544
544
  if self.inner.is_recursive():
545
545
  return self.inner._update_recursive(
546
- ops, node, val, has_defaults, _path, nop, guard=self._guard(settings), settings=settings)
546
+ ops, node, val, has_defaults, _path, nop, guard=self._guard(settings), settings=settings,
547
+ nop_from_unwrap=nop_from_unwrap)
547
548
  if not ops and not nop:
548
549
  # the leaf: upsert() has no settings, and the guard needs them
549
550
  for k in list(self.keys(node, settings=settings)):
@@ -788,8 +789,9 @@ class FilterWrap(Wrap):
788
789
  return self
789
790
  return FilterWrap(new_inner, new_filters)
790
791
 
791
- def do_update(self, ops, node, val, has_defaults, _path, nop, settings=base.SETTINGS):
792
- return access.BaseOp.do_update(self, ops, node, val, has_defaults, _path, nop, settings=settings)
792
+ def do_update(self, ops, node, val, has_defaults, _path, nop, nop_from_unwrap=False, settings=base.SETTINGS):
793
+ return access.BaseOp.do_update(
794
+ self, ops, node, val, has_defaults, _path, nop, nop_from_unwrap=nop_from_unwrap, settings=settings)
793
795
 
794
796
  def do_remove(self, ops, node, val, nop, settings=base.SETTINGS):
795
797
  return access.BaseOp.do_remove(self, ops, node, val, nop, settings=settings)
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: dotted_notation
3
- Version: 0.49.3
3
+ Version: 0.49.4
4
4
  Summary: Dotted notation for safe nested data traversal with optional chaining, pattern matching, and transforms
5
5
  Author-email: Frey Waid <logophage1@gmail.com>
6
6
  License-Expression: MIT
@@ -6,7 +6,7 @@ build-backend = "setuptools.build_meta"
6
6
 
7
7
  [project]
8
8
  name = "dotted_notation"
9
- version = "0.49.3"
9
+ version = "0.49.4"
10
10
  description = "Dotted notation for safe nested data traversal with optional chaining, pattern matching, and transforms"
11
11
  readme = "README.md"
12
12
  requires-python = ">=3.6"