Skip to content

Commit

Permalink
Update E2E tests to use Microsoft.Azure.Cosmos (#2872)
Browse files Browse the repository at this point in the history
  • Loading branch information
liliankasem authored Nov 19, 2024
1 parent ffb8a46 commit c4113d1
Show file tree
Hide file tree
Showing 3 changed files with 59 additions and 73 deletions.
9 changes: 8 additions & 1 deletion test/E2ETests/E2ETests/Cosmos/CosmosDBEndToEndTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -32,7 +32,14 @@ public async Task CosmosDBTriggerAndOutput_Succeeds()
await CosmosDBHelpers.CreateDocument(expectedDocId, expectedDocId);

//Read
var documentId = await CosmosDBHelpers.ReadDocument(expectedDocId);
string documentId = string.Empty;
await TestUtility.RetryAsync(async () =>
{
documentId = await CosmosDBHelpers.ReadDocument(expectedDocId);
return documentId is not null;
});

//Assert
Assert.Equal(expectedDocId, documentId);
}
finally
Expand Down
2 changes: 1 addition & 1 deletion test/E2ETests/E2ETests/E2ETests.csproj
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@
<PackageReference Include="Azure.Data.Tables" Version="12.9.0" />
<PackageReference Include="Azure.Storage.Blobs" Version="12.21.2" />
<PackageReference Include="Azure.Storage.Queues" Version="12.19.1" />
<PackageReference Include="Microsoft.Azure.DocumentDB.Core" Version="2.22.0" />
<PackageReference Include="Microsoft.Azure.Cosmos" Version="3.45.2" />
<PackageReference Include="Microsoft.Extensions.Logging" Version="8.0.0" />
<PackageReference Include="Microsoft.NET.Test.Sdk" Version="17.11.0" />
<PackageReference Include="Moq" Version="4.20.70" />
Expand Down
121 changes: 50 additions & 71 deletions test/E2ETests/E2ETests/Helpers/CosmosDBHelpers.cs
Original file line number Diff line number Diff line change
Expand Up @@ -4,153 +4,132 @@
using System;
using System.Net.Http;
using System.Threading.Tasks;
using Microsoft.Azure.Documents;
using Microsoft.Azure.Documents.Client;
using Microsoft.Azure.Cosmos;
using Microsoft.Extensions.Logging;

namespace Microsoft.Azure.Functions.Tests.E2ETests
{
public static class CosmosDBHelpers
{
private static readonly DocumentClient _docDbClient;
private static readonly Uri inputCollectionsUri = UriFactory.CreateDocumentCollectionUri(Constants.CosmosDB.DbName, Constants.CosmosDB.InputCollectionName);
private static readonly Uri outputCollectionsUri = UriFactory.CreateDocumentCollectionUri(Constants.CosmosDB.DbName, Constants.CosmosDB.OutputCollectionName);
private static readonly Uri leasesCollectionsUri = UriFactory.CreateDocumentCollectionUri(Constants.CosmosDB.DbName, Constants.CosmosDB.LeaseCollectionName);
private static readonly CosmosClient _cosmosClient;
private static readonly Container _inputContainer;
private static readonly Container _outputContainer;
private static readonly Container _leaseContainer;

static CosmosDBHelpers()
{
var builder = new System.Data.Common.DbConnectionStringBuilder
{
ConnectionString = Constants.CosmosDB.CosmosDBConnectionStringSetting
};
var serviceUri = new Uri(builder["AccountEndpoint"].ToString());
_docDbClient = new DocumentClient(serviceUri, builder["AccountKey"].ToString());
_cosmosClient = new CosmosClient(Constants.CosmosDB.CosmosDBConnectionStringSetting);

var database = _cosmosClient.GetDatabase(Constants.CosmosDB.DbName);
_inputContainer = database.GetContainer(Constants.CosmosDB.InputCollectionName);
_outputContainer = database.GetContainer(Constants.CosmosDB.OutputCollectionName);
_leaseContainer = database.GetContainer(Constants.CosmosDB.LeaseCollectionName);
}

// keep
public async static Task CreateDocument(string docId, string docText = "test")
{
Document documentToTest = new Document() { Id = docId };
documentToTest.SetPropertyValue("Text", docText);

_ = await _docDbClient.CreateDocumentAsync(UriFactory.CreateDocumentCollectionUri(Constants.CosmosDB.DbName, Constants.CosmosDB.InputCollectionName), documentToTest);
var documentToTest = new { id = docId, Text = docText };
await _inputContainer.CreateItemAsync(documentToTest, new PartitionKey(docId));
}

// keep
public async static Task<string> ReadDocument(string docId)
{
var docUri = UriFactory.CreateDocumentUri(Constants.CosmosDB.DbName, Constants.CosmosDB.OutputCollectionName, docId);
Document retrievedDocument = null;
await TestUtility.RetryAsync(async () =>
try
{
var response = await _outputContainer.ReadItemAsync<dynamic>(docId, new PartitionKey(docId));
return response.Resource?.id;
}
catch (CosmosException ex) when (ex.StatusCode == System.Net.HttpStatusCode.NotFound)
{
try
{
retrievedDocument = await _docDbClient.ReadDocumentAsync(docUri, new RequestOptions { PartitionKey = new PartitionKey(docId) });
return true;
}
catch (DocumentClientException ex) when (ex.Error.Code == "NotFound")
{
return false;
}
}, pollingInterval: 500);

return retrievedDocument?.Id;
return null;
}
}

// keep
public async static Task DeleteTestDocuments(string docId)
{
var inputDocUri = UriFactory.CreateDocumentUri(Constants.CosmosDB.DbName, Constants.CosmosDB.InputCollectionName, docId);
await DeleteDocument(inputDocUri, docId);
var outputDocUri = UriFactory.CreateDocumentUri(Constants.CosmosDB.DbName, Constants.CosmosDB.OutputCollectionName, docId);
await DeleteDocument(outputDocUri, docId);
await DeleteDocument(_inputContainer, docId);
await DeleteDocument(_outputContainer, docId);
}

private async static Task DeleteDocument(Uri docUri, string docId)
private async static Task DeleteDocument(Container container, string docId)
{
try
{
await _docDbClient.DeleteDocumentAsync(docUri, new RequestOptions { PartitionKey = new PartitionKey(docId) });
await container.DeleteItemAsync<dynamic>(docId, new PartitionKey(docId));
}
catch (Exception)
catch (CosmosException ex) when (ex.StatusCode == System.Net.HttpStatusCode.NotFound)
{
//ignore
// Ignore if the document is already deleted
}
}

private async static Task<bool> CanConnectAsync(ILogger logger)
{
try
{
await new HttpClient().GetAsync(_docDbClient.ServiceEndpoint);
var response = await _cosmosClient.ReadAccountAsync();
return response != null;
}
catch
{
// typically "the target machine actively refused it" if the emulator isn't running.
logger.LogError($"Could not connect to CosmosDB endpoint: '{_docDbClient.ServiceEndpoint}'. Are you using the emulator?");
logger.LogError($"Could not connect to CosmosDB. Check the emulator or connection string.");
return false;
}

return true;
}


// keep
public async static Task<bool> TryCreateDocumentCollectionsAsync(ILogger logger)
{
if (!await CanConnectAsync(logger))
{
// This can hang if the service is unavailable. Just return and let tests fail.
// The Cosmos tests may be filtered out anyway without an emulator running.
return false;
}

Database db = await _docDbClient.CreateDatabaseIfNotExistsAsync(new Database { Id = Constants.CosmosDB.DbName });
Uri dbUri = UriFactory.CreateDatabaseUri(db.Id);
var databaseResponse = await _cosmosClient.CreateDatabaseIfNotExistsAsync(Constants.CosmosDB.DbName);
var database = databaseResponse.Database;

await Task.WhenAll(
CreateCollection(dbUri, Constants.CosmosDB.InputCollectionName),
CreateCollection(dbUri, Constants.CosmosDB.OutputCollectionName),
CreateCollection(dbUri, Constants.CosmosDB.LeaseCollectionName));
CreateCollection(database, Constants.CosmosDB.InputCollectionName),
CreateCollection(database, Constants.CosmosDB.OutputCollectionName),
CreateCollection(database, Constants.CosmosDB.LeaseCollectionName));

return true;
}

public async static Task DeleteDocumentCollections()
{
var database = _cosmosClient.GetDatabase(Constants.CosmosDB.DbName);
await Task.WhenAll(
DeleteCollection(inputCollectionsUri),
DeleteCollection(outputCollectionsUri),
DeleteCollection(leasesCollectionsUri));
DeleteCollection(database, Constants.CosmosDB.InputCollectionName),
DeleteCollection(database, Constants.CosmosDB.OutputCollectionName),
DeleteCollection(database, Constants.CosmosDB.LeaseCollectionName));
}

private async static Task DeleteCollection(Uri collectionUri)
private async static Task DeleteCollection(Database database, string collectionName)
{
try
{
await _docDbClient.DeleteDocumentCollectionAsync(collectionUri);
var container = database.GetContainer(collectionName);
await container.DeleteContainerAsync();
}
catch (Exception)
catch (CosmosException ex) when (ex.StatusCode == System.Net.HttpStatusCode.NotFound)
{
//Ignore
// Ignore if the container is already deleted
}
}

private async static Task CreateCollection(Uri dbUri, string collectioName)
private async static Task CreateCollection(Database database, string collectionName)
{
var pkd = new PartitionKeyDefinition();
pkd.Paths.Add("/id");
DocumentCollection collection = new DocumentCollection()
var containerProperties = new ContainerProperties
{
Id = collectioName,
PartitionKey = pkd
Id = collectionName,
PartitionKeyPath = "/id"
};
await _docDbClient.CreateDocumentCollectionIfNotExistsAsync(dbUri, collection,
new RequestOptions()
{
PartitionKey = new PartitionKey("/id"),
OfferThroughput = 400
});

await database.CreateContainerIfNotExistsAsync(containerProperties, throughput: 400);
}
}
}

0 comments on commit c4113d1

Please sign in to comment.