博客
关于我
强烈建议你试试无所不能的chatGPT,快点击我
系统运维工程师的法宝:python paramiko
阅读量:2387 次
发布时间:2019-05-10

本文共 18458 字,大约阅读时间需要 61 分钟。

paramiko是用python语言写的一个模块,遵循SSH2协议,支持以加密和认证的方式,进行远程服务器的连接。

使用paramiko可以很好的解决以下问题:

需要使用windows客户端,

远程连接到Linux服务器,查看上面的日志状态,批量配置远程服务器,文件上传,文件下载等




#!/usr/bin/env python 

# -*- coding: utf-8 -*- 

     

import pexpect 

     

def ssh_cmd(ip, passwd, cmd): 

    ret = -1 

    ssh = 
pexpect.spawn
('ssh root@%s "%s"' % (ip, cmd)) 

    try: 

       i = 
ssh.expect
(['password:', 'continue connecting (yes/no)?'], timeout=5) 

       if i == 0 : 

          
ssh.sendline
(passwd) 

       elif i == 1: 

          ssh.sendline('yes\n') 

          ssh.expect('password: ') 

          ssh.sendline(passwd) 

          ssh.sendline(cmd) 

          r = 
ssh.read()
 

          print r 

          ret = 0 

    except pexpect.EOF: 

       print "EOF" 

       ssh.close() 

       ret = -1 

    except pexpect.TIMEOUT: 

       print "TIMEOUT" 

       
ssh.close()
 

       ret = -2 

    return ret 









#-*- coding: utf-8 -*-  

#!/usr/bin/python   

import paramiko 
 

import threading  

def ssh2(ip,username,passwd,cmd):  

    try:  

        ssh = 
paramiko.SSHClient()  

        ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())  

        
ssh.connect
(ip,22,username,passwd,timeout=5)  

        for m in cmd:  

            stdin, stdout, stderr = 
ssh.exec_command
(m)  

#           
stdin.write("Y") 
  #简单交互,输入 ‘Y’   

            out = 
stdout.readlines()  

            #屏幕输出  

            for o in out:  

                print o,  

        print '%s\tOK\n'%(ip)  

        
ssh.close()  

    except :  

        print '%s\tError\n'%(ip)  

if __name__=='__main__':  

    cmd = ['cal','echo hello!']#你要执行的命令列表  

    username = ""  #用户名  

    passwd = ""    #密码  

    threads = []   #多线程  

    print "Begin......" 

    for i in range(1,254):  

        ip = '192.168.1.'+str(i)  

        a=
threading.Thread
(target=ssh2,args=(ip,username,passwd,cmd))   

        
a.start()
 




"paramiko" is a combination of the esperanto words for "paranoid" and

"friend".  it's a module for python 2.5+ that implements the SSH2 protocol

for secure (encrypted and authenticated) connections to remote machines.

unlike SSL (aka TLS), SSH2 protocol does not require hierarchical

certificates signed by a powerful central authority. you may know SSH2 as

the protocol that replaced telnet and rsh for secure access to remote

shells, but the protocol also includes the ability to open arbitrary

channels to remote services across the encrypted tunnel (this is how sftp

works, for example).



it is written entirely in python (no C or platform-dependent code) and is

released under the GNU LGPL (lesser GPL). 



the package and its API is fairly well documented in the "doc/" folder

that should have come with this archive.





Requirements

------------



 - python 2.5 or better 

 - pycrypto 2.1 or better 



If you have setuptools, you can build and install paramiko and all its

dependencies with this command (as root)::



   easy_install ./





Portability

-----------



i code and test this library on Linux and MacOS X. for that reason, i'm

pretty sure that it works for all posix platforms, including MacOS. it

should also work on Windows, though i don't test it as frequently there.

if you run into Windows problems, send me a patch: portability is important

to me.



some python distributions don't include the utf-8 string encodings, for

reasons of space (misdirected as that is). if your distribution is

missing encodings, you'll see an error like this::



   LookupError: no codec search functions registered: can't find encoding



this means you need to copy string encodings over from a working system.

(it probably only happens on embedded systems, not normal python

installs.) Valeriy Pogrebitskiy says the best place to look is

``.../lib/python*/encodings/__init__.py``.





Bugs & Support

--------------



Please file bug reports at https://github.com/paramiko/paramiko/. There is currently no mailing list but we plan to create a new one ASAP.





Demo

----



several demo scripts come with paramiko to demonstrate how to use it.

probably the simplest demo of all is this::



   import paramiko, base64

   key = paramiko.RSAKey(data=base64.decodestring('AAA...'))

   client = paramiko.SSHClient()

   client.get_host_keys().add('ssh.example.com', 'ssh-rsa', key)

   client.connect('ssh.example.com', username='strongbad', password='thecheat')

   stdin, stdout, stderr = client.exec_command('ls')

   for line in stdout:

       print '... ' + line.strip('\n')

   client.close()



...which prints out the results of executing ``ls`` on a remote server.

(the host key 'AAA...' should of course be replaced by the actual base64

encoding of the host key.  if you skip host key verification, the

connection is not secure!)



the following example scripts (in demos/) get progressively more detailed:



:demo_simple.py:

   calls invoke_shell() and emulates a terminal/tty through which you can

   execute commands interactively on a remote server.  think of it as a

   poor man's ssh command-line client.



:demo.py:

   same as demo_simple.py, but allows you to authenticiate using a

   private key, attempts to use an SSH-agent if present, and uses the long

   form of some of the API calls.



:forward.py:

   command-line script to set up port-forwarding across an ssh transport.

   (requires python 2.3.)



:demo_sftp.py:

   opens an sftp session and does a few simple file operations.



:demo_server.py:

   an ssh server that listens on port 2200 and accepts a login for

   'robey' (password 'foo'), and pretends to be a BBS.  meant to be a

   very simple demo of writing an ssh server.



:demo_keygen.py:

   an key generator similar to openssh ssh-keygen(1) program with

   paramiko keys generation and progress functions.



Use

---



the demo scripts are probably the best example of how to use this package.

there is also a lot of documentation, generated with epydoc, in the doc/

folder.  point your browser there.  seriously, do it.  mad props to

epydoc, which actually motivated me to write more documentation than i

ever would have before.



there are also unit tests here::



   $ python ./test.py



which will verify that most of the core components are working correctly.



-、执行远程命令:

#!/usr/bin/python

#coding:utf-8

import paramiko

port =22

ssh = paramiko.SSHClient()

ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

ssh.connect("*.*.*.*",port,"username", "password")

stdin, stdout, stderr = ssh.exec_command("你的命令")

print stdout.readlines()

ssh.close()



二、上传文件到远程

#!/usr/bin/python

#coding:utf-8

import paramiko



port =22

t = paramiko.Transport(("IP",port))

t.connect(username = "username", password = "password")

sftp = paramiko.SFTPClient.from_transport(t)

remotepath='/tmp/test.txt'

localpath='/tmp/test.txt'

sftp.put(localpath,remotepath)

t.close()



三、从远程下载文件

#!/usr/bin/python

#coding:utf-8

import paramiko



port =22

t = paramiko.Transport(("IP",port))

t.connect(username = "username", password = "password")

sftp = paramiko.SFTPClient.from_transport(t)

remotepath='/tmp/test.txt'

localpath='/tmp/test.txt'

sftp.get(remotepath, localpath)

t.close()



四、执行多个命令

#!/usr/bin/python

#coding:utf-8



import sys

sys.stderr = open('/dev/null')       # Silence silly warnings from paramiko

import paramiko as pm

sys.stderr = sys.__stderr__

import os



class AllowAllKeys(pm.MissingHostKeyPolicy):

   def missing_host_key(self, client, hostname, key):

       return



HOST = '127.0.0.1'

USER = ''

PASSWORD = ''



client = pm.SSHClient()

client.load_system_host_keys()

client.load_host_keys(os.path.expanduser('~/.ssh/known_hosts'))

client.set_missing_host_key_policy(AllowAllKeys())

client.connect(HOST, username=USER, password=PASSWORD)



channel = client.invoke_shell()

stdin = channel.makefile('wb')

stdout = channel.makefile('rb')



stdin.write('''

cd tmp

ls

exit

''')

print stdout.read()



stdout.close()

stdin.close()

client.close()



五、获取多个文件

#!/usr/bin/python

#coding:utf-8



import paramiko

import os



ssh = paramiko.SSHClient()

ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

ssh.connect('localhost',username='****')  



apath = '/var/log'

apattern = '"*.log"'

rawcommand = 'find {path} -name {pattern}'

command = rawcommand.format(path=apath, pattern=apattern)

stdin, stdout, stderr = ssh.exec_command(command)

filelist = stdout.read().splitlines()



ftp = ssh.open_sftp()

for afile in filelist:

   (head, filename) = os.path.split(afile)

   print(filename)

   ftp.get(afile, './'+filename)

ftp.close()

ssh.close()

paramiko是用python语言写的一个模块,遵循SSH2协议,支持以加密和认证的方式,进行远程服务器的连接。paramiko支持Linux, Solaris, BSD, MacOS X, Windows等平台通过SSH从一个平台连接到另外一个平台。

利用该模块,可以方便的进行ssh连接和sftp协议进行sftp文件传输。


paramiko是一个基于SSH用于连接远程服务器并执行相关操作(SSHClient和SFTPClinet,即一个是远程连接,一个是上传下载服务),使用该模块可以对远程服务器进行命令或文件操作,值得一说的是,

fabric和ansible内部的远程管理就是使用的paramiko来实现。

pycrypto,由于 paramiko 模块内部依赖pycrypto,所以先下载安装pycrypto

pip3 install pycrypto
pip3 install paramiko

一、paramiko模块的安装

paramiko模块依赖PyCrypto模块,而PyCrypto需要GCC库编译,不过一般发行版的源里带有该模块。这里以centos6为例,直接借助以下命令可以直接完成安装:

yum install gcc python-crypto python-paramiko python-devel  -y 

windows版下可以安装windows版的GCC(MinGW),然后编辑安装pycrypto和paramiko ,下载安成后,直接运行python.exe setup.py build 和 python.exe setup.py install 就可以了。 

二、paramiko的连接

使用paramiko模块有两种连接方式,一种是通过paramiko.SSHClient()函数,另外一种是通过paramiko.Transport()函数。 

(1)基于用户名和密码的连接

import paramiko
 
# 创建SSH对象
ssh = paramiko.SSHClient()

# 允许连接不在know_hosts文件中的主机
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

# 连接服务器
ssh.connect(hostname='c1.salt.com', port=22, username='GSuser', password='123')

# 执行命令
stdin, stdout, stderr = ssh.exec_command('ls')

# 获取命令结果
result = stdout.read()

# 关闭连接
ssh.close()

​SSHClient 封装 Transport

import paramiko
 
transport = paramiko.Transport(('hostname', 22))

transport.connect(username='GSuser', password='123')
 
ssh = paramiko.SSHClient()

ssh._transport = transport
 
stdin, stdout, stderr = ssh.exec_command('df')

print(stdout.read())
transport.close()

(2)基于公钥秘钥连接

import paramiko

private_key = paramiko.RSAKey.from_private_key_file('/home/auto/.ssh/id_rsa')

# 创建SSH对象
ssh = paramiko.SSHClient()

# 允许连接不在know_hosts文件中的主机
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())

# 连接服务器
ssh.connect(hostname='c1.salt.com', port=22, username='wupeiqi', key=private_key)

# 执行命令
stdin, stdout, stderr = ssh.exec_command('df')
# 获取命令结果
result = stdout.read()
# 关闭连接
ssh.close()

SSHClient 封装Transport

import paramiko
 
private_key = paramiko.RSAKey.from_private_key_file('/home/auto/.ssh/id_rsa')

transport = paramiko.Transport(('hostname', 22))

transport.connect(username='wupeiqi', pkey=private_key)

ssh = paramiko.SSHClient()

ssh._transport = transport

stdin, stdout, stderr = ssh.exec_command('df')

transport.close()

SFTPClient:

用于连接远程服务器并进行上传下载功能。

(1)基于用户名密码上传下载
import paramiko
 
transport = paramiko.Transport(('hostname',22))
transport.connect(username='GSuser',password='123')
 
sftp = paramiko.SFTPClient.from_transport(transport)

# 将location.py 上传至服务器 /tmp/test.py

sftp.put('/tmp/location.py', '/tmp/test.py')

# 将remove_path 下载到本地 local_path

sftp.get('remove_path', 'local_path')
 
transport.close()

(2)基于公钥秘钥上传下载

import paramiko
 
private_key = paramiko.RSAKey.from_private_key_file('/home/auto/.ssh/id_rsa')
 
transport = paramiko.Transport(('hostname', 22))
transport.connect(username='GSuser', pkey=private_key )
 
sftp = paramiko.SFTPClient.from_transport(transport)

# 将location.py 上传至服务器 /tmp/test.py
sftp.put('/tmp/location.py', '/tmp/test.py')
# 将remove_path 下载到本地 local_path
sftp.get('remove_path', 'local_path')
 
transport.close()


下面是两种使用paramiko连接到linux服务器的代码
方式一:

ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
ssh.connect("某IP地址",22,"用户名", "口令")
上面的第二行代码的作用是允许连接不在know_hosts文件中的主机。

方式二:

t = paramiko.Transport((“主机”,”端口”))
t.connect(username = “用户名”, password = “口令”)

如果连接远程主机需要提供密钥,上面第二行代码可改成:

t.connect(username = “用户名”, password = “口令”, hostkey=”密钥”)


从widnows端下载linux服务器上的文件

#!/usr/bin/python 
import paramiko
 
t = paramiko.Transport((“主机”,”端口”))
t.connect(username = “用户名”, password = “口令”)
sftp = paramiko.SFTPClient.from_transport(t)
remotepath=’/var/log/system.log’
localpath=’/tmp/system.log’
sftp.get(remotepath, localpath)
t.close()

从widnows端上传文件到linux服务器

#!/usr/bin/python 
import paramiko

t = paramiko.Transport((“主机”,”端口”))
t.connect(username = “用户名”, password = “口令”)
sftp = paramiko.SFTPClient.from_transport(t)
remotepath=’/var/log/system.log’
localpath=’/tmp/system.log’
sftp.put(localpath,remotepath)
t.close()

windows对linux运行任意命令,并将结果输出

如果linux服务器开放了22端口,在windows端,我们可以使用paramiko远程连接到该服务器,并执行任意命令,然后通过 print或其它方式得到该结果,

#!/usr/bin/python 
import paramiko
 
ssh = paramiko.SSHClient()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
ssh.connect("某IP地址",22,"用户名", "口令")

stdin, stdout, stderr = ssh.exec_command("你的命令")
print stdout.readlines()

ssh.close() 

单个文件小传下载的示例:


import paramiko

#建立一个加密的管道
scp=paramiko.Transport(('192.168.0.102',22))

#建立连接
scp.connect(username='root',password='361way')

#建立一个sftp客户端对象,通过ssh transport操作远程文件

sftp=paramiko.SFTPClient.from_transport(scp)

#Copy a remote file (remotepath) from the SFTP server to the local host
sftp.get('/root/testfile','/tmp/361way')

#Copy a local file (localpath) to the SFTP server as remotepath
sftp.put('/root/crash-6.1.6.tar.gz','/tmp/crash-6.1.6.tar.gz')

scp.close()

一个目录下多个文件上传下载的示例:

#!/usr/bin/env python
#-*- coding: utf-8 -*-
import paramiko,datetime,os
hostname='192.168.0.102'
username='root'
password='361way'
port=22
local_dir='/tmp/getfile'
remote_dir='/tmp/abc'
try:
    t=paramiko.Transport((hostname,port))
    t.connect(username=username,password=password)
    sftp=paramiko.SFTPClient.from_transport(t)
    #files=sftp.listdir(dir_path)
    files=sftp.listdir(remote_dir)
    for f in files:
        print ''
        print '#########################################'
        print 'Beginning to download file  from %s  %s ' % (hostname,datetime.datetime.now())
        print 'Downloading file:',os.path.join(remote_dir,f)
        sftp.get(os.path.join(remote_dir,f),os.path.join(local_dir,f))#下载
        #sftp.put(os.path.join(local_dir,f),os.path.join(remote_dir,f))#上传
        print 'Download file success %s ' % datetime.datetime.now()
        print ''
        print '##########################################'
    t.close()
except Exception:
       print "connect error!" 

利用paramiko实现ssh的交互式连接

以下是通过paramiko模块直接用ssh协议登陆到远程服务器的操作代码,这里先定义一个interactive模块,代码如下:

import socket
import sys
# windows does not have termios...
try:
    import termios
    import tty
    has_termios = True
except ImportError:
    has_termios = False
def interactive_shell(chan):
    if has_termios:
        posix_shell(chan)
    else:
        windows_shell(chan)
def posix_shell(chan):
    import select
    oldtty = termios.tcgetattr(sys.stdin)
    try:
        tty.setraw(sys.stdin.fileno())
        tty.setcbreak(sys.stdin.fileno())
        chan.settimeout(0.0)
        while True:
            r, w, e = select.select([chan, sys.stdin], [], [])
            if chan in r:
                try:
                    x = chan.recv(1024)
                    if len(x) == 0:
                        print 'rn*** EOFrn',
                        break
                    sys.stdout.write(x)
                    sys.stdout.flush()
                except socket.timeout:
                    pass
            if sys.stdin in r:
                x = sys.stdin.read(1)
                if len(x) == 0:
                    break
                chan.send(x)
    finally:
        termios.tcsetattr(sys.stdin, termios.TCSADRAIN, oldtty)
# thanks to Mike Looijmans for this code
def windows_shell(chan):
    import threading
    sys.stdout.write("Line-buffered terminal emulation. Press F6 or ^Z to send EOF.rnrn")
    def writeall(sock):
        while True:
            data = sock.recv(256)
            if not data:
                sys.stdout.write('rn*** EOF ***rnrn')
                sys.stdout.flush()
                break
            sys.stdout.write(data)
            sys.stdout.flush()
    writer = threading.Thread(target=writeall, args=(chan,))
    writer.start()
    try:
        while True:
            d = sys.stdin.read(1)
            if not d:
                break
            chan.send(d)
    except EOFError:
        # user hit ^Z or F6
        pass

import paramiko
import interactive
#记录日志
paramiko.util.log_to_file('/tmp/test')
#建立ssh连接
ssh=paramiko.SSHClient()
ssh.load_system_host_keys()
ssh.set_missing_host_key_policy(paramiko.AutoAddPolicy())
ssh.connect('192.168.0.102',port=22,username='root',password='xxxxxx',compress=True)
#建立交互式shell连接
channel=ssh.invoke_shell()
#建立交互式管道
interactive.interactive_shell(channel)
#关闭连接
channel.close()
ssh.close() 

实现远程命令执行和文件上传

#!/usr/bin/env python
# -*- coding:utf-8 -*-
import paramiko
 
class SSHConnection(object):
 
    def __init__(self, host='192.168.12.68', port=22, username='locojoy',pwd='123321QQ!'):
        self.host = host
        self.port = port
        self.username = username
        self.pwd = pwd
        self.__k = None
 
    def run(self):
        self.connect()  # 连接远程服务器
        self.upload('db.py','/tmp/1.py')  # 将本地的db.py文件上传到远端服务器的/tmp/目录下并改名为1.py
        self.cmd('df')  # 执行df 命令
        self.close()    # 关闭连接
 
    def connect(self):
        transport = paramiko.Transport((self.host, self.port))
        transport.connect(username=self.username, password=self.pwd)
        self.__transport = transport
 
    def close(self):
        self.__transport.close()
 
    def upload(self,local_path,target_path):
        sftp = paramiko.SFTPClient.from_transport(self.__transport)
        sftp.put(local_path,target_path)
 
    def cmd(self, command):
        ssh = paramiko.SSHClient()
        ssh._transport = self.__transport
        # 执行命令
        stdin, stdout, stderr = ssh.exec_command(command)
        # 获取命令结果
        result = stdout.read()
        print(result)
        return result
 
obj = SSHConnection()
obj.run()


paramiko在堡垒机中的应用

简单实例:远程连接一台主机,操作命令,linux版本,输入终端为回车则发送命令。不支持tab补全功能

import paramiko, sys, os, socket, select, getpass
from paramiko.py3compat import u   # 在python3中是这样使用的,如果在Python2中则注释这行
 
# 这个程序依赖于终端,只能在Liunx下运行,windows用其他的方式
 
tran = paramiko.Transport(('192.168.12.68', 22,))
tran.start_client()
tran.auth_password('locojoy', '123321QQ!')
 
# 打开一个通道
chan = tran.open_session()
# 获取一个终端
chan.get_pty()
# 激活器
chan.invoke_shell()
 
# 原始的方法利用终端进行收发消息
# 利用sys.stdin,肆意妄为执行操作
# 用户在终端输入内容,并将内容发送至远程服务器
# 远程服务器执行命令,并将结果返回
# 用户终端显示内容
 
while True:
    # 监视用户输入和服务器返回数据
    # sys.stdin 处理用户输入
    # chan 是之前创建的通道,用于接收服务器返回信息
    # 通过select监听终端(输入输出),一旦变化,就将拿到的数据发送给服务器
    # 通过监听socket句柄,如果有变化表示服务器要给我发消息
    readable, writeable, error = select.select([chan, sys.stdin, ],[],[],1)
    # 通过select.select 监听chan(打开的通道(和远程服务器连接的状态)), sys.stdin(输入),一旦变化就写入readable
    # 当chan变化时,加入到readable,远程服务器发送内容过来
    if chan in readable:
        try:
            x = u(chan.recv(1024))  # Python3用这个
            # x = chan.recv(1024)  Python2使用这个
            if len(x) == 0:
                print('\r\n*** EOF\r\n')
                break
            sys.stdout.write(x)   # 写入缓冲区
            sys.stdout.flush()    # 刷新,将缓冲区内容显示出来
        except socket.timeout:
            pass
    # 当sys.stdin 放入readable中时,将获取到的内容发送到远程服务器
    if sys.stdin in readable:
        inp = sys.stdin.readline()
        chan.sendall(inp)
 
chan.close()
tran.close()


(2)每按一个键就发送记录,并支持tab自动补全

import paramiko, sys, os, socket, select, getpass, termios, tty
from paramiko.py3compat import u
 
tran = paramiko.Transport(('10.211.55.4', 22,))
tran.start_client()
tran.auth_password('wupeiqi', '123')
# 打开一个通道
chan = tran.open_session()
# 获取一个终端
chan.get_pty()
# 激活器
chan.invoke_shell()
 
# 获取原tty属性
oldtty = termios.tcgetattr(sys.stdin)
try:
    # 为tty设置新属性
    # 默认当前tty设备属性:
    #   输入一行回车,执行
    #   CTRL+C 进程退出,遇到特殊字符,特殊处理。
    # 这是为原始模式,不认识所有特殊符号
    # 放置特殊字符应用在当前终端,如此设置,将所有的用户输入均发送到远程服务器
    tty.setraw(sys.stdin.fileno())  # 恢复终端原始状态,每按一个键就发送
    chan.settimeout(0.0)
 
    while True:
        # 监视 用户输入 和 远程服务器返回数据(socket)
        # 阻塞,直到句柄可读
        r, w, e = select.select([chan, sys.stdin], [], [], 1)
        if chan in r:  # 获取服务返回的内容
            try:
                x = u(chan.recv(1024))
                if len(x) == 0:
                    print('\r\n*** EOF\r\n')
                    break
                sys.stdout.write(x)
                sys.stdout.flush()
            except socket.timeout:
                pass
        if sys.stdin in r: # 发送命令
            x = sys.stdin.read(1) # 读取一个字符
            if len(x) == 0:
                break
            chan.send(x) # 发送一个字符
 
finally:
    # 重新设置终端属性,将终端状态还原
    termios.tcsetattr(sys.stdin, termios.TCSADRAIN, oldtty)
 
chan.close()
tran.close()

转载地址:http://vlsab.baihongyu.com/

你可能感兴趣的文章
php获取中文字符串的首字符拼音字母
查看>>
php curl通过代理获取数据
查看>>
6 个 Linux性能监控命令行工具
查看>>
mysql 编码字符集配置
查看>>
php查看opcode编码的扩展 opdumper
查看>>
php转换html格式为文本格式
查看>>
mysql-proxy主从服务架构下读写分离和负载均衡实现及原理
查看>>
Nginx location 和 rewrite retry
查看>>
基于nginx的FastCGI的缓存配置
查看>>
Nginx模块fastcgi_cache的几个注意点
查看>>
PHP使用curl伪造IP地址和header信息
查看>>
代理服务器中的HTTP代理与SOCKS代理有什么区别?
查看>>
零基础Python学习路线,小白的进阶之路!
查看>>
CSS的23个垂直居中技巧,你都学会了吗?
查看>>
黑客攻击用的最短代码大揭秘,颠覆你的世界观!
查看>>
零基础的自学前端之路,当年的入坑之旅
查看>>
新手程序员?教你解决办法!基础都掌握了,动手敲代码就一脸懵逼
查看>>
程序员快速进阶学习到底要看书还是要看视频?
查看>>
web游戏框架哪家强?国内外精选优质框架分析及注意事项
查看>>
各行业都爱用什么编程语言开发?
查看>>