Skip to content

[Bug]: Duration encoded as integer (e.g. milliseconds) can serialize as floating point due to use of TimeSpan.TotalMilliseconds #10831

@joseharriaga

Description

@joseharriaga

Describe the bug

In TypeSpec, it is possible to define a property of type duration with different encodings as described here: https://typespec.io/docs/libraries/http/encoding/#duration

Example definition:

@encode(DurationKnownEncoding.milliseconds, integer)
audio_end_ms: duration;

This indicates that the audio_end_ms property is an integer (milliseconds). However, the generated C# code represents this as a TimeSpan and serializes it as follows:

if (!Patch.Contains("$.audio_end_ms"u8))
{
    writer.WritePropertyName("audio_end_ms"u8);
    writer.WriteNumberValue(AudioEndMs.TotalMilliseconds);
}

The issue: TimeSpan.TotalMilliseconds is a double, so this code can serialize values with fractional milliseconds (e.g., 123.45), violating the contract where audio_end_ms must be an integer. This can result in serialization output not matching the expected API contract.

Expected: The code should round TotalMilliseconds up or down (or something like AudioEndMs.Ticks / TimeSpan.TicksPerMillisecond) to ensure only integers are written for the property.

Please consider updating the serialization logic to guarantee integer values when the original TypeSpec contract expects an integer.

Reproduction

Define a property in TypeSpec using:

@encode(DurationKnownEncoding.milliseconds, integer)
audio_end_ms: duration;

Generate the C# client and observe the serialization code for this member: AudioEndMs will use TotalMilliseconds resulting in double output values. Test with a TimeSpan representing fractional milliseconds and see if output is a floating point value. The value should be serialized as an integer.

Checklist

Metadata

Metadata

Labels

bugSomething isn't workingemitter:client:csharpIssue for the C# client emitter: @typespec/http-client-csharp

Type

No fields configured for Bug.

Projects

No projects

Milestone

No milestone

Relationships

None yet

Development

No branches or pull requests

Issue actions