首页 > 其他分享 >(3) MasaFramework 入门第三篇,使用MasaFramework

(3) MasaFramework 入门第三篇,使用MasaFramework

时间:2023-03-17 19:23:45浏览次数:67  
标签:第三篇 入门 Service app MasaFramework options logger TokenDemo public

首先我们需要创建一个MasaFramework模板的项目,项目名称TokenDemo,项目类型如图所示

删除Web/TokenDemo.Admin项目,新建Masa Blazor Pro项目模板

项目,项目位置在src/Web项目

项目类型选择ServerAndWasm,为了让我们支持俩种模式

创建完成以后的目录,然后在TokenDemo.Admin中添加项目引用TokenDemo.Caller

配置EntityFrameworkCoreSqlite

修改TokenDemo.Service项目的包依赖为预览版

	<ItemGroup>
		<PackageReference Include="Masa.BuildingBlocks.Dispatcher.Events" Version="1.0.0-preview.18" />
		<PackageReference Include="Masa.Contrib.Data.Contracts" Version="1.0.0-preview.18" />
		<PackageReference Include="Masa.Contrib.Data.EFCore.Sqlite" Version="1.0.0-preview.18" />
		<PackageReference Include="Masa.Contrib.Dispatcher.Events" Version="1.0.0-preview.18" />
		<PackageReference Include="Masa.Contrib.Dispatcher.IntegrationEvents.EventLogs.EFCore" Version="1.0.0-preview.18" />
		<PackageReference Include="FluentValidation" Version="11.5.1" />
		<PackageReference Include="FluentValidation.AspNetCore" Version="11.2.2" />
		<PackageReference Include="Masa.Utils.Extensions.DependencyInjection" Version="1.0.0-preview.18" />
		<PackageReference Include="Masa.Contrib.Service.MinimalAPIs" Version="1.0.0-preview.18" />
		<PackageReference Include="Microsoft.AspNetCore.Authentication.JwtBearer" Version="6.0.3" />
		<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
	</ItemGroup>

Masa.Contrib.Data.Contracts提供了数据过滤的能力, 但它不是必须的

然后会出现报错

LogMiddleware将代码修改为以下代码

namespace TokenDemo.Service.Infrastructure.Middleware;

public class LogMiddleware<TEvent> : EventMiddleware<TEvent>
    where TEvent : notnull, IEvent
{
    private readonly ILogger<LogMiddleware<TEvent>> _logger;

    public LogMiddleware(ILogger<LogMiddleware<TEvent>> logger)
    {
        _logger = logger;
    }

    public override async Task HandleAsync(TEvent action, EventHandlerDelegate next)
    {
        var typeName = action.GetType().FullName;

        _logger.LogInformation("----- command {CommandType}", typeName);

        await next();
    }
}

ValidatorMiddleware将代码修改为以下代码

namespace TokenDemo.Service.Infrastructure.Middleware;

public class ValidatorMiddleware<TEvent> : EventMiddleware<TEvent>
    where TEvent : notnull, IEvent
{
    private readonly ILogger<ValidatorMiddleware<TEvent>> _logger;
    private readonly IEnumerable<IValidator<TEvent>> _validators;

    public ValidatorMiddleware(IEnumerable<IValidator<TEvent>> validators, ILogger<ValidatorMiddleware<TEvent>> logger)
    {
        _validators = validators;
        _logger = logger;
    }

    public override async Task HandleAsync(TEvent action, EventHandlerDelegate next)
    {
        var typeName = action.GetType().FullName;

        _logger.LogInformation("----- Validating command {CommandType}", typeName);

        var failures = _validators
            .Select(v => v.Validate(action))
            .SelectMany(result => result.Errors)
            .Where(error => error != null)
            .ToList();

        if (failures.Any())
        {
            _logger.LogWarning("Validation errors - {CommandType} - Command: {@Command} - Errors: {@ValidationErrors}", typeName, action, failures);

            throw new ValidationException("Validation exception", failures);
        }

        await next();
    }
}

OrderEventHandler将代码修改为以下代码

namespace TokenDemo.Service.Infrastructure.Handlers;

public class OrderEventHandler
{
    readonly IOrderRepository _orderRepository;

    public OrderEventHandler(IOrderRepository orderRepository)
    {
        _orderRepository = orderRepository;
    }

    [EventHandler(Order = 1)]
    public async Task HandleAsync(QueryOrderListEvent @event)
    {
        @event.Orders = await _orderRepository.GetListAsync();
    }
}

public class OrderEventAfterHandler : IEventHandler<QueryOrderListEvent>
{
    public async Task HandleAsync(QueryOrderListEvent @event, CancellationToken cancellationToken = new CancellationToken())
    {
        await Task.CompletedTask;
    }
}

修改appsettings.json 添加Sqlite地址

{
  "Logging": {
    "LogLevel": {
      "Default": "Information",
      "Microsoft": "Warning",
      "Microsoft.Hosting.Lifetime": "Information"
    }
  },
  "AllowedHosts": "*",
  "ConnectionStrings": {
    "DefaultConnection": "Data Source=Catalog.db;"
  }
}

修改Program.cs代码

using TokenDemo.Service.Infrastructure;

var builder = WebApplication.CreateBuilder(args);

builder.Services
    .AddAuthorization()
    .AddAuthentication(options =>
    {
        options.DefaultAuthenticateScheme = JwtBearerDefaults.AuthenticationScheme;
        options.DefaultChallengeScheme = JwtBearerDefaults.AuthenticationScheme;
    })
    .AddJwtBearer(options =>
    {
        options.Authority = "";
        options.RequireHttpsMetadata = false;
        options.Audience = "";
    });

builder.Services.AddMasaDbContext<ShopDbContext>(dbContextBuilder =>
{
    dbContextBuilder
        .UseSqlite() //使用Sqlite数据库
        .UseFilter(); //数据数据过滤
});

builder.Services.AddAutoInject();
var app = builder.Services
    .AddEndpointsApiExplorer()
    .AddSwaggerGen(options =>
    {
        options.AddSecurityDefinition("Bearer", new OpenApiSecurityScheme()
        {
            Name = "Authorization",
            Type = SecuritySchemeType.ApiKey,
            Scheme = "Bearer",
            BearerFormat = "JWT",
            In = ParameterLocation.Header,
            Description = "JWT Authorization header using the Bearer scheme. \r\n\r\n Enter 'Bearer' [space] and then your token in the text input below.\r\n\r\nExample: \"Bearer xxxxxxxxxxxxxxx\"",
        });
        options.AddSecurityRequirement(new OpenApiSecurityRequirement
        {
            {
                new OpenApiSecurityScheme
                {
                    Reference = new OpenApiReference
                    {
                        Type = ReferenceType.SecurityScheme,
                        Id = "Bearer"
                    }
                },
                new string[] {}
            }
        });
    })
    .AddFluentValidationAutoValidation().AddFluentValidationClientsideAdapters()
    .AddEventBus(eventBusBuilder =>
    {
        eventBusBuilder.UseMiddleware(typeof(ValidatorMiddleware<>));
        eventBusBuilder.UseMiddleware(typeof(LogMiddleware<>));
    })
    .AddServices(builder);

// Configure the HTTP request pipeline.
if (app.Environment.IsDevelopment())
{
    app.UseSwagger();
    app.UseSwaggerUI();
}
app.UseRouting();

app.UseAuthentication();
app.UseAuthorization();

app.UseHttpsRedirection();

app.Run();

添加EFCore迁移依赖

		<PackageReference Include="Microsoft.EntityFrameworkCore.Design" Version="6.0.15">
		  <PrivateAssets>all</PrivateAssets>
		  <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
		</PackageReference>
		<PackageReference Include="Microsoft.EntityFrameworkCore.Tools" Version="6.0.15">
		  <PrivateAssets>all</PrivateAssets>
		  <IncludeAssets>runtime; build; native; contentfiles; analyzers; buildtransitive</IncludeAssets>
		</PackageReference>

程序包管理器控制台中输入 Add-Migration Init生成Init的迁移文件(如果出现 error NETSDK1082: Microsoft.AspNetCore.App 没有运行时包可用于指定的 RuntimeIdentifier“browser-wasm”这个错误的话就先把TokenDemo.Admin.WebAssembly项目移除)

使用Update-Database生成Sqlitem

然后就可以看到项目中生成了Catalog.db文件

启动TokenDemo.Service.Order我们就可以看到Swagger的界面了

如何对接接口

打开TokenDemo.Caller项目中的``Callers\OrderCaller.cs`文件

修改BaseAdderssTokenDemo.Service.Order的服务地址

打开TokenDemo.Service.Order项目的Services\OrderService.cs文件并且修改代码

namespace TokenDemo.Service.Services;

public class OrderService : ServiceBase
{
    public OrderService(IServiceCollection services) : base(services)
    {
        App.MapGet("/order/list", QueryList).Produces<List<Infrastructure.Entities.Order>>()
            .WithName("GetOrders");
    }

    public async Task<IResult> QueryList(IEventBus eventBus)
    {
        var orderQueryEvent = new QueryOrderListEvent();
        await eventBus.PublishAsync(orderQueryEvent);
        return Results.Ok(orderQueryEvent.Orders);
    }
}

然后在通过命令行启动TokenDemo.Service.Order项目

打开TokenDemo\Admin项目的Pages\Home\Index.razor文件并且修改代码

@page "/"
@using TokenDemo.Caller.Callers
@inherits LayoutComponentBase
@inject NavigationManager Nav
@inject OrderCaller OrderCaller
@code {

    protected override async Task OnAfterRenderAsync(bool firstRender)
    {
        Nav.NavigateTo(GlobalVariables.DefaultRoute,true);
        var data = await OrderCaller.GetListAsync();
        await base.OnAfterRenderAsync(firstRender);
    }

}

并且在await base.OnAfterRenderAsync(firstRender);这里打一个断点用于查看是否获取到消息

打开TokenDemo.Admin.Server项目的Program.cs,添加以下代码

builder.Services.AddCaller(typeof(TokenDemo.Caller.Callers.OrderCaller).Assembly);

然后启动TokenDemo.Admin.Server项目,进入断点

得到结果

结尾

通过上文我们可以基本将MasaFramework的使用掌握,前端和后端的接口也掌握了

当前是MasaFramework的第三篇入门,我会继续学习MasaFramework并且分享给大家

来自token的分享

MASA Framework

学习交流:737776595

标签:第三篇,入门,Service,app,MasaFramework,options,logger,TokenDemo,public
From: https://www.cnblogs.com/hejiale010426/p/17227910.html

相关文章

  • schema入门
    定义一个schema的步骤:1、创建一个文件,后缀名为.xsd2、定义文档声明(因为schema文件也是一个xml文件,所以它的文档声明和xml一样:<?xmlversion="1.0"encoding="UTF-8"?>......
  • msfconsole入门
    jpg改pdf本文我们简单的来学习,msfconsole在实际的渗透测试中长应用的手段和方法。以及msf在后渗透阶段的使用。注意本文所讲到的技术仅在本地靶场环境运行,同时本文的......
  • 从0到1入门Docker(七)配置国内加速器
     配置国内加速器 上篇文章内容是Docker引擎的安装,今天这篇文章来说一下配置国内加速器​​https://blog.51cto.com/u_15485663/6127076​​学习Docker推荐大家可以看动......
  • Thingsboard 开源 IoT 平台入门
    参考:https://github.com/thingsboard/thingsboardhttps://thingsboard.io/https://docs.thingskit.com/1.Thingsboard简介ThingsBoard是一个基于Java的开源的物联......
  • 1、GO语言入门-环境准备及第一个go程序开发
    1、Windows开发环境准备(1)Golang编译器下载golang中文网:https://studygolang.com/dl或者:https://go.dev/dl/(2)下载解压,找到bin目录(3)配置环境变量右键此电脑,点击属......
  • go微服务开发:go-zero入门教程(二)
    以下内容,参考了go-zero官方文档,是对官方文档的进阶指南章节的梳理汇总。go-zero的进阶指南,请参考 https://go-zero.dev/cn/docs/advance/business-dev 通过本文,你将学......
  • MasaFramework入门第二篇,安装MasaFramework了解各个模板
    安装MasaFramework模板执行以下命令安装最新Masa的模板dotnetnew--installMasa.Template安装完成将出现四个模板MasaBlazorApp:MasaBlazorApp的模板创建的是......
  • Steamlit初识和安装入门
    Streamlit 是可以用于快速搭建Web应用的Python库。Streamlit基于tornado框架,封装了大量互动组件,同时也支持大量表格、图表、数据表等对象的渲染,并且支持栅格化响应式布......
  • 【10分钟入门】想学爬虫?关于正则表达式,看这一篇就够了!
    最近接触到正则表达式,用于匹配对应的字符串,觉得很神奇,于是开始一个学习。有句老话说得好:“爬虫写得好,牢范吃得饱。”哈哈哈当然是开个玩笑。工具推荐regex101:build,......
  • 我的Python学习之路,从入门到实战
    Python学习手册【学习线路】【学习线路图】【技能对照表】一、容器列表(list)元组(tuple)集合(set)字典(dict)1、列表线性表:数组:连续内存的实现栈:先进后出,后进先出队列:先进先出,后进......