Thanks to visit codestin.com
Credit goes to github.com

Skip to content

Commit 1771b54

Browse files
committed
Implement #8521. Added named argument handling to winreg's CreateKeyEx,
DeleteKeyEx, and OpenKeyEx. Note that CKE and DKE are new functions for 3.2 so I didn't give them a versionchanged because of the existing versionadded. OpenKeyEx already existed so it gets a versionchanged tag.
1 parent 6d7df63 commit 1771b54

4 files changed

Lines changed: 73 additions & 36 deletions

File tree

Doc/library/winreg.rst

Lines changed: 5 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ This module offers the following functions:
6060
:exc:`WindowsError` exception is raised.
6161

6262

63-
.. function:: CreateKeyEx(key, sub_key[, res[, sam]])
63+
.. function:: CreateKeyEx(key, sub_key, reserved=0, access=KEY_ALL_ACCESS)
6464

6565
Creates or opens the specified key, returning a
6666
:ref:`handle object <handle-object>`.
@@ -103,7 +103,7 @@ This module offers the following functions:
103103
If the method fails, a :exc:`WindowsError` exception is raised.
104104

105105

106-
.. function:: DeleteKeyEx(key, sub_key[, sam[, res]])
106+
.. function:: DeleteKeyEx(key, sub_key, access=KEY_ALL_ACCESS, reserved=0)
107107

108108
Deletes the specified key.
109109

@@ -243,7 +243,7 @@ This module offers the following functions:
243243
specified in *file_name* is relative to the remote computer.
244244

245245

246-
.. function:: OpenKey(key, sub_key[, res[, sam]])
246+
.. function:: OpenKey(key, sub_key, reserved=0, access=KEY_ALL_ACCESS)
247247

248248
Opens the specified key, returning a :ref:`handle object <handle-object>`.
249249

@@ -262,6 +262,8 @@ This module offers the following functions:
262262

263263
If the function fails, :exc:`WindowsError` is raised.
264264

265+
.. versionchanged:: 3.2 Allow the use of named arguments.
266+
265267

266268
.. function:: OpenKeyEx()
267269

Lib/test/test_winreg.py

Lines changed: 22 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -185,6 +185,16 @@ def _test_all(self, root_key, subkeystr="sub_key"):
185185
self._read_test_data(root_key, subkeystr)
186186
self._delete_test_data(root_key, subkeystr)
187187

188+
def _test_named_args(self, key, sub_key):
189+
with CreateKeyEx(key=key, sub_key=sub_key, reserved=0,
190+
access=KEY_ALL_ACCESS) as ckey:
191+
self.assertTrue(ckey.handle != 0)
192+
193+
with OpenKeyEx(key=key, sub_key=sub_key, reserved=0,
194+
access=KEY_ALL_ACCESS) as okey:
195+
self.assertTrue(okey.handle != 0)
196+
197+
188198
class LocalWinregTests(BaseWinregTests):
189199

190200
def test_registry_works(self):
@@ -203,6 +213,12 @@ def test_registry_works_extended_functions(self):
203213

204214
self._delete_test_data(HKEY_CURRENT_USER)
205215

216+
def test_named_arguments(self):
217+
self._test_named_args(HKEY_CURRENT_USER, test_key_name)
218+
# Use the regular DeleteKey to clean up
219+
# DeleteKeyEx takes named args and is tested separately
220+
DeleteKey(HKEY_CURRENT_USER, test_key_name)
221+
206222
def test_connect_registry_to_local_machine_works(self):
207223
# perform minimal ConnectRegistry test which just invokes it
208224
h = ConnectRegistry(None, HKEY_LOCAL_MACHINE)
@@ -314,6 +330,12 @@ def test_remote_registry_works(self):
314330
@unittest.skipUnless(WIN64_MACHINE, "x64 specific registry tests")
315331
class Win64WinregTests(BaseWinregTests):
316332

333+
def test_named_arguments(self):
334+
self._test_named_args(HKEY_CURRENT_USER, test_key_name)
335+
# Clean up and also exercise the named arguments
336+
DeleteKeyEx(key=HKEY_CURRENT_USER, sub_key=test_key_name,
337+
access=KEY_ALL_ACCESS, reserved=0)
338+
317339
def test_reflection_functions(self):
318340
# Test that we can call the query, enable, and disable functions
319341
# on a key which isn't on the reflection list with no consequences.

Misc/NEWS

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -10,6 +10,9 @@ What's New in Python 3.2 Alpha 3?
1010
Core and Builtins
1111
-----------------
1212

13+
- Issue #8521: Allow CreateKeyEx, OpenKeyEx, and DeleteKeyEx functions
14+
of winreg to use named arguments.
15+
1316
- Issue #9930: Remove bogus subtype check that was causing (e.g.)
1417
float.__rdiv__(2.0, 3) to return NotImplemented instead of the
1518
expected 1.5.

PC/winreg.c

Lines changed: 43 additions & 33 deletions
Original file line numberDiff line numberDiff line change
@@ -989,23 +989,26 @@ PyCreateKey(PyObject *self, PyObject *args)
989989
}
990990

991991
static PyObject *
992-
PyCreateKeyEx(PyObject *self, PyObject *args)
992+
PyCreateKeyEx(PyObject *self, PyObject *args, PyObject *kwargs)
993993
{
994994
HKEY hKey;
995-
PyObject *obKey;
996-
wchar_t *subKey;
995+
PyObject *key;
996+
wchar_t *sub_key;
997997
HKEY retKey;
998-
int res = 0;
999-
REGSAM sam = KEY_WRITE;
998+
int reserved = 0;
999+
REGSAM access = KEY_WRITE;
10001000
long rc;
1001-
if (!PyArg_ParseTuple(args, "OZ|ii:CreateKeyEx", &obKey, &subKey,
1002-
&res, &sam))
1001+
1002+
char *kwlist[] = {"key", "sub_key", "reserved", "access", NULL};
1003+
1004+
if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OZ|ii:CreateKeyEx", kwlist,
1005+
&key, &sub_key, &reserved, &access))
10031006
return NULL;
1004-
if (!PyHKEY_AsHKEY(obKey, &hKey, FALSE))
1007+
if (!PyHKEY_AsHKEY(key, &hKey, FALSE))
10051008
return NULL;
10061009

1007-
rc = RegCreateKeyExW(hKey, subKey, res, NULL, (DWORD)NULL,
1008-
sam, NULL, &retKey, NULL);
1010+
rc = RegCreateKeyExW(hKey, sub_key, reserved, NULL, (DWORD)NULL,
1011+
access, NULL, &retKey, NULL);
10091012
if (rc != ERROR_SUCCESS)
10101013
return PyErr_SetFromWindowsErrWithFunction(rc, "CreateKeyEx");
10111014
return PyHKEY_FromHKEY(retKey);
@@ -1030,22 +1033,23 @@ PyDeleteKey(PyObject *self, PyObject *args)
10301033
}
10311034

10321035
static PyObject *
1033-
PyDeleteKeyEx(PyObject *self, PyObject *args)
1036+
PyDeleteKeyEx(PyObject *self, PyObject *args, PyObject *kwargs)
10341037
{
10351038
HKEY hKey;
1036-
PyObject *obKey;
1039+
PyObject *key;
10371040
HMODULE hMod;
10381041
typedef LONG (WINAPI *RDKEFunc)(HKEY, const wchar_t*, REGSAM, int);
10391042
RDKEFunc pfn = NULL;
1040-
wchar_t *subKey;
1043+
wchar_t *sub_key;
10411044
long rc;
1042-
int res = 0;
1043-
REGSAM sam = KEY_WOW64_64KEY;
1045+
int reserved = 0;
1046+
REGSAM access = KEY_WOW64_64KEY;
10441047

1045-
if (!PyArg_ParseTuple(args, "Ou|ii:DeleteKeyEx",
1046-
&obKey, &subKey, &sam, &res))
1048+
char *kwlist[] = {"key", "sub_key", "access", "reserved", NULL};
1049+
if (!PyArg_ParseTupleAndKeywords(args, kwargs, "Ou|ii:DeleteKeyEx", kwlist,
1050+
&key, &sub_key, &access, &reserved))
10471051
return NULL;
1048-
if (!PyHKEY_AsHKEY(obKey, &hKey, FALSE))
1052+
if (!PyHKEY_AsHKEY(key, &hKey, FALSE))
10491053
return NULL;
10501054

10511055
/* Only available on 64bit platforms, so we must load it
@@ -1060,7 +1064,7 @@ PyDeleteKeyEx(PyObject *self, PyObject *args)
10601064
return NULL;
10611065
}
10621066
Py_BEGIN_ALLOW_THREADS
1063-
rc = (*pfn)(hKey, subKey, sam, res);
1067+
rc = (*pfn)(hKey, sub_key, access, reserved);
10641068
Py_END_ALLOW_THREADS
10651069

10661070
if (rc != ERROR_SUCCESS)
@@ -1282,24 +1286,26 @@ PyLoadKey(PyObject *self, PyObject *args)
12821286
}
12831287

12841288
static PyObject *
1285-
PyOpenKey(PyObject *self, PyObject *args)
1289+
PyOpenKey(PyObject *self, PyObject *args, PyObject *kwargs)
12861290
{
12871291
HKEY hKey;
1288-
PyObject *obKey;
1289-
1290-
wchar_t *subKey;
1291-
int res = 0;
1292+
PyObject *key;
1293+
wchar_t *sub_key;
1294+
int reserved = 0;
12921295
HKEY retKey;
12931296
long rc;
1294-
REGSAM sam = KEY_READ;
1295-
if (!PyArg_ParseTuple(args, "OZ|ii:OpenKey", &obKey, &subKey,
1296-
&res, &sam))
1297+
REGSAM access = KEY_READ;
1298+
1299+
char *kwlist[] = {"key", "sub_key", "reserved", "access", NULL};
1300+
1301+
if (!PyArg_ParseTupleAndKeywords(args, kwargs, "OZ|ii:OpenKey", kwlist,
1302+
&key, &sub_key, &reserved, &access))
12971303
return NULL;
1298-
if (!PyHKEY_AsHKEY(obKey, &hKey, FALSE))
1304+
if (!PyHKEY_AsHKEY(key, &hKey, FALSE))
12991305
return NULL;
13001306

13011307
Py_BEGIN_ALLOW_THREADS
1302-
rc = RegOpenKeyExW(hKey, subKey, res, sam, &retKey);
1308+
rc = RegOpenKeyExW(hKey, sub_key, reserved, access, &retKey);
13031309
Py_END_ALLOW_THREADS
13041310
if (rc != ERROR_SUCCESS)
13051311
return PyErr_SetFromWindowsErrWithFunction(rc, "RegOpenKeyEx");
@@ -1667,9 +1673,11 @@ static struct PyMethodDef winreg_methods[] = {
16671673
{"CloseKey", PyCloseKey, METH_VARARGS, CloseKey_doc},
16681674
{"ConnectRegistry", PyConnectRegistry, METH_VARARGS, ConnectRegistry_doc},
16691675
{"CreateKey", PyCreateKey, METH_VARARGS, CreateKey_doc},
1670-
{"CreateKeyEx", PyCreateKeyEx, METH_VARARGS, CreateKeyEx_doc},
1676+
{"CreateKeyEx", (PyCFunction)PyCreateKeyEx,
1677+
METH_VARARGS | METH_KEYWORDS, CreateKeyEx_doc},
16711678
{"DeleteKey", PyDeleteKey, METH_VARARGS, DeleteKey_doc},
1672-
{"DeleteKeyEx", PyDeleteKeyEx, METH_VARARGS, DeleteKeyEx_doc},
1679+
{"DeleteKeyEx", (PyCFunction)PyDeleteKeyEx,
1680+
METH_VARARGS | METH_KEYWORDS, DeleteKeyEx_doc},
16731681
{"DeleteValue", PyDeleteValue, METH_VARARGS, DeleteValue_doc},
16741682
{"DisableReflectionKey", PyDisableReflectionKey, METH_VARARGS, DisableReflectionKey_doc},
16751683
{"EnableReflectionKey", PyEnableReflectionKey, METH_VARARGS, EnableReflectionKey_doc},
@@ -1679,8 +1687,10 @@ static struct PyMethodDef winreg_methods[] = {
16791687
ExpandEnvironmentStrings_doc },
16801688
{"FlushKey", PyFlushKey, METH_VARARGS, FlushKey_doc},
16811689
{"LoadKey", PyLoadKey, METH_VARARGS, LoadKey_doc},
1682-
{"OpenKey", PyOpenKey, METH_VARARGS, OpenKey_doc},
1683-
{"OpenKeyEx", PyOpenKey, METH_VARARGS, OpenKeyEx_doc},
1690+
{"OpenKey", (PyCFunction)PyOpenKey, METH_VARARGS | METH_KEYWORDS,
1691+
OpenKey_doc},
1692+
{"OpenKeyEx", (PyCFunction)PyOpenKey, METH_VARARGS | METH_KEYWORDS,
1693+
OpenKeyEx_doc},
16841694
{"QueryValue", PyQueryValue, METH_VARARGS, QueryValue_doc},
16851695
{"QueryValueEx", PyQueryValueEx, METH_VARARGS, QueryValueEx_doc},
16861696
{"QueryInfoKey", PyQueryInfoKey, METH_VARARGS, QueryInfoKey_doc},

0 commit comments

Comments
 (0)