aboutsummaryrefslogtreecommitdiffstats
path: root/docs/design
diff options
context:
space:
mode:
authoreunhhu <[email protected]>2026-10-04 13:30:31 +0100
committereunhhu <[email protected]>2026-10-04 13:30:31 +0100
commitfafed7edaf36ba18c200d395bd229d1f071cd409 (patch)
tree9181a75677c7744c80c03f4609c1b47b50c511d6 /docs/design
parent57804c158610996433dc57b31b6d05938a292ec7 (diff)
downloadaup-fafed7edaf36ba18c200d395bd229d1f071cd409.tar.gz
aup-fafed7edaf36ba18c200d395bd229d1f071cd409.zip
Declare transient state: held while the app runs, never stored (Pure 018)
Diffstat (limited to 'docs/design')
-rw-r--r--docs/design/001-language-v0.md4
-rw-r--r--docs/design/002-dsl-direction.md38
2 files changed, 40 insertions, 2 deletions
diff --git a/docs/design/001-language-v0.md b/docs/design/001-language-v0.md
index 7694188..1e11f6b 100644
--- a/docs/design/001-language-v0.md
+++ b/docs/design/001-language-v0.md
@@ -1,6 +1,6 @@
# aup v0 — 한 언어, 한 모듈 형식
-2026-09-25. 상태: v0a(scalar), v0b(바이트·영속 문서·text·커서), v0c(레코드·리스트·인덱스·조건식·표 보기·fn·use·라이브러리의 레코드·`bool`·`i64`) 구현.
+2026-09-25. 상태: v0a(scalar), v0b(바이트·영속 문서·text·커서), v0c(레코드·리스트·인덱스·조건식·표 보기·fn·use·라이브러리의 레코드·`bool`·`i64`·`transient state`) 구현.
text와 리스트 문법은 [002](002-dsl-direction.md).
착수 기준:
@@ -49,7 +49,7 @@ on frame { # 1/60초 진행. 핸들러 안에서 dt를 쓸
- 선언과 문장은 줄바꿈이나 `;`로 끝난다. 이름은 ASCII `[A-Za-z_][A-Za-z_0-9]*`, 31바이트 이하다.
- 예약어: `state input view on if else key frame dt min max clamp message by bytes u32 reply require record each fn use now
- every floor output send for let true false`.
+ every floor output send for let true false transient`.
- 키: `Space Enter ArrowLeft ArrowRight ArrowUp ArrowDown KeyA..KeyZ Digit0..Digit9`. 입력 이름과
키는 각각 한 번만 쓴다. 상태·입력·보기의 이름공간은 서로 겹칠 수 없다.
- 식: 숫자, `true`·`false`, 상태 이름, `dt`(핸들러 안에서만), 괄호, 단항 `- !`, 이항 `* /`, `+ -`,
diff --git a/docs/design/002-dsl-direction.md b/docs/design/002-dsl-direction.md
index f59019f..a226bc8 100644
--- a/docs/design/002-dsl-direction.md
+++ b/docs/design/002-dsl-direction.md
@@ -303,6 +303,44 @@ view golds = count(u in users where store.rank(u.points) == "gold")
- 값을 이름이 아니라 선언으로 맞추는 까닭: 쓰이지 않아 모듈에 없는 다른 라이브러리의 같은 이름 레코드가, 이름만 같아서 리스트에
들어가는 일을 막는다.
+### 상태의 수명: transient (구현)
+
+Pure [018](/srv/git/pure.git)의 1단계다. 지금까지 모든 `state`는 저장됐다. 접속 수, 캐시, 계산의 중간값처럼 다시 시작한 뒤에는
+뜻이 없는 상태도 커밋마다 저장소에 썼다. 이제 값의 수명은 선언이 말한다.
+
+```text
+state visits = 0 # 저장한다: 다시 시작해도 남는다
+transient state online = 0 # 앱이 도는 동안만: 저장하지 않고, 다시 시작하면 초기값
+transient state recent: list of Hit
+transient state status: text = "idle"
+transient state picked: index of tasks # 저장되는 리스트의 저장되지 않는 선택
+on tap.down {
+ let n = online + 1 # 이벤트의 값: 이벤트가 끝나면 없다
+ online = n
+}
+```
+
+| | 실패한 이벤트 | 저장소 | 다시 시작하면 | 모듈을 바꾸면 |
+|---|---|---|---|---|
+| `state` | 되돌린다 | 쓴다 | 저장된 값 | 이름으로 잇는다 |
+| `transient state` | 되돌린다 | 쓰지 않는다 | 초기값 | 이름으로 잇는다 |
+| `let` | 버린다 | 없다 | — | — |
+
+- **`transient state`** 는 모든 상태 타입에 쓴다(수, bool, i64, text, 커서, 리스트, 인덱스). 보기, 이벤트, 되돌리기, 메모리 예산,
+ 스냅숏의 읽기에서는 다른 상태와 같다. 다른 것은 저장소뿐이다: 그것만 바꾼 이벤트는 저장소에 아무것도 쓰지 않는다.
+- 저장되는 커서나 인덱스는 transient text나 리스트를 가리키지 못한다(다시 시작하면 가리키던 것이 비어 있다). transient 커서나
+ 인덱스는 저장되는 것을 가리켜도 된다.
+- 모듈의 상태 타입 워드에 비트 하나다(Pure 008). transient가 없는 앱의 모듈은 바이트 그대로 지금과 같다.
+- 모듈을 바꿀 때(`aup watch`, 호스트의 SIGHUP) 저장되던 상태를 transient로, 또는 그 반대로 바꿀 수 있다. 저장소에 남은 옛 값은
+ 버린 상태의 것처럼 다룬다.
+- `transient`는 예약어다.
+
+검증(`tests/check.py`의 `transients`와 진단 5건, Pure의 `test-module`과 `server_transient`): 같은 앱의 transient 판과 저장 판의
+모듈이 상태 타입 워드 세 바이트만 다르다. 같은 저장 이벤트(`tap`) 사이에 transient만 바꾸는 이벤트와 실패하는 이벤트를 섞은 실행의
+저장소가, 섞지 않은 실행의 저장소와 파일과 바이트까지 같다. 다시 열면 transient는 초기값이고 저장되는 것은 그대로다. 달리는 동안
+모듈을 바꿔 저장되던 것을 transient로, transient를 저장되는 것으로 바꾸면 다시 열었을 때 바뀐 대로다. `pure-serve`에서 transient만
+바꾸는 요청 100개가 저장소의 어떤 파일도 바꾸지 않고, `kill -9` 뒤에 다시 띄우면 transient는 초기값이다.
+
### 시간
```text