root/livinglogic.python.xist/src/ll/orasql/scripts/oragrant.py @ 4470:00f08d1e01b0

Revision 4470:00f08d1e01b0, 5.4 KB (checked in by Walter Doerwald <walter@…>, 8 years ago)

Replace schema argument with a user argument with the values None/ALL/username.

Line 
1#!/usr/bin/env python
2# -*- coding: utf-8 -*-
3
4## Copyright 2005-2011 by LivingLogic AG, Bayreuth/Germany.
5## Copyright 2005-2011 by Walter Dörwald
6##
7## All Rights Reserved
8##
9## See orasql/__init__.py for the license
10
11
12"""
13Purpose
14-------
15
16``oragrant`` prints all existing grants in an Oracle database schema.
17It can also be used to execute these grant statements directly.
18
19
20Options
21-------
22
23``oragrant`` supports the following options:
24
25    ``connectstring``
26        An Oracle connectstring.
27
28    ``-v``, ``--verbose`` : ``false``, ``no``, ``0``, ``true``, ``yes`` or ``1``
29        Produces output (on stderr) while to database is read or written.
30
31    ``-c``, ``--color`` : ``yes``, ``no`` or ``auto``
32        Should the output (when the ``-v`` option is used) be colored. If ``auto``
33        is specified (the default) then the output is colored if stderr is a
34        terminal.
35
36    ``-x``, ``--execute`` : connectstring
37        When the ``-x`` argument is given the SQL script isn't printed on stdout,
38        but executed in the database specfied as the ``-x`` argument.
39
40    ``-k``, ``--keepjunk`` : ``false``, ``no``, ``0``, ``true``, ``yes`` or ``1``
41        If true (the default), database objects that have ``$`` or
42        ``SYS_EXPORT_SCHEMA_`` in their name will be skipped (otherwise these
43        objects will be included in the output).
44
45    ``-i``, ``--ignore`` : ``false``, ``no``, ``0``, ``true``, ``yes`` or ``1``
46        If true, errors occuring while the database is read or written will be
47        ignored.
48
49    ``-m``, ``--mapgrantee`` : Python expression: ``list`` or ``dict``
50        A Python ``dict`` or ``list`` literal which will be evaluated. If the
51        grantee is not in this list (or dictionary) no grant statement will be
52        returned. If it's a dictionary and the grantee exists as a key, the
53        privilege will be granted to the user specified as the value instead of
54        the original one. The default is to grant all privileges to the original
55        grantee.
56
57    ``-e``, ``--encoding`` : encoding
58        The encoding of the output (if ``-x`` is not given; default is ``utf-8``).
59
60
61Example
62-------
63
64Grant all privileges that ``alice`` has in the schema ``user@db`` to ``bob`` in
65``user2@db2``::
66
67    $ oragrant user/pwd@db -x user2/pwd2@db2 -m '{"alice": "bob"}' -v
68"""
69
70
71import sys, os, argparse
72
73from ll import misc, astyle, orasql
74
75
76__docformat__ = "reStructuredText"
77
78
79s4warning = astyle.Style.fromenv("LL_ORASQL_REPRANSI_WARNING", "red:black")
80s4error = astyle.Style.fromenv("LL_ORASQL_REPRANSI_ERROR", "red:black")
81s4connectstring = astyle.Style.fromenv("LL_ORASQL_REPRANSI_CONNECTSTRING", "yellow:black")
82s4object = astyle.Style.fromenv("LL_ORASQL_REPRANSI_OBJECT", "green:black")
83
84
85def main(args=None):
86    p = argparse.ArgumentParser(description="Print (and execute) grants statements from an Oracle database schema", epilog="For more info see http://www.livinglogic.de/Python/orasql/scripts/oragrant.html")
87    p.add_argument("connectstring", help="Oracle connect string")
88    p.add_argument("-v", "--verbose", dest="verbose", help="Give a progress report? (default %(default)s)", default=False, action=misc.FlagAction)
89    p.add_argument("-c", "--color", dest="color", help="Color output (default %(default)s)", default="auto", choices=("yes", "no", "auto"))
90    p.add_argument("-x", "--execute", metavar="CONNECTSTRING2", dest="execute", help="Execute in target database")
91    p.add_argument("-k", "--keepjunk", dest="keepjunk", help="Output objects with '$' or 'SYS_EXPORT_SCHEMA_' in their name? (default %(default)s)", default=False, action="store_true")
92    p.add_argument("-i", "--ignore", dest="ignore", help="Ignore errors? (default %(default)s)", default=False, action=misc.FlagAction)
93    p.add_argument("-m", "--mapgrantee", dest="mapgrantee", help="Map grantees (Python expression: list or dict)", default="True")
94    p.add_argument("-e", "--encoding", dest="encoding", help="Encoding for output (default %(default)s)", default="utf-8")
95
96    args = p.parse_args(args)
97
98    if args.color == "yes":
99        color = True
100    elif args.color == "no":
101        color = False
102    else:
103        color = None
104    stdout = astyle.Stream(sys.stdout, color)
105    stderr = astyle.Stream(sys.stderr, color)
106
107    connection = orasql.connect(args.connectstring)
108
109    if args.execute:
110        connection2 = orasql.connect(args.execute)
111        cursor2 = connection2.cursor()
112        term = False
113    else:
114        term = True
115
116    cs1 = s4connectstring(connection.connectstring())
117    if args.execute:
118        cs2 = s4connectstring(connection2.connectstring())
119
120    mapgrantee = eval(args.mapgrantee)
121
122    def keep(obj):
123        if args.keepjunk:
124            return True
125        if "$" in obj.name or "/" in obj.name or obj.name.startswith("SYS_EXPORT_SCHEMA_"):
126            return False
127        return True
128
129    for (i, obj) in enumerate(connection.iterprivileges(None)):
130        keepobj = keep(obj)
131        if args.verbose:
132            if args.execute:
133                msg = astyle.style_default("oragrant.py: ", cs1, " -> ", cs2, ": fetching/granting #{}".format(i+1))
134            else:
135                msg = astyle.style_default("oragrant.py: ", cs1, " fetching #{}".format(i+1))
136            msg = astyle.style_default(msg, " ", s4object(str(obj)))
137            if not keepobj:
138                msg = astyle.style_default(msg, " ", s4warning("(skipped)"))
139            stderr.writeln(msg)
140
141        if keepobj:
142            ddl = obj.grantddl(connection, term, mapgrantee=mapgrantee)
143            if ddl:
144                if args.execute:
145                    try:
146                        cursor2.execute(ddl)
147                    except orasql.DatabaseError, exc:
148                        if not args.ignore or "ORA-01013" in str(exc):
149                            raise
150                        stderr.writeln("oragrant.py: ", s4error("{}: {}".format(exc.__class__.__name__, str(exc).strip())))
151                else:
152                    stdout.writeln(ddl.encode(args.encoding))
153                    stdout.writeln()
154
155
156if __name__ == "__main__":
157    sys.exit(main())
Note: See TracBrowser for help on using the browser.