ICR Program
HomeProjectsCreditsTransactionsInsights
  • Welcome to the ICR program documentation
    • About ICR
      • ICR Team
        • Gudmundur Sigbergsson
        • Olafur "Oli" Torfason
        • Bjorn H. Helgason
        • Thordur "Thor" Agustsson
        • Alondra Silva Munoz
        • Dr. Rannveig Anna Guicharnaud
        • Robert Huldarsson
        • Ria Antil
        • Alvaro Vallejo Rendón
      • ICR's Mission Statement
      • ICR's Context
      • Leadership
        • Leadership and Commitment
        • Policies
          • Quality policy
          • KYC/KYB Compliance Policy
          • Grievance policy
          • Anti-Corruption Compliance Policy
          • Impartiality policy
          • ICR Privacy and Cybersecurity Policy
          • Diversity, Equality, and Inclusion policy
        • Organizational Roles, Responsibilities, and Authorities
          • Leadership
            • Chief Executive Officer (CEO)
            • Chief Operating Officer (COO)
            • Chief Technology Officer (CTO)
            • Chief Product Officer (CPO)
            • Chief Science Officer (CSO)
            • Chief Marketing Officer (CMO)
            • ICR Board
              • Members
                • Daníel F. Jónsson
                • Kristján I. Mikaelsson
              • ICR Board Procedures v3.0
            • ICR Program Advisory Panel
              • Members
              • ICR Program Advisory Panel 3.0
          • ICR Program Advisory Panel
            • Amit Sharma
            • Geetha Gopal
            • Javier Castro
          • Forums
            • ICR Project Proponent and Developer forum
              • ICR Project Proponent and Developer Forum Terms of Reference
            • ICR Stakeholder forum
              • ICR Stakeholder Forum - Terms of Reference
            • ICR VVB forum
              • ICR VVB Forum Terms of Reference
            • ICR Forum Guidelines
            • Forum Application
          • Committees
            • Appeals Committee
              • ICR Appeals Committee Terms of Reference
      • Articles of Association for International Carbon Registry ehf.
  • Fundamentals
    • Climate change
    • Kyoto protocol
    • Paris Agreement
      • Nationally Determined Contributions
      • Carbon Markets Under the Paris Agreement
    • Voluntary Carbon Markets
    • Compensation
      • ÍST 92
      • ISO 14068-1:2023
  • ICR Program
    • Overview
    • Fundamentals
      • ISO
        • ISO 14064
          • ISO 14064-1
          • ISO 14064-2
          • ISO 14064-3
          • ISO 14068-1
      • Project Origination
      • Additionality
      • ICR Registration Process
      • Validation and verification
        • Accreditation
    • Definitions
      • ICR Definitions v3.1
        • Version history
          • ICR Definitions v3.0
          • ICR Definitions v2.0
          • ICR Definitions v1.0
    • Methodology Development
      • Criteria
        • ICR Methodology Requirements v3.0
        • Version history
          • ICR Methodology Requirements 2.0
          • ICR Methodology Requirements 1.0
      • Procedural
        • ICR Methodology Approval Process v3.0
        • Version history
          • ICR Methodology Approval Process v2.0
          • ICR Methodology Approval Process v1.0
      • ICR Methodologies
        • Under development
          • M-ICR001
          • M-ICR002
          • M-ICR003
          • M-ICR004
          • M-ICR005:
          • M-ICR006
          • M-ICR007
          • M-ICR009
          • M-ICR011
        • Approved ICR Methodologies
      • Templates
        • Concept note
          • Older versions
        • Methodology description
          • Older versions
        • Methodology summary
          • Older versions
    • Project development
      • Criteria
        • ICR Requirement Document v6.0
          • Version history
            • ICR Requirement Document v5.0
            • ICR Requirement Document v4.0
      • Procedural
        • ICR Process Requirements v6.1
          • Version history
            • ICR Process Requirements v6.0
            • ICR Process Requirements v5.0
            • ICR Process Requirements v4.0 Final
            • ICR Process Requirements v3.0
        • ICR Article 6 2 procedures v1.0
      • Templates
        • Project concept description (PCD)
          • Older versions
        • Project design description (PDD)
          • Older versions
        • Monitoring report (MR)
          • Older versions
        • Project design description and monitoring report
          • Older versions
        • Letter of attestation
        • Non-performance report
          • Older versions
        • Non-permanence event report
          • Older versions
        • Non-permanence risk assessment
        • Non-performance risk assessment
      • Tools
        • ICR Tool for Environmental and Socio-economic Safeguards and Sustainable Development
      • Approved methodologies, modules and tools
        • ICR approved methodologies, modules and tools v4.0
    • Validation and verification
      • Validation and Verification Bodies
      • Criteria
        • ICR validation and verification specifications v2.0
          • Version history
            • ICR validation and verification specifications v1.0
      • Templates
        • Methodology validation report (MValR)
          • Older versions
        • Validation report (ValR)
          • Older versions
        • Verification report (VerR)
          • Older versions
        • Validation and verification report (ValVerR)
          • Older versions
    • Terms and conditions
      • Terms and Conditions - Users
      • Terms and Conditions - Project
      • ICR Terms and Conditions Market Participants
      • Fee Schedule 2024-2025
      • 🔦ICR KYC/KYB Complience Policy
      • ICR Terms and Conditions - Organizations
        • Older versions
          • ICR Terms and Conditions - Organizations
    • Public consultation
      • Methodologies
        • 2023
          • M-ICR0001
          • M-ICR0002
          • M-ICR0003
          • M-ICR0004
          • M-ICR0005
        • 2024
          • M-ICR0006
        • 2025
          • M-ICR009
          • M-ICR007
          • M-ICR011
      • ICR Program
        • 2023
          • Specifications to guide validation and verification
          • Program revision August 2023
        • 2024
          • Program Revision - July 2024
    • Grievance
      • ICR Grievance process
        • Submit a Complaint
    • Document Library
      • Documents
  • Biodiversity Program
    • Overview
    • Fundamentals
    • Definitions
    • Requirements
      • Templates
        • Concept note
    • Public consultation
    • Document Library
    • Fee Schedule - Biodiversity Pilot Phase 2024-2025
  • Carbonregistry.com
    • Marketplaces
      • Terms and Conditions - Trading Hub
    • On Chain
      • How it works
      • Credit data
      • Contracts
      • Retiring Credits Onchain
    • Registry user guide
      • Introduction
      • Get started
        • Create a user account
          • User profile
            • Authentication
            • Documents
            • API
          • KYC
        • Create an organizational account
          • KYB
      • Account management
        • User account management
        • Organizational account management
          • Projects
          • Users
          • Documentation
          • Settings
          • API
      • Project proponents and developers
        • Registering a project
          • Create a New Project
            • New Project Home Screen
            • Project mitigations
            • Project location
            • Benefits
            • Documents and files
            • People and Organizations
              • People
              • Organizations
            • Home screen tabs
              • Overview
              • Mitigations
              • Benefits
              • Documents
              • People
              • Media
              • VVB
            • Submit for ICR Review
          • Manage a project
          • Transition
          • Page
          • Transition
          • Validation/verification
          • Authorized representatives
          • Finish
        • Credits
          • Ex-ante issuance
          • Ex-post issuance
          • Transferring credits
          • Retiring credits
          • Cancelling credits
        • Side Panel
        • Page 1
      • Organizations
        • Account management
        • Credits
        • Retiring credits
      • Insights
    • API
      • Apps
        • Using ICR apps
          • Approve new permissions
          • Review installations
        • Creating ICR apps
          • About creating ICR apps
            • Best practices
          • Registering an ICR app
            • Permissions
            • Webhooks
              • Webhook actions and payloads
              • Handle deliveries
              • Validate deliveries
              • Handle failed deliveries
            • Callback URLs
        • Authentication
          • Authenticate as an app
          • Generate a JWT
          • Authenticate as an installation
          • App private keys
          • Authenticate as an organization
        • Examples
          • Setting up an ICR app
          • Requesting credit action for organization
          • Interacting with the organization warehouse
      • Endpoints
        • V0.5
          • Apps
          • Organizations
          • Inventory
          • Projects
          • Retirements
          • Warehouse
          • Credits
          • Documents
          • Utility
        • V1 - Beta
          • Organizations
          • Projects
          • Transactions
          • Retirements
          • Credit actions
          • Subaccounts
          • Utility
      • Environments
      • Versions
      • Authentication
    • The Credit Bundler
      • Purchasing Credits
      • Post Purchase: Accepting Credits
  • Quality management system
    • ICR QMS
Powered by GitBook
LogoLogo
On this page
  • Creating the app
  • Setting up the minimum test app's website
  • Setting up remaining configs
  • Integrating the first user
  1. Carbonregistry.com
  2. API
  3. Apps
  4. Examples

Setting up an ICR app

We'll go through, step by step, the process of setting up an ICR app. From creating the app on carbonregistry.com to the first user installing the app on their organization.

PreviousExamplesNextRequesting credit action for organization

Last updated 10 months ago

Everything in this tutorial will be made on the .

Creating the app

To create an app you have to start by creating an organization and setting the type of the organization as "Market participant". If you have not made an organization start by creating one. If you already have an organization then go to organization -> settings and change the type to Market participant .

Now your organization dashboard should look something like this:

Notice that the buttons now say "Create app" and the table displays "Apps" instead of "Projects".

Click the "Create app" and go through the flow to create your first app.

Setting up the minimum test app's website

git clone https://github.com/Mojoflower-garden/best-marketplace.git

For it to be able to run you'll have to define some environment variables in the .env file

```shellscript
ICR_PRIVATE_KEY=""
ICR_WEBHOOK_SECRET="" # optional
NEXT_PUBLIC_ICR_APP_ID=""
NEXT_PUBLIC_ICR_NAME_ID=""
DATABASE_URL="file:./db.sqlite" # path to local db
```

Open the downloaded ICR_PRIVATE_KEY pem file and copy paste the key into your .env file as the variable ICR_PRIVATE_KEY.

You can find the NEXT_PUBLIC_ICR_APP_ID and NEXT_PUBLIC_ICR_NAME_ID on your app's dashboard.

Now run

pnpm i
pnpx prisma db push
pnpm dev

The app should be running successfully on whatever port is open on your machine. The output should look like this:

Setting up remaining configs

The main configs to setup so your app's installation will work are:

We've already created the RSA keypair so we only need to define the callbackURL. Go to the "General" tab on the app's dashboard and input your callback url. The callback url should point to the path where your app is running. For our example it will likely be running on localhost:3000, but you can see where your instance of the example app is running in the output from the pnpm devcommand (see image above). So copy the path to your running instance and paste it with the /api/icrCallback path to the Callback URLs section of the General tab on your app's dashboard.

http://localhost:3000/api/icrCallback

And save the updated info.

Integrating the first user

For this example we are only going to look at the integrations part of the App.

This is the user facing code. The only thing it does is show a "Connect to ICR" button to the user of our app. This button then takes the user to the url

https://sandbox-app.carbonregistry.com/apps/${env.NEXT_PUBLIC_ICR_NAME_ID}/installations/new?state=${stateVariable}&redirectUri=http://localhost:3001/api/icrCallback

Some explanation on the query params is needed.

  • state - you can use this variable to link the user to the callback and also this makes it harder for attackers to fake an installation by calling your callback endpoint with an installationId that they have no real connection to

  • redirectUri - here you can put where the user will be redirected after installing the app on their organization. This must match one of the callbackURLs you defined on the app's dashboard. If left empty the first callbackUrl you defined on the app's dashboard is used.

Now if you go through installing the app on an organization you are an admin of, by going through the "Best marketplace" ui, the Best marketplace will show your organization.

This example uses the demo app. Clone it:

To generate the ICR_PRIVATE_KEY navigate to the "Credentials" tab on your app's dashboard, there you can generate your keypair. Press the "Generate a private key" button. It automatically creates a keypair and downloads the "icr_private_key.pem" file to your machine. ICR does NOT store your private key. ICR only stores the public key and a fingerprint / hash for your convenience (see for more info).

Please make sure you store your private key in a secure location where your website / app can use it for signing requests. Ideally it is stored in such away it can only be used for signing. Definitely make sure it is not committed to a repository, even if that repository is private. See for more details on why.

a callbackUrl (see for more info on callback urls)

creating an RSA keypair (see for more info on private keys)

After installing the app the user is redirected to our /api/icrCallback endpoint where our app verifies the state variable, here you could match it to an internal user if it contains its uid, and calls the to both verify that this installtionId is legit and get data to save with the user so we know which apps are integrated with this user.

That's about it for integrating the first user with our app. This integration only has limited permission though, i.e. only the organization_info permission so the only thing we can do is read basic info about the connected organization. Next up we'll add permissions to our app and request moving credits from an organization's inventory. To see available permission see "".

Best marketplace
Callback URLs
App private keys
App permissions
sandbox
Private keys
App's client Id ←→ App's name Id
User chooses where to install the app
User reviews the permissions
/app/installations/:installationId
Verifying private keys
https://github.com/Mojoflower-garden/best-marketplace/blob/main/src/components/connectToICRButton.tsx
import Link from "next/link";
import { Button } from "~/components/ui/button";
import { env } from "~/env.mjs";
import { api } from "~/utils/api";
import { Loader2 } from "lucide-react";

export const ConnectToICRButton = () => {
  const { data: stateVariable, isLoading: isLoadingStateVar } =
    api.icr.getStateVar.useQuery();
  return (
    <>
      {isLoadingStateVar && <Loader2 className="w-5" />}
      {!isLoadingStateVar && (
        <Link
          href={`${env.NEXT_PUBLIC_ICR_APP_URL}/apps/${
            env.NEXT_PUBLIC_ICR_NAME_ID
          }/installations/new?state=${stateVariable}&redirectUri=http://localhost:${
            process.env.PORT ?? "3000"
          }/api/icrCallback`}
        >
          <Button className="">Connect to ICR</Button>
        </Link>
      )}
    </>
  );
};
https://github.com/Mojoflower-garden/best-marketplace/blob/main/src/pages/api/icrCallback.ts
import { organizations } from "@prisma/client";
import axios from "axios";
import { type NextApiRequest, type NextApiResponse } from "next";
import { env } from "~/env.mjs";
import { db } from "~/server/db";
import { createJWT } from "~/utils/auth";

export default async function icrCallbackHandler(
  req: NextApiRequest,
  res: NextApiResponse,
) {
  const { installationId, state, event } = req.query;
  if (typeof installationId !== "string") {
    return res.redirect("/?error=invalid_installation_id");
  }

  if (typeof state !== "string") {
    return res.redirect("/?error=invalid_state");
  }

  const user = await db.user.findFirst({
    where: {
      id: state.split("-")[0], // This state should be a jwt or something that you generated when the user initiated the installation where you can identify the user. Note: it should probably not be the Id like in this example.
    },
  });

  if (!user) {
    return res.redirect("/?error=invalid_state");
  }

  const jwt = createJWT();
  try {
    const response = await axios.get(
      `${env.ICR_API_URL}/app/installations/${installationId}`,
      {
        headers: {
          Authorization: `Bearer ${jwt}`,
        },
      },
    );
    const data = response.data;
    delete data.organization.organizationIndustries;
    delete data.organization.url;
    const organization = data.organization as organizations;

    await db.organizations.create({
      data: {
        ...organization,
        permissions: JSON.stringify(data.permissions),
        installationId: installationId,
      },
    });

    res.redirect("/");
  } catch (error) {
    console.error(error);
    res.redirect("/?error=install_error");
    return;
  }
}