public EditableJsonElement(JsonElement raw)
        {
            switch (raw.ValueKind)
            {
            case JsonValueKind.Object:
                Object = raw.EnumerateObject()
                         .ToDictionary(kvp => kvp.Name, kvp => new EditableJsonElement(kvp.Value));
                break;

            case JsonValueKind.Array:
                Array = raw.EnumerateArray()
                        .Select(v => new EditableJsonElement(v))
                        .ToList();
                break;

            case JsonValueKind.Undefined:
            case JsonValueKind.String:
            case JsonValueKind.Number:
            case JsonValueKind.True:
            case JsonValueKind.False:
            case JsonValueKind.Null:
                _raw = raw.Clone();
                break;

            default:
                throw new ArgumentOutOfRangeException();
            }
        }
예제 #2
0
        /// <summary>
        /// Safe way to access a property. Returns an element that evaluates to <c>null</c>
        /// when the underlying property doesn't exist.
        /// </summary>
        /// <param name="element">The <see cref="JsonElement"/> to inspect.</param>
        /// <param name="propertyName">The name of the property.</param>
        /// <returns>The property node, or a <c>null</c> node.</returns>
        public static JsonElement GetNullableProperty(this JsonElement element, string propertyName)
        {
            if (element.TryGetProperty(propertyName, out JsonElement property))
            {
                return(property);
            }

            return(NullDoc.Clone().GetProperty("null"));
        }
        private PatchOperation(OperationType op, JsonPointer from, JsonPointer path, JsonElement value, IPatchOperationHandler handler)
        {
            _handler = handler;
            Op       = op;
            From     = from;
            Path     = path;

            Value = value.ValueKind == JsonValueKind.Undefined ? default : value.Clone();
        }
예제 #4
0
            private static ResponseError?Read(JsonElement element)
            {
                if (element.ValueKind == JsonValueKind.Null)
                {
                    return(null);
                }

                string?code = null;

                if (element.TryGetProperty("code", out var property))
                {
                    code = property.GetString();
                }

                string?message = null;

                if (element.TryGetProperty("message", out property))
                {
                    message = property.GetString();
                }

                string?target = null;

                if (element.TryGetProperty("target", out property))
                {
                    target = property.GetString();
                }

                ResponseInnerError?innererror = null;

                if (element.TryGetProperty("innererror", out property))
                {
                    innererror = ResponseInnerError.Converter.Read(property);
                }

                List <ResponseError>?details = null;

                if (element.TryGetProperty("details", out property) &&
                    property.ValueKind == JsonValueKind.Array)
                {
                    foreach (var item in property.EnumerateArray())
                    {
                        var detail = Read(item);
                        if (detail != null)
                        {
                            details ??= new();
                            details.Add(detail);
                        }
                    }
                }

                return(new ResponseError(code, message, target, element.Clone(), innererror, details));
            }
예제 #5
0
        private static void CloneAtInner(string innerJson, JsonValueKind valueType)
        {
            string json = $"{{ \"obj\": [ {{ \"not target\": true, \"target\": {innerJson} }}, 5 ] }}";

            JsonElement clone;

            using (JsonDocument doc = JsonDocument.Parse(json))
            {
                JsonElement target = doc.RootElement.GetProperty("obj")[0].GetProperty("target");
                Assert.Equal(valueType, target.ValueKind);
                clone = target.Clone();
            }

            Assert.Equal(innerJson, clone.GetRawText());
        }
        string ParseAndLookupMappedDeviceName(JsonElement map, string mappedDeviceName)
        {
            string[]    tokens        = mappedDeviceName.Split('.');
            JsonElement deviceElement = map.Clone();

            if (tokens.Length > 1)
            {
                for (int i = 0; i < tokens.Length; i++)
                {
                    deviceElement = deviceElement.GetProperty(tokens[i]);
                }
            }

            return(deviceElement.GetString());
        }
예제 #7
0
        public JsonResult(int index, JsonElement data, SourceInfo sourceInfo) : base(index)
        {
            SourceInfo = sourceInfo;
            if (data.ValueKind != JsonValueKind.Object)
            {
                throw new ArgumentException("must be a JSON Object", nameof(data));
            }

            // break the reference to the underlying file stream,
            // which on close would dispose the memory backing the JsonElement
            this.data = data.Clone();
            // this is not a great solution, but none of the inbuilt mechanism for creating lookups for string keys
            // support a StringComparison argument when checking if a key exists!
            names = data.EnumerateObject().Select(property => property.Name).ToArray();
        }
예제 #8
0
        public static void CloneInnerElementFromClonedElement()
        {
            JsonElement clone;

            using (JsonDocument doc = JsonDocument.Parse("[[[]]]"))
            {
                JsonElement middle = doc.RootElement[0].Clone();
                JsonElement inner  = middle[0];
                clone = inner.Clone();

                Assert.Equal(inner.GetRawText(), clone.GetRawText());
                Assert.NotSame(doc, clone.SniffDocument());
                Assert.Same(middle.SniffDocument(), clone.SniffDocument());
                Assert.Same(inner.SniffDocument(), clone.SniffDocument());
            }

            // After document Dispose
            Assert.Equal("[]", clone.GetRawText());
        }
예제 #9
0
        public static INode AsNode(this JsonElement json, XName?rootName = null, string?baseUri = null)
        {
            if (rootName == null || string.IsNullOrWhiteSpace(rootName.LocalName))
            {
                rootName = XName.Get(json.ValueKind.ToString(), baseUri ?? "");
            }

            return(new ExtensibleElementNode(
                       rootName,
                       json.Clone(),

                       valueSelector: v => v switch
            {
                JsonElement element => element.ValueKind switch
                {
                    JsonValueKind.Array => null,
                    JsonValueKind.Object => null,

                    JsonValueKind.String => element.GetString(),
                    _ => element.GetRawText()
                },
예제 #10
0
            internal static ResponseInnerError?Read(JsonElement element)
            {
                if (element.ValueKind == JsonValueKind.Null)
                {
                    return(null);
                }

                string?code = null;

                if (element.TryGetProperty("code", out var property))
                {
                    code = property.GetString();
                }

                ResponseInnerError?innererror = null;

                if (element.TryGetProperty("innererror", out property))
                {
                    innererror = Read(property);
                }

                return(new ResponseInnerError(code, innererror, element.Clone()));
            }
예제 #11
0
 public LiteralRule(JsonElement value)
 {
     _value = value.Clone();
 }
예제 #12
0
 /// <summary>
 /// Creates a new <see cref="ConstKeyword"/>.
 /// </summary>
 /// <param name="value">The constant value.</param>
 public ConstKeyword(JsonElement value)
 {
     Value = value.Clone();
 }
예제 #13
0
        private async void ReceiveMessageLoop(InternalSessionInfo session, CancellationToken token)
        {
            using ClientWebSocket ws = new ClientWebSocket();
            try
            {
                await ws.ConnectAsync(new Uri($"ws://{session.Options.Host}:{session.Options.Port}/all?sessionKey={session.SessionKey}"), token);

                while (true)
                {
                    using MemoryStream ms = await ws.ReceiveFullyAsync(token);

                    JsonElement root = JsonSerializer.Deserialize <JsonElement>(new ReadOnlySpan <byte>(ms.GetBuffer(), 0, (int)ms.Length));
                    switch (root.GetProperty("type").GetString())
                    {
                    case "BotOnlineEvent":
                    {
                        _ = InvokeAsync(Plugins, BotOnlineEvt, this, root.Deserialize <BotEventArgs>());
                        break;
                    }

                    case "BotOfflineEventActive":
                    {
                        _ = InvokeAsync(Plugins, BotPositiveOfflineEvt, this, root.Deserialize <BotEventArgs>());
                        break;
                    }

                    case "BotOfflineEventForce":
                    {
                        _ = InvokeAsync(Plugins, BotKickedOfflineEvt, this, root.Deserialize <BotEventArgs>());
                        break;
                    }

                    case "BotOfflineEventDropped":
                    {
                        _ = InvokeAsync(Plugins, BotDroppedEvt, this, root.Deserialize <BotEventArgs>());
                        break;
                    }

                    case "BotReloginEvent":
                    {
                        _ = InvokeAsync(Plugins, BotReloginEvt, this, root.Deserialize <BotEventArgs>());
                        break;
                    }

                    case "BotInvitedJoinGroupRequestEvent":
                    {
                        _ = InvokeAsync(Plugins, BotInvitedJoinGroupEvt, this, root.Deserialize <CommonGroupApplyEventArgs>());
                        break;
                    }

                    case "FriendMessage":
                    {
                        _ = InvokeAsync(Plugins, FriendMessageEvt, this, root.Deserialize <FriendMessageEventArgs>());
                        break;
                    }

                    case "GroupMessage":
                    {
                        _ = InvokeAsync(Plugins, GroupMessageEvt, this, root.Deserialize <GroupMessageEventArgs>());
                        break;
                    }

                    case "TempMessage":
                    {
                        _ = InvokeAsync(Plugins, TempMessageEvt, this, root.Deserialize <TempMessageEventArgs>());
                        break;
                    }

                    case "GroupRecallEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMessageRevokedEvt, this, root.Deserialize <GroupMessageRevokedEventArgs>());
                        break;
                    }

                    case "FriendRecallEvent":
                    {
                        _ = InvokeAsync(Plugins, FriendMessageRevokedEvt, this, root.Deserialize <FriendMessageRevokedEventArgs>());
                        break;
                    }

                    case "BotGroupPermissionChangeEvent":
                    {
                        _ = InvokeAsync(Plugins, BotGroupPermissionChangedEvt, this, root.Deserialize <BotGroupPermissionChangedEventArgs>());
                        break;
                    }

                    case "BotMuteEvent":
                    {
                        _ = InvokeAsync(Plugins, BotMutedEvt, this, root.Deserialize <BotMutedEventArgs>());
                        break;
                    }

                    case "BotUnmuteEvent":
                    {
                        _ = InvokeAsync(Plugins, BotUnmutedEvt, this, root.Deserialize <BotUnmutedEventArgs>());
                        break;
                    }

                    case "BotJoinGroupEvent":
                    {
                        _ = InvokeAsync(Plugins, BotJoinedGroupEvt, this, root.Deserialize <GroupEventArgs>());
                        break;
                    }

                    case "BotLeaveEventActive":
                    {
                        _ = InvokeAsync(Plugins, BotPositiveLeaveGroupEvt, this, root.Deserialize <GroupEventArgs>());
                        break;
                    }

                    case "BotLeaveEventKick":
                    {
                        _ = InvokeAsync(Plugins, BotKickedOutEvt, this, root.Deserialize <GroupEventArgs>());
                        break;
                    }

                    case "GroupNameChangeEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupNameChangedEvt, this, root.Deserialize <GroupStringPropertyChangedEventArgs>());
                        break;
                    }

                    case "GroupEntranceAnnouncementChangeEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupEntranceAnnouncementChangedEvt, this, root.Deserialize <GroupStringPropertyChangedEventArgs>());
                        break;
                    }

                    case "GroupMuteAllEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMuteAllChangedEvt, this, root.Deserialize <GroupBoolPropertyChangedEventArgs>());
                        break;
                    }

                    case "GroupAllowAnonymousChatEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupAnonymousChatChangedEvt, this, root.Deserialize <GroupBoolPropertyChangedEventArgs>());
                        break;
                    }

                    case "GroupAllowConfessTalkEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupConfessTalkChangedEvt, this, root.Deserialize <GroupBoolPropertyChangedEventArgs>());
                        break;
                    }

                    case "GroupAllowMemberInviteEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberInviteChangedEvt, this, root.Deserialize <GroupBoolPropertyChangedEventArgs>());
                        break;
                    }

                    case "MemberJoinEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberJoinedEvt, this, root.Deserialize <MemberEventArgs>());
                        break;
                    }

                    case "MemberLeaveEventKick":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberKickedEvt, this, root.Deserialize <MemberOperatingEventArgs>());
                        break;
                    }

                    case "MemberLeaveEventQuit":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberPositiveLeaveEvt, this, root.Deserialize <MemberEventArgs>());
                        break;
                    }

                    case "MemberCardChangeEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberCardChangedEvt, this, root.Deserialize <GroupMemberStringPropertyChangedEventArgs>());
                        break;
                    }

                    case "MemberSpecialTitleChangeEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberSpecialTitleChangedEvt, this, root.Deserialize <GroupMemberStringPropertyChangedEventArgs>());
                        break;
                    }

                    case "MemberPermissionChangeEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberPermissionChangedEvt, this, root.Deserialize <GroupMemberPermissionChangedEventArgs>());
                        break;
                    }

                    case "MemberMuteEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberMutedEvt, this, root.Deserialize <GroupMemberMutedEventArgs>());
                        break;
                    }

                    case "MemberUnmuteEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupMemberUnmutedEvt, this, root.Deserialize <GroupMemberUnmutedEventArgs>());
                        break;
                    }

                    case "NewFriendRequestEvent":
                    {
                        _ = InvokeAsync(Plugins, NewFriendApplyEvt, this, root.Deserialize <NewFriendApplyEventArgs>());
                        break;
                    }

                    case "MemberJoinRequestEvent":
                    {
                        _ = InvokeAsync(Plugins, GroupApplyEvt, this, root.Deserialize <CommonGroupApplyEventArgs>());
                        break;
                    }

                    default:
                    {
                        _ = InvokeAsync(Plugins, UnknownMessageEvt, this, new UnknownMessageEventArgs(root.Clone()));
                        break;
                    }
                    }
                }
            }
            catch (OperationCanceledException)
            {
            }
            catch (Exception e)
            {
                if (Interlocked.CompareExchange(ref SessionInfo, null, session) != null)
                {
                    _ = InternalReleaseAsync(session, default); // 不异步等待, 省的抛错没地捕获
                    _ = InvokeAsync(Plugins, DisconnectedEvt, this, new DisconnectedEventArgs(e));
                }
            }
        }
예제 #14
0
 /// <summary>
 /// Creates a new <see cref="DefaultKeyword"/>.
 /// </summary>
 /// <param name="value">The value to use as the default.</param>
 public DefaultKeyword(JsonElement value)
 {
     Value = value.Clone();
 }
예제 #15
0
 private LuaParser(JsonElement root)
 {
     _root = root.Clone();
     currentJsonElement = _root;
 }
예제 #16
0
 /// <summary>
 /// Decodes the "data" property provided within a structured-mode message,
 /// populating the <see cref="CloudEvent.Data"/> property accordingly.
 /// </summary>
 /// <remarks>
 /// <para>
 /// This implementation converts JSON string tokens to strings when the content type suggests
 /// that's appropriate, but otherwise returns the token directly.
 /// </para>
 /// <para>
 /// Override this method to provide more specialized conversions.
 /// </para>
 /// </remarks>
 /// <param name="dataElement">The "data" property value within the structured-mode message. Will not be null, and will
 /// not have a null token type.</param>
 /// <param name="cloudEvent">The event being decoded. This should not be modified except to
 /// populate the <see cref="CloudEvent.Data"/> property, but may be used to provide extra
 /// information such as the data content type. Will not be null.</param>
 /// <returns>The data to populate in the <see cref="CloudEvent.Data"/> property.</returns>
 protected virtual void DecodeStructuredModeDataProperty(JsonElement dataElement, CloudEvent cloudEvent) =>
 cloudEvent.Data = dataElement.ValueKind == JsonValueKind.String && cloudEvent.DataContentType?.StartsWith("text/") == true
         ? dataElement.GetString()
         : (object)dataElement.Clone();  // Deliberately cast to object to provide the conditional operator expression type.
예제 #17
0
 public StjAttributesTable(JsonElement rootElement)
 {
     RootElement = rootElement.Clone();
 }
예제 #18
0
 /// <summary>
 /// Decodes the "data" property provided within a structured-mode message,
 /// populating the <see cref="CloudEvent.Data"/> property accordingly.
 /// </summary>
 /// <remarks>
 /// <para>
 /// This implementation will populate the Data property with the verbatim <see cref="JsonElement"/> if
 /// the content type is deemed to be JSON according to <see cref="IsJsonMediaType(string)"/>. Otherwise,
 /// it validates that the token is a string, and the Data property is populated with that string.
 /// </para>
 /// <para>
 /// Override this method to provide more specialized conversions.
 /// </para>
 /// </remarks>
 /// <param name="dataElement">The "data" property value within the structured-mode message. Will not be null, and will
 /// not have a null token type.</param>
 /// <param name="cloudEvent">The event being decoded. This should not be modified except to
 /// populate the <see cref="CloudEvent.Data"/> property, but may be used to provide extra
 /// information such as the data content type. Will not be null, and the <see cref="CloudEvent.DataContentType"/>
 /// property will be non-null.</param>
 /// <returns>The data to populate in the <see cref="CloudEvent.Data"/> property.</returns>
 protected virtual void DecodeStructuredModeDataProperty(JsonElement dataElement, CloudEvent cloudEvent)
 {
     if (IsJsonMediaType(cloudEvent.DataContentType !))
     {
         cloudEvent.Data = dataElement.Clone();
     }