Saltstack的syndic、salt-ssh模块、api调用

saltstack的salt-ssh模块的调用

说明,在minion关闭的情况下通过认证,查找信息

[root@server9 ~]# /etc/init.d/salt-minion stop
Stopping salt-minion:root:server9 daemon: OK

[root@server7 ~]yum install salt-ssh -y
[root@server7 ~]# vim /etc/salt/roster 
server9:
  host: 172.25.23.9
  user: root
  passwd: westos123
[root@server7 ~]# salt-ssh 'server9' test.ping -i 
server9:
    True

[root@server7 ~]# salt-ssh 'server9' my_disk.df
server9:
    Filesystem                    Size  Used Avail Use% Mounted on
    /dev/mapper/VolGroup-lv_root   19G  1.1G   17G   6% /
    tmpfs                         499M   32K  499M   1% /dev/shm
    /dev/vda1                     485M   33M  427M   8% /boot
[root@server7 ~]# 

这里写图片描述

syndic的使用

工作原理图
这里写图片描述
syndic的意思为理事,其实如果叫salt-proxy的话那就更好理解了,它就是一层代理,如同zabbix proxy功能一样,隔离master与minion,使其不需要通讯,只需要与syndic都通讯就可以,这样的话就可以在跨机房的时候将架构清晰部署了。
首先两个虚拟机:
172.25.23.7 master syndic
172.25.23.9:top master
安装服务

[root@server7 _modules]# yum install syndic
[root@server7 _modules]# vim /etc/salt/salt-master
[root@server10 ~]# yum install salt-master -y

之前10作为server7的minion,这里我们关闭10的salt-minion,同时删除server10的钥匙
[root@server7 _modules]# /etc/init.d/salt-master restart
Stopping salt-master daemon:                               [  OK  ]
Starting salt-master daemon:                               [  OK  ]
[root@server7 _modules]# salt-key -L
Accepted Keys:
server10
server7
server8
server9
Denied Keys:
Unaccepted Keys:
Rejected Keys:

删除server10的钥匙,这里如果是新的虚拟机,则不用执行

[root@server7 _modules]# salt-key -d 172.25.23.10
The key glob '172.25.23.10' does not match any unaccepted keys.
[root@server7 _modules]# salt-key -d server10
The following keys are going to be deleted:
Accepted Keys:
server10
Proceed? [N/y] y
Key for minion server10 deleteed.
[root@server7 _modules]# salt-key -L
Accepted Keys:
server7
server8
server9
Denied Keys:
Unaccepted Keys:
Rejected Keys:

这里写图片描述
这里写图片描述

[root@server7 _modules]# /etc/init.d/salt-syndic start
Starting salt-syndic daemon:                               [  OK  ]
[root@server7 _modules]# salt-key -L
Accepted Keys:
server7
server8
server9
Denied Keys:
Unaccepted Keys:
Rejected Keys:

server10:
安装topmaster服务

将之前所有服务都停掉
[root@server10 ~]# yum install salt-master -y
[root@server10 ~]# vim /etc/salt/master
order_masters: True
[root@server10 ~]# /etc/init.d/salt-master restart

添加server7的钥匙

[root@server10 ~]# salt-key -L
Accepted Keys:
Denied Keys:
Unaccepted Keys:
Rejected Keys:
[root@server10 ~]# salt-key -A
The following keys are going to be accepted:
Unaccepted Keys:
server7
Proceed? [n/Y] y
Key for minion server7 accepted.
[root@server10 ~]# salt-key -L
Accepted Keys:
server7
Denied Keys:
Unaccepted Keys:
Rejected Keys:
[root@server10 ~]# salt-key -L
Accepted Keys:
server7
Denied Keys:
Unaccepted Keys:
Rejected Keys:

这里写图片描述
测试:显示只有server7一个,但是执行指令却出现全部服务器,这里的server7相当于代理,传达topmaster的指令。

[root@server10 ~]# salt '*' test.ping
server7:
    True
server9:
    True
server8:
    True
[root@server10 ~]# salt-key -L
Accepted Keys:
server7
Denied Keys:
Unaccepted Keys:
Rejected Keys:

这里写图片描述

saltstack的api模块的调用

[root@server9 ~]# /etc/init.d/nginx stop
Stopping nginx:   
[root@server9 ~]# /etc/init.d/salt.minion start  
[root@server7 pki]# cd /etc/pki/
[root@server7 pki]# cd tls/
[root@server7 tls]# ls
cert.pem  certs  misc  openssl.cnf  private
[root@server7 tls]# cd private/
[root@server7 private]# ls
[root@server7 private]# openssl genrsa 1024 > localhost.key
Generating RSA private key, 1024 bit long modulus
.............++++++
.............................++++++
e is 65537 (0x10001)

这里写图片描述

[root@server7 private]# cd ..
[root@server7 tls]# cd cert
cert.pem  certs/    
[root@server7 tls]# cd cert
cert.pem  certs/    
[root@server7 tls]# cd certs/
[root@server7 certs]# make testcert
umask 77 ; \
    /usr/bin/openssl req -utf8 -new -key /etc/pki/tls/private/localhost.key -x509 -days 365 -out /etc/pki/tls/certs/localhost.crt -set_serial 0
You are about to be asked to enter information that will be incorporated
into your certificate request.
What you are about to enter is what is called a Distinguished Name or a DN.
There are quite a few fields but you can leave some blank
For some fields there will be a default value,
If you enter '.', the field will be left blank.
-----
Country Name (2 letter code) [XX]:cn
State or Province Name (full name) []:shaanxi
Locality Name (eg, city) [Default City]:xi'an
Organization Name (eg, company) [Default Company Ltd]:westos
Organizational Unit Name (eg, section) []:linux
Common Name (eg, your name or your server's hostname) []:server9
Email Address []:root@localhost
[root@server7 certs]# ll localhost.crt
-rw-------. 1 root root 1029 Aug 18 17:25 localhost.crt
[root@server7 certs]# pwd
/etc/pki/tls/certs

这里写图片描述

[root@server7 certs]# cd /etc/salt/master.d
[root@server7 master.d]# vim api.conf
rest_cherrypy:
  port: 8000
  ssl_crt: /etc/pki/tls/certs/localhost.crt
  ssl_key: /etc/pki/tls/private/localhost.key

[root@server7 master.d]# vim auth.conf
external_auth:
  pam:
    saltapi:
      - '.*'
      - '@wheel'
      - '@runner'
      - '@jobs'
~                 
[root@server7 master.d]# 
[root@server7 master.d]# useradd saltapi
[root@server7 master.d]# passwd saltapi
Changing password for user saltapi.
New password: 
BAD PASSWORD: it is based on a dictionary word
BAD PASSWORD: is too simple
Retype new password: 
passwd: all authentication tokens updated successfully.
[root@server7 master.d]# /etc/init.d/salt-master stop
Stopping salt-master daemon:                               [  OK  ]
[root@server7 master.d]# /etc/init.d/salt-master start
Starting salt-master daemon:                               [  OK  ]
[root@server7 master.d]# /etc/init.d/salt-api srestart
Usage: /etc/init.d/salt-api {start|stop|status|restart|condrestart|try-restart|reload}
[root@server7 master.d]# /etc/init.d/salt-api restart
Stopping salt-api daemon:                                  [  OK  ]
Starting salt-api daemon:                                  [  OK  ]

这里写图片描述
这里写图片描述
这里写图片描述

[root@server7 master.d]# curl -sSk https://localhost:8000/login -H 'Accept: application/x-yaml' -d username=saltapi -d password=westos -d eauth=pam
return:
- eauth: pam
  expire: 1534629628.940074
  perms:
  - .*
  - '@wheel'
  - '@runner'
  - '@jobs'
  start: 1534586428.940073
  token: fbb25045e501ec18cdc67c7bd779722cd5c358ad
  user: saltapi

这里写图片描述


[root@server7 master.d]# curl -sSk https://localhost:8000 -H 'Accept: application/x-yaml' -H 'X-Auth-Token: fbb25045e501ec18cdc67c7bd779722cd5c358ad' -d client=local -d tgt='*' -d fun=test.ping
return:
- server7: true
  server8: true
  server9: true

这里写图片描述

[root@server7 ~]# vim saltapi.py 

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

import urllib2,urllib
import time

try:
    import json
except ImportError:
    import simplejson as json

class SaltAPI(object):
    __token_id = ''
    def __init__(self,url,username,password):
        self.__url = url.rstrip('/')
        self.__user = username
        self.__password = password
    def token_id(self):
        ''' user login and get token id '''
        params = {'eauth': 'pam', 'username': self.__user, 'password': self.__password}
        encode = urllib.urlencode(params)
        obj = urllib.unquote(encode)
        content = self.postRequest(obj,prefix='/login')
    try:
            self.__token_id = content['return'][0]['token']
        except KeyError:
            raise KeyError

    def postRequest(self,obj,prefix='/'):
        url = self.__url + prefix
        headers = {'X-Auth-Token'   : self.__token_id}
        req = urllib2.Request(url, obj, headers)
        opener = urllib2.urlopen(req)
        content = json.loads(opener.read())
        return content

    def list_all_key(self):
        params = {'client': 'wheel', 'fun': 'key.list_all'}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        minions = content['return'][0]['data']['return']['minions']
        minions_pre = content['return'][0]['data']['return']['minions_pre']
        return minions,minions_pre

    def delete_key(self,node_name):
        params = {'client': 'wheel', 'fun': 'key.delete', 'match': node_name}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        ret = content['return'][0]['data']['success']
        return ret

    def accept_key(self,node_name):
        params = {'client': 'wheel', 'fun': 'key.accept', 'match': node_name}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        ret = content['return'][0]['data']['success']
        return ret

    def remote_noarg_execution(self,tgt,fun):
        ''' Execute commands without parameters '''
        params = {'client': 'local', 'tgt': tgt, 'fun': fun}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        ret = content['return'][0][tgt]
        return ret

    def remote_execution(self,tgt,fun,arg):
        ''' Command execution with parameters '''        
        params = {'client': 'local', 'tgt': tgt, 'fun': fun, 'arg': arg}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        ret = content['return'][0][tgt]
        return ret

    def target_remote_execution(self,tgt,fun,arg):
        ''' Use targeting for remote execution '''
        params = {'client': 'local', 'tgt': tgt, 'fun': fun, 'arg': arg, 'expr_form': 'nodegroup'}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        jid = content['return'][0]['jid']
        return jid

    def deploy(self,tgt,arg):
        ''' Module deployment '''
        params = {'client': 'local', 'tgt': tgt, 'fun': 'state.sls', 'arg': arg}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        return content

    def async_deploy(self,tgt,arg):
        ''' Asynchronously send a command to connected minions '''
        params = {'client': 'local_async', 'tgt': tgt, 'fun': 'state.sls', 'arg': arg}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        jid = content['return'][0]['jid']
        return jid

    def target_deploy(self,tgt,arg):
        ''' Based on the node group forms deployment '''
        params = {'client': 'local_async', 'tgt': tgt, 'fun': 'state.sls', 'arg': arg, 'expr_form': 'nodegroup'}
        obj = urllib.urlencode(params)
        self.token_id()
        content = self.postRequest(obj)
        jid = content['return'][0]['jid']
        return jid

def main():
    sapi = SaltAPI(url='https://172.25.0.3:8000',username='saltapi',password='westos')
    sapi.token_id()
    print sapi.list_all_key()
    #sapi.delete_key('test-01')
    #sapi.accept_key('test-01')
    sapi.deploy('*','httpd.apache')
    #print sapi.remote_noarg_execution('test-01','grains.items')

if __name__ == '__main__':
    main()
[root@server7 ~]# python saltapi.py 

测试:
server9:nginx的状态自动开启
这里写图片描述

猜你喜欢

转载自blog.csdn.net/ningyuxuan123/article/details/81812017