From 0aa2c91f5a71dc4d52e5734b8fb762f9db4d31c6 Mon Sep 17 00:00:00 2001 From: Nikolay M Date: Thu, 9 May 2024 15:29:27 +0400 Subject: [PATCH] Add custom fields support (#78) --- src/Funogram.Generator/CustomFields.json | 38 +++++++++++++++++++ .../Funogram.Generator.fsproj | 1 + src/Funogram.Generator/Program.fs | 1 + src/Funogram.Generator/Types/TypesParser.fs | 36 +++++++++++++++++- src/Funogram.Telegram/Directory.Build.props | 2 +- src/Funogram.Telegram/Types.fs | 18 +++++++-- 6 files changed, 91 insertions(+), 5 deletions(-) create mode 100644 src/Funogram.Generator/CustomFields.json diff --git a/src/Funogram.Generator/CustomFields.json b/src/Funogram.Generator/CustomFields.json new file mode 100644 index 0000000..cd97099 --- /dev/null +++ b/src/Funogram.Generator/CustomFields.json @@ -0,0 +1,38 @@ +[ + { + "Name": "VideoChatStarted", + "Kind": { + "Case": "Fields", + "Fields": [ + [ + { + "OriginalName": "id", + "ConvertedName": "Id", + "Description": "Unique identifier of video chat (not present in Bot API at the moment, for internal use)", + "OriginalFieldType": "Integer", + "ConvertedFieldType": "int64", + "Optional": true + } + ] + ] + } + }, + { + "Name": "VideoChatEnded", + "Kind": { + "Case": "Fields", + "Fields": [ + [ + { + "OriginalName": "id", + "ConvertedName": "Id", + "Description": "Unique identifier of video chat (not present in Bot API at the moment, for internal use)", + "OriginalFieldType": "Integer", + "ConvertedFieldType": "int64", + "Optional": true + } + ] + ] + } + } +] \ No newline at end of file diff --git a/src/Funogram.Generator/Funogram.Generator.fsproj b/src/Funogram.Generator/Funogram.Generator.fsproj index 69dfc57..d1db48c 100644 --- a/src/Funogram.Generator/Funogram.Generator.fsproj +++ b/src/Funogram.Generator/Funogram.Generator.fsproj @@ -19,6 +19,7 @@ + diff --git a/src/Funogram.Generator/Program.fs b/src/Funogram.Generator/Program.fs index 9649c00..af6fa92 100644 --- a/src/Funogram.Generator/Program.fs +++ b/src/Funogram.Generator/Program.fs @@ -38,6 +38,7 @@ let processAsync (args: CliArguments list) = |> TypesParser.withResultPath (Path.Combine(Constants.OutputDir, "types.json")) |> TypesParser.loadRemapData "./RemapTypes.json" |> TypesParser.parse + |> TypesParser.mergeCustomFields "./CustomFields.json" |> TypesGenerator.mkGenerator (Path.Combine(Constants.CodeOutputDir, Constants.TypesFileName)) |> TypesGenerator.generate diff --git a/src/Funogram.Generator/Types/TypesParser.fs b/src/Funogram.Generator/Types/TypesParser.fs index a85ac2f..20d9adf 100644 --- a/src/Funogram.Generator/Types/TypesParser.fs +++ b/src/Funogram.Generator/Types/TypesParser.fs @@ -240,4 +240,38 @@ let parse (config: ParseConfig) = | None -> () - types \ No newline at end of file + types + +let mergeCustomFields (customFieldsPath: string) (types: ApiType[]) = + if File.Exists customFieldsPath then + let serializerOptions = Helpers.getJsonSerializerOptions () + + use file = File.OpenRead customFieldsPath + let result = + JsonSerializer.Deserialize(file, serializerOptions) + |> Seq.map (fun x -> x.Name, x) |> Map.ofSeq + + let types = [| + for tp in types do + match result |> Map.tryFind tp.Name with + | Some typeWithCustomFields -> + match tp.Kind, typeWithCustomFields.Kind with + | ApiTypeKind.Fields fields, ApiTypeKind.Fields extraFields -> + let mergedFields = Array.append fields extraFields + let mergedFieldsDistinct = mergedFields |> Array.distinctBy (_.ConvertedName) + + if mergedFields.Length <> mergedFieldsDistinct.Length then + failwith $"Custom fields must be unique (type {tp.Name}).\nTelegram API fields:\n%A{fields}\nCustom fields:\n%A{extraFields}" + + yield { tp with Kind = ApiTypeKind.Fields mergedFields } + | ApiTypeKind.Stub, kind -> + yield { tp with Kind = kind } + | _ -> + yield tp + | None -> yield tp + |] + + types + else + printfn "WARN: Custom fields file not found at path %s" customFieldsPath + types \ No newline at end of file diff --git a/src/Funogram.Telegram/Directory.Build.props b/src/Funogram.Telegram/Directory.Build.props index 4e03b45..f1fc90c 100644 --- a/src/Funogram.Telegram/Directory.Build.props +++ b/src/Funogram.Telegram/Directory.Build.props @@ -1,6 +1,6 @@ - 7.3.0.0 + 7.3.0.1 Nikolay Matyushin Funogram.Telegram Funogram.Telegram diff --git a/src/Funogram.Telegram/Types.fs b/src/Funogram.Telegram/Types.fs index 4bfd82d..d5f08b0 100644 --- a/src/Funogram.Telegram/Types.fs +++ b/src/Funogram.Telegram/Types.fs @@ -2058,8 +2058,16 @@ and [] VideoChatScheduled = } /// This object represents a service message about a video chat started in the chat. Currently holds no information. -and VideoChatStarted = - new() = {} +and [] VideoChatStarted = + { + /// Unique identifier of video chat (not present in Bot API at the moment, for internal use) + [] + Id: int64 option + } + static member Create(?id: int64) = + { + Id = id + } /// This object represents a service message about a video chat ended in the chat. and [] VideoChatEnded = @@ -2067,10 +2075,14 @@ and [] VideoChatEnded = /// Video chat duration in seconds [] Duration: int64 + /// Unique identifier of video chat (not present in Bot API at the moment, for internal use) + [] + Id: int64 option } - static member Create(duration: int64) = + static member Create(duration: int64, ?id: int64) = { Duration = duration + Id = id } /// This object represents a service message about new members invited to a video chat.