Skip to content

Commit 7e5e71d

Browse files
committed
add option api
1 parent 71820c7 commit 7e5e71d

File tree

6 files changed

+164
-1
lines changed

6 files changed

+164
-1
lines changed
Lines changed: 83 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,83 @@
1+
// Copyright 2025 Google LLC
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
public struct ExplainOptions: OptionProtocol, Sendable, Equatable, Hashable {
16+
public struct Mode: Sendable, Equatable, Hashable {
17+
let rawValue: String
18+
19+
public static let execute = Mode(rawValue: "execute")
20+
public static let explain = Mode(rawValue: "explain")
21+
public static let analyze = Mode(rawValue: "analyze")
22+
23+
init(rawValue: String) {
24+
self.rawValue = rawValue
25+
}
26+
}
27+
28+
public struct OutputFormat: Sendable, Equatable, Hashable {
29+
let rawValue: String
30+
31+
public static let text = OutputFormat(rawValue: "text")
32+
public static let json = OutputFormat(rawValue: "json")
33+
public static let `struct` = OutputFormat(rawValue: "struct")
34+
35+
init(rawValue: String) {
36+
self.rawValue = rawValue
37+
}
38+
}
39+
40+
public struct Verbosity: Sendable, Equatable, Hashable {
41+
let rawValue: String
42+
43+
public static let summaryOnly = Verbosity(rawValue: "summary_only")
44+
public static let executionTree = Verbosity(rawValue: "execution_tree")
45+
46+
init(rawValue: String) {
47+
self.rawValue = rawValue
48+
}
49+
}
50+
51+
public struct Profiles: Sendable, Equatable, Hashable {
52+
let rawValue: String
53+
54+
public static let latency = Profiles(rawValue: "latency")
55+
public static let recordsCount = Profiles(rawValue: "records_count")
56+
public static let bytesThroughput = Profiles(rawValue: "bytes_throughput")
57+
58+
init(rawValue: String) {
59+
self.rawValue = rawValue
60+
}
61+
}
62+
63+
public let mode: Mode?
64+
public let outputFormat: OutputFormat?
65+
public let verbosity: Verbosity?
66+
public let indexRecommendation: Bool?
67+
public let profiles: Profiles?
68+
public let redact: Bool?
69+
70+
public init(mode: Mode? = nil,
71+
outputFormat: OutputFormat? = nil,
72+
verbosity: Verbosity? = nil,
73+
indexRecommendation: Bool? = nil,
74+
profiles: Profiles? = nil,
75+
redact: Bool? = nil) {
76+
self.mode = mode
77+
self.outputFormat = outputFormat
78+
self.verbosity = verbosity
79+
self.indexRecommendation = indexRecommendation
80+
self.profiles = profiles
81+
self.redact = redact
82+
}
83+
}
Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
// Copyright 2025 Google LLC
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
public struct CustomOptions: OptionProtocol {
16+
var values: [String: Sendable]
17+
public init(_ values: [String: Sendable] = [:]) {
18+
self.values = values
19+
}
20+
}
Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// Copyright 2025 Google LLC
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
public struct IndexMode: Sendable, Equatable, Hashable {
16+
let rawValue: String
17+
18+
public static let recommended = IndexMode(rawValue: "recommended")
19+
20+
init(rawValue: String) {
21+
self.rawValue = rawValue
22+
}
23+
}
Lines changed: 15 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,15 @@
1+
// Copyright 2025 Google LLC
2+
//
3+
// Licensed under the Apache License, Version 2.0 (the "License");
4+
// you may not use this file except in compliance with the License.
5+
// You may obtain a copy of the License at
6+
//
7+
// http://www.apache.org/licenses/LICENSE-2.0
8+
//
9+
// Unless required by applicable law or agreed to in writing, software
10+
// distributed under the License is distributed on an "AS IS" BASIS,
11+
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
12+
// See the License for the specific language governing permissions and
13+
// limitations under the License.
14+
15+
public protocol OptionProtocol: Sendable {}

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

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -109,7 +109,9 @@ public struct Pipeline: @unchecked Sendable {
109109
///
110110
/// - Throws: An error if the pipeline execution fails on the backend.
111111
/// - Returns: A `PipelineSnapshot` containing the result of the pipeline execution.
112-
public func execute() async throws -> PipelineSnapshot {
112+
public func execute(explainOptions: ExplainOptions? = nil,
113+
indexMode: IndexMode? = nil,
114+
customOptions: CustomOptions? = nil) async throws -> PipelineSnapshot {
113115
return try await withCheckedThrowingContinuation { continuation in
114116
self.bridge.execute { result, error in
115117
if let error {

Firestore/Swift/Tests/Integration/PipelineApiTests.swift

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -401,4 +401,24 @@ final class PipelineTests: FSTIntegrationTestCase {
401401
// Create a generic AggregateFunction for use where AggregateFunction is required
402402
let mySum = AggregateFunction("sum", [Field("price")])
403403
}
404+
405+
func testOption() async throws {
406+
let _: PipelineSnapshot = try await db.pipeline().database().execute(
407+
explainOptions:
408+
ExplainOptions(
409+
mode: .analyze,
410+
outputFormat: .json,
411+
verbosity: .executionTree,
412+
indexRecommendation: true,
413+
profiles: .bytesThroughput,
414+
redact: false
415+
),
416+
indexMode: .recommended,
417+
customOptions: CustomOptions(
418+
["option_not_known_to_sdk": true,
419+
"explain_options.new_explain_option": "any value here",
420+
"explain_options.mode": "newServerKnownMode"]
421+
)
422+
)
423+
}
404424
}

0 commit comments

Comments
 (0)