Skip to content

Commit 2367365

Browse files
committed
Merge branch 'dev'
2 parents adc45e7 + b2e344a commit 2367365

34 files changed

Lines changed: 1746 additions & 50 deletions

.gitmodules

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,3 +1,6 @@
11
[submodule "lib/forge-std"]
22
path = lib/forge-std
33
url = https://github.com/foundry-rs/forge-std
4+
[submodule "lib/solady"]
5+
path = lib/solady
6+
url = https://github.com/vectorized/solady

Makefile

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
tree:
2+
@python3 convert_trees.py test/unit
3+
4+
gen:
5+
@python3 convert_trees.py test/unit
6+
@find test/unit -type f -name "*.tree" \
7+
! -size 0c \
8+
! -exec test -f "$$(dirname "{}")/$$(basename "{}" .tree).t.sol" \; \
9+
-exec sh -c 'if grep -q "[A-Za-z]" "$$1"; then bulloak scaffold -S -w -s 0.8.30 "$$1"; fi' _ {} \;
10+
11+
check:
12+
@python3 convert_trees.py test/unit
13+
@bulloak check test/unit
14+
15+
fix:
16+
@python3 convert_trees.py test/unit
17+
@find test/unit -type f -name "*.tree" -exec bulloak check --fix {} \;
18+
19+
coverage:
20+
@forge coverage --report lcov

README.md

Lines changed: 44 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -1,66 +1,68 @@
1-
## Foundry
21

3-
**Foundry is a blazing fast, portable and modular toolkit for Ethereum application development written in Rust.**
2+
# Lending & Borrowing Protocol
43

5-
Foundry consists of:
4+
ZToken Protocol is a modular lending and borrowing system built with Foundry. It supports ERC20 and native-asset markets, interest rate modeling, and collateralized lending mechanics.
65

7-
- **Forge**: Ethereum testing framework (like Truffle, Hardhat and DappTools).
8-
- **Cast**: Swiss army knife for interacting with EVM smart contracts, sending transactions and getting chain data.
9-
- **Anvil**: Local Ethereum node, akin to Ganache, Hardhat Network.
10-
- **Chisel**: Fast, utilitarian, and verbose solidity REPL.
6+
## Overview
117

12-
## Documentation
8+
Core contracts live in `src/` and are composed around a base ZToken implementation with ERC20 and native-asset market variants plus collateral and liquidation management.
139

14-
https://book.getfoundry.sh/
10+
## Contracts
1511

16-
## Usage
12+
- `ZToken` – Base interest-bearing token
13+
- `ZErc20` / `ZNative` – ERC20 and native-asset market implementations
14+
- `CollateralManager` – Collateral deposits, limits, and liquidation flows
15+
- `LiquidationManger` – Liquidation execution logic
16+
- `ZTokenFactory` – Market deployment and setup
1717

18-
### Build
18+
## Repo Layout
1919

20-
```shell
21-
$ forge build
22-
```
20+
- `src/` – Solidity contracts
21+
- `src/interfaces/` – External interfaces
22+
- `src/libraries/` – Math and helpers
23+
- `test/` – Foundry tests
24+
- `script/` – Deployment / utility scripts
25+
- `docs/` – mdBook documentation
2326

24-
### Test
27+
## Quickstart
2528

26-
```shell
27-
$ forge test
28-
```
29+
```zsh
30+
# Install dependencies
31+
forge install
2932

30-
### Format
31-
32-
```shell
33-
$ forge fmt
33+
# Build contracts
34+
forge build
3435
```
3536

36-
### Gas Snapshots
37+
## Make Targets
3738

38-
```shell
39-
$ forge snapshot
40-
```
39+
```zsh
40+
# Convert bulloak trees for unit tests
41+
make tree
4142

42-
### Anvil
43+
# Generate scaffolds for missing test files
44+
make gen
4345

44-
```shell
45-
$ anvil
46-
```
46+
# Check test trees
47+
make check
4748

48-
### Deploy
49+
# Auto-fix tree check issues
50+
make fix
4951

50-
```shell
51-
$ forge script script/Counter.s.sol:CounterScript --rpc-url <your_rpc_url> --private-key <your_private_key>
52+
# Coverage report
53+
make coverage
5254
```
5355

54-
### Cast
56+
## Documentation
57+
58+
The mdBook source lives in `docs/`. To build and serve locally:
5559

56-
```shell
57-
$ cast <subcommand>
60+
```zsh
61+
mdbook build docs
62+
mdbook serve docs -p 3000
5863
```
5964

60-
### Help
65+
## Notes
6166

62-
```shell
63-
$ forge --help
64-
$ anvil --help
65-
$ cast --help
66-
```
67+
- Contract docs in `docs/src/src/` are generated from the Solidity sources.
68+
- Use `foundry.toml` for compiler and remapping configuration.

convert_trees.py

Lines changed: 104 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,104 @@
1+
import os
2+
import sys
3+
4+
ASCII_SIGNS = ("├──", "└──", "│")
5+
6+
def is_ascii_tree_line(line: str) -> bool:
7+
"""Return True if the line is already part of an ASCII tree."""
8+
return line.strip().startswith(ASCII_SIGNS)
9+
10+
def parse_tree(lines):
11+
"""Build a nested tree structure based on '#' indentation."""
12+
tree = []
13+
stack = [(-1, tree)]
14+
for line in lines:
15+
if not line.strip():
16+
continue
17+
level = line.count('#')
18+
text = line.replace('#', '').strip()
19+
while level <= stack[-1][0]:
20+
stack.pop()
21+
node = {"text": text, "children": []}
22+
stack[-1][1].append(node)
23+
stack.append((level, node["children"]))
24+
return tree
25+
26+
def render_ascii(nodes, prefix=""):
27+
"""Recursively render tree nodes as ASCII."""
28+
lines = []
29+
for i, node in enumerate(nodes):
30+
connector = "└── " if i == len(nodes) - 1 else "├── "
31+
lines.append(prefix + connector + node["text"])
32+
if node["children"]:
33+
extension = " " if i == len(nodes) - 1 else "│ "
34+
lines.extend(render_ascii(node["children"], prefix + extension))
35+
return lines
36+
37+
def convert_section(section_lines):
38+
"""Convert only the #-based part of one section into ASCII."""
39+
if not section_lines:
40+
return section_lines
41+
42+
header = section_lines[0].strip()
43+
body = [l for l in section_lines[1:] if l.strip().startswith("#")]
44+
if not body:
45+
# nothing to convert
46+
return section_lines
47+
48+
tree = parse_tree(body)
49+
ascii_tree = render_ascii(tree)
50+
return [header] + ascii_tree + [""]
51+
52+
def convert_file(filepath):
53+
"""Convert only unformatted (#-based) sections in a .tree file."""
54+
with open(filepath, "r", encoding="utf-8") as f:
55+
raw = [line.rstrip("\n") for line in f.readlines()]
56+
57+
# If the entire file is already ASCII, skip it.
58+
if all(is_ascii_tree_line(l) or not l.strip() or "::" in l for l in raw):
59+
print(f"Skipped (already formatted): {filepath}")
60+
return
61+
62+
new_content = []
63+
current_section = []
64+
65+
def flush_section():
66+
if current_section:
67+
if any("#" in l for l in current_section):
68+
new_content.extend(convert_section(current_section))
69+
else:
70+
new_content.extend(current_section)
71+
current_section.clear()
72+
73+
for line in raw:
74+
if "::" in line and not line.strip().startswith("#"):
75+
flush_section()
76+
current_section.append(line)
77+
else:
78+
current_section.append(line)
79+
flush_section()
80+
81+
with open(filepath, "w", encoding="utf-8") as f:
82+
f.write("\n".join(new_content).strip() + "\n")
83+
84+
print(f"Updated: {filepath}")
85+
86+
def convert_all(folder):
87+
"""Convert all .tree files recursively."""
88+
for root, _, files in os.walk(folder):
89+
for file in files:
90+
if file.endswith(".tree"):
91+
convert_file(os.path.join(root, file))
92+
print("\\Incremental conversion complete!")
93+
94+
if __name__ == "__main__":
95+
if len(sys.argv) < 2:
96+
print("Usage: python3 convert_trees_incremental_fixed.py <path/to/folder>")
97+
sys.exit(1)
98+
99+
folder = sys.argv[1]
100+
if not os.path.isdir(folder):
101+
print("Invalid folder path.")
102+
sys.exit(1)
103+
104+
convert_all(folder)

foundry.lock

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4,5 +4,11 @@
44
"name": "v1.11.0",
55
"rev": "8e40513d678f392f398620b3ef2b418648b33e89"
66
}
7+
},
8+
"lib/solady": {
9+
"tag": {
10+
"name": "v0.1.26",
11+
"rev": "acd959aa4bd04720d640bf4e6a5c71037510cc4b"
12+
}
713
}
814
}

images/contract-interaction.png

346 KB
Loading

design.mmd renamed to images/design.mmd

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -31,3 +31,4 @@ graph TD
3131
AM --> AN[Borrower Redeems Collateral]
3232
AN --> AO[Exit]
3333
AL -->|Continue Borrowing| AG
34+

images/user-interaction.png

820 KB
Loading

0 commit comments

Comments
 (0)