Add support for multipart form body

This commit is contained in:
samwelkanda 2024-03-01 03:34:30 +03:00
Родитель fbffef56c5
Коммит 45ece1eb2f
9 изменённых файлов: 35 добавлений и 4 удалений

Просмотреть файл

@ -11,6 +11,7 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0
- Added the init command as part of the experience revamp of [#3356](https://github.com/microsoft/kiota/issues/3356)
- Added uri-form encoded serialization for Python. [#2075](https://github.com/microsoft/kiota/issues/2075)
- Added support for multipart form data request body in Python. [#3030](https://github.com/microsoft/kiota/issues/3030)
### Changed

Просмотреть файл

@ -25,7 +25,7 @@ The following table provides an overview of the languages supported by Kiota and
| Go | ✔ | [](https://github.com/microsoft/kiota-abstractions-go) | [FORM](https://github.com/microsoft/kiota-serialization-form-go), [JSON](https://github.com/microsoft/kiota-serialization-json-go), [MULTIPART](https://github.com/microsoft/kiota-serialization-multipart-go), [TEXT](https://github.com/microsoft/kiota-serialization-text-go) | [Anonymous](https://github.com/microsoft/kiota-abstractions-go/blob/main/authentication/anonymous_authentication_provider.go), [API Key](https://github.com/microsoft/kiota-abstractions-go/blob/main/authentication/api_key_authentication_provider.go), [Azure](https://github.com/microsoft/kiota-authentication-azure-go/) | [](https://github.com/microsoft/kiota-http-go/) | [link](https://learn.microsoft.com/openapi/kiota/quickstarts/go) |
| Java | ✔ | [](https://github.com/microsoft/kiota-java/tree/main/components/abstractions) | [FORM](https://github.com/microsoft/kiota-java/tree/main/components/serialization/form), [JSON](https://github.com/microsoft/kiota-java/tree/main/components/serialization/json), [MULTIPART](https://github.com/microsoft/kiota-java/tree/main/components/serialization/multipart), [TEXT](https://github.com/microsoft/kiota-java/tree/main/components/serialization/text) | [Anonymous](https://github.com/microsoft/kiota-java/blob/main/components/abstractions/src/main/java/com/microsoft/kiota/authentication/AnonymousAuthenticationProvider.java), [API Key](https://github.com/microsoft/kiota-java/blob/main/components/abstractions/src/main/java/com/microsoft/kiota/authentication/ApiKeyAuthenticationProvider.java), [Azure](https://github.com/microsoft/kiota-java/tree/main/components/authentication/azure) | [](https://github.com/microsoft/kiota-java/tree/main/components/http/okHttp) | [link](https://learn.microsoft.com/openapi/kiota/quickstarts/java) |
| PHP | ✔ | [](https://github.com/microsoft/kiota-abstractions-php) | [JSON](https://github.com/microsoft/kiota-serialization-json-php), [❌ FORM](https://github.com/microsoft/kiota/issues/2074), [❌ MULTIPART](https://github.com/microsoft/kiota/issues/3029), [TEXT](https://github.com/microsoft/kiota-serialization-text-php) | [Anonymous](https://github.com/microsoft/kiota-abstractions-php/blob/main/src/Authentication/AnonymousAuthenticationProvider.php), [✔️ PHP League](https://github.com/microsoft/kiota-authentication-phpleague-php) | [](https://github.com/microsoft/kiota-http-guzzle-php) | [link](https://learn.microsoft.com/openapi/kiota/quickstarts/php) |
| Python | ✔ | [](https://github.com/microsoft/kiota-abstractions-python) | [FORM](https://github.com/microsoft/kiota-serialization-form-python), [JSON](https://github.com/microsoft/kiota-serialization-json-python), [MULTIPART](https://github.com/microsoft/kiota/issues/3030), [TEXT](https://github.com/microsoft/kiota-serialization-text-python) | [Anonymous](https://github.com/microsoft/kiota-abstractions-python/blob/main/kiota_abstractions/authentication/anonymous_authentication_provider.py), [Azure](https://github.com/microsoft/kiota-authentication-azure-python) | [](https://github.com/microsoft/kiota-http-python) | [link](https://learn.microsoft.com/openapi/kiota/quickstarts/python) |
| Python | ✔ | [](https://github.com/microsoft/kiota-abstractions-python) | [FORM](https://github.com/microsoft/kiota-serialization-form-python), [JSON](https://github.com/microsoft/kiota-serialization-json-python), [MULTIPART](https://github.com/microsoft/kiota-serialization-multipart-python), [TEXT](https://github.com/microsoft/kiota-serialization-text-python) | [Anonymous](https://github.com/microsoft/kiota-abstractions-python/blob/main/kiota_abstractions/authentication/anonymous_authentication_provider.py), [Azure](https://github.com/microsoft/kiota-authentication-azure-python) | [](https://github.com/microsoft/kiota-http-python) | [link](https://learn.microsoft.com/openapi/kiota/quickstarts/python) |
| Ruby | ✔ | [](https://github.com/microsoft/kiota-abstractions-ruby) | [❌ FORM](https://github.com/microsoft/kiota/issues/2077), [JSON](https://github.com/microsoft/kiota-serialization-json-ruby), [❌ MULTIPART](https://github.com/microsoft/kiota/issues/3032), [❌ TEXT](https://github.com/microsoft/kiota/issues/1049) | [Anonymous](https://github.com/microsoft/kiota-abstractions-ruby/blob/main/lib/microsoft_kiota_abstractions/authentication/anonymous_authentication_provider.rb), [✔️ OAuth2](https://github.com/microsoft/kiota-authentication-oauth-ruby) | [](https://github.com/microsoft/kiota-http-ruby)| |
| CLI | ✔ | (see CSharp) + [](https://github.com/microsoft/kiota-cli-commons) | (see CSharp) | (see CSharp) | (see CSharp) | [link](https://learn.microsoft.com/openapi/kiota/quickstarts/cli) |
| Swift | [](https://github.com/microsoft/kiota/issues/1449) | [](./abstractions/swift) | [❌ FORM](https://github.com/microsoft/kiota/issues/2076), [❌ JSON](https://github.com/microsoft/kiota/issues/1451), [❌ FORM](https://github.com/microsoft/kiota/issues/3033), [❌ TEXT](https://github.com/microsoft/kiota/issues/1452) | [Anonymous](./abstractions/swift/Source/MicrosoftKiotaAbstractions/Authentication/AnonymousAuthenticationProvider.swift), [❌ Azure](https://github.com/microsoft/kiota/issues/1453) | [](https://github.com/microsoft/kiota/issues/1454)| |

Просмотреть файл

@ -13,6 +13,7 @@ dependencies = [
"microsoft-kiota-serialization-json >= 1.0.0",
"microsoft-kiota-serialization-text >= 1.0.0",
"microsoft-kiota-serialization-form >= 0.1.0",
"microsoft-kiota-serialization-multipart >= 0.1.0",
]
license = {file = "LICENSE"}
readme = "README.md"

Просмотреть файл

@ -104,12 +104,14 @@ microsoft-kiota-authentication-azure==1.0.0
microsoft-kiota-http==1.3.0
microsoft-kiota-serialization-json==1.0.1
microsoft-kiota-serialization-json==1.1.0
microsoft-kiota-serialization-text==1.0.0
microsoft-kiota-serialization-form==0.1.0
microsoft-kiota-serialization-multipart==0.1.0
msal==1.27.0
msal-extensions==1.1.0

Просмотреть файл

@ -113,6 +113,7 @@ public class PythonRefiner : CommonLanguageRefiner, ILanguageRefiner
"kiota_serialization_json.json_serialization_writer_factory.JsonSerializationWriterFactory",
"kiota_serialization_text.text_serialization_writer_factory.TextSerializationWriterFactory",
"kiota_serialization_form.form_serialization_writer_factory.FormSerializationWriterFactory",
"kiota_serialization_multipart.multipart_serialization_writer_factory.MultipartSerializationWriterFactory",
}
);
ReplaceDefaultDeserializationModules(
@ -150,6 +151,7 @@ public class PythonRefiner : CommonLanguageRefiner, ILanguageRefiner
}, cancellationToken);
}
private const string MultipartBodyClassName = "MultipartBody";
private const string AbstractionsPackageName = "kiota_abstractions";
private const string SerializationModuleName = $"{AbstractionsPackageName}.serialization";
private const string StoreModuleName = $"{AbstractionsPackageName}.store";
@ -160,6 +162,8 @@ public class PythonRefiner : CommonLanguageRefiner, ILanguageRefiner
$"{AbstractionsPackageName}.request_adapter", "RequestAdapter"),
new (static x => x is CodeMethod method && method.IsOfKind(CodeMethodKind.RequestGenerator),
$"{AbstractionsPackageName}.method", "Method"),
new (static x => x is CodeMethod method && method.IsOfKind(CodeMethodKind.RequestExecutor, CodeMethodKind.RequestGenerator) && method.Parameters.Any(static y => y.IsOfKind(CodeParameterKind.RequestBody) && y.Type.Name.Equals(MultipartBodyClassName, StringComparison.OrdinalIgnoreCase)),
$"{AbstractionsPackageName}.multipart_body", MultipartBodyClassName),
new (static x => x is CodeMethod method && method.IsOfKind(CodeMethodKind.RequestGenerator),
$"{AbstractionsPackageName}.request_information", "RequestInformation"),
new (static x => x is CodeMethod method && method.IsOfKind(CodeMethodKind.RequestGenerator),

Просмотреть файл

@ -44,6 +44,7 @@ public class PythonReservedNamesProvider : IReservedNamesProvider
"yield",
"property",
"BaseRequestBuilder",
"MultipartBody",
});
public HashSet<string> ReservedNames => _reservedNames.Value;
}

Просмотреть файл

@ -833,7 +833,7 @@ public class CodeMethodWriter : BaseElementWriter<CodeMethod, PythonConventionSe
}
else
{
var setMethodName = requestParams.requestBody.Type is CodeType bodyType && bodyType.TypeDefinition is CodeClass ? "set_content_from_parsable" : "set_content_from_scalar";
var setMethodName = requestParams.requestBody.Type is CodeType bodyType && (bodyType.TypeDefinition is CodeClass || bodyType.Name.Equals("MultipartBody", StringComparison.OrdinalIgnoreCase)) ? "set_content_from_parsable" : "set_content_from_scalar";
writer.WriteLine($"{RequestInfoVarName}.{setMethodName}(self.{requestAdapterProperty.Name}, \"{sanitizedRequestBodyContentType}\", {requestParams.requestBody.Name})");
}
}

Просмотреть файл

@ -214,6 +214,10 @@
{
"Name": "microsoft-kiota-serialization-form",
"Version": "0.1.0"
},
{
"Name": "microsoft-kiota-serialization-multipart",
"Version": "0.1.0"
}
],
"DependencyInstallCommand": "pip install {0}=={1}"
@ -280,4 +284,4 @@
"DependencyInstallCommand": "dotnet add package {0} --version {1}"
}
}
}
}

Просмотреть файл

@ -694,6 +694,24 @@ public sealed class CodeMethodWriterTests : IDisposable
Assert.Contains("return request_info", result);
}
[Fact]
public void WritesRequestGeneratorBodyForMultipart()
{
setup();
method.Kind = CodeMethodKind.RequestGenerator;
method.HttpMethod = HttpMethod.Post;
AddRequestProperties();
AddRequestBodyParameters(false);
method.Parameters.OfKind(CodeParameterKind.RequestBody).Type = new CodeType
{
Name = "MultipartBody",
IsExternal = true,
};
method.RequestBodyContentType = "multipart/form-data";
writer.Write(method);
var result = tw.ToString();
Assert.Contains("set_content_from_parsable", result);
}
[Fact]
public void WritesRequestGeneratorBodyWhenUrlTemplateIsOverrode()
{
setup();