Contact List API CSV Export

When we use the get/api/v2/outbound/contactlists/{contactListId}/export API to export a CSV of the contact list, we have multiple struggles. The first is, you have to be logged into the Genesys GUI in the web browser for the download to initiate. The second is if I try a direct the download to a file path, the result is a CSV containing only random HTML. I don't see an alternative API where we can just pull the raw data either. Our goal is to export the full contact list (our list will always remain short, few hundred or so contacts) at least daily and push all the information to a live dashboard for operations to see the status of each contact as needed. Please help!! Thanks!

@mhanna77

You can refer below example implementation for Contact List export from genesys cloud using .Net SDK, it exports everthing from contact list in CSV format. Hope this will help you!

public async Task<Result> ExportContactListAsync(string contactListId, string contactListChannelId)
		{
			try
			{
				// Initiate Export 
				await _genesysApiClient.ExecuteAsync(() =>
					_outboundApi.PostOutboundContactlistExportAsync(contactListId),
					useRetry: false);

				// Get URI
				_Download = "false";
				var exportResponse = await _genesysApiClient.ExecuteAsync(() =>
					_outboundApi.GetOutboundContactlistExportAsync(contactListId, _Download),
					useRetry: false);

				// Get Genesys Auth Token to call Genesys API over Http
				Configuration configuration = new Configuration();
				var accessTokenInfo = await _genesysConfigurationHandler.GetAccessTokenInfoAsync(Configuration.Default.ApiClient);
                               
                //Export Data
				var response = await _apiClientWrapper.Send(
					new RequestParameters
					{
						RequestUri = new Uri(exportResponse.Uri, UriKind.Absolute),
						Method = HttpMethod.Get,
						DefaultRequestHeaders = new DefaultRequestHeaders(
							[MediaTypeNames.Application.Json], 
							new HeaderData("Authorization", 
								$"Bearer {accessTokenInfo.Data.AccessToken}")),
					},
					CancellationToken.None);

				if (response.StatusCode == StatusCodes.Status200OK) // add to check empty content
				{
                 //Create CSV file
					await CreateCsvFile(
						response,
						_config.ApiDetails.ExportContactListPath,
						contactListChannelId);
					return Result.Success();
				}
				else
					return Result.Failure(GenesysContactListError.DownLoadContactListError(
								response.StatusCode.ToString(),
								response.Content.ToString()));
			}
			catch (Exception ex)
			{
				throw ex.With(ex.Message, ex.Source, ex.StackTrace);
			}
		}

		private static async Task<bool> CreateCsvFile(ResponseData downloadContactListResult, string exportContactListPath, string contactListChannelId)
		{
			var content = downloadContactListResult.Content;
			var sharedPath = exportContactListPath;
			string fileName = $"ExportedContactList_{contactListChannelId}_{DateTime.Now:yyyyMMddHHmm}.csv";
			string filePath = Path.Combine(sharedPath, fileName);

			// Ensure the directory exists
			if (!Directory.Exists(sharedPath))
			{
				Directory.CreateDirectory(sharedPath);
			}
            // Check if content has no data
            var lines = content.Split(new[] { '\r', '\n' }, StringSplitOptions.RemoveEmptyEntries);
            if (lines.Length <= 1)
            {
                return false;
            }
            
			// Write content to CSV file
            
			await File.WriteAllTextAsync(filePath, content);
            return true;
            
			
		}
1 Like

Using Python, I'm initiating the URI export, opening it in a browser and then helping the file along to it's final destination. My problem is, in order for the file to download, it requires user level authentication and if I'm not already logged into Genesys GUI, then the process fails and takes me to the Genesys login screen. This will not work as an automated process. How do I work around the user authentication, why isn't the API auth enough? Thanks!

+1 to this question:

 I don't see an alternative API where we can just pull the raw data either

This is not accurate. See the example here: https://developer.genesys.cloud/routing/outbound/exportcontactlists

This is caused by a problem in your application. It's likely trying to download the login page because it's not making the request correctly and is also following the redirect to login. It should provide the correct authorization with the request and should not follow redirects so you can catch the 401 error response.

The process being discussed in this thread and documented at the link above is the only method for obtaining the contact list data in its entirety. Because of its potential size and non-JSON format, it cannot be returned as a simple API payload and requires downloading a file.

1 Like

Thanks for the reply @tim.smith, I'll post my Python here if you could take a look and see what the issue might be. This code works to get the URI, download the csv and move it to a final destination. This all works well as long as I'm logged into Genesys, if I'm not logged in, it takes me to the Genesys login screen and the file download does not happen.

import glob
import os
import shutil
import webbrowser
from pprint import pprint
import time
import PureCloudPlatformClientV2
from PureCloudPlatformClientV2.rest import ApiException
from datetime import datetime

GENESYS_CLOUD_CLIENT_ID = 'my ID'
GENESYS_CLOUD_CLIENT_SECRET = 'my secret'

PureCloudPlatformClientV2.configuration.host = 'https://api.usw2.pure.cloud'

apiclient = PureCloudPlatformClientV2.api_client.ApiClient().get_client_credentials_token(GENESYS_CLOUD_CLIENT_ID,
GENESYS_CLOUD_CLIENT_SECRET)

api_instance = PureCloudPlatformClientV2.OutboundApi(apiclient)
contact_list_id = 'my contact list'
download = 'false' # Redirect to download uri (optional) (default to 'false')

try:
api_response = api_instance.get_outbound_contactlist_export(contact_list_id, download=download)
pprint(api_response)

uri = api_response.uri

webbrowser.open(uri)

downloads_folder = 'C:/Users/xxxx000/Downloads'
partial_filename = '4c661398-5570-4e4a-9f86-06c8c42a2700'

current_date = datetime.now().strftime("%Y-%m-%d")
final_destination = f'C:/Final/downloaded_file_v5_{current_date}.csv'

print(f"Checking downloads folder at: {downloads_folder}")
time.sleep(10)

downloaded_files = glob.glob(os.path.join(downloads_folder, f"{partial_filename}*.csv"))
if downloaded_files:
    most_recent_file = max(downloaded_files, key=os.path.getmtime)
    print(f"Found most recent file: {most_recent_file}")
else:
    raise FileNotFoundError(f"CSV file with partial name {partial_filename} not found in the downloads folder")

shutil.move(most_recent_file, final_destination)
print(f"Most recent CSV file moved successfully to: {final_destination}")

except ApiException as e:
print("Exception when calling OutboundApi->get_outbound_contactlist_export: %s\n" % e)
except Exception as e:
print(f"Error downloading file: {e}")

It appears to be this part based on your code. You're not authorizing the request to the file's uri like is shown in the example.

That was the issue, setting the access token in the request headers before making the request to download the exported file solved the problem. Thank you

This topic was automatically closed 31 days after the last reply. New replies are no longer allowed.