# How to Integrate Lovable with Pipedrive

- Tool: Lovable
- Difficulty: Intermediate
- Time required: 25 minutes
- Last updated: March 2026

## TL;DR

To integrate Pipedrive with Lovable, generate an API token from your Pipedrive account settings, store it in Cloud → Secrets, then build Edge Functions that proxy calls to Pipedrive's REST API for deals, persons, organizations, and activities. Pipedrive is the top choice for sales-focused founders who want a visual pipeline CRM integrated into their Lovable app without the complexity of Salesforce or the breadth of HubSpot.

## Add a live sales pipeline to your Lovable app with Pipedrive and Edge Functions

Pipedrive is purpose-built for sales teams who live and die by their pipeline. Where HubSpot tries to be everything (marketing, sales, service), Pipedrive does one thing extremely well: visual deal pipeline management. For founders building internal sales tools, deal tracking dashboards, or customer-facing portals on top of their Pipedrive data, the Lovable + Pipedrive combination offers a straightforward path from CRM data to custom UI.

Pipedrive's API is one of the most developer-friendly in the CRM space. Authentication requires only a personal API token — a static string you generate in your account settings with no OAuth flows, token expiry, or refresh logic required. The REST API v1 uses consistent resource patterns: /deals, /persons, /organizations, /activities, /pipelines, /stages. Every response wraps data in a 'data' key, with pagination via 'additional_data.pagination'.

The most common Lovable + Pipedrive integration patterns are: syncing app events (signups, demo requests, trial starts) as new deals in Pipedrive; building custom pipeline views that match your team's workflow better than Pipedrive's default UI; and creating activity logs when app users perform key actions. Pipedrive's webhook system also allows real-time updates to flow from Pipedrive back into your Lovable app whenever deals are updated by your sales team.

A key distinction from HubSpot: Pipedrive's free tier is significantly more limited (only 1 user, 2 pipelines). The Essential plan ($14/user/month) is usually the minimum for team use. However, the API is available on all paid plans, and Pipedrive's pipeline-first design makes it significantly simpler to build custom pipeline UIs compared to HubSpot's broader feature set.

## Before you start

- A Lovable project with Lovable Cloud enabled (Edge Functions require a deployed app)
- A Pipedrive account with at least the Essential plan (API access is not available on the free tier beyond limited trial)
- Your Pipedrive account must have at least one pipeline with stages configured
- Basic familiarity with Pipedrive concepts: deals, persons, organizations, pipelines, stages, and activities

## Step-by-step guide

### 1. Generate a Pipedrive API token from account settings

Pipedrive uses personal API tokens for API authentication. Unlike OAuth2, these tokens do not expire and do not require periodic refresh — they remain valid until you regenerate them. Each user in your Pipedrive account has their own API token, so the token you generate is tied to your user account's permissions.

To get your API token: log in to Pipedrive and click your avatar in the top-right corner. Select 'Personal preferences' from the dropdown. Go to the 'API' tab in the left sidebar. Your personal API token is displayed. Click 'Select all' then copy the token.

If you need to regenerate the token (for security rotation), click the circular arrow icon next to the token. Note that regenerating invalidates the previous token immediately — update Cloud → Secrets right away if you regenerate.

For production integrations, consider creating a dedicated Pipedrive user account for your integration (e.g., 'API Integration Bot') and using that account's API token. This way, the integration token is isolated from any individual team member's account. If a salesperson leaves your company and their account is deactivated, your integration token is not affected.

Also note your Pipedrive company domain — it appears in your Pipedrive URL as 'yourcompany.pipedrive.com'. This domain is not needed for API calls (the API base URL is always api.pipedrive.com) but is useful to know for configuring webhooks and OAuth apps if you expand the integration later.

**Expected result:** A Pipedrive API token is copied and ready to store. The token is a 40-character alphanumeric string visible in Pipedrive → Personal preferences → API.

### 2. Store the API token and fetch your pipeline stage IDs

Add the Pipedrive API token to Cloud → Secrets in Lovable. In Lovable, click the '+' icon at the top to open the Cloud panel, go to Secrets, and click 'Add new secret'.

Name: PIPEDRIVE_API_TOKEN
Value: your 40-character Pipedrive API token

Before building Edge Functions, you also need your pipeline and stage IDs. Pipedrive stages are identified by numeric IDs (e.g., stage 1, stage 2) rather than names in API calls. The stage IDs are specific to your Pipedrive account — you cannot hardcode generic values.

To fetch your stage IDs, make a test API call (from Postman, Insomnia, or any REST client):
GET https://api.pipedrive.com/v1/stages?api_token=YOUR_TOKEN

This returns all stages across all pipelines with their ID, name, and pipeline_id. Note the stage IDs you will use (typically 'Qualified Lead', 'Demo Scheduled', 'Proposal Sent', 'Closed Won', etc. — whatever you have configured).

You can also fetch pipelines: GET https://api.pipedrive.com/v1/pipelines?api_token=YOUR_TOKEN

Store any frequently-used stage IDs as additional secrets (PIPEDRIVE_STAGE_LEAD_ID, PIPEDRIVE_STAGE_CLOSED_WON_ID) so they can be changed without code modifications if you restructure your pipeline.

**Expected result:** PIPEDRIVE_API_TOKEN appears in Cloud → Secrets. You have a reference list of your pipeline stage IDs and their names for use in Edge Function code.

### 3. Create the Pipedrive CRM proxy Edge Function

Build the core Edge Function that handles common Pipedrive operations: creating persons, creating deals, updating deal stages, and logging activities. A single multi-action proxy pattern keeps your Edge Function count manageable while covering all integration needs.

Pipedrive API v1 authentication uses the api_token query parameter — append ?api_token=YOUR_TOKEN to every request URL. Alternatively, Pipedrive accepts the API token as an Authorization header (Bearer token format), which is cleaner. Use the header approach to avoid the token appearing in server logs as a URL parameter.

The Pipedrive API base URL is https://api.pipedrive.com/v1 for all accounts regardless of company domain.

Key Pipedrive API behaviors to be aware of: creating a person and deal are separate operations — you create the person first, then create the deal with the person_id from the person creation response. Pipedrive also uses numeric IDs for all resources. When listing deals, the response includes the full person and organization objects nested inside, so you rarely need separate lookups for dashboard displays.

For the pipeline board use case, also fetch stages via GET /stages?pipeline_id=X to get ordered stage names and IDs for building columns.

```
import { serve } from 'https://deno.land/std@0.168.0/http/server.ts'

const corsHeaders = {
  'Access-Control-Allow-Origin': '*',
  'Access-Control-Allow-Headers': 'authorization, x-client-info, apikey, content-type',
}

const PIPEDRIVE_BASE = 'https://api.pipedrive.com/v1'

async function pdFetch(path: string, method = 'GET', body?: object) {
  const token = Deno.env.get('PIPEDRIVE_API_TOKEN')
  if (!token) throw new Error('PIPEDRIVE_API_TOKEN secret not configured')

  const resp = await fetch(`${PIPEDRIVE_BASE}${path}`, {
    method,
    headers: {
      Authorization: `Bearer ${token}`,
      'Content-Type': 'application/json',
    },
    body: body ? JSON.stringify(body) : undefined,
  })
  return resp.json()
}

serve(async (req) => {
  if (req.method === 'OPTIONS') return new Response('ok', { headers: corsHeaders })

  try {
    const { action, params = {} } = await req.json()
    let result

    switch (action) {
      case 'create_person':
        result = await pdFetch('/persons', 'POST', {
          name: params.name,
          email: [{ value: params.email, primary: true }],
          phone: params.phone ? [{ value: params.phone }] : undefined,
          org_id: params.orgId,
        })
        break

      case 'create_deal':
        result = await pdFetch('/deals', 'POST', {
          title: params.title,
          person_id: params.personId,
          org_id: params.orgId,
          stage_id: params.stageId,
          value: params.value,
          currency: params.currency || 'USD',
          expected_close_date: params.expectedCloseDate,
        })
        break

      case 'update_deal_stage':
        result = await pdFetch(`/deals/${params.dealId}`, 'PUT', {
          stage_id: params.stageId,
        })
        break

      case 'log_activity':
        result = await pdFetch('/activities', 'POST', {
          subject: params.subject,
          type: params.type || 'task',
          deal_id: params.dealId,
          person_id: params.personId,
          note: params.note,
          due_date: params.dueDate || new Date().toISOString().split('T')[0],
        })
        break

      case 'list_deals':
        result = await pdFetch(`/deals?stage_id=${params.stageId || ''}&status=${params.status || 'open'}&limit=${params.limit || 50}`)
        break

      case 'get_stages':
        result = await pdFetch(`/stages${params.pipelineId ? `?pipeline_id=${params.pipelineId}` : ''}`)
        break

      default:
        return new Response(JSON.stringify({ error: 'Unknown action' }), {
          status: 400, headers: { ...corsHeaders, 'Content-Type': 'application/json' },
        })
    }

    return new Response(JSON.stringify(result), {
      headers: { ...corsHeaders, 'Content-Type': 'application/json' },
    })
  } catch (error) {
    return new Response(JSON.stringify({ error: error.message }), {
      status: 500, headers: { ...corsHeaders, 'Content-Type': 'application/json' },
    })
  }
})
```

**Expected result:** The pipedrive-crm Edge Function deploys in Cloud → Edge Functions. Test it with action 'get_stages' to verify the connection — it should return your pipeline stages without any credentials in the response.

### 4. Build the pipeline dashboard and wire app events to Pipedrive

With the Edge Function deployed, build the UI components that display and interact with Pipedrive data. For a pipeline board, fetch stages on component mount, then fetch deals filtered by stage, and render Kanban columns.

For wiring app events to Pipedrive deal creation, add the supabase.functions.invoke('pipedrive-crm') call at the relevant points in your app's user flow. The most impactful integration points are: new user registration (creates a deal in a 'New Signup' stage), trial-to-paid upgrade intent (moves the deal to a 'Demo Requested' stage), and subscription cancellation (creates an activity on the deal with cancellation reason).

Use the fire-and-forget pattern (no await) for Pipedrive sync calls in user-facing flows — CRM sync failures should never block the primary user experience. Log errors to the console for monitoring but do not surface them to end users.

For the pipeline board with drag-and-drop, use @hello-pangea/dnd (the maintained fork of react-beautiful-dnd) — it is available in Lovable's React environment. On drop, call the pipedrive-crm Edge Function with action 'update_deal_stage' and the new stage_id. Optimistically update the UI before the API call completes for a responsive feel.

For complex pipeline integrations requiring webhook-driven real-time updates from Pipedrive back to your Lovable app (so your board reflects changes made directly in Pipedrive), RapidDev's team can help set up the webhook receiver Edge Function and real-time sync architecture.

**Expected result:** A Kanban pipeline board displays your Pipedrive deals grouped by stage. New deals created via the form appear in Pipedrive within seconds. Deal stage updates from the UI reflect immediately in Pipedrive.

## Best practices

- Create a dedicated Pipedrive user account for your integration (not your personal account) so the API token is not tied to an individual user who might leave the team.
- Store frequently-used stage IDs as named secrets (PIPEDRIVE_STAGE_LEAD_ID, PIPEDRIVE_STAGE_CLOSED_WON_ID) rather than hardcoding numeric IDs in Edge Function code.
- Use the fire-and-forget pattern for Pipedrive sync calls in user-facing forms — CRM sync latency should never delay form submission confirmation.
- Always create a Person before creating a Deal in Pipedrive and link them via person_id — deals without associated persons lose important context and break contact-based filtering in Pipedrive.
- Validate email format before sending to Pipedrive — the API returns an error for malformed emails that can disrupt your app's flow if not caught early.
- Fetch pipeline stages dynamically (via the get_stages action) rather than hardcoding IDs, so pipeline restructuring in Pipedrive does not require code changes in Lovable.
- Handle Pipedrive's 429 rate limit responses in your Edge Function with a retry-after delay — Pipedrive's response includes a 'X-RateLimit-Reset' header indicating when the limit resets.

## Use cases

### Automatically create a Pipedrive deal when a user signs up for a trial

When a new user completes registration in your Lovable app, an Edge Function creates a Pipedrive Person (contact) and associated Deal in the relevant pipeline stage. The deal title includes the user's company and plan intent, and is assigned to the appropriate sales team member based on territory or round-robin logic. Your sales team sees every trial signup as an actionable deal without manual data entry.

Prompt example:

```
Create an Edge Function called pipedrive-create-deal that accepts a POST with { personName, email, company, phone, planInterest, source } and creates a Pipedrive Person and associated Deal using PIPEDRIVE_API_TOKEN from secrets. Set the deal title to company + ' - ' + planInterest, stage to the first stage ID of the main pipeline, and person email. Return the deal ID. Call this Edge Function from the user registration success handler in my app.
```

### Build a custom Kanban pipeline board in Lovable

Fetch deals from Pipedrive and display them as a Kanban board with columns matching your Pipedrive pipeline stages. Sales reps can drag deals between stages, which calls the Pipedrive API to update the deal's stage. This gives your team a custom-branded pipeline view embedded in your app, with all changes syncing back to Pipedrive in real time.

Prompt example:

```
Create Edge Functions to fetch Pipedrive pipeline stages and deals. Then build a Kanban board UI with columns for each pipeline stage showing deal cards with title, person name, and expected close date. Add drag-and-drop to move cards between columns — when a card moves, call a pipedrive-update-deal Edge Function to update the stage_id in Pipedrive. Show deal value on each card.
```

### Log sales activities from app interactions

When a user performs key actions in your app (views a pricing page, starts a feature tour, reaches a usage milestone), log a Pipedrive activity linked to their deal record. This gives your sales team contextual signals about prospect engagement without requiring manual note-taking. Activities appear in the deal's timeline in Pipedrive.

Prompt example:

```
Create an Edge Function called pipedrive-log-activity that accepts { dealId, subject, type, note } and creates a Pipedrive activity linked to the deal. Use PIPEDRIVE_API_TOKEN from secrets. Activity types should be: 'call', 'meeting', 'task', 'email'. Set the due date to today. Return the activity ID. Then call this function when users view the pricing page (type: 'task', subject: 'Pricing page viewed').
```

## Troubleshooting

### Pipedrive API returns 401 Unauthorized with 'Authentication failed' error

Cause: The PIPEDRIVE_API_TOKEN secret is missing, incorrect, or was recently regenerated in Pipedrive.

Solution: In Cloud → Secrets, verify PIPEDRIVE_API_TOKEN is present and the value matches exactly what is shown in Pipedrive → Personal preferences → API. Pipedrive tokens are 40-character alphanumeric strings. If you recently regenerated the token in Pipedrive, update the secret value and redeploy the Edge Function by asking Lovable in chat to add a comment to the Edge Function to trigger redeployment.

### Deals are created in Pipedrive but appear in the wrong pipeline stage

Cause: The stage_id used in the create_deal call does not correspond to the intended stage. Stage IDs are account-specific numeric values that must be fetched from the API.

Solution: Call the get_stages action in your Edge Function to retrieve the correct stage IDs for your account. In Pipedrive's API response, each stage has an 'id' (numeric) and 'name'. Map stage names to IDs in your Edge Function or store frequently-used stage IDs as separate secrets (PIPEDRIVE_STAGE_LEAD_ID, etc.) for easy reference.

### Pipedrive API returns 'Field is required: name' when creating a person

Cause: The 'name' field is mandatory for creating a Pipedrive Person. If name is empty, null, or undefined in the request body, Pipedrive returns a 400 validation error.

Solution: Validate that the name parameter is present and non-empty before calling the create_person action. If you only have an email address (no name), use the email local part as a fallback name (e.g., split on '@' and capitalize). Pipedrive also requires at least one email or phone value for a person to be searchable.

```
// Ensure name is always provided:
const personName = params.name || params.email.split('@')[0]
```

### Pipedrive webhook events are not reaching the Lovable Edge Function

Cause: The webhook URL registered in Pipedrive points to the Lovable preview URL instead of the deployed app URL, or the Edge Function has not been deployed.

Solution: In Pipedrive → Settings → Webhooks, ensure the endpoint URL is your deployed Edge Function URL (visible in Cloud → Edge Functions), not the Lovable editor preview URL. Preview URLs are not publicly accessible for incoming webhooks. Also verify the Edge Function accepts POST requests from unauthenticated sources (Pipedrive webhooks do not send authentication headers by default).

## Frequently asked questions

### Does Pipedrive have a free plan that supports API access?

Pipedrive offers a 14-day free trial with full API access. After the trial, the Essential plan ($14/user/month billed annually) is the minimum paid tier, and it includes API access. There is no permanent free tier — unlike HubSpot's free CRM. For Lovable integration testing, the 14-day trial is sufficient to build and test the integration before committing to a plan.

### Can multiple people in my team use the same Pipedrive API token?

Technically yes, but it is not recommended. Personal API tokens in Pipedrive are tied to specific user accounts and inherit that user's permissions. If your team has multiple users, consider creating a dedicated integration user with the appropriate permissions and using that user's token. This way the integration does not break if a specific team member's account is deactivated or their token is regenerated.

### How do I sync Pipedrive deal updates back to my Lovable app in real time?

Use Pipedrive webhooks to push changes to your Lovable app. In Pipedrive → Settings → Webhooks, create a webhook pointing to your Lovable Edge Function URL for events like 'deal.updated' or 'deal.stage_change'. The Edge Function receives the webhook payload, validates it, and can update a Supabase table or trigger a Supabase Realtime broadcast that updates the UI. This gives you a live pipeline board that reflects changes made directly in Pipedrive without polling.

### What is the difference between Pipedrive persons and organizations?

In Pipedrive's data model, a Person represents an individual contact (a human), while an Organization represents a company or account. Deals can be associated with both a person and an organization. When integrating from a Lovable signup form, create a Person for the individual user and an Organization for their company, then link both to the deal. This gives your sales team visibility into both individual contacts and company-level relationships.

---

Source: https://www.rapidevelopers.com/lovable-integration/pipedrive
© RapidDev — https://www.rapidevelopers.com/lovable-integration/pipedrive
