Skip to main content

Project NFT

Anyone can build on the JBProjects NFT contract. This allows developers to write new contracts which use JBProjects NFTs to manage permissions in a standardized way, and allows any project using Juicebox payment terminals to access your contracts, and vice versa.

Create a project​

Instead of calling JBController3_1.launchProjectFor(...) to create a project, configure its first funding cycle, and attach payment terminals and a juicebox controller contract to it in the same transaction, JBProjects can be minted independently to represent ownership over projects with subsequent capabilities attached later on.

To create a project, call JBProjects.createFor(...). The JBProjectMetadata structure allows arbitrary metadata to be mapped to any namespace domain. metadata uses a domain of 0 to store its formatted metadata.

function createFor(address _owner, JBProjectMetadata calldata _metadata)
returns (uint256 projectId) { ... }
struct JBProjectMetadata {
string content;
uint256 domain;
View project info

Launching a project will mint a new NFT in the JBProjects contract. The owner can be found using JBProjects.ownerOf(...).

function ownerOf(uint256 _projectId) external returns (address owner) { ... }

The project's metadata can be found using JBProjects.metadataContentOf(...).

function metadataContentOf(uint256 _projectId, uint256 _domain)
returns (string memory) { ... }

Once a project has been created, new metadata can be added by calling JBProjects.metadataContentOf(...).

function setMetadataOf(uint256 _projectId, JBProjectMetadata calldata _metadata)
requirePermission(ownerOf(_projectId), _projectId, JBOperations.SET_METADATA) { ... }

The project can set a new token URI by calling JBProjects.setTokenUriResolver(...).

function setTokenUriResolver(IJBTokenUriResolver _newResolver) external override onlyOwner { ... }

Attaching application-specific functionality​

Project owners can configure their first funding cycle for their JBProject, attach payment terminals, and set all other standard Juicebox project properties by calling JBController3_1.launchFundingCyclesFor(...).

Most Juicebox protocol contracts are generic utilities for any JBProject owner, meaning stored data tends to me mapped from project IDs, and functionality that affects a project tends to be exposed only to the project's owner or a operator address specified by the project's owner.

function launchFundingCyclesFor(
uint256 _projectId,
JBFundingCycleData calldata _data,
JBFundingCycleMetadata calldata _metadata,
uint256 _mustStartAtOrAfter,
JBGroupedSplits[] calldata _groupedSplits,
JBFundAccessConstraints[] memory _fundAccessConstraints,
IJBPaymentTerminal[] memory _terminals,
string calldata _memo
requirePermission(projects.ownerOf(_projectId), _projectId, JBOperations.RECONFIGURE)
returns (uint256 configuration) { ... }