参考引用
https://github.com/hierynomus/smbj
fileAttributes,包含文件属性掩码
https://learn.microsoft.com/en-us/openspecs/windows_protocols/ms-fscc/ca28ec38-f155-4768-81d6-4bfeb8586fc9
使用
maven
1 2 3 4 5
| <dependency> <groupId>com.hierynomus</groupId> <artifactId>smbj</artifactId> <version>0.11.5</version> </dependency>
|
SMB 关于 Windows 的共享文件夹
如果开启了密码保护需要提供账户和密码
计算机处于睡眠状态时无法访问共享目录
如果为 EveryOne 开启了访问权限,即使不存在的账户,也可以访问,此时密码应该被忽略
如果账户是系统存在的,则会进行密码认证,失败则不通过。
获得一个 SMBClient
无参构造器:
1
| SMBClient client = new SMBClient();
|
自定义配置:
1 2 3 4 5
| SmbConfig config = SmbConfig.builder() .withTimeout(120, TimeUnit.SECONDS) .withSoTimeout(180, TimeUnit.SECONDS) .build(); SMBClient client = new SMBClient(config);
|
获得一个 Connection
1 2 3 4 5 6 7
| try (Connection connection = client.connect("127.0.0.1")) {
} catch (IOException e) { throw new RuntimeException(e.getMessage(), e); }
|
获得一个 Session
获得一个会话示例代码:
1 2
| Session session = connection.authenticate( new AuthenticationContext("USERNAME", "PASSWORD".toCharArray(), null));
|
获得 DiskShare
1 2 3 4 5 6
| try (DiskShare share = (DiskShare) session.connectShare("shareDirectory")) { for (FileIdBothDirectoryInformation f : share.list("data", "*.csv")) { System.out.println("File : " + f.getFileName()); } }
|
整体 Demo
获得共享名称为 shareDir 下的所有文件名信息,并输出:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17
|
try (SMBClient client = new SMBClient(); Connection connection = client.connect("127.0.0.1"); Session session = connection.authenticate(new AuthenticationContext("USERNAME", "PASSWORD".toCharArray(), null)); DiskShare share = (DiskShare) session.connectShare("shareDir")) { for (FileIdBothDirectoryInformation f : share.list("", "*.csv")) { System.out.println("File : " + f.getFileName()); } } catch (Exception e) { throw new RuntimeException(e); }
|
1 2 3 4 5 6 7
| File smbFileRead = dirShare.openFile( fileName, EnumSet.of(AccessMask.GENERIC_READ), null, SMB2ShareAccess.ALL, SMB2CreateDisposition.FILE_OPEN, null);
|
SMB2CreateDisposition: 如果传递 FILE_OPEN
,那么文件找不到的情况下会抛出异常;如果设置为 FILE_OPEN_IF
,那么文件找不到的情况下会静默继续
就是直接在远程机器上将一个文件拷贝到另一个文件
1 2 3 4 5 6 7 8 9 10
| this.ensureDirectoryExists(diskShare, dir); com.hierynomus.smbj.share.File backupShareFile = diskShare.openFile( "copy-directory\\" + filename, EnumSet.of(AccessMask.GENERIC_ALL), null, SMB2ShareAccess.ALL, SMB2CreateDisposition.FILE_CREATE, null); smbFile.remoteCopyTo(backupShareFile);
|
1 2 3 4 5
| boolean isDirectory = (f.getFileAttributes() & 0x10) == 0x10;
boolean directory = shareFile.getFileInformation().getStandardInformation().isDirectory();
|
案例
将共享文件夹 \\127.0.0.1\shareDirectory
下的所有文件都转移到 \\127.0.0.1\shareDirectory\backup
文件夹下
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34
| public static void transferAllFiles(String path) { try (SMBClient client = new SMBClient(); Connection connection = client.connect("127.0.0.1"); Session session = connection.authenticate(new AuthenticationContext("USERNAME", "PASSWORD".toCharArray(), null)); DiskShare share = (DiskShare) session.connectShare("shareDirectory")) { List<FileIdBothDirectoryInformation> fileIdBothDirectoryInformationList = share.list(path, "*"); fileIdBothDirectoryInformationList = fileIdBothDirectoryInformationList.stream().filter(fileIdBothDirectoryInformation -> { return (fileIdBothDirectoryInformation.getFileAttributes() & 0x10) == 0; }).collect(Collectors.toList());
for (FileIdBothDirectoryInformation f : fileIdBothDirectoryInformationList) { com.hierynomus.smbj.share.File shareFile = share.openFile( path + "\\" + f.getFileName(), EnumSet.of(AccessMask.GENERIC_ALL), null, SMB2ShareAccess.ALL, SMB2CreateDisposition.FILE_OPEN, null); com.hierynomus.smbj.share.File backupShareFile = share.openFile( path + "\\backup\\" + f.getFileName(), EnumSet.of(AccessMask.GENERIC_ALL), null, SMB2ShareAccess.ALL, SMB2CreateDisposition.FILE_CREATE, null); shareFile.remoteCopyTo(backupShareFile); shareFile.deleteOnClose(); } } catch (Exception e) { throw new RuntimeException(e); } }
|