Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
sagemathinc
GitHub Repository: sagemathinc/cocalc
Path: blob/master/src/packages/next/pages/index.tsx
1447 views
1
/*
2
* This file is part of CoCalc: Copyright © 2021 Sagemath, Inc.
3
* License: MS-RSL – see LICENSE.md for details
4
*/
5
6
import { Layout, Tooltip } from "antd";
7
import { GetServerSidePropsContext } from "next";
8
import { join } from "path";
9
10
import { getRecentHeadlines } from "@cocalc/database/postgres/news";
11
import { COLORS } from "@cocalc/util/theme";
12
import { RecentHeadline } from "@cocalc/util/types/news";
13
import { CoCalcComFeatures } from "components/landing/cocalc-com-features";
14
import Content from "components/landing/content";
15
import Footer from "components/landing/footer";
16
import Head from "components/landing/head";
17
import Header from "components/landing/header";
18
import { NewsBanner } from "components/landing/news-banner";
19
import { Tagline } from "components/landing/tagline";
20
import Logo from "components/logo";
21
import { CSS, Paragraph, Title } from "components/misc";
22
import A from "components/misc/A";
23
import Videos, { Video } from "components/videos";
24
import basePath from "lib/base-path";
25
import { Customize, CustomizeType } from "lib/customize";
26
import { PublicPath as PublicPathType } from "lib/share/types";
27
import withCustomize from "lib/with-customize";
28
import screenshot from "public/cocalc-screenshot-20200128-nq8.png";
29
30
import type { JSX } from "react";
31
32
const TOP_LINK_STYLE: CSS = { marginRight: "20px" } as const;
33
34
interface Props {
35
customize: CustomizeType;
36
publicPaths: PublicPathType[];
37
recentHeadlines: RecentHeadline[] | null;
38
headlineIndex: number;
39
}
40
41
export default function Home(props: Props) {
42
const { customize, recentHeadlines, headlineIndex } = props;
43
const {
44
siteName,
45
siteDescription,
46
organizationName,
47
organizationURL,
48
splashImage,
49
indexInfo,
50
onCoCalcCom,
51
account,
52
isCommercial,
53
indexTagline,
54
} = customize;
55
56
function contentDescription() {
57
return (
58
<Paragraph type="secondary">
59
{onCoCalcCom ? (
60
<>by Sagemath, Inc.</>
61
) : (
62
<>
63
An instance of <A href="https://cocalc.com">CoCalc</A>
64
{organizationName && organizationURL ? (
65
<>
66
{" "}
67
hosted by <A href={organizationURL}>{organizationName}</A>
68
</>
69
) : undefined}
70
.
71
</>
72
)}
73
</Paragraph>
74
);
75
}
76
77
function topAccountLinks() {
78
if (!account) return;
79
return (
80
<div
81
style={{
82
textAlign: "center",
83
margin: "30px 0 15px 0",
84
}}
85
>
86
<Title level={1} style={{ color: COLORS.GRAY }}>
87
Signed in as{" "}
88
<Tooltip title={"View all your account settings"} placement={"right"}>
89
<a href={join(basePath, "settings")}>
90
{`${account.first_name} ${account.last_name} ${
91
account.name ? "(@" + account.name + ")" : ""
92
}`}
93
</a>
94
</Tooltip>
95
</Title>
96
<Paragraph style={{ fontSize: "11pt", margin: "15px 0" }}>
97
{isCommercial && account && !account.is_anonymous && (
98
<>
99
<a href={join(basePath, "store")} style={TOP_LINK_STYLE}>
100
Store
101
</a>{" "}
102
<a
103
href={join(basePath, "settings/purchases")}
104
style={TOP_LINK_STYLE}
105
>
106
Purchases
107
</a>{" "}
108
<A href={"/vouchers"} style={TOP_LINK_STYLE}>
109
Vouchers
110
</A>{" "}
111
</>
112
)}
113
<a href={join(basePath, "projects")} style={TOP_LINK_STYLE}>
114
Projects
115
</a>{" "}
116
{customize.landingPages && (
117
<>
118
<A href="/features/" style={TOP_LINK_STYLE}>
119
Features
120
</A>{" "}
121
<A href="/software" style={TOP_LINK_STYLE}>
122
Software
123
</A>{" "}
124
{isCommercial && (
125
<>
126
<A href="/pricing" style={TOP_LINK_STYLE}>
127
Pricing
128
</A>{" "}
129
</>
130
)}
131
</>
132
)}
133
</Paragraph>
134
</div>
135
);
136
}
137
138
function renderCoCalcComFeatures() {
139
if (!onCoCalcCom) return;
140
return <CoCalcComFeatures />;
141
}
142
143
function logo(): JSX.Element {
144
return <Logo type="full" style={{ width: "50%" }} />;
145
}
146
147
function renderNews() {
148
if (recentHeadlines == null) return;
149
return (
150
<NewsBanner
151
recentHeadlines={recentHeadlines}
152
headlineIndex={headlineIndex}
153
/>
154
);
155
}
156
157
return (
158
<Customize value={customize}>
159
<Head title={siteDescription ?? "Collaborative Calculation"} />
160
<Layout>
161
<Header />
162
<Layout.Content style={{ backgroundColor: "white" }}>
163
{renderNews()}
164
{topAccountLinks()}
165
<Content
166
style={{ minHeight: "30vh" }}
167
body={logo()}
168
title={onCoCalcCom ? "" : siteName}
169
subtitle={siteDescription}
170
description={contentDescription()}
171
image={splashImage ? splashImage : screenshot}
172
alt={"Screenshot showing CoCalc in action!"}
173
imageAlternative={
174
onCoCalcCom ? <Videos videos={YOUTUBE_IDS} /> : indexInfo
175
}
176
/>
177
<Tagline value={indexTagline} style={{ padding: "5px" }} />
178
{renderCoCalcComFeatures()}
179
<Footer />
180
</Layout.Content>
181
</Layout>
182
</Customize>
183
);
184
}
185
186
export async function getServerSideProps(context: GetServerSidePropsContext) {
187
// get most recent headlines
188
const recentHeadlines = await getRecentHeadlines(5);
189
// we want to not always show the same headlines at the start
190
const headlineIndex =
191
recentHeadlines != null
192
? Math.floor(Date.now() % recentHeadlines.length)
193
: 0;
194
195
return await withCustomize(
196
{ context, props: { recentHeadlines, headlineIndex } },
197
{ name: true },
198
);
199
}
200
201
const YOUTUBE_IDS: Readonly<Video[]> = [
202
{ id: "oDdfmkQ0Hvw", title: "CoCalc Overview" },
203
{ id: "UfmjYxalyh0", title: "Using AI in CoCalc" },
204
{ id: "LLtLFtD8qfo", title: "Using JupyterLab in CoCalc" },
205
{ id: "OMN1af0LUcA", title: "Using OpenWebUI and Ollama On CoCalc" },
206
{ id: "Owq90O0vLJo", title: "R Studio on CoCalc" },
207
{ id: "JG6jm6yv_KE", title: "PyTorch with a GPU on CoCalc" },
208
{
209
id: "Uwn3ngzXD0Y",
210
title: "JAX Quickstart on CoCalc using a GPU (or on CPU)",
211
},
212
{ id: "NkNx6tx3nu0", title: "Running On-Prem Compute Servers on CoCalc" },
213
] as const;
214
215