Skip to content

Commit

Permalink
Merge pull request #2225 from microsoft/feat/raw-url-support
Browse files Browse the repository at this point in the history
PHP Raw URL support for Request Builders.
  • Loading branch information
SilasKenneth authored Feb 2, 2023
2 parents 35cb0b5 + eb636d7 commit cd48833
Show file tree
Hide file tree
Showing 7 changed files with 63 additions and 34 deletions.
3 changes: 2 additions & 1 deletion CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,8 @@ and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0

### Added

- Added support for external documentation links on request execution methods (PHP Generation). [2038](https://github.com/microsoft/kiota/issues/2138)
- Added support for Raw Url in Request Builders for PHP Generation. [2205](https://github.com/microsoft/kiota/issues/2205)
- Added support for external documentation links on request execution methods (PHP Generation). [2138](https://github.com/microsoft/kiota/issues/2138)
- Added support for nullable reference types in dotnet for projects running Netstandard 2.1/Net 6.0 and above [2073](https://github.com/microsoft/kiota/issues/2073)
- Added support for multi-value headers to CLI generation. (Shell)
- Added support for multi-value headers for PHP Generation. [#2052](https://github.com/microsoft/kiota/issues/2052)
Expand Down
9 changes: 6 additions & 3 deletions src/Kiota.Builder/Refiners/PhpRefiner.cs
Original file line number Diff line number Diff line change
Expand Up @@ -226,12 +226,15 @@ private static void CorrectParameterType(CodeElement codeElement)
{
if (codeElement is CodeMethod currentMethod)
{
currentMethod.Parameters.Where(x => x.IsOfKind(CodeParameterKind.ParseNode)).ToList().ForEach(static x =>
currentMethod.Parameters.Where(static x => x.IsOfKind(CodeParameterKind.ParseNode, CodeParameterKind.PathParameters)).ToList().ForEach(static x =>
{
x.Type.Name = "ParseNode";
if (x.IsOfKind(CodeParameterKind.ParseNode))
x.Type.Name = "ParseNode";
else
x.Documentation.Description += " or a String representing the raw URL.";
});
currentMethod.Parameters.Where(x => x.IsOfKind(CodeParameterKind.BackingStore)
&& currentMethod.IsOfKind(CodeMethodKind.ClientConstructor)).ToList().ForEach(static x =>
&& currentMethod.IsOfKind(CodeMethodKind.ClientConstructor)).ToList().ForEach(static x =>
{
x.Type.Name = "BackingStoreFactory";
x.DefaultValue = "null";
Expand Down
4 changes: 2 additions & 2 deletions src/Kiota.Builder/Writers/Php/CodeEnumWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -27,9 +27,9 @@ public override void WriteCodeElement(CodeEnum codeElement, LanguageWriter write
!x.Declaration.Name.Equals(codeElement.Name, StringComparison.OrdinalIgnoreCase)))
.Select(x => x.Declaration is { IsExternal: true }
? $"use {x.Declaration.Name.ReplaceDotsWithSlashInNamespaces()}\\{x.Name.ReplaceDotsWithSlashInNamespaces()};"
: $"use {x.Name.ReplaceDotsWithSlashInNamespaces()}\\{x.Declaration.Name.ReplaceDotsWithSlashInNamespaces()};")
: $"use {x.Name.ReplaceDotsWithSlashInNamespaces()}\\{x.Declaration!.Name.ReplaceDotsWithSlashInNamespaces()};")
.Distinct()
.OrderBy(x => x)
.Order()
.ToList()
.ForEach(x =>
{
Expand Down
66 changes: 44 additions & 22 deletions src/Kiota.Builder/Writers/Php/CodeMethodWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -71,7 +71,9 @@ public override void WriteCodeElement(CodeMethod codeElement, LanguageWriter wri
writer.WriteLine();
}

private static void WriteConstructorBody(CodeClass parentClass, CodeMethod currentMethod, LanguageWriter writer, bool inherits)
private const string UrlTemplateTempVarName = "$urlTplParams";
private const string RawUrlParameterKey = "request-raw-url";
private void WriteConstructorBody(CodeClass parentClass, CodeMethod currentMethod, LanguageWriter writer, bool inherits)
{
if (inherits)
writer.WriteLine("parent::__construct();");
Expand Down Expand Up @@ -101,24 +103,44 @@ private static void WriteConstructorBody(CodeClass parentClass, CodeMethod curre
if (currentMethod.IsOfKind(CodeMethodKind.Constructor, CodeMethodKind.ClientConstructor))
{
AssignPropertyFromParameter(parentClass, currentMethod, CodeParameterKind.RequestAdapter, CodePropertyKind.RequestAdapter, writer);
AssignPropertyFromParameter(parentClass, currentMethod, CodeParameterKind.PathParameters, CodePropertyKind.PathParameters, writer);
AssignPropertyFromParameter(parentClass, currentMethod, CodeParameterKind.RawUrl, CodePropertyKind.UrlTemplate, writer);
}
var urlTemplateTempVarName = "$urlTplParams";
if (currentMethod.IsOfKind(CodeMethodKind.Constructor, CodeMethodKind.ClientConstructor) &&
parentClass.IsOfKind(CodeClassKind.RequestBuilder) &&
currentMethod.Parameters.Any(x => x.IsOfKind(CodeParameterKind.Path)))
{
if (currentMethod.Parameters.OfKind(CodeParameterKind.PathParameters) is CodeParameter pathParametersParameter)
writer.WriteLine($"{urlTemplateTempVarName} = ${pathParametersParameter.Name};");
currentMethod.Parameters.Where(parameter => parameter.IsOfKind(CodeParameterKind.Path)).ToList()
.ForEach(parameter =>
{
writer.WriteLine($"{urlTemplateTempVarName}['{parameter.Name}'] = ${parameter.Name.ToFirstCharacterLowerCase()};");
});
if (parentClass.GetPropertyOfKind(CodePropertyKind.PathParameters) is CodeProperty pathParametersProperty)
writer.WriteLine($"{GetPropertyCall(pathParametersProperty, "[]")} = array_merge({GetPropertyCall(pathParametersProperty, "[]")}, {urlTemplateTempVarName});");
}
if (parentClass.IsOfKind(CodeClassKind.RequestBuilder) &&
currentMethod.IsOfKind(CodeMethodKind.Constructor, CodeMethodKind.ClientConstructor) &&
currentMethod.Parameters.OfKind(CodeParameterKind.PathParameters) is CodeParameter pathParametersParameter &&
parentClass.GetPropertyOfKind(CodePropertyKind.PathParameters) is CodeProperty pathParametersProperty
)
{
var pathParametersParameterName = conventions.GetParameterName(pathParametersParameter);
writer.StartBlock($"if (is_array({pathParametersParameterName})) {{");
WritePathParametersOptions(currentMethod, parentClass, pathParametersParameter, writer);
writer.CloseBlock("} else {");
writer.IncreaseIndent();
writer.WriteLine($"{GetPropertyCall(pathParametersProperty, "[]")} = ['{RawUrlParameterKey}' => {conventions.GetParameterName(pathParametersParameter)}];");
writer.CloseBlock();
}
}
private void WritePathParametersOptions(CodeMethod currentMethod, CodeClass parentClass, CodeParameter pathParameter, LanguageWriter writer)
{
var pathParametersProperty = parentClass.GetPropertyOfKind(CodePropertyKind.PathParameters);

if (pathParametersProperty != null && !currentMethod.Parameters.Any(static x => x.IsOfKind(CodeParameterKind.Path)))
{
writer.WriteLine($"{GetPropertyCall(pathParametersProperty, "[]")} = {conventions.GetParameterName(pathParameter)};");
return;
}

writer.WriteLine($"{UrlTemplateTempVarName} = {conventions.GetParameterName(pathParameter)};");
currentMethod.Parameters.Where(static parameter => parameter.IsOfKind(CodeParameterKind.Path)).ToList()
.ForEach(parameter =>
{
var key = String.IsNullOrEmpty(parameter.SerializationName)
? parameter.Name
: parameter.SerializationName;
writer.WriteLine($"{UrlTemplateTempVarName}['{key}'] = ${parameter.Name.ToFirstCharacterLowerCase()};");
});
if (pathParametersProperty != null)
writer.WriteLine(
$"{GetPropertyCall(pathParametersProperty, "[]")} = {UrlTemplateTempVarName};");
}
private static void AssignPropertyFromParameter(CodeClass parentClass, CodeMethod currentMethod, CodeParameterKind parameterKind, CodePropertyKind propertyKind, LanguageWriter writer)
{
Expand Down Expand Up @@ -146,8 +168,7 @@ private void WriteMethodPhpDocs(CodeMethod codeMethod, LanguageWriter writer, IR
var isSetterForAdditionalData = codeMethod.IsOfKind(CodeMethodKind.Setter) &&
(accessedProperty?.IsOfKind(CodePropertyKind.AdditionalData) ?? false);

var parametersWithDescription = codeMethod.Parameters
.Where(static x => x.Documentation.DescriptionAvailable)
var parametersWithOrWithoutDescription = codeMethod.Parameters
.Select(x => GetParameterDocString(codeMethod, x, isSetterForAdditionalData))
.ToList();
var returnDocString = GetDocCommentReturnType(codeMethod, accessedProperty);
Expand All @@ -158,7 +179,7 @@ private void WriteMethodPhpDocs(CodeMethod codeMethod, LanguageWriter writer, IR
else returnDocString = String.Empty;
conventions.WriteLongDescription(codeMethod.Documentation,
writer,
parametersWithDescription.Union(new[] { returnDocString })
parametersWithOrWithoutDescription.Union(new[] { returnDocString })
);

}
Expand Down Expand Up @@ -567,11 +588,12 @@ private static void WriteDeserializerBodyForUnionModel(CodeMethod method, CodeCl

private void WriteIndexerBody(CodeMethod codeElement, CodeClass parentClass, string returnType, LanguageWriter writer)
{
var pathParameters = codeElement.Parameters.Where(static x => x.IsOfKind(CodeParameterKind.Path, CodeParameterKind.Custom));
if (parentClass.GetPropertyOfKind(CodePropertyKind.PathParameters) is CodeProperty pathParametersProperty &&
codeElement.OriginalIndexer != null)
conventions.AddParametersAssignment(writer, pathParametersProperty.Type, $"$this->{pathParametersProperty.Name}",
(codeElement.OriginalIndexer.IndexType, codeElement.OriginalIndexer.SerializationName, "$id"));
conventions.AddRequestBuilderBody(parentClass, returnType, writer, conventions.TempDictionaryVarName);
conventions.AddRequestBuilderBody(parentClass, returnType, writer, conventions.TempDictionaryVarName, pathParameters);
}

private void WriteRequestExecutorBody(CodeMethod codeElement, CodeClass parentClass, RequestParams requestParams, LanguageWriter writer)
Expand Down
2 changes: 1 addition & 1 deletion src/Kiota.Builder/Writers/Php/CodePropertyWriter.cs
Original file line number Diff line number Diff line change
Expand Up @@ -28,7 +28,7 @@ public override void WriteCodeElement(CodeProperty codeElement, LanguageWriter w
private void WritePropertyDocComment(CodeProperty codeProperty, LanguageWriter writer)
{
var propertyDescription = codeProperty.Documentation.Description;
var hasDescription = !string.IsNullOrEmpty(propertyDescription);
var hasDescription = codeProperty.Documentation.DescriptionAvailable;

var collectionKind = codeProperty.Type.IsArray || codeProperty.Type.IsCollection;
var typeString = (collectionKind
Expand Down
7 changes: 4 additions & 3 deletions src/Kiota.Builder/Writers/Php/PhpConventionService.cs
Original file line number Diff line number Diff line change
Expand Up @@ -76,7 +76,7 @@ public string GetParameterName(CodeParameter parameter)
{
CodeParameterKind.RequestConfiguration => "$requestConfiguration",
CodeParameterKind.BackingStore => "$backingStore",
CodeParameterKind.PathParameters => "$pathParameters",
CodeParameterKind.PathParameters => "$pathParametersOrRawUrl",
CodeParameterKind.RequestAdapter => RequestAdapterPropertyName,
CodeParameterKind.RequestBody => "$body",
CodeParameterKind.RawUrl => "$rawUrl",
Expand All @@ -93,6 +93,7 @@ public override string GetParameterSignature(CodeParameter parameter, CodeElemen
{
CodeParameterKind.RequestAdapter => $"RequestAdapter {GetParameterName(parameter)}",
CodeParameterKind.ResponseHandler => $"ResponseHandler {GetParameterName(parameter)}",
CodeParameterKind.PathParameters => GetParameterName(parameter),
CodeParameterKind.RequestConfiguration => $"{parameter.Type.Name.ToFirstCharacterUpperCase()} {GetParameterName(parameter)}",
CodeParameterKind.Serializer => $"SerializationWriter {GetParameterName(parameter)}",
CodeParameterKind.BackingStore => $"{parameter.Type.Name.ToFirstCharacterUpperCase()} {GetParameterName(parameter)}",
Expand All @@ -108,7 +109,7 @@ public string GetParameterDocNullable(CodeParameter parameter, CodeElement codeE
var parameterSignature = GetParameterSignature(parameter, codeElement).Trim().Split(' ');
if (parameter.IsOfKind(CodeParameterKind.PathParameters))
{
return $"array<string, mixed>{(parameter.Optional ? "|null" : string.Empty)} {parameterSignature[1]}";
return $"array<string, mixed>|string{(parameter.Optional ? "|null" : string.Empty)} {parameterSignature[0]}";
}

var isCollection = parameter.Type.IsCollection;
Expand Down Expand Up @@ -224,7 +225,7 @@ public void WriteNamespaceAndImports(ClassDeclaration codeElement, LanguageWrite
internal void AddRequestBuilderBody(CodeClass parentClass, string returnType, LanguageWriter writer, string? urlTemplateVarName = default, IEnumerable<CodeParameter>? pathParameters = default)
{
var codeParameters = pathParameters as CodeParameter[] ?? pathParameters?.ToArray();
var codePathParametersSuffix = !(codeParameters?.Any() ?? false) ? string.Empty : $", {string.Join(", ", codeParameters.Select(x => $"{x.Name.ToFirstCharacterLowerCase()}"))}";
var codePathParametersSuffix = !(codeParameters?.Any() ?? false) ? string.Empty : $", {string.Join(", ", codeParameters.Select(x => $"${x.Name.ToFirstCharacterLowerCase()}"))}";
var urlTemplateParams = string.IsNullOrEmpty(urlTemplateVarName) && parentClass.GetPropertyOfKind(CodePropertyKind.PathParameters) is CodeProperty pathParametersProperty ?
$"$this->{pathParametersProperty.Name}" :
urlTemplateVarName;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -661,7 +661,7 @@ public async Task WriteIndexerBody()

Assert.Contains("$urlTplParams['message_id'] = $id;", result);
Assert.Contains("public function messageById(string $id): MessageRequestBuilder {", result);
Assert.Contains("return new MessageRequestBuilder($urlTplParams, $this->requestAdapter);", result);
Assert.Contains("return new MessageRequestBuilder($urlTplParams, $this->requestAdapter, $id);", result);

}

Expand Down Expand Up @@ -1160,7 +1160,9 @@ public void WriteRequestBuilderConstructor()
var result = stringWriter.ToString();
Assert.Contains("__construct", result);
Assert.Contains($"$this->{propName} = {defaultValue};", result);
Assert.Contains("$this->pathParameters = array_merge($this->pathParameters, $urlTplParams);", result);
Assert.Contains("if (is_array($pathParametersOrRawUrl)) {", result);
Assert.Contains("$this->pathParameters = ['request-raw-url' => $pathParametersOrRawUrl];", result);
Assert.Contains("$this->pathParameters = $urlTplParams;", result);
}

[Fact]
Expand Down

0 comments on commit cd48833

Please sign in to comment.