Skip to content

Commit

Permalink
Add manifest export
Browse files Browse the repository at this point in the history
  • Loading branch information
ggatward committed Dec 19, 2016
1 parent fb2adcf commit 730d80d
Show file tree
Hide file tree
Showing 7 changed files with 193 additions and 0 deletions.
9 changes: 9 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -49,6 +49,7 @@ satellite:
username: svc-api-user
password: 1t$a$3cr3t
disconnected: [True|False] (Is direct internet connection available?)
manifest: my-satellite (Red Hat Portal satellite application name)
default_org: MyOrg (Default org to use - can be overridden with -o)
logging:
Expand Down Expand Up @@ -77,6 +78,14 @@ tasks that have stopped but been marked as Incomplete.
Running with the -l flag will loop the check until terminated with CTRL-C


# download_manifest
Script originally written by Rich Jerrido downloads subscription manifest from
Red Hat portal. Need to provide a username (-l) with access to download the
manifest. Manifest name is configured in config.yml, but can be overridden on the
command line with the (-s) option. Manifest is downloaded to the the configured
export directory, and included in the bundle generated by sat_export.


# sat_export
Intended to perform content export from a Connected Satellite (Sync Host), for
transfer into a disconnected environment. The Default Organization View (DOV)
Expand Down
12 changes: 12 additions & 0 deletions bin/download_manifest
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
#!/usr/bin/python
import sys

#sys.path.insert(0, '/usr/share/sat6_scripts')
sys.path.insert(0, '/usr/local/bin/sat6_scripts')
try:
import download_manifest
download_manifest.main(sys.argv[1:])
except KeyboardInterrupt, e:
print >> sys.stderr, "\n\nExiting on user cancel."
sys.exit(1)

1 change: 1 addition & 0 deletions config/config.yml.example
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ satellite:
username: svc-api-user
password: 1t$a$3cr3t
default_org: MyOrg
manifest: my-satellite
disconnected: False

logging:
Expand Down
152 changes: 152 additions & 0 deletions download_manifest.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,152 @@
#!/usr/bin/env python

# File: rhsmDownloadManifest.py
# Author: Rich Jerrido <[email protected]>
# Purpose: Given a username, password &
# Subscription Management Application,
# Download its manifest
#
# This program is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, version 2 of the License.
#
# This program is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.

import json
import getpass
import urllib2
import base64
import sys
import ssl
import datetime
from optparse import OptionParser
# ggatward: Additional imports for sat6_scripts integration
import helpers
import os, shutil

parser = OptionParser()
parser.add_option("-l", "--login", dest="login", help="Login user for RHSM", metavar="LOGIN")
parser.add_option("-p", "--password", dest="password", help="Password for specified user. Will prompt if omitted",
metavar="PASSWORD")
parser.add_option("-d", "--debug", dest='debug', help="print more details for debugging", default=False,
action='store_true')
parser.add_option("-s", "--subscription-management-app", dest='sma',
help="Which Subscription Management Application to download manifests from", metavar="SMA")
parser.add_option("--host", dest='portal_host', help="RHSM host to use (Default subscription.rhn.redhat.com)",
default="subscription.rhn.redhat.com")
(options, args) = parser.parse_args()

if not (options.login):
print "Must specify a login (will prompt for password if omitted). See usage:"
parser.print_help()
print "\nExample usage: ./rhsmDownloadManifest.py -l rh_user_account -s My_Satellite"
sys.exit(1)
else:
login = options.login
password = options.password
portal_host = options.portal_host

if options.sma:
sma = options.sma
else:
sma = helpers.MANIFEST

if not password:
password = getpass.getpass("%s's password:" % login)

if hasattr(ssl, '_create_unverified_context'):
ssl._create_default_https_context = ssl._create_unverified_context

# ggatward: Change timestamp format
timestamp = datetime.datetime.now().strftime("%Y%m%d")

# ggatward: Use existing sat-export directory structure
# Remove any existing manifests so we only grab the current one
EXPORTDIR = helpers.EXPORTDIR + '/manifest'
if os.path.exists(EXPORTDIR):
shutil.rmtree(helpers.EXPORTDIR + '/manifest')
os.makedirs(EXPORTDIR)
else:
os.makedirs(EXPORTDIR)

# Grab the Candlepin account number
url = "https://" + portal_host + "/subscription/users/" + login + "/owners/"
try:
if options.debug:
print "Attempting to connect: " + url
request = urllib2.Request(url)
base64string = base64.encodestring('%s:%s' % (login, password)).strip()
request.add_header("Authorization", "Basic %s" % base64string)
result = urllib2.urlopen(request)
except urllib2.HTTPError, e:
print "Error: cannot connect to the API due to HTTP Error: %s" % e.code
sys.exit(1)
except urllib2.URLError, e:
print "Error: cannot connect to the API: %s" % e
print "Check your URL & try to login using the same user/pass via the WebUI and check the error!"
sys.exit(1)

accountdata = json.load(result)
for accounts in accountdata:
acct = accounts["key"]

# Grab a list of Consumers
url = "https://" + portal_host + "/subscription/owners/" + acct + "/consumers/"

try:
if options.debug:
print "Attempting to connect: " + url
request = urllib2.Request(url)
base64string = base64.encodestring('%s:%s' % (login, password)).strip()
request.add_header("Authorization", "Basic %s" % base64string)
result = urllib2.urlopen(request)
except urllib2.HTTPError, e:
print "Error: cannot connect to the API due to HTTP Error: %s" % e.code
sys.exit(1)
except urllib2.URLError, e:
print "Error: cannot connect to the API: %s" % e
print "Check your URL & try to login using the same user/pass via the WebUI and check the error!"
sys.exit(1)

consumerdata = json.load(result)

# Now that we have a list of Consumers, loop through them and
# see if one matches our

for consumer in consumerdata:
consumerType = consumer["type"]["label"]
uuid = consumer["uuid"]
consumerName = consumer["name"]
if consumerType in ['satellite', 'sam']:
if sma == consumerName:
url = "https://" + portal_host + "/subscription/consumers/" + uuid + "/export/"
if options.debug:
print "\tAttempting to connect: " + url
print "\tSubscription Management Application %s matches parameters. Exporting..." % sma
try:
request = urllib2.Request(url)
base64string = base64.encodestring('%s:%s' % (login, password)).strip()
request.add_header("Authorization", "Basic %s" % base64string)
result = urllib2.urlopen(request)
# ggatward: Updated export location and name formatting
manifest_file = EXPORTDIR + "/manifest_%s_%s.zip" % (consumerName, timestamp)
if options.debug:
print "\tWriting Manifest to %s" % manifest_file
with open(manifest_file, "wb") as manifest:
manifest.write(result.read())
sys.exit(0)
except urllib2.HTTPError, e:
print "Error: cannot connect to the API due to HTTP Error: %s" % e.code
sys.exit(1)
except urllib2.URLError, e:
print "Error: cannot connect to the API: %s" % e
print "Check your URL & try to login using the same user/pass via the WebUI and check the error!"
sys.exit(1)

print "The Subscription Management Application %s could not be found" % sma
print "Reminder: names are case-sensitive"
sys.exit(0)

1 change: 1 addition & 0 deletions helpers.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@
USERNAME = CONFIG["satellite"]["username"]
PASSWORD = CONFIG["satellite"]["password"]
DISCONNECTED = CONFIG["satellite"]["disconnected"]
MANIFEST = CONFIG["satellite"]["manifest"]
ORG_NAME = CONFIG["satellite"]["default_org"]
LOGDIR = CONFIG["logging"]["dir"]
DEBUG = CONFIG["logging"]["debug"]
Expand Down
2 changes: 2 additions & 0 deletions sat6_scripts.spec
Original file line number Diff line number Diff line change
Expand Up @@ -41,6 +41,7 @@ install -m 0644 sat_import.py %{buildroot}/usr/share/sat6_scripts/sat_import.py
install -m 0644 publish_content_views.py %{buildroot}/usr/share/sat6_scripts/publish_content_views.py
install -m 0644 promote_content_views.py %{buildroot}/usr/share/sat6_scripts/promote_content_views.py
install -m 0644 clean_content_views.py %{buildroot}/usr/share/sat6_scripts/clean_content_views.py
install -m 0644 download_manifest.py %{buildroot}/usr/share/sat6_scripts/download_manifest.py



Expand All @@ -57,6 +58,7 @@ install -m 0644 clean_content_views.py %{buildroot}/usr/share/sat6_scripts/clean
/usr/share/sat6_scripts/publish_content_views.py
/usr/share/sat6_scripts/promote_content_views.py
/usr/share/sat6_scripts/clean_content_views.py
/usr/share/sat6_scripts/download_manifest.py

/usr/local/bin/check_sync
/usr/local/bin/sat_export
Expand Down
16 changes: 16 additions & 0 deletions sat_export.py
Original file line number Diff line number Diff line change
Expand Up @@ -285,6 +285,19 @@ def export_puppet(repo_id, repo_label, repo_relative, last_export, export_type,
return numfiles


def export_manifest():
"""
Copies manifest downloaded by 'download_manifest.py' into the export bundle
"""
if os.path.exists(helpers.EXPORTDIR + '/manifest'):
msg = 'Found manifest to export'
helpers.log_msg(msg, 'DEBUG')
MFSTEXPORTDIR = helpers.EXPORTDIR + '/export/manifest'
if not os.path.exists(MFSTEXPORTDIR):
os.makedirs(MFSTEXPORTDIR)
os.system('cp ' + helpers.EXPORTDIR + '/manifest/* ' + MFSTEXPORTDIR)


def count_packages(repo_id):
"""
Return the number of packages/erratum in a respository
Expand Down Expand Up @@ -1000,6 +1013,9 @@ def main(args):
if not args.nogpg:
do_gpg_check(export_dir)

# Copy in the manifest, if it has been downloaded
export_manifest()

# Add our exported data to a tarfile
create_tar(export_dir, ename)

Expand Down

0 comments on commit 730d80d

Please sign in to comment.