Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

feat!: Standalone integration test package #1585

Merged
merged 20 commits into from
Jun 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
15 changes: 11 additions & 4 deletions .github/workflows/integration-test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -111,12 +111,13 @@ jobs:
TOKEN_ESCAPED=`echo -n "$AWS_SESSION_TOKEN" | jq -Rsa .`
# Insert the credentials into the .xctestplan file, write the modified JSON
# to a temp file, then move the temp over the original.
jq ".defaultOptions.environmentVariableEntries += [{\"key\": \"AWS_ACCESS_KEY_ID\", \"value\": $AKID_ESCAPED}, {\"key\": \"AWS_SECRET_ACCESS_KEY\", \"value\": $SECRET_ESCAPED}, {\"key\": \"AWS_DEFAULT_REGION\", \"value\": $REGION_ESCAPED}, {\"key\": \"AWS_SESSION_TOKEN\", \"value\": $TOKEN_ESCAPED}]" XCTestPlans/AWSIntegrationTestsOnCI.xctestplan > testplan.tmp
mv testplan.tmp XCTestPlans/AWSIntegrationTestsOnCI.xctestplan
jq ".defaultOptions.environmentVariableEntries += [{\"key\": \"AWS_ACCESS_KEY_ID\", \"value\": $AKID_ESCAPED}, {\"key\": \"AWS_SECRET_ACCESS_KEY\", \"value\": $SECRET_ESCAPED}, {\"key\": \"AWS_DEFAULT_REGION\", \"value\": $REGION_ESCAPED}, {\"key\": \"AWS_SESSION_TOKEN\", \"value\": $TOKEN_ESCAPED}]" IntegrationTests/XCTestPlans/AWSIntegrationTestsOnCI.xctestplan > testplan.tmp
mv testplan.tmp IntegrationTests/XCTestPlans/AWSIntegrationTestsOnCI.xctestplan
- name: Prepare Integration Tests
run: ./scripts/ci_steps/prepare_integration_tests.sh
- name: Run Integration Tests
run: |
cd IntegrationTests
set -o pipefail && \
NSUnbufferedIO=YES xcodebuild \
-scheme AWSIntegrationTestsOnCI \
Expand Down Expand Up @@ -192,6 +193,12 @@ jobs:
- name: Prepare Integration Tests
run: ./scripts/ci_steps/prepare_integration_tests.sh
- name: Build Integration Tests
run: swift build --build-tests
run: |
cd IntegrationTests
swift build --build-tests
cd ..
- name: Run Integration Tests
run: swift test
run: |
cd IntegrationTests
swift test
cd ..
Original file line number Diff line number Diff line change
Expand Up @@ -32,9 +32,6 @@ struct GeneratePackageManifestCommand: ParsableCommand {
@Option(help: "The names of the services to include in the package manifest. This defaults to all services located in aws-sdk-swift/Sources/Services")
var services: [String] = []

@Flag(help: "If the package manifest should include the integration tests.")
var includeIntegrationTests: Bool = false

@Flag(help: "If the package manifest should exclude AWS services.")
var excludeAWSServices = false

Expand All @@ -48,7 +45,6 @@ struct GeneratePackageManifestCommand: ParsableCommand {
clientRuntimeVersion: clientRuntimeVersion,
crtVersion: crtVersion,
services: services.isEmpty ? nil : services,
includeIntegrationTests: includeIntegrationTests,
excludeAWSServices: excludeAWSServices,
excludeRuntimeTests: excludeRuntimeTests
)
Expand All @@ -73,8 +69,6 @@ struct GeneratePackageManifest {
/// The list of services to include as products
/// If `nil` then the list is populated with the names of all items within the `Sources/Services` directory
let services: [String]?
/// If the package manifest should include the integration tests.
let includeIntegrationTests: Bool
/// If the package manifest should exclude the AWS services.
let excludeAWSServices: Bool
/// If the package manifest should exclude runtime unit tests.
Expand All @@ -87,7 +81,7 @@ struct GeneratePackageManifest {
) throws -> String
/// Returns the contents of the package manifest file given the versions of dependencies and the list of services.
let buildPackageManifest: BuildPackageManifest

/// Generates a package manifest file and saves it to `packageFileName`
func run() throws {
try FileManager.default.changeWorkingDirectory(repoPath)
Expand All @@ -103,19 +97,13 @@ struct GeneratePackageManifest {
/// - Returns: The contents of the generated package manifest.
func generatePackageManifestContents() throws -> String {
let versions = try resolveVersions()
let servicesWithIntegrationTests = try resolveServicesWithIntegrationTests()
let services = try resolveServices().map {
PackageManifestBuilder.Service(
name: $0,
includeIntegrationTests: servicesWithIntegrationTests.contains($0)
)
}
let services = try resolveServices().map { PackageManifestBuilder.Service(name: $0) }
log("Creating package manifest contents...")
let contents = try buildPackageManifest(versions.clientRuntime, versions.crt, services)
log("Successfully created package manifest contents")
return contents
}

/// Saves the package manifest file.
/// If no file exists, then this will create a new file. Otherwise, this will overwrite the existing file.
///
Expand All @@ -129,7 +117,7 @@ struct GeneratePackageManifest {
)
log("Successfully saved package manifest to \(packageFileName)")
}

/// Returns the versions for ClientRuntime and CRT.
/// If explcit versions are provided by the command, then this returns the specified versions.
/// Otherwise, this returns the versions defined in `packageDependencies.plist`.
Expand All @@ -147,35 +135,35 @@ struct GeneratePackageManifest {
}
let resolvedClientRuntime: Version
let resolvedCRT: Version

if let explicitVersion = self.clientRuntimeVersion {
resolvedClientRuntime = explicitVersion
log("Using ClientRuntime version provided: \(resolvedClientRuntime.description)")
} else {
resolvedClientRuntime = packageDependencies.value.clientRuntimeVersion
log("Using ClientRuntime version loaded from file: \(resolvedClientRuntime.description)")
}

if let explicitVersion = self.crtVersion {
resolvedCRT = explicitVersion
log("Using CRT version provided: \(resolvedCRT.description)")
} else {
resolvedCRT = packageDependencies.value.awsCRTSwiftVersion
log("Using CRT version loaded from file: \(resolvedCRT.description)")
}

log("""
Resolved versions of dependencies:
* ClientRuntime: \(resolvedClientRuntime.description)
* CRT: \(resolvedCRT.description)
""")

return (
clientRuntime: resolvedClientRuntime,
crt: resolvedCRT
)
}

/// Returns the list of services to include in the package manifest.
/// If an explicit list of services was provided by the command, then this returns the specified services.
/// Otherwise, this returns the list of services that exist within `Sources/Services`
Expand All @@ -194,21 +182,6 @@ struct GeneratePackageManifest {
log("Resolved list of services: \(resolvedServices.count)")
return resolvedServices
}

/// Returns the list of services to include in the package manifest.
/// If an explicit list of services was provided by the command, then this returns the specified services.
/// Otherwise, this returns the list of services that exist within `Sources/Services`
///
/// - Returns: The list of services to include in the package manifest
func resolveServicesWithIntegrationTests() throws -> [String] {
log("Resolving services with integration tests...")
let resolvedServices = try FileManager
.default
.integrationTests()
.map { $0.replacingOccurrences(of: "IntegrationTests", with: "") }
log("List of services with integration tests: \(resolvedServices.count)")
return resolvedServices
}
}

// MARK: - Factory
Expand All @@ -231,7 +204,6 @@ extension GeneratePackageManifest {
clientRuntimeVersion: Version? = nil,
crtVersion: Version? = nil,
services: [String]? = nil,
includeIntegrationTests: Bool = false,
excludeAWSServices: Bool = false,
excludeRuntimeTests: Bool = false
) -> Self {
Expand All @@ -241,15 +213,13 @@ extension GeneratePackageManifest {
clientRuntimeVersion: clientRuntimeVersion,
crtVersion: crtVersion,
services: services,
includeIntegrationTests: includeIntegrationTests,
excludeAWSServices: excludeAWSServices,
excludeRuntimeTests: excludeRuntimeTests
) { _clientRuntimeVersion, _crtVersion, _services in
let builder = PackageManifestBuilder(
clientRuntimeVersion: _clientRuntimeVersion,
crtVersion: _crtVersion,
services: _services,
includeIntegrationTests: includeIntegrationTests,
excludeAWSServices: excludeAWSServices,
excludeRuntimeTests: excludeRuntimeTests
)
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,11 @@ import PackageDescription
struct PackageManifestBuilder {
struct Service {
let name: String
let includeIntegrationTests: Bool
}

let clientRuntimeVersion: Version
let crtVersion: Version
let services: [Service]
let includeIntegrationTests: Bool
let excludeAWSServices: Bool
let excludeRuntimeTests: Bool
let basePackageContents: () throws -> String
Expand All @@ -27,15 +25,13 @@ struct PackageManifestBuilder {
clientRuntimeVersion: Version,
crtVersion: Version,
services: [Service],
includeIntegrationTests: Bool,
excludeAWSServices: Bool,
excludeRuntimeTests: Bool,
basePackageContents: @escaping () throws -> String
) {
self.clientRuntimeVersion = clientRuntimeVersion
self.crtVersion = crtVersion
self.services = services
self.includeIntegrationTests = includeIntegrationTests
self.excludeAWSServices = excludeAWSServices
self.basePackageContents = basePackageContents
self.excludeRuntimeTests = excludeRuntimeTests
Expand All @@ -45,11 +41,10 @@ struct PackageManifestBuilder {
clientRuntimeVersion: Version,
crtVersion: Version,
services: [Service],
includeIntegrationTests: Bool,
excludeAWSServices: Bool,
excludeRuntimeTests: Bool
) {
self.init(clientRuntimeVersion: clientRuntimeVersion, crtVersion: crtVersion, services: services, includeIntegrationTests: includeIntegrationTests, excludeAWSServices: excludeAWSServices, excludeRuntimeTests: excludeRuntimeTests) {
self.init(clientRuntimeVersion: clientRuntimeVersion, crtVersion: crtVersion, services: services, excludeAWSServices: excludeAWSServices, excludeRuntimeTests: excludeRuntimeTests) {
// Returns the contents of the base package manifest stored in the bundle at `Resources/Package.Base.swift`
let basePackageName = "Package.Base"

Expand Down Expand Up @@ -97,9 +92,6 @@ struct PackageManifestBuilder {
// Add the generated content that defines the list of services to include
buildServiceTargets(),
"",
// Add the generated content that defines the list of services with integration tests to include
buildIntegrationTestsTargets(),
"",
buildResolvedServices(),
"\n"
]
Expand Down Expand Up @@ -146,21 +138,6 @@ struct PackageManifestBuilder {
return lines.joined(separator: .newline)
}

/// Builds the list of services to add integration test targets for..
/// This generates an array of strings, where the each item is a name of a service
/// and calls the `addIntegrationTestTarget` for each item.
private func buildIntegrationTestsTargets() -> String {
var lines: [String] = []
lines += ["let servicesWithIntegrationTests: [String] = ["]
lines += services.filter(\.includeIntegrationTests).map { " \($0.name.wrappedInQuotes())," }
lines += ["]"]
lines += [""]
lines += ["// Uncomment this line to enable integration tests"]
lines += ["\(includeIntegrationTests ? "" : "// ")addIntegrationTests()"]

return lines.joined(separator: .newline)
}

private func buildResolvedServices() -> String {
"addResolvedTargets()"
}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -228,46 +228,6 @@ func addServiceUnitTestTarget(_ name: String) {
]
}

func addIntegrationTestTarget(_ name: String) {
let integrationTestName = "\(name)IntegrationTests"
var additionalDependencies: [String] = []
var exclusions: [String] = []
switch name {
case "AWSEC2":
additionalDependencies = ["AWSIAM", "AWSSTS", "AWSCloudWatchLogs"]
exclusions = [
"Resources/IMDSIntegTestApp"
]
case "AWSECS":
additionalDependencies = ["AWSCloudWatchLogs", "AWSEC2", "AWSIAM", "AWSSTS"]
exclusions = [
"README.md",
"Resources/ECSIntegTestApp/"
]
case "AWSS3":
additionalDependencies = ["AWSSSOAdmin", "AWSS3Control", "AWSSTS"]
case "AWSEventBridge":
additionalDependencies = ["AWSRoute53"]
case "AWSCloudFrontKeyValueStore":
additionalDependencies = ["AWSCloudFront"]
case "AWSSTS":
additionalDependencies = ["AWSIAM", "AWSCognitoIdentity"]
default:
break
}
integrationTestServices.insert(name)
additionalDependencies.forEach { integrationTestServices.insert($0) }
package.targets += [
.testTarget(
name: integrationTestName,
dependencies: [.crt, .clientRuntime, .awsClientRuntime, .byName(name: name), .smithyTestUtils, .awsSDKIdentity, .smithyIdentity, .awsSDKCommon] + additionalDependencies.map { Target.Dependency.target(name: $0, condition: nil) },
path: "./IntegrationTests/Services/\(integrationTestName)",
exclude: exclusions,
resources: [.process("Resources")]
)
]
}

var enabledServices = Set<String>()
var enabledServiceUnitTests = Set<String>()

Expand All @@ -276,12 +236,6 @@ func addAllServices() {
enabledServiceUnitTests = Set(serviceTargets)
}

var integrationTestServices = Set<String>()

func addIntegrationTests() {
servicesWithIntegrationTests.forEach { addIntegrationTestTarget($0) }
}

func excludeRuntimeUnitTests() {
package.targets.removeAll {
$0.name == "AWSClientRuntimeTests" ||
Expand All @@ -292,6 +246,6 @@ func excludeRuntimeUnitTests() {
}

func addResolvedTargets() {
enabledServices.union(integrationTestServices).forEach(addServiceTarget)
enabledServices.forEach(addServiceTarget)
enabledServiceUnitTests.forEach(addServiceUnitTestTarget)
}
Original file line number Diff line number Diff line change
Expand Up @@ -114,7 +114,6 @@ extension GeneratePackageManifest {
clientRuntimeVersion: Version? = nil,
crtVersion: Version? = nil,
services: [String]? = nil,
includesIntegrationTests: Bool = false,
includeProtocolTests: Bool = false,
excludeAWSServices: Bool = false,
excludeRuntimeTests: Bool = false,
Expand All @@ -126,7 +125,6 @@ extension GeneratePackageManifest {
clientRuntimeVersion: clientRuntimeVersion,
crtVersion: crtVersion,
services: services,
includeIntegrationTests: includesIntegrationTests,
includeProtocolTests: includeProtocolTests,
excludeAWSServices: excludeAWSServices,
excludeRuntimeTests: excludeRuntimeTests,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -34,17 +34,6 @@ let serviceTargets: [String] = [
// Uncomment this line to enable all services
addAllServices()

let servicesWithIntegrationTests: [String] = [
"A",
"B",
"C",
"D",
"E",
]

// Uncomment this line to enable integration tests
// addIntegrationTests()

// Uncomment this line to enable protocol tests
// addProtocolTests()

Expand All @@ -57,9 +46,8 @@ addResolvedTargets()
let subject = PackageManifestBuilder(
clientRuntimeVersion: .init("1.2.3"),
crtVersion: .init("4.5.6"),
services: ["A","B","C","D","E"].map { PackageManifestBuilder.Service(name: $0, includeIntegrationTests: true) },
services: ["A","B","C","D","E"].map { PackageManifestBuilder.Service(name: $0) },
includeProtocolTests: false,
includeIntegrationTests: false,
excludeAWSServices: false,
excludeRuntimeTests: false,
basePackageContents: { "<contents of base package>" }
Expand Down
Loading
Loading