Skip to content

Commit f2773d3

Browse files
hheydarycopybara-github
authored andcommitted
Integrate native error reporting into the LiteRT-LM Swift API.
LiteRT-LM-PiperOrigin-RevId: 979218526
1 parent 8096ebb commit f2773d3

9 files changed

Lines changed: 626 additions & 124 deletions

swift/BUILD

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -121,6 +121,7 @@ cc_library(
121121
"//c:conversation.h",
122122
"//c:embedding_engine.h",
123123
"//c:engine.h",
124+
"//c:error_reporter.h",
124125
"//c:experimental.h",
125126
"//c:model_info.h",
126127
],
@@ -150,6 +151,7 @@ apple_xcframework(
150151
"//c:engine.h",
151152
"//c:conversation.h",
152153
"//c:embedding_engine.h",
154+
"//c:error_reporter.h",
153155
"//c:experimental.h",
154156
"//c:model_info.h",
155157
],
@@ -188,6 +190,7 @@ genrule(
188190
"//c:engine.h",
189191
"//c:conversation.h",
190192
"//c:embedding_engine.h",
193+
"//c:error_reporter.h",
191194
"//c:experimental.h",
192195
"//c:model_info.h",
193196
],
@@ -200,6 +203,7 @@ genrule(
200203
cp $(location //c:engine.h) CLiteRTLM_mac/Headers/
201204
cp $(location //c:conversation.h) CLiteRTLM_mac/Headers/
202205
cp $(location //c:embedding_engine.h) CLiteRTLM_mac/Headers/
206+
cp $(location //c:error_reporter.h) CLiteRTLM_mac/Headers/
203207
cp $(location //c:experimental.h) CLiteRTLM_mac/Headers/
204208
cp $(location //c:model_info.h) CLiteRTLM_mac/Headers/
205209
# Create module map
@@ -208,6 +212,7 @@ module CLiteRTLM {
208212
header "engine.h"
209213
header "conversation.h"
210214
header "embedding_engine.h"
215+
header "error_reporter.h"
211216
header "experimental.h"
212217
header "model_info.h"
213218
export *

swift/Conversation.swift

Lines changed: 39 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -193,8 +193,10 @@ public final class Conversation: Sendable {
193193
}
194194
if let repetitionPenaltyConfig = repetitionPenaltyConfig {
195195
guard let cRepetitionPenaltyConfig = litert_lm_repetition_penalty_config_create() else {
196-
throw LiteRTLMError.conversation(
197-
.invalidResponse("Failed to create native repetition penalty config."))
196+
let errorMsg =
197+
LiteRTLMError.consumeLastError()
198+
?? "Failed to create native repetition penalty config."
199+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
198200
}
199201
defer { litert_lm_repetition_penalty_config_delete(cRepetitionPenaltyConfig) }
200202

@@ -219,8 +221,9 @@ public final class Conversation: Sendable {
219221
}
220222
if let noRepeatNgramConfig = noRepeatNgramConfig {
221223
guard let cNoRepeatNgramConfig = litert_lm_no_repeat_ngram_config_create() else {
222-
throw LiteRTLMError.conversation(
223-
.invalidResponse("Failed to create native no repeat ngram config."))
224+
let errorMsg =
225+
LiteRTLMError.consumeLastError() ?? "Failed to create native no repeat ngram config."
226+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
224227
}
225228
defer { litert_lm_no_repeat_ngram_config_delete(cNoRepeatNgramConfig) }
226229

@@ -237,8 +240,9 @@ public final class Conversation: Sendable {
237240
}
238241
if let suppressTokens = suppressTokensConfig?.suppressTokens, !suppressTokens.isEmpty {
239242
guard let cSuppressTokensConfig = litert_lm_suppress_tokens_config_create() else {
240-
throw LiteRTLMError.conversation(
241-
.invalidResponse("Failed to create native suppress tokens config."))
243+
let errorMsg =
244+
LiteRTLMError.consumeLastError() ?? "Failed to create native suppress tokens config."
245+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
242246
}
243247
defer { litert_lm_suppress_tokens_config_delete(cSuppressTokensConfig) }
244248

@@ -256,8 +260,9 @@ public final class Conversation: Sendable {
256260
}
257261
if let thinkingConfig = thinkingConfig {
258262
guard let cThinkingConfig = litert_lm_thinking_config_create() else {
259-
throw LiteRTLMError.conversation(
260-
.invalidResponse("Failed to create native thinking config."))
263+
let errorMsg =
264+
LiteRTLMError.consumeLastError() ?? "Failed to create native thinking config."
265+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
261266
}
262267
defer { litert_lm_thinking_config_delete(cThinkingConfig) }
263268
litert_lm_thinking_config_set_enable_thinking(
@@ -278,16 +283,17 @@ public final class Conversation: Sendable {
278283
let responsePtr = litert_lm_conversation_send_message(
279284
handle, messageString, extraContextString, optionalArgs)
280285
else {
281-
throw LiteRTLMError.conversation(.invalidResponse("Native sendMessage returned null."))
282-
286+
let errorMsg = LiteRTLMError.consumeLastError() ?? "Native sendMessage returned null."
287+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
283288
}
284289
// Delete the response pointer at the end of each iteration. Handled by defer block.
285290
let responsePtrRef = responsePtr
286291
defer { litert_lm_json_response_delete(responsePtrRef) }
287292

288293
guard let responseChars = litert_lm_json_response_get_string(responsePtr) else {
289-
throw LiteRTLMError.conversation(
290-
.invalidResponse("Native get string for response returned null."))
294+
let errorMsg =
295+
LiteRTLMError.consumeLastError() ?? "Native get string for response returned null."
296+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
291297
}
292298
let responseString = String(cString: responseChars)
293299

@@ -438,8 +444,10 @@ public final class Conversation: Sendable {
438444
}
439445
if let repetitionPenaltyConfig = repetitionPenaltyConfig {
440446
guard let cRepetitionPenaltyConfig = litert_lm_repetition_penalty_config_create() else {
441-
throw LiteRTLMError.conversation(
442-
.invalidResponse("Failed to create native repetition penalty config."))
447+
let errorMsg =
448+
LiteRTLMError.consumeLastError()
449+
?? "Failed to create native repetition penalty config."
450+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
443451
}
444452
defer { litert_lm_repetition_penalty_config_delete(cRepetitionPenaltyConfig) }
445453

@@ -464,8 +472,9 @@ public final class Conversation: Sendable {
464472
}
465473
if let noRepeatNgramConfig = noRepeatNgramConfig {
466474
guard let cNoRepeatNgramConfig = litert_lm_no_repeat_ngram_config_create() else {
467-
throw LiteRTLMError.conversation(
468-
.invalidResponse("Failed to create native no repeat ngram config."))
475+
let errorMsg =
476+
LiteRTLMError.consumeLastError() ?? "Failed to create native no repeat ngram config."
477+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
469478
}
470479
defer { litert_lm_no_repeat_ngram_config_delete(cNoRepeatNgramConfig) }
471480

@@ -482,8 +491,9 @@ public final class Conversation: Sendable {
482491
}
483492
if let suppressTokens = suppressTokensConfig?.suppressTokens, !suppressTokens.isEmpty {
484493
guard let cSuppressTokensConfig = litert_lm_suppress_tokens_config_create() else {
485-
throw LiteRTLMError.conversation(
486-
.invalidResponse("Failed to create native suppress tokens config."))
494+
let errorMsg =
495+
LiteRTLMError.consumeLastError() ?? "Failed to create native suppress tokens config."
496+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
487497
}
488498
defer { litert_lm_suppress_tokens_config_delete(cSuppressTokensConfig) }
489499

@@ -501,8 +511,9 @@ public final class Conversation: Sendable {
501511
}
502512
if let thinkingConfig = thinkingConfig {
503513
guard let cThinkingConfig = litert_lm_thinking_config_create() else {
504-
throw LiteRTLMError.conversation(
505-
.invalidResponse("Failed to create native thinking config."))
514+
let errorMsg =
515+
LiteRTLMError.consumeLastError() ?? "Failed to create native thinking config."
516+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
506517
}
507518
defer { litert_lm_thinking_config_delete(cThinkingConfig) }
508519
litert_lm_thinking_config_set_enable_thinking(
@@ -532,7 +543,8 @@ public final class Conversation: Sendable {
532543

533544
guard status == 0 else {
534545
Unmanaged<StreamContext>.fromOpaque(contextPtr).release()
535-
throw LiteRTLMError.conversation(.failedToStartStream(status: Int(status)))
546+
let errorMsg = LiteRTLMError.consumeLastError() ?? ""
547+
throw LiteRTLMError.conversation(.failedToStartStream(status: Int(status), message: errorMsg))
536548
}
537549
}
538550

@@ -559,7 +571,9 @@ public final class Conversation: Sendable {
559571

560572
guard let cString = litert_lm_conversation_render_message_to_string(handle, messageString)
561573
else {
562-
throw LiteRTLMError.conversation(.invalidResponse("Failed to render message into string."))
574+
let errorMsg =
575+
LiteRTLMError.consumeLastError() ?? "Failed to render message into string."
576+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
563577
}
564578
return String(cString: cString)
565579
}
@@ -571,7 +585,9 @@ public final class Conversation: Sendable {
571585
public func renderPrefaceIntoString() throws -> String {
572586
let handle = try checkIsAlive()
573587
guard let cString = litert_lm_conversation_render_preface_to_string(handle) else {
574-
throw LiteRTLMError.conversation(.invalidResponse("Failed to render preface into string."))
588+
let errorMsg =
589+
LiteRTLMError.consumeLastError() ?? "Failed to render preface into string."
590+
throw LiteRTLMError.conversation(.invalidResponse(errorMsg))
575591
}
576592
return String(cString: cString)
577593
}

0 commit comments

Comments
 (0)