Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
366 changes: 136 additions & 230 deletions website/src/assets/images/infographs/Architecture.svg
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
Binary file modified website/src/assets/images/pluginised.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
1,158 changes: 859 additions & 299 deletions website/src/css/customTheme.css

Large diffs are not rendered by default.

276 changes: 81 additions & 195 deletions website/src/pages/index.js
Original file line number Diff line number Diff line change
@@ -1,218 +1,104 @@
const React = require("react");
import Link from "@docusaurus/Link";
import React, { useState, useEffect, useLayoutEffect } from "react";
import useDocusaurusContext from "@docusaurus/useDocusaurusContext";
import useBaseUrl from "@docusaurus/useBaseUrl";
import Layout from "@theme/Layout";
import GitHubLogo from "../assets/icons/github-logo.svg";
import { useState, useEffect } from "react";
import { CSSTransition } from "react-transition-group";
import ChevronRight from "../assets/icons/chevron-right.svg";
import useThemeContext from '@theme/hooks/useThemeContext';

const HomeSplash = () => {
const [featureWordIndex, setFeatureWordIndex] = useState(0);
const featureWords = ["Dynamic", "Real-Time", "Performant"];
import HeroSection from "./sections/heroSection";
import Architecture from "./sections/architecture";
import Features from "./sections/features";
import Benefits from "./sections/benefits";
import Comparison from "./sections/comparison";
import OpensourcePromo from "./sections/opensourcePromo";
import NewsSection from "./sections/newsSection";
import EndCTA from "./sections/endcta";
import EventPosterCard from "./sections/components/eventPosterCard";

const [isShow, setIsShow] = useState(true);
const useWindowSize = () => {
const [size, setSize] = useState([0, 0]);
useLayoutEffect(() => {
function updateSize() {
setSize([window.innerWidth, window.innerHeight]);
}
window.addEventListener('resize', updateSize);
updateSize();
return () => window.removeEventListener('resize', updateSize);
}, []);
return size;
}

const changeFeatureWordIndex = (index) => {
setIsShow(false);
setFeatureWordIndex(index);
setIsShow(true);
};

useEffect(() => {
const timer = setInterval(() => {
if (featureWordIndex >= featureWords.length - 1) {
changeFeatureWordIndex(0);
} else {
changeFeatureWordIndex(featureWordIndex + 1);
}
}, 3600);
return () => clearInterval(timer);
}, [featureWordIndex]);
const Showcase = () => {
const {isDarkTheme, setLightTheme, setDarkTheme} = useThemeContext();

useEffect(() => {
if(isDarkTheme) {
setLightTheme(true);
}
}, [])

const { siteConfig } = useDocusaurusContext();
if (!(siteConfig.customFields.showcases || []).length) {
return null;
}
const showcases = siteConfig.customFields.showcases.map((user) => (
<a href={user.infoLink} key={user.infoLink} target="_blank">
<img className="user-logo" src={'https://cdn.jsdelivr.net/gh/apache/apisix-website@master/website/static/img/' + user.image} alt={user.caption} />
</a>
));
const middleIndex = (showcases.length / 2).toFixed(0);

return (
<div className="hero home-splash">
<div className="hero text--center showcase">
<div className="container">
<div className="inner">
<div className="padding-vert--md">
<h1 className="title slogan">
A&nbsp;
<span className="feature-word">
<CSSTransition
in={isShow}
timeout={2000}
classNames="feature-word-text"
appear={true}
>
<span>{featureWords[featureWordIndex]}</span>
</CSSTransition>
</span>
<span className="hide-on-mobile">&nbsp;</span>Cloud-Native API
Gateway
</h1>
<div className="subtitle">
Provides rich traffic management features such as load balancing,
dynamic upstream, canary release, circuit breaking,
authentication, observability, and more. Based on the Nginx
library and etcd.
</div>
<p>
A wide variety of Companies and Organizations use APISIX for Research, Production and Commercial products
<br />&nbsp;
<a
href="https://github.com/apache/apisix/blob/master/powered-by.md"
target="_blank"
rel="noopener"
>
<u>Add your company</u>
</a>
</p>
<div className="user-logos">
<div className="logo-row">
<span className="user-logos-container">
<section>
<span>{showcases.slice(0, middleIndex)}</span>
<span>{showcases.slice(0, middleIndex)}</span>
</section>
</span>
</div>
<div className="pluginWrapper button-wrapper">
<Link
to="https://github.com/apache/apisix"
className="button button--outline button--primary github"
>
<GitHubLogo className="github-logo" />
View on GitHub
</Link>
<Link
to={useBaseUrl("downloads")}
className="button button--outline button--primary secondary"
>
Downloads
</Link>
<div className="logo-row">
<span className="user-logos-container">
<section>
<span>{showcases.slice(middleIndex, showcases.length)}</span>
<span>{showcases.slice(middleIndex, showcases.length)}</span>
</section>
</span>
</div>
</div>
</div>
</div>
);
};

const LearnHow = () => (
<div className="hero">
<div className="learn-how">
<div className="container">
<div className="row">
<div className="col col--7">
<p className="hero__title">
<small>Description</small>
</p>
<p className="hero__subtitle">
<small>
Cloud-native microservices API gateway, delivering the ultimate
performance, security, open source and scalable platform for all
your APIs and microservices. Apache APISIX is based on Nginx and
etcd. Compared with traditional API gateways, APISIX has dynamic
routing and plug-in hot loading, which is especially suitable
for API management under micro-service system.
</small>
</p>
</div>
<div className="col">
<img
className="image"
src="https://user-images.githubusercontent.com/40708551/114740649-a9bf2200-9d67-11eb-8e1d-1409fb5c18c2.png"
align="right"
alt="apisix-description"
/>
</div>
</div>
</div>
</div>
</div>
);

const EventsSection = () => {
const { siteConfig } = useDocusaurusContext();
const events = (siteConfig.customFields.events || [])
.slice(0, 4)
.map((event) => {
const publishTime = event.fileName.slice(0, 10);
const splittedFileName = event.fileName.split("-");
const url = `/blog/${splittedFileName
.slice(0, 3)
.join("/")}/${splittedFileName.slice(3).join("-")}`;
return (
<a className="event-item" key={event.title} href={url} target="_blank">
<div>
<div className="event-title">{event.title}</div>
<div className="event-publish-time">{publishTime}</div>
</div>
<div className="event-read-button">
Read <ChevronRight />
</div>
</a>
);
});
return (
<div className="hero text--center events-section">
<div className="container">
<div>
<h1 className="color-primary">Events</h1>
</div>
<div className="events-view-all-button">
<a href="blog/tags/Events" target="_blank">
<u>View All Events</u>
</a>
</div>
<div className="events-container">{events}</div>
</div>
</div>
);
};

const ContributionSection = () => {

return (
<div className="contribution">
<div className="center-elem contribution-text">
<h2>Make your first contribution to Apache APISIX®</h2>
</div>
<div className="center-elem">
<p>Find a good first issue to get you started !</p>
</div>
<div className="contribution-link">
<Link
to="/docs/general/contributor-guide#good-first-issues"
>
<GitHubLogo className="contribution-logo" />
Good First Issues
</Link>
</div>
</div>
);
};

const NewsletterSection = () => {
const Index = (props) => {

return (
<div className="newsletter">
<div className="center-elem news-logo">
<svg className="news-logo-svg" width="185" height="156" viewBox="0 0 185 156" fill="none" xmlns="http://www.w3.org/2000/svg">
<path d="M0 155.5L94 0L185 155.5H140L94 83L42.5 155.5H0Z" fill="#F8423F" />
<path d="M94 82.5L42.5 155H0L76.5 57L94 82.5Z" fill="url(#paint0_linear)" />
<path d="M140 155.5H185L94 0L140 155.5Z" fill="url(#paint1_linear)" />
<defs>
<linearGradient id="paint0_linear" x1="222.5" y1="50" x2="85" y2="223.5" gradientUnits="userSpaceOnUse">
<stop offset="0.536111" stopColor="#FC0A04" />
<stop offset="1" stopColor="#CF0500" stopOpacity="0.77" />
</linearGradient>
<linearGradient id="paint1_linear" x1="139.5" y1="1.50861e-06" x2="226" y2="136" gradientUnits="userSpaceOnUse">
<stop offset="0.473466" stopColor="#E2423E" />
<stop offset="1" stopColor="#E2423E" stopOpacity="0.77" />
</linearGradient>
</defs>
</svg>
</div>
<div className="center-elem news-text">
<h2>Stay up to date about all Apache APISIX® News</h2>
</div>
<div className="center-elem">
<a className="news-button" href="/docs/general/subscribe-guide">Subscribe</a>
</div>
</div>
);
};
const [screenWidth, screenHeight] = useWindowSize();

const Index = (props) => {
return (
<Layout>
<HomeSplash />
<LearnHow />
<EventsSection />
<ContributionSection />
<NewsletterSection />
<HeroSection />
<Showcase />
<Architecture screenWidth={screenWidth} screenHeight={screenHeight}/>
<Features screenWidth={screenWidth} screenHeight={screenHeight}/>
<Benefits screenWidth={screenWidth} screenHeight={screenHeight}/>
<Comparison />
<OpensourcePromo />
<NewsSection />
<EndCTA />
<EventPosterCard />
</Layout>
);
};
Expand Down
87 changes: 87 additions & 0 deletions website/src/pages/sections/architecture.jsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
import React, { useEffect } from "react";
import gsap from "gsap";

import "../../css/customTheme.css";
import HLDesign from "../../assets/images/infographs/Architecture.svg";
import Pattern from "../../assets/images/PatternGrouped.svg";

const Architecture = (props) => {
const screenWidth = props.screenWidth;

useEffect(() => {
let strokePaths = []
for (let i=1; i<28; i++) {
strokePaths.push(".PatternGrouped_svg__p"+i);
}

let tlStroke = gsap.timeline({
paused: true,
defaults: {
ease: "power2.inOut",
yoyo: true,
repeat: -1,
},
});

tlStroke.fromTo(strokePaths, {
strokeDashoffset: 10000
}, {
strokeDashoffset: 0,
duration: 5,
stagger: 0.3,
ease: "power2.inOut",
stroke: "red",
});

let observer = new IntersectionObserver(onIntersection, {
root: null,
threshold: 0.4,
})

function onIntersection(entries, opts){
entries.forEach(entry => {
if (entry.isIntersecting) {
tlStroke.paused(false);
} else {
tlStroke.paused(true);
}
}
);
}

observer.observe( document.querySelector('.arch'));

return () => {
tlStroke.pause(0).kill(true);
observer.disconnect();
}
}, []);

Comment thread
1502shivam-singh marked this conversation as resolved.
return (
<>
<div className="arch">
<div style={{position: "absolute", display: "flex", justifyContent: "center", alignItems: "center", height: "120vh"}}>
<Pattern className="arch-scale-svg" style={{width: "100vw", strokeWidth: "3", zIndex: "-10", opacity: "0.25", strokeDasharray: "10000"}}/>
</div>
<div>
<h3 className="arch-head">Building for large-scale, high value systems</h3>
</div>
<div className="arch-subtitle">
<p>Apache APISIX lets you build Cloud-Native Microservices API gateways, delivering the ultimate performance, security, open source and scalable platform for all your APIs and microservices.</p>
</div>
<div className="arch-card" style={{position: "relative"}}>
<div className="hldesign">
<HLDesign className="hldesign-graphic"/>
</div>
<div className="arch-card-caption">
<p style={{width: screenWidth >=768 ? "50%" : "90%"}}>Apache APISIX is based on Nginx and etcd. Compared with traditional API gateways, APISIX has dynamic routing and hot-loading plugins</p>
</div>
<div className="arch-card-border">
</div>
</div>
</div>
</>
);
}

export default Architecture;
Loading