///|
/// Return the package release version.
pub fn package_version() -> String {
"0.1.0"
}
///|
/// Selects the rendered representation of a Pinyin syllable.
pub(all) enum ToneStyle {
ToneMarks
ToneNumbers
PlainPinyin
} derive(Eq, Debug)
///|
/// Controls casing after a syllable has been normalized.
pub(all) enum TextCase {
Lowercase
Uppercase
} derive(Eq, Debug)
///|
/// Controls how text without a known Pinyin reading is handled.
pub(all) enum UnknownPolicy {
PreserveUnknown
DropUnknown
RejectUnknown
} derive(Eq, Debug)
///|
/// Controls how multiple documented readings are exposed.
pub(all) enum AmbiguityPolicy {
SelectFirstReading
PreserveAllReadings
RejectAmbiguous
} derive(Eq, Debug)
///|
/// Stable errors returned by parsing, configuration, and conversion APIs.
pub(all) enum PinyinError {
InvalidSeparator(String)
InvalidSyllable(String, String)
UnknownCharacter(Int)
AmbiguousCharacter(Int, Int)
InvalidSourceSpan(Int, Int)
InvalidLexiconEntry(String, String)
ConflictingLexiconEntry(String)
InvalidLexiconText(String)
InvalidBatchItem(String, String)
InvalidSearchDocument(String, String)
InvalidSearchOptions(String, String)
InvalidSearchQuery(String)
InvalidVariantLimit(Int)
InvalidConversionResult(String)
InvalidAlignment(String)
InvalidWeight(String, Double)
InvalidGeneratedData(String)
} derive(Eq, Debug)
///|
/// Half-open character offsets in the caller's source text.
pub struct SourceSpan {
start_offset : Int
end_offset : Int
} derive(Eq, Debug)
///|
/// Structured warning or decision note emitted by an operation.
pub struct Diagnostic {
code_value : String
message_value : String
source_span : SourceSpan?
} derive(Eq, Debug)
///|
/// Immutable options shared by conversion and rendering operations.
pub struct ConvertOptions {
output_style : ToneStyle
token_separator : String
output_case : TextCase
unknown_behavior : UnknownPolicy
ambiguity_behavior : AmbiguityPolicy
} derive(Eq, Debug)
///|
/// Creates a validated half-open source span.
pub fn source_span(start : Int, end : Int) -> Result[SourceSpan, PinyinError] {
if start < 0 || end < start {
return Err(InvalidSourceSpan(start, end))
}
Ok({ start_offset: start, end_offset: end })
}
///|
pub fn SourceSpan::start(self : SourceSpan) -> Int {
self.start_offset
}
///|
pub fn SourceSpan::end(self : SourceSpan) -> Int {
self.end_offset
}
///|
pub fn SourceSpan::length(self : SourceSpan) -> Int {
self.end_offset - self.start_offset
}
///|
/// Creates a structured diagnostic without interpreting its message.
pub fn diagnostic(
code : String,
message : String,
span : SourceSpan?,
) -> Diagnostic {
{ code_value: code, message_value: message, source_span: span }
}
///|
pub fn Diagnostic::code(self : Diagnostic) -> String {
self.code_value
}
///|
pub fn Diagnostic::message(self : Diagnostic) -> String {
self.message_value
}
///|
pub fn Diagnostic::span(self : Diagnostic) -> SourceSpan? {
self.source_span
}
///|
/// Builds a validated conversion configuration.
pub fn convert_options(
style : ToneStyle,
separator : String,
text_case : TextCase,
unknown_policy : UnknownPolicy,
ambiguity_policy : AmbiguityPolicy,
) -> Result[ConvertOptions, PinyinError] {
if separator.length() == 0 {
return Err(InvalidSeparator("empty"))
}
if separator == "\n" || separator == "\r" || separator == "\r\n" {
return Err(InvalidSeparator("line_break"))
}
Ok({
output_style: style,
token_separator: separator,
output_case: text_case,
unknown_behavior: unknown_policy,
ambiguity_behavior: ambiguity_policy,
})
}
///|
/// Returns conservative display defaults without hiding ambiguity metadata.
pub fn default_convert_options() -> ConvertOptions {
convert_options(
ToneMarks,
" ",
Lowercase,
PreserveUnknown,
SelectFirstReading,
).unwrap()
}
///|
pub fn ConvertOptions::tone_style(self : ConvertOptions) -> ToneStyle {
self.output_style
}
///|
pub fn ConvertOptions::separator(self : ConvertOptions) -> String {
self.token_separator
}
///|
pub fn ConvertOptions::text_case(self : ConvertOptions) -> TextCase {
self.output_case
}
///|
pub fn ConvertOptions::unknown_policy(self : ConvertOptions) -> UnknownPolicy {
self.unknown_behavior
}
///|
pub fn ConvertOptions::ambiguity_policy(
self : ConvertOptions,
) -> AmbiguityPolicy {
self.ambiguity_behavior
}