CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutSign UpSign In
sagemathinc

Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.

GitHub Repository: sagemathinc/cocalc
Path: blob/master/src/packages/frontend/compute/onprem-config.tsx
Views: 687
1
import type {
2
ComputeServerTemplate,
3
OnPremCloudConfiguration,
4
State,
5
} from "@cocalc/util/db-schema/compute-servers";
6
import { ON_PREM_DEFAULTS } from "@cocalc/util/db-schema/compute-servers";
7
import { Checkbox, Divider, Select, Spin } from "antd";
8
import { setServerConfiguration } from "./api";
9
import { useEffect, useState } from "react";
10
import SelectImage, { ImageDescription, ImageLinks } from "./select-image";
11
import ExcludeFromSync from "./exclude-from-sync";
12
import ShowError from "@cocalc/frontend/components/error";
13
import Ephemeral from "./ephemeral";
14
import { SELECTOR_WIDTH } from "./google-cloud-config";
15
import Proxy from "./proxy";
16
import { useImages } from "./images-hook";
17
import DNS from "@cocalc/frontend/compute/cloud/common/dns";
18
import { A, Icon } from "@cocalc/frontend/components";
19
import Template from "@cocalc/frontend/compute/cloud/common/template";
20
import { useTypedRedux } from "@cocalc/frontend/app-framework";
21
22
interface Props {
23
configuration: OnPremCloudConfiguration;
24
editable?: boolean;
25
// if id not set, then doesn't try to save anything to the backend
26
id?: number;
27
project_id: string;
28
// called whenever changes are made.
29
onChange?: (configuration: OnPremCloudConfiguration) => void;
30
disabled?: boolean;
31
state?: State;
32
data?;
33
template?: ComputeServerTemplate;
34
}
35
36
export default function OnPremCloudConfiguration({
37
configuration: configuration0,
38
editable,
39
id,
40
project_id,
41
onChange,
42
disabled,
43
state,
44
data,
45
template,
46
}: Props) {
47
const [IMAGES, ImagesError] = useImages();
48
const [loading, setLoading] = useState<boolean>(false);
49
const [error, setError] = useState<string>("");
50
const [configuration, setLocalConfiguration] =
51
useState<OnPremCloudConfiguration>(configuration0);
52
53
useEffect(() => {
54
if (!editable) {
55
setLocalConfiguration(configuration0);
56
}
57
}, [configuration0]);
58
59
const setConfig = async (changes) => {
60
try {
61
const newConfiguration = { ...configuration, ...changes };
62
setLoading(true);
63
if (onChange != null) {
64
onChange(newConfiguration);
65
}
66
setLocalConfiguration(newConfiguration);
67
if (id != null) {
68
await setServerConfiguration({ id, configuration: changes });
69
}
70
} catch (err) {
71
setError(`${err}`);
72
} finally {
73
setLoading(false);
74
}
75
};
76
77
if (!editable || !project_id) {
78
return (
79
<div>
80
Self Hosted {configuration.arch == "arm64" ? "ARM64" : "x86_64"} Linux
81
VM
82
{configuration.gpu ? " that has an NVIDIA GPU" : ""}.
83
</div>
84
);
85
}
86
87
if (ImagesError != null) {
88
return ImagesError;
89
}
90
91
return (
92
<div style={{ marginBottom: "30px" }}>
93
<div style={{ color: "#666", marginBottom: "15px" }}>
94
<div style={{ color: "#666", marginBottom: "5px" }}>
95
<b>Self Hosted Compute Server</b>
96
</div>
97
You can connect your own <b>Ubuntu 22.04 Virtual Machine</b> to this
98
CoCalc project and seamlessly run Jupyter notebooks and terminals on it.
99
<ul>
100
<li>
101
Watch the{" "}
102
<A href="https://youtu.be/NkNx6tx3nu0">
103
<Icon name="youtube" style={{ color: "red" }} /> compute server
104
tutorial
105
</A>
106
.
107
</li>
108
<li>Self hosted compute servers are currently free.</li>
109
<li>
110
<A href="https://onprem.cocalc.com/overview.html">CoCalc OnPrem</A>{" "}
111
is a related product for running a self-contained CoCalc cluster.
112
</li>
113
</ul>
114
</div>
115
<div style={{ color: "#666", marginBottom: "5px" }}>
116
<b>Architecture</b>
117
</div>
118
<Select
119
disabled={loading || disabled}
120
style={{ width: SELECTOR_WIDTH }}
121
options={[
122
{ label: "x86_64 (e.g., Linux VM on Intel or AMD)", value: "x86_64" },
123
{
124
label: "ARM 64 (e.g., Linux VM on an M1 Mac)",
125
value: "arm64",
126
disabled: configuration.gpu,
127
},
128
]}
129
value={configuration.arch ?? "x86_64"}
130
onChange={(arch) => {
131
setConfig({ arch });
132
}}
133
/>
134
<div style={{ margin: "15px 0" }}>
135
<Checkbox
136
disabled={
137
loading ||
138
disabled ||
139
configuration.arch ==
140
"arm64" /* we only have x86_64 docker images */
141
}
142
style={{ width: SELECTOR_WIDTH }}
143
checked={configuration.gpu}
144
onChange={() => {
145
setConfig({
146
gpu: !configuration.gpu,
147
image:
148
ON_PREM_DEFAULTS[!configuration.gpu ? "gpu" : "cpu"]?.image,
149
});
150
}}
151
>
152
NVIDIA GPU with CUDA 12.x installed
153
</Checkbox>
154
</div>
155
<Image
156
state={state}
157
disabled={loading || disabled}
158
setConfig={setConfig}
159
configuration={configuration}
160
/>
161
<ShowError error={error} setError={setError} />
162
<Divider />
163
<Proxy
164
id={id}
165
project_id={project_id}
166
setConfig={setConfig}
167
configuration={configuration}
168
data={data}
169
state={state}
170
IMAGES={IMAGES}
171
/>
172
{data?.externalIp && (
173
<>
174
<Divider />
175
<DNS
176
setConfig={setConfig}
177
configuration={configuration}
178
loading={loading}
179
/>
180
</>
181
)}
182
{loading && <Spin style={{ marginLeft: "15px" }} />}
183
<Admin id={id} template={template} />
184
</div>
185
);
186
}
187
188
function Admin({ id, template }) {
189
const isAdmin = useTypedRedux("account", "is_admin");
190
if (!isAdmin) {
191
return null;
192
}
193
return <Template id={id} template={template} />;
194
}
195
196
function Image(props) {
197
const { state = "deprovisioned" } = props;
198
return (
199
<div>
200
<div style={{ color: "#666", marginBottom: "5px" }}>
201
<b>Image</b>
202
</div>
203
{(state == "deprovisioned" || state == "off") && (
204
<div style={{ color: "#666", marginBottom: "5px" }}>
205
Select compute server image. You will be able to use sudo with no
206
password and can easily install anything into the Ubuntu Linux image.
207
</div>
208
)}
209
<SelectImage
210
{...props}
211
gpu={!!props.configuration.gpu}
212
arch={props.configuration.arch}
213
warnBigGb={4}
214
/>
215
<div style={{ color: "#666", marginTop: "5px" }}>
216
<ImageDescription configuration={props.configuration} />
217
<ImageLinks
218
image={props.configuration.image}
219
style={{ flexDirection: "row" }}
220
/>
221
{!(state == "deprovisioned" || state == "off") && (
222
<div style={{ color: "#666", marginTop: "5px" }}>
223
You can only edit the image when server is deprovisioned or off.
224
</div>
225
)}
226
</div>
227
<ExcludeFromSync {...props} />
228
<Divider />
229
<Ephemeral style={{ marginTop: "30px" }} {...props} />
230
</div>
231
);
232
}
233
234