Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Real-time collaboration for Jupyter Notebooks, Linux Terminals, LaTeX, VS Code, R IDE, and more,
all in one place.
Path: blob/master/src/packages/next/components/landing/software-libraries.tsx
Views: 687
/*1* This file is part of CoCalc: Copyright © 2022 Sagemath, Inc.2* License: MS-RSL – see LICENSE.md for details3*/45import { Divider, Input, Table } from "antd";6import { debounce } from "lodash";7import { useMemo, useState } from "react";89import { Paragraph, Text } from "components/misc";10import A from "components/misc/A";11import { getLibaries } from "lib/landing/get-libraries";12import {13ComputeComponents,14ComputeInventory,15Item,16LanguageName,17SoftwareSpec,18} from "lib/landing/types";1920// check if the string is a URL21function isURL(url?: string) {22return url && url.match(/^(http|https):\/\//);23}2425export function renderName(name, record) {26const url = record.url;27return (28<div>29<b>{isURL(url) ? <A href={url}>{name}</A> : name}</b>30<br />31{record.summary}32</div>33);34}3536type Columns = {37width: string;38title: string;39key: string;40dataIndex: string;41render?: typeof renderName;42}[];43interface Props {44timestamp: string;45libWidthPct?: number;46spec: SoftwareSpec[LanguageName];47inventory: ComputeInventory[LanguageName];48components: ComputeComponents[LanguageName];49}5051export default function SoftwareLibraries(props: Props) {52const { spec, inventory, components, libWidthPct = 60, timestamp } = props;53const dataSource = getLibaries(spec, inventory, components);54const [search, setSearch] = useState<string>("");55const onChange = useMemo(56() =>57debounce((e) => {58setSearch(e.target.value);59}, 500),60[]61);6263let data: Item[];64if (!search) {65data = dataSource;66} else {67const s = search.toLowerCase();68data = [];69for (const x of dataSource) {70if (x.search.includes(s)) {71data.push(x);72}73}74}7576const columns = useMemo((): Columns => {77const envs = Object.entries(spec);78const width = (100 - libWidthPct) / envs.length;7980const columns: Columns = [81{82width: `${libWidthPct}%`,83title: "Library",84key: "library",85dataIndex: "name",86render: renderName,87},88];8990for (const [name, val] of envs) {91columns.push({92width: `${width}%`,93title: val.name,94key: name,95dataIndex: name,96});97}9899return columns;100}, [libWidthPct]);101102return (103<div>104<h2>Showing {data.length} libraries</h2>105<Input.Search106style={{ padding: "0 30px 15px 0", width: "50%", minWidth: "300px" }}107placeholder="Search..."108allowClear109onChange={onChange}110onPressEnter={(e) => setSearch((e.target as any).value)}111/>112<div style={{ overflowX: "auto", width: "100%" }}>113<Table114columns={columns}115bordered116pagination={false}117rowKey={"index"}118dataSource={data}119/>120</div>121<SoftwareSpecTimestamp timestamp={timestamp} />122</div>123);124}125126export function SoftwareSpecTimestamp({ timestamp }: { timestamp: string }) {127return (128<>129<Divider />130<Paragraph style={{ textAlign: "center" }}>131<Text type="secondary">132This information was collected at {timestamp}.133</Text>134</Paragraph>135</>136);137}138139140