Skip to content

Commit

Permalink
add examples web app to test v2 hooks (#550)
Browse files Browse the repository at this point in the history
  • Loading branch information
krzysu authored Sep 28, 2023
1 parent afd1cd6 commit 422d8da
Show file tree
Hide file tree
Showing 45 changed files with 956 additions and 64 deletions.
2 changes: 2 additions & 0 deletions .vscode/settings.json
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
{
"eslint.workingDirectories": [
"examples/nextjs",
"examples/node",
"examples/react-native",
"examples/shared",
"examples/web",
"examples/web-wagmi",
"packages/api-bindings",
"packages/blockchain-bindings",
Expand Down
2 changes: 2 additions & 0 deletions examples/web/.eslintignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,2 @@
dist
*.js
23 changes: 23 additions & 0 deletions examples/web/.eslintrc.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,23 @@
module.exports = {
root: true,
extends: [
'@lens-protocol/eslint-config',
'plugin:react/recommended',
'plugin:react-hooks/recommended',
'plugin:react/jsx-runtime',
],
plugins: ['react', 'react-hooks'],
settings: {
react: {
version: 'detect',
},
},
rules: {
'react/prop-types': 'off',
'react/no-unescaped-entities': 'off',
'react/jsx-curly-brace-presence': [
'error',
{ props: 'never', children: 'never', propElementValues: 'always' },
],
},
};
26 changes: 26 additions & 0 deletions examples/web/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
# Logs
logs
*.log
npm-debug.log*
yarn-debug.log*
yarn-error.log*
pnpm-debug.log*
lerna-debug.log*

node_modules
dist
dist-ssr
*.local

stats.html

# Editor directories and files
.vscode/*
!.vscode/extensions.json
.idea
.DS_Store
*.suo
*.ntvs*
*.njsproj
*.sln
*.sw?
3 changes: 3 additions & 0 deletions examples/web/.prettierignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
dist
coverage
stats.html
15 changes: 15 additions & 0 deletions examples/web/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,15 @@
# Lens SDK + ethers + wagmi + Bundlr

This package is an example app showcasing the `@lens-protocol/react` capabilities as well as a possible integration with [wagmi](https://wagmi.sh/) and Aerwave via [Bundlr](https://github.com/Bundlr-Network).

To play with the latest version of the `web-wagmi` example without running it locally visit `https://lens-sdk-example-web-wagmi.vercel.app/`.

## Getting Started

You can run the dev server via:

```bash
pnpm dev
```

Ensure you previously built all the dependencies. See [main setup](../../README.md#setup).
19 changes: 19 additions & 0 deletions examples/web/index.html
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Lens SDK - web</title>
<link
rel="icon"
href="data:image/svg+xml,<svg xmlns=%22http://www.w3.org/2000/svg%22 viewBox=%220 0 100 100%22><text y=%22.9em%22 font-size=%2290%22>🌿</text></svg>"
/>
<style>
@import 'src/index.css';
</style>
</head>
<body>
<div id="root"></div>
<script type="module" src="/src/main.tsx"></script>
</body>
</html>
49 changes: 49 additions & 0 deletions examples/web/package.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
{
"name": "example-web",
"private": true,
"version": "0.1.0",
"scripts": {
"dev": "vite",
"build": "vite build",
"preview": "vite preview",
"eslint:fix": "pnpm run eslint --fix",
"eslint": "eslint src",
"lint": "pnpm run prettier && pnpm run eslint && pnpm run tsc",
"lint:fix": "pnpm run prettier:fix && pnpm run eslint:fix && pnpm run tsc",
"prettier:fix": "prettier --write .",
"prettier": "prettier --check .",
"tsc": "tsc --noEmit"
},
"dependencies": {
"@bundlr-network/client": "^0.11.9",
"@ethersproject/providers": "^5.7.2",
"@lens-protocol/react": "workspace:*",
"@lens-protocol/storage": "workspace:*",
"@lens-protocol/wagmi": "workspace:*",
"@xmtp/react-sdk": "1.0.0-preview.40",
"example-shared": "workspace:*",
"react": "^18.2.0",
"react-cool-inview": "^3.0.1",
"react-dom": "^18.2.0",
"react-hot-toast": "^2.4.0",
"react-router-dom": "^6.8.1",
"readable-web-to-node-stream": "^3.0.2",
"viem": "^1.0.0",
"wagmi": "^1.1.0"
},
"devDependencies": {
"@babel/core": "^7.20.12",
"@lens-protocol/eslint-config": "workspace:*",
"@lens-protocol/prettier-config": "workspace:*",
"@types/node": "^18.15.11",
"@types/react": "^18.0.28",
"@types/react-dom": "^18.0.11",
"@vitejs/plugin-react": "^4.0.3",
"prettier": "^2.8.4",
"rollup-plugin-visualizer": "^5.9.2",
"typescript": "^4.9.5",
"vite": "^4.4.3",
"vite-plugin-node-polyfills": "^0.9.0"
},
"prettier": "@lens-protocol/prettier-config"
}
75 changes: 75 additions & 0 deletions examples/web/src/App.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,75 @@
import { LensConfig, LensProvider, development } from '@lens-protocol/react';
import { XMTPProvider } from '@xmtp/react-sdk';
import { Toaster } from 'react-hot-toast';
import { Route, BrowserRouter as Router, Routes } from 'react-router-dom';
import { WagmiConfig, configureChains, createConfig } from 'wagmi';
import { polygonMumbai } from 'wagmi/chains';
import { InjectedConnector } from 'wagmi/connectors/injected';
import { publicProvider } from 'wagmi/providers/public';

import { Home } from './HomePage';
import { Breadcrumbs } from './components/Breadcrumbs';
import { GenericErrorBoundary } from './components/GenericErrorBoundary';
import { ErrorMessage } from './components/error/ErrorMessage';
import { Header } from './components/header/Header';
import { ProfilesPage } from './profiles/ProfilesPage';
import { UseProfile } from './profiles/UseProfile';
import { PublicationsPage } from './publications/PublicationsPage';
import { UsePublication } from './publications/UsePublication';
import { localStorage } from './storage';

const { publicClient, webSocketPublicClient } = configureChains(
[polygonMumbai],
[publicProvider()],
);

const config = createConfig({
autoConnect: true,
publicClient,
webSocketPublicClient,
connectors: [
new InjectedConnector({
options: {
shimDisconnect: false,
},
}),
],
});

const lensConfig: LensConfig = {
environment: development,
storage: localStorage(),
};

export function App() {
return (
<WagmiConfig config={config}>
<LensProvider config={lensConfig}>
<XMTPProvider>
<Router>
<Header />
<main>
<Breadcrumbs />
<GenericErrorBoundary fallback={ErrorMessage}>
<Routes>
<Route index element={<Home />} />

<Route path="/publications">
<Route index element={<PublicationsPage />} />
<Route path="usePublication" element={<UsePublication />} />
</Route>

<Route path="/profiles">
<Route index element={<ProfilesPage />} />
<Route path="useProfile" element={<UseProfile />} />
</Route>
</Routes>
</GenericErrorBoundary>
<Toaster />
</main>
</Router>
</XMTPProvider>
</LensProvider>
</WagmiConfig>
);
}
20 changes: 20 additions & 0 deletions examples/web/src/HomePage.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,20 @@
import { Link } from 'react-router-dom';

import { CATEGORIES } from './config';

export function Home() {
return (
<>
<h1>Home</h1>

<div>
{CATEGORIES.map(({ path, label }) => (
<article key={path}>
<h2>{label}</h2>
<Link to={path}>View</Link>
</article>
))}
</div>
</>
);
}
30 changes: 30 additions & 0 deletions examples/web/src/components/Breadcrumbs.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,30 @@
import { Fragment } from 'react';
import { Link, useLocation } from 'react-router-dom';

function capitalizeFirstLetter(string: string) {
return string.charAt(0).toUpperCase() + string.slice(1);
}

export function Breadcrumbs() {
const { pathname } = useLocation();
const paths = pathname.split('/').filter(Boolean);

return (
<div style={{ display: 'flex', flexDirection: 'row', gap: '.5rem' }}>
<Link to="/">Home</Link>

{paths.map((path, index) => {
const to = `/${paths.slice(0, index + 1).join('/')}`;

return (
<Fragment key={index}>
<span>/</span>
<span key={to}>
<Link to={to}>{capitalizeFirstLetter(path)}</Link>
</span>
</Fragment>
);
})}
</div>
);
}
28 changes: 28 additions & 0 deletions examples/web/src/components/GenericErrorBoundary.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
import { ReactNode, Component } from 'react';

type Props = {
children: ReactNode;
fallback: React.ComponentType<{ error: Error }>;
};

type State = {
error: Error | null;
};

export class GenericErrorBoundary extends Component<Props, State> {
state: State = {
error: null,
};

render() {
if (this.state.error) {
return <this.props.fallback error={this.state.error} />;
}

return <>{this.props.children}</>;
}

static getDerivedStateFromError(error: Error) {
return { error: error };
}
}
19 changes: 19 additions & 0 deletions examples/web/src/components/LinkCard.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,19 @@
import { Link } from 'react-router-dom';

type LinkCardProps = {
path: string;
label: string;
description: string;
};

export function LinkCard({ path, label, description }: LinkCardProps) {
return (
<article key={path}>
<h3>
<code>{label}</code>
</h3>
<p>{description}</p>
<Link to={path}>View example</Link>
</article>
);
}
12 changes: 12 additions & 0 deletions examples/web/src/components/error/ErrorMessage.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
type ErrorMessageProps = {
error: Error | null;
};

export function ErrorMessage({ error }: ErrorMessageProps) {
return (
<section>
<h3>Something went wrong</h3>
<pre>{error?.message ?? 'Unknown error'}</pre>
</section>
);
}
44 changes: 44 additions & 0 deletions examples/web/src/components/header/Header.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,44 @@
import { NavLink } from 'react-router-dom';

import { CATEGORIES } from '../../config';

export function Header() {
return (
<header>
<div
style={{
display: 'flex',
alignItems: 'center',
justifyContent: 'space-between',
maxWidth: '1600px',
margin: 'auto',
padding: '1rem',
}}
>
<span>
<strong>🌿 Lens SDK</strong>
</span>
<div
style={{
display: 'flex',
alignItems: 'center',
justifyContent: 'space-between',
gap: '1rem',
}}
></div>
</div>

<nav>
{CATEGORIES.map(({ path, label }) => (
<NavLink
key={path}
to={path}
className={({ isActive }) => (isActive ? 'current' : undefined)}
>
{label}
</NavLink>
))}
</nav>
</header>
);
}
3 changes: 3 additions & 0 deletions examples/web/src/components/loading/Loading.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
export function Loading() {
return <div>Loading...</div>;
}
Loading

0 comments on commit 422d8da

Please sign in to comment.