With the Google Chat API, you can import data from your other messaging platforms into Google Chat. You can import existing messages, attachments, reactions, memberships, and space entities from your other messaging platforms to corresponding Chat API resources. You can import this data by creating Chat spaces in import mode and importing data into those spaces. After the process successfully completes, these spaces become standard Chat spaces.
The following outlines the complete import process:
- Plan your import
- Configure authorization for the Chat app
- Create a space in import mode
- Import resources
- Validate imported resources
- Reconcile imported resource differences from source data
- Complete import mode
- Give access to the space after import mode
- Troubleshooting
Prerequisites
Apps Script
- A Business or Enterprise Google Workspace account with access to Google Chat.
- Create a Google Cloud project.
- Enable and configure the Google Chat API with a name, icon, and description for your Chat app.
- Create a standalone Apps Script project, and turn on the Advanced Chat Service.
- The Chat app must be delegated domain-wide authority in any domains that the app imports content in, see Authorize Chat apps.
Python
- A Business or Enterprise Google Workspace account with access to Google Chat.
- Create a Google Cloud project.
- Enable and configure the Google Chat API with a name, icon, and description for your Chat app.
- Python 3.6 or greater
- The pip package management tool
- The Chat app must be delegated domain-wide authority in any domains that the app imports content in, see Authorize Chat apps.
Plan your import
Plan accordingly for the amount of data to be imported, understand how the usage limits and quotas can impact the import process, and be aware of the types of Chat spaces supported when importing to a new space.
Review API usage limits
The time required to import data into Chat can vary greatly depending on the quantity of Chat resources to import. Review your Chat app's usage limits and the amount of data scheduled for import from the source messaging platform to determine an estimated timeline.
When importing messages to a space, we recommend that you spread the calls
to the messages.create()
method across different message threads.
Identify the supported spaces to import
Import mode only supports the SpaceType
of SPACE
and GROUP_CHAT
. It does
not support DIRECT_MESSAGE
.
See the documentation for SpaceType
for more information.
Create a space in import mode
To create a space in import mode, call the
create
method
on the
Space
resource
and set importMode
to true
.
When you create the space in import mode, make note of the following.
- The date and time - Remember, import mode must be completed within 30
days. If the space is still in import mode after 30
days from the time the
spaces.create()
method was called, it's automatically deleted and becomes inaccessible and unrecoverable.- Don't use the value of the
createTime
field to track the expiration of the 30 day timeframe. This is not always the same as when you call thespaces.create()
method. When using import mode, thecreateTime
field can be set to the historical timestamp at which the space was created in the source in order to preserve the original creation time.
- Don't use the value of the
- The space resource name (
name
) - The unique identifier that is used to retrieve information about the specific space and is referenced in later steps when importing content into the space.
To preserve the creation time of the equivalent space entity from the source
messaging platform, you can set the createTime
of the space. This
createTime
must be set to a value between January 1, 2000 and present time.
To create an external space in import mode, set externalUserAllowed
to true
.
After import is successfully completed, you can add external users.
The following example shows how to create a space in import mode:
Apps Script
function createSpaceInImportMode() {
const space = Chat.Spaces.create({
spaceType: 'SPACE',
displayName: 'DISPLAY_NAME',
importMode: true,
createTime: (new Date('January 1, 2000')).toJSON()
});
console.log(space.name);
}
Python
"""Create a space in import mode."""
import datetime
from google.oauth2 import service_account
from googleapiclient.discovery import build
# Specify required scopes.
SCOPES = [
'https://www.googleapis.com/auth/chat.import',
]
CREDENTIALS = (
service_account.Credentials.from_service_account_file('credentials.json')
.with_scopes(SCOPES)
.with_subject('EMAIL')
)
# Build a service endpoint for Chat API.
service = build('chat', 'v1', credentials=CREDENTIALS)
result = (
service.spaces()
.create(
body={
'spaceType': 'SPACE',
'displayName': 'DISPLAY_NAME',
'importMode': True,
'createTime': f'{datetime.datetime(2000, 1, 1).isoformat()}Z',
}
)
.execute()
)
print(result)
Replace the following:
EMAIL
: the email address of the user account that you're impersonating with domain-wide authority.DISPLAY_NAME
: the name for the space created in import mode. This must be a unique name for the space that's displayed to Chat users. We recommend using the same display name as the space from which you're importing data.
Import resources
To import resources from other messaging platforms, you create Google Chat resources (such as messages, reactions, attachments) in the import mode space. When you create a resource in the space, you specify data from the related resource from the message platform that you're migrating from.
Messages
Your Chat apps can import messages using their own authority, or
on behalf of a user through impersonation. The message author is set to the
impersonated user account. For more information, see
Authorize Chat apps.
To import a
message in an import mode space, call the
create
method
on the
Message
resource.
In order to preserve the creation time of the original message from the source
messaging platform, you can set the createTime
of the message. This
createTime
must be set to a value between the space creation time that you
previously set and present time.
Messages in the same space cannot contain the same createTime
, even if
previous messages with that time are deleted.
Messages containing third-party URLs in import mode spaces can't render link previews within Google Chat.
When you create the messages in import mode, spaces don't notify or send email to any users, including messages which contain user mentions.
The following example shows how to create a message in an import mode space:
Python
"""Create a message in import mode space."""
import datetime
from google.oauth2 import service_account
from googleapiclient.discovery import build
# Specify required scopes.
SCOPES = [
'https://www.googleapis.com/auth/chat.import',
]
CREDENTIALS = (
service_account.Credentials.from_service_account_file('credentials.json')
.with_scopes(SCOPES)
.with_subject('EMAIL')
)
# Build a service endpoint for Chat API.
service = build('chat', 'v1', credentials=CREDENTIALS)
NAME = 'spaces/SPACE_NAME'
result = (
service.spaces()
.messages()
.create(
parent=NAME,
body={
'text': 'Hello, world!',
'createTime': f'{datetime.datetime(2000, 1, 2).isoformat()}Z',
},
)
.execute()
)
print(result)
Replace the following:
EMAIL
: the email address of the user account that you're impersonating with domain-wide authority.SPACE_NAME
: the name for the space created in import mode.
Reactions
Your Chat app can import reactions for messages by using the Chat API. For information about the resource methods and types of authentication support in import mode spaces, see Authorize Chat apps.
Attachments
Your Chat app can upload attachments using the Chat API. For information about the resource methods and types of authentication support in import mode spaces, see Authorize Chat apps. However, we highly recommended that you use Google Drive API to upload attachments as Google Drive files and link the file URIs to the respective messages in the import mode spaces to import attachments from other messaging platforms to avoid hitting Google Chat internal limit for attachment upload.
Historical memberships
Historical memberships are memberships created for users who had already left the original space entity from the source messaging platform, but you want to retain their data in Chat. For information about adding new members after the space is no longer in import mode, see Create membership resource.
In many cases, when those historical members are subject to a
data retention policy in Google,
you want to preserve the data (such as Messages and reactions) created by
historical memberships in a space before importing them to Chat.
While the space is in import mode, you can import those historical memberships
into the space, using the
create
method
on the
Membership
resource.
In order to preserve the leave time of the historical membership, you must set
the deleteTime
of the membership. This leave time must be accurate because it
impacts which data to retain for those memberships. Moreover, this deleteTime
must be after the space creation timestamp and must not be a future timestamp.
In addition to deleteTime
, you can also set createTime
to preserve the
original join time of the historical membership. Unlike deleteTime
, the
createTime
is optional. If unset, createTime
is automatically calculated by
subtracting 1 microsecond from deleteTime
. If set, createTime
must be before
deleteTime
and must be on or after the space creation time. This createTime
information isn't used to determine data retention and isn't visible in admin
tools such as the Google Admin console and Google Vault.
While there might be multiple ways that a user can join and leave a space in the
source messaging platform (through invites, joining by themselves, being added
by another user), in Chat those actions are all represented by
the historical membership createTime
and deleteTime
fields as being added
or removed.
The following example shows how to create a historical membership in an import mode space:
Python
"""Create a historical membership in import mode space."""
import datetime
from google.oauth2 import service_account
from googleapiclient.discovery import build
# Specify required scopes.
SCOPES = [
'https://www.googleapis.com/auth/chat.import',
]
CREDENTIALS = (
service_account.Credentials.from_service_account_file('credentials.json')
.with_scopes(SCOPES)
.with_subject('EMAIL')
)
# Build a service endpoint for Chat API.
service = build('chat', 'v1', credentials=CREDENTIALS)
NAME = 'spaces/SPACE_NAME'
USER = 'users/USER_ID'
result = (
service.spaces()
.members()
.create(
parent=NAME,
body={
'createTime': f'{datetime.datetime(2000, 1, 3).isoformat()}Z',
'deleteTime': f'{datetime.datetime(2000, 1, 4).isoformat()}Z',
'member': {'name': USER, 'type': 'HUMAN'},
},
)
.execute()
)
print(result)
Replace the following:
EMAIL
: the email address of the user account that you're impersonating with domain-wide authority.SPACE_NAME
: the name for the space created in import mode.USER_ID
: the unique ID for the user.
Import resources in an external space
You can only create an external space with import mode using credentials belonging to users inside your Workspace organization. This only applies while the space is in import mode. Once the space completes import mode, external users can be invited to join the imported spaces (see access section) and their credentials can be used to call Chat API.
Validate imported resources
Your Chat app can read back and validate the contents
of an import mode space by calling the
list
method on the
Message
resource.
You can read Reaction
and Attachment
resources from any returned message's
emojiReactionSummaries
and attachment
fields. Chat apps can
only call this method on behalf of a user through impersonation. For more
information, see
Authorize Chat apps.
Your Chat app can also read individual messages for
validation by calling the
get
method
on the Message
resource.
Chat apps can only call this method to read their own messages by
using their own authority. For more information, see
Authorize Chat apps.
Chat apps can also list historical memberships by calling the
list
method
on the
Membership
resource.
After the space exits import mode, the list
method doesn't expose historical
memberships anymore. Chat apps can only call this method on
behalf of a user through impersonation. For more information, see
Authorize Chat apps.
You can read an import mode space's properties by calling the
get
method
on the
Space
resource.
Chat apps can only call this method using their own authority.
For more information, see
Authorize Chat apps.
Reconcile imported resource differences from source data
If any imported resource no longer matches the original entity from the source messaging platform due to changes in the original entity during import, Chat apps can call the Chat API to modify the imported chat resource. For example, if a user edits a message in the source messaging platform after that message was created in Chat, Chat apps can update the imported message so that it reflects the current content of the original message.
Messages
To update
supported fields
on a message in an import mode space, call the
update
method
on the
Message
resource.
Chat apps can only call this method using the same authority that
was used during the initial message creation. If you used user impersonation
during the initial message creation, you must use the same impersonated user to
update that message.
To delete a message in an import mode space, call the
delete
method
on the
Message
resource.
Messages in an import mode space don't need to be deleted by the original
message creator and can be deleted by impersonating any user in the domain.
Chat apps can only delete their own messages using their own
authority. For more information, see
Authorize Chat apps.
Reactions
To delete a reaction for a message in an import mode space, use the
delete
method
on the reactions
resource. For information about the resource methods and
types of authentication support in import mode spaces, see
Authorize Chat apps.
Attachments
To update attachments for a message in an import mode space, use the
upload
method on the media
resource. For information about the resource methods and types of authentication
support in import mode spaces, see
Authorize Chat apps.
Historical memberships
To delete a historical membership in an import mode space, use the
delete
method
on the
Membership
resource. After a
space exits import mode, the delete
method doesn't let you delete historical
memberships anymore.
You can't update a historical membership in an import mode space. If you want to correct an incorrectly imported historical membership, you need to delete it first and then recreate it while the space is still in import mode.
Spaces
To update
supported fields in
an import mode space, use the
patch
method
on the spaces
resource.
To delete an import mode space, use the
delete
method
on the spaces
resource.
For information about the resource methods and types of authentication support in import mode spaces, and see Authorize Chat apps.
Complete import mode
Before calling the completeImport
method, you should ensure that validation and
reconciliation of resource differences
are completed. Exiting a space out of import mode is an irreversible process and
converts the import mode space into a regular space. There's no indicator in
Chat that attributes these spaces to a data import.
Make note of the date and time you call completeImport
, the resource name
of the user who made the call, and the response returned. This can be helpful
if you must encounter any issues and must investigate them.
To complete import mode and make the space accessible to users, the
Chat app can call the completeImport
method on the
Space
resource.
Chat apps can only call this method on behalf of a user through
impersonation. For more information, see
Authorize Chat apps.
The impersonated user is added to the space as a
space manager
once this method completes. This method must be called within 30 days of the
initial create.space
method call. If you attempt to call this method after the
30 day duration has elapsed, the call results in failures because the import
mode space is deleted and is no longer accessible to the
Chat app.
The impersonated user in the completeImport
method doesn't need to be the
space creator.
The following example shows how to complete the import mode:
Python
"""Complete import."""
from google.oauth2 import service_account
from googleapiclient.discovery import build
# Specify required scopes.
SCOPES = [
'https://www.googleapis.com/auth/chat.import',
]
CREDENTIALS = (
service_account.Credentials.from_service_account_file('credentials.json')
.with_scopes(SCOPES)
.with_subject('EMAIL')
)
# Build a service endpoint for Chat API.
service = build('chat', 'v1', credentials=CREDENTIALS)
NAME = 'spaces/SPACE_NAME'
result = service.spaces().completeImport(name=NAME).execute()
print(result)
Replace the following:
EMAIL
: the email address of the user account that you're impersonating with domain-wide authority.SPACE_NAME
: the name for the space created in import mode.
Give access to the space after import mode
To give Chat users access to the recently imported space,
Chat apps can continue to use the chat.import
scope and user
impersonation within 30 days of the initial create.space()
method call to do
the following:
- Add members to the space: Call the
create()
method on theMembership
resource. We recommend that Chat apps createMembership
resources immediately after the space import is completed, so that Chat apps can continue to use thechat.import
scope, and ensure that all imported members have access to the space. - Set a target audience: Call the
update()
method on theSpace
resource. To learn how to create and add target audiences, see Make a Google Chat space discoverable to specific users in a Google Workspace organization.
To use these methods with the chat.import
scope, the impersonated user must
be a space manager.
For external spaces, the membership
create()
method
also allows to invite users outside of your Workspace organization. Make sure
you understand all the
known limitations for
external users.
Troubleshooting
If you experience a problem when importing Chat spaces, review the following issues for assistance. If you encounter an error response, make note of it (copy/paste the text into a document or save a screenshot) for future reference and troubleshooting.
When a space is successfully imported, CompleteImportSpace
completes with
a status of OK
.
Didn't complete import before the 30-day window expired
As previously described in Create a space in import mode, if the space is still in import mode after 30 days from the time the create method was called, it's automatically deleted and becomes inaccessible and unrecoverable.
Unfortunately, the deleted space is no longer available or recoverable and the import process must be initiated again.
Find missing spaces
If you're unable to find the new Chat space, review the
following table for the response you received from CompleteImportSpace
to
see the explanation and how to resolve it.
Response received | Investigation steps | Explanation | Resolution |
---|---|---|---|
CompleteImportSpace throws an exception and calling
GetSpace returns PERMISSION_DENIED . |
Check your records for when the space was created and if it's older than 30 days, it was automatically deleted. Additionally, there is no record of the imported space in the space management tool or audit log. | It's been longer than 30 days since the import process was started and the space failed to successfully exit migration. | Create a new space and run the import process again. |
CompleteImportSpace returns OK and calling
GetSpace returns PERMISSION_DENIED . |
There's no record of the imported space in the space management tool, but the space is shown to be deleted in the audit log. | The space was successfully imported, but subsequently deleted. | Create a new space and run the import process again. |