Skip to content

Commit e8fc6fd

Browse files
committed
Update failure reason
1 parent 4914d61 commit e8fc6fd

File tree

7 files changed

+52
-50
lines changed

7 files changed

+52
-50
lines changed

.gitignore

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
*.egg-info
44
__pycache__
55
.ipynb_checkpoints
6+
setup.py
67

78
# Temporary OS files
89
Icon*

CHANGELOG.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
# 0.6 (unreleased)
22

33
- Added a registration system for custom formatter classes.
4+
- Fixed loading of missing attribute from disk for ORM methods.
45

56
# 0.5.1 (2019-11-14)
67

datafiles/manager.py

Lines changed: 19 additions & 19 deletions
Original file line numberDiff line numberDiff line change
@@ -23,20 +23,19 @@
2323
Missing = dataclasses._MISSING_TYPE
2424

2525

26+
class HasDatafile(Protocol):
27+
datafile: Mapper
28+
29+
30+
class Splats:
31+
def __getattr__(self, name):
32+
return '*'
33+
34+
2635
class Manager:
2736
def __init__(self, cls):
2837
self.model = cls
2938

30-
def all(self) -> Iterator[HasDatafile]:
31-
root = Path(inspect.getfile(self.model)).parent
32-
pattern = str(root / self.model.Meta.datafile_pattern)
33-
splatted = pattern.format(self=Splats())
34-
log.info(f'Finding files matching pattern: {splatted}')
35-
for filename in iglob(splatted):
36-
log.debug(f'Found matching path: {filename}')
37-
results = parse(pattern, filename)
38-
yield self.get(*results.named.values())
39-
4039
def get(self, *args, **kwargs) -> HasDatafile:
4140
fields = dataclasses.fields(self.model)
4241
missing_args = [Missing] * (len(fields) - len(args) - len(kwargs))
@@ -62,6 +61,16 @@ def get_or_create(self, *args, **kwargs) -> HasDatafile:
6261
log.info(f"File not found, creating '{self.model.__name__}' object")
6362
return self.model(*args, **kwargs)
6463

64+
def all(self) -> Iterator[HasDatafile]:
65+
root = Path(inspect.getfile(self.model)).parent
66+
pattern = str(root / self.model.Meta.datafile_pattern)
67+
splatted = pattern.format(self=Splats())
68+
log.info(f'Finding files matching pattern: {splatted}')
69+
for filename in iglob(splatted):
70+
log.debug(f'Found matching path: {filename}')
71+
results = parse(pattern, filename)
72+
yield self.get(*results.named.values())
73+
6574
def filter(self, **query):
6675
for item in self.all():
6776
match = True
@@ -70,12 +79,3 @@ def filter(self, **query):
7079
match = False
7180
if match:
7281
yield item
73-
74-
75-
class HasDatafile(Protocol):
76-
datafile: Mapper
77-
78-
79-
class Splats:
80-
def __getattr__(self, name):
81-
return '*'

datafiles/tests/test_manager.py

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -21,12 +21,6 @@ def manager():
2121
model = create_model(MyClass, pattern='files/{self.foo}.yml')
2222
return Manager(model)
2323

24-
def describe_all():
25-
@patch('datafiles.mapper.Mapper.exists', False)
26-
def when_no_files_exist(expect, manager):
27-
items = list(manager.all())
28-
expect(items) == []
29-
3024
def describe_get_or_none():
3125
@patch('datafiles.mapper.Mapper.load')
3226
@patch('datafiles.mapper.Mapper.exists', True)
@@ -55,6 +49,12 @@ def when_file_missing(mock_save, expect, manager):
5549
expect(manager.get_or_create(foo=1, bar=2)) == MyClass(foo=1, bar=2)
5650
expect(mock_save.called) == True
5751

52+
def describe_all():
53+
@patch('datafiles.mapper.Mapper.exists', False)
54+
def when_no_files_exist(expect, manager):
55+
items = list(manager.all())
56+
expect(items) == []
57+
5858
def describe_filter():
5959
@patch('datafiles.mapper.Mapper.exists', False)
6060
def when_no_files_exist(expect, manager):

docs/api/manager.md

Lines changed: 23 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -14,29 +14,6 @@ class MyModel:
1414

1515
Many of the following examples are also shown in this [Jupyter Notebook](https://github.com/jacebrowning/datafiles/blob/develop/notebooks/manager_api.ipynb).
1616

17-
# `all()`
18-
19-
Iterate over all objects matching the pattern:
20-
21-
```python
22-
>>> generator = MyModel.objects.all()
23-
>>> list(generator)
24-
[]
25-
```
26-
27-
```python
28-
>>> m1 = MyModel('foo')
29-
>>> m2 = MyModel('bar', 42)
30-
```
31-
32-
```python
33-
>>> for m in MyModel.objects.all():
34-
... print(m)
35-
...
36-
MyModel(my_key='foo' my_value=0)
37-
MyModel(my_key='bar', my_value=42)
38-
```
39-
4017
# `get_or_none()`
4118

4219
Instantiate an object from an existing file or return `None` if no matching file exists:
@@ -73,6 +50,29 @@ MyModel(my_key='foo', my_value=42)
7350
MyModel(my_key='bar', my_value=0)
7451
```
7552

53+
# `all()`
54+
55+
Iterate over all objects matching the pattern:
56+
57+
```python
58+
>>> generator = MyModel.objects.all()
59+
>>> list(generator)
60+
[]
61+
```
62+
63+
```python
64+
>>> m1 = MyModel('foo')
65+
>>> m2 = MyModel('bar', 42)
66+
```
67+
68+
```python
69+
>>> for m in MyModel.objects.all():
70+
... print(m)
71+
...
72+
MyModel(my_key='foo' my_value=0)
73+
MyModel(my_key='bar', my_value=42)
74+
```
75+
7676
# `filter()`
7777

7878
Iterate all objects matching the pattern with additional required attribute values:

pyproject.toml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
11
[tool.poetry]
22

33
name = "datafiles"
4-
version = "0.6b2"
4+
version = "0.6b3"
55
description = "File-based ORM for dataclasses."
66

77
license = "MIT"

tests/test_orm_usage.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -71,7 +71,7 @@ class Bar:
7171
expect(bar.nested.value) == 2
7272

7373

74-
@pytest.mark.xfail(reason='https://github.com/jacebrowning/datafiles/issues/139')
74+
@pytest.mark.xfail(reason='https://github.com/jacebrowning/datafiles/issues/147')
7575
def test_values_are_filled_from_disk(expect):
7676
InventoryItem.objects.get_or_create(42, "Things", 0.99)
7777

0 commit comments

Comments
 (0)