Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Implement AH example that covers AH creation, list and direct buy #25

Open
wants to merge 27 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
27 commits
Select commit Hold shift + click to select a range
fb5bbfc
Implement AH example that covers AH creation, list and direct buy
zaxozhu Sep 23, 2022
90d16f4
Upgrade metaplex-foundation/js version
antey13 Oct 10, 2022
05b11e9
Upgrade metaplex-foundation/js version for all examples
antey13 Oct 11, 2022
1e2324b
Add create sft page
antey13 Oct 12, 2022
a51939f
Add create sft page
antey13 Oct 12, 2022
6be4fb9
Fix sft image upload
antey13 Oct 13, 2022
9d4d889
Add sft in createListing
antey13 Oct 13, 2022
f18d0e1
Add wallet listings
antey13 Oct 14, 2022
4b50069
Use devnet bundlr
zaxozhu Oct 17, 2022
440361d
Refactor
zaxozhu Oct 17, 2022
50e0d55
Add partial buy for sft
antey13 Oct 17, 2022
e6b31d2
Add tokens on sale for sft listings
antey13 Oct 17, 2022
dd6f919
Fix SFT owner on creation
antey13 Oct 18, 2022
566e724
Fix lint errors
antey13 Oct 18, 2022
0f325f7
Fix fetch assets for listing
antey13 Oct 19, 2022
e06ad06
Add dependency to the hook
antey13 Oct 19, 2022
4232e86
Merge branch 'main' into feature/auction-house
antey13 Oct 19, 2022
9347225
PR fixed
antey13 Oct 19, 2022
c0cfc06
Add token supply info
antey13 Oct 21, 2022
719d382
Add NFT creation; AuctionHouse disconnect; Wallet buttons
antey13 Oct 21, 2022
444455b
Add AH address input
antey13 Oct 23, 2022
2453c45
Add load user`s AH button
antey13 Oct 24, 2022
5f37c70
Fix styles
m-sebastiian Oct 24, 2022
251ebf3
Fix NavBar styling
antey13 Oct 24, 2022
f835181
Update js sdk version
antey13 Oct 27, 2022
72914da
Fix user listings
antey13 Oct 27, 2022
3a4ee0d
Add Readme for ah examples
antey13 Oct 31, 2022
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
4 changes: 4 additions & 0 deletions auction-house/.eslintignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,4 @@
**/.next/*
**/.vscode/*
**/node_modules/*
**/*.js
26 changes: 26 additions & 0 deletions auction-house/.eslintrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
{
"plugins": ["@typescript-eslint"],
"extends": [
"airbnb",
"airbnb/hooks",
"airbnb-typescript",
"next/core-web-vitals",
"plugin:@typescript-eslint/recommended",
"prettier"
],
"parserOptions": {
"project": "./tsconfig.json"
},
"rules": {
"@typescript-eslint/no-unused-vars": "error",
"@typescript-eslint/no-explicit-any": "error",
"react/jsx-props-no-spreading": 0,
"react/require-default-props": 0,
"react/function-component-definition": [
"error",
{
"namedComponents": ["function-declaration", "arrow-function"]
}
]
}
}
36 changes: 36 additions & 0 deletions auction-house/.gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,36 @@
# See https://help.github.com/articles/ignoring-files/ for more about ignoring files.

# dependencies
/node_modules
/.pnp
.pnp.js

# testing
/coverage

# next.js
/.next/
/out/

# production
/build

# misc
.DS_Store
*.pem

# debug
npm-debug.log*
yarn-debug.log*
yarn-error.log*
.pnpm-debug.log*

# local env files
.env*.local

# vercel
.vercel

# typescript
*.tsbuildinfo
next-env.d.ts
7 changes: 7 additions & 0 deletions auction-house/.prettierrc
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"semi": false,
"trailingComma": "es5",
"singleQuote": true,
"tabWidth": 2,
"useTabs": false
}
7 changes: 7 additions & 0 deletions auction-house/.vscode/settings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
{
"editor.codeActionsOnSave": {
"source.fixAll.eslint": true
},
"editor.formatOnSave": true,
"editor.defaultFormatter": "esbenp.prettier-vscode"
}
87 changes: 87 additions & 0 deletions auction-house/README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,87 @@
# Auction House usage example

In this example, we will see how to use [Auction House](https://docs.metaplex.com/programs/auction-house/overview) program using the [Metaplex JS SDK](https://github.com/metaplex-foundation/js).

Once the user has connected their wallet, we display input for the Auction House address and allow the user to create their own Auction House marketplace.

This is achieved by using AuctionHouse context from `./context/AuctionHouse.tsx`.

**Auction House context**

The `./context/AuctionHouse.tsx` file is responsible for creating and exposing a new Auction House Context which will be used within our components to access the Auction House SDK.

It gives the ability to create an auction house.

```ts
const response = await client.create({
sellerFeeBasisPoints: 200, // 2% Fee
})
```

To fetch the user's auction house.

```ts
const userAuctionHouse = await client.findByCreatorAndMint({
creator: toPublicKey(wallet.publicKey),
treasuryMint: WRAPPED_SOL_MINT,
})
```

To load auction house by address.

```ts
const userAuctionHouse = await client.findByAddress({
address: ahAddress,
})
```

**Assets Loading hook**

The `./hooks/useAssets.tsx` file is responsible to fetch the user's NFTs and SFTs that can be then listed in the auction house.

```ts
// Finds and loads user's assets.
const userAssetsMetadata = await fetchAssetsMetadata() // todo: JS SDK method as it will be developed
if (!userAssetsMetadata) {
return
}

const promises: Promise<LoadMetadataOutput>[] = []
userAssetsMetadata.forEach((metadata) => {
if (isMetadata(metadata)) {
promises.push(client.load({ metadata }))
}
})

const userAssets = await Promise.all(promises)
```


**Listings Loading hook**

The `./hooks/useListings.tsx` file is responsible to fetch the user's listings or listings of a given user in the current auction house.

```ts
// Finds and loads listings from auction house.
const lazyListings = seller
? await client.findListings({
auctionHouse,
seller
})
: await client.findListings({
auctionHouse
})

if (!lazyListings) {
return
}

// Fetch listing for lazy listings
const fetchedListings = await Promise.all(
lazyListings.map((listing) =>
!listing.lazy
? Promise.resolve(listing)
: client.loadListing({ lazyListing: listing })
)
)
```
112 changes: 112 additions & 0 deletions auction-house/components/ArtworkCard/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
import { Avatar, Box, BoxProps, Flex, Image, Text } from '@chakra-ui/react'
import { isSft, Listing, LoadMetadataOutput } from '@metaplex-foundation/js'
import React from 'react'

import formatPrice from 'utils/formatPrice'

interface Props extends BoxProps {
artwork: LoadMetadataOutput
listing?: Listing
}

const ArtworkCard: React.FC<Props> = ({
artwork,
listing,
children,
...boxProps
}) => {
const { name } = artwork
const imageSrc = artwork.json?.image
const tokenType = isSft(artwork) ? 'SFT' : 'NFT'

return (
<Box
layerStyle="base"
p={0}
overflow="hidden"
w="full"
maxW="full"
{...boxProps}
role="group"
transition="transform 100ms ease-in-out"
_hover={{
transform: 'translateY(-2px)',
}}
cursor="pointer"
borderRadius="xl"
backgroundColor="#292929"
>
<Box layerStyle="base" p={0}>
<Box
borderRadius="xl"
transition="background 100ms ease-in-out"
_groupHover={{
bg: 'rgba(255, 255, 255, 0.02)',
}}
>
<Image
pos="relative"
_groupHover={{
zIndex: -1,
filter: 'none',
}}
src={imageSrc}
objectFit="cover"
w="full"
h="360px"
filter="drop-shadow(0px 0px 24px rgba(0, 0, 0, 0.2))"
borderRadius="xl"
alt="NFT"
/>
</Box>

<Box p={4}>
<Flex alignItems="center">
<Avatar
size="2xs"
borderRadius="2px"
src="https://bit.ly/kent-c-dodds"
/>
</Flex>

<Flex flexDirection="row" justifyContent="space-between">
<Text
mt={4}
fontSize="2xl"
fontWeight="bold"
textTransform="capitalize"
color="white"
>
{name}
</Text>

<Text
mt={4}
fontSize="2xl"
fontWeight="bold"
textTransform="capitalize"
color="white"
>
{tokenType}
</Text>
</Flex>
</Box>
</Box>
{listing && (
<Text
mt={4}
fontSize="2xl"
fontWeight="bold"
textTransform="capitalize"
textAlign="start"
padding="2px 10px 10px 5px"
color="white"
>
{formatPrice(listing)}
</Text>
)}
</Box>
)
}

export default ArtworkCard
45 changes: 45 additions & 0 deletions auction-house/components/NavBar/index.tsx
Original file line number Diff line number Diff line change
@@ -0,0 +1,45 @@
import React from 'react'
import { Box, Button, Flex, Text } from '@chakra-ui/react'
import { WalletMultiButton } from '@solana/wallet-adapter-react-ui'
import { useAuctionHouse } from '../../context/AuctionHouse'

const NavBar: React.FC = () => {
const { auctionHouse, handleAuctionHouseDisconnect } = useAuctionHouse()

return (
<Box flexGrow={1}>
<Flex
flexDirection="row"
justifyContent="space-between"
alignItems="start"
>
<Box marginTop="20px">
<WalletMultiButton />{' '}
</Box>
{auctionHouse && (
<>
<Text
mt={5}
fontSize="xl"
fontWeight="bold"
textTransform="capitalize"
color="white"
>
{`Auction House Address: ${auctionHouse.address.toBase58()}`}
</Text>
<Button
colorScheme="purple"
size="md"
mt={5}
onClick={handleAuctionHouseDisconnect}
>
Disconnect from Auction House
</Button>
</>
)}
</Flex>
</Box>
)
}

export default NavBar
Loading