Version: Next

Subscribing

Subscribe to realtime changes in your own database.

We will be using these tables as reference for our examples.

Toggle Example Tables

We will be fictional "world" database in all of our examples.

Countries
idnameiso2population_range_millionsmain_exports
76BrazilBR( 205, 215 )[ beans, minerals ]
156ChinaCN( 1380, 1390 )[ computers, phones ]
250FranceFR( 60, 70 )[ cars, machines ]
554New ZealandNZ( 4, 6 )[ food, machines ]
556NigeriaNG( 185, 195 )[ oil, beans ]
840United StatesUS( 320, 330 )[ oil, cars, food ]
Cities
namecountry_id
Rio de Janeiro76
Beijing156
Paris250
Auckland554
Lagos556
Los Angeles840
San Francisco840

Listen to all database changes

Subscribes to all database changes in realtime.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('*')
.on('*', payload => {
console.log('Change received!', payload)
})
.subscribe()

If you want to receive the "previous" data for updates and deletes, you will need to set REPLICA IDENTITY to FULL, like this: ALTER TABLE your_table REPLICA IDENTITY FULL;

Listening to a specific table

Subscribes to a specific table for changes in realtime.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('countries')
.on('*', payload => {
console.log('Change received!', payload)
})
.subscribe()

If you want to receive the "previous" data for updates and deletes, you will need to set REPLICA IDENTITY to FULL, like this: ALTER TABLE your_table REPLICA IDENTITY FULL;

Listening only to INSERT

Subscribes only to the INSERT event.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('countries')
.on('INSERT', payload => {
console.log('Change received!', payload)
})
.subscribe()

Listening only to UPDATE

Subscribes only to the UPDATE event.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('countries')
.on('UPDATE', payload => {
console.log('Change received!', payload)
})
.subscribe()

If you want to receive the "previous" data for updates, you will need to set REPLICA IDENTITY to FULL, like this: ALTER TABLE your_table REPLICA IDENTITY FULL;

Listening only to DELETE

Subscribes only to the DELETE event.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('countries')
.on('DELETE', payload => {
console.log('Change received!', payload)
})
.subscribe()

You will not be able to delete data from your database unless you set your set your table to use FULL REPLICA IDENTITY, like this: ALTER TABLE your_table REPLICA IDENTITY FULL;

Unsubscribing

Unsubscribes from a specific subscription.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('countries')
.on('*', payload => {
console.log('Change received!', payload)
})
.subscribe()
// Unsubscribe from changes
mySubscription.unsubscribe()

Removing a subscription

Disconnects from a subscription fully.
import { createClient } from '@supabase/supabase-js'
// Create a single supabase client for interacting with your database
const supabase = createClient('https://world.supabase.co', '1a2b-3c4d-5e6f-7g8h')
// Listen to changes
const mySubscription = supabase
.from('countries')
.on('*', payload => {
console.log('Change received!', payload)
})
.subscribe()
// Disconnect mySubscription
supabase.removeSubscription(mySubscription)

Reference

from()

supabase
.from(tableName)

tableName: string

Name of the database table to be listened to. Using the wildcard "*" will lead to all tables to be listened to.

tableName: string

Name of the database table that will be read from.

tableName: string

Name of the database table where data will be saved.

tableName: string

Name of the database table where data will be updated.

tableName: string

Name of the database table where data will be deleted.


on()

const mySubscription = supabase
.from('tableName')
.on('eventType', callbackFunction)

eventType: string { "INSERT" | "UPDATE" | "DELETE" | "*" }

The database event which you would like to receive updates for, or you can use the special wildcard * to listen to all changes.

callbackFunction: function

A callback that will handle the payload that is sent whenever your database changes. See all Change Events below to understand all the possible payloads.


subscribe()

const mySubscription = supabase
.from(tableName)
.on(eventType, callbackFunction)
.subscribe()

Subscribes to the database table specified in from() and starts listening to it. An object of type subscription will be returned.

mySubscription.subscribe()

If the subscription already exists, but has been unsubscribed from with the function unsubscribe(), it can be subscribed to again through the above method.


unsubscribe()

mySubscription
.unsubscribe()

Stop listening to changes. At any point you can call subscribe on the subscription object to restart the listeners. If you don't need to connect again in the future, use removeSubscription() instead.


removeSubscription()

supabase
.removeSubscription(mySubscription)

Disconnects and destroys a subscription. This is the preferred method for cleaning up subscriptions which you no longer require.

mySubscription: subscription

A subscription that was previously created. If you don't have access to the subscription, you can always call getSubscriptions().


getSubscriptions()

supabase
.getSubscriptions()

Returns an array of all your subscriptions (including disconnected subscriptions).

Toggle Example Response
[
{
uuid: 'xxxx-xxxx-xxxx-xxxx',
state: 'CONNECTED',
tableName: 'users',
eventListeners: {
'*': null,
'INSERT': null,
'UPDATE': null,
'DELETE': null,
}
},
{
uuid: 'yyyy-yyyy-yyyy-yyyy',
state: 'DISCONNECTED',
tableName: 'messages',
eventListeners: {
'*': null,
'INSERT': null,
'UPDATE': null,
'DELETE': null,
}
}
]

Change Events

@TODO what happens on bulk insert/update/delete?

New record created

Upon inserting or creating a new row, the following will be returned by our listener:

{
"schema": "public",
"table": "countries",
"commit_timestamp": "2020-01-01T00:00:00Z",
"eventType": "INSERT",
"new": {
"id": 533,
"name": "Columbia",
"iso2": "CO",
"population_range_millions": [40, 50],
"main_exports": ["oil", "minerals"]
}
}

Existing record updated

Upon updating a row, the following will be returned by our listener: `

{
"schema": "public",
"table": "countries",
"commit_timestamp": "2020-01-01T00:00:00Z",
"eventType": "UPDATE",
"old": {},
"new": {
"id": 76,
"name": "Brazil",
"iso2": "BR",
"population_range_millions": [205, 215],
"main_exports": ["beans", "minerals"]
}
}

Existing record deleted

Upon deleting a row, the following will be returned by our listener:

{
"schema": "public",
"table": "countries",
"commit_timestamp": "2020-01-01T00:00:00Z",
"eventType": "DELETE",
"old": {
"id": 76
}
}