@@ -0,0 +1,2841 @@
+# -*- coding: utf-8 -*-%0A%22%22%22%0APass Renderer for Salt%0A%0A%5Bpass%5D(https://www.passwordstore.org/)%0A%0A# Setup%0A__Note__: %60%3Cuser%3E%60 needs to be replaced with the user salt-master will be%0Arunning as%0A%0A1. Have private gpg loaded into %60user%60's gpg keyring%0A   * Example salt code%0A        %60%60%60%0A        load_private_gpg_key:%0A          cmd.run:%0A            - name: gpg --import %3Clocation_of_private_gpg_key%3E%0A            - unless: gpg --list-keys '%3Cgpg_name%3E'%0A        %60%60%60%0A1. Said private key's public key should have been used when encrypting pass%0Aentries that are of interest for pillar data%0A1. Fetch and keep local pass git repo up-to-date%0A   * Example salt code%0A        %60%60%60%0A        update_pass:%0A          git.latest:%0A            - force_reset: True%0A            - name: %3Cgit_repo%3E%0A            - target: /%3Cuser%3E/.password-store%0A            - identity: %3Clocation_of_ssh_private_key%3E%0A            - require:%0A              - cmd: load_private_gpg_key%0A        %60%60%60%0A1. Install pass binary%0A   * Example salt code%0A        %60%60%60%0A        pass:%0A          pkg.installed%0A        %60%60%60%0A%22%22%22%0A%0A# Import python libs%0Afrom __future__ import absolute_import%0Aimport logging%0Aimport os%0Afrom os.path import expanduser%0Afrom subprocess import Popen, PIPE%0A%0A# Import salt libs%0Aimport salt.utils%0Afrom salt.exceptions import SaltRenderError%0A%0A# Import 3rd-party libs%0Aimport salt.ext.six as six%0A%0Alog = logging.getLogger(__name__)%0A%0A%0Adef _get_pass_exec():%0A    %22%22%22%0A    Return the pass executable or raise an error%0A    %22%22%22%0A    pass_exec = salt.utils.which('pass')%0A    if pass_exec:%0A        return pass_exec%0A    else:%0A        raise SaltRenderError('pass unavailable')%0A%0A%0Adef _fetch_secret(pass_path):%0A    %22%22%22%0A    Fetch secret from pass based on pass_path. If there is%0A    any error, return back the original pass_path value%0A    %22%22%22%0A    cmd = %22pass show %7B0%7D%22.format(pass_path.strip('%5Cn'))%0A    log.debug('Fetching secret: %7B0%7D'.format(cmd))%0A%0A    proc = Popen(cmd.split(' '), stdout=PIPE, stderr=PIPE)%0A    pass_data, pass_error = proc.communicate()%0A%0A    # The version of pass used during development sent output to%0A    # stdout instead of stderr even though its returncode was non zero.%0A    if proc.returncode or not pass_data:%0A        msg = 'Could not fetch secret: %7B0%7D %7B1%7D'.format(pass_data, pass_error)%0A        log.warn(msg)%0A        pass_data = pass_path%0A%0A    return pass_data%0A%0A%0Adef render(pass_info, saltenv='base', sls='', argline='', **kwargs):%0A    %22%22%22%0A    Fetch secret from pass based on pass_path%0A    %22%22%22%0A    try:%0A        _get_pass_exec()%0A    except SaltRenderError:%0A        raise%0A%0A    # Make sure environment variable HOME is set, since Pass looks for the%0A    # password-store under ~/.password-store.%0A    os.environ%5B'HOME'%5D = expanduser('~')%0A%0A    for pass_key, pass_path in six.iteritems(pass_info):%0A        secret = _fetch_secret(pass_path)%0A        pass_info%5Bpass_key%5D = secret%0A%0A    return pass_info%0A

Create pass renderer