Skip to content

Commit ec61354

Browse files
authored
Make status code fields settable (#377)
* Make status code fields settable This is very handy for constructing status codes dynamically. * Clear category when setting severity
1 parent 00801eb commit ec61354

File tree

3 files changed

+166
-17
lines changed

3 files changed

+166
-17
lines changed

Cognite.Extensions/TimeSeries/Alpha/StatusCodeHelpers.cs

Lines changed: 73 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
using System;
22
using System.Collections.Generic;
3+
using System.ComponentModel;
34
using System.Linq;
45
using System.Text;
56

@@ -156,14 +157,16 @@ public InvalidStatusCodeException()
156157
/// </summary>
157158
public struct StatusCode
158159
{
160+
private ulong _code;
161+
159162
/// <summary>
160163
/// Status code
161164
/// </summary>
162-
public ulong Code { get; }
165+
public ulong Code { get => _code; }
163166

164167
internal StatusCode(ulong code)
165168
{
166-
Code = code;
169+
_code = code;
167170
}
168171

169172
/// <summary>
@@ -270,19 +273,19 @@ public static StatusCode Create(ulong code)
270273
/// <inheritdoc />
271274
public override readonly bool Equals(object? obj)
272275
{
273-
return obj is StatusCode code && code.Code == Code;
276+
return obj is StatusCode code && code.Code == _code;
274277
}
275278

276279
/// <inheritdoc />
277280
public override readonly int GetHashCode()
278281
{
279-
return Code.GetHashCode();
282+
return _code.GetHashCode();
280283
}
281284

282285
/// <inheritdoc />
283286
public override readonly string ToString()
284287
{
285-
if (Code == 0) return "Good";
288+
if (_code == 0) return "Good";
286289
var builder = new StringBuilder();
287290

288291
builder.Append(Category);
@@ -298,57 +301,111 @@ public override readonly string ToString()
298301
return builder.ToString();
299302
}
300303

304+
private void SetBool(bool value, byte offset)
305+
{
306+
_code = _code & ~(1ul << offset) | ((value ? 1ul : 0ul) << offset);
307+
}
308+
309+
private readonly bool GetBool(byte offset)
310+
{
311+
return (_code & (1ul << offset)) != 0;
312+
}
313+
301314
/// <summary>
302315
/// Type of status code.
303316
/// </summary>
304-
public readonly Severity Severity => (Severity)((Code >> 30) & 0b11);
317+
public Severity Severity
318+
{
319+
readonly get => (Severity)((_code >> 30) & 0b11);
320+
set => _code = _code & ~StatusCodeHelpers.CATEGORY_MASK | ((((ulong)value) & 0b11) << 30);
321+
}
305322

306323
/// <summary>
307324
/// Structure changed flag.
308325
/// </summary>
309-
public readonly bool StructureChanged => (Code & (1 << 15)) != 0;
326+
public bool StructureChanged
327+
{
328+
readonly get => GetBool(15);
329+
set => SetBool(value, 15);
330+
}
310331
/// <summary>
311332
/// Semantics changed flag.
312333
/// </summary>
313-
public readonly bool SemanticsChanged => (Code & (1 << 14)) != 0;
334+
public bool SemanticsChanged
335+
{
336+
readonly get => GetBool(14);
337+
set => SetBool(value, 14);
338+
}
314339

315340
/// <summary>
316341
/// Whether this is a data value info type.
317342
/// </summary>
318-
public readonly bool IsDataValueInfoType => (Code & (1 << 10)) != 0;
343+
public bool IsDataValueInfoType
344+
{
345+
readonly get => GetBool(10);
346+
set => SetBool(value, 10);
347+
}
319348

320349
/// <summary>
321350
/// Whether the value is bounded by some limit.
322351
/// </summary>
323-
public readonly Limit Limit => (Limit)((Code >> 8) & 0b11);
352+
public Limit Limit
353+
{
354+
readonly get => (Limit)((_code >> 8) & 0b11);
355+
set => _code = _code & ~(0b11ul << 8) | ((((ulong)value) & 0b11) << 8);
356+
}
324357

325358
/// <summary>
326359
/// Status code category.
327360
/// </summary>
328-
public readonly StatusCodeCategory Category => (StatusCodeCategory)(Code & StatusCodeHelpers.CATEGORY_MASK);
361+
public StatusCodeCategory Category
362+
{
363+
readonly get => (StatusCodeCategory)(_code & StatusCodeHelpers.CATEGORY_MASK);
364+
set => _code = _code & ~StatusCodeHelpers.CATEGORY_MASK | ((ulong)value) & StatusCodeHelpers.CATEGORY_MASK;
365+
}
329366

330367
/// <summary>
331368
/// Whether the value is overflowed.
332369
/// </summary>
333-
public readonly bool IsOverflow => (Code & (1 << 7)) != 0;
370+
public bool IsOverflow
371+
{
372+
readonly get => GetBool(7);
373+
set => SetBool(value, 7);
374+
}
334375

335376
/// <summary>
336377
/// Multi value flag.
337378
/// </summary>
338-
public readonly bool IsMultiValue => (Code & (1 << 4)) != 0;
379+
public bool IsMultiValue
380+
{
381+
readonly get => GetBool(4);
382+
set => SetBool(value, 4);
383+
}
339384
/// <summary>
340385
/// Has extra data flag.
341386
/// </summary>
342-
public readonly bool HasExtraData => (Code & (1 << 3)) != 0;
387+
public bool HasExtraData
388+
{
389+
readonly get => GetBool(3);
390+
set => SetBool(value, 3);
391+
}
343392
/// <summary>
344393
/// Is partial flag.
345394
/// </summary>
346-
public readonly bool IsPartial => (Code & (1 << 2)) != 0;
395+
public bool IsPartial
396+
{
397+
readonly get => GetBool(2);
398+
set => SetBool(value, 2);
399+
}
347400

348401
/// <summary>
349402
/// Type of value origin.
350403
/// </summary>
351-
public readonly ValueType ValueType => (ValueType)(Code & 0b11);
404+
public ValueType ValueType
405+
{
406+
readonly get => (ValueType)(_code & 0b11);
407+
set => _code = _code & ~0b11ul | ((ulong)value) & 0b11ul;
408+
}
352409
}
353410

354411
/// <summary>

ExtractorUtils.Test/unit/StatusCodeTests.cs

Lines changed: 92 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -27,5 +27,97 @@ public void TestParse()
2727
Assert.Throws<InvalidStatusCodeException>(() => StatusCode.Parse("Bad, Whoop"));
2828
}
2929

30+
[Fact]
31+
public void TestModify()
32+
{
33+
var code = StatusCode.Create(0);
34+
Assert.Equal(Severity.Good, code.Severity);
35+
code.Severity = Severity.Uncertain;
36+
Assert.Equal(Severity.Uncertain, code.Severity);
37+
code.Severity = Severity.Bad;
38+
Assert.Equal(Severity.Bad, code.Severity);
39+
40+
41+
Assert.False(code.StructureChanged);
42+
code.StructureChanged = true;
43+
Assert.True(code.StructureChanged);
44+
code.StructureChanged = false;
45+
Assert.False(code.StructureChanged);
46+
code.StructureChanged = true;
47+
48+
Assert.False(code.SemanticsChanged);
49+
code.SemanticsChanged = true;
50+
Assert.True(code.SemanticsChanged);
51+
code.SemanticsChanged = false;
52+
Assert.False(code.SemanticsChanged);
53+
code.SemanticsChanged = true;
54+
55+
Assert.False(code.IsDataValueInfoType);
56+
code.IsDataValueInfoType = true;
57+
Assert.True(code.IsDataValueInfoType);
58+
code.IsDataValueInfoType = false;
59+
Assert.False(code.IsDataValueInfoType);
60+
code.IsDataValueInfoType = true;
61+
62+
Assert.Equal(Limit.None, code.Limit);
63+
code.Limit = Limit.High;
64+
Assert.Equal(Limit.High, code.Limit);
65+
code.Limit = Limit.Constant;
66+
Assert.Equal(Limit.Constant, code.Limit);
67+
68+
Assert.Equal(StatusCodeCategory.Bad, code.Category);
69+
code.Category = StatusCodeCategory.BadAggregateInvalidInputs;
70+
Assert.Equal(StatusCodeCategory.BadAggregateInvalidInputs, code.Category);
71+
code.Category = StatusCodeCategory.UncertainDataSubNormal;
72+
Assert.Equal(StatusCodeCategory.UncertainDataSubNormal, code.Category);
73+
74+
Assert.False(code.IsOverflow);
75+
code.IsOverflow = true;
76+
Assert.True(code.IsOverflow);
77+
code.IsOverflow = false;
78+
Assert.False(code.IsOverflow);
79+
code.IsOverflow = true;
80+
81+
Assert.False(code.IsMultiValue);
82+
code.IsMultiValue = true;
83+
Assert.True(code.IsMultiValue);
84+
code.IsMultiValue = false;
85+
Assert.False(code.IsMultiValue);
86+
code.IsMultiValue = true;
87+
88+
Assert.False(code.HasExtraData);
89+
code.HasExtraData = true;
90+
Assert.True(code.HasExtraData);
91+
code.HasExtraData = false;
92+
Assert.False(code.HasExtraData);
93+
code.HasExtraData = true;
94+
95+
Assert.False(code.IsPartial);
96+
code.IsPartial = true;
97+
Assert.True(code.IsPartial);
98+
code.IsPartial = false;
99+
Assert.False(code.IsPartial);
100+
code.IsPartial = true;
101+
102+
Assert.Equal(ValueType.Raw, code.ValueType);
103+
code.ValueType = ValueType.Calculated;
104+
Assert.Equal(ValueType.Calculated, code.ValueType);
105+
code.ValueType = ValueType.Interpolated;
106+
Assert.Equal(ValueType.Interpolated, code.ValueType);
107+
108+
109+
Assert.Equal(Severity.Uncertain, code.Severity);
110+
Assert.True(code.StructureChanged);
111+
Assert.True(code.SemanticsChanged);
112+
Assert.True(code.IsDataValueInfoType);
113+
Assert.Equal(Limit.Constant, code.Limit);
114+
Assert.Equal(StatusCodeCategory.UncertainDataSubNormal, code.Category);
115+
Assert.True(code.IsOverflow);
116+
Assert.True(code.IsMultiValue);
117+
Assert.True(code.HasExtraData);
118+
Assert.True(code.IsPartial);
119+
Assert.Equal(ValueType.Interpolated, code.ValueType);
120+
}
121+
30122
}
31123
}

version

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
1.20.0
1+
1.21.0

0 commit comments

Comments
 (0)