Skip to content

Commit

Permalink
Refactor Card list for service instances (#732)
Browse files Browse the repository at this point in the history
* Refactor Card list for service instances

* Rename PreformattedCard for InfoCard. Other minor css changes
  • Loading branch information
andresmgot committed Oct 17, 2018
1 parent 82a54d7 commit a29ec5c
Show file tree
Hide file tree
Showing 18 changed files with 476 additions and 188 deletions.
11 changes: 11 additions & 0 deletions dashboard/src/components/AppList/AppListItem.scss
@@ -0,0 +1,11 @@
.deleted {
background-color: #c5c5c5;
}

.failed {
background-color: #cb1515;
}

.deployed {
background-color: #15cb2d;
}
28 changes: 8 additions & 20 deletions dashboard/src/components/AppList/AppListItem.test.tsx
Expand Up @@ -3,7 +3,7 @@ import * as React from "react";
import { Link } from "react-router-dom";

import { IAppOverview } from "../../shared/types";
import Card from "../Card";
import InfoCard from "../InfoCard";
import AppListItem from "./AppListItem";

it("renders a app item", () => {
Expand All @@ -19,23 +19,11 @@ it("renders a app item", () => {
}
/>,
);
expect(wrapper.find(Card).key()).toBe("foo");
expect(
wrapper
.find(Card)
.children()
.find(Link)
.props().title,
).toBe("foo");
expect(
wrapper
.find(Card)
.children()
.find(Link)
.props().to,
).toBe("/apps/ns/default/foo");
expect(wrapper.find(".ChartListItem__content__info_version").text()).toBe("1.0.0");
expect(wrapper.find(".DEPLOYED").exists()).toBe(true);
expect(wrapper.find(".ChartListItem__content__info_repo").text()).toBe("default");
expect(wrapper.find(".ChartListItem__content__info_other").text()).toBe("deployed");
const card = wrapper.find(InfoCard).shallow();
expect(card.find(Link).props().title).toBe("foo");
expect(card.find(Link).props().to).toBe("/apps/ns/default/foo");
expect(card.find(".type-color-light-blue").text()).toBe("1.0.0");
expect(card.find(".deployed").exists()).toBe(true);
expect(card.find(".ListItem__content__info_tag-1").text()).toBe("default");
expect(card.find(".ListItem__content__info_tag-2").text()).toBe("deployed");
});
46 changes: 12 additions & 34 deletions dashboard/src/components/AppList/AppListItem.tsx
@@ -1,10 +1,9 @@
import * as React from "react";
import { Link } from "react-router-dom";

import placeholder from "../../placeholder.png";
import { IAppOverview } from "../../shared/types";
import Card, { CardContent, CardIcon } from "../Card";
import "../ChartList/ChartListItem.css";
import InfoCard from "../InfoCard";
import "./AppListItem.css";

interface IAppListItemProps {
app: IAppOverview;
Expand All @@ -16,37 +15,16 @@ class AppListItem extends React.Component<IAppListItemProps> {
const icon = app.icon ? app.icon : placeholder;

return (
<Card key={app.releaseName} responsive={true} className="AppListItem">
<Link to={`/apps/ns/${app.namespace}/${app.releaseName}`} title={app.releaseName}>
<CardIcon icon={icon} />
<CardContent>
<div className="ChartListItem__content">
<h3 className="ChartListItem__content__title type-big">{app.releaseName}</h3>
<div className="ChartListItem__content__info">
<p className="ChartListItem__content__info_version margin-reset type-small padding-t-tiny type-color-light-blue">
{app.version || "-"}
</p>
<div>
<span
className={
"ChartListItem__content__info_repo type-small type-color-white padding-t-tiny padding-h-normal"
}
>
{app.namespace}
</span>
<span
className={`ChartListItem__content__info_other ${
app.status
} type-small type-color-white padding-t-tiny padding-h-normal`}
>
{app.status.toLowerCase()}
</span>
</div>
</div>
</div>
</CardContent>
</Link>
</Card>
<InfoCard
key={app.releaseName}
link={`/apps/ns/${app.namespace}/${app.releaseName}`}
title={app.releaseName}
icon={icon}
info={app.version || "-"}
tag1Content={app.namespace}
tag2Content={app.status.toLocaleLowerCase()}
tag2Class={app.status.toLocaleLowerCase()}
/>
);
}
}
Expand Down
50 changes: 2 additions & 48 deletions dashboard/src/components/ChartList/ChartListItem.scss
@@ -1,53 +1,7 @@
.ChartListItem {
color: #1c2b39;
}

.ChartListItem__content__title {
margin: 0;
width: 100%;
font-weight: bold;
text-overflow: ellipsis;
overflow: hidden;
white-space: nowrap;
color: #1c2b39;
}

.ChartListItem__content__info {
display: flex;
justify-content: space-between;
}

.ChartListItem__content__info_repo {
display: inline-block;
color: #fff;
border-radius: 16px;
background-color: #1c2b39;
}

.ChartListItem__content__info_other {
display: inline-block;
color: rgb(0, 0, 0);
margin-left: 0.3em;
border-radius: 16px;
background-color: #1598cb;
}

.DELETED {
background-color: #c5c5c5;
}

.FAILED {
background-color: #cb1515;
}

.DEPLOYED {
background-color: #15cb2d;
}

.ChartListItem__content__info_repo.stable {
.ListItem__content__info_tag.stable {
background-color: #1598cb;
}

.ChartListItem__content__info_repo.incubator {
.ListItem__content__info_tag.incubator {
background-color: #f58220;
}
17 changes: 15 additions & 2 deletions dashboard/src/components/ChartList/ChartListItem.test.tsx
Expand Up @@ -3,6 +3,7 @@ import * as React from "react";

import { IChart, IRepo } from "../../shared/types";
import { CardIcon } from "../Card";
import InfoCard from "../InfoCard";
import ChartListItem from "./ChartListItem";

jest.mock("../../placeholder.png", () => "placeholder.png");
Expand Down Expand Up @@ -37,12 +38,24 @@ it("should use the default placeholder for the icon if it doesn't exist", () =>
chartWithoutIcon.attributes.icon = undefined;
const wrapper = shallow(<ChartListItem chart={chartWithoutIcon} />);
// Importing an image returns "undefined"
expect(wrapper.find(CardIcon).prop("src")).toBe(undefined);
expect(
wrapper
.find(InfoCard)
.shallow()
.find(CardIcon)
.prop("src"),
).toBe(undefined);
});

it("should place a dash if the version is not avaliable", () => {
const chartWithoutVersion = { ...defaultChart };
chartWithoutVersion.relationships.latestChartVersion.data.app_version = "";
const wrapper = shallow(<ChartListItem chart={chartWithoutVersion} />);
expect(wrapper.find(".ChartListItem__content__info_version").text()).toBe("-");
expect(
wrapper
.find(InfoCard)
.shallow()
.find(".type-color-light-blue")
.text(),
).toBe("-");
});
34 changes: 10 additions & 24 deletions dashboard/src/components/ChartList/ChartListItem.tsx
@@ -1,9 +1,8 @@
import * as React from "react";
import { Link } from "react-router-dom";

import placeholder from "../../placeholder.png";
import { IChart } from "../../shared/types";
import Card, { CardContent, CardIcon } from "../Card";
import InfoCard from "../InfoCard";

import "./ChartListItem.css";

Expand All @@ -18,28 +17,15 @@ class ChartListItem extends React.Component<IChartListItemProps> {
const iconSrc = icon ? `/api/chartsvc/${icon}` : placeholder;
const latestAppVersion = chart.relationships.latestChartVersion.data.app_version;
return (
<Card key={`${repo}/${name}`} responsive={true} className="ChartListItem">
<Link to={"/charts/" + chart.id} title={name}>
<CardIcon icon={iconSrc} />
<CardContent>
<div className="ChartListItem__content">
<h3 className="ChartListItem__content__title type-big">{name}</h3>
<div className="ChartListItem__content__info">
<p className="ChartListItem__content__info_version margin-reset type-small padding-t-tiny type-color-light-blue">
{latestAppVersion || "-"}
</p>
<span
className={`ChartListItem__content__info_repo ${
repo.name
} type-small padding-t-tiny padding-h-normal`}
>
{repo.name}
</span>
</div>
</div>
</CardContent>
</Link>
</Card>
<InfoCard
key={`${repo}/${name}`}
title={name}
link={`/charts/${chart.id}`}
info={latestAppVersion || "-"}
icon={iconSrc}
tag1Content={repo.name}
tag1Class={repo.name}
/>
);
}
}
Expand Down
@@ -1,42 +1,11 @@
// Jest Snapshot v1, https://goo.gl/fbAQLP

exports[`should render an item 1`] = `
<Card
className="ChartListItem"
<InfoCard
icon="/api/chartsvc/icon.png"
info="1.0.0"
key="[object Object]/foo"
responsive={true}
>
<Link
replace={false}
title="foo"
to="/charts/foo"
>
<CardIcon
icon="/api/chartsvc/icon.png"
/>
<CardContent>
<div
className="ChartListItem__content"
>
<h3
className="ChartListItem__content__title type-big"
>
foo
</h3>
<div
className="ChartListItem__content__info"
>
<p
className="ChartListItem__content__info_version margin-reset type-small padding-t-tiny type-color-light-blue"
>
1.0.0
</p>
<span
className="ChartListItem__content__info_repo undefined type-small padding-t-tiny padding-h-normal"
/>
</div>
</div>
</CardContent>
</Link>
</Card>
link="/charts/foo"
title="foo"
/>
`;
34 changes: 34 additions & 0 deletions dashboard/src/components/InfoCard/InfoCard.scss
@@ -0,0 +1,34 @@
.ListItem {
color: #1c2b39;
}

.ListItem__content__title {
margin: 0;
width: 100%;
font-weight: bold;
text-overflow: ellipsis;
overflow: hidden;
white-space: nowrap;
color: #1c2b39;
}

.ListItem__content__info {
display: flex;
justify-content: space-between;
}

.ListItem__content__info_tag {
float: right;
margin-left: 3px;
margin-bottom: 3px;
color: #fff;
border-radius: 16px;
}

.ListItem__content__info_tag-1 {
background-color: #1c2b39;
}

.ListItem__content__info_tag-2 {
background-color: #1598cb;
}
43 changes: 43 additions & 0 deletions dashboard/src/components/InfoCard/InfoCard.test.tsx
@@ -0,0 +1,43 @@
import { shallow } from "enzyme";
import * as React from "react";

import { Link } from "react-router-dom";
import InfoCard from "./InfoCard";

it("should render a Card", () => {
const wrapper = shallow(
<InfoCard
title="foo"
info="foobar"
link="/a/link/somewhere"
icon="an-icon.png"
tag1Class="blue"
tag1Content="database"
tag2Class="red"
tag2Content="running"
/>,
);
expect(wrapper).toMatchSnapshot();
});

it("should generate a dummy link if it's not provided", () => {
const wrapper = shallow(
<InfoCard
title="foo"
info="foobar"
icon="an-icon.png"
tag1Class="blue"
tag1Content="database"
tag2Class="red"
tag2Content="running"
/>,
);
expect(wrapper.find(Link).props()).toMatchObject({ to: "#" });
});

it("should avoid tags if they are not defined", () => {
const wrapper = shallow(
<InfoCard title="foo" info="foobar" link="/a/link/somewhere" icon="an-icon.png" />,
);
expect(wrapper.find(".ListItem__content__info_tag")).not.toExist();
});

0 comments on commit a29ec5c

Please sign in to comment.