@valbuild/server 0.130.0 → 0.131.0
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.
package/CHANGELOG.md
CHANGED
|
@@ -1,5 +1,76 @@
|
|
|
1
1
|
# @valbuild/server
|
|
2
2
|
|
|
3
|
+
## 0.131.0
|
|
4
|
+
|
|
5
|
+
### Minor Changes
|
|
6
|
+
|
|
7
|
+
- [#686](https://github.com/valbuild/val/pull/686) [`0d5857b`](https://github.com/valbuild/val/commit/0d5857b731e11f7e6a011f79297df6485908c31f) Thanks [@freekh](https://github.com/freekh)! - Say `VAL_MODE=memory` where there is no disk, and get a sentence instead of an `EPERM`
|
|
8
|
+
|
|
9
|
+
Memory mode — the one for a host that holds the project's source itself — is
|
|
10
|
+
selected by passing `sourceFiles`, and it has to be: nothing in an environment
|
|
11
|
+
can supply a project's source, so a mode that an env var could switch on would
|
|
12
|
+
be a server with no content in it.
|
|
13
|
+
|
|
14
|
+
The cost was the failure when a host forgot. Val inferred `fs` mode, `fs` mode
|
|
15
|
+
went looking for a working tree, and in a Worker isolate the first thing to
|
|
16
|
+
touch the disk failed:
|
|
17
|
+
|
|
18
|
+
```
|
|
19
|
+
patch-error /bundle/.val/patches.lock: EPERM
|
|
20
|
+
```
|
|
21
|
+
|
|
22
|
+
That names a path two layers below the decision that caused it, and nobody
|
|
23
|
+
reading it would guess "your server was configured for the wrong mode".
|
|
24
|
+
|
|
25
|
+
So an environment can now DECLARE that it has no disk:
|
|
26
|
+
|
|
27
|
+
```
|
|
28
|
+
VAL_MODE=memory
|
|
29
|
+
```
|
|
30
|
+
|
|
31
|
+
It does not turn memory mode on. It says the host is supposed to be supplying
|
|
32
|
+
`sourceFiles`, so if none arrive, Val refuses at configuration time and says
|
|
33
|
+
where to pass them. `VAL_MODE=` counts as unset, the way a shell means it; any
|
|
34
|
+
other value is refused rather than ignored, since leaving you in `fs` mode is
|
|
35
|
+
the exact failure this is meant to catch.
|
|
36
|
+
|
|
37
|
+
**`initValContent` takes the same options, and this is the release that
|
|
38
|
+
noticed.** It builds a Val server of its own — these readers resolve content by
|
|
39
|
+
asking it, not by calling the API over HTTP — so configuring `initValServer`
|
|
40
|
+
alone left them inferring `fs` mode. On a host with no filesystem that is a
|
|
41
|
+
reader looking for a working tree that is not there; it went unnoticed because
|
|
42
|
+
published reads still worked.
|
|
43
|
+
|
|
44
|
+
```ts
|
|
45
|
+
const patchStore = new InMemoryPatchStore(); // now exported from this package
|
|
46
|
+
|
|
47
|
+
const { valApiHandler, draftMode } = initValServer(valModules, config, {
|
|
48
|
+
sourceFiles: FILES,
|
|
49
|
+
patchStore,
|
|
50
|
+
unsafelyAllowUnauthenticated: true,
|
|
51
|
+
});
|
|
52
|
+
|
|
53
|
+
const { fetchValStega } = initValContent(config, valModules, {
|
|
54
|
+
draftMode,
|
|
55
|
+
// The same three. Two patch stores are two sets of pending edits, and a
|
|
56
|
+
// reader that checks a session the host never issues answers itself 401 and
|
|
57
|
+
// falls back to published content — a draft render showing the live site.
|
|
58
|
+
sourceFiles: FILES,
|
|
59
|
+
patchStore,
|
|
60
|
+
unsafelyAllowUnauthenticated: true,
|
|
61
|
+
});
|
|
62
|
+
```
|
|
63
|
+
|
|
64
|
+
All three are optional. Left out, this reader gets its own store and its own
|
|
65
|
+
answer about authentication, which is right for published content.
|
|
66
|
+
|
|
67
|
+
`@valbuild/next` has no memory mode: its `initValServer` takes neither option,
|
|
68
|
+
so for a Next app `VAL_MODE=memory` names an environment Val cannot serve from,
|
|
69
|
+
and the error says so.
|
|
70
|
+
|
|
71
|
+
Nothing changes for an app that sets none of this: `http` when `VAL_API_KEY`
|
|
72
|
+
and `VAL_SECRET` are both present, `fs` otherwise, as before.
|
|
73
|
+
|
|
3
74
|
## 0.130.0
|
|
4
75
|
|
|
5
76
|
### Minor Changes
|
|
@@ -61,6 +61,11 @@ type ValServerOverrides = Partial<{
|
|
|
61
61
|
* and "proxy" this one cannot be inferred from the environment -- there is
|
|
62
62
|
* nothing to infer it FROM, and a mode that can be turned on without
|
|
63
63
|
* supplying the source would be a server with no content in it.
|
|
64
|
+
*
|
|
65
|
+
* An environment that has no disk can still say it EXPECTS this, by setting
|
|
66
|
+
* `VAL_MODE=memory`. That does not select the mode; it makes forgetting to
|
|
67
|
+
* pass the source an error here rather than an `EPERM` from `fs` mode two
|
|
68
|
+
* layers down.
|
|
64
69
|
*/
|
|
65
70
|
sourceFiles: Record<string, string>;
|
|
66
71
|
/**
|
|
@@ -10103,6 +10103,31 @@ async function initHandlerOptions(route, opts, config) {
|
|
|
10103
10103
|
config
|
|
10104
10104
|
};
|
|
10105
10105
|
}
|
|
10106
|
+
/*
|
|
10107
|
+
* `VAL_MODE=memory` says the host MEANT to hold the source, and did not.
|
|
10108
|
+
*
|
|
10109
|
+
* It cannot SELECT memory mode -- nothing in the environment can supply
|
|
10110
|
+
* `sourceFiles`, and a mode turned on without them is a server with no
|
|
10111
|
+
* content in it. What it does is turn the fall-through into an error.
|
|
10112
|
+
*
|
|
10113
|
+
* Without it, a host that forgot to pass its source got `fs` mode, and `fs`
|
|
10114
|
+
* mode in a Worker isolate reaches for a working tree that is not there: the
|
|
10115
|
+
* failure is an `EPERM` on `.val/patches.lock`, several layers below the
|
|
10116
|
+
* mistake, naming a path rather than the decision that led to it. Every
|
|
10117
|
+
* environment that runs Val without a disk can set this once and get a
|
|
10118
|
+
* sentence instead.
|
|
10119
|
+
*/
|
|
10120
|
+
const declaredMode = process.env.VAL_MODE;
|
|
10121
|
+
if (declaredMode === "memory") {
|
|
10122
|
+
throw new Error("VAL_MODE is 'memory', but no `sourceFiles` were given here, so there " + "is no source to serve. Memory mode cannot be turned on by the " + "environment: it needs the project's own source, and only the host " + "that holds it can hand it over. On TanStack Start that is the " + "`sourceFiles` option, passed to `initValServer` AND to " + "`initValContent`, which has a Val server of its own and is " + "configured separately. @valbuild/next has no memory mode yet, so " + "for a Next app this variable is set on an environment Val cannot " + "serve from. Unset " + "VAL_MODE to go back to the inferred mode instead ('http' when " + "VAL_API_KEY and VAL_SECRET are both set, 'fs' otherwise).");
|
|
10123
|
+
}
|
|
10124
|
+
// An empty value counts as unset, which is what `VAL_MODE=` in a shell or a
|
|
10125
|
+
// CI settings page means. Every other value is refused rather than ignored:
|
|
10126
|
+
// ignoring `VAL_MODE=memry` would leave the app in `fs` mode, which is the
|
|
10127
|
+
// exact failure this variable exists to catch.
|
|
10128
|
+
if (declaredMode !== undefined && declaredMode !== "") {
|
|
10129
|
+
throw new Error(`VAL_MODE is '${declaredMode}', which is not a mode Val knows. The only ` + "value it accepts is 'memory', which asserts that the host supplies " + "`sourceFiles`. 'fs' and 'http' are inferred rather than named: " + "'http' when VAL_API_KEY and VAL_SECRET are both set, 'fs' otherwise.");
|
|
10130
|
+
}
|
|
10106
10131
|
const maybeApiKey = opts.apiKey || process.env.VAL_API_KEY;
|
|
10107
10132
|
const maybeValSecret = opts.valSecret || process.env.VAL_SECRET;
|
|
10108
10133
|
const isProxyMode = opts.mode === "proxy" || opts.mode === undefined && (maybeApiKey || maybeValSecret);
|
|
@@ -10103,6 +10103,31 @@ async function initHandlerOptions(route, opts, config) {
|
|
|
10103
10103
|
config
|
|
10104
10104
|
};
|
|
10105
10105
|
}
|
|
10106
|
+
/*
|
|
10107
|
+
* `VAL_MODE=memory` says the host MEANT to hold the source, and did not.
|
|
10108
|
+
*
|
|
10109
|
+
* It cannot SELECT memory mode -- nothing in the environment can supply
|
|
10110
|
+
* `sourceFiles`, and a mode turned on without them is a server with no
|
|
10111
|
+
* content in it. What it does is turn the fall-through into an error.
|
|
10112
|
+
*
|
|
10113
|
+
* Without it, a host that forgot to pass its source got `fs` mode, and `fs`
|
|
10114
|
+
* mode in a Worker isolate reaches for a working tree that is not there: the
|
|
10115
|
+
* failure is an `EPERM` on `.val/patches.lock`, several layers below the
|
|
10116
|
+
* mistake, naming a path rather than the decision that led to it. Every
|
|
10117
|
+
* environment that runs Val without a disk can set this once and get a
|
|
10118
|
+
* sentence instead.
|
|
10119
|
+
*/
|
|
10120
|
+
const declaredMode = process.env.VAL_MODE;
|
|
10121
|
+
if (declaredMode === "memory") {
|
|
10122
|
+
throw new Error("VAL_MODE is 'memory', but no `sourceFiles` were given here, so there " + "is no source to serve. Memory mode cannot be turned on by the " + "environment: it needs the project's own source, and only the host " + "that holds it can hand it over. On TanStack Start that is the " + "`sourceFiles` option, passed to `initValServer` AND to " + "`initValContent`, which has a Val server of its own and is " + "configured separately. @valbuild/next has no memory mode yet, so " + "for a Next app this variable is set on an environment Val cannot " + "serve from. Unset " + "VAL_MODE to go back to the inferred mode instead ('http' when " + "VAL_API_KEY and VAL_SECRET are both set, 'fs' otherwise).");
|
|
10123
|
+
}
|
|
10124
|
+
// An empty value counts as unset, which is what `VAL_MODE=` in a shell or a
|
|
10125
|
+
// CI settings page means. Every other value is refused rather than ignored:
|
|
10126
|
+
// ignoring `VAL_MODE=memry` would leave the app in `fs` mode, which is the
|
|
10127
|
+
// exact failure this variable exists to catch.
|
|
10128
|
+
if (declaredMode !== undefined && declaredMode !== "") {
|
|
10129
|
+
throw new Error(`VAL_MODE is '${declaredMode}', which is not a mode Val knows. The only ` + "value it accepts is 'memory', which asserts that the host supplies " + "`sourceFiles`. 'fs' and 'http' are inferred rather than named: " + "'http' when VAL_API_KEY and VAL_SECRET are both set, 'fs' otherwise.");
|
|
10130
|
+
}
|
|
10106
10131
|
const maybeApiKey = opts.apiKey || process.env.VAL_API_KEY;
|
|
10107
10132
|
const maybeValSecret = opts.valSecret || process.env.VAL_SECRET;
|
|
10108
10133
|
const isProxyMode = opts.mode === "proxy" || opts.mode === undefined && (maybeApiKey || maybeValSecret);
|
|
@@ -10069,6 +10069,31 @@ async function initHandlerOptions(route, opts, config) {
|
|
|
10069
10069
|
config
|
|
10070
10070
|
};
|
|
10071
10071
|
}
|
|
10072
|
+
/*
|
|
10073
|
+
* `VAL_MODE=memory` says the host MEANT to hold the source, and did not.
|
|
10074
|
+
*
|
|
10075
|
+
* It cannot SELECT memory mode -- nothing in the environment can supply
|
|
10076
|
+
* `sourceFiles`, and a mode turned on without them is a server with no
|
|
10077
|
+
* content in it. What it does is turn the fall-through into an error.
|
|
10078
|
+
*
|
|
10079
|
+
* Without it, a host that forgot to pass its source got `fs` mode, and `fs`
|
|
10080
|
+
* mode in a Worker isolate reaches for a working tree that is not there: the
|
|
10081
|
+
* failure is an `EPERM` on `.val/patches.lock`, several layers below the
|
|
10082
|
+
* mistake, naming a path rather than the decision that led to it. Every
|
|
10083
|
+
* environment that runs Val without a disk can set this once and get a
|
|
10084
|
+
* sentence instead.
|
|
10085
|
+
*/
|
|
10086
|
+
const declaredMode = process.env.VAL_MODE;
|
|
10087
|
+
if (declaredMode === "memory") {
|
|
10088
|
+
throw new Error("VAL_MODE is 'memory', but no `sourceFiles` were given here, so there " + "is no source to serve. Memory mode cannot be turned on by the " + "environment: it needs the project's own source, and only the host " + "that holds it can hand it over. On TanStack Start that is the " + "`sourceFiles` option, passed to `initValServer` AND to " + "`initValContent`, which has a Val server of its own and is " + "configured separately. @valbuild/next has no memory mode yet, so " + "for a Next app this variable is set on an environment Val cannot " + "serve from. Unset " + "VAL_MODE to go back to the inferred mode instead ('http' when " + "VAL_API_KEY and VAL_SECRET are both set, 'fs' otherwise).");
|
|
10089
|
+
}
|
|
10090
|
+
// An empty value counts as unset, which is what `VAL_MODE=` in a shell or a
|
|
10091
|
+
// CI settings page means. Every other value is refused rather than ignored:
|
|
10092
|
+
// ignoring `VAL_MODE=memry` would leave the app in `fs` mode, which is the
|
|
10093
|
+
// exact failure this variable exists to catch.
|
|
10094
|
+
if (declaredMode !== undefined && declaredMode !== "") {
|
|
10095
|
+
throw new Error(`VAL_MODE is '${declaredMode}', which is not a mode Val knows. The only ` + "value it accepts is 'memory', which asserts that the host supplies " + "`sourceFiles`. 'fs' and 'http' are inferred rather than named: " + "'http' when VAL_API_KEY and VAL_SECRET are both set, 'fs' otherwise.");
|
|
10096
|
+
}
|
|
10072
10097
|
const maybeApiKey = opts.apiKey || process.env.VAL_API_KEY;
|
|
10073
10098
|
const maybeValSecret = opts.valSecret || process.env.VAL_SECRET;
|
|
10074
10099
|
const isProxyMode = opts.mode === "proxy" || opts.mode === undefined && (maybeApiKey || maybeValSecret);
|