当前位置: 首页 > news >正文

ASP.NET Core 6 MVC 文件上传

概述

        应用程序中的文件上传是一项功能,用户可以使用该功能将用户本地系统或网络上的文件上传到 Web 应用程序。Web 应用程序将处理该文件,然后根据需要对文件进行一些验证,最后根据要求将该文件存储在系统中配置的用于保存文件的存储中,即本地存储、共享远程存储或数据库等。

        文件上传是一项重要功能,可用于上传用户的个人资料图片、客户 KYC 详细信息(如照片)、签名和其他支持文件。文件上传还可用于上传数据,用户可以使用 CSV 或XML文件格式一起提交记录列表,而不是一次提交一条记录。

        在本文中,我们将主要关注如何在 ASP.NET Core MVC 中实现文件上传。 IFormFile 接口是 Microsoft.AspNetCore.Http 命名空间的一部分,可用于在 ASP.NET Core 中上传一个或多个文件。 ASP.NET Core 支持使用缓冲模型绑定上传较小文件的文件,并使用无缓冲流上传较大文件的文件。

文件上传方法

        在 ASP.NET Core 中有两种方法可以执行文件上传。

        源码下载:https://download.csdn.net/download/hefeng_aspnet/90294631 

缓冲

        在此方法中,IFormFile(文件的 C# 表示)用于在 Web 服务器上传输、处理和保存文件。整个文件被读入 IFormFile 对象,因此服务器上的磁盘和内存要求将取决于并发文件上传的数量和大小。

        如果上传的任何单个文件大于 64KB,则该文件将从内存移动到磁盘上的临时文件。如果应用程序或 Web 服务器资源因文件过大和并发文件上传过多而耗尽,则应考虑在这种情况下使用流式传输方法。

流媒体

        在这种方法中,文件以多部分请求的形式上传,并由应用程序直接处理或保存。与缓冲方法相比,上传文件流式方法消耗的内存或磁盘空间更少。在 Web 服务器上上传较大文件时,流式传输应该是首选方法。

在ASP.NET Core中实现文件上传

        为了开发演示应用程序,我们将使用带有 .NET 6.0 SDK 的 Visual Studio Community 2022 版本 17.2.1。

总体方法

为了演示如何在 ASP.NET Core 中执行文件上传,我们将采用以下方法:

        1、我们将首先创建一个 ASP.NET Core MVC 类型的应用程序并将其命名为 ProCodeGuide.Samples.FileUpload。

        2、我们将实现两种类型的文件上传,即针对小文件的缓冲模型绑定和针对大文件的流式上传。

        3、我们将添加具有所需 ViewModel 的所需控制器,将文件作为输入并将其保存到本地文件夹。

        4、我们将添加视图,用户可以使用该视图从本地文件系统中选择文件进行上传,并将文件提交给控制器操作方法。

        5、最后,我们将运行应用程序并测试 ASP.NET Core 中的文件上传功能。

创建 ASP.NET Core 项目进行演示

根据下面的屏幕截图创建一个 ASP.NET Core MVC 类型的新项目,项目名称为 ProCodeGuide.Samples.FileUpload

        我们将使用该项目来演示在 ASP.NET Core 中执行文件上传的两种类型,即缓冲和流式上传。

使用缓冲模型绑定上传小文件

        在这里,我们将看到如何使用缓冲模型绑定上传小文件。为了在 ASP.NET Core 中执行文件上传,我们将使用缓冲模型绑定方法,该方法易于实现,可用于上传小文件。

添加服务

        我们将添加一个服务,该服务将以 IFormFile 作为输入,并将提交的文件保存到路径环境当前目录下名为 UploadedFile 的文件夹中。此服务将在控制器中用于保存作为缓冲模型绑定发布的文件。

        我们将在 Interfaces/IBufferedFileUploadService.cs 下为接口添加以下代码

public interface IBufferedFileUploadService
{
    Task<bool> UploadFile(IFormFile file);
}

        我们将在 Services/BufferedFileUploadLocalService.cs 下为服务添加以下代码 

public class BufferedFileUploadLocalService : IBufferedFileUploadService
{
    public async Task<bool> UploadFile(IFormFile file)
    {
        string path = "";
        try
        {
            if (file.Length > 0)
            {
                path = Path.GetFullPath(Path.Combine(Environment.CurrentDirectory, "UploadedFiles"));
                if (!Directory.Exists(path))
                {
                    Directory.CreateDirectory(path);
                }
                using (var fileStream = new FileStream(Path.Combine(path, file.FileName), FileMode.Create))
                {
                    await file.CopyToAsync(fileStream);
                }
                return true;
            }
            else
            {
                return false;
            }
        }
        catch (Exception ex)
        {
            throw new Exception("File Copy Failed", ex);
        }
    }

在上述服务中的代码:

    1、使用 IFormFile 通过模型绑定来访问上传的文件。
    2、Path.GetFullPath 用于获取保存上传文件的完整限定路径。
    3、如果不存在,则使用 Directory.CreateDirectory 来创建完整限定路径。
    4、使用 Stream 访问 IFormFile 中文件的内容。
    5、路径和文件名一起传递给文件流。如果没有指定文件名,则会抛出异常。
    6、使用 IFormFile 提供的文件名将文件保存到指定路径上的文件系统。(这样做是为了保持代码简单,否则您应该生成一个新文件名,而不是使用用户指定的文件名)。

现在我们已经添加了服务,我们将在依赖项容器中注册该服务,以便可以使用构造函数将其注入到控制器中。要在依赖项容器中注册服务,我们将在 Program.cs 文件中添加以下代码行。

builder.Services.AddTransient<IBufferedFileUploadService, BufferedFileUploadLocalService>(); 

添加控制器

        现在让我们添加用于缓冲文件上传的 MVC 控制器,它将实现获取操作来显示视图和后期操作来处理 ASP.NET Core 中的文件上传。

我们将在 Controllers\BufferedFileUploadController.cs 下添加一个控制器,代码如下:

public class BufferedFileUploadController : Controller
{
    readonly IBufferedFileUploadService _bufferedFileUploadService;

    public BufferedFileUploadController(IBufferedFileUploadService bufferedFileUploadService)
    {
        _bufferedFileUploadService = bufferedFileUploadService;
    }

    public IActionResult Index()
    {
        return View();
    }

    [HttpPost]
    public async Task<ActionResult> Index(IFormFile file)
    {
        try
        {
            if (await _bufferedFileUploadService.UploadFile(file))
            {
                ViewBag.Message = "File Upload Successful";
            }
            else
            {
                ViewBag.Message = "File Upload Failed";
            }
        }
        catch (Exception ex)
        {
            // Log ex
            ViewBag.Message = "File Upload Failed";
        }
        return View();
    }
}

        在上面的控制器中,我们通过依赖注入的构造函数注入了 BufferedFileUploadService。

        上述后期操作将文件输入作为 IFormFile,并且使用 IFormFile 上传的文件在控制器或服务中处理文件之前缓冲在服务器的内存或磁盘中。

添加视图

        我们将添加视图以允许用户选择要上传的文件并将其提交到服务器。我们将根据以下代码在 Views\BufferedFileUpload\Index.cshtml 下添加一个视图:

<h1>Buffered File Upload</h1>
<hr />
<form method="post" enctype="multipart/form-data">
    <input type="file" name="file" /> 
    <button type="submit">Upload File</button>
</form>
 
@if (ViewBag.Message != null)
{
    <div class="alert" style="margin-top: 20px">
        @ViewBag.Message
    </div>
}

        为了在 ASP.NET Core 中执行文件上传,HTML 表单必须指定编码类型 (enctype) 为 multipart/form-data。

        要使输入元素上传文件,您需要将输入类型指定为“文件”。

什么是 multipart/form-data?

        multipart/form-data 只是 post 方法的 content-type 标头之一。此内容类型主要用于将文件作为请求的一部分发送。使用此内容类型意味着每个值都作为数据块发送。

运行并测试代码

        最后,添加所有必需的代码后,编译并执行代码。执行后,导航到路径 /BufferedFileUpload/Index,它应该会显示如下所示的屏幕。

        在上面的屏幕上,您可以选择要上传的文件,然后单击“上传文件”按钮以在 ASP.NET Core 中执行文件上传。成功提交后,您应该能够在服务器上的 UploadedFiles 文件夹下看到该文件。

使用流式传输上传大文件

        在这里,我们将看到如何使用流式传输上传大文件。为了在 ASP.NET Core 中执行文件上传,我们将使用可用于上传较大文件的流式传输方法。

添加服务

        我们将添加一个服务,它将以流的形式读取文件输入,并将提交的文件保存到路径环境当前目录下名为 UploadedFile 的文件夹中。此服务将在控制器中用于将发布的文件保存为流。

        我们将在 Interfaces/IStreamFileUploadService.cs 下为接口添加以下代码

 public interface IStreamFileUploadService
{
    Task<bool> UploadFile(MultipartReader reader, MultipartSection section);
}

        我们将在 Services/StreamFileUploadLocalService.cs 下为服务添加以下代码 

public class StreamFileUploadLocalService : IStreamFileUploadService
{
    public async Task<bool> UploadFile(MultipartReader reader,MultipartSection? section)
    {
        while (section != null)
        {
            var hasContentDispositionHeader = ContentDispositionHeaderValue.TryParse(
                section.ContentDisposition, out var contentDisposition
            );

            if (hasContentDispositionHeader)
            {
                if (contentDisposition.DispositionType.Equals("form-data") &&
                (!string.IsNullOrEmpty(contentDisposition.FileName.Value) ||
                !string.IsNullOrEmpty(contentDisposition.FileNameStar.Value)))
                {
                    string filePath = Path.GetFullPath(Path.Combine(Environment.CurrentDirectory, "UploadedFiles"));
                    byte[] fileArray;
                    using (var memoryStream = new MemoryStream())
                    {
                        await section.Body.CopyToAsync(memoryStream);
                        fileArray = memoryStream.ToArray();
                    }
                    using (var fileStream = System.IO.File.Create(Path.Combine(filePath, contentDisposition.FileName.Value)))
                    {
                        await fileStream.WriteAsync(fileArray);
                    }
                }
            }
            section = await reader.ReadNextSectionAsync();
        }
        return true;
    }
}

        在此模型中,绑定不会读取表单,从表单绑定的参数不会绑定。后置操作方法直接与 Request 属性配合使用。MultipartReader 用于读取每个部分。

        现在我们已经添加了服务,我们将在依赖项容器中注册该服务,以便可以使用构造函数将其注入到控制器中。要在依赖项容器中注册服务,我们将在 Program.cs 文件中添加以下代码行。

builder.Services.AddTransient<IStreamFileUploadService, StreamFileUploadLocalService>();

添加控制器

        现在让我们添加用于流文件上传的 MVC 控制器,它将实现获取操作来显示视图和后期操作来处理 ASP.NET Core 中的文件上传。

        我们将在 Controllers\StreamFileUploadController.cs 下添加一个控制器,代码如下:

public class StreamFileUploadController : Controller
{
    readonly IStreamFileUploadService _streamFileUploadService;

    public StreamFileUploadController(IStreamFileUploadService streamFileUploadService)
    {
        _streamFileUploadService = streamFileUploadService;
    }

    [HttpGet]
    public IActionResult Index()
    {
        return View();
    }

    [ActionName("Index")]
    [HttpPost]
    public async Task<IActionResult> SaveFileToPhysicalFolder()
    {
        var boundary = HeaderUtilities.RemoveQuotes(
            MediaTypeHeaderValue.Parse(Request.ContentType).Boundary
        ).Value;
        var reader = new MultipartReader(boundary, Request.Body);
        var section = await reader.ReadNextSectionAsync();
        string response = string.Empty;
        try
        {
            if (await _streamFileUploadService.UploadFile(reader, section))
            {
                ViewBag.Message = "File Upload Successful";
            }
            else
            {
                ViewBag.Message = "File Upload Failed";
            }
        }
        catch (Exception ex)
        {
            // Log ex
            ViewBag.Message = "File Upload Failed";
        }
        return View();
    }
}

        在上面的控制器中,我们通过依赖注入的构造函数注入了 StreamFileUploadService。

        上述后置操作从流中读取文件输入,并且使用流上传的文件在控制器或服务中处理文件之前不会缓冲在服务器的内存或磁盘中。从流中输入的文件只能读取一次。

        创建类型为 Microsoft.AspNetCore.WebUtilities.MultipartReader 的读取器对象,以从多部分数据中读取子部分流。

添加视图

        我们将添加视图以允许用户选择要上传的文件并将其提交到服务器。我们将根据以下代码在 Views\StreamFileUpload\Index.cshtml 下添加一个视图:

<h1>Stream File Upload</h1>
<hr />
<div>
    <form asp-route="StreamFileUpload/Index" enctype="multipart/form-data" method="POST">
        <input type="file" name="file" /> 
        <button type="submit" class="btn btn-primary">Save</button>
    </form>
</div>
@if (ViewBag.Message != null)
{
    <div class="alert" style="margin-top:20px">
        @ViewBag.Message
    </div>

运行并测试代码

        最后,添加所有必需的服务、控制器和视图后,编译并执行代码。执行后导航到路径 /StreamFileUpload/Index,它应该显示如下所示的屏幕:

        在上面的屏幕上,您可以选择要上传的文件,然后单击“上传文件”按钮以在 ASP.NET Core 中执行文件上传。成功提交后,您应该能够在服务器上的 UploadedFiles 文件夹下看到该文件。

文件存储选项

        在我们上面的演示中,我们将文件保存到本地文件系统。不过,在选择文件在 Web 服务器上的存储目标时,还有其他选项可用。文件的常见存储选项如下:

        1、文件系统——在此选项中,文件将保存在本地或网络共享的物理存储上。

        2、数据库— 在此选项中,文件将以 BLOB 或原始数据的形式保存在数据库表的某一列中。

        3、云- 在此选项中,使用云提供商提供的一些文件存储服务将文件保存在云中。

上述选项也支持 ASP.NET Core 中的文件上传。以下是在选择存储选项时应考虑的一些要点:

        1、对于较小的文件上传,与物理存储相比,数据库通常是更快的选择

        2、对于较大的文件上传,物理存储比数据库存储不太经济。

        3、数据库可以成为文件存储的有效选择,因为当我们从数据库中选择记录时,我们也可以与记录一起选择文件数据。

        4、此外,当您将文件存储在数据库中时,您可以将记录与文件数据一起插入作为同一数据库事务的一部分,否则,如果文件位于物理存储中而记录位于数据库中,则如果设计不正确,可能会在记录和文件数据之间产生一些不一致。

        5、当您在数据库中存储较大的文件时,数据库大小会显著增加,从而使数据库备份和恢复成为一个繁重且耗时的过程。

        6、数据库限制可能会对允许存储的文件的最大大小施加一些限制。

        7、对于物理存储,尝试在物理路径上保存文件的应用程序应该对存储位置具有读写权限。

        8、与本地解决方案相比,云存储通常提供更好的稳定性和弹性

        9、与数据库存储相比,物理存储通常不太经济,而且与云数据存储服务相比,数据库存储可能更便宜。

安全注意事项

        在应用程序中提供文件上传功能时,如果您始终保持谨慎,这将有所帮助,因为攻击者可能会尝试通过 ASP.NET Core 中的文件上传功能来利用应用程序。攻击者可能会尝试通过上传受病毒或恶意软件感染的文件来破坏系统,或者可能试图闯入系统以访问网络或服务器。

        以下是您应该考虑的措施,因为这些措施将帮助您阻止攻击者成功破坏系统或侵入系统:

        1、对可上传文件的最大大小进行限制。

        2、如果使用物理存储,则应将上传的文件复制到非系统驱动器。

        3、最好将所有上传文件复制到专用位置,以便更容易对该位置施加访问权限。

        4、当您为磁盘分配读写权限以复制上传的文件时,请确保您最终不会授予执行权限。

        5、您应该将上传的文件复制到与应用程序部署目录不同的目录中。

        6、首先,不要允许用户决定要上传的文件的文件名,或者如果允许用户选择文件名,请确保对文件进行所有验证,以避免出现不必要的关键字或字符。

        7、另外,验证文件扩展名,以便只允许上传允许的文件类型。

        8、对所有上传的文件执行virus\maclware检查。为此,您可以使用第三方API对上传的内容进行病毒/恶意软件扫描。

        9、确保除了客户端验证之外,还要在服务器端对文件执行所有验证。

概括

        我们了解了如何在 ASP.NET Core 应用程序中执行缓冲和流类型的文件上传。在文件大小较小且并发文件提交数量较少的情况下,缓冲方法是更可取的。

        当我们提交大文件或并发文件提交数量较高时,应使用流方法。流类型将有助于减少对服务器内存和磁盘的要求。

如果您喜欢此文章,请收藏、点赞、评论,谢谢,祝您快乐每一天。  

相关文章:

ASP.NET Core 6 MVC 文件上传

概述 应用程序中的文件上传是一项功能&#xff0c;用户可以使用该功能将用户本地系统或网络上的文件上传到 Web 应用程序。Web 应用程序将处理该文件&#xff0c;然后根据需要对文件进行一些验证&#xff0c;最后根据要求将该文件存储在系统中配置的用于保存文件的存储中&#…...

【VBA】WPS/PPT设置标题字体

通过VBA&#xff0c;配合左上角的快速访问工具栏&#xff0c;实现自动化调整 选中文本框的 字体位置、大小、颜色。 配合quicker更加便捷 Sub DisableAutoWrapAndFormat()Dim shp As Shape 检查是否选中了一个形状&#xff08;文本框&#xff09;If ActiveWindow.Selection.Typ…...

白盒测试(4):电源瞬态电流测试

电源瞬态电流测试至关重要&#xff0c;主要用于评估电源在负载突变时的响应能力。通过测试&#xff0c;可以确保电源在短时间内提供足够的电流并快速恢复稳定&#xff0c;避免电压波动或系统故障。这对于保证电子设备的可靠性和稳定性尤为关键&#xff0c;尤其是在高动态负载应…...

三维建模与视频融合(3D-Video Integration)技术初探。

三维建模与视频融合&#xff08;3D-Video Integration&#xff09;是一种将虚拟三维模型无缝嵌入实拍视频场景的技术&#xff0c;广泛应用于影视特效、增强现实&#xff08;AR&#xff09;、游戏开发、广告制作 、视频监控 等领域。 一、技术核心流程 三维建模与动画 使用工具…...

DeepSeek提问术:解锁AI交互新姿势-20 个精准提问框架

一、引言 在人工智能的浩瀚星空中,DeepSeek 无疑是一颗耀眼的新星,以其独特的光芒照亮了 AI 发展的新路径。自问世以来,DeepSeek 凭借先进的技术架构、强大的自然语言处理能力和出色的性能表现,迅速在竞争激烈的 AI 领域崭露头角,成为众多开发者、研究人员以及各行业从业者…...

避免魔法值和多层if的关键:编程范式和设计模式

提示&#xff1a;文章写完后&#xff0c;目录可以自动生成&#xff0c;如何生成可参考右边的帮助文档 文章目录 前言一、案例分析二、技术手段函数式接口在枚举中 三、优化后完整代码总结 前言 提示&#xff1a;避免魔法值和多层if的关键&#xff1a;编程范式和设计模式&#…...

第六课:数据存储三剑客:CSV/JSON/MySQL

在Python的数据存储与处理领域&#xff0c;CSV、JSON和MySQL被广大开发者誉为“数据存储三剑客”。它们各自在不同的场景下发挥着重要作用&#xff0c;无论是简单的数据交换、轻量级的数据存储&#xff0c;还是复杂的关系型数据库管理&#xff0c;都能找到它们的身影。本文将详…...

Qt常用控件之表格QTableWidget

表格QTableWidget QTableWidget 是一个表格控件&#xff0c;行和列交汇形成的每个单元格&#xff0c;是一个 QTableWidgetItem 对象。 1. QTableWidget属性 QTableWidget 的属性只有两个&#xff1a; 属性说明rowCount当前行的个数。columnCount当前列的个数。 2. QTableW…...

基于websocket的多用户网页五子棋 --- 测试报告

目录 功能测试自动化测试性能测试 功能测试 1.登录注册页面 2.游戏大厅页面 3.游戏房间页面 自动化测试 1.使用脑图编写web自动化测试用例 2.创建自动化项目&#xff0c;根据用例通过selenium来实现脚本 根据脑图进行测试用例的编写&#xff1a; 每个页面一个测试类&am…...

TypeError: Cannot assign to read only property ‘xxx‘ of object ‘#<Object>‘

&#x1f90d; 前端开发工程师、技术日更博主、已过CET6 &#x1f368; 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 &#x1f560; 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》、《前端求职突破计划》 &#x1f35a; 蓝桥云课签约作者、…...

SyntaxError: Unexpected token ‘xxx‘

&#x1f90d; 前端开发工程师、技术日更博主、已过CET6 &#x1f368; 阿珊和她的猫_CSDN博客专家、23年度博客之星前端领域TOP1 &#x1f560; 牛客高级专题作者、打造专栏《前端面试必备》 、《2024面试高频手撕题》、《前端求职突破计划》 &#x1f35a; 蓝桥云课签约作者、…...

简记_开关电源基础知识(二)

一、控制器与稳压器 假设开关损耗、导通损耗、驱动损耗的变化远小于输出功率的变化&#xff08;可忽略&#xff09;&#xff0c;则占空比越大&#xff0c;Po越大&#xff0c;效率越高。 二、同步与非同步 同步是采用通态电阻极低的MOSFET来取代整流二极管&#xff0c;以降低整…...

grum-与gam-词源故事

“grum”词根的含义主要与“咕隆、发哼声、咕咕叫、发隆隆声”等相关。在16世纪90年代后&#xff0c;这个词开始被用来表示发出低沉持续的咆哮声或隆隆声&#xff0c;类似于饥饿的胃或某些动物发出的声音。 早期的富贵家族经常雇佣人去干活&#xff0c;体力活很容易因为劳工过…...

联合索引关于In和范围查询影响索引使用的情况分析

索引类型 1、unique &#xff0c;唯一索引 2、normal&#xff0c;普通索引 3、fulltext, 全文索引 4、spatial&#xff0c;空间索引 样例 三个字段的联合索引&#xff0c;走一个字段是key_len是5&#xff0c;三个是15. 联合索引关于 使用in是不影响后续列 范围查询大于或小于…...

【目标检测】【NeuralPS 2023】Gold-YOLO:通过收集与分发机制实现的高效目标检测器

Gold-YOLO&#xff1a; Efficient Object Detector via Gather-and-Distribute Mechanism Gold-YOLO&#xff1a;通过收集与分发机制实现的高效目标检测器 0.论文摘要 在过去的几年中&#xff0c;YOLO系列模型已成为实时目标检测领域的领先方法。许多研究通过修改架构、增强数…...

2025上软考下周开启报名!附报考流程和常见问题解答

报名时间 &#xff1a;3月10日开始报名&#xff08;以当地报名时间为准&#xff09; 考试时间 &#xff1a;2025年5月24日~27日&#xff08;具体时间以准考证为准&#xff09; 报名网址 &#xff1a;中国计算机技术职业资格网(https://bm.ruankao.org.cn/sign/welcome) 目前已…...

PPT 小黑第16套

对应大猫19 在excel中复制表格 粘贴-选择性粘贴 -粘贴链接 业务部门和档案管理部门 剩下都是他们的下属级别 业务部门下面的选中按Tab 再选中Tab降级变成所属...

Swagger-01.介绍和使用方式

一.Swagger介绍 有了接口文档&#xff0c;我们就可以根据接口文档来开发后端的代码了。如果我们开发完了某个功能&#xff0c;后端如何验证我们开发的是否正确呢&#xff1f;我们就需要测试&#xff0c;使用Swagger就可以帮助后端生成接口文档&#xff0c;并且可以进行后端的接…...

从CL1看生物计算机的创新突破与发展前景:技术、应用与挑战的多维度剖析

一、引言 1.1 研究背景与意义 随着科技的飞速发展&#xff0c;计算机技术已经成为推动现代社会进步的核心力量之一。从最初的电子管计算机到如今的大规模集成电路计算机&#xff0c;计算机的性能得到了极大的提升&#xff0c;应用领域也不断拓展。然而&#xff0c;传统计算机…...

OpenCV视频解码性能优化十连击(实测帧率提升300%)

解密工业级视频处理优化方案&#xff01;从硬件加速到多线程榨干CPU/GPU性能&#xff0c;附RTSP流调优参数与内存泄漏排查技巧。 &#x1f527; 优化前准备 环境检测脚本 import cv2# 验证硬件加速支持 print("CUDA支持:", cv2.cuda.getCudaEnabledDeviceCount() &…...

springboot3 RestClient、HTTP 客户端区别

1 RestClient使用 RestClient 是 Spring 6.1 M2 中引入的同步 HTTP 客户端&#xff0c;它取代了 RestTemplate。同步 HTTP 客户端以阻塞方式发送和接收 HTTP 请求和响应&#xff0c;这意味着它会等待每个请求完成后才继续下一个请求。本文将带你了解 RestClient 的功能以及它与…...

智能手表不可插卡怎么用

一、连接蓝牙 智能手表一般都可以通过蓝牙连接手机&#xff0c;以实现一些基础功能。连接方式一般分为以下几步&#xff1a; 1、首先打开手机的蓝牙功能&#xff0c;并在蓝牙列表中搜索手表的设备名称。 2、找到手表的设备名称后&#xff0c;点击连接即可完成蓝牙连接。 3、…...

blender看不到导入的模型

参考&#xff1a;blender 快捷键 常见问题_blender材质预览快捷键-CSDN博客 方法一&#xff1a;视图-裁剪起点&#xff0c;设置一个很大的值 方法二&#xff1a;选中所有对象&#xff0c;对齐视图-视图对齐活动项-选择一个视图...

【Unity】 HTFramework框架(六十一)Project窗口文件夹锁定器

更新日期&#xff1a;2025年3月7日。 Github源码&#xff1a;[点我获取源码] Gitee源码&#xff1a;[点我获取源码] 索引 Project窗口文件夹锁定器框架文件夹锁定自定义文件夹锁定限制条件 Project窗口文件夹锁定器 在Project窗口中&#xff0c;文件夹锁定器能够为任何文件夹加…...

智能体开发:推理-行动(ReAct)思维链提示

人类在处理一个需要多个步骤才能完成任务时&#xff0c;显著特点是能够将言语推理&#xff08;内心独白&#xff09;和实际行动融合在一起&#xff0c;在面对陌生或不确定的情况时通过这种方法学习新知识&#xff0c;做出决策&#xff0c;并执行&#xff0c;从而应对复杂的任务…...

机试准备第11天

第一题是浮点数加法&#xff0c;目前写过最长的代码。 #include <stdio.h> #include <string> #include <iostream> #include <vector> using namespace std; int main() {string str1;string str2;while (getline(cin, str1) && getline(cin…...

【Proteus仿真】【STM32单片机】智能阳台控制系统

文章目录 一、功能简介二、软件设计三、实验现象联系作者 一、功能简介 本项目使用Proteus8仿真STM32单片机控制器&#xff0c;使用按键、LCD1604液晶、DHT11温湿度模块、PCF8591 ADC、光线传感器、PM2.5传感器、土壤湿度传感器、继电器、水泵、电灯、28BYJ48步进电机等。 主要…...

Manus AI Agent 技术解读:架构、机制与竞品对比

目录 1. Manus 是什么&#xff1f; 1.1 研发背景 1.2 技术特点 1.3 工具调用能力 1.4 主要应用场景 2. Manus 一夜爆火的原因何在&#xff1f; 2.1 技术突破带来的震撼 2.2 完整交付的产品体验 2.3 生态与开源策略 3. Manus 与其他 AI Agent 的对比分析 3.1 技术架构…...

【时间序列】因果推断:从时序数据中探寻“因”与“果”

在日常生活中&#xff0c;我们经常听到这样的问题&#xff1a;“为什么股票价格会突然下跌&#xff1f;”、“天气变化是否会影响销售额&#xff1f;”这些问题背后&#xff0c;其实都在试图寻找一种因果关系。然而&#xff0c;在时间序列数据中&#xff0c;探寻因果关系并不像…...

IDEA2023 使用枚举类型java: 非法字符: ‘\ufffd‘

一、异常&#xff1a; 二、原因 文件编码问题 IDE或文本编辑器的文件编码设置不正确&#xff0c;可能会导致在保存文件时引入了错误的字符。 三、解决 在IntelliJ IDEA中&#xff0c;你可以通过File -> Settings -> Editor -> File Encodings来设置。...