文件传输服务应用1——java集成smb2/3详细教程和windows共享服务使用技巧

news2025/1/11 21:47:41

在实际项目开发过程中,读取网络资源或者局域网内主机的文件是必要的操作和需求。而FTP(文件传输协议)和SMB(服务器消息块)是两种最为常见的文件传输协议。它们各自在文件传输领域拥有独特的优势和特点,但同时也存在一些差异。

本文以java集成smb为案例说明,其中SMB作为一种在Windows环境中广泛使用的文件共享协议,特别适合于局域网内的文件共享和协作,具体如何集成开发请详细阅读。

本文案以springboot2.1.5作为开发对象。

一.设置共享文件夹,也就是smb服务(以windows为测试对象)

1.首先在我的电脑下,找C盘之外的盘符新建一个文件夹,本例以SMB_Server做介绍

2.然后就可以用网络路径在局域网内的浏览器或者我的电脑访问共享的文件。

注意:

可以使用ip或者域来访问,其中域指的是smb服务电脑的设备名称(在我的电脑属性查看)

3.开启smb服务后,如果不能正常访问请查看以下网站处理

https://learn.microsoft.com/zh-CN/troubleshoot/windows-server/networking/dns-cname-alias-cannot-access-smb-file-server-share

二.java项目引入smb共享文件包

需要注意的是:

使用smb作为传输协议时,其存在协议版本的问题,需要同时引入smb1和smb2/3才能正常工作。

        <!--SMB共享文件-->
        <!-- https://mvnrepository.com/artifact/jcifs/jcifs -->
        <!--smb1-->
        <dependency>
            <groupId>jcifs</groupId>
            <artifactId>jcifs</artifactId>
            <version>1.3.17</version>
        </dependency>
        <!--smb2/3-->
        <dependency>
            <groupId>com.hierynomus</groupId>
            <artifactId>smbj</artifactId>
            <version>0.11.3</version>
        </dependency>

三.配置smb链接信息,构造java链接使用工具

1.新增smb-config.properties配置文件
##########################
# SMB配置信息
##########################

########### ———以下是Windows本地服务配置信息
smb.hostname=127.0.0.1
## 域名,没有可以为空
smb.domain=wp-pc
smb.username=wp
smb.password=123456
## 一定记得是共享目录名称,其他无须添加
smb.server.root=SMB_Server
## 需要访问的目录名称,后缀必须带"/"
smb.server.path=/project/opt/
## 本地存放SMB下载的结果文件的目录
smb.local.path=D:\\test\\project\\opt\\
# 本地存放运行对接需要的数据
smb.local.rundata=D:\\data\\rundata\\


############## ———以下是linux服务器配置信息
#smb.hostname=10.1.0.21
#smb.domain=
#smb.username=root
#smb.password=root
#smb.server.root=SMB_Server
#smb.server.path=/project/opt/
#smb.local.path=/root/demo/project/opt/
#smb.local.rundata=/root/demo/project/rundata/
@lombok.Data
@Component
/**
 * 加载SMB自定义配置文件
 * 配置文件需放在resources文件夹根目录
 */
@PropertySource("classpath:smb-config.properties")
public class SMBConfigInfo {

    @Value("${smb.hostname}")
    private String hostname;
    @Value("${smb.domain}")
    private String domain;
    @Value("${smb.username}")
    private String username;
    @Value("${smb.password}")
    private String password;
    @Value("${smb.server.root}")
    private String rootPath;
    @Value("${smb.server.path}")
    private String serverPath;
    @Value("${smb.local.rundata}")
    private String runDataPath;
}
 2.新增SMB共享文件工具,可支持登录,读取,下载,上传等操作
/**
 * SMB共享文件工具
 * 支持登录,读取,下载,上传等操作
 * @author wp
 */
@Component
public class SMBUtils {

    @Autowired
    private SMBConfigInfo smbConfigInfo;

    /**
     * 登录SMB服务
     *
     * @return
     */
    private NtlmPasswordAuthentication loginSMBServer() {
        UniAddress dc;
        NtlmPasswordAuthentication authentication = null;
        try {
            dc = UniAddress.getByName(smbConfigInfo.getHostname());
            authentication = new NtlmPasswordAuthentication(smbConfigInfo.getDomain(), smbConfigInfo.getUsername(), smbConfigInfo.getPassword());
            SmbSession.logon(dc, authentication);
        } catch (Exception e) {
            e.printStackTrace();
            System.out.println("loginSMBServer fail:" + smbConfigInfo.toString());
            return null;
        }
        return authentication;
    }


    /**
     * 从SMB服务器下载文件到本地路径
     * 路径格式:smb://192.168.1.21/test/新建文本文档.txt
     * smb://username:password@192.168.1.21/test
     *
     * @param remoteUrl 远程路径
     * @param localDir  要写入的本地路径
     */
    public void getSMBFileByDown(String remoteUrl, String localDir) {
        InputStream in = null;
        OutputStream out = null;
        NtlmPasswordAuthentication auth = loginSMBServer();
        if (auth == null) {
            return;
        }
        try {
            SmbFile remoteFile = new SmbFile(remoteUrl, auth);
            if (!remoteFile.isFile()) {
                System.out.println("共享文件不存在");
                return;
            }
            String fileName = remoteFile.getName();
            File fileDir = new File(localDir);
            if (!fileDir.exists()) {
                fileDir.mkdirs();
            }
            File localFile = new File(localDir + File.separator + fileName);
            in = new BufferedInputStream(new SmbFileInputStream(remoteFile));
            out = new BufferedOutputStream(new FileOutputStream(localFile));
            byte[] buffer = new byte[1024];
            while (in.read(buffer) != -1) {
                out.write(buffer);
                buffer = new byte[1024];
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                out.close();
                in.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    /**
     * 通过读取SMB远程文件获得输入流
     * 如果输入流在别处使用的时候,一定记得不要先关闭
     * 另外流不能直接上传或者操作,否则有异常
     * 须先下载到本地,然后再处理
     *
     * @param remoteUrl
     * @return
     */
    public InputStream getInputStreamBySMBFile(String remoteUrl) {
        NtlmPasswordAuthentication auth = loginSMBServer();
        if (auth == null) {
            return null;
        }
        InputStream in = null;
        try {
            SmbFile remoteFile = new SmbFile(remoteUrl, auth);
            if (!remoteFile.isFile()) {
                System.out.println("共享文件不存在");
                return in;
            }
            in = new BufferedInputStream(new SmbFileInputStream(remoteFile));
            byte[] buffer = new byte[1024];
            while (in.read(buffer) != -1) {
                buffer = new byte[1024];
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            /*try {
                in.close();
            } catch (IOException e) {
                e.printStackTrace();
            }*/
        }
        return in;
    }


    /**
     * 从本地上传文件到指定SMB指定目录
     *
     * @param remoteUrl     文件的全路径+文件名称
     * @param localFilePath
     */
    public void getSMBFileByUpload(String remoteUrl, String localFilePath) {
        NtlmPasswordAuthentication auth = loginSMBServer();
        if (auth == null) {
            return;
        }
        InputStream in = null;
        OutputStream out = null;
        try {
            File localFile = new File(localFilePath);
            String fileName = localFile.getName();
            SmbFile remoteFile = new SmbFile(remoteUrl + "/" + fileName, auth);
            if (!remoteFile.exists()) {
                remoteFile.createNewFile();
            }
            in = new BufferedInputStream(new FileInputStream(localFile));
            out = new BufferedOutputStream(new SmbFileOutputStream(remoteFile));
            byte[] buffer = new byte[1024];
            while (in.read(buffer) != -1) {
                out.write(buffer);
                buffer = new byte[1024];
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                out.close();
                in.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    /**
     * 读取SMB服务指定目录的文件
     * smb://administrator:dibindb@10.1.1.12/share/aa.txt
     *
     * @param remoteUrl
     * @param fileName
     * @return
     */
    public String readSMBFile(String remoteUrl, String fileName) {
        NtlmPasswordAuthentication auth = loginSMBServer();
        if (auth == null) {
            return "";
        }
        SmbFileInputStream smbIn = null;
        StringBuffer strBu = new StringBuffer();
        try {
            SmbFile smbCatalog = new SmbFile(remoteUrl, auth);
            if (!smbCatalog.exists()) {
                smbCatalog.mkdirs();
            }
            SmbFile smbFile = new SmbFile(remoteUrl + fileName, auth);
            if (!smbFile.isFile()) {
                smbFile.createNewFile();
            }
            // 得到文件的大小
            int length = smbFile.getContentLength();
            byte buffer[] = new byte[ConstantDataList.SYSTEM_BUFFER_SIZE];
            // 建立smb文件输入流
            smbIn = new SmbFileInputStream(smbFile);
            int leng = -1;
            while ((leng = smbIn.read(buffer)) != -1) {
                strBu.append(new String(buffer, 0, leng));
            }
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                smbIn.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
        return strBu.toString();
    }

    /**
     * 将jsonStr写入SMB指定的目录文件中
     *
     * @param remoteUrl
     * @param fileName
     * @param jsonStr
     */
    public void writeSMBFile(String remoteUrl, String fileName,
                             String jsonStr) {

        NtlmPasswordAuthentication auth = loginSMBServer();
        if (auth == null) {
            return;
        }
        //将str转化成输入流
        ByteArrayInputStream smbIn = new ByteArrayInputStream(jsonStr.getBytes());
        SmbFileOutputStream out = null;
        try {
            SmbFile smbCatalog = new SmbFile(remoteUrl, auth);
            if (!smbCatalog.exists()) {
                smbCatalog.mkdirs();
            }
            SmbFile smbFile = new SmbFile(remoteUrl + fileName, auth);
            if (!smbFile.isFile()) {
                smbFile.createNewFile();
            }
            out = new SmbFileOutputStream(smbFile);
            // 得到文件的大小
            byte buffer[] = new byte[4096];
            int leng = -1;
            while ((leng = smbIn.read(buffer)) != -1) {
                out.write(buffer, 0, leng);
            }
            out.flush();
        } catch (Exception e) {
            e.printStackTrace();
        } finally {
            try {
                smbIn.close();
                out.close();
            } catch (IOException e) {
                e.printStackTrace();
            }
        }
    }

    
}

 四.测试java链接操作smb功能

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1686548.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

mac清理软件推荐免费 mac清理系统数据怎么清理 cleanmymac和腾讯柠檬哪个好

macbook是苹果公司的一款高性能的笔记本电脑&#xff0c;受到了很多用户的喜爱。但是&#xff0c;随着使用时间的增长&#xff0c;macbook的系统也会积累一些垃圾文件&#xff0c;影响其运行速度和空间。那么&#xff0c;macbook系统清理软件推荐有哪些呢&#xff1f;macbook用…

【Text2SQL 论文】SQLova:首次将 PLM 应用到 NL2SQL 中

论文&#xff1a;A Comprehensive Exploration on WikiSQL with Table-Aware Word Contextualization ⭐⭐⭐⭐ KR2ML Workshop at NeurIPS 2019, arXiv:1902.01069 Code: SQLova | GitHub 参考文章&#xff1a;将预训练语言模型引入WikiSQL任务 | CSDN 一、论文速度 这篇论文…

ZEDmini使用完全指南

ZEDmini使用 ZED stereolabs 开箱测评 使用说明 ubuntu18.04nvidiacuda10 ubuntu18.04ZED SDK安装和使用 Ubuntu16.04安装NVIDIA显卡驱动 查看显卡信息 redwallredwall-G3-3500:~/catkin_ws$ lspci | grep VGA 00:02.0 VGA compatible controller: Intel Corporation Device …

XV7011BB陀螺仪传感器广泛用于工业应用

陀螺仪传感器作为一种重要的惯性传感器&#xff0c;在航空航天、智能手机与可穿戴设备、工业控制与机器人、汽车行业、医疗仪器等多个领域都有着重要的应用&#xff0c;为这些领域的发展和创新提供了关键支持。 Epson陀螺仪传感器系列以其优异的性能和可靠性著称&#xff0c…

【20天拿下Pytorch:Day 8】模型层layers

文章目录 1. 内置模型层1.1 基础层1.2 卷积网络相关层1.3 循环网络相关层1.4 Transformer相关层 2. 自定义模型层 深度学习模型一般由各种模型层组合而成。 torch.nn中内置了非常丰富的各种模型层。它们都属于nn.Module的子类&#xff0c;具备参数管理功能。 注&#xff1a;这…

最新 ROS 2 Jazzy Jalisco 发布!支持 Ubuntu 24.04

系列文章目录 前言 世界海龟日快乐 今天&#xff0c;ROS 2 发布团队很高兴地宣布 ROS 2 的第十个版本&#xff1a;Jazzy Jalisco&#xff08;代号 jazzy&#xff09;。 除了之前分享的官方徽标&#xff0c;我们还发布了全新的 Jazzy Jalisco 图标。 Jazzy Jalisco 是一个长期支…

2024电工杯A题保姆级分析完整思路+代码+数据教学

2024电工杯A题保姆级分析完整思路代码数据教学 A题题目&#xff1a;园区微电网风光储协调优化配置 接下来我们将按照题目总体分析-背景分析-各小问分析的形式来 总体分析&#xff1a; 题目要求对园区微电网进行风光储协调优化配置&#xff0c;具体涉及三个园区&#xff08…

小蓝和小青在做数字破解游戏

小蓝和小青在做数字破解游戏,设某图案由m*n的0和1点阵组成&#xff0c;依照以下规则破解连续一组数值&#xff0c;从点阵图第一行第一个符号开始计算&#xff0c;从左到右&#xff0c;由上至下。第一个数表示连续有几个0&#xff0c;第二个数表示接下来连续有几个1&#xff0c;…

链表经典OJ问题【环形链表】

题目导入 题目一&#xff1a;给你一个链表的头节点 head &#xff0c;判断链表中是否有环 题目二&#xff1a;给定一个链表的头节点 head &#xff0c;返回链表开始入环的第一个节点。 如果链表无环&#xff0c;则返回 NULL。 题目一 给你一个链表的头节点 head &#xff0c;…

什么是物联网通信网关?-天拓四方

在信息化、智能化的时代&#xff0c;物联网技术的广泛应用正在逐渐改变我们的生活方式。物联网通过各种传感器和设备&#xff0c;将现实世界与数字世界紧密相连&#xff0c;从而实现智能化、自动化的生活和工作方式。作为物联网生态系统中的重要组成部分&#xff0c;物联网通信…

Q-Learning学习笔记-李宏毅

introduction 学习的并不是policy&#xff0c;而是学习critic&#xff0c;critic用来评价policy好还是不好&#xff1b;一种critic&#xff1a;state value function V π ( s ) V^\pi(s) Vπ(s)是给定一个policy π \pi π&#xff0c;在遇到state s s s之后累积的reward的…

并发控制利器Semaphore

并发控制利器&#xff1a;Semaphore详解与应用 简介 Semaphore 是Java并发编程中的一个重要工具&#xff0c;用于管理对共享资源的访问权限&#xff0c;确保系统资源不会因过度访问而耗尽。形象地说&#xff0c;Semaphore 可以比喻为交通信号灯&#xff0c;它控制着能够同时进…

Spring Cloud 系列之Gateway:(9)初识网关

传送门 Spring Cloud Alibaba系列之nacos&#xff1a;(1)安装 Spring Cloud Alibaba系列之nacos&#xff1a;(2)单机模式支持mysql Spring Cloud Alibaba系列之nacos&#xff1a;(3)服务注册发现 Spring Cloud 系列之OpenFeign&#xff1a;(4)集成OpenFeign Spring Cloud …

探索 JavaScript 新增声明命令与解构赋值的魅力:从 ES5 迈向 ES6

个人主页&#xff1a;学习前端的小z 个人专栏&#xff1a;JavaScript 精粹 本专栏旨在分享记录每日学习的前端知识和学习笔记的归纳总结&#xff0c;欢迎大家在评论区交流讨论&#xff01; ES5、ES6介绍 文章目录 &#x1f4af;声明命令 let、const&#x1f35f;1 let声明符&a…

【区块链】caliper压力测试

本文上接postman接口测试 参照工程项目使用Caliper测试工具对食品安全溯源系统智能合约生成新食品(newFood)功能进行压力测试 首先启动webase python3 deploy.py startAll vim /opt/bencahmark/caliper-benchmark/networks/fisco-bcos/test-nw/fisco-bcos.json 命令便捷查…

刷代码随想录有感(75):回溯问题——非递减子序列

题干&#xff1a; 代码&#xff1a; class Solution { public:vector<int> tmp;vector<vector<int>> res;void backtracking(vector<int> nums, int start){if(tmp.size() > 2){res.push_back(tmp);}unordered_set<int> uset;for(int i sta…

JMeter 基本使用【Windows Jmeter GUI 图形界面】

1.安装jmeter GUI图形界面 需要安装JDK 官方网址: Apache JMeter - Apache JMeter™ linux tgz windows zip 2. 目录及文件 bin: 核心可执行文件&#xff0c;包含配置 extras&#xff1a;插件扩展包 lib&#xff1a;核心依赖包 ext&#xff1a;核心包 junit&#xff1a;单…

低代码开发:成本革命,还是技术幻象?

在当今快速发展的数字化时代&#xff0c;企业面临着不断增长的技术需求和日益紧缩的预算压力。开源低代码开发平台&#xff08;YDUIbuilder&#xff09;应运而生&#xff0c;承诺以更低的成本和更快的速度交付应用程序。但低代码开发真的能减少成本吗&#xff1f;本文将深入探讨…

uniapp集成websocket不断线的处理-打牌记账

背景 近期在开发打牌记账微信小程序时&#xff0c;我们将房间这个业务场景做成了类似聊天室功能。 对房间内发生的动作&#xff0c;都能实时对其他人可见。 如:转账&#xff0c;离开&#xff0c;加入&#xff0c;结算等动作 其他人员都能实时接收到推送消息&#xff0c; 这个时…