diff --git a/src/Candid/Models/Values/CandidService.cs b/src/Candid/Models/Values/CandidService.cs index c339b200..9f1f924c 100644 --- a/src/Candid/Models/Values/CandidService.cs +++ b/src/Candid/Models/Values/CandidService.cs @@ -58,11 +58,7 @@ internal override void EncodeValue(CandidType type, Func(0); return; } - int size = this.principalId!.Raw.Length + 1; - Span bytes = destination.GetSpan(size); - bytes[0] = 1; // Set first byte to 1 - this.principalId.Raw.CopyTo(bytes[1..]); // Set other bytes to raw id - destination.Advance(size); + CandidValue.Principal(this.principalId!).EncodeValue(CandidType.Principal(), getReferencedType, destination); } /// diff --git a/src/Candid/Parsers/CandidByteParser.cs b/src/Candid/Parsers/CandidByteParser.cs index 167ed881..90c295e1 100644 --- a/src/Candid/Parsers/CandidByteParser.cs +++ b/src/Candid/Parsers/CandidByteParser.cs @@ -582,11 +582,14 @@ public Principal ReadPrincipal() // Opaque reference throw new NotImplementedException(); } - else - { - List bytes = this.ReadVectorInner(() => this.ReadByte()); - return Principal.FromBytes(bytes.ToArray()); - } + + return this.ReadTransparentPrincipal(); + } + + private Principal ReadTransparentPrincipal() + { + List bytes = this.ReadVectorInner(this.ReadByte); + return Principal.FromBytes(bytes.ToArray()); } public sbyte ReadInt8() @@ -647,7 +650,7 @@ public CandidService ReadServiceValue() } else { - Principal? principalId = this.ReadPrincipal(); + Principal principalId = this.ReadTransparentPrincipal(); return new CandidService(principalId); } } diff --git a/test/Candid.Tests/CandidEncodingTests.cs b/test/Candid.Tests/CandidEncodingTests.cs index 8ac1c6bd..86f8d603 100644 --- a/test/Candid.Tests/CandidEncodingTests.cs +++ b/test/Candid.Tests/CandidEncodingTests.cs @@ -432,6 +432,33 @@ public void Encode_Record_Recursive() Assert.Equal(expectedArg, actualArg); } + [Fact] + public void Encode_Service_Example1() + { + const string hex = "4449444C026A000001016901076D6574686F6431000101010A0000000001E0102A0101"; + var value1 = new CandidService(Principal.FromText("bpo6s-4qaaa-aaaap-acava-cai")); + var type1 = new CandidServiceType(new Dictionary{ + { + CandidId.Create("method1"), + new CandidFuncType(new List{FuncMode.Query}, new List(), new List()) + }, + }); + var expectedArg = CandidArg.FromCandid(new List + { + CandidTypedValue.FromValueAndType(value1, type1) + }); + + + byte[] actualBytes = ByteUtil.FromHexString(hex); + CandidArg actualArg = CandidArg.FromBytes(actualBytes); + + Assert.Equal(expectedArg, actualArg); + + string actualHex = ByteUtil.ToHexString(expectedArg.Encode()); + + Assert.Equal(hex, actualHex); + } + [Fact] public void EncodeDecode_1()