Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Plus.AutoApi/IAutoApi.cs → Plus.AutoApi.Core/IAutoApi.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,4 @@
namespace Plus.AutoApi
namespace Plus.AutoApi.Core
{
public interface IAutoApi
{
Expand Down
7 changes: 7 additions & 0 deletions Plus.AutoApi.Core/Plus.AutoApi.Core.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
</PropertyGroup>

</Project>
2 changes: 2 additions & 0 deletions Plus.AutoApi/Attributes/AutoApiAttribute.cs
Original file line number Diff line number Diff line change
Expand Up @@ -9,5 +9,7 @@ public class AutoApiAttribute : Attribute
public string AreaName { get; set; }

public bool Disabled { get; set; } = false;

public bool Inherited { get; set; } = true;
}
}
1 change: 1 addition & 0 deletions Plus.AutoApi/AutoApiControllerFeatureProvider.cs
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@
using Plus.AutoApi.Attributes;
using Plus.AutoApi.Helpers;
using System.Reflection;
using Plus.AutoApi.Core;

namespace Plus.AutoApi
{
Expand Down
102 changes: 60 additions & 42 deletions Plus.AutoApi/AutoApiConvention.cs
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
using Microsoft.AspNetCore.Mvc;
using System;
using System.Linq;
using System.Reflection;
using Microsoft.AspNetCore.Mvc;
using Microsoft.AspNetCore.Mvc.ActionConstraints;
using Microsoft.AspNetCore.Mvc.ApplicationModels;
using Microsoft.AspNetCore.Mvc.ModelBinding;
using Plus.AutoApi.Attributes;
using Plus.AutoApi.Extensions;
using Plus.AutoApi.Helpers;
using System;
using System.Linq;
using System.Reflection;

namespace Plus.AutoApi
{
Expand All @@ -22,7 +22,7 @@ public void Apply(ApplicationModel application)

if (typeof(IAutoApi).GetTypeInfo().IsAssignableFrom(type))
{
controller.ControllerName = controller.ControllerName.RemoveSuffix(PlusConsts.ControllerSuffixes.ToArray());
controller.ControllerName = GetRestFulControllerName(controller.ControllerName);

ConfigureArea(controller, attribute);

Expand All @@ -43,7 +43,9 @@ public void Apply(ApplicationModel application)
private void ConfigureArea(ControllerModel controller, AutoApiAttribute attribute)
{
if (attribute == null)
{
throw new ArgumentException(nameof(attribute));
}

if (!controller.RouteValues.ContainsKey("area"))
{
Expand All @@ -60,35 +62,38 @@ private void ConfigureArea(ControllerModel controller, AutoApiAttribute attribut

private void ConfigureAutoApi(ControllerModel controller, AutoApiAttribute attribute)
{
ConfigureApiExplorer(controller);
ConfigureApiExplorer(controller, attribute);
ConfigureSelector(controller, attribute);
ConfigureParameters(controller);
}

private void ConfigureApiExplorer(ControllerModel controller)
private void ConfigureApiExplorer(ControllerModel controller, AutoApiAttribute attribute)
{
if (string.IsNullOrEmpty(controller.ApiExplorer.GroupName))
{
controller.ApiExplorer.GroupName = controller.ControllerName;
}

if (controller.ApiExplorer.IsVisible == null)
{
controller.ApiExplorer.IsVisible = true;
}
controller.ApiExplorer.IsVisible ??= true;

foreach (var action in controller.Actions)
{
ConfigureApiExplorer(action);
ConfigureApiExplorer(action, attribute);
}
}

private void ConfigureApiExplorer(ActionModel action)
private void ConfigureApiExplorer(ActionModel action, AutoApiAttribute attribute)
{
if (action.ApiExplorer.IsVisible == null)
if (!attribute.Inherited)
{
action.ApiExplorer.IsVisible = true;
if (action.ActionMethod.DeclaringType != action.Controller.ControllerType)
{
action.ApiExplorer.IsVisible = false;
return;
}
}

action.ApiExplorer.IsVisible ??= true;
}

private void ConfigureSelector(ControllerModel controller, AutoApiAttribute attribute)
Expand Down Expand Up @@ -165,15 +170,18 @@ private void NormalizeSelectorRoutes(string areaName, string controllerName, Act

foreach (var selector in action.Selectors)
{
selector.AttributeRouteModel = selector.AttributeRouteModel == null ?
CreateActionRouteModel(areaName, controllerName, action) :
AttributeRouteModel.CombineAttributeRouteModel(CreateActionRouteModel(areaName, controllerName, action), selector.AttributeRouteModel);
selector.AttributeRouteModel = selector.AttributeRouteModel == null
? CreateActionRouteModel(areaName, controllerName, action)
: AttributeRouteModel.CombineAttributeRouteModel(
CreateActionRouteModel(areaName, controllerName, action), selector.AttributeRouteModel);
}
}

private static string GetHttpVerb(ActionModel action)
{
var getValueSuccess = PlusConsts.AssemblyAutoApiOptions.TryGetValue(action.Controller.ControllerType.Assembly, out AssemblyAutoApiOptions assemblyAutoApiOptions);
var getValueSuccess =
PlusConsts.AssemblyAutoApiOptions.TryGetValue(action.Controller.ControllerType.Assembly,
out var assemblyAutoApiOptions);

if (getValueSuccess && !string.IsNullOrWhiteSpace(assemblyAutoApiOptions?.HttpVerb))
{
Expand All @@ -182,35 +190,44 @@ private static string GetHttpVerb(ActionModel action)

var verbKey = action.ActionName.GetPascalOrCamelCaseFirstWord().ToLower();

return PlusConsts.HttpVerbs.ContainsKey(verbKey) ? PlusConsts.HttpVerbs[verbKey] : PlusConsts.DefaultHttpVerb;
return PlusConsts.HttpVerbs.ContainsKey(verbKey)
? PlusConsts.HttpVerbs[verbKey]
: PlusConsts.DefaultHttpVerb;
}

private string GetRestFulControllerName(string controllerName)
{
controllerName = controllerName.RemoveSuffix(PlusConsts.ControllerSuffixes.ToArray());
var name = PlusConsts.GetRestFulControllerName?.Invoke(controllerName);
if (!string.IsNullOrWhiteSpace(name))
{
return name;
}

return controllerName;
}

private string GetRestFulActionName(string actionName)
{
actionName = actionName.RemoveSuffix(PlusConsts.ActionSuffixes.ToArray());
var name = PlusConsts.GetRestFulActionName?.Invoke(actionName);
if (name != null)
{
return name;
}

actionName = actionName.RemoveSuffix(PlusConsts.ActionSuffixes.ToArray());

var verbKey = actionName.GetPascalOrCamelCaseFirstWord().ToLower();
if (PlusConsts.HttpVerbs.ContainsKey(verbKey))
{
if (actionName.Length == verbKey.Length)
{
return "";
}
else
{
return actionName.Substring(verbKey.Length);
}
}
else
{
return actionName;

return actionName.Substring(verbKey.Length);
}

return actionName;
}

private AttributeRouteModel CreateActionRouteModel(string areaName, string controllerName, ActionModel action)
Expand All @@ -223,7 +240,9 @@ private AttributeRouteModel CreateActionRouteModel(string areaName, string contr

private static string GetApiPreFix(ActionModel action)
{
var getValueSuccess = PlusConsts.AssemblyAutoApiOptions.TryGetValue(action.Controller.ControllerType.Assembly, out AssemblyAutoApiOptions assemblyAutoApiOptions);
var getValueSuccess =
PlusConsts.AssemblyAutoApiOptions.TryGetValue(action.Controller.ControllerType.Assembly,
out var assemblyAutoApiOptions);

if (getValueSuccess && !string.IsNullOrWhiteSpace(assemblyAutoApiOptions?.ApiPrefix))
{
Expand All @@ -236,28 +255,27 @@ private static string GetApiPreFix(ActionModel action)
private void ConfigureParameters(ControllerModel controller)
{
foreach (var action in controller.Actions)
foreach (var para in action.Parameters)
{
foreach (var para in action.Parameters)
if (para.BindingInfo != null)
{
if (para.BindingInfo != null)
{
continue;
}
continue;
}

if (!TypeHelper.IsPrimitiveExtendedIncludingNullable(para.ParameterInfo.ParameterType))
if (!TypeHelper.IsPrimitiveExtendedIncludingNullable(para.ParameterInfo.ParameterType))
{
if (CanUseFormBodyBinding(action, para))
{
if (CanUseFormBodyBinding(action, para))
{
para.BindingInfo = BindingInfo.GetBindingInfo(new[] { new FromBodyAttribute() });
}
para.BindingInfo = BindingInfo.GetBindingInfo(new[] { new FromBodyAttribute() });
}
}
}
}

private bool CanUseFormBodyBinding(ActionModel action, ParameterModel parameter)
{
if (PlusConsts.FormBodyBindingIgnoredTypes.Any(t => t.IsAssignableFrom(parameter.ParameterInfo.ParameterType)))
if (PlusConsts.FormBodyBindingIgnoredTypes.Any(t =>
t.IsAssignableFrom(parameter.ParameterInfo.ParameterType)))
{
return false;
}
Expand Down
2 changes: 2 additions & 0 deletions Plus.AutoApi/AutoApiOptions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -31,6 +31,8 @@ public AutoApiOptions()

public Func<string, string> GetRestFulActionName { get; set; }

public Func<string, string> GetRestFulControllerName { get; set; }

public Dictionary<Assembly, AssemblyAutoApiOptions> AssemblyAutoApiOptions { get; }

public void Valid()
Expand Down
1 change: 1 addition & 0 deletions Plus.AutoApi/AutoApiServiceExtensions.cs
Original file line number Diff line number Diff line change
Expand Up @@ -38,6 +38,7 @@ private static IServiceCollection AddAutoApi(this IServiceCollection services, A
PlusConsts.ActionSuffixes = options.RemoveActionSuffixes;
PlusConsts.FormBodyBindingIgnoredTypes = options.FormBodyBindingIgnoredTypes;
PlusConsts.GetRestFulActionName = options.GetRestFulActionName;
PlusConsts.GetRestFulControllerName = options.GetRestFulControllerName;
PlusConsts.AssemblyAutoApiOptions = options.AssemblyAutoApiOptions;

var partManager = services.GetSingletonInstanceOrNull<ApplicationPartManager>();
Expand Down
46 changes: 27 additions & 19 deletions Plus.AutoApi/Plus.AutoApi.csproj
Original file line number Diff line number Diff line change
@@ -1,24 +1,32 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netcoreapp3.1</TargetFramework>
<PackageId>Plus.AutoApi</PackageId>
<Authors>阿星Plus</Authors>
<Company>https://meowv.com</Company>
<Description>Plus.AutoApi 是一个可以用来动态生成 WebApi 不用写 Controller 的组件</Description>
<PackageLicenseExpression>MIT</PackageLicenseExpression>
<Copyright>https://meowv.com</Copyright>
<PackageProjectUrl>https://github.com/Meowv/Plus.AutoApi</PackageProjectUrl>
<PackageIconUrl>https://avatars2.githubusercontent.com/u/13010050</PackageIconUrl>
<RepositoryUrl>https://github.com/Meowv/Plus.AutoApi</RepositoryUrl>
<RepositoryType>git</RepositoryType>
<PackageTags>plus;autoapi;plus.autoapi;</PackageTags>
<PackageReleaseNotes>.NET Core 开发工具包</PackageReleaseNotes>
<Version>0.1.0</Version>
</PropertyGroup>
<PropertyGroup>
<TargetFramework>netcoreapp3.1</TargetFramework>
<PackageId>Plus.AutoApi</PackageId>
<Authors>阿星Plus</Authors>
<Company>https://meowv.com</Company>
<Description>Plus.AutoApi 是一个可以用来动态生成 WebApi 不用写 Controller 的组件</Description>
<PackageLicenseExpression>MIT</PackageLicenseExpression>
<Copyright>https://meowv.com</Copyright>
<PackageProjectUrl>https://github.com/Meowv/Plus.AutoApi</PackageProjectUrl>
<PackageIconUrl>https://avatars2.githubusercontent.com/u/13010050</PackageIconUrl>
<RepositoryUrl>https://github.com/Meowv/Plus.AutoApi</RepositoryUrl>
<RepositoryType>git</RepositoryType>
<PackageTags>plus;autoapi;plus.autoapi;</PackageTags>
<PackageReleaseNotes>.NET Core 开发工具包</PackageReleaseNotes>
<Version>0.1.0</Version>
</PropertyGroup>

<ItemGroup>
<FrameworkReference Include="Microsoft.AspNetCore.App" />
</ItemGroup>
<ItemGroup>
<FrameworkReference Include="Microsoft.AspNetCore.App" />
</ItemGroup>

<ItemGroup>
<ProjectReference Include="..\Plus.AutoApi.Core\Plus.AutoApi.Core.csproj" />
</ItemGroup>

<ItemGroup>
<PackageReference Include="Microsoft.AspNetCore.Mvc" Version="2.2.0" />
</ItemGroup>

</Project>
2 changes: 2 additions & 0 deletions Plus.AutoApi/PlusConsts.cs
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,8 @@ static PlusConsts()

public static Func<string, string> GetRestFulActionName { get; set; }

public static Func<string, string> GetRestFulControllerName { get; set; }

public static Dictionary<Assembly, AssemblyAutoApiOptions> AssemblyAutoApiOptions { get; set; }
}
}
12 changes: 12 additions & 0 deletions Plus.AutoApi/Properties/launchSettings.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
{
"profiles": {
"Plus.AutoApi": {
"commandName": "Project",
"launchBrowser": true,
"environmentVariables": {
"ASPNETCORE_ENVIRONMENT": "Development"
},
"applicationUrl": "http://localhost:64869"
}
}
}
17 changes: 17 additions & 0 deletions Plus.AutoApiGenerator/Plus.AutoApiGenerator.csproj
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
<Project Sdk="Microsoft.NET.Sdk">

<PropertyGroup>
<TargetFramework>netstandard2.0</TargetFramework>
<IncludeBuildOutput>false</IncludeBuildOutput>
<IncludeSymbols>false</IncludeSymbols>
<CopyLocalLockFileAssemblies>true</CopyLocalLockFileAssemblies>
</PropertyGroup>
<ItemGroup>
<PackageReference Include="Microsoft.CodeAnalysis.CSharp" Version="4.9.2" PrivateAssets="all" />
<PackageReference Include="Microsoft.CodeAnalysis.Analyzers" Version="3.3.4" PrivateAssets="all" />
</ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Plus.AutoApi.Core\Plus.AutoApi.Core.csproj" />
</ItemGroup>

</Project>
Loading