braidfs 0.0.55 → 0.0.57
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/README.md +48 -15
- package/index.js +30 -13
- package/package.json +1 -1
package/README.md
CHANGED
|
@@ -1,8 +1,45 @@
|
|
|
1
|
-
#
|
|
1
|
+
# BraidFS: Braid your Filesystem with the Web
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
Provides interoperability between **web pages** via http and your **OS filesystem**.
|
|
4
|
+
- Using collaborative CRDTs and the Braid extensions for HTTP.
|
|
4
5
|
|
|
5
|
-
|
|
6
|
+
The `braidfs` daemon performs bi-directional synchronization between remote Braid-HTTP resources and your local filesystem.
|
|
7
|
+
|
|
8
|
+
### Web resources map onto your filesystem
|
|
9
|
+
|
|
10
|
+
It creates a `~/http` folder in your home directory to synchronize webpages with:
|
|
11
|
+
|
|
12
|
+
```
|
|
13
|
+
~/http/
|
|
14
|
+
├── example.com/
|
|
15
|
+
│ ├── document.html
|
|
16
|
+
│ ├── notes.md
|
|
17
|
+
│ └── assets/
|
|
18
|
+
│ └── style.css
|
|
19
|
+
└── braid.org/
|
|
20
|
+
└── meeting-53
|
|
21
|
+
```
|
|
22
|
+
|
|
23
|
+
|
|
24
|
+
https://github.com/user-attachments/assets/4fb36208-e0bd-471b-b47b-bbeee20e4f3f
|
|
25
|
+
|
|
26
|
+
|
|
27
|
+
|
|
28
|
+
### Two-way sync edits between files and web
|
|
29
|
+
|
|
30
|
+
As long as `braidfs` is running, it will keep the file and web resources in
|
|
31
|
+
sync!
|
|
32
|
+
|
|
33
|
+
- Edit to the file → web resource
|
|
34
|
+
- Edit to the web resource → file
|
|
35
|
+
|
|
36
|
+
Each edit to the file is diffed and sent as a CRDT patch, so you can edit
|
|
37
|
+
files offline, and even collaboratively edit them, with one caveat:
|
|
38
|
+
|
|
39
|
+
#### Caveat
|
|
40
|
+
|
|
41
|
+
For the period of time that you have edited the file in your editor but not
|
|
42
|
+
saved it, external edits cannot be integrated.
|
|
6
43
|
|
|
7
44
|
## Installation
|
|
8
45
|
|
|
@@ -39,13 +76,13 @@ braidfs unsync <url>
|
|
|
39
76
|
|
|
40
77
|
## Configuration
|
|
41
78
|
|
|
42
|
-
braidfs looks for a configuration file at `~/http/.braidfs/config
|
|
79
|
+
braidfs looks for a configuration file at `~/http/.braidfs/config`, or creates it if it doesn't exist. You can set the following options:
|
|
43
80
|
|
|
44
|
-
- `sync`: An object where the keys are URLs to sync, and the values are simply
|
|
45
|
-
- `
|
|
81
|
+
- `sync`: An object where the keys are URLs to sync, and the values are simply `true`
|
|
82
|
+
- `cookies`: An object for setting domain-specific cookies for authentication
|
|
46
83
|
- `port`: The port number for the internal daemon (default: 45678)
|
|
47
84
|
|
|
48
|
-
Example `config
|
|
85
|
+
Example `config`:
|
|
49
86
|
|
|
50
87
|
```json
|
|
51
88
|
{
|
|
@@ -53,19 +90,15 @@ Example `config.json`:
|
|
|
53
90
|
"https://example.com/document1.txt": true,
|
|
54
91
|
"https://example.com/document2.txt": true
|
|
55
92
|
},
|
|
56
|
-
"
|
|
57
|
-
"example.com":
|
|
58
|
-
"auth_headers": {
|
|
59
|
-
"Cookie": "secret_pass"
|
|
60
|
-
}
|
|
61
|
-
}
|
|
93
|
+
"cookies": {
|
|
94
|
+
"example.com": "secret_pass"
|
|
62
95
|
},
|
|
63
96
|
"port": 45678
|
|
64
97
|
}
|
|
65
98
|
```
|
|
66
99
|
|
|
67
|
-
The `
|
|
100
|
+
The `cookies` configuration allows you to set authentication cookies for specific domains. In the example above, any requests to `example.com` will include the specified cookie value.
|
|
68
101
|
|
|
69
102
|
## Security
|
|
70
103
|
|
|
71
|
-
braidfs is designed to run locally and only accepts connections from localhost (127.0.0.1 or ::1) for security reasons. The `
|
|
104
|
+
braidfs is designed to run locally and only accepts connections from localhost (127.0.0.1 or ::1) for security reasons. The `cookies` configuration enables secure communication with servers that require authentication by allowing you to set domain-specific cookie values.
|
package/index.js
CHANGED
|
@@ -23,13 +23,24 @@ var config = null,
|
|
|
23
23
|
if (require('fs').existsSync(proxy_base)) {
|
|
24
24
|
try {
|
|
25
25
|
config = JSON.parse(require('fs').readFileSync(braidfs_config_file, 'utf8'))
|
|
26
|
+
|
|
27
|
+
// for 0.0.55 users upgrading to 0.0.56,
|
|
28
|
+
// which changes the config "domains" key to "cookies",
|
|
29
|
+
// and condenses its structure a bit
|
|
30
|
+
if (config.domains) {
|
|
31
|
+
config.cookies = Object.fromEntries(Object.entries(config.domains).map(([k, v]) => {
|
|
32
|
+
if (v.auth_headers?.Cookie) return [k, v.auth_headers.Cookie]
|
|
33
|
+
}).filter(x => x))
|
|
34
|
+
delete config.domains
|
|
35
|
+
require('fs').writeFileSync(braidfs_config_file, JSON.stringify(config, null, 4))
|
|
36
|
+
}
|
|
26
37
|
} catch (e) {
|
|
27
38
|
return console.log(`Cannot parse the configuration file at: ${braidfs_config_file}`)
|
|
28
39
|
}
|
|
29
40
|
} else {
|
|
30
41
|
config = {
|
|
31
42
|
sync: {},
|
|
32
|
-
|
|
43
|
+
cookies: { 'example.com': 'secret_pass' },
|
|
33
44
|
port: 45678,
|
|
34
45
|
scan_interval_ms: 1000 * 20,
|
|
35
46
|
}
|
|
@@ -132,12 +143,12 @@ async function main() {
|
|
|
132
143
|
// have the appropriate connections reconnect
|
|
133
144
|
let changed = new Set()
|
|
134
145
|
// any old domains no longer exist?
|
|
135
|
-
for (let domain of Object.keys(prev.
|
|
136
|
-
if (!config.
|
|
146
|
+
for (let domain of Object.keys(prev.cookies ?? {}))
|
|
147
|
+
if (!config.cookies?.[domain]) changed.add(domain)
|
|
137
148
|
// any new domains not like the old?
|
|
138
|
-
for (let [domain, v] of Object.entries(config.
|
|
139
|
-
if (!prev.
|
|
140
|
-
|| JSON.stringify(prev.
|
|
149
|
+
for (let [domain, v] of Object.entries(config.cookies ?? {}))
|
|
150
|
+
if (!prev.cookies?.[domain]
|
|
151
|
+
|| JSON.stringify(prev.cookies[domain]) !== JSON.stringify(v))
|
|
141
152
|
changed.add(domain)
|
|
142
153
|
// ok, have every domain which has changed reconnect
|
|
143
154
|
for (let [path, x] of Object.entries(proxy_url.cache))
|
|
@@ -388,7 +399,7 @@ async function proxy_url(url) {
|
|
|
388
399
|
headers: {
|
|
389
400
|
"Merge-Type": "dt",
|
|
390
401
|
"Content-Type": 'text/plain',
|
|
391
|
-
...config.
|
|
402
|
+
...(x => x && {Cookie: x})(config.cookies?.[new URL(url).hostname])
|
|
392
403
|
},
|
|
393
404
|
method: "PUT",
|
|
394
405
|
retry: true,
|
|
@@ -488,11 +499,17 @@ async function proxy_url(url) {
|
|
|
488
499
|
file_needs_writing = false
|
|
489
500
|
let { version, body } = await braid_text.get(url, {})
|
|
490
501
|
if (!v_eq(version, file_last_version)) {
|
|
491
|
-
|
|
492
|
-
|
|
493
|
-
// make sure the file has what it had before
|
|
502
|
+
// let's do a final check to see if anything has changed
|
|
503
|
+
// before writing out a new version of the file
|
|
494
504
|
let text = await require('fs').promises.readFile(fullpath, { encoding: 'utf8' })
|
|
495
|
-
if (self.file_last_text != text)
|
|
505
|
+
if (self.file_last_text != text) {
|
|
506
|
+
// if the text is different, let's read it first..
|
|
507
|
+
file_needs_reading = true
|
|
508
|
+
file_needs_writing = true
|
|
509
|
+
continue
|
|
510
|
+
}
|
|
511
|
+
|
|
512
|
+
console.log(`writing file ${fullpath}`)
|
|
496
513
|
|
|
497
514
|
try { if (await is_read_only(fullpath)) await set_read_only(fullpath, false) } catch (e) { }
|
|
498
515
|
|
|
@@ -542,7 +559,7 @@ async function proxy_url(url) {
|
|
|
542
559
|
headers: {
|
|
543
560
|
"Merge-Type": "dt",
|
|
544
561
|
Accept: 'text/plain',
|
|
545
|
-
...config.
|
|
562
|
+
...(x => x && {Cookie: x})(config.cookies?.[new URL(url).hostname]),
|
|
546
563
|
},
|
|
547
564
|
subscribe: true,
|
|
548
565
|
retry: {
|
|
@@ -594,7 +611,7 @@ async function proxy_url(url) {
|
|
|
594
611
|
method: "HEAD",
|
|
595
612
|
headers: {
|
|
596
613
|
Accept: 'text/plain',
|
|
597
|
-
...config.
|
|
614
|
+
...(x => x && {Cookie: x})(config.cookies?.[new URL(url).hostname]),
|
|
598
615
|
},
|
|
599
616
|
retry: true
|
|
600
617
|
})
|