Commit 8737709db876420b4db1aea9a323d248fd75fe20
initial work on standalone sbot and custom ports / data directory
Matt McKegg committed on 8/14/2017, 4:46:31 AMParent: 81ab2bfaf7653df34639deb578b81f7e80308bb0
Files changed
blob/sync/url.js | changed |
index.js | changed |
package-lock.json | changed |
package.json | changed |
assets/base.html | added |
background-process.js | added |
config.js | added |
electron.js | added |
blob/sync/url.js | ||
---|---|---|
@@ -1,11 +1,18 @@ | ||
1 | 1 | const nest = require('depnest') |
2 | 2 | |
3 | 3 | exports.gives = nest('blob.sync.url') |
4 | 4 | |
5 | +exports.needs = nest({ | |
6 | + 'config.sync.load': 'first' | |
7 | +}) | |
8 | + | |
5 | 9 | exports.create = function (api) { |
6 | 10 | return nest('blob.sync.url', function (id) { |
7 | - // return id | |
8 | - | |
9 | - return 'http://localhost:8989/blobs/get/' + id | |
11 | + var config = api.config.sync.load() | |
12 | + var prefix = config.blobsPrefix != null ? config.blobsPrefix : `http://localhost:${config.ws.port}/blobs/get` | |
13 | + if (id && typeof id.link === 'string') { | |
14 | + id = id.link | |
15 | + } | |
16 | + return `${prefix}/${encodeURIComponent(id)}` | |
10 | 17 | }) |
11 | 18 | } |
index.js | ||
---|---|---|
@@ -1,7 +1,8 @@ | ||
1 | 1 | const ticktack = { |
2 | 2 | app: require('./app'), |
3 | 3 | blob: require('./blob'), |
4 | + config: require('./config'), | |
4 | 5 | router: require('./router'), |
5 | 6 | styles: require('./styles') |
6 | 7 | } |
7 | 8 |
package-lock.json | ||
---|---|---|
The diff is too large to show. Use a local git client to view these changes. Old file size: 62962 bytes New file size: 209660 bytes |
package.json | ||
---|---|---|
@@ -3,11 +3,11 @@ | ||
3 | 3 | "version": "1.0.0", |
4 | 4 | "description": "", |
5 | 5 | "main": "index.js", |
6 | 6 | "scripts": { |
7 | - "setup": "npm install electron electro -g", | |
8 | - "rebuild": "npm rebuild --runtime=electron --target=$(electron -v) --abi=$(electron --abi) --disturl=https://atom.io/download/atom-shell", | |
9 | - "start": "electro main.js", | |
7 | + "rebuild": "cross-script npm rebuild --runtime=electron \"--target=$(electron -v)\" \"--abi=$(electron --abi)\" --disturl=https://atom.io/download/atom-shell", | |
8 | + "start": "electron electron.js", | |
9 | + "postinstall": "npm run rebuild", | |
10 | 10 | "test": "echo \"Error: no test specified\" && exit 1" |
11 | 11 | }, |
12 | 12 | "repository": { |
13 | 13 | "type": "git", |
@@ -15,10 +15,13 @@ | ||
15 | 15 | }, |
16 | 16 | "author": "", |
17 | 17 | "license": "GPL-3.0", |
18 | 18 | "dependencies": { |
19 | + "cross-script": "^1.0.5", | |
19 | 20 | "depject": "^4.1.0", |
20 | 21 | "depnest": "^1.3.0", |
22 | + "electron-default-menu": "^1.0.1", | |
23 | + "electron-window-state": "^4.1.1", | |
21 | 24 | "insert-css": "^2.0.0", |
22 | 25 | "libnested": "^1.2.1", |
23 | 26 | "lodash": "^4.17.4", |
24 | 27 | "micro-css": "^2.0.1", |
@@ -27,10 +30,23 @@ | ||
27 | 30 | "patch-history": "^1.0.0", |
28 | 31 | "patchcore": "^1.9.1", |
29 | 32 | "pull-stream": "^3.6.0", |
30 | 33 | "read-directory": "^2.1.0", |
34 | + "scuttlebot": "^10.4.4", | |
31 | 35 | "setimmediate": "^1.0.5", |
36 | + "ssb-about": "^0.1.0", | |
37 | + "ssb-backlinks": "^0.4.0", | |
38 | + "ssb-blobs": "^1.1.3", | |
39 | + "ssb-contacts": "0.0.2", | |
40 | + "ssb-friends": "^2.2.1", | |
41 | + "ssb-keys": "^7.0.10", | |
42 | + "ssb-private": "^0.1.2", | |
43 | + "ssb-query": "^0.1.2", | |
32 | 44 | "ssb-reduce-stream": "0.0.0", |
33 | 45 | "ssb-ref": "^2.7.1", |
46 | + "ssb-ws": "^1.0.3", | |
34 | 47 | "url": "^0.11.0" |
48 | + }, | |
49 | + "devDependencies": { | |
50 | + "electron": "~1.7.5" | |
35 | 51 | } |
36 | 52 | } |
assets/base.html | ||
---|---|---|
@@ -1,0 +1,31 @@ | ||
1 | + | |
2 | +<html> | |
3 | + <head></head> | |
4 | + <body> | |
5 | + <script> | |
6 | + // redirect console to main process | |
7 | + var electron = require('electron') | |
8 | + var localLog = console.log | |
9 | + var localError = console.error | |
10 | + var remoteLog = electron.remote.getGlobal('console').log | |
11 | + var remoteError = electron.remote.getGlobal('console').error | |
12 | + | |
13 | + console.log = function (...args) { | |
14 | + localLog.apply(console, args) | |
15 | + remoteLog(...args) | |
16 | + } | |
17 | + | |
18 | + console.error = function (...args) { | |
19 | + localError.apply(console, args) | |
20 | + remoteError(...args) | |
21 | + } | |
22 | + | |
23 | + process.exit = electron.remote.app.quit | |
24 | + // redirect errors to stderr | |
25 | + window.addEventListener('error', function (e) { | |
26 | + e.preventDefault() | |
27 | + console.error(e.error.stack || 'Uncaught ' + e.error) | |
28 | + }) | |
29 | + </script> | |
30 | + </body> | |
31 | +</html> |
background-process.js | ||
---|---|---|
@@ -1,0 +1,28 @@ | ||
1 | +var fs = require('fs') | |
2 | +var Path = require('path') | |
3 | +var electron = require('electron') | |
4 | + | |
5 | +var createSbot = require('scuttlebot') | |
6 | + .use(require('scuttlebot/plugins/master')) | |
7 | + .use(require('scuttlebot/plugins/gossip')) | |
8 | + .use(require('scuttlebot/plugins/replicate')) | |
9 | + .use(require('ssb-friends')) | |
10 | + .use(require('ssb-blobs')) | |
11 | + .use(require('ssb-backlinks')) | |
12 | + .use(require('ssb-private')) | |
13 | + .use(require('scuttlebot/plugins/invite')) | |
14 | + .use(require('scuttlebot/plugins/local')) | |
15 | + .use(require('scuttlebot/plugins/logging')) | |
16 | + .use(require('ssb-query')) | |
17 | + .use(require('ssb-about')) | |
18 | + .use(require('ssb-contacts')) | |
19 | + // .use(require('ssb-ebt')) | |
20 | + .use(require('ssb-ws')) | |
21 | + | |
22 | +// pull config options out of depject | |
23 | +var config = require('./config').create().config.sync.load() | |
24 | + | |
25 | +var sbot = createSbot(config) | |
26 | +var manifest = sbot.getManifest() | |
27 | +fs.writeFileSync(Path.join(config.path, 'manifest.json'), JSON.stringify(manifest)) | |
28 | +electron.ipcRenderer.send('server-started') |
config.js | ||
---|---|---|
@@ -1,0 +1,28 @@ | ||
1 | +const Config = require('ssb-config/inject') | |
2 | +const nest = require('depnest') | |
3 | +const ssbKeys = require('ssb-keys') | |
4 | +const Path = require('path') | |
5 | + | |
6 | +const appName = 'ticktack-ssb' | |
7 | +const opts = { | |
8 | + port: 43750, | |
9 | + blobsPort: 43751, | |
10 | + ws: { | |
11 | + port: 43751 | |
12 | + } | |
13 | +} | |
14 | + | |
15 | +exports.gives = nest('config.sync.load') | |
16 | +exports.create = (api) => { | |
17 | + var config | |
18 | + return nest('config.sync.load', () => { | |
19 | + if (!config) { | |
20 | + config = Config(process.env.ssb_appname || appName, opts) | |
21 | + config.keys = ssbKeys.loadOrCreateSync(Path.join(config.path, 'secret')) | |
22 | + | |
23 | + // HACK: fix offline on windows by specifying 127.0.0.1 instead of localhost (default) | |
24 | + config.remote = `net:127.0.0.1:${config.port}~shs:${config.keys.id.slice(1).replace('.ed25519', '')}` | |
25 | + } | |
26 | + return config | |
27 | + }) | |
28 | +} |
electron.js | ||
---|---|---|
@@ -1,0 +1,135 @@ | ||
1 | +var defaultMenu = require('electron-default-menu') | |
2 | +var WindowState = require('electron-window-state') | |
3 | +var electron = require('electron') | |
4 | +var Menu = electron.Menu | |
5 | +var Path = require('path') | |
6 | + | |
7 | +var windows = {} | |
8 | +var quitting = false | |
9 | + | |
10 | +electron.app.on('ready', () => { | |
11 | + var menu = defaultMenu(electron.app, electron.shell) | |
12 | + var view = menu.find(x => x.label === 'View') | |
13 | + view.submenu = [ | |
14 | + { role: 'reload' }, | |
15 | + { role: 'toggledevtools' }, | |
16 | + { type: 'separator' }, | |
17 | + { role: 'resetzoom' }, | |
18 | + { role: 'zoomin' }, | |
19 | + { role: 'zoomout' }, | |
20 | + { type: 'separator' }, | |
21 | + { role: 'togglefullscreen' } | |
22 | + ] | |
23 | + if (process.platform === 'darwin') { | |
24 | + var win = menu.find(x => x.label === 'Window') | |
25 | + win.submenu = [ | |
26 | + { role: 'minimize' }, | |
27 | + { role: 'zoom' }, | |
28 | + { role: 'close', label: 'Close' }, | |
29 | + { type: 'separator' }, | |
30 | + { role: 'front' } | |
31 | + ] | |
32 | + } | |
33 | + | |
34 | + Menu.setApplicationMenu(Menu.buildFromTemplate(menu)) | |
35 | + | |
36 | + startBackgroundProcess() | |
37 | + | |
38 | + // wait until server has started before opening main window | |
39 | + electron.ipcMain.once('server-started', function (ev, config) { | |
40 | + openMainWindow() | |
41 | + }) | |
42 | + | |
43 | + electron.app.on('before-quit', function () { | |
44 | + quitting = true | |
45 | + }) | |
46 | + | |
47 | + // allow inspecting of background process | |
48 | + electron.ipcMain.on('open-background-devtools', function (ev, config) { | |
49 | + if (windows.background) { | |
50 | + windows.background.webContents.openDevTools({detach: true}) | |
51 | + } | |
52 | + }) | |
53 | +}) | |
54 | + | |
55 | +function startBackgroundProcess () { | |
56 | + if (!windows.background) { | |
57 | + windows.background = openWindow(Path.join(__dirname, 'background-process.js'), { | |
58 | + connect: false, | |
59 | + center: true, | |
60 | + fullscreen: false, | |
61 | + fullscreenable: false, | |
62 | + height: 150, | |
63 | + maximizable: false, | |
64 | + minimizable: false, | |
65 | + resizable: false, | |
66 | + show: false, | |
67 | + skipTaskbar: true, | |
68 | + title: 'ticktack-server', | |
69 | + useContentSize: true, | |
70 | + width: 150 | |
71 | + }) | |
72 | + } | |
73 | +} | |
74 | + | |
75 | +function openMainWindow () { | |
76 | + if (!windows.main) { | |
77 | + var windowState = WindowState({ | |
78 | + defaultWidth: 1024, | |
79 | + defaultHeight: 768 | |
80 | + }) | |
81 | + windows.main = openWindow(Path.join(__dirname, 'main.js'), { | |
82 | + minWidth: 800, | |
83 | + x: windowState.x, | |
84 | + y: windowState.y, | |
85 | + width: windowState.width, | |
86 | + height: windowState.height, | |
87 | + autoHideMenuBar: true, | |
88 | + title: 'Ticktack', | |
89 | + show: true, | |
90 | + backgroundColor: '#EEE', | |
91 | + icon: './assets/icon.png' | |
92 | + }) | |
93 | + windowState.manage(windows.main) | |
94 | + windows.main.setSheetOffset(40) | |
95 | + windows.main.on('close', function (e) { | |
96 | + if (!quitting && process.platform === 'darwin') { | |
97 | + e.preventDefault() | |
98 | + windows.main.hide() | |
99 | + } | |
100 | + }) | |
101 | + windows.main.on('closed', function () { | |
102 | + windows.main = null | |
103 | + if (process.platform !== 'darwin') electron.app.quit() | |
104 | + }) | |
105 | + } | |
106 | +} | |
107 | + | |
108 | +function openWindow (path, opts) { | |
109 | + var window = new electron.BrowserWindow(opts) | |
110 | + window.webContents.on('dom-ready', function () { | |
111 | + window.webContents.executeJavaScript(` | |
112 | + var electron = require('electron') | |
113 | + var h = require('mutant/h') | |
114 | + electron.webFrame.setZoomLevelLimits(1, 1) | |
115 | + var title = ${JSON.stringify(opts.title || 'Ticktack')} | |
116 | + document.documentElement.querySelector('head').appendChild( | |
117 | + h('title', title) | |
118 | + ) | |
119 | + require(${JSON.stringify(path)}) | |
120 | + `) | |
121 | + }) | |
122 | + | |
123 | + window.webContents.on('will-navigate', function (e, url) { | |
124 | + e.preventDefault() | |
125 | + electron.shell.openExternal(url) | |
126 | + }) | |
127 | + | |
128 | + window.webContents.on('new-window', function (e, url) { | |
129 | + e.preventDefault() | |
130 | + electron.shell.openExternal(url) | |
131 | + }) | |
132 | + | |
133 | + window.loadURL('file://' + Path.join(__dirname, 'assets', 'base.html')) | |
134 | + return window | |
135 | +} |
Built with git-ssb-web