Skip to content

Commit d6dfc51

Browse files
committed
add more tests
1 parent bb87efd commit d6dfc51

File tree

5 files changed

+226
-13
lines changed

5 files changed

+226
-13
lines changed

Firestore/Source/API/FIRPipelineBridge.mm

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -96,13 +96,15 @@ @implementation FIRExprBridge
9696
@end
9797

9898
@implementation FIRFieldBridge {
99+
FIRFieldPath *field_path;
99100
std::shared_ptr<Field> field;
100101
}
101102

102103
- (id)init:(NSString *)name {
103104
self = [super init];
104105
if (self) {
105-
field = std::make_shared<Field>(MakeString(name));
106+
field_path = [FIRFieldPath pathWithDotSeparatedString:name];
107+
field = std::make_shared<Field>([field_path internalValue].CanonicalString());
106108
}
107109
return self;
108110
}
@@ -111,6 +113,10 @@ - (id)init:(NSString *)name {
111113
return field;
112114
}
113115

116+
- (NSString *)field_name {
117+
return MakeNSString([field_path internalValue].CanonicalString());
118+
}
119+
114120
@end
115121

116122
@implementation FIRConstantBridge {

Firestore/Source/Public/FirebaseFirestore/FIRPipelineBridge.h

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -35,6 +35,7 @@ NS_SWIFT_SENDABLE
3535
NS_SWIFT_NAME(FieldBridge)
3636
@interface FIRFieldBridge : FIRExprBridge
3737
- (id)init:(NSString *)name;
38+
- (NSString *)field_name;
3839
@end
3940

4041
NS_SWIFT_SENDABLE

Firestore/Swift/Source/ExprImpl.swift

Lines changed: 8 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -25,12 +25,12 @@ public extension Expr {
2525

2626
// MARK: Arithmetic Operators
2727

28-
func add(_ values: Expr) -> FunctionExpr {
29-
return FunctionExpr("add", [self, Helper.array([values])])
28+
func add(_ value: Expr) -> FunctionExpr {
29+
return FunctionExpr("add", [self, value])
3030
}
3131

32-
func add(_ values: Sendable) -> FunctionExpr {
33-
return FunctionExpr("add", [self, Helper.array([values])])
32+
func add(_ value: Sendable) -> FunctionExpr {
33+
return FunctionExpr("add", [self, Helper.sendableToExpr(value)])
3434
}
3535

3636
func add(_ values: [Expr]) -> FunctionExpr {
@@ -49,12 +49,12 @@ public extension Expr {
4949
return FunctionExpr("subtract", [self, Helper.sendableToExpr(other)])
5050
}
5151

52-
func multiply(_ values: Expr) -> FunctionExpr {
53-
return FunctionExpr("multiply", [self, Helper.array([values])])
52+
func multiply(_ value: Expr) -> FunctionExpr {
53+
return FunctionExpr("multiply", [self, value])
5454
}
5555

56-
func multiply(_ values: Sendable) -> FunctionExpr {
57-
return FunctionExpr("multiply", [self, Helper.array([values])])
56+
func multiply(_ value: Sendable) -> FunctionExpr {
57+
return FunctionExpr("multiply", [self, Helper.sendableToExpr(value)])
5858
}
5959

6060
func multiply(_ values: [Expr]) -> FunctionExpr {

Firestore/Swift/Source/SwiftAPI/Pipeline/Expr/Field.swift

Lines changed: 4 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -25,8 +25,9 @@ public class Field: ExprBridge, Expr, Selectable, BridgeWrapper, SelectableWrapp
2525
public let fieldName: String
2626

2727
public init(_ fieldName: String) {
28-
self.fieldName = fieldName
29-
alias = fieldName
30-
bridge = FieldBridge(alias)
28+
let fieldBridge = FieldBridge(fieldName)
29+
bridge = fieldBridge
30+
self.fieldName = fieldBridge.field_name()
31+
alias = self.fieldName
3132
}
3233
}

Firestore/Swift/Tests/Integration/PipelineTests.swift

Lines changed: 206 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -596,7 +596,6 @@ class PipelineIntegrationTests: FSTIntegrationTestCase {
596596
try await randomCol.document("dummyDoc").setData(["field": "value"])
597597

598598
let refDate = Date(timeIntervalSince1970: 1_678_886_400)
599-
let refTimestamp = Timestamp(date: refDate)
600599

601600
let constantsFirst: [Selectable] = [
602601
Constant.nil.as("nil"),
@@ -2142,4 +2141,210 @@ class PipelineIntegrationTests: FSTIntegrationTestCase {
21422141
XCTFail("No document retrieved for distance functions part 1")
21432142
}
21442143
}
2144+
2145+
func testVectorLength() async throws {
2146+
let collRef = collectionRef() // Using a new collection for this test
2147+
let db = collRef.firestore
2148+
let docRef = collRef.document("vectorDocForLengthTestFinal")
2149+
2150+
// Add a document with a known vector field
2151+
try await docRef.setData(["embedding": VectorValue([1.0, 2.0, 3.0])])
2152+
2153+
// Construct a pipeline query
2154+
let pipeline = db.pipeline()
2155+
.collection(collRef.path)
2156+
.limit(1) // Limit to the document we just added
2157+
.select(Field("embedding").vectorLength().as("vectorLength"))
2158+
2159+
// Execute the pipeline
2160+
let snapshot = try await pipeline.execute()
2161+
2162+
// Assert that the vectorLength in the result is 3
2163+
XCTAssertEqual(snapshot.results.count, 1, "Should retrieve one document")
2164+
if let resultDoc = snapshot.results.first {
2165+
let expectedResult: [String: Sendable?] = ["vectorLength": 3]
2166+
TestHelper.compare(pipelineResult: resultDoc, expected: expectedResult)
2167+
} else {
2168+
XCTFail("No document retrieved for vectorLength test")
2169+
}
2170+
}
2171+
2172+
func testNestedFields() async throws {
2173+
let collRef = collectionRef(withDocuments: bookDocs)
2174+
let db = collRef.firestore
2175+
2176+
let pipeline = db.pipeline()
2177+
.collection(collRef.path)
2178+
.where(Field("awards.hugo").eq(true))
2179+
.sort(Field("title").descending())
2180+
.select(Field("title"), Field("awards.hugo"))
2181+
2182+
let snapshot = try await pipeline.execute()
2183+
2184+
let expectedResults: [[String: Sendable?]] = [
2185+
["title": "The Hitchhiker's Guide to the Galaxy", "awards.hugo": true],
2186+
["title": "Dune", "awards.hugo": true],
2187+
]
2188+
2189+
TestHelper.compare(pipelineSnapshot: snapshot, expected: expectedResults, enforceOrder: true)
2190+
}
2191+
2192+
func testMapGetWithFieldNameIncludingDotNotation() async throws {
2193+
let collRef = collectionRef(withDocuments: bookDocs)
2194+
let db = collRef.firestore
2195+
2196+
let pipeline = db.pipeline()
2197+
.collection(collRef.path)
2198+
.where(Field("awards.hugo").eq(true)) // Filters to book1 and book10
2199+
.select(
2200+
Field("title"),
2201+
Field("nestedField.level.1"),
2202+
Field("nestedField").mapGet("level.1").mapGet("level.2").as("nested")
2203+
)
2204+
.sort(Field("title").descending())
2205+
2206+
let snapshot = try await pipeline.execute()
2207+
2208+
XCTAssertEqual(snapshot.results.count, 2, "Should retrieve two documents")
2209+
2210+
let expectedResultsArray: [[String: Sendable?]] = [
2211+
[
2212+
"title": "The Hitchhiker's Guide to the Galaxy",
2213+
"nestedField.level.`1`": nil,
2214+
"nested": true,
2215+
],
2216+
[
2217+
"title": "Dune",
2218+
"nestedField.level.`1`": nil,
2219+
"nested": nil,
2220+
],
2221+
]
2222+
TestHelper.compare(
2223+
pipelineSnapshot: snapshot,
2224+
expected: expectedResultsArray,
2225+
enforceOrder: true
2226+
)
2227+
}
2228+
2229+
func testGenericFunctionAddSelectable() async throws {
2230+
let collRef = collectionRef(withDocuments: bookDocs)
2231+
let db = collRef.firestore
2232+
2233+
let pipeline = db.pipeline()
2234+
.collection(collRef.path)
2235+
.sort(Field("rating").descending())
2236+
.limit(1)
2237+
.select(
2238+
FunctionExpr("add", [Field("rating"), Constant(1)]).as(
2239+
"rating"
2240+
)
2241+
)
2242+
2243+
let snapshot = try await pipeline.execute()
2244+
2245+
XCTAssertEqual(snapshot.results.count, 1, "Should retrieve one document")
2246+
2247+
let expectedResult: [String: Sendable?] = [
2248+
"rating": 5.7,
2249+
]
2250+
2251+
if let resultDoc = snapshot.results.first {
2252+
TestHelper.compare(pipelineResult: resultDoc, expected: expectedResult)
2253+
} else {
2254+
XCTFail("No document retrieved for testGenericFunctionAddSelectable")
2255+
}
2256+
}
2257+
2258+
func testGenericFunctionAndVariadicSelectable() async throws {
2259+
let collRef = collectionRef(withDocuments: bookDocs)
2260+
let db = collRef.firestore
2261+
2262+
let pipeline = db.pipeline()
2263+
.collection(collRef.path)
2264+
.where(
2265+
BooleanExpr("and", [Field("rating").gt(0),
2266+
Field("title").charLength().lt(5),
2267+
Field("tags").arrayContains("propaganda")])
2268+
)
2269+
.select("title")
2270+
2271+
let snapshot = try await pipeline.execute()
2272+
2273+
XCTAssertEqual(snapshot.results.count, 1, "Should retrieve one document")
2274+
2275+
let expectedResult: [[String: Sendable?]] = [
2276+
["title": "1984"],
2277+
]
2278+
2279+
TestHelper.compare(pipelineSnapshot: snapshot, expected: expectedResult, enforceOrder: false)
2280+
}
2281+
2282+
func testGenericFunctionArrayContainsAny() async throws {
2283+
let collRef = collectionRef(withDocuments: bookDocs)
2284+
let db = collRef.firestore
2285+
2286+
let pipeline = db.pipeline()
2287+
.collection(collRef.path)
2288+
.where(BooleanExpr("array_contains_any", [Field("tags"), ArrayExpression(["politics"])]))
2289+
.select(Field("title"))
2290+
2291+
let snapshot = try await pipeline.execute()
2292+
2293+
XCTAssertEqual(snapshot.results.count, 1, "Should retrieve one document")
2294+
2295+
let expectedResult: [[String: Sendable?]] = [
2296+
["title": "Dune"],
2297+
]
2298+
2299+
TestHelper.compare(pipelineSnapshot: snapshot, expected: expectedResult, enforceOrder: false)
2300+
}
2301+
2302+
func testGenericFunctionCountIfAggregate() async throws {
2303+
let collRef = collectionRef(withDocuments: bookDocs)
2304+
let db = collRef.firestore
2305+
2306+
let pipeline = db.pipeline()
2307+
.collection(collRef.path)
2308+
.aggregate(AggregateFunction("count_if", [Field("rating").gte(4.5)]).as("countOfBest"))
2309+
2310+
let snapshot = try await pipeline.execute()
2311+
2312+
XCTAssertEqual(snapshot.results.count, 1, "Aggregate should return a single document")
2313+
2314+
let expectedResult: [String: Sendable?] = [
2315+
"countOfBest": 3,
2316+
]
2317+
2318+
if let resultDoc = snapshot.results.first {
2319+
TestHelper.compare(pipelineResult: resultDoc, expected: expectedResult)
2320+
} else {
2321+
XCTFail("No document retrieved for testGenericFunctionCountIfAggregate")
2322+
}
2323+
}
2324+
2325+
func testGenericFunctionSortByCharLen() async throws {
2326+
let collRef = collectionRef(withDocuments: bookDocs)
2327+
let db = collRef.firestore
2328+
2329+
let pipeline = db.pipeline()
2330+
.collection(collRef.path)
2331+
.sort(
2332+
FunctionExpr("char_length", [Field("title")]).ascending(),
2333+
Field("__name__").descending()
2334+
)
2335+
.limit(3)
2336+
.select(Field("title"))
2337+
2338+
let snapshot = try await pipeline.execute()
2339+
2340+
XCTAssertEqual(snapshot.results.count, 3, "Should retrieve three documents")
2341+
2342+
let expectedResults: [[String: Sendable?]] = [
2343+
["title": "1984"],
2344+
["title": "Dune"],
2345+
["title": "The Great Gatsby"],
2346+
]
2347+
2348+
TestHelper.compare(pipelineSnapshot: snapshot, expected: expectedResults, enforceOrder: true)
2349+
}
21452350
}

0 commit comments

Comments
 (0)