rda-python-dbms 1.0.1__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,176 @@
1
+ #!/usr/bin/env python3
2
+ #
3
+ ##################################################################################
4
+ #
5
+ # Title : pgddl
6
+ # Author : Zaihua Ji, zji@ucar.edu
7
+ # Date : 11/15/2020
8
+ # 2025-04-04 transferred to package rda_python_dbms from
9
+ # https://github.com/NCAR/rda-database.git
10
+ # Purpose : process a ddl (Data Definition Language) file to manipulate data
11
+ # definition of a table defined in tablename.json
12
+ #
13
+ # Github : https://github.com/NCAR/rda-python-dbms.git
14
+ #
15
+ ##################################################################################
16
+ #
17
+ import os
18
+ import sys
19
+ import re
20
+ import pwd
21
+ from os import path as op
22
+ from rda_python_common import PgDBI
23
+ from rda_python_common import PgLOG
24
+ from rda_python_common import PgUtil
25
+ from . import PgDDLLib
26
+
27
+ PGACT = {
28
+ 'PKY' : ['', 'DEL', 'ADD'], # DEL - to drop, ADD - to add primary key
29
+ 'UNQ' : ['', 'DEL', 'ADD'], # DEL - to drop, ADD - to add unique constraint
30
+ 'CMT' : ['', 'DEL', 'ADD'], # DEL - to set null, ADD to set comment
31
+ 'DFT' : ['', 'DEL', 'ADD'], # DEL - to drop, ADD - to set default value
32
+ 'JSN' : ['', 'ADD'], # ADD - to add a new defination json file
33
+ 'NNL' : ['', 'DEL', 'ADD'], # DEL - to drop, ADD - to set not null
34
+ 'IDX' : ['', 'DEL', 'ADD', 'CHG'], # DEL/ADD/CHG - to drop, add and rename index
35
+ 'REF' : ['', 'DEL', 'ADD'], # DEL - to drop, ADD - to add reference
36
+ 'TBL' : ['', 'DEL', 'ADD'], # DEL - drop table, ADD - create table
37
+ 'FLD' : ['', 'DEL', 'ADD', 'MOD', 'CHG'], # ADD/DEL/CHG/MOD - to add, drop, change and modify field
38
+ }
39
+
40
+ ACTIONS = {
41
+ 'a' : 'ADD',
42
+ 'c' : 'CHG',
43
+ 'd' : 'DEL',
44
+ 'm' : 'MOD'
45
+ }
46
+
47
+ OPTIONS = {
48
+ 'a' : ['TBL', 'IDX', 'REF'],
49
+ 'f' : 'FLD',
50
+ 'c' : 'CMT',
51
+ 'd' : 'DFT',
52
+ 'j' : 'JSN',
53
+ 'n' : 'NNL',
54
+ 'i' : 'IDX',
55
+ 'p' : 'PKY',
56
+ 'r' : 'REF',
57
+ 't' : 'TBL',
58
+ 'u' : 'UNQ'
59
+ }
60
+
61
+ VALUES = {
62
+ 'TBL' : [],
63
+ 'IDX' : [],
64
+ 'FLD' : [],
65
+ 'DFT' : [],
66
+ 'NNL' : [],
67
+ 'REF' : [],
68
+ 'UNQ' : []
69
+ }
70
+
71
+ DBFLDS = {
72
+ 'd' : 'dbname',
73
+ 'c' : 'scname',
74
+ 'h' : 'dbhost',
75
+ 'p' : 'dbport',
76
+ 'u' : 'lnname',
77
+ 'w' : 'pwname',
78
+ }
79
+
80
+ #
81
+ # main function to excecute this script
82
+ #
83
+ def main():
84
+
85
+ option = 't'
86
+ actopt = False
87
+ tablenames = action = None
88
+ dbopt = getall = False
89
+ argv = sys.argv[1:]
90
+ for arg in argv:
91
+ ms = re.match(r'^-([abcdefhlmpstTuwxy])$', arg)
92
+ if ms:
93
+ option = ms.group(1)
94
+ actopt = False
95
+ if option in 'abefm':
96
+ if option == "b":
97
+ PgLOG.PGLOG['BCKGRND'] = 1
98
+ elif option == "a":
99
+ getall= True
100
+ elif option == "e":
101
+ PgDDLLib.PGDDL['override'] = True
102
+ elif option == "f":
103
+ PgDDLLib.PGDDL['usefile'] = True
104
+ elif option == "m":
105
+ PgDDLLib.PGDDL['mysqldb'] = True
106
+ option = None
107
+ continue
108
+
109
+ ms = re.match(r'^-(\w)(\w)$', arg)
110
+ if ms:
111
+ action = ms.group(1)
112
+ option = ms.group(2)
113
+ actopt = True
114
+ if option in OPTIONS and action in ACTIONS:
115
+ act = ACTIONS[action]
116
+ if option == 'a' and action != 'a':
117
+ PgLOG.pglog("{}: Invalid Action to {} ALL".format(arg, act), PgLOG.LGEREX)
118
+ opt = OPTIONS['t'] if option == 'a' else OPTIONS[option]
119
+ if act in PGACT[opt][1:]:
120
+ if option == 'a':
121
+ for opt in OPTIONS['a']:
122
+ PGACT[opt][0] = act
123
+ else:
124
+ PGACT[opt][0] = act
125
+ if 'ap'.find(option) > -1: option = 't'
126
+ continue
127
+ PgLOG.pglog(arg + ": Invalid Action", PgLOG.LGEREX)
128
+
129
+ if re.match(r'^-.*', arg): PgLOG.pglog(arg + ": Unknown Option", PgLOG.LGEREX)
130
+ if not option: PgLOG.pglog(arg + ": Value passed in without leading Option", PgLOG.LGEREX)
131
+
132
+ if actopt:
133
+ VALUES[OPTIONS[option]].append(arg)
134
+ elif option in DBFLDS:
135
+ PgDDLLib.DBINFO[DBFLDS[option]] = arg
136
+ dbopt = True
137
+ elif option == 'T':
138
+ PgDDLLib.PGDDL['TBPATH'] = arg
139
+ elif option == 'l':
140
+ PgDDLLib.PGDDL['username'] = arg
141
+ elif option == 'x':
142
+ PgDDLLib.PGDDL['suffix'].append(arg)
143
+ elif option == 'y':
144
+ PgDDLLib.PGDDL['prefix'].append(arg)
145
+ elif option == 's':
146
+ PgDBI.PGDBI['SCPATH'] = arg
147
+ else:
148
+ VALUES[OPTIONS[option]].append(arg)
149
+
150
+ if dbopt:
151
+ PgDBI.default_scinfo(PgDDLLib.DBINFO['dbname'], PgDDLLib.DBINFO['scname'], PgDDLLib.DBINFO['dbhost'],
152
+ PgDDLLib.DBINFO['lnname'], PgDDLLib.DBINFO['pwname'], PgDDLLib.DBINFO['dbport'])
153
+ if VALUES['TBL']:
154
+ tablenames = VALUES['TBL']
155
+ elif getall:
156
+ tablenames = PgDDLLib.allschematables(); # action on all tables
157
+ if not (tablenames and action): PgLOG.show_usage('pgddl')
158
+ PgLOG.PGLOG['LOGFILE'] = "pgddl.log"
159
+ PgLOG.cmdlog("pgddl {}".format(' '.join(argv)))
160
+
161
+ # process all or given tables to add/drop table/pkey/index/reference/field
162
+ act = PGACT['TBL'][0]
163
+ if act: PgDDLLib.process_tables(tablenames, act, 'TBL')
164
+ for opt in PGACT:
165
+ act = PGACT[opt][0]
166
+ if opt == 'TBL' or not act: continue
167
+ names = VALUES[opt] if opt in VALUES and VALUES[opt] else None
168
+ PgDDLLib.process_tables(tablenames, act, opt, names)
169
+
170
+ PgLOG.cmdlog()
171
+ PgLOG.pgexit(0)
172
+
173
+ #
174
+ # call main() to start program
175
+ #
176
+ if __name__ == "__main__": main()
@@ -0,0 +1,59 @@
1
+
2
+ Manipulates data definition of PostgreSQL databases.
3
+
4
+ Usage: pgddl [-b] [-d DBName] [-c Schema] [-h HostName] [-p DBPort] [-s SchemaPath] \
5
+ [-T TBPATH] [-u DBLoginName] [-w DBPassword] [-a] [-e] [-f] [-l username] \
6
+ [[-t] TableNamelist] [-x SuffixList] [-y PrefixList] [-xy [names]]
7
+
8
+ - Option -b, log process information in logfile only;
9
+
10
+ - Option -c, schema name;
11
+
12
+ - Option -d, database name;
13
+
14
+ - Option -e, override existing json file for action -aj;
15
+
16
+ - Option -f, use .tb files only to add json files for action -aj,
17
+ without -f, table info defined in database is used if a
18
+ .tb file not exists;
19
+
20
+ - Option -h, server host name;
21
+
22
+ - Option -l, Linux user login name;
23
+
24
+ - Option -m, get table info from MySQL server to add json files for action -aj;
25
+
26
+ - Option -p, port number to connect to the server remotely;
27
+
28
+ - Option -s, addtional schema to be include in the schema search_path for
29
+ modifying column type;
30
+
31
+ - Option -t, table name list, the -t can be omitted if table names
32
+ are passed in first;
33
+
34
+ - Option -T, path to where the table definition files are located;
35
+
36
+ - Option -u, database server login name;
37
+
38
+ - Option -w, user password;
39
+
40
+ - Option -xy, x = [a]dd, [c]hange, [d]rop, or [m]odify actions on
41
+ y = [a]ll, [t]able, [p]key, [u]nique, [i]ndex, [r]eference,
42
+ [j]sonfile, [f]ield, [c]omment, [d]efault, or [n]otnull;
43
+
44
+ - Option -a, actions on all existing tables of a given schema;
45
+
46
+ - TableNameList, actions described above on given table names;
47
+
48
+ - Option -x, suffixes to be appended to the TableNameList with a leading
49
+ undrescore character, '_', such as TableName_Suffix;
50
+
51
+ - Option -y, prefixes to be prepended to the TableNameList with a trailing
52
+ undrescore character, '_', such as Prefix_TableName;
53
+
54
+ One of the actions, -xy, and either -a or TableNameList must be specified
55
+ to run this application.
56
+
57
+ For examples:
58
+ pgddl -t TableName -aa # add a table with its fields and associated constraints;
59
+ pgddl TableName -af FieldName # add a new Field to a existing table
@@ -0,0 +1,133 @@
1
+ #!/usr/bin/env python3
2
+ #
3
+ ##################################################################################
4
+ #
5
+ # Title : pgseq
6
+ # Author : Zaihua Ji, zji@ucar.edu
7
+ # Date : 12/31/2020
8
+ # 2025-04-09 transferred to package rda_python_dbms from
9
+ # https://github.com/NCAR/rda-database.git
10
+ # Purpose : check all tables for given schemas to reset the related sequences
11
+ #
12
+ # Github : https://github.com/NCAR/rda-python-dbms.git
13
+ #
14
+ ##################################################################################
15
+
16
+ import sys
17
+ import re
18
+ from rda_python_common import PgLOG
19
+ from rda_python_common import PgDBI
20
+ from rda_python_common import PgUtil
21
+
22
+ SINFO = {
23
+ 'ht' : 'rda-pgdb-02.ucar.edu',
24
+ 'db' : 'rdadb',
25
+ 'us' : '',
26
+ 'pw' : '',
27
+ }
28
+
29
+ #
30
+ # main function to run this program
31
+ #
32
+ def main():
33
+
34
+ option = None
35
+ alltb = 0
36
+ scnames = []
37
+ tbnames = []
38
+ argv = sys.argv[1:]
39
+
40
+ for arg in argv:
41
+ if arg == "-b":
42
+ PgLOG.MYLOG['BCKGRND'] = 1
43
+ elif re.match(r'^-([dhpstu])$', arg):
44
+ option = arg[1]
45
+ elif re.match(r'^-', arg):
46
+ PgLOG.pglog(arg + ": Invalid Option", PgLOG.LGWNEX)
47
+ elif option:
48
+ if option == 'd':
49
+ SINFO['db'] = arg
50
+ elif option == 'h':
51
+ SINFO['ht'] = arg
52
+ elif option == 'p':
53
+ SINFO['pw'] = arg
54
+ elif option == 'u':
55
+ SINFO['us'] = arg
56
+ elif option == 's':
57
+ scnames.append(arg)
58
+ elif option == 't':
59
+ tbnames.append(arg)
60
+ else:
61
+ PgLOG.pglog(arg + ": Passed in without leading Option", PgLOG.LGWNEX)
62
+
63
+ if not scnames:
64
+ print("Usage: pgseq [-h HostName] [-d DatabaseName] -s SchemaNames \\")
65
+ print(" [-t TableNames] [-u UserName] [-p Password]")
66
+ print(" -h: PostgreSQL Database server hostname, default to " + SINFO['ht'])
67
+ print(" -d: PostgreSQL Database name, default to " + SINFO['db'])
68
+ print(" -s: Reset sequences for the provided Schemas, at least provide one")
69
+ print(" -t: Table names to reset sequences, default to all tables in the schema")
70
+ print(" -u: Provide database login username if other than the schema name")
71
+ print(" -p: Optional database login password")
72
+ sys.exit(0)
73
+
74
+ PgLOG.cmdlog("pgseq {}".format(' '.join(argv)))
75
+ for scname in scnames:
76
+ reset_table_sequence(scname, tbnames)
77
+ PgLOG.cmdlog()
78
+ sys.exit(0)
79
+
80
+ def reset_table_sequence(scname, tbnames):
81
+
82
+ us = SINFO['us'] if SINFO['us'] else scname
83
+ pw = SINFO['pw'] if SINFO['pw'] else us
84
+ PgDBI.default_scinfo(SINFO['db'], scname, SINFO['ht'], us, pw)
85
+ scnd = "table_catalog = '{}' AND table_schema = '{}' AND table_type = 'BASE TABLE'".format(SINFO['db'], scname)
86
+ if tbnames:
87
+ cnd = " AND table_name "
88
+ tcnt = len(tbnames)
89
+ if tcnt == 1:
90
+ cnd += "= '{}'".format(tbnames[0])
91
+ else:
92
+ cnd += "IN ('{}'".format(tbnames[0])
93
+ for i in range(1, tcnt):
94
+ cnd += ", '{}'".format(tbnames[i])
95
+ cnd += ')'
96
+ else:
97
+ cnd = ''
98
+ pgrecs = PgDBI.pgmget('information_schema.tables', 'table_name', scnd + cnd)
99
+ tbnames = pgrecs['table_name'] if pgrecs else []
100
+ tcnt = len(tbnames)
101
+ if tcnt == 0:
102
+ PgLOG.pglog("{}.{}: No Table Name found".format(SINFO['db'], scname), PgLOG.LOGWRN)
103
+ return
104
+
105
+ scnt = 0
106
+ scnd = "sequence_catalog = '{}' AND sequence_schema = '{}' AND sequence_name LIKE ".format(SINFO['db'], scname)
107
+ qscname = PgDBI.pgname(scname)
108
+ for tbname in tbnames:
109
+ cnd = "'{}_%_seq'".format(tbname)
110
+ pgrecs = PgDBI.pgmget('information_schema.sequences', 'sequence_name', scnd + cnd)
111
+ if not pgrecs: continue
112
+ qscname = PgDBI.pgname(scname)
113
+ qtname = '{}.{}'.format(qscname, PgDBI.pgname(tbname))
114
+ for sname in pgrecs['sequence_name']:
115
+ fname = sname[len(tbname)+1:-4]
116
+ fcnd = "table_name = '{}' AND table_schema = '{}' AND column_name = '{}'".format(tbname, scname, fname)
117
+ if not PgDBI.pgget('information_schema.columns', '', fcnd): continue
118
+ pgrec = PgDBI.pgget(qtname, "MAX({}) mval".format(PgDBI.pgname(fname)))
119
+ mval = pgrec['mval'] if pgrec and pgrec['mval'] else 1
120
+ qsname = '{}.{}'.format(qscname, PgDBI.pgname(sname))
121
+ qstr = "setval('{}', {})".format(qsname, mval)
122
+ pgrec = PgDBI.pgget('', qstr)
123
+ if pgrec:
124
+ PgLOG.pglog("{}.{}: Sequence Value set to {}".format(scname, sname, pgrec['setval']), PgLOG.LOGWRN)
125
+ scnt += 1
126
+
127
+ if scnt > 1 and tcnt > 1:
128
+ PgLOG.pglog("{}.{}: {}/{} Sequences/Tables Reset Values".format(SINFO['db'], scname, scnt, tcnt), PgLOG.LOGWRN)
129
+
130
+ #
131
+ # call main() to start program
132
+ #
133
+ if __name__ == "__main__": main()
@@ -0,0 +1,17 @@
1
+ Metadata-Version: 2.4
2
+ Name: rda_python_dbms
3
+ Version: 1.0.1
4
+ Summary: RDA Python Package to manage PostreSQL databases
5
+ Author-email: Zaihua Ji <zji@ucar.edu>
6
+ Project-URL: Homepage, https://github.com/NCAR/rda-python-dbms
7
+ Classifier: Programming Language :: Python :: 3
8
+ Classifier: License :: OSI Approved :: MIT License
9
+ Classifier: Operating System :: OS Independent
10
+ Classifier: Development Status :: 5 - Production/Stable
11
+ Requires-Python: >=3.7
12
+ Description-Content-Type: text/markdown
13
+ License-File: LICENSE
14
+ Requires-Dist: rda_python_common
15
+ Dynamic: license-file
16
+
17
+ RDA python Package to manage RDA PostgreSQL databases.
@@ -0,0 +1,15 @@
1
+ rda_python_dbms/MyDBI.py,sha256=VXtzR6zYojez2sPJreGlHKHgEJfF-V359T2mhSGJKHk,64376
2
+ rda_python_dbms/PgDDLLib.py,sha256=DzBocr7c4c482zB8jxw0lughXOj327OL_TTx6ZvmjXA,40814
3
+ rda_python_dbms/__init__.py,sha256=AbpHGcgLb-kRsJGnwFEktk7uzpZOCcBY74-YBdrKVGs,1
4
+ rda_python_dbms/pgbackup.py,sha256=ICYmuFCjlI_ICRaL33ZUGVzEE1CyEfC5xwhq3t9vJH0,3647
5
+ rda_python_dbms/pgchksum.py,sha256=NlIW4N45nRYj16qF00lndiw5wyIB2YAFi5NfORRbuPk,19044
6
+ rda_python_dbms/pgcmptables.py,sha256=y5Tx45BguJ4IVw0thgZmg9D9B2gcYMdem3shNugtAcA,47126
7
+ rda_python_dbms/pgddl.py,sha256=0obj6Lsc0DVKSIvaP1n9d9TCMYb10f_Hoyc3Gg4jYnI,5441
8
+ rda_python_dbms/pgddl.usg,sha256=7ly6YbusvyIy9yQn9reGIUtZQ5Wiehp9-DKDgfjqSBE,2267
9
+ rda_python_dbms/pgseq.py,sha256=OkGhdYB03smGMo9fecdS3dZgR2jOm-ZODM9_1QjAlWE,4736
10
+ rda_python_dbms-1.0.1.dist-info/licenses/LICENSE,sha256=Uky6fiiVw7cakFVRtVpzg-mvqOQ-WcA_H8lHqhPRg58,1101
11
+ rda_python_dbms-1.0.1.dist-info/METADATA,sha256=CxpCsnO_spfFnD6vFY8aqAU5Xq8dB0q_N5w95PoPnpc,617
12
+ rda_python_dbms-1.0.1.dist-info/WHEEL,sha256=CmyFI0kx5cdEMTLiONQRbGQwjIoR1aIYB7eCAQ4KPJ0,91
13
+ rda_python_dbms-1.0.1.dist-info/entry_points.txt,sha256=e-Mc9poQZhN4C82G03V5Vyoh56jpz75-bpWkb7yG9l4,217
14
+ rda_python_dbms-1.0.1.dist-info/top_level.txt,sha256=4T1ShNUMyiqmwDIuDL7pDOm_S-6zWWW3Vy6OdAzYA4c,16
15
+ rda_python_dbms-1.0.1.dist-info/RECORD,,
@@ -0,0 +1,5 @@
1
+ Wheel-Version: 1.0
2
+ Generator: setuptools (78.1.0)
3
+ Root-Is-Purelib: true
4
+ Tag: py3-none-any
5
+
@@ -0,0 +1,6 @@
1
+ [console_scripts]
2
+ pgbackup = rda_python_dbms.pgbackup:main
3
+ pgchksum = rda_python_dbms.pgchksum:main
4
+ pgcmptables = rda_python_dbms.pgcmptables:main
5
+ pgddl = rda_python_dbms.pgddl:main
6
+ pgseq = rda_python_dbms.pgseq:main
@@ -0,0 +1,21 @@
1
+ MIT License
2
+
3
+ Copyright (c) 2025 NSF National Center for Atmospheric Research
4
+
5
+ Permission is hereby granted, free of charge, to any person obtaining a copy
6
+ of this software and associated documentation files (the "Software"), to deal
7
+ in the Software without restriction, including without limitation the rights
8
+ to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
9
+ copies of the Software, and to permit persons to whom the Software is
10
+ furnished to do so, subject to the following conditions:
11
+
12
+ The above copyright notice and this permission notice shall be included in all
13
+ copies or substantial portions of the Software.
14
+
15
+ THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
18
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
20
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
21
+ SOFTWARE.
@@ -0,0 +1 @@
1
+ rda_python_dbms