History log of /dokuwiki/_test/tests/inc/ (Results 1 – 25 of 586)
Revision Date Author Comments
(<<< Hide modified files)
(Show modified files >>>)
0579c2f819-Jul-2026 Andreas Gohr <andi@splitbrain.org>

security(media): authorize the resolved target of media write operations

The media manager computed a permission level for the request's namespace
and passed it to the media write helpers, which the

security(media): authorize the resolved target of media write operations

The media manager computed a permission level for the request's namespace
and passed it to the media write helpers, which then acted on a target that
need not live in that namespace. Reachability differs per helper:

- media_restore() took the id to restore from the separate "image"
parameter, unrelated to the namespace the permission was computed for. A
user with upload permission in any one namespace could restore revisions
of media in namespaces they cannot write.

- media_upload() and media_upload_xhr() derive the target from the upload
namespace plus a user-controlled filename that may carry its own namespace
segments, so the target can only resolve into a sub-namespace of the upload
namespace. Where that child has a stricter ACL, the parent's permission was
applied instead.

- media_metasave() was not vulnerable: its target and its permission both
derive from the same request id, so the namespaces always matched. It is
changed only for consistency.

Each helper now recomputes the permission from its resolved target id, as
media_delete() already does. The redundant $auth parameter is removed from
media_restore() and media_metasave(), which have no other callers, and
ignored but kept for compatibility in media_upload() and media_upload_xhr().

Severity: medium - an authenticated user with upload rights in one namespace
can restore media revisions in other namespaces, or write into a stricter
sub-namespace of one they can upload to; an authorization bypass affecting
media integrity, not code execution or disclosure.

fixes #4702

show more ...

3ed3408919-Jul-2026 Andreas Gohr <andi@splitbrain.org>

security(auth): use strict comparison in membership and ACL checks

Loose comparison treated numerically-equal strings as the same value, so
a superuser, manager, or ACL entry named with a numeric st

security(auth): use strict comparison in membership and ACL checks

Loose comparison treated numerically-equal strings as the same value, so
a superuser, manager, or ACL entry named with a numeric string (e.g. 1e3
or @1e3) matched any user or group whose name was numerically equal
(1000, 01000, 1000.0). Such names survive auth_nameencode() untouched,
allowing silent privilege escalation. Match names strictly in
auth_isMember() and auth_aclcheck_cb().

Severity: low - only exploitable when an administrator names a superuser,
manager or ACL group with a numeric string such as 1e3, an unusual
configuration, so realistic deployments are rarely affected.

fixes #4701

show more ...


/dokuwiki/.gitattributes
/dokuwiki/.github/workflows/autoFix.yml
/dokuwiki/.github/workflows/deletedFiles.yml
/dokuwiki/.github/workflows/phpCS.yml
/dokuwiki/.github/workflows/release-build.yml
/dokuwiki/.github/workflows/release-preparation.yml
/dokuwiki/.github/workflows/testLinux.yml
/dokuwiki/.github/workflows/testWindows.yml
/dokuwiki/.github/workflows/todoChecker.yml
/dokuwiki/AI_POLICY.md
/dokuwiki/CONTRIBUTING.md
/dokuwiki/_test/tests/Parsing/Lexer/LexerTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/FormattingTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/GfmDeletedTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/GfmEmphasisStrongTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/GfmEmphasisStrongUnderscoreTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/GfmEmphasisTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/GfmEmphasisUnderscoreTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/GfmStrongUnderscoreTest.php
/dokuwiki/_test/tests/Remote/ApiCoreAclCheckTest.php
/dokuwiki/_test/tests/Search/Index/LockTest.php
/dokuwiki/_test/tests/Search/IndexerTest.php
auth_admincheck.test.php
/dokuwiki/inc/ChangeLog/ChangeLog.php
/dokuwiki/inc/ChangeLog/RevisionInfo.php
/dokuwiki/inc/MailUtils.php
/dokuwiki/inc/Parsing/Lexer/CloserPattern.php
/dokuwiki/inc/Parsing/Lexer/Lexer.php
/dokuwiki/inc/Parsing/Lexer/ParallelRegex.php
/dokuwiki/inc/Parsing/Lexer/StateStack.php
/dokuwiki/inc/Parsing/ParserMode/AbstractFormatting.php
/dokuwiki/inc/Parsing/ParserMode/AbstractMode.php
/dokuwiki/inc/Parsing/ParserMode/Deleted.php
/dokuwiki/inc/Parsing/ParserMode/Emphasis.php
/dokuwiki/inc/Parsing/ParserMode/Footnote.php
/dokuwiki/inc/Parsing/ParserMode/GfmBacktickDouble.php
/dokuwiki/inc/Parsing/ParserMode/GfmBacktickSingle.php
/dokuwiki/inc/Parsing/ParserMode/GfmCode.php
/dokuwiki/inc/Parsing/ParserMode/GfmDeleted.php
/dokuwiki/inc/Parsing/ParserMode/GfmEmphasis.php
/dokuwiki/inc/Parsing/ParserMode/GfmEmphasisStrong.php
/dokuwiki/inc/Parsing/ParserMode/GfmEmphasisStrongUnderscore.php
/dokuwiki/inc/Parsing/ParserMode/GfmEmphasisUnderscore.php
/dokuwiki/inc/Parsing/ParserMode/GfmLink.php
/dokuwiki/inc/Parsing/ParserMode/GfmQuote.php
/dokuwiki/inc/Parsing/ParserMode/GfmStrongUnderscore.php
/dokuwiki/inc/Parsing/ParserMode/Media.php
/dokuwiki/inc/Parsing/ParserMode/Monospace.php
/dokuwiki/inc/Parsing/ParserMode/Strong.php
/dokuwiki/inc/Parsing/ParserMode/Subscript.php
/dokuwiki/inc/Parsing/ParserMode/Superscript.php
/dokuwiki/inc/Parsing/ParserMode/Underline.php
/dokuwiki/inc/Parsing/ParserMode/Windowssharelink.php
/dokuwiki/inc/Remote/ApiCore.php
/dokuwiki/inc/Search/Collection/DirectCollection.php
/dokuwiki/inc/Search/Index/FileIndex.php
/dokuwiki/inc/Search/Index/Lock.php
/dokuwiki/inc/Search/Indexer.php
/dokuwiki/inc/Ui/Admin.php
/dokuwiki/inc/auth.php
/dokuwiki/inc/parser/xhtml.php
/dokuwiki/lib/plugins/authad/adLDAP/classes/adLDAPUsers.php
/dokuwiki/lib/plugins/authplain/_test/escaping.test.php
/dokuwiki/lib/plugins/authplain/auth.php
/dokuwiki/lib/plugins/extension/GuiExtension.php
/dokuwiki/lib/plugins/extension/Notice.php
/dokuwiki/lib/plugins/extension/_test/NoticeTest.php
/dokuwiki/lib/plugins/extension/action.php
/dokuwiki/lib/plugins/extension/script.js
/dokuwiki/lib/plugins/info/syntax.php
/dokuwiki/lib/plugins/revert/admin.php
/dokuwiki/lib/scripts/locktimer.js
e5358e0d08-Jul-2026 Andreas Gohr <gohr@cosmocode.de>

fix(infoutils): use git --pretty=reference to avoid Windows escaping

On Windows escapeshellarg() replaces percent signs with spaces, so the
--pretty=format:%h %cd argument reached git as literal tex

fix(infoutils): use git --pretty=reference to avoid Windows escaping

On Windows escapeshellarg() replaces percent signs with spaces, so the
--pretty=format:%h %cd argument reached git as literal text. Git then
echoed the format string verbatim, a truthy value that made the version
display report an empty hash and the date "h" while skipping the working
.git-directory fallback.

The named --pretty=reference format carries no percent signs on the
command line, so the shell path works on Windows too. Its "hash
(subject, date)" output is validated before being trusted.

Introduced in b9e35b2f0.

show more ...

12ead38a08-Jul-2026 Andreas Gohr <gohr@cosmocode.de>

fix(httputils): canonicalize paths when building X-Accel-Redirect URLs

http_xaccel_url() compared the fullpath()-collapsed target file against a
non-canonicalized DOKU_INC and the raw savedir config

fix(httputils): canonicalize paths when building X-Accel-Redirect URLs

http_xaccel_url() compared the fullpath()-collapsed target file against a
non-canonicalized DOKU_INC and the raw savedir config value. The lib/exe entry
points define DOKU_INC as __DIR__.'/../../' and savedir defaults to the relative
'./data', so the in-tree prefix check never matched: nginx installs using
X-Accel-Redirect served in-tree files behind the /_x_accel_redirect/ escape
hatch and returned 404 without extra location config.

Canonicalize DOKU_INC and every configured root with fullpath() before the
prefix comparisons so they match the already-canonicalized file path.

The comparison lost its fullpath() wrapping in b8c2692f7, which replaced the
earlier substr($file, strlen(fullpath(DOKU_INC)) + 1) with a raw DOKU_INC
prefix check.

show more ...

c3a14f6706-Jul-2026 Andreas Gohr <gohr@cosmocode.de>

fix(media): don't upscale small images in the detail previews

The detail page, media manager and media diff requested a bounding-box
resize at the full box size, so an image smaller than the box was

fix(media): don't upscale small images in the detail previews

The detail page, media manager and media diff requested a bounding-box
resize at the full box size, so an image smaller than the box was enlarged
and fetch.php generated and cached the upscaled copy.

slika 1.2 adds an $upscale option to resize/crop. getDisplayDimensions()
now takes a $fit flag mirroring fetch.php one to one and predicts the
matching no-upscale dimensions, media_resize_image()/media_mod_image()
forward $upscale, and fetch.php disables upscaling for fit=1 requests.
In-page image scaling is unchanged.

show more ...


/dokuwiki/_test/composer.lock
/dokuwiki/_test/rector.php
/dokuwiki/_test/tests/Feed/FeedParserTest.php
/dokuwiki/_test/tests/File/MediaFileTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/AbstractModeTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/PreformattedTest.php
/dokuwiki/_test/tests/Remote/ApiCoreAclCheckTest.php
/dokuwiki/_test/tests/Search/Collection/CollectionSearchTest.php
/dokuwiki/_test/tests/Search/Collection/DirectCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/FrequencyCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/LookupCollectionTest.php
/dokuwiki/_test/tests/Search/Index/LockTest.php
/dokuwiki/_test/tests/Search/Index/MemoryIndexTest.php
/dokuwiki/_test/tests/Search/Index/TupleOpsTest.php
/dokuwiki/_test/tests/Search/Query/QueryEvaluatorTest.php
/dokuwiki/_test/tests/Search/Query/QueryParserTest.php
/dokuwiki/_test/tests/Ui/Media/DisplayTest.php
media_resize.test.php
/dokuwiki/composer.json
/dokuwiki/composer.lock
/dokuwiki/data/pages/wiki/syntax.txt
/dokuwiki/inc/Action/Register.php
/dokuwiki/inc/Cache/CacheImageMod.php
/dokuwiki/inc/Cache/CacheParser.php
/dokuwiki/inc/Cache/CacheRenderer.php
/dokuwiki/inc/Extension/AuthPlugin.php
/dokuwiki/inc/Feed/FeedParserFile.php
/dokuwiki/inc/File/MediaFile.php
/dokuwiki/inc/JpegMeta.php
/dokuwiki/inc/Parsing/Handler.php
/dokuwiki/inc/Parsing/Lexer/Lexer.php
/dokuwiki/inc/Parsing/Parser.php
/dokuwiki/inc/Parsing/ParserMode/AbstractMode.php
/dokuwiki/inc/Parsing/ParserMode/GfmQuote.php
/dokuwiki/inc/Parsing/ParserMode/Preformatted.php
/dokuwiki/inc/Remote/ApiCore.php
/dokuwiki/inc/Search/Collection/AbstractCollection.php
/dokuwiki/inc/Search/Collection/DirectCollection.php
/dokuwiki/inc/Search/Index/AbstractIndex.php
/dokuwiki/inc/Search/Index/Lock.php
/dokuwiki/inc/Search/Index/TupleOps.php
/dokuwiki/inc/Search/LegacyIndexer.php
/dokuwiki/inc/Search/Query/QueryEvaluator.php
/dokuwiki/inc/Search/Tokenizer.php
/dokuwiki/inc/Ui/Media/Display.php
/dokuwiki/inc/Ui/MediaDiff.php
/dokuwiki/inc/lang/cs/lang.php
/dokuwiki/inc/legacy.php
/dokuwiki/inc/media.php
/dokuwiki/inc/parser/metadata.php
/dokuwiki/inc/parser/xhtml.php
/dokuwiki/inc/template.php
/dokuwiki/lib/exe/css.php
/dokuwiki/lib/exe/fetch.php
/dokuwiki/lib/exe/js.php
/dokuwiki/lib/plugins/authad/auth.php
/dokuwiki/lib/plugins/authldap/auth.php
/dokuwiki/lib/plugins/authpdo/auth.php
/dokuwiki/lib/plugins/authplain/_test/userdata.test.php
/dokuwiki/lib/plugins/authplain/auth.php
/dokuwiki/lib/plugins/config/core/Setting/Setting.php
/dokuwiki/lib/plugins/config/core/Setting/SettingArray.php
/dokuwiki/lib/plugins/config/core/Setting/SettingEmail.php
/dokuwiki/lib/plugins/config/core/Setting/SettingImConvert.php
/dokuwiki/lib/plugins/config/core/Setting/SettingMulticheckbox.php
/dokuwiki/lib/plugins/config/core/Setting/SettingMultichoice.php
/dokuwiki/lib/plugins/config/core/Setting/SettingOnoff.php
/dokuwiki/lib/plugins/config/core/Setting/SettingSavedir.php
/dokuwiki/lib/plugins/config/core/Setting/SettingString.php
/dokuwiki/lib/plugins/config/lang/cs/lang.php
/dokuwiki/lib/plugins/config/lang/fr/lang.php
/dokuwiki/lib/plugins/usermanager/lang/cs/lang.php
/dokuwiki/lib/scripts/media.js
/dokuwiki/vendor/composer/installed.json
/dokuwiki/vendor/composer/installed.php
/dokuwiki/vendor/phpseclib/phpseclib/README.md
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DES.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/Formats/Keys/PKCS1.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/Formats/Keys/PKCS1.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/File/ASN1.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/File/X509.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Math/BigInteger.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Math/BigInteger/Engines/GMP.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Net/SFTP.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Net/SSH2.php
/dokuwiki/vendor/splitbrain/php-archive/src/Zip.php
/dokuwiki/vendor/splitbrain/slika/README.md
/dokuwiki/vendor/splitbrain/slika/src/Adapter.php
/dokuwiki/vendor/splitbrain/slika/src/GdAdapter.php
/dokuwiki/vendor/splitbrain/slika/src/ImageInfo.php
/dokuwiki/vendor/splitbrain/slika/src/ImageMagickAdapter.php
6372bc8006-Jul-2026 Andreas Gohr <gohr@cosmocode.de>

fix(changelog): detect an externally restored deleted page as a re-creation

A deleted page restored outside DokuWiki with a preserved mtime predating the
deletion (cp -p from an old backup, rsync --

fix(changelog): detect an externally restored deleted page as a re-creation

A deleted page restored outside DokuWiki with a preserved mtime predating the
deletion (cp -p from an old backup, rsync --times) has content matching the
delete revision's attic copy. That copy holds the pre-delete content, so the
unchanged-content shortcut in getCurrentRevisionInfo() wrongly treated the
restore as an unchanged file, touched the mtime back to the delete revision and
kept the DELETE as the current revision. The page then stayed "deleted" on every
subsequent read.

A last recorded revision of type DELETE means the page did not exist then, so an
existing file is an external re-creation regardless of its mtime.
getCurrentRevisionInfo() now classifies the external change and delegates to
synthesizeExternalDeletion/synthesizeExternalCreate/synthesizeExternalEdit; only
the edit path keeps the unchanged-content shortcut. A re-creation records the full
file as its size change and, when the restored mtime predates the delete, is dated
just after it with an unknown date.

The getCurrentRevisionInfo() method got rather unwieldy, so it was refactored to
use three helper methods, for synthesizing the changelog data.

show more ...


/dokuwiki/_test/composer.lock
/dokuwiki/_test/rector.php
/dokuwiki/_test/tests/ChangeLog/PageChangeLogTest.php
/dokuwiki/_test/tests/Feed/FeedParserTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/AbstractModeTest.php
/dokuwiki/_test/tests/Parsing/ParserMode/PreformattedTest.php
/dokuwiki/_test/tests/Remote/ApiCoreAclCheckTest.php
/dokuwiki/_test/tests/Search/Collection/CollectionSearchTest.php
/dokuwiki/_test/tests/Search/Collection/DirectCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/FrequencyCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/LookupCollectionTest.php
/dokuwiki/_test/tests/Search/Index/LockTest.php
/dokuwiki/_test/tests/Search/Index/MemoryIndexTest.php
/dokuwiki/_test/tests/Search/Index/TupleOpsTest.php
/dokuwiki/_test/tests/Search/Query/QueryEvaluatorTest.php
/dokuwiki/_test/tests/Search/Query/QueryParserTest.php
common_saveWikiText.test.php
/dokuwiki/composer.lock
/dokuwiki/data/pages/wiki/syntax.txt
/dokuwiki/inc/Action/Register.php
/dokuwiki/inc/Cache/CacheParser.php
/dokuwiki/inc/Cache/CacheRenderer.php
/dokuwiki/inc/ChangeLog/ChangeLog.php
/dokuwiki/inc/Extension/AuthPlugin.php
/dokuwiki/inc/Feed/FeedParserFile.php
/dokuwiki/inc/JpegMeta.php
/dokuwiki/inc/Parsing/Handler.php
/dokuwiki/inc/Parsing/Lexer/Lexer.php
/dokuwiki/inc/Parsing/Parser.php
/dokuwiki/inc/Parsing/ParserMode/AbstractMode.php
/dokuwiki/inc/Parsing/ParserMode/GfmQuote.php
/dokuwiki/inc/Parsing/ParserMode/Preformatted.php
/dokuwiki/inc/Remote/ApiCore.php
/dokuwiki/inc/Search/Collection/AbstractCollection.php
/dokuwiki/inc/Search/Collection/DirectCollection.php
/dokuwiki/inc/Search/Index/AbstractIndex.php
/dokuwiki/inc/Search/Index/Lock.php
/dokuwiki/inc/Search/Index/TupleOps.php
/dokuwiki/inc/Search/LegacyIndexer.php
/dokuwiki/inc/Search/Query/QueryEvaluator.php
/dokuwiki/inc/Search/Tokenizer.php
/dokuwiki/inc/lang/cs/lang.php
/dokuwiki/inc/legacy.php
/dokuwiki/inc/media.php
/dokuwiki/inc/parser/metadata.php
/dokuwiki/inc/parser/xhtml.php
/dokuwiki/lib/exe/css.php
/dokuwiki/lib/exe/js.php
/dokuwiki/lib/plugins/authad/auth.php
/dokuwiki/lib/plugins/authldap/auth.php
/dokuwiki/lib/plugins/authpdo/auth.php
/dokuwiki/lib/plugins/authplain/_test/userdata.test.php
/dokuwiki/lib/plugins/authplain/auth.php
/dokuwiki/lib/plugins/config/core/Setting/Setting.php
/dokuwiki/lib/plugins/config/core/Setting/SettingArray.php
/dokuwiki/lib/plugins/config/core/Setting/SettingEmail.php
/dokuwiki/lib/plugins/config/core/Setting/SettingImConvert.php
/dokuwiki/lib/plugins/config/core/Setting/SettingMulticheckbox.php
/dokuwiki/lib/plugins/config/core/Setting/SettingMultichoice.php
/dokuwiki/lib/plugins/config/core/Setting/SettingOnoff.php
/dokuwiki/lib/plugins/config/core/Setting/SettingSavedir.php
/dokuwiki/lib/plugins/config/core/Setting/SettingString.php
/dokuwiki/lib/plugins/config/lang/cs/lang.php
/dokuwiki/lib/plugins/config/lang/fr/lang.php
/dokuwiki/lib/plugins/usermanager/lang/cs/lang.php
/dokuwiki/lib/scripts/media.js
/dokuwiki/vendor/composer/installed.json
/dokuwiki/vendor/composer/installed.php
/dokuwiki/vendor/phpseclib/phpseclib/README.md
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DES.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/Formats/Keys/PKCS1.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/Formats/Keys/PKCS1.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/File/ASN1.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/File/X509.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Math/BigInteger.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Math/BigInteger/Engines/GMP.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Net/SFTP.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Net/SSH2.php
/dokuwiki/vendor/splitbrain/php-archive/src/Zip.php
40981bcc25-Jun-2026 Andreas Gohr <gohr@cosmocode.de>

Ip: validate CIDR mask to prevent fatal error and over-broad proxy trust

A non-numeric or empty mask in trustedproxies (e.g. 10.0.0.0/abc or
10.0.0.0/) threw an uncaught TypeError on the IPv4 path,

Ip: validate CIDR mask to prevent fatal error and over-broad proxy trust

A non-numeric or empty mask in trustedproxies (e.g. 10.0.0.0/abc or
10.0.0.0/) threw an uncaught TypeError on the IPv4 path, and a negative
mask (10.0.0.0/-1) passed the bounds check and produced a bitmask that
matched every IPv4, silently trusting all proxies.

Validate the mask as a non-negative integer in ipInRange() and broaden
the ipMatches() catch to Throwable so an invalid range degrades to
'no match' instead of a 500.

show more ...

b12755b007-Jun-2026 Andreas Gohr <andi@splitbrain.org>

Make common_pageinfo tests independent of execution order

The pageinfo() tests relied on running in a fixed order: test_editor_and_externaledits
mutated wiki:syntax (changelog entry + file mtime), a

Make common_pageinfo tests independent of execution order

The pageinfo() tests relied on running in a fixed order: test_editor_and_externaledits
mutated wiki:syntax (changelog entry + file mtime), and the other tests relied on
that page being pristine. Move the mutating test to its own page (wiki:dokuwiki) so
the shared per-class data dir stays clean, prime the last_change metadata within each
test instead of across tests, and fix the affected expectations. The suite now passes
in isolation and in random/reverse order.

While here, modernize the file:
- capture the pageinfo() result once instead of calling it twice
- add public/protected visibility markers to all methods
- convert array() to the short [] syntax
- replace the deprecated addLogEntry() with the PageFile API it wraps

show more ...

b8c2692f29-May-2026 Andreas Gohr <andi@splitbrain.org>

fix(httputils): build a proper internal URL for nginx X-Accel-Redirect

Unlike Apache's mod_xsendfile and lighttpd's X-LIGHTTPD-send-file,
which both accept an absolute file system path and stream th

fix(httputils): build a proper internal URL for nginx X-Accel-Redirect

Unlike Apache's mod_xsendfile and lighttpd's X-LIGHTTPD-send-file,
which both accept an absolute file system path and stream the file
directly, nginx treats X-Accel-Redirect as a URL: it performs an
internal subrequest against the value and resolves it through
`internal` location blocks in its own configuration. The redirect
target therefore must be a request path nginx can map back to a file,
not the file system path itself.

The previous implementation blindly stripped DOKU_INC's length from
the file path, which produced a broken URL whenever a data directory
had been relocated outside the DokuWiki tree.

Route the file through three cases instead: files inside DOKU_INC keep
their path relative to the wiki root; files in a relocated mediadir,
mediaolddir, cachedir or savedir are mapped back to their default URL
below data/; everything else falls through an opt-in /_x_accel_redirect/
prefix.

Path segments are URL-encoded so filenames with spaces or other
special characters resolve (fixes another potential bug in the previous
implementation).

Nginx configuration:

For the default layout no extra configuration is needed - files keep
their path relative to the wiki root and the regular wiki location
already serves them. For relocated data directories admins must add an
`internal` location below the wiki's URL space pointing at the actual
file system path, e.g.:

location /data/media/ { internal; alias /srv/dokuwiki-media/; }

For the /_x_accel_redirect/ fallback (used when a plugin serves files
from outside the wiki and its data directories), admins opt in by
adding:

location /_x_accel_redirect/ { internal; alias /; }

When the wiki is installed under a sub path, prefix both locations
accordingly (e.g. /wiki/data/media/ and /wiki/_x_accel_redirect/).

fixes: #2895

show more ...

7e687fd829-May-2026 Andreas Gohr <andi@splitbrain.org>

fix(auth): scope media ACL checks to the namespace

Media files have no per-file ACLs; permissions must be evaluated against
the namespace they live in. Several call sites passed the raw media ID
to

fix(auth): scope media ACL checks to the namespace

Media files have no per-file ACLs; permissions must be evaluated against
the namespace they live in. Several call sites passed the raw media ID
to auth_quickaclcheck(), so a page-intended exact-ID rule (e.g. on
wiki:secret.png) could silently apply to a media file sharing that ID.

Introduce mediaAclPath() that builds the correct namespace wildcard
path (handling root-namespace media) and route all media-related ACL
checks through it. Also normalize the lone `:X` sentinel variant in
fetch.functions.php to the standard `:*` form.

fixes: #4647

show more ...

36ba8ead12-May-2026 Andreas Gohr <andi@splitbrain.org>

test: add tests to catch #4637

Issue #4637 was fixed in 7686f2030b19f948d2e50df1613ef6592fa44b46 but I
didn't like that no test had caught the issue.

This adds a specific test for the issue as a Ha

test: add tests to catch #4637

Issue #4637 was fixed in 7686f2030b19f948d2e50df1613ef6592fa44b46 but I
didn't like that no test had caught the issue.

This adds a specific test for the issue as a HandlerTest. Additionally a
simple smoke test is added that renders the wiki:syntax page and
inspects the created DOM. It's not comprehensive but might help flagging
similar issue in the future.

show more ...

73dc0a8906-May-2026 Andreas Gohr <andi@splitbrain.org>

fix(mail): keep '&' intact in mailto links with multiple query params

Move the email-handling helpers (obfuscate, mail_isvalid,
mail_quotedprintable_encode, mail_setup) out of the procedural
inc/mai

fix(mail): keep '&' intact in mailto links with multiple query params

Move the email-handling helpers (obfuscate, mail_isvalid,
mail_quotedprintable_encode, mail_setup) out of the procedural
inc/mail.php into a namespaced dokuwiki\MailUtils class plus a new
Mailer::configInit(), and add a separate MailUtils::obfuscateUrl() for
the mailto-href context.

The xhtml renderer and PluginTrait now build the link label and the
href separately: the address half is run through the mailguard
obfuscation, the query string is preserved verbatim with only HTML
escaping applied. This fixes #1690 — in 'visible' mode the previous
code rawurlencoded the entire address+query, turning '?' into '%3F' and
breaking multi-parameter mailto links; in all modes the query string is
no longer mangled by the [at]/[dot] substitution.

Core call sites (Mailer, auth, LegacyApiCore, common, the xhtml
renderer, the parser, the bundled config/styling/usermanager plugins)
are migrated to MailUtils directly. The old top-level functions and
PREG_PATTERN_VALID_EMAIL constant remain as deprecated shims with
rector mappings.

Tests for obfuscate / mail_isvalid / mail_quotedprintable_encode are
consolidated into a single _test/tests/MailUtilsTest.php and extended
with regression coverage for the multi-parameter, double-escape and
URL-shape cases.

Closes #1690
Replaces #1964

show more ...


/dokuwiki/_test/data/media/wiki/exif-orient-6.jpg
/dokuwiki/_test/rector.php
/dokuwiki/_test/tests/File/MediaFileTest.php
/dokuwiki/_test/tests/MailUtilsTest.php
/dokuwiki/_test/tests/Ui/Media/DisplayTest.php
/dokuwiki/_test/tests/lib/exe/fetch_imagetoken.test.php
/dokuwiki/bin/indexer.php
/dokuwiki/composer.json
/dokuwiki/composer.lock
/dokuwiki/data/deleted.files
/dokuwiki/inc/Action/Search.php
/dokuwiki/inc/Ajax.php
/dokuwiki/inc/ChangeLog/ChangeLog.php
/dokuwiki/inc/Extension/PluginTrait.php
/dokuwiki/inc/Feed/FeedCreator.php
/dokuwiki/inc/File/MediaFile.php
/dokuwiki/inc/MailUtils.php
/dokuwiki/inc/Mailer.class.php
/dokuwiki/inc/Parsing/Handler.php
/dokuwiki/inc/Parsing/ParserMode/Emaillink.php
/dokuwiki/inc/Parsing/ParserMode/Internallink.php
/dokuwiki/inc/Remote/ApiCore.php
/dokuwiki/inc/Remote/LegacyApiCore.php
/dokuwiki/inc/Search/FulltextSearch.php
/dokuwiki/inc/Sitemap/Mapper.php
/dokuwiki/inc/TaskRunner.php
/dokuwiki/inc/Ui/Backlinks.php
/dokuwiki/inc/Ui/Media/Display.php
/dokuwiki/inc/Ui/MediaDiff.php
/dokuwiki/inc/Ui/Search.php
/dokuwiki/inc/Ui/SearchState.php
/dokuwiki/inc/auth.php
/dokuwiki/inc/common.php
/dokuwiki/inc/deprecated.php
/dokuwiki/inc/html.php
/dokuwiki/inc/infoutils.php
/dokuwiki/inc/init.php
/dokuwiki/inc/load.php
/dokuwiki/inc/media.php
/dokuwiki/inc/parser/xhtml.php
/dokuwiki/inc/search.php
/dokuwiki/inc/template.php
/dokuwiki/lib/exe/fetch.php
/dokuwiki/lib/plugins/config/core/Setting/SettingEmail.php
/dokuwiki/lib/plugins/info/syntax.php
/dokuwiki/lib/plugins/styling/_test/general.test.php
/dokuwiki/lib/plugins/usermanager/admin.php
/dokuwiki/lib/plugins/usermanager/remote.php
/dokuwiki/vendor/composer/installed.json
/dokuwiki/vendor/composer/installed.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/Formats/Keys/OpenSSH.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/File/ASN1.php
/dokuwiki/vendor/splitbrain/slika/README.md
/dokuwiki/vendor/splitbrain/slika/src/GdAdapter.php
/dokuwiki/vendor/splitbrain/slika/src/ImageInfo.php
01e8d73925-Apr-2026 Andreas Gohr <andi@splitbrain.org>

refactor(changelog): persist external-edit detection on first read

This addresses the flaky test that makes tests randomly fail (mostly on
windows runners).

The flake in common_saveWikiText_test::t

refactor(changelog): persist external-edit detection on first read

This addresses the flaky test that makes tests randomly fail (mostly on
windows runners).

The flake in common_saveWikiText_test::test_savesequence5 came from
this line in ChangeLog::getCurrentRevisionInfo():

'date' => max($lastRev + 1, time() - 1)

The synthesized "external delete" entry was kept in memory only and
only persisted later, when saveWikiText next called detectExternalEdit.
That meant the formula was evaluated twice on different ChangeLog
instances — once during the test's inspection, and again during the
following saveWikiText — and the two evaluations could pick different
seconds depending on how long the surrounding I/O took. The test
cached the first result in $expectExternal and asserted it against the
on-disk entry written during the second call. On the slower Windows
runner the second call sometimes crossed a second boundary, producing
the off-by-one date mismatch.

The questions I had was, why are we persisting external file deletions
(or edits) only when a page is saved when we are obviously already
detecting it earlier during the changelog read already?

Instead of recording the external delete at the time a new page is
written, it makes sense to record it as soon as we detect it (when the
changelog is requested by a user or a bot). This will make the recoded
timestamp closer to the actual deletion.

This patch refactors the changelog accordingly, but still tries to be
minimal invasive (I think the changelog handling would need much more
refactoring, but that's beyond the scope of this change).

To enable proper locking (when logging an external edit and copying
the attic file), locking had to be moved to the Changelog class,
duplicating some code of io_saveFile.

PageFile::detectExternalEdit() and the deprecated procedural wrapper
detectExternalEdit() in inc/common.php are removed. A codesearch.dokuwiki.org
check confirmed no plugin calls the method directly; the only external
caller of the procedural function is the farmsync plugin, which needs
a parallel update.

show more ...

90c2f6e318-Apr-2026 Andreas Gohr <andi@splitbrain.org>

Clean up stale realip references after client_ip_header rename

Update docblocks in Ip.php and common.php, fix old tests to use
the new config key, remove outdated translations, fix method casing
in

Clean up stale realip references after client_ip_header rename

Update docblocks in Ip.php and common.php, fix old tests to use
the new config key, remove outdated translations, fix method casing
in test, and add example to English config description.

show more ...

504c13e818-Apr-2026 Andreas Gohr <andi@splitbrain.org>

migrate parser tests to modern namespaced classes

Move old-style parser tests from _test/tests/inc/parser/ to namespaced
test classes under _test/tests/Parsing/ParserMode/ and
_test/tests/Parsing/Le

migrate parser tests to modern namespaced classes

Move old-style parser tests from _test/tests/inc/parser/ to namespaced
test classes under _test/tests/Parsing/ParserMode/ and
_test/tests/Parsing/Lexer/.

- Add ParserTestBase with assertCalls() helper for comparing handler
call sequences with byte index stripping
- Split lexer.test.php into ParallelRegexTest, StateStackTest, and
LexerTest with a RecordingHandler that extends Handler
- Merge handler_parse_highlight_options tests into CodeTest
- Add new tests for previously untested modes: Nocache, Notoc, Rss,
and all individual formatting modes (Strong, Emphasis, etc.)
- Modernize test code: [] syntax, lowercase null, correct assertEquals
argument order, replace deprecated withConsecutive and string callables
- Renderer tests remain in old location (renderers not yet migrated)

show more ...

71096e4618-Apr-2026 Andreas Gohr <andi@splitbrain.org>

move handler methods into ParserMode classes and rename Handler

Each ParserMode class now implements handle() from ModeInterface,
containing the token handling logic that previously lived as individ

move handler methods into ParserMode classes and rename Handler

Each ParserMode class now implements handle() from ModeInterface,
containing the token handling logic that previously lived as individual
methods on Doku_Handler.

The Handler class (formerly Doku_Handler) is the single dispatch point:
Lexer passes tokens to Handler::handleToken() which routes to mode
objects, plugins, or returns false. The Lexer only tokenizes and
resolves mapHandler aliases.

Key changes:
- Add handle() to ModeInterface, implemented by all mode classes
- Move Doku_Handler to dokuwiki\Parsing\Handler namespace
- File extends Code (shared parsing via $type property)
- Quotes uses mapHandler() + Handler::getModeName() for sub-modes
- Media::parseMedia() replaces Doku_Handler_Parse_Media()
- Code::parseHighlightOptions() replaces parse_highlight_options()
- Per-parse state (footnote, doublequote) stays on Handler
- Deprecated wrappers kept for base/header/internallink/media
- Class alias and rector rules added for backward compatibility

show more ...


/dokuwiki/_test/rector.php
/dokuwiki/_test/tests/Parsing/HandlerTest.php
/dokuwiki/_test/tests/Parsing/ModeRegistryTest.php
parser/handler_parse_highlight_options.test.php
parser/lexer.test.php
parser/parser.inc.php
parser/parser_quotes.test.php
/dokuwiki/inc/Cache/CacheParser.php
/dokuwiki/inc/Extension/SyntaxPlugin.php
/dokuwiki/inc/Parsing/Handler.php
/dokuwiki/inc/Parsing/Handler/CallWriter.php
/dokuwiki/inc/Parsing/Lexer/Lexer.php
/dokuwiki/inc/Parsing/ModeRegistry.php
/dokuwiki/inc/Parsing/Parser.php
/dokuwiki/inc/Parsing/ParserMode/AbstractFormatting.php
/dokuwiki/inc/Parsing/ParserMode/Acronym.php
/dokuwiki/inc/Parsing/ParserMode/Base.php
/dokuwiki/inc/Parsing/ParserMode/Camelcaselink.php
/dokuwiki/inc/Parsing/ParserMode/Code.php
/dokuwiki/inc/Parsing/ParserMode/Deleted.php
/dokuwiki/inc/Parsing/ParserMode/Emaillink.php
/dokuwiki/inc/Parsing/ParserMode/Emphasis.php
/dokuwiki/inc/Parsing/ParserMode/Entity.php
/dokuwiki/inc/Parsing/ParserMode/Eol.php
/dokuwiki/inc/Parsing/ParserMode/Externallink.php
/dokuwiki/inc/Parsing/ParserMode/File.php
/dokuwiki/inc/Parsing/ParserMode/Filelink.php
/dokuwiki/inc/Parsing/ParserMode/Footnote.php
/dokuwiki/inc/Parsing/ParserMode/Header.php
/dokuwiki/inc/Parsing/ParserMode/Hr.php
/dokuwiki/inc/Parsing/ParserMode/Internallink.php
/dokuwiki/inc/Parsing/ParserMode/Linebreak.php
/dokuwiki/inc/Parsing/ParserMode/Listblock.php
/dokuwiki/inc/Parsing/ParserMode/Media.php
/dokuwiki/inc/Parsing/ParserMode/ModeInterface.php
/dokuwiki/inc/Parsing/ParserMode/Monospace.php
/dokuwiki/inc/Parsing/ParserMode/Multiplyentity.php
/dokuwiki/inc/Parsing/ParserMode/Nocache.php
/dokuwiki/inc/Parsing/ParserMode/Notoc.php
/dokuwiki/inc/Parsing/ParserMode/Preformatted.php
/dokuwiki/inc/Parsing/ParserMode/Quote.php
/dokuwiki/inc/Parsing/ParserMode/Quotes.php
/dokuwiki/inc/Parsing/ParserMode/Rss.php
/dokuwiki/inc/Parsing/ParserMode/Smiley.php
/dokuwiki/inc/Parsing/ParserMode/Strong.php
/dokuwiki/inc/Parsing/ParserMode/Subscript.php
/dokuwiki/inc/Parsing/ParserMode/Superscript.php
/dokuwiki/inc/Parsing/ParserMode/Table.php
/dokuwiki/inc/Parsing/ParserMode/Underline.php
/dokuwiki/inc/Parsing/ParserMode/Unformatted.php
/dokuwiki/inc/Parsing/ParserMode/Windowssharelink.php
/dokuwiki/inc/Parsing/ParserMode/Wordblock.php
/dokuwiki/inc/deprecated.php
/dokuwiki/inc/legacy.php
/dokuwiki/inc/load.php
/dokuwiki/inc/parserutils.php
1f44347616-Apr-2026 Andreas Gohr <andi@splitbrain.org>

split Formatting into individual classes per formatting type

Introduce AbstractFormatting as a base class and seven concrete
classes (Strong, Emphasis, Underline, Monospace, Subscript,
Superscript,

split Formatting into individual classes per formatting type

Introduce AbstractFormatting as a base class and seven concrete
classes (Strong, Emphasis, Underline, Monospace, Subscript,
Superscript, Deleted) that each define their own patterns and
sort order. Delete the old Formatting class and update tests
to use the new classes directly. ModeRegistry now treats
formatting modes as regular built-in modes.

show more ...

c8dd1b9d16-Apr-2026 Andreas Gohr <andi@splitbrain.org>

introduce ModeRegistry to encapsulate parser mode categories

Replace the global $PARSER_MODES definition in inc/parser/parser.php
with a ModeRegistry singleton that initializes and manages the mode

introduce ModeRegistry to encapsulate parser mode categories

Replace the global $PARSER_MODES definition in inc/parser/parser.php
with a ModeRegistry singleton that initializes and manages the mode
categories. The global array is still populated for backward
compatibility with plugins that access it directly.

Mode constructors now use ModeRegistry::getModesForCategories()
instead of accessing the global directly. p_get_parsermodes() and
p_sort_modes() are moved to inc/deprecated.php as thin wrappers.

show more ...

8ab4ec3016-Apr-2026 Andreas Gohr <gohr@cosmocode.de>

remove dead ParallelRegex::apply() method

Remove apply() which was never called from production code. Rewrite
the inherited SimpleTest tests to use split() instead, and add a
test for pre/post-match

remove dead ParallelRegex::apply() method

Remove apply() which was never called from production code. Rewrite
the inherited SimpleTest tests to use split() instead, and add a
test for pre/post-match splitting.

show more ...


/dokuwiki/_test/rector.php
parser/lexer.test.php
/dokuwiki/composer.lock
/dokuwiki/data/deleted.files
/dokuwiki/inc/ErrorHandler.php
/dokuwiki/inc/Ip.php
/dokuwiki/inc/Manifest.php
/dokuwiki/inc/Parsing/Lexer/Lexer.php
/dokuwiki/inc/Parsing/Lexer/ParallelRegex.php
/dokuwiki/inc/PassHash.php
/dokuwiki/inc/fulltext.php
/dokuwiki/inc/lang/de-informal/lang.php
/dokuwiki/inc/lang/de/lang.php
/dokuwiki/inc/lang/en/lang.php
/dokuwiki/inc/lang/pl/lang.php
/dokuwiki/inc/lang/ru/lang.php
/dokuwiki/inc/parserutils.php
/dokuwiki/lib/images/larger.svg
/dokuwiki/lib/images/smaller.svg
/dokuwiki/lib/images/wrap.svg
/dokuwiki/lib/plugins/extension/Extension.php
/dokuwiki/lib/plugins/logviewer/style.less
/dokuwiki/lib/plugins/usermanager/lang/ru/lang.php
/dokuwiki/lib/scripts/editor.js
/dokuwiki/lib/scripts/page.js
/dokuwiki/lib/styles/screen.css
/dokuwiki/lib/tpl/dokuwiki/css/content.less
/dokuwiki/lib/tpl/dokuwiki/css/pagetools.less
/dokuwiki/vendor/composer/installed.json
/dokuwiki/vendor/composer/installed.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/AsymmetricKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/Formats/Keys/PKCS8.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DES.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DH.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Curves/Curve25519.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Curves/Curve448.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/Common.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/MontgomeryPrivate.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/OpenSSH.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/PKCS8.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Hash.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Rijndael.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Net/SSH2.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/openssl.cnf
fe6048cc14-Apr-2026 Alexander Lehmann <alexlehm@gmail.com>

remove realip option, add default in conf/dokuwiki.php

bfc167db11-Apr-2026 Andreas Gohr <andi@splitbrain.org>

Limit namespace depth in io_createNamespace() #4613

Throw a RuntimeException when the given ID contains 128 or more
colon-separated segments, preventing creation of excessively deep
directory hierar

Limit namespace depth in io_createNamespace() #4613

Throw a RuntimeException when the given ID contains 128 or more
colon-separated segments, preventing creation of excessively deep
directory hierarchies.

show more ...


/dokuwiki/_test/rector.php
io_createnamespace.test.php
/dokuwiki/composer.lock
/dokuwiki/inc/ErrorHandler.php
/dokuwiki/inc/Ip.php
/dokuwiki/inc/Manifest.php
/dokuwiki/inc/PassHash.php
/dokuwiki/inc/fulltext.php
/dokuwiki/inc/io.php
/dokuwiki/inc/lang/de-informal/lang.php
/dokuwiki/inc/lang/de/lang.php
/dokuwiki/inc/lang/en/lang.php
/dokuwiki/inc/lang/pl/lang.php
/dokuwiki/inc/parserutils.php
/dokuwiki/lib/plugins/extension/Extension.php
/dokuwiki/lib/scripts/page.js
/dokuwiki/lib/styles/screen.css
/dokuwiki/lib/tpl/dokuwiki/css/content.less
/dokuwiki/vendor/composer/installed.json
/dokuwiki/vendor/composer/installed.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/AsymmetricKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Common/Formats/Keys/PKCS8.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DES.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DH.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/DSA/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Curves/Curve25519.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Curves/Curve448.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/Common.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/MontgomeryPrivate.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/OpenSSH.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/Formats/Keys/PKCS8.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/EC/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Hash.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/PrivateKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/RSA/PublicKey.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Crypt/Rijndael.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/Net/SSH2.php
/dokuwiki/vendor/phpseclib/phpseclib/phpseclib/openssl.cnf
5e9d26e307-Apr-2026 Andreas Gohr <andi@splitbrain.org>

SearchIndex: move search() function tests back to tests/inc/search/

The search.test.php file tests the search() function from inc/search.php,
not the Search namespace classes. It was incorrectly mov

SearchIndex: move search() function tests back to tests/inc/search/

The search.test.php file tests the search() function from inc/search.php,
not the Search namespace classes. It was incorrectly moved into
tests/Search/ during the test suite reorganization. Move it and its
data files (ns1/, ns2/) back to their original location, keeping only
searchtest.txt in tests/Search/data/ where it belongs.

show more ...

e1272c0807-Apr-2026 Andreas Gohr <andi@splitbrain.org>

SearchIndex: add backward compatibility wrappers

Add deprecated wrappers for idx_* and ft_* functions that were removed
when inc/indexer.php and inc/fulltext.php were replaced by the new
Search clas

SearchIndex: add backward compatibility wrappers

Add deprecated wrappers for idx_* and ft_* functions that were removed
when inc/indexer.php and inc/fulltext.php were replaced by the new
Search classes. These wrappers delegate to the new architecture and
ensure existing plugins continue to work.

Deprecated standalone functions: idx_get_indexer, idx_getIndex,
idx_lookup, idx_listIndexLengths, idx_indexLengths, ft_pageSearch,
ft_backlinks, ft_mediause, ft_pageLookup, ft_snippet, ft_pagesorter,
ft_snippet_re_preprocess, ft_queryParser.

Deprecated methods on Indexer: lookupKey, getPages, addMetaKeys,
renameMetaValue, getPID, lookup.

Also migrates remaining core callers (Ajax, FeedCreator, ApiCore) to
use the new classes directly and fixes a UTF-8 case folding bug in
MetadataSearch title lookups.

show more ...

74a9499c07-Apr-2026 Andreas Gohr <andi@splitbrain.org>

SearchIndex: remove legacy intermediate classes from PR #2943

Remove FulltextIndex, MetadataIndex, and the old AbstractIndex which
were introduced as a stepping stone in #2943. All callers now use t

SearchIndex: remove legacy intermediate classes from PR #2943

Remove FulltextIndex, MetadataIndex, and the old AbstractIndex which
were introduced as a stepping stone in #2943. All callers now use the
Collection/Index architecture directly.

Also fix a bug in detail.php where mediause() was called with
ignore_perms=true, leaking references from hidden/protected pages
to unprivileged users. This bug existed on master as well.

Old test files replaced by their modernized equivalents in tests/Search/.

show more ...

ede4646606-Apr-2026 Andreas Gohr <andi@splitbrain.org>

SearchIndex: reorganize and expand test suite

Move all Search tests from _test/tests/inc/Search/ to _test/tests/Search/
to match the dokuwiki\test autoloader convention. Fix namespaces from
tests\*

SearchIndex: reorganize and expand test suite

Move all Search tests from _test/tests/inc/Search/ to _test/tests/Search/
to match the dokuwiki\test autoloader convention. Fix namespaces from
tests\* to dokuwiki\test\* so all tests work in isolation.

Extract inline test helpers into separate autoloadable mock files:
TestDirectCollection → MockDirectCollection, TestLookupCollection →
MockLookupCollection, TestFrequencyCollection → MockFrequencyCollection.

Rename AbstractIndexTest → AbstractIndexTestCase to fix PHPUnit warning
about abstract classes with Test suffix.

Replace dead xxxRealWord() with proper testWildcardSearch() verifying
exact token matches and frequencies for all three wildcard types.
Add testTokenizedPageSearch() using a dedicated test data file. Add
testNoMatchReturnsEmptyFrequencies() which exposed a bug in Term where
uninitialized $tokens/$frequencies caused crashes on zero-match terms.

Replace fulltext_query.test.php with modern QueryParserTest in the
Search\Query namespace.

Add new test files:
- LockTest: acquire/release, reference counting, stale lock override,
foreign lock rejection, releaseAll, independent locks
- NamespacePredicateTest: filter/exclude, sub-namespaces, partial prefix
safety, empty sets, score preservation
- PageSetTest: intersect, unite, subtract, isEmpty
- QueryEvaluatorTest: word lookups, AND/OR/NOT, namespace filtering,
combined queries, partial namespace prefix safety

Fix Term.php: initialize $tokens and $frequencies to [] instead of null.

show more ...


/dokuwiki/_test/tests/Search/Collection/DirectCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/FrequencyCollectionSearchTest.php
/dokuwiki/_test/tests/Search/Collection/FrequencyCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/LookupCollectionTest.php
/dokuwiki/_test/tests/Search/Collection/MockDirectCollection.php
/dokuwiki/_test/tests/Search/Collection/MockFrequencyCollection.php
/dokuwiki/_test/tests/Search/Collection/MockLookupCollection.php
/dokuwiki/_test/tests/Search/Collection/TermTest.php
/dokuwiki/_test/tests/Search/Index/AbstractIndexTestCase.php
/dokuwiki/_test/tests/Search/Index/FileIndexTest.php
/dokuwiki/_test/tests/Search/Index/LockTest.php
/dokuwiki/_test/tests/Search/Index/MemoryIndexTest.php
/dokuwiki/_test/tests/Search/Index/TupleOpsTest.php
/dokuwiki/_test/tests/Search/IndexerTest.php
/dokuwiki/_test/tests/Search/Query/NamespacePredicateTest.php
/dokuwiki/_test/tests/Search/Query/PageSetTest.php
/dokuwiki/_test/tests/Search/Query/QueryEvaluatorTest.php
/dokuwiki/_test/tests/Search/Query/QueryParserTest.php
/dokuwiki/_test/tests/Search/data/ns1/ns3/page3.txt
/dokuwiki/_test/tests/Search/data/ns1/page1.txt
/dokuwiki/_test/tests/Search/data/ns1/page2.txt
/dokuwiki/_test/tests/Search/data/ns2/nopage.ext
/dokuwiki/_test/tests/Search/data/ns2/page1.txt
/dokuwiki/_test/tests/Search/data/searchtest.txt
/dokuwiki/_test/tests/Search/search.test.php
/dokuwiki/inc/Action/Search.php
/dokuwiki/inc/Remote/ApiCore.php
/dokuwiki/inc/Search/Collection/Term.php
/dokuwiki/inc/Search/FulltextSearch.php
/dokuwiki/inc/Search/MetadataSearch.php
/dokuwiki/inc/Search/Query/NamespacePredicate.php
/dokuwiki/inc/Search/Query/NegatedEntry.php
/dokuwiki/inc/Search/Query/PageSet.php
/dokuwiki/inc/Search/Query/QueryEvaluator.php
/dokuwiki/inc/Search/Query/QueryParser.php
/dokuwiki/inc/Search/Query/StackEntry.php
/dokuwiki/inc/Ui/Search.php
/dokuwiki/inc/Ui/SearchState.php

12345678910>>...24