我可以访问一些有大量数据的服务器。我无法在计算机上复制整个数据。
我无法在服务器上编译我想要的程序,因为服务器没有我需要的所有库。
我认为服务器管理员不会很高兴看到我来找他并为他安装一些库...
所以,我试着想办法是否有办法打开像
这样的文件FILE *fopen(const char *filename, const char *mode);
或
void std::ifstream::open(const char* filename, ios_base::openmode mode = ios_base::in);
但通过SSH连接。然后像平常程序那样读取文件。
计算机和服务器都在运行linux
答案 0 :(得分:3)
我假设你正在使用你的Linux笔记本电脑而远程机器是一台超级计算机。
首先是非技术性建议:首先请求权限远程访问数据。在某些工作场所,即使技术上可行,也不允许这样做。
您可以为此目的使用libssh,但是您需要一些编码并阅读其文档。
你可以考虑使用一些FUSE文件系统(在你的笔记本电脑上),例如:一些sshfs
;然后,您就可以访问一些超级计算机文件/sshfilesystem/foo.bar
)。它可能是最慢的解决方案,可能不是一个非常可靠的解决方案。我不是真的推荐它。
您可以请求使用NFS坐骑的权限。
使用某些HTTP / HTTPS客户端库(如HTTPS(或者反过来,某些HTTP / HTTPS服务器),也许您可能会考虑使用某些libcurl访问权限(如果远程计算机将其用于您的文件)库像libonion)
你可能(但首先请求权限!)使用一些TLS连接(例如,手动启动远程超级计算机上的程序之类的服务器)或许通过OpenSSL或libgnutls
最后,您应该考虑安装(即礼貌地询问远程超级计算机上的安装)或使用某些database软件(例如PostgreSQL或MariaDB或Redis或远程计算机上的MongoDB服务器),使您的程序成为数据库客户端应用程序......
顺便说一下,如果您在随机访问中访问几十个TB级文件(每个内部读取几千字节)或一百万个文件,其中一个给定的运行只能访问十几个文件,情况可能会有所不同顺序读取,每个文件的大小合理(几兆字节)。换句话说,DNA数据,视频电影,HTML文档,源代码......都是不同的情况!答案 1 :(得分:1)
好吧,你的问题的答案是 no ,正如已经多次说过的那样(除非你考虑自己实施 ssh ,这超出了理智范围)。 / p>
但是,当你还描述你的真正的问题时,它可能只是提出错误的问题,所以 - 寻找替代方案:
将要使用静态的库链接到二进制文件。假设您要静态链接 libfoo :
确保您的图书馆搜索路径中有libfoo.a
(图书馆的对象存档)。通常,您的发行版提供的库的开发包已包含它,如果没有,请自行编译库以使用选项来启用静态库的创建
假设使用GNU工具链,使用以下标志构建程序:-Wl,-Bstatic -lfoo -Wl,-Bdynamic
(而不仅仅是-lfoo
)
像往常一样创建二进制文件(链接到动态库)并放置该库(libfoo.so
),例如在服务器上的~/lib
中。然后使用LD_LIBRARY_PATH=~/lib ./a.out
运行您的二进制文件。
答案 2 :(得分:1)
您可以通过SSH连接将部分文件复制到您的计算机:
dd
命令将源文件的一部分复制到临时文件scp
或rsync
如果需要多次执行此操作,可以创建一个shell脚本来自动执行此操作。
答案 3 :(得分:1)
而不是路径上的fopen
,您可以在ssh命令上使用popen
。 (不要忘记从FILE *
获得的popen
流已被pclose
而不是fclose
关闭。
您可以通过编写包裹popen
的函数来简化界面。该函数只接受远程文件名,然后生成ssh
命令以获取该文件,正确转义所有内容,如文件名中的空格,shell元字符等等。
FILE *stream = popen("ssh user@host cat /path/to/remote/file", "r");
if (stream != 0) {
/* ... */
pclose(stream);
}
popen
有一些缺点,因为它处理shell命令。因为ssh
的参数也是在远程端处理的shell命令,所以会引发双重转义问题:将命令作为shell命令传递。
要执行更强大的功能,您可以使用pipe
创建管道,然后fork
和exec*
ssh
进程创建管道,安装管道的写入端作为其stdout,并使用fdopen
在父进程中管道的读取端创建FILE *
流。通过这种方式,可以准确控制传递给进程的参数:至少在本地,您没有运行shell命令。
答案 4 :(得分:0)
你不能直接(1)用fopen()或ifstream :: open在ssh上打开文件。但您可以利用现有的ssh
二进制文件。只需从stdin读取程序,然后通过ssh将文件传递给它:
ssh that_server cat /path/to/largefile | ./yourprogram
(1)好吧,如果使用sshfs挂载远程系统,则可以通过ssh访问文件,就像它们是本地文件一样。