querysub 0.252.0 → 0.253.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.
@@ -0,0 +1,212 @@
1
+ import { SocketFunction } from "socket-function/SocketFunction";
2
+ import { qreact } from "../../4-dom/qreact";
3
+ import { MachineServiceController, MachineInfo, ServiceConfig } from "../machineSchema";
4
+ import { showFullscreenModal } from "../../5-diagnostics/FullscreenModal";
5
+ import { InputLabel } from "../../library-components/InputLabel";
6
+ import { css } from "../../4-dom/css";
7
+ import { formatTime } from "socket-function/src/formatting/format";
8
+ import { formatTimeJSX } from "../../misc/formatJSX";
9
+ import { MachineController } from "../machineController";
10
+
11
+ module.hotreload = true;
12
+
13
+ function bigEmoji(emoji: string, topOffset = 0) {
14
+ return <span className={css.fontSize(26).marginTop(topOffset)}>{emoji}</span>;
15
+ }
16
+
17
+ export class RenderGitRefInfo extends qreact.Component<{
18
+ gitRef: string;
19
+ isQuerysub?: boolean;
20
+ }> {
21
+ render() {
22
+ let controller = MachineServiceController(SocketFunction.browserNodeId());
23
+ let gitRefInfo = controller.getGitRefInfo({
24
+ ref: this.props.gitRef,
25
+ useQuerysub: this.props.isQuerysub,
26
+ });
27
+ if (!gitRefInfo) return undefined;
28
+ return <div className={css.fontWeight("normal")}>{formatTimeJSX(gitRefInfo.time)} AGO {gitRefInfo.description}</div>;
29
+ }
30
+ }
31
+
32
+ const buttonStyle = css.pad2(12, 8).button.bord2(0, 0, 20).fontWeight("bold").vbox(0).alignItems("center");
33
+
34
+ export class UpdateButtons extends qreact.Component<{
35
+ services: ServiceConfig[];
36
+ }> {
37
+ render() {
38
+ let controller = MachineServiceController(SocketFunction.browserNodeId());
39
+ const gitInfo = controller.getGitInfo();
40
+
41
+ let outdatedServices = this.props.services.filter(service => {
42
+ let { gitRef, repoUrl } = service.parameters;
43
+ return repoUrl === gitInfo?.repoUrl && gitRef !== gitInfo?.latestRef;
44
+ });
45
+ let outdatedRefs = outdatedServices.map(service => service.parameters.gitRef);
46
+
47
+ return <>
48
+ {!!gitInfo?.querysubUncommitted.length && <button
49
+ className={buttonStyle.hsl(260, 60, 55)}
50
+ title={gitInfo?.querysubUncommitted.join("\n")}
51
+ onClick={() => {
52
+ showFullscreenModal({
53
+ content: <div>
54
+ <InputLabel
55
+ label="Commit message (enter to commit, escape to cancel)"
56
+ value={""}
57
+ textarea
58
+ fillWidth
59
+ onChangeValue={value => {
60
+ if (!value) return;
61
+ void controller.commitPushAndPublishQuerysub.promise(value);
62
+ }}
63
+ />
64
+ <div className={css.vbox(5)}>
65
+ {gitInfo?.querysubUncommitted.map(change => {
66
+ return <div>
67
+ {change}
68
+ </div>;
69
+ })}
70
+ </div>
71
+ </div>
72
+ });
73
+ }}
74
+ >
75
+ <div>
76
+ {bigEmoji("📚", -5)}
77
+ Publish & Commit & Push Querysub & Update Package.json ({gitInfo?.querysubUncommitted.length} Files Changed)
78
+ </div>
79
+ <RenderGitRefInfo gitRef={gitInfo.querysubRef} isQuerysub />
80
+ </button>}
81
+ {!!gitInfo?.uncommitted.length && <button
82
+ className={buttonStyle.hsl(210, 40, 50)}
83
+ title={gitInfo?.uncommitted.join("\n")}
84
+ onClick={() => {
85
+ showFullscreenModal({
86
+ content: <div>
87
+ <InputLabel
88
+ label="Commit message (enter to commit, escape to cancel)"
89
+ value={""}
90
+ textarea
91
+ fillWidth
92
+ onChangeValue={value => {
93
+ if (!value) return;
94
+ void controller.commitPushService.promise(value);
95
+ }}
96
+ />
97
+ <div className={css.vbox(5)}>
98
+ {gitInfo?.uncommitted.map(change => {
99
+ return <div>
100
+ {change}
101
+ </div>;
102
+ })}
103
+ </div>
104
+ </div>
105
+ });
106
+ }}
107
+ >
108
+ {bigEmoji("⬆️")} <span>Commit & Push ({gitInfo?.uncommitted.length} Files Changed)</span>
109
+ </button>}
110
+
111
+ {outdatedServices.length > 0 && gitInfo &&
112
+ <button
113
+ className={buttonStyle.hsl(120, 70, 50)}
114
+ onClick={async () => {
115
+ for (let service of outdatedServices) {
116
+ service.parameters.gitRef = gitInfo.latestRef;
117
+ }
118
+ await controller.setServiceConfigs.promise(outdatedServices);
119
+ }}
120
+ >
121
+ <div>
122
+ {bigEmoji("🎯")} <span>Deploy & Restart All ({outdatedServices.length}) Services</span>
123
+ </div>
124
+ <div className={css.hbox(5)}>
125
+ <b>New</b>
126
+ <RenderGitRefInfo gitRef={gitInfo.latestRef} />
127
+ </div>
128
+ {outdatedRefs.map(ref => <div className={css.hbox(5)}>
129
+ <b>Current</b>
130
+ <RenderGitRefInfo gitRef={ref} />
131
+ </div>)}
132
+ </button>
133
+ }
134
+ </>;
135
+ }
136
+ }
137
+
138
+ export class UpdateServiceButtons extends qreact.Component<{
139
+ service: ServiceConfig;
140
+ }> {
141
+ render() {
142
+ let controller = MachineServiceController(SocketFunction.browserNodeId());
143
+ const gitInfo = controller.getGitInfo();
144
+ let gitRef = this.props.service.parameters.gitRef;
145
+ let repoUrl = this.props.service.parameters.repoUrl;
146
+ if (gitInfo?.repoUrl !== repoUrl) return undefined;
147
+
148
+ return <>
149
+ {gitRef !== gitInfo.latestRef && <button
150
+ className={buttonStyle.hsl(120, 70, 50).alignSelf("stretch")}
151
+ onClick={async () => {
152
+ this.props.service.parameters.gitRef = gitInfo.latestRef;
153
+ await controller.setServiceConfigs.promise([this.props.service]);
154
+ }}
155
+ >
156
+ <div>
157
+ {bigEmoji("🎯", -4)} <span>Deploy & Restart</span>
158
+ </div>
159
+ <div className={css.hbox(5)}>
160
+ <b>New</b>
161
+ <RenderGitRefInfo gitRef={gitInfo.latestRef} />
162
+ </div>
163
+ <div className={css.hbox(5)}>
164
+ <b>Current</b>
165
+ <RenderGitRefInfo gitRef={gitRef} />
166
+ </div>
167
+ </button>}
168
+ </>;
169
+ }
170
+ }
171
+
172
+ export class DeployMachineButtons extends qreact.Component<{
173
+ machines: MachineInfo[];
174
+ }> {
175
+ render() {
176
+ let controller = MachineServiceController(SocketFunction.browserNodeId());
177
+ const gitInfo = controller.getGitInfo();
178
+ if (!gitInfo) return undefined;
179
+
180
+ let outdatedMachines = this.props.machines.filter(machine => {
181
+ return machine.repoUrl === gitInfo.repoUrl && machine.gitRef !== gitInfo.latestRef;
182
+ });
183
+ let oudatedRefs = outdatedMachines.map(machine => machine.gitRef);
184
+
185
+ return <>
186
+ {outdatedMachines.length > 0 && <div
187
+ className={buttonStyle.alignSelf("stretch").hsl(120, 70, 50)}
188
+ onClick={async () => {
189
+ let machineController = MachineController(SocketFunction.browserNodeId());
190
+ await Promise.all(outdatedMachines.map(machine => {
191
+ return machineController.deployMachineFromBrowser.promise({
192
+ machineNodeId: machine.applyNodeId,
193
+ gitRef: gitInfo.latestRef,
194
+ });
195
+ }));
196
+ }}
197
+ >
198
+ <div>
199
+ {bigEmoji("🎯", -4)} <span>Deploy {outdatedMachines.length} Machines</span>
200
+ </div>
201
+ <div className={css.hbox(5)}>
202
+ <b>New</b>
203
+ <RenderGitRefInfo gitRef={gitInfo.latestRef} />
204
+ </div>
205
+ {oudatedRefs.map(ref => <div className={css.hbox(5)}>
206
+ <b>Current</b>
207
+ <RenderGitRefInfo gitRef={ref} />
208
+ </div>)}
209
+ </div>}
210
+ </>;
211
+ }
212
+ }
@@ -4,7 +4,7 @@ import { measureWrap } from "socket-function/src/profiling/measure";
4
4
  import { getOwnMachineId } from "../-a-auth/certs";
5
5
  import { getOurNodeId, getOurNodeIdAssert } from "../-f-node-discovery/NodeDiscovery";
6
6
  import { Querysub } from "../4-querysub/QuerysubController";
7
- import { MACHINE_RESYNC_INTERVAL, DeployControllerBase, MachineInfo, ServiceConfig, serviceConfigs, SERVICE_FOLDER, machineInfos } from "./machineSchema";
7
+ import { MACHINE_RESYNC_INTERVAL, MachineServiceControllerBase, MachineInfo, ServiceConfig, serviceConfigs, SERVICE_FOLDER, machineInfos } from "./machineSchema";
8
8
  import { runPromise } from "../functional/runCommand";
9
9
  import { getExternalIP } from "socket-function/src/networking";
10
10
  import { errorToUndefined, errorToUndefinedSilent } from "../errors";
@@ -18,7 +18,7 @@ import os from "os";
18
18
  import fs from "fs";
19
19
  import { spawn, ChildProcess } from "child_process";
20
20
  import { lazy } from "socket-function/src/caching";
21
- import { getGitRefLive, setGitRef } from "../4-deploy/git";
21
+ import { getGitRefLive, getGitURLLive, setGitRef } from "../4-deploy/git";
22
22
  import { blue, green, magenta, red } from "socket-function/src/formatting/logColors";
23
23
  import { shutdown } from "../diagnostics/periodic";
24
24
  import { onServiceConfigChange } from "./machineController";
@@ -34,6 +34,8 @@ const getLiveMachineInfo = measureWrap(async function getLiveMachineInfo() {
34
34
  heartbeat: Date.now(),
35
35
  info: {},
36
36
  services: {},
37
+ repoUrl: "",
38
+ gitRef: "",
37
39
  };
38
40
 
39
41
  machineInfo.info.hostnamectl = await errorToUndefinedSilent(runPromise("hostnamectl")) || "";
@@ -41,6 +43,9 @@ const getLiveMachineInfo = measureWrap(async function getLiveMachineInfo() {
41
43
  machineInfo.info.lscpu = await errorToUndefinedSilent(runPromise("lscpu")) || "";
42
44
  machineInfo.info.id = await errorToUndefinedSilent(runPromise("id")) || await errorToUndefinedSilent(runPromise("whoami")) || "";
43
45
 
46
+ machineInfo.repoUrl = await getGitURLLive(".");
47
+ machineInfo.gitRef = await getGitRefLive(".");
48
+
44
49
  return machineInfo;
45
50
  });
46
51
 
@@ -78,7 +83,7 @@ export async function streamScreenOutput(config: {
78
83
  try {
79
84
  await serialOnData(data);
80
85
  } catch (e: any) {
81
- console.log(`Callback for stream output ${screenName} failed. It probably just disconnected, almost certainly not an error: ${e.stack}`);
86
+ console.log(`Callback for stream output ${screenName} failed. It probably just disconnected, almost certainly not an error: ${e.message}`);
82
87
  await stop();
83
88
  } finally {
84
89
  pendingDataCalls--;
@@ -425,7 +430,7 @@ async function quickIsOutdated() {
425
430
  index: i,
426
431
  });
427
432
  let screen = screens.find(x => x.screenName === screenName);
428
- if (!screen) return true;
433
+ if (!screen?.isProcessRunning) return true;
429
434
 
430
435
  let folder = root + screenName + "/";
431
436
  await fs.promises.mkdir(folder, { recursive: true });
@@ -433,6 +438,7 @@ async function quickIsOutdated() {
433
438
  if (!fs.existsSync(parameterPath)) return true;
434
439
  let prevParameters = await fs.promises.readFile(parameterPath, "utf8");
435
440
  if (prevParameters !== newParametersString) return true;
441
+
436
442
  }
437
443
  }
438
444
  return false;
@@ -8,6 +8,10 @@ import { isNode } from "typesafecss";
8
8
  import { streamScreenOutput } from "./machineApplyMainCode";
9
9
  import { Querysub } from "../4-querysub/QuerysubController";
10
10
  import { getPathStr2 } from "../path";
11
+ import { getGitURLLive, setGitRef } from "../4-deploy/git";
12
+ import os from "os";
13
+ import { runPromise } from "../functional/runCommand";
14
+ import { getSyncedController } from "../library-components/SyncedController";
11
15
 
12
16
  const POLL_INTERVAL = timeInMinute * 15;
13
17
 
@@ -78,27 +82,50 @@ class MachineControllerBase {
78
82
  }) {
79
83
  let caller = SocketFunction.getCaller();
80
84
  forwardedCallbacks.set(config.callbackId, caller.nodeId);
81
- await MachineController.nodes[config.nodeId].streamScreenOutput({
85
+ await MachineController(config.nodeId).streamScreenOutput.promise({
82
86
  key: config.key,
83
87
  index: config.index,
84
88
  callbackId: config.callbackId,
85
89
  });
86
90
  }
91
+
92
+ public async deployMachineFromBrowser(config: {
93
+ machineNodeId: string;
94
+ gitRef: string;
95
+ }) {
96
+ await MachineController(config.machineNodeId).deployService.promise({
97
+ gitRef: config.gitRef,
98
+ });
99
+ }
100
+
101
+ public async deployService(config: {
102
+ gitRef: string;
103
+ }) {
104
+ let gitFolder = os.homedir() + "/machine-alwaysup";
105
+ await setGitRef({
106
+ gitFolder,
107
+ gitRef: config.gitRef,
108
+ });
109
+ await runPromise("bash machine-startup.sh", { cwd: os.homedir() });
110
+ }
111
+
87
112
  }
88
113
 
89
114
  let forwardedCallbacks = new Map<string, string>();
90
115
 
91
- const MachineController = SocketFunction.register(
116
+ export const MachineController = getSyncedController(SocketFunction.register(
92
117
  "machine-controller-c3157d4a-580c-4e76-9dc9-072dd92e70af",
93
118
  () => new MachineControllerBase(),
94
119
  () => ({
95
120
  streamScreenOutput: {},
96
121
  watchOtherScreenOutput: {},
122
+ deployMachineFromBrowser: {},
123
+ deployService: {},
97
124
  }),
98
125
  () => ({
99
126
  hooks: [assertIsManagementUser],
100
127
  }),
101
- );
128
+ ));
102
129
 
103
130
  let callbacks = new Map<string, (data: string) => Promise<void>>();
104
131
  export async function watchScreenOutput(config: {
@@ -110,7 +137,7 @@ export async function watchScreenOutput(config: {
110
137
  }) {
111
138
  let callbackId = config.callbackId;
112
139
  callbacks.set(callbackId, config.onData);
113
- await MachineController.nodes[SocketFunction.browserNodeId()].watchOtherScreenOutput({
140
+ await MachineController(SocketFunction.browserNodeId()).watchOtherScreenOutput.promise({
114
141
  nodeId: config.nodeId,
115
142
  key: config.key,
116
143
  index: config.index,
@@ -13,12 +13,42 @@ import { getOwnMachineId } from "../-a-auth/certs";
13
13
  import { runInSerial, runInfinitePollCallAtStart } from "socket-function/src/batching";
14
14
  import { lazy } from "socket-function/src/caching";
15
15
  import { errorToUndefinedSilent } from "../errors";
16
- import { getGitRefLive, getGitURLLive } from "../4-deploy/git";
16
+ import { commitAndPush, getGitRefInfo, getGitRefLive, getGitURLLive, getGitUncommitted, getLatestRefOnUpstreamBranch, setGitRef } from "../4-deploy/git";
17
17
  import { OnServiceChange } from "./machineController";
18
+ import path from "path";
19
+ import fs from "fs";
20
+ import { runPromise } from "../functional/runCommand";
18
21
 
19
22
  export const SERVICE_FOLDER = "machine-services/";
20
23
  export const MACHINE_RESYNC_INTERVAL = timeInMinute * 15;
21
24
 
25
+ export type MachineInfo = {
26
+ machineId: string;
27
+
28
+ // Used to tell the apply tool to update it's configs now
29
+ applyNodeId: string;
30
+
31
+ heartbeat: number;
32
+ /*
33
+ // TODO: ShowMore on each of the infos, so large ones are fine.
34
+ hostnamectl (fallback to hostname)
35
+ getExternalIP()
36
+ lscpu
37
+ id (fallback to whoami)
38
+ */
39
+ info: Record<string, string>;
40
+
41
+ repoUrl: string;
42
+ gitRef: string;
43
+
44
+ services: Record<string, {
45
+ lastLaunchedTime: number;
46
+ errorFromLastRun: string;
47
+ // Only times launched for the current applyNodeId, but... still very useful.
48
+ totalTimesLaunched: number;
49
+ }>;
50
+ };
51
+
22
52
 
23
53
  export type ServiceConfig = {
24
54
  /** Just a random id to manage the service */
@@ -50,38 +80,13 @@ export type ServiceConfig = {
50
80
  lastUpdatedTime: number;
51
81
  };
52
82
  };
53
-
54
- export type MachineInfo = {
55
- machineId: string;
56
-
57
- // Used to tell the apply tool to update it's configs now
58
- applyNodeId: string;
59
-
60
- heartbeat: number;
61
- /*
62
- // TODO: ShowMore on each of the infos, so large ones are fine.
63
- hostnamectl (fallback to hostname)
64
- getExternalIP()
65
- lscpu
66
- id (fallback to whoami)
67
- */
68
- info: Record<string, string>;
69
-
70
- services: Record<string, {
71
- lastLaunchedTime: number;
72
- errorFromLastRun: string;
73
- // Only times launched for the current applyNodeId, but... still very useful.
74
- totalTimesLaunched: number;
75
- }>;
76
- };
77
-
78
- export const serviceConfigs = archiveJSONT<ServiceConfig>(() => nestArchives("machines/service-configs/", getArchivesBackblaze(getDomain())));
79
83
  export const machineInfos = archiveJSONT<MachineInfo>(() => nestArchives("machines/machine-heartbeats/", getArchivesBackblaze(getDomain())));
84
+ export const serviceConfigs = archiveJSONT<ServiceConfig>(() => nestArchives("machines/service-configs/", getArchivesBackblaze(getDomain())));
80
85
 
81
86
 
82
- export class DeployControllerBase {
87
+ export class MachineServiceControllerBase {
83
88
 
84
- public async getMachineList(): Promise<string[]> {
89
+ public async getMachineList() {
85
90
  return [...new Set([
86
91
  ...(await machineInfos.keys()),
87
92
  ])];
@@ -151,17 +156,28 @@ export class DeployControllerBase {
151
156
  await this.notifyMachines(config.machineIds, []);
152
157
  }
153
158
 
154
- public async setServiceConfig(serviceId: string, config: ServiceConfig) {
155
- config.info.lastUpdatedTime = Date.now();
156
- let serviceConfig = await serviceConfigs.get(serviceId);
159
+ public async setServiceConfigs(configs: ServiceConfig[]) {
160
+ let newMachines = new Set<string>();
161
+ let oldMachines = new Set<string>();
162
+ for (let config of configs) {
163
+ let serviceId = config.serviceId;
164
+ config.info.lastUpdatedTime = Date.now();
165
+ let serviceConfig = await serviceConfigs.get(serviceId);
157
166
 
158
- if (!serviceConfig) {
159
- throw new Error(`Service ${serviceId} does not exist`);
160
- }
167
+ if (!serviceConfig) {
168
+ throw new Error(`Service ${serviceId} does not exist`);
169
+ }
161
170
 
162
- // Set the new service config
163
- await serviceConfigs.set(serviceId, config);
164
- await this.notifyMachines(config.machineIds, serviceConfig.machineIds);
171
+ // Set the new service config
172
+ await serviceConfigs.set(serviceId, config);
173
+ for (let machineId of config.machineIds) {
174
+ newMachines.add(machineId);
175
+ }
176
+ for (let machineId of serviceConfig.machineIds) {
177
+ oldMachines.add(machineId);
178
+ }
179
+ }
180
+ await this.notifyMachines([...newMachines], [...oldMachines]);
165
181
  }
166
182
 
167
183
  public async deleteServiceConfig(serviceId: string) {
@@ -180,19 +196,86 @@ export class DeployControllerBase {
180
196
  }
181
197
  public async getGitInfo() {
182
198
  let repoUrl = await getGitURLLive();
183
- let gitRef = await getGitRefLive();
199
+ let uncommitted = await getGitUncommitted(".");
200
+ let latestRef = await getLatestRefOnUpstreamBranch(".");
201
+ let querysubFolder = path.resolve("../querysub");
202
+ let querysubRef = "";
203
+ let querysubUncommitted: string[] = [];
204
+ if (fs.existsSync(querysubFolder)) {
205
+ querysubRef = await getGitRefLive(querysubFolder);
206
+ querysubUncommitted = await getGitUncommitted(querysubFolder);
207
+ }
184
208
  return {
185
209
  repoUrl,
186
- gitRef,
210
+ latestRef,
211
+ uncommitted,
212
+ querysubRef,
213
+ querysubUncommitted,
187
214
  };
188
215
  }
216
+
217
+ public async getGitRefInfo(config: {
218
+ ref: string;
219
+ useQuerysub?: boolean;
220
+ }) {
221
+ if (!config.ref) return undefined;
222
+ try {
223
+ let gitDir = ".";
224
+ if (config.useQuerysub) {
225
+ gitDir = path.resolve("../querysub");
226
+ }
227
+ return await getGitRefInfo({
228
+ gitDir,
229
+ ref: config.ref,
230
+ });
231
+ } catch (error) {
232
+ console.error(error);
233
+ return undefined;
234
+ }
235
+ }
236
+
237
+ public async commitPushService(commitMessage: string) {
238
+ await commitAndPush({
239
+ gitDir: ".",
240
+ message: commitMessage,
241
+ });
242
+ }
243
+ public async commitPushAndPublishQuerysub(commitMessage: string) {
244
+ let querysubFolder = path.resolve("../querysub");
245
+ if (!fs.existsSync(querysubFolder)) {
246
+ throw new Error(`Querysub folder does not exist at ${querysubFolder}`);
247
+ }
248
+
249
+ // Increment minor version and publish to npm with yarn
250
+ await runPromise("yarn version --minor --no-git-tag-version", { cwd: querysubFolder });
251
+ await runPromise("yarn publish --non-interactive", { cwd: querysubFolder });
252
+
253
+ // Update package.json reference in our actual repo (version only, no install)
254
+ let querysubPackageJson = JSON.parse(fs.readFileSync(path.join(querysubFolder, "package.json"), "utf8"));
255
+ let newVersion = querysubPackageJson.version;
256
+
257
+ let currentPackageJsonPath = path.join(".", "package.json");
258
+ let currentPackageJson = JSON.parse(fs.readFileSync(currentPackageJsonPath, "utf8"));
259
+
260
+ if (!currentPackageJson.dependencies?.querysub) {
261
+ throw new Error(`Querysub is not a dependency in package.json?`);
262
+ }
263
+ currentPackageJson.dependencies.querysub = `^${newVersion}`;
264
+
265
+ fs.writeFileSync(currentPackageJsonPath, JSON.stringify(currentPackageJson, null, 2));
266
+
267
+ await commitAndPush({
268
+ gitDir: querysubFolder,
269
+ message: commitMessage,
270
+ });
271
+ }
189
272
  }
190
273
 
191
274
 
192
- export const DeployController = getSyncedController(
275
+ export const MachineServiceController = getSyncedController(
193
276
  SocketFunction.register(
194
- "deploy-eda94f05-5e4d-4f5a-b1c1-98613fba60b8",
195
- () => new DeployControllerBase(),
277
+ "machine-controller-eda94f05-5e4d-4f5a-b1c1-98613fba60b8",
278
+ () => new MachineServiceControllerBase(),
196
279
  () => ({
197
280
  getMachineList: {},
198
281
  deleteMachineIds: {},
@@ -202,10 +285,13 @@ export const DeployController = getSyncedController(
202
285
  getServiceList: {},
203
286
  getServiceConfig: {},
204
287
  addServiceConfig: {},
205
- setServiceConfig: {},
288
+ setServiceConfigs: {},
206
289
  getServiceConfigType: {},
207
290
  deleteServiceConfig: {},
208
291
  getGitInfo: {},
292
+ getGitRefInfo: {},
293
+ commitPushService: {},
294
+ commitPushAndPublishQuerysub: {},
209
295
  }),
210
296
  () => ({
211
297
  hooks: [assertIsManagementUser],
@@ -217,14 +303,17 @@ export const DeployController = getSyncedController(
217
303
  addMachineInfo: ["MachineInfo", "MachineInfoList"],
218
304
  setMachineInfo: ["MachineInfo"],
219
305
  addServiceConfig: ["ServiceConfig", "ServiceConfigList"],
220
- setServiceConfig: ["ServiceConfig"],
306
+ setServiceConfigs: ["ServiceConfig"],
221
307
  deleteServiceConfig: ["ServiceConfig", "ServiceConfigList"],
308
+ commitPushService: ["gitInfo"],
309
+ commitPushAndPublishQuerysub: ["gitInfo"],
222
310
  },
223
311
  reads: {
224
312
  getMachineList: ["MachineInfoList"],
225
313
  getMachineInfo: ["MachineInfo"],
226
314
  getServiceList: ["ServiceConfigList"],
227
315
  getServiceConfig: ["ServiceConfig"],
316
+ getGitInfo: ["gitInfo"],
228
317
  }
229
318
  }
230
319
  );
@@ -1,62 +1,4 @@
1
- Ugh...
2
- 1) Our local http server can't talk to the remote PathValueServer server?
3
- 2) The remote http server isn't loading the modules?
4
- - Which... come from permissions, and so the PathValueServer?
5
- - Ah, and, it can't find the PathValueServer either?
6
-
7
- OH! It is... that we keep picking the wrong server, thinking it is working, but it has an old config?
8
-
9
- bd6cf9eb4accffba8
10
-
11
- 4) Add 2X redundancy to PathValueServer, and... FunctionRunner?
12
-
13
-
14
- 5) Setup on our regular digital ocean server
15
- - Setup all the services in the new UI
16
- - Copy from the previous startup.sh, running the same services
17
- - Changing the UI if anything is extremely annoying, but... I don't see how it would be...
18
- tmux send-keys -t server1 "cd ~/cyoa && yarn server-public" Enter
19
- tmux send-keys -t server2 "cd ~/cyoa && yarn server-public" Enter
20
- tmux send-keys -t fnc "cd ~/cyoa && yarn function-public --verbosecalls" Enter
21
-
22
- tmux send-keys -t http "cd ~/cyoa && yarn cyoa-public --verbosecalls" Enter
23
- tmux send-keys -t watch "cd ~/cyoa && yarn gc-watch-public" Enter
24
- tmux send-keys -t join "cd ~/cyoa && yarn join-public" Enter
25
- 5) Verify the editor works
26
-
27
-
28
-
29
-
30
- 8) REIMPLEMENT yarn do-update functionality, with UI on the configuration page
31
- - Components
32
- <UpdateButtons />
33
- - Commit all (add, commit, push)
34
- - Only shows up if there are unsaved changes
35
- - Commit querysub (publish, add, commit, push querysub, update package.json of app, add, commit, push)
36
- - Only shows up if there are unsaved changes
37
- - Deploy all (set hash to latest and save)
38
- - Only shows up if (any) deployed hashes differ from latest for app
39
- <UpdateServiceButtons service={serviceConfig} />
40
- - Commit (add, commit, push)
41
- - Only shows up if there are unsaved changes
42
- - Deploy (set hash to latest and save)
43
- - Only shows up if deployed hash differ from latest for app
44
- - Endpoints
45
- - anyQuerysubUnsaved
46
- - anyAppUnsaved
47
- - querysubLatestHash
48
- - appLatestHash (already have this)
49
- - publish, add, commit, and push querysub (and update app package.json reference)
50
- - add, commit and push app
51
-
52
- - On services list page, and individual service page
53
- - So... maybe the button a component
54
- - MULTIPLE buttons, to just update the main site, just querysub, or both
55
- - Button to update on each service where the repoUrl === the repoUrl of the server
56
- - Only from a non-public server
57
- - ALSO, button to update all (that match repoUrl)
58
- - Commit, push, update hash
59
- - Also with an option to also update querysub (it'll tell us if querysub has changes), updating package.json to
1
+ OH, okay, so... we DO need machine update support, because... we will need to update them
60
2
 
61
3
 
62
4
  7) Quick node removal on process crash OR removal
@@ -67,6 +9,8 @@ bd6cf9eb4accffba8
67
9
 
68
10
 
69
11
  In general, hit our servers hard, to make sure we can launch them, they can talk to each other, etc. Even with entirely new folders (to somewhat emulate another machine), and they can all startup smoothly.
12
+
13
+ AH, I think I fixed that bug. I think it was an issue with using old hosts?
70
14
  6) BUG! On startup, new nodes might take a poll interval to be fully ready? Hmm... we should restart our servers a lot again to make sure they come back up QUICKLY
71
15
  - OH! It might be that the identity takes some time to propagate (the DNS), which causes us to require a second poll to be alive? Maybe... our local machine deleted it, because it couldn't see the DNS? No... none of these are reasonable...
72
16
  - Try changing the key, so it syncs again, so we start fresh with the server
@@ -76,9 +20,6 @@ In general, hit our servers hard, to make sure we can launch them, they can talk
76
20
  FORTUNATELY, looking at logs is now very simple, as well as updating nodes, so... this shouldn't be too hard to debug
77
21
 
78
22
 
79
- 6) Verify PathValueServer gracefully shutdowns, not losing any values (because it delays and flushes writes before shutting down, detecting the ctrl+c).
80
-
81
-
82
23
  8) Fix deploy user notification issue, where the refresh button doesn't work?
83
24
 
84
25
  9) Rolling service updates