diff --git a/Libraries.xctestplan b/Libraries.xctestplan
new file mode 100644
index 0000000..67792eb
--- /dev/null
+++ b/Libraries.xctestplan
@@ -0,0 +1,24 @@
+{
+ "configurations" : [
+ {
+ "id" : "BF43DE96-4FFB-475F-B056-3EE94ACD1F54",
+ "name" : "Test Scheme Action",
+ "options" : {
+
+ }
+ }
+ ],
+ "defaultOptions" : {
+ "codeCoverage" : false
+ },
+ "testTargets" : [
+ {
+ "target" : {
+ "containerPath" : "container:Libraries",
+ "identifier" : "ReviewsFoundationTest",
+ "name" : "ReviewsFoundationTest"
+ }
+ }
+ ],
+ "version" : 1
+}
diff --git a/Libraries/.swiftpm/xcode/xcshareddata/xcschemes/ReviewsFoundationTest.xcscheme b/Libraries/.swiftpm/xcode/xcshareddata/xcschemes/ReviewsFoundationTest.xcscheme
new file mode 100644
index 0000000..212da11
--- /dev/null
+++ b/Libraries/.swiftpm/xcode/xcshareddata/xcschemes/ReviewsFoundationTest.xcscheme
@@ -0,0 +1,54 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Libraries/.swiftpm/xcode/xcshareddata/xcschemes/ReviewsKit.xcscheme b/Libraries/.swiftpm/xcode/xcshareddata/xcschemes/ReviewsKit.xcscheme
new file mode 100644
index 0000000..6b81aea
--- /dev/null
+++ b/Libraries/.swiftpm/xcode/xcshareddata/xcschemes/ReviewsKit.xcscheme
@@ -0,0 +1,72 @@
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
diff --git a/Libraries/Foundation/Kit/Sources/Extensions/String+Constants.swift b/Libraries/Foundation/Kit/Sources/Extensions/String+Constants.swift
new file mode 100644
index 0000000..ab80392
--- /dev/null
+++ b/Libraries/Foundation/Kit/Sources/Extensions/String+Constants.swift
@@ -0,0 +1,18 @@
+//
+// String+Constants.swift
+// ReviewsFoundation
+//
+// Created by Javier Cicchelli on 16/03/2024.
+// Copyright © 2024 Röck+Cöde VoF. All rights reserved.
+//
+
+import Foundation
+
+public extension String {
+
+ // MARK: Constants
+
+ /// A representation of an empty string.
+ static let empty: String = ""
+
+}
diff --git a/Libraries/Foundation/Test/Tests/Extensions/String+ConstantsTests.swift b/Libraries/Foundation/Test/Tests/Extensions/String+ConstantsTests.swift
new file mode 100644
index 0000000..fcd80c7
--- /dev/null
+++ b/Libraries/Foundation/Test/Tests/Extensions/String+ConstantsTests.swift
@@ -0,0 +1,27 @@
+//
+// String+ConstantsTests.swift
+// ReviewsFoundationTest
+//
+// Created by Javier Cicchelli on 16/03/2024.
+// Copyright © 2024 Röck+Cöde VoF. All rights reserved.
+//
+
+import ReviewsFoundation
+import XCTest
+
+final class String_ConstantsTests: XCTestCase {
+
+ // MARK: Properties
+ private var sut: String!
+
+ // MARK: Constants tests
+ func testEmpty() throws {
+ // GIVEN
+ sut = .empty
+
+ // WHEN
+ // THEN
+ XCTAssertTrue(sut.isEmpty)
+ }
+
+}
diff --git a/Libraries/Package.swift b/Libraries/Package.swift
new file mode 100644
index 0000000..2fa99db
--- /dev/null
+++ b/Libraries/Package.swift
@@ -0,0 +1,57 @@
+// swift-tools-version: 5.10
+
+import PackageDescription
+
+let package = Package(
+ name: .Package.name,
+ platforms: [
+ .iOS(.v14)
+ ],
+ products: [
+ .library(
+ name: .Product.name.kit,
+ targets: [
+ .Target.foundation
+ ]
+ ),
+ ],
+ targets: [
+ .target(
+ name: .Target.foundation,
+ path: "Foundation/Kit"
+ ),
+ .testTarget(
+ name: .Target.foundation.test,
+ dependencies: [
+ .byName(name: .Target.foundation)
+ ],
+ path: "Foundation/Test"
+ ),
+ ]
+)
+
+// MARK: - String+Constants
+private extension String {
+ enum Package {
+ static let name = "reviews-kit"
+ }
+
+ enum Product {
+ static let name = "Reviews"
+ }
+
+ enum Target {
+ static let foundation = "\(String.Product.name)Foundation"
+ }
+}
+
+// MARK: - String+Computed
+private extension String {
+ var kit: String {
+ "\(self)Kit"
+ }
+
+ var test: String {
+ "\(self)Test"
+ }
+}
diff --git a/Reviews.xcodeproj/project.pbxproj b/Reviews.xcodeproj/project.pbxproj
index 0c43e56..4feecf0 100644
--- a/Reviews.xcodeproj/project.pbxproj
+++ b/Reviews.xcodeproj/project.pbxproj
@@ -14,6 +14,8 @@
02DC7FAD2BA51B4C000EEEBE /* ReviewCell.swift in Sources */ = {isa = PBXBuildFile; fileRef = 345AD13024C6EE64004E2EE1 /* ReviewCell.swift */; };
02DC7FAE2BA51B4C000EEEBE /* FeedViewController.swift in Sources */ = {isa = PBXBuildFile; fileRef = 345AD12F24C6EE64004E2EE1 /* FeedViewController.swift */; };
02DC7FAF2BA51B4C000EEEBE /* Review.swift in Sources */ = {isa = PBXBuildFile; fileRef = 345AD13124C6EE64004E2EE1 /* Review.swift */; };
+ 02DC7FB32BA52518000EEEBE /* ReviewsKit in Frameworks */ = {isa = PBXBuildFile; productRef = 02DC7FB22BA52518000EEEBE /* ReviewsKit */; };
+ 02DC7FB52BA52520000EEEBE /* ReviewsKit in Frameworks */ = {isa = PBXBuildFile; productRef = 02DC7FB42BA52520000EEEBE /* ReviewsKit */; };
345AD11C24C6EDD9004E2EE1 /* AppDelegate.swift in Sources */ = {isa = PBXBuildFile; fileRef = 345AD11B24C6EDD9004E2EE1 /* AppDelegate.swift */; };
345AD12524C6EDDC004E2EE1 /* Assets.xcassets in Resources */ = {isa = PBXBuildFile; fileRef = 345AD12424C6EDDC004E2EE1 /* Assets.xcassets */; };
345AD12824C6EDDC004E2EE1 /* LaunchScreen.storyboard in Resources */ = {isa = PBXBuildFile; fileRef = 345AD12624C6EDDC004E2EE1 /* LaunchScreen.storyboard */; };
@@ -44,8 +46,10 @@
/* End PBXCopyFilesBuildPhase section */
/* Begin PBXFileReference section */
+ 02900C492BA530E6008D2E8D /* Libraries.xctestplan */ = {isa = PBXFileReference; lastKnownFileType = text; path = Libraries.xctestplan; sourceTree = ""; };
02DC7F8F2BA51793000EEEBE /* ReviewsFeed.framework */ = {isa = PBXFileReference; explicitFileType = wrapper.framework; includeInIndex = 0; path = ReviewsFeed.framework; sourceTree = BUILT_PRODUCTS_DIR; };
02DC7F912BA51793000EEEBE /* ReviewsFeed.h */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.c.h; path = ReviewsFeed.h; sourceTree = ""; };
+ 02DC7FB12BA52084000EEEBE /* Libraries */ = {isa = PBXFileReference; lastKnownFileType = wrapper; path = Libraries; sourceTree = ""; };
345AD11824C6EDD9004E2EE1 /* Reviews.app */ = {isa = PBXFileReference; explicitFileType = wrapper.application; includeInIndex = 0; path = Reviews.app; sourceTree = BUILT_PRODUCTS_DIR; };
345AD11B24C6EDD9004E2EE1 /* AppDelegate.swift */ = {isa = PBXFileReference; lastKnownFileType = sourcecode.swift; path = AppDelegate.swift; sourceTree = ""; };
345AD12424C6EDDC004E2EE1 /* Assets.xcassets */ = {isa = PBXFileReference; lastKnownFileType = folder.assetcatalog; path = Assets.xcassets; sourceTree = ""; };
@@ -62,6 +66,7 @@
isa = PBXFrameworksBuildPhase;
buildActionMask = 2147483647;
files = (
+ 02DC7FB32BA52518000EEEBE /* ReviewsKit in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
@@ -70,12 +75,21 @@
buildActionMask = 2147483647;
files = (
02DC7FA22BA51793000EEEBE /* ReviewsFeed.framework in Frameworks */,
+ 02DC7FB52BA52520000EEEBE /* ReviewsKit in Frameworks */,
);
runOnlyForDeploymentPostprocessing = 0;
};
/* End PBXFrameworksBuildPhase section */
/* Begin PBXGroup section */
+ 02900C4A2BA53162008D2E8D /* Test Plans */ = {
+ isa = PBXGroup;
+ children = (
+ 02900C492BA530E6008D2E8D /* Libraries.xctestplan */,
+ );
+ name = "Test Plans";
+ sourceTree = "";
+ };
02DC7F722BA4F8F0000EEEBE /* Resources */ = {
isa = PBXGroup;
children = (
@@ -149,8 +163,10 @@
345AD10F24C6EDD9004E2EE1 = {
isa = PBXGroup;
children = (
+ 02DC7FB12BA52084000EEEBE /* Libraries */,
02DC7FAB2BA51848000EEEBE /* Frameworks */,
345AD11A24C6EDD9004E2EE1 /* App */,
+ 02900C4A2BA53162008D2E8D /* Test Plans */,
345AD11924C6EDD9004E2EE1 /* Products */,
);
sourceTree = "";
@@ -201,6 +217,9 @@
dependencies = (
);
name = Feed;
+ packageProductDependencies = (
+ 02DC7FB22BA52518000EEEBE /* ReviewsKit */,
+ );
productName = Feed;
productReference = 02DC7F8F2BA51793000EEEBE /* ReviewsFeed.framework */;
productType = "com.apple.product-type.framework";
@@ -220,6 +239,9 @@
02DC7FA12BA51793000EEEBE /* PBXTargetDependency */,
);
name = App;
+ packageProductDependencies = (
+ 02DC7FB42BA52520000EEEBE /* ReviewsKit */,
+ );
productName = AppStoreReviews;
productReference = 345AD11824C6EDD9004E2EE1 /* Reviews.app */;
productType = "com.apple.product-type.application";
@@ -625,6 +647,17 @@
defaultConfigurationName = Release;
};
/* End XCConfigurationList section */
+
+/* Begin XCSwiftPackageProductDependency section */
+ 02DC7FB22BA52518000EEEBE /* ReviewsKit */ = {
+ isa = XCSwiftPackageProductDependency;
+ productName = ReviewsKit;
+ };
+ 02DC7FB42BA52520000EEEBE /* ReviewsKit */ = {
+ isa = XCSwiftPackageProductDependency;
+ productName = ReviewsKit;
+ };
+/* End XCSwiftPackageProductDependency section */
};
rootObject = 345AD11024C6EDD9004E2EE1 /* Project object */;
}