1
0
mirror of https://github.com/Jermolene/TiddlyWiki5 synced 2026-05-02 11:41:30 +00:00

Compare commits

...

110 Commits

Author SHA1 Message Date
Jeremy Ruston
ea84baa5a3 Merge branch 'tiddlywiki-com' 2026-04-21 20:24:23 +01:00
Mario Pietsch
a4e4d36bf6 Fix Typo in Link in Multi-Valued Variables (#9824) 2026-04-20 21:31:52 +01:00
Mario Pietsch
3ed481b2e2 Update the Archive and Release Notes Description (#9823) 2026-04-20 21:31:09 +01:00
Jeremy Ruston
27c60ff58d Prepare for v5.5.0 2026-04-20 20:03:12 +01:00
Jeremy Ruston
748ef8aa8d New release should be first thumbnail 2026-04-20 19:56:08 +01:00
Jeremy Ruston
9cfa5a29fb Version number update for 5.4.0 2026-04-20 19:36:07 +01:00
Jeremy Ruston
5ea43ce212 Revert package.json 2026-04-20 19:35:55 +01:00
Jeremy Ruston
df6bbbdedf More v5.4.0 preparations 2026-04-20 19:33:07 +01:00
Jeremy Ruston
37a461323e Preparing for release of v5.4.0 2026-04-20 19:31:36 +01:00
Cameron Fischer
b29da7baac I didn't capitalize one of the instances of my name (#9822) 2026-04-19 16:42:52 +01:00
Mario Pietsch
75b54457ed German translations update (#9821)
* German translations update

* fix typo
2026-04-18 15:16:32 +01:00
superuser-does
51f322c3c6 [5.4.0] Add release note for Greek translation update (#9818)
* [5.4.0] Add release note for Greek translation update

Add release note for #9782

* Remove trailing newline
2026-04-18 14:03:27 +01:00
lin onetwo
853af2d848 Fix: limit macro call parser to need >> to work, prevent > in regex (#9813)
* fix: limit macro call parser to need >> to work, prevent > in regex

* test: add malformed macro parameter regression coverage

The parser fix on this branch only changes parseMacroParameterAsAttribute() when an unquoted value starts with <<, so the previous broader parser tests did not prove the regression. Add a focused structural test that fails without the guard and passes with it.

Ultraworked with [Sisyphus](https://github.com/code-yeongyu/oh-my-openagent)

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>

* Revert "fix: limit macro call parser to need >> to work, prevent > in regex"

This reverts commit f96b062902.

* lint: test

* Reapply "fix: limit macro call parser to need >> to work, prevent > in regex"

This reverts commit 075f7cc282.

---------

Co-authored-by: Sisyphus <clio-agent@sisyphuslabs.ai>
2026-04-18 09:59:22 +01:00
Jeremy Ruston
2c1cb33081 Restore v5.3.8 handling of malformed attribute syntax (#9812)
Also add a bunch of tests

Fixes #9808
2026-04-18 09:56:22 +01:00
Keiran Harcombe
2f63abc12a Merge pull request #9809 from kjharcombe/master
Remove CNAME
2026-04-15 10:34:50 +01:00
Keiran Harcombe
5f80256576 Remove CNAME
I've removed the CNAME file which is blocking access to Yunohost
2026-04-14 12:44:30 +01:00
Jeremy Ruston
aa837300d0 Update Chinese translation change note 2026-04-13 17:10:03 +01:00
Bram Chen
7f2baa17a9 Update chinese translations (#9804)
* Update chinese translations

* Update languages/zh-Hans/ControlPanel.multids (commit 33b2f51)
* Update languages/zh-Hant/ControlPanel.multids (commit 33b2f51)
* Update languages/zh-Hans/Import.multids (commit b673651)
* Update languages/zh-Hant/Import.multids (commit b673651)
* Update languages/zh-Hans/TiddlerInfo.multids (commit 0177f09, cd8b1fa )
* Update languages/zh-Hant/TiddlerInfo.multids (commit 0177f09, cd8b1fa )
* Add languages/zh-Hant/Draft.multids (commit 9c09841)

* Update chinese translations

* Clarify wording of tiddler info cascade view
2026-04-13 17:08:23 +01:00
Jeremy Ruston
39c6d8fb53 Missing change notes
Fixes #9773
2026-04-12 14:50:40 +01:00
Jeremy Ruston
9afe5226f1 Clarify wording of tiddler info cascade view 2026-04-12 14:33:52 +01:00
Jeremy Ruston
94aa37fe7e Merge branch 'tiddlywiki-com' 2026-04-11 08:38:49 +01:00
superuser-does
1e9c1ef82a [DOCS] Fix MWS Banner image display (#9801) 2026-04-11 08:45:27 +02:00
Saq Imtiaz
6cde5e94ff Update pr-validation.yml to use Cerebrus v8.1 2026-04-11 08:45:01 +02:00
Saq Imtiaz
fd0d3ccc27 Revert "Replace fill rules in tw5.com edition (#9624)" (#9800)
This reverts commit dc764b3a4a.
2026-04-10 12:23:37 +02:00
Saq Imtiaz
1ad2e66cbc Revert "Use currentColor to style svg (#9316)" (#9799)
This reverts commit dc7f2a57bb.
2026-04-10 12:23:07 +02:00
Saq Imtiaz
4699db9f89 Revert "Fix side effects of PR 9316 (#9568)" (#9798)
This reverts commit bf7c0b575c.
2026-04-10 12:22:41 +02:00
lin onetwo
d977b0ac5c Fix #9788: only allow colon-separator named params with strict identifiers (#9791)
The reAttributeName regexp in parseMacroParameterAsAttribute was too
permissive, allowing single-character names like dollar sign followed by
colon. This caused values such as dollar-colon-slash-plugins-foo to be
mis-parsed as a named parameter dollar with value slash-plugins-foo.

Fix: when the separator is colon (legacy syntax), require the parameter
name to match [A-Za-z0-9-_]+ (same as the historic parseMacroParameter).
When the separator is equals (new-style dynamic parameters from #9055),
the wide character set is preserved so that names like double-dollar-one
continue to work.

Adds regression test Transclude/Procedures/Dollar/Param.
2026-04-10 11:06:07 +02:00
Saq Imtiaz
7298684951 Update package.json to resolve CI issues 2026-04-10 08:35:32 +02:00
Mario Pietsch
f78d8252af Fix issue #9795 tree view regression (#9796) 2026-04-10 08:29:54 +02:00
Saq Imtiaz
54260b5be8 Updates Cerebrus action to v8.1 (#9793)
* Update pr-check-build-size.yml

* Update pr-comment-build-size.yml

* Update pr-validation.yml
2026-04-09 09:13:45 +02:00
IchijikuIchigo
95f12eb857 [ja_JP] Update of Japanese translations (#9792)
* [ja_JP] Japanese translation update from commit: a71ac56

* [ja_JP] Japanese translation update from commit: 32a3a3e

* [ja_JP] Japanese translation update from commit: 65fcded

* [ja_JP] Japanese translation update from commit: a3acbaa

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\functions\Functions.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\functions\Functions.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\definitions\Base64.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\definitions\Definitions.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\definitions\Cascading Style Sheets.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\definitions\Tiddlyhost.tid'
2026-04-07 14:56:55 +02:00
IchijikuIchigo
207a68cc59 [ja_JP] Japanese translation update - 'Reference' section of tiddlywiki.com (#9790)
* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\reference\Reference.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\concepts\WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Horizontal Rules in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\_tw_shared\doc-utilities\wikitext-macros.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Block Quotes in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Code Blocks in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Conditional Shortcut Syntax.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Block Quotes in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Block Quotes in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Dashes in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Description Lists in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Filtered Attribute Values.tid'

* [ja-JP] A little correction to the Japanese translation

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Formatting in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Headings in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Paragraphs in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Hard Linebreaks in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\howtos\Hard_Linebreaks_with_CSS.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\howtos\Hard_Linebreaks_with_CSS_-_Example.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\HTML Entities.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Literal Attribute Values.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Lists in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Tables in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Table Classes Captions Headers and Footers.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Transcluded Attribute Values.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Utility Classes.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Widgets in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\parser\WikiText Parser Modes.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\HTML in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\HTML_Links_in_WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Typed Blocks in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Anchor Links using HTML.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Linking in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Macro Calls.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Macro Definitions.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Macro Parameter Handling.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Substituted Attribute Values.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Substituted Attribute Values.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\Concatenating variables to create a URL.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\Concatenating a text reference to create a URL.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\procedures\Procedure Calls.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\procedures\Procedure Definitions.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\procedures\Procedure Parameter Handling.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Transclusion and Substitution.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Transclusion in WikiText.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Transclusion Basic Usage.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Transclusion Basic Usage.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Transclusion with Templates.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Variable Attribute Values.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\variables\Behaviour of variables invoked via widget attributes.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Tables in WikiText CSS Utility Classes.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\Widget Attributes.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\concepts\TemplateTiddlers.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\concepts\Transclusion.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\parser\table-example.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\wikitext\parser\WikiText parser mode_ transclusion examples.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\concepts\TextReference.tid'
2026-04-06 11:34:48 +02:00
superuser-does
b434b9d7ea [DOCS] Include description lists in lists tiddler (#9786) 2026-04-05 10:55:36 +01:00
superuser-does
b0013333de [DOCS] Expand description list documentation (#9784)
* [DOCS] Expand description list documentation

* remove stray word
2026-04-05 10:15:15 +01:00
superuser-does
bcc30e305a Update Greek translation for 5.4.0 (#9782)
* Update Greek translation for 5.4.0

* Add Greek translation for Draft

* Correction to 'Saving'
2026-04-04 14:08:54 +01:00
Jeremy Ruston
34f4dfb903 Merge branch 'tiddlywiki-com' 2026-04-04 09:23:58 +01:00
superuser-does
32a3a3e478 [DOCS] Clean up Forums tiddler (#9780) 2026-04-04 08:49:55 +01:00
Bram Chen
c6520c4429 Update chinese translations (#9781)
* Update languages/zh-Hans/ControlPanel.multids (commit 33b2f51)
* Update languages/zh-Hant/ControlPanel.multids (commit 33b2f51)
* Update languages/zh-Hans/Import.multids (commit b673651)
* Update languages/zh-Hant/Import.multids (commit b673651)
* Update languages/zh-Hans/TiddlerInfo.multids (commit 0177f09, cd8b1fa )
* Update languages/zh-Hant/TiddlerInfo.multids (commit 0177f09, cd8b1fa )
* Add languages/zh-Hant/Draft.multids (commit 9c09841)
2026-04-04 08:48:34 +01:00
Jeremy Ruston
83d242fb2c Merge branch 'tiddlywiki-com' 2026-04-03 11:10:58 +01:00
Jeremy Ruston
ecafb7a4c0 A very minor tweak to the donation graphic
Spot the difference; the wonky text was offending me
2026-04-03 11:10:45 +01:00
Jeremy Ruston
0640e0abe2 Merge branch 'tiddlywiki-com' 2026-04-03 11:00:11 +01:00
Jeremy Ruston
a71ac56cc9 More prominent donations link 2026-04-03 10:49:26 +01:00
Jeremy Ruston
f518bdf27c Hire Jeremy banner now defaults to just being in the sidebar 2026-04-03 10:49:14 +01:00
Jeremy Ruston
0387b1100b Update CI dependencies 2026-04-01 17:13:32 +01:00
Jeremy Ruston
c3a73fccd1 Fixed typo in v5.3.8 change note 2026-04-01 17:00:29 +01:00
Jeremy Ruston
c25659d87c Restore compact call syntax (#9778)
* Initial commit

* Oops broken test
2026-04-01 15:22:42 +02:00
Saq Imtiaz
0c26a75472 Updates cerebrus action to v8 (#9779)
* Update pr-validation.yml

* Update pr-comment-build-size.yml

* Update pr-check-build-size.yml
2026-04-01 15:21:16 +02:00
Saq Imtiaz
a24dc0e9e8 Update package.json to allow all current LTS versions of nodejs 2026-04-01 15:13:27 +02:00
Jeremy Ruston
a499ed0906 Fix CI
Broken by 3cfb6b1202
2026-04-01 13:22:42 +01:00
Jeremy Ruston
3cfb6b1202 Update minimum Node version for as discussed for v5.4.0 2026-04-01 11:51:43 +01:00
Jeremy Ruston
ac769e5dcd Commit package-lock.json
Benefit is that it pins dependencies and sub-dependencies, helping mitigate supply chain attacks
2026-04-01 11:42:17 +01:00
Jeremy Ruston
ed01af8e47 Update release note with new release banner 2026-03-31 18:43:00 +01:00
Jeremy Ruston
92caa7312e Update new release banner
See https://talk.tiddlywiki.org/t/discussion-ai-and-vote-for-the-banner-for-5-4-0/15108/10
2026-03-31 18:25:20 +01:00
Mario Pietsch
478dce7009 fix problem with idDate() duplication in boot.js (#9771) 2026-03-31 18:50:31 +02:00
IchijikuIchigo
f3c9cb2310 [ja_JP] Update Japanese translation (#9768)
* [ja_JP] Japanese translation update from commit: 5d0d2b1, e8fe6b9, 33b2f51

* [ja_JP] Japanese translation update from commit: 3543fe5

* [ja_JP] Japanese translation update from commit: 9c09841

* [ja_JP] Japanese translation update from commit: 390b755, 3e966d4, d17525e

* [ja_JP] Japanese translation update from commit: 4007610, 65afdac

* [ja_JP] Japanese translation update from commit: 5e8420a, 2adf091

* [ja_JP] Japanese translation update from commit: b673651

* [ja_JP] Japanese translation update from commit: a494361, 3af2a0a, 0e765bd

* [ja_JP] Japanese translation update from commit: daa24a5

* [ja_JP] Japanese translation update from commit: daa24a5, 881aed8

* [ja_JP] Japanese translation update from commit: 98e7255

* [ja_JP] Japanese translation update from commit: 4d9e683, cd8b1fa, 0177f09

* [ja_JP] Japanese translation update from commit: a494361

* [ja_JP] Japanese translation update from commit: eee3a0c, 169a381, f4fd5e7, 6332089, 1ce9973, c05c0d3, 9268a8c, e16635a

* [ja_JP] Delete duplicate Japanese translation files

* [ja_JP] Japanese translation update from commit: c02c3a0

* [ja_JP] Japanese translation update from commit: 147d758

* [ja_JP] Japanese translation update from commit: c6e4b7a, c4e2793, 12630d4

* [ja_JP] Japanese translation update from commit: 11b09be

* [ja_JP] Japanese translation update from commit: f7e50e0, e9557b5, 4ccdaf3, 6f93ce6

* [ja_JP] Japanese translation update from commit: f7e50e0, e9557b5, e87dadd, 814353d, 35a7a66, 5d91c27

* [ja_JP] Japanese translation update from commit: f7e50e0, e9557b5, 35a7a66

* [ja_JP] Japanese translation update from commit: d880cb1, 5176f00, 814353d, 35a7a66

* [ja_JP] Japanese translation update from commit: 5e8420a, 2adf091
2026-03-30 07:52:57 +02:00
Cameron Fischer
85fb634cae Moved bulkops relink behavior into dedicated module (#9703)
* Moved bulkops relink behavior into dedicated module

* Release notes

* Fixes for lint
2026-03-28 12:06:27 +00:00
Saq Imtiaz
280701fbde Fixes MVV's so that getVariableInfo returns undefined (#9765)
* wip: non-existent variables as attributes should be undefined

* wip: non-existent variables as attributes should be undefined

* tests: added missing test

* fix: restore mistakenly commited files

* fix: whitespace
2026-03-28 12:04:29 +00:00
Saq Imtiaz
01d3cde964 Fixes an issue where blockquotes trigger parsing as macros (#9695)
* fix: blockquotes trigger parsing as macros

* fix: blockquotes trigger parsing as macros

* fix: remove backwards incompatible change

* fix: whitespace

* fix: whitespace

* merge improvents from @hoelzro
2026-03-25 12:24:32 +01:00
Jeremy Ruston
2ea3663ea7 Merge branch 'tiddlywiki-com' 2026-03-24 17:14:24 +00:00
Jeremy Ruston
78b6f6f442 Docs: clarify parameters within calls in filters 2026-03-24 12:23:58 +00:00
Jeremy Ruston
3a4a8a206f Hotfix for broken test for dates
Fixes #9726
2026-03-24 11:19:17 +00:00
Mario Pietsch
aff5be7195 fix flaky test runner (#9718) 2026-03-24 09:48:32 +01:00
Mario Pietsch
c4991a54a0 Some minor changes to the filter docs (#9709)
* Some minor changes to the filter docs

* Fix wording in Intersection Filter Run Prefix documentation
2026-03-24 09:46:03 +01:00
Mario Pietsch
1d915389d9 Gitignore for automated tests (#9761)
* Add elements to gitignore, that are used for automated future test

* Add playwright configuration for Edge users that have no Chrome installed

* update tw-mcp setting
2026-03-22 08:42:13 +00:00
Mario Pietsch
f5b4b1781e Fix edit toolbar button spaceing (#9763) 2026-03-22 08:31:38 +00:00
Mario Pietsch
65fcded29f Fix name clashes - definition tiddlers with images (#9759) 2026-03-20 07:54:03 +00:00
Urban Alič
962692c90c FIX: restore mhchem require for \ce and \pu macro support (#9756) 2026-03-19 22:34:56 +00:00
Mario Pietsch
533414b1df Change codewrapping option to pre-wrap
Fixes: #9757

Changed at: https://github.com/TiddlyWiki/TiddlyWiki5/pull/9107/changes#diff-9c7b0f26dc347b90265ea42dd89565ecf1d7b85ac8b5ff3f7dc49eeec42003b5

Talk:  https://talk.tiddlywiki.org/t/5-4-0-prerelease-code-lines-pre-wrap-setting-as-default/15066
2026-03-19 19:47:26 +01:00
Himmel
ec27a4bf20 Add new contributor Himmel to CLA (#9755) 2026-03-19 07:12:33 +00:00
Jeremy Ruston
e1cf523e2c Merge branch 'tiddlywiki-com' 2026-03-17 13:20:55 +00:00
Keiran Harcombe
1ece822d7a Update kjharcombe.tid (#9750)
I've created my community card for tiddlywiki.com
2026-03-16 23:27:50 +00:00
Keiran Harcombe
b7a3418823 Signing CLA (#9749) 2026-03-16 21:58:42 +00:00
Xavier Cazin
bb6d88f144 fr-FR translation catchup before 5.4.0 (#9748)
* fr-FR translation for the Alerts aria string

* fr-FR translation for WikiInformation-related strings

* fr-FR updates for TiddlySpot/TiddlyHost-related strings

* fr-FR translation for Stability- and InfoTab-related strings
2026-03-16 17:08:06 +00:00
Jeremy Ruston
57c72756ef Fix releasenote avatars
Fixes #9746

Thanks @pmario
2026-03-16 16:57:55 +00:00
Jeremy Ruston
dda4c7fb10 Update to latest version of dom-to-image-more library
Include it in tw5.com for testing
2026-03-15 16:53:51 +00:00
Jeremy Ruston
fd3b96e2dd Merge branch 'tiddlywiki-com' 2026-03-15 10:46:16 +00:00
Jeremy Ruston
c07396c453 Community: Add @kjharcombe as infrastructure team lead
Please add your community card when you can, many thanks.
2026-03-15 10:46:02 +00:00
Jeremy Ruston
7fc255f90c Merge branch 'tiddlywiki-com' 2026-03-14 18:18:09 +00:00
Jeremy Ruston
4cd84a6ba1 Geospatial plugin: remove residue of dom-to-image plugin
Fixes #9683
2026-03-11 17:30:23 +00:00
Jeremy Ruston
fdfcd66c9b dom-to-image fix indentation 2026-03-11 17:14:47 +00:00
Andrew Gregory
3983086b96 Document alternating table row styling (#9713)
* Document alternating table row styling

Resolves issue #8738 (and explains why my old wiki row styles were swapped).

* Make note more prominent

Use note macro for note

Co-authored-by: Mario Pietsch <pmariojo@gmail.com>

---------

Co-authored-by: Mario Pietsch <pmariojo@gmail.com>
2026-03-11 14:22:49 +00:00
Jeremy Ruston
a61331e6ed Fix readme for tw5.com-docs plugin
Fixes #9721
2026-03-11 13:50:37 +00:00
Jeremy Ruston
8773a0433c Dynaview: Fix RSOE with Update address bar while scrolling
See https://talk.tiddlywiki.org/t/your-help-is-needed-to-test-v5-4-0/14945/52
2026-03-11 12:22:14 +00:00
Mario Pietsch
846deb3039 Git Ignore Claude AI local settings (#9719) 2026-03-09 17:09:07 +00:00
Saq Imtiaz
111a168b0c feat: added community card for saqimtiaz (#9701) 2026-03-06 22:47:35 +00:00
Cameron Fischer
02b4c04a56 Release notes for PRs I've made, as requested (#9707)
* Release notes for PRs I've made, as requested

* Update #9297.tid

blog -> blob
2026-03-03 09:23:27 +01:00
Saq Imtiaz
9d5b5111d0 Revert "Add locale support for sort operator (#9400)" (#9702)
This reverts commit 98a61f01bb.
2026-03-01 08:02:18 +01:00
btheado
48cff401b2 Add tests/examples for transclusion shortcut syntax (#9705) 2026-03-01 07:58:59 +01:00
Saq Imtiaz
7a866b93e3 fix: alt support for images in markdown (#9700) 2026-02-27 18:53:58 +01:00
s793016
b0d99f3bd3 Fix Freelinks Aho-Corasick: failure links, cache invalidation, longest-match, and Unicode safety (#9676)
* Update aho-corasick.js

 fix transition logic; ensure complete outputs (via failure-output merge); clean up stats/build scoping; clarify CJK boundary behavior.

* Update text.js

implement global longest-match priority with overlap suppression; fix refresh invalidation to ignore $:/state and drafts; handle deletions precisely to avoid rebuilding on draft deletion; add defensive check for cached automaton presence.

* Update text.js

remove comment

* Update aho-corasick.js

remove comment

* Create #9672.tid

* Create #2026-0222.tid

* Delete editions/tw5.com/tiddlers/releasenotes/5.4.0/#2026-0222.tid

* Update text.js

remove \"

* Update and rename #9672.tid to #9676.tid

change to right number

* Update #9397.tid

update the existing release note with the new PR link instead of creating a new release note.

* Delete editions/tw5.com/tiddlers/releasenotes/5.4.0/#9676.tid

update the existing release note with the new PR link instead of creating a new release note.

* Rename #9397.tid to #9676.tid

update the existing release note with the new PR link instead of creating a new release note.

* Update and rename #9676.tid to #9397.tid

add link

* Rename #9397.tid to #9676.tid

* Update tiddlywiki.info

add plugin for test build

* Update tiddlywiki.info

reverse change, ready to be merge.
2026-02-25 12:07:32 +01:00
Andrew Gregory
91e7a62c13 docs: Tabs examples dynamically setting default tab (#9693)
Where tabs have been selected using a filter it is sometimes useful to set the default tab dynamically from the filter results. In most of these cases it is also desirable that the state not be persistent.
2026-02-25 08:14:38 +01:00
Saq Imtiaz
9f7763710e fix: MVV handling should distinguish between blank and undefined attributes (#9687) 2026-02-24 11:12:21 +01:00
lin onetwo
b673651103 Fixes slow when import html on upgrade (#9689)
* Short-circuit the import option; only show it when you click a button

* Add aira-label

Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>

* perf(import): lazy evaluate import options panel, shortcircuit when no options, and flatten let widgets

- Only parse $:/Import JSON when user expands the import options panel
- Skip all import option logic if no $:/tags/ImportOptions tiddlers exist
- Merge nested let widgets into single multi-variable let for better performance and readability
- Add lingo for import options panel and no-match message

This greatly improves import speed for large wikis, especially when no import options are present.

* fix(import): use correct transclusion for aria-label on import options panel buttons\n\nBind aria-label using {{$:/language/Import/Listing/ImportOptions/Caption}} instead of macro literal, matching TiddlyWiki convention and ensuring accessibility tools read the correct label.

---------

Co-authored-by: Copilot <175728472+Copilot@users.noreply.github.com>
2026-02-23 11:58:24 +01:00
Saq Imtiaz
49faefcca5 fix: zoomin storyview should not remove CSS properties when element is already removed (#9686) 2026-02-23 08:59:32 +01:00
Saq Imtiaz
75c26b46c6 fix: missing attributes must be undefined (#9682) 2026-02-22 22:16:07 +01:00
btheado
add3d425b5 Add let filter run examples (#9681)
* Add :let filter run prefix examples

Includes one example from @yaisog at #8972

* Added link to the new :let filter run examples

* Fixed broken link
2026-02-22 21:10:10 +01:00
Mario Pietsch
c23a0bedfd Add some links and info text to release notes (#9680) 2026-02-22 17:44:42 +00:00
Saq Imtiaz
36b20e02a3 ci: update to v7 cerebrus 2026-02-22 17:43:47 +01:00
Saq Imtiaz
ab6172981c Update cerebrus action to version 7 2026-02-22 17:40:41 +01:00
lin onetwo
431b7fa3bf Update ImportListing.tid (#9674) 2026-02-21 17:37:37 +00:00
Jeremy Ruston
1c1f157079 More release note tweaks 2026-02-20 21:26:44 +00:00
Jeremy Ruston
ac19f300a9 Fix changenote 2026-02-20 12:05:51 +00:00
Jeremy Ruston
9012b00806 Search changenotes and impact notes (#9670)
* Tweak some changenotes

* Tweak release note tabs

* Simplify summary tab

* Remove #8702 changes/impacts

* Search change notes and impacts

* Fix release note category search

* Tweak headline changenotes
2026-02-20 12:02:14 +00:00
Jeremy Ruston
a3acbaa2f1 Update road map 2026-02-20 09:30:25 +00:00
Jeremy Ruston
07634d6595 Merge branch 'tiddlywiki-com' 2026-02-20 09:28:07 +00:00
Saq Imtiaz
785086e0a5 Fixes ESLint errors (#9668)
* fix: apply automatic eslint fixes

* lint: allow hashbang comment for tiddlywiki.js

* lint: first back of manual lint fixes for unused vars

* lint: added more fixes for unused vars

* lint: missed files

* lint: updated eslint config with selected rules from #9669
2026-02-20 08:38:42 +00:00
IchijikuIchigo
8cd6bbc075 [ja_JP] Japanese translation update - 'Community' section of tiddlywiki.com (#9662)
* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 381388f, 4dc89f6, 5fa1098

* [ja_JP] Japanese translation update from commit: 3c1d658

* [ja_JP] Japanese translation update from commit: 3c1d658

* [ja_JP] Japanese translation update from commit: 29a567f, 6aee5eb

* [ja_JP] Japanese translation update from commit: 0ac2b6c

* [ja_JP] Japanese translation update from commit: 1994574

* [ja_JP] Japanese translation update from commit: 5dfdbc8

* [ja_JP] Japanese translation update from commit: 1994574

* [ja_JP] Japanese translation update from commit: 81d8d67

* [ja_JP] Japanese translation update from commit: 81d8d67

* [ja_JP] Japanese translation update from commit: 4196d96

* [ja_JP] Japanese translation update from commit: 1994574

* [ja_JP] Japanese translation update from commit: 1994574

* [ja-JP] Japanese translation of 'community\project\TiddlyWiki Project.tid'

* [ja-JP] Japanese translation of 'community\docs\Community Cards Caveats.tid'

* [ja-JP] Japanese translation of 'community\project\TiddlyWiki People.tid'

* [ja-JP] Japanese translation of 'community\project\Vacant Positions.tid'

* [ja-JP] Japanese translation of 'community\docs\Community Cards.tid'

* [ja-JP] Japanese translation of 'community\docs\Displaying Community Cards.tid'

* [ja-JP] Japanese translation of 'community\docs\Submitting a Community Card.tid'

* [ja-JP] Japanese translation of 'community\tools\cards\Procedures.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\Resources.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\Resources.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\Community Links Aggregator.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\TiddlyWiki Newsletter.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\marketplace\TiddlyWiki Marketplace.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\hellothere\HelloThumbnail.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\Improving TiddlyWiki Documentation.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\Translate TiddlyWiki into your language.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\TiddlyWiki_European_Meetup_2016.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\TiddlyWiki_European_Meetup_2017.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\editions\Tidme by oflg.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\editions\_Cardo-A Task and Project Management Wiki_ by David_Szego.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\editions\Drift by Tony K.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\editions\Stroll by David Gifford.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\plugins\GSD5.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\plugins\TiddlyWiki for Scholars.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\_TiddlyStudy_ by Kebi.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\resources\Wikilabs by PMario.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\resources\Projectify by Nicolas Petton.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\plugins\TW5-Graph by Flibbles.tid'

* [ja-JP] Japanese translation has been modified to display the ja-title.

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\articles\_A free, open source wiki revisited_ by Mark Gibbs, NetworkWorld.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\articles\_Notizen mit TiddlyWiki systemubergreifend nutzen_ by Michael Sonntag.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\articles\_Setting Up a Personal TiddlyWiki Server on OS X_ by Kris Johnson.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\articles\_TiddlyWiki 5 im Betatest_ by besim.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\articles\_TiddlyWiki_ by Sander de Boer.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\community\resources\TiddlyWiki Posts.tid'

* [ja-JP] A little correction to the Japanese translation
2026-02-15 11:56:40 +01:00
Mario Pietsch
6fc65c1560 [DOCS] Slightly Improve "How to create keyboard shortcuts" Readability (#9478) 2026-02-05 17:01:40 +01:00
Mario Pietsch
ab29f17d35 [DOCS] Add Repo-link to "Installing official plugins on Node.js" (#9483)
* [DOCS] Add Repo-link to "Installing official plugins on Node.js"

* Update Installing official plugins on Node.js.tid
2026-02-04 21:26:48 +01:00
IchijikuIchigo
5ae4770317 [ja_JP] Update of Japanese translations (#9581)
* [ja_JP] Japanese translation update from commit: 5ff4e02

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\hire-jeremy\Hire Jeremy Sidebar Segment.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\hire-jeremy\Hire Jeremy Sidebar Segment.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\hire-jeremy\HireJeremy.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\hellothere\thumbnails\HelloThumbnail - Community Survey.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\hellothere\thumbnails\HelloThumbnail - TW5-Graph.tid'

* [ja_JP] Japanese translation update from commit: e3af967

* [ja_JP] Japanese translation update from commit: bdc0fe1

* [ja_JP] Japanese translation update from commit: e3af967

* [ja_JP] Japanese translation update from commit: bdc0fe1, e3af967

* [ja_JP] Japanese translation update from commit: fdafdba, e3af967, ecba671, 935e89b

* [ja_JP] Japanese translation update from commit: bdc0fe1, e3af967

* [ja_JP] Japanese translation update from commit: 0763ee5

* [ja_JP] Japanese translation update from commit: bdc0fe1

* [ja_JP] Japanese translation update from commit: b0d950f, 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: b0d950f, 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: 4dc89f6

* [ja_JP] Japanese translation update from commit: b0d950f

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\Commands.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\BuildCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\ClearPasswordCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\CommandsCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\DeleteTiddlersCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\EditionsCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\FetchCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\HelpCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\ImportCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\InitCommand.tid'

* [ja-JP] Japanese translation of 'editions\ja-JP\tiddlers\commands\ListenCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\LoadCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\MakeLibraryCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\OutputCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\PasswordCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\RenderCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\SaveCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\SaveWikiFolderCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\SetFieldCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\UnpackPluginCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\VerboseCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\VersionCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\RenderTiddlerCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\RenderTiddlersCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\SaveTiddlerCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\SaveTiddlersCommand.tid'

* [ja-JP] Japanese translation of 'editions\tw5.com\tiddlers\commands\ServerCommand.tid'
2026-02-04 21:24:55 +01:00
666 changed files with 10528 additions and 5261 deletions

View File

@@ -5,17 +5,17 @@ on:
- master
- tiddlywiki-com
env:
NODE_VERSION: "22"
NODE_VERSION: "22.22"
jobs:
test:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v5
- uses: actions/setup-node@v4
- uses: actions/checkout@v6
- uses: actions/setup-node@v6
with:
node-version: "${{ env.NODE_VERSION }}"
- run: "./bin/ci-test.sh"
- uses: actions/upload-artifact@v4
- uses: actions/upload-artifact@v7
if: always()
with:
name: playwright-report
@@ -30,8 +30,8 @@ jobs:
TW5_BUILD_MAIN_EDITION: "./editions/prerelease"
TW5_BUILD_OUTPUT: "./output/prerelease"
steps:
- uses: actions/checkout@v5
- uses: actions/setup-node@v4
- uses: actions/checkout@v6
- uses: actions/setup-node@v6
with:
node-version: "${{ env.NODE_VERSION }}"
- run: "./bin/ci-pre-build.sh"
@@ -62,8 +62,8 @@ jobs:
TW5_BUILD_OUTPUT: "./output"
TW5_BUILD_ARCHIVE: "./output"
steps:
- uses: actions/checkout@v5
- uses: actions/setup-node@v4
- uses: actions/checkout@v6
- uses: actions/setup-node@v6
with:
node-version: "${{ env.NODE_VERSION }}"
- run: "./bin/ci-pre-build.sh"

View File

@@ -20,7 +20,7 @@ jobs:
steps:
- name: build-size-check
id: get_sizes
uses: TiddlyWiki/cerebrus@v6
uses: TiddlyWiki/cerebrus@v8.1
with:
pr_number: ${{ github.event.pull_request.number }}
repo: ${{ github.repository }}
@@ -52,4 +52,4 @@ jobs:
pr_size: '${{ needs.calculate-build-size.outputs.pr_size }}',
base_size: '${{ needs.calculate-build-size.outputs.base_size }}'
}
});
});

View File

@@ -25,7 +25,7 @@ jobs:
steps:
- name: Build and check size
uses: TiddlyWiki/cerebrus@v6
uses: TiddlyWiki/cerebrus@v8.1
with:
pr_number: ${{ inputs.pr_number }}
repo: ${{ github.repository }}

View File

@@ -15,7 +15,7 @@ jobs:
steps:
# Step 1: Validate PR paths
- name: Validate PR Paths
uses: TiddlyWiki/cerebrus@v6
uses: TiddlyWiki/cerebrus@v8.1
with:
pr_number: ${{ github.event.pull_request.number }}
repo: ${{ github.repository }}
@@ -26,7 +26,7 @@ jobs:
# Step 2: Validate change notes
- name: Validate Change Notes
uses: TiddlyWiki/cerebrus@v6
uses: TiddlyWiki/cerebrus@v8.1
with:
pr_number: ${{ github.event.pull_request.number }}
repo: ${{ github.repository }}

12
.gitignore vendored
View File

@@ -2,10 +2,20 @@
.c9/
.vs/
.vscode/
.claude/
# TiddlyWiki
tmp/
output/
node_modules/
$__StoryList.tid
# Playwright
/test-results/
/playwright-report/
/blob-report/
/playwright/.cache/
$__StoryList.tid
/playwright/.auth/
test-screenshots/
test-output.txt
.playwright-mcp
# TiddlyWiki MPC
.tw-mcp

View File

@@ -5,7 +5,7 @@
# Default to the current version number for building the plugin library
if [ -z "$TW5_BUILD_VERSION" ]; then
TW5_BUILD_VERSION=v5.4.0
TW5_BUILD_VERSION=v5.5.0
fi
echo "Using TW5_BUILD_VERSION as [$TW5_BUILD_VERSION]"

View File

@@ -45,7 +45,7 @@ git clone --depth=1 --branch=main "https://github.com/TiddlyWiki/tiddlywiki.org-
# Make the CNAME file that GitHub Pages requires
echo "tiddlywiki.org" > $TWORG_BUILD_OUTPUT/CNAME
# echo "tiddlywiki.org" > $TWORG_BUILD_OUTPUT/CNAME
# Delete any existing static content

View File

@@ -15,40 +15,40 @@ var fs = require("fs"),
{ optimize } = require("svgo"),
config = {
plugins: [
'cleanupAttrs',
'removeDoctype',
'removeXMLProcInst',
'removeComments',
'removeMetadata',
'removeTitle',
'removeDesc',
'removeUselessDefs',
'removeEditorsNSData',
'removeEmptyAttrs',
'removeHiddenElems',
'removeEmptyText',
'removeEmptyContainers',
"cleanupAttrs",
"removeDoctype",
"removeXMLProcInst",
"removeComments",
"removeMetadata",
"removeTitle",
"removeDesc",
"removeUselessDefs",
"removeEditorsNSData",
"removeEmptyAttrs",
"removeHiddenElems",
"removeEmptyText",
"removeEmptyContainers",
// 'removeViewBox',
'cleanupEnableBackground',
'convertStyleToAttrs',
'convertColors',
'convertPathData',
'convertTransform',
'removeUnknownsAndDefaults',
'removeNonInheritableGroupAttrs',
'removeUselessStrokeAndFill',
'removeUnusedNS',
'cleanupIDs',
'cleanupNumericValues',
'moveElemsAttrsToGroup',
'moveGroupAttrsToElems',
'collapseGroups',
"cleanupEnableBackground",
"convertStyleToAttrs",
"convertColors",
"convertPathData",
"convertTransform",
"removeUnknownsAndDefaults",
"removeNonInheritableGroupAttrs",
"removeUselessStrokeAndFill",
"removeUnusedNS",
"cleanupIDs",
"cleanupNumericValues",
"moveElemsAttrsToGroup",
"moveGroupAttrsToElems",
"collapseGroups",
// 'removeRasterImages',
'mergePaths',
'convertShapeToPath',
'sortAttrs',
"mergePaths",
"convertShapeToPath",
"sortAttrs",
//'removeDimensions',
{name: 'removeAttrs', params: { attrs: '(stroke|fill)' } }
{name: "removeAttrs", params: { attrs: "(stroke|fill)" } }
]
};
@@ -72,7 +72,7 @@ files.forEach(function(filename) {
var newSVG = header.join("\n") + "\n\n" + result.data.replace("&lt;&lt;now &quot;DD&quot;&gt;&gt;","<<now \"DD\">>");
fs.writeFileSync(filepath,newSVG);
} else {
console.log("Error " + err + " with " + filename)
console.log("Error " + err + " with " + filename);
process.exit();
};
}

View File

@@ -12,8 +12,6 @@ On the server this file is executed directly to boot TiddlyWiki. In the browser,
var _boot = (function($tw) {
/*jslint node: true, browser: true */
/*global modules: false, $tw: false */
"use strict";
// Include bootprefix if we're not given module data
@@ -37,7 +35,7 @@ if($tw.node) {
$tw.boot.log = function(str) {
$tw.boot.logMessages = $tw.boot.logMessages || [];
$tw.boot.logMessages.push(str);
}
};
/*
Check if an object has a property
@@ -47,7 +45,14 @@ $tw.utils.hop = function(object,property) {
};
/** @deprecated Use Array.isArray instead */
$tw.utils.isArray = value => Array.isArray(value);
$tw.utils.isArray = (value) => Array.isArray(value);
/*
Determine if a value is a date, even across VM boundaries
*/
$tw.utils.isDate = function(value) {
return Object.prototype.toString.call(value) === "[object Date]";
};
/*
Check if an array is equal by value and by reference.
@@ -126,9 +131,6 @@ $tw.utils.pushTop = function(array,value) {
return array;
};
/** @deprecated Use instanceof Date instead */
$tw.utils.isDate = value => value instanceof Date;
/** @deprecated Use array iterative methods instead */
$tw.utils.each = function(object,callback) {
if(object) {
@@ -138,7 +140,7 @@ $tw.utils.each = function(object,callback) {
return next !== false;
});
} else {
Object.entries(object).every(entry => {
Object.entries(object).every((entry) => {
const next = callback(entry[1], entry[0], object);
return next !== false;
});
@@ -565,7 +567,7 @@ using a lowercase extension only.
*/
$tw.utils.getFileExtensionInfo = function(ext) {
return ext ? $tw.config.fileExtensionInfo[ext.toLowerCase()] : null;
}
};
/*
Given an extension, get the correct encoding for that file.
@@ -588,7 +590,7 @@ var globalCheck =[
" delete Object.prototype.__temp__;",
" }",
" delete Object.prototype.__temp__;",
].join('\n');
].join("\n");
/*
Run code globally with specified context variables in scope
@@ -616,7 +618,7 @@ $tw.utils.evalGlobal = function(code,context,filename,sandbox,allowGlobals) {
fn = Function("return " + code + "\n\n//# sourceURL=" + filename)(); // See https://github.com/TiddlyWiki/TiddlyWiki5/issues/6839
} else {
if(sandbox){
fn = vm.runInContext(code,sandbox,filename)
fn = vm.runInContext(code,sandbox,filename);
} else {
fn = vm.runInThisContext(code,filename);
}
@@ -727,7 +729,7 @@ $tw.utils.PasswordPrompt.prototype.createPrompt = function(options) {
var self = this;
form.addEventListener("submit",function(event) {
// Collect the form data
var data = {},t;
var data = {};
$tw.utils.each(form.elements,function(element) {
if(element.name && element.value) {
data[element.name] = element.value;
@@ -773,7 +775,7 @@ $tw.utils.PasswordPrompt.prototype.removePrompt = function(promptInfo) {
promptInfo.form.parentNode.removeChild(promptInfo.form);
this.setWrapperDisplay();
}
}
};
/*
Crypto helper object for encrypted content. It maintains the password text in a closure, and provides methods to change
@@ -812,7 +814,7 @@ $tw.utils.Crypto = function() {
};
this.hasPassword = function() {
return !!currentPassword;
}
};
this.encrypt = function(text,password) {
// set default ks:256 -- see: http://bitwiseshiftleft.github.io/sjcl/doc/convenience.js.html
return callSjcl("encrypt",text,password,{v:1,iter:10000,ks:256,ts:64,mode:"ccm",adata:"",cipher:"aes"});
@@ -830,7 +832,7 @@ Execute the module named 'moduleName'. The name can optionally be relative to th
$tw.modules.execute = function(moduleName,moduleRoot) {
var name = moduleName;
if(moduleName.charAt(0) === ".") {
name = $tw.utils.resolvePath(moduleName,moduleRoot)
name = $tw.utils.resolvePath(moduleName,moduleRoot);
}
if(!$tw.modules.titles[name]) {
if($tw.modules.titles[name + ".js"]) {
@@ -891,7 +893,6 @@ $tw.modules.execute = function(moduleName,moduleRoot) {
if(!moduleInfo) {
// We could not find the module on this path
// Try to defer to browserify etc, or node
var deferredModule;
if($tw.browser) {
if(window.require) {
try {
@@ -1146,8 +1147,7 @@ enableIndexers - Array of indexer names to enable, or null to use all available
*/
$tw.Wiki = function(options) {
options = options || {};
var self = this,
tiddlers = Object.create(null), // Hashmap of tiddlers
var tiddlers = Object.create(null), // Hashmap of tiddlers
tiddlerTitles = null, // Array of tiddler titles
getTiddlerTitles = function() {
if(!tiddlerTitles) {
@@ -1201,7 +1201,7 @@ $tw.Wiki = function(options) {
shadow: this.isShadowTiddler(title),
exists: this.tiddlerExists(title)
}
}
};
// Save the new tiddler
tiddlers[title] = tiddler;
// Check we've got the title
@@ -1211,7 +1211,7 @@ $tw.Wiki = function(options) {
tiddler: tiddler,
shadow: this.isShadowTiddler(title),
exists: this.tiddlerExists(title)
}
};
// Update indexes
this.clearCache(title);
this.clearGlobalCache();
@@ -1236,7 +1236,7 @@ $tw.Wiki = function(options) {
shadow: this.isShadowTiddler(title),
exists: this.tiddlerExists(title)
}
}
};
// Delete the tiddler
delete tiddlers[title];
// Delete it from the list of titles
@@ -1251,7 +1251,7 @@ $tw.Wiki = function(options) {
tiddler: this.getTiddler(title),
shadow: this.isShadowTiddler(title),
exists: this.tiddlerExists(title)
}
};
// Update indexes
this.clearCache(title);
this.clearGlobalCache();
@@ -1439,8 +1439,7 @@ $tw.Wiki = function(options) {
// Unregister the plugin tiddlers of a particular type, or null/undefined for any type, optionally restricting unregistering to an array of tiddler titles. Returns an array of the titles affected
this.unregisterPluginTiddlers = function(pluginType,titles) {
var self = this,
unregisteredTitles = [];
var unregisteredTitles = [];
// Remove any previous registered plugins of this type
for(var t=pluginTiddlers.length-1; t>=0; t--) {
var tiddler = pluginTiddlers[t];
@@ -1454,16 +1453,15 @@ $tw.Wiki = function(options) {
// Unpack the currently registered plugins, creating shadow tiddlers for their constituent tiddlers
this.unpackPluginTiddlers = function() {
var self = this;
// Sort the plugin titles by the `plugin-priority` field, if this field is missing, default to 1
pluginTiddlers.sort(function(a, b) {
var priorityA = "plugin-priority" in a.fields ? a.fields["plugin-priority"] : 1;
var priorityB = "plugin-priority" in b.fields ? b.fields["plugin-priority"] : 1;
if (priorityA !== priorityB) {
if(priorityA !== priorityB) {
return priorityA - priorityB;
} else if (a.fields.title < b.fields.title) {
} else if(a.fields.title < b.fields.title) {
return -1;
} else if (a.fields.title === b.fields.title) {
} else if(a.fields.title === b.fields.title) {
return 0;
} else {
return +1;
@@ -1570,7 +1568,7 @@ $tw.Wiki.prototype.processSafeMode = function() {
// Assemble a report tiddler
var titleReportTiddler = "TiddlyWiki Safe Mode",
report = [];
report.push("TiddlyWiki has been started in [[safe mode|https://tiddlywiki.com/static/SafeMode.html]]. All plugins are temporarily disabled. Most customisations have been disabled by renaming the following tiddlers:")
report.push("TiddlyWiki has been started in [[safe mode|https://tiddlywiki.com/static/SafeMode.html]]. All plugins are temporarily disabled. Most customisations have been disabled by renaming the following tiddlers:");
// Delete the overrides
overrides.forEach(function(title) {
var tiddler = self.getTiddler(title),
@@ -1579,7 +1577,7 @@ $tw.Wiki.prototype.processSafeMode = function() {
self.addTiddler(new $tw.Tiddler(tiddler, {title: newTitle}));
report.push("* [[" + title + "|" + newTitle + "]]");
});
report.push()
report.push();
this.addTiddler(new $tw.Tiddler({title: titleReportTiddler, text: report.join("\n\n")}));
// Set $:/DefaultTiddlers to point to our report
this.addTiddler(new $tw.Tiddler({title: "$:/DefaultTiddlers", text: "[[" + titleReportTiddler + "]]"}));
@@ -2013,7 +2011,7 @@ $tw.loadTiddlersFromSpecification = function(filepath,excludeRegExp) {
value = $tw.utils.stringifyList(path.relative(rootPath, filename).split(path.sep).slice(0, -1));
break;
case "filepath":
value = path.relative(rootPath, filename).split(path.sep).join('/');
value = path.relative(rootPath, filename).split(path.sep).join("/");
break;
case "filename":
value = path.basename(filename);
@@ -2066,7 +2064,7 @@ $tw.loadTiddlersFromSpecification = function(filepath,excludeRegExp) {
}
});
return arrayOfFiles;
}
};
// Process the listed tiddlers
$tw.utils.each(filesInfo.tiddlers,function(tidInfo) {
if(tidInfo.prefix && tidInfo.suffix) {
@@ -2175,7 +2173,7 @@ Returns the path of the plugin folder
$tw.findLibraryItem = function(name,paths) {
var pathIndex = 0;
do {
var pluginPath = path.resolve(paths[pathIndex],"./" + name)
var pluginPath = path.resolve(paths[pathIndex],"./" + name);
if(fs.existsSync(pluginPath) && fs.statSync(pluginPath).isDirectory()) {
return pluginPath;
}
@@ -2534,7 +2532,7 @@ $tw.boot.initStartup = function(options) {
}
});
return result;
}
};
}
};
$tw.boot.loadStartup = function(options){
@@ -2551,7 +2549,7 @@ $tw.boot.loadStartup = function(options){
}
// Give hooks a chance to modify the store
$tw.hooks.invokeHook("th-boot-tiddlers-loaded");
}
};
$tw.boot.execStartup = function(options){
// Unpack plugin tiddlers
$tw.wiki.readPluginInfo();
@@ -2581,7 +2579,7 @@ $tw.boot.execStartup = function(options){
$tw.boot.disabledStartupModules = $tw.boot.disabledStartupModules || [];
// Repeatedly execute the next eligible task
$tw.boot.executeNextStartupTask(options.callback);
}
};
/*
Startup TiddlyWiki
*/
@@ -2600,7 +2598,7 @@ $tw.addUnloadTask = function(task) {
if($tw.unloadTasks.indexOf(task) === -1) {
$tw.unloadTasks.push(task);
}
}
};
/*
Execute the remaining eligible startup tasks
@@ -2647,7 +2645,7 @@ $tw.boot.executeNextStartupTask = function(callback) {
}
taskIndex++;
}
if(typeof callback === 'function') {
if(typeof callback === "function") {
callback();
}
return false;

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@@ -1,6 +1,7 @@
created: 20250909171928024
modified: 20251110133437795
tags: Community/Team
leader: @kjharcombe
team: @MotovunJack
title: Infrastructure Team
@@ -12,4 +13,4 @@ The infrastructure includes:
* github.com/TiddlyWiki
* tiddlywiki.com DNS
* Netlify account for PR previews
* edit.tiddlywiki.com
* edit.tiddlywiki.com

File diff suppressed because one or more lines are too long

View File

@@ -103,7 +103,7 @@ Commander.prototype.executeNextCommand = function() {
c = new command.Command(params,this);
err = c.execute();
if(err && typeof err.then === "function") {
err.then(e => { e ? this.callback(e) : this.executeNextCommand(); });
err.then((e) => { e ? this.callback(e) : this.executeNextCommand(); });
} else if(err) {
this.callback(err);
} else {
@@ -120,7 +120,7 @@ Commander.prototype.executeNextCommand = function() {
});
err = c.execute();
if(err && typeof err.then === "function") {
err.then(e => { if(e) this.callback(e); });
err.then((e) => { if(e) this.callback(e); });
} else if(err) {
this.callback(err);
}

View File

@@ -25,7 +25,7 @@ Command.prototype.execute = function() {
if(!filter) {
return "No filter specified";
}
var commands = this.commander.wiki.filterTiddlers(filter)
var commands = this.commander.wiki.filterTiddlers(filter);
if(commands.length === 0) {
return "No tiddlers found for filter '" + filter + "'";
}

View File

@@ -24,8 +24,7 @@ Command.prototype.execute = function() {
if(this.params.length < 1) {
return "Missing filter";
}
var self = this,
wiki = this.commander.wiki,
var wiki = this.commander.wiki,
filter = this.params[0],
tiddlers = wiki.filterTiddlers(filter);
$tw.utils.each(tiddlers,function(title) {

View File

@@ -66,7 +66,7 @@ Command.prototype.fetchFiles = function(options) {
// Get the list of URLs
var urls;
if(options.url) {
urls = [options.url]
urls = [options.url];
} else if(options.urlFilter) {
urls = this.commander.wiki.filterTiddlers(options.urlFilter);
} else {
@@ -96,30 +96,30 @@ Command.prototype.fetchFile = function(url,options,callback,redirectCount) {
var self = this,
lib = url.substr(0,8) === "https://" ? require("https") : require("http");
lib.get(url).on("response",function(response) {
var type = (response.headers["content-type"] || "").split(";")[0],
data = [];
self.commander.write("Reading " + url + ": ");
response.on("data",function(chunk) {
data.push(chunk);
self.commander.write(".");
});
response.on("end",function() {
self.commander.write("\n");
if(response.statusCode === 200) {
self.processBody(Buffer.concat(data),type,options,url);
callback(null);
} else {
if(response.statusCode === 302 || response.statusCode === 303 || response.statusCode === 307) {
return self.fetchFile(response.headers.location,options,callback,redirectCount + 1);
} else {
return callback("Error " + response.statusCode + " retrieving " + url)
}
}
});
response.on("error",function(e) {
var type = (response.headers["content-type"] || "").split(";")[0],
data = [];
self.commander.write("Reading " + url + ": ");
response.on("data",function(chunk) {
data.push(chunk);
self.commander.write(".");
});
response.on("end",function() {
self.commander.write("\n");
if(response.statusCode === 200) {
self.processBody(Buffer.concat(data),type,options,url);
callback(null);
} else {
if(response.statusCode === 302 || response.statusCode === 303 || response.statusCode === 307) {
return self.fetchFile(response.headers.location,options,callback,redirectCount + 1);
} else {
return callback("Error " + response.statusCode + " retrieving " + url);
}
}
});
response.on("error",function(e) {
console.log("Error on GET request: " + e);
callback(e);
});
});
});
return null;
};
@@ -153,18 +153,18 @@ Command.prototype.processBody = function(body,type,options,url) {
if(options.transformFilter) {
var transformedTitle = (incomingWiki.filterTiddlers(options.transformFilter,null,self.commander.wiki.makeTiddlerIterator([title])) || [""])[0];
if(transformedTitle) {
self.commander.log("Importing " + title + " as " + transformedTitle)
self.commander.log("Importing " + title + " as " + transformedTitle);
newTiddler = new $tw.Tiddler(tiddler,{title: transformedTitle});
}
} else {
self.commander.log("Importing " + title)
self.commander.log("Importing " + title);
newTiddler = tiddler;
}
self.commander.wiki.importTiddler(newTiddler);
count++;
}
});
self.commander.log("Imported " + count + " tiddlers")
self.commander.log("Imported " + count + " tiddlers");
};
exports.Command = Command;

View File

@@ -22,8 +22,7 @@ var Command = function(params,commander,callback) {
Command.prototype.execute = function() {
var self = this,
fs = require("fs"),
path = require("path");
fs = require("fs");
if(this.params.length < 2) {
return "Missing parameters";
}

View File

@@ -20,8 +20,7 @@ var Command = function(params,commander) {
};
Command.prototype.execute = function() {
var fs = require("fs"),
path = require("path");
var fs = require("fs");
// Check that we don't already have a valid wiki folder
if($tw.boot.wikiTiddlersPath || ($tw.utils.isDirectory($tw.boot.wikiPath) && !$tw.utils.isDirectoryEmpty($tw.boot.wikiPath))) {
return "Wiki folder is not empty";

View File

@@ -19,7 +19,6 @@ exports.info = {
};
var Command = function(params,commander,callback) {
var self = this;
this.params = params;
this.commander = commander;
this.callback = callback;

View File

@@ -21,9 +21,7 @@ var Command = function(params,commander,callback) {
};
Command.prototype.execute = function() {
var self = this,
fs = require("fs"),
path = require("path");
var self = this;
if(this.params.length < 1) {
return "Missing filename";
}

View File

@@ -21,8 +21,7 @@ var Command = function(params,commander,callback) {
};
Command.prototype.execute = function() {
var fs = require("fs"),
path = require("path");
var path = require("path");
if(this.params.length < 1) {
return "Missing output path";
}

View File

@@ -7,59 +7,57 @@ Render individual tiddlers and save the results to the specified files
\*/
"use strict";
"use strict";
var widget = require("$:/core/modules/widgets/widget.js");
exports.info = {
name: "render",
synchronous: true
};
exports.info = {
name: "render",
synchronous: true
};
var Command = function(params,commander,callback) {
this.params = params;
this.commander = commander;
this.callback = callback;
};
var Command = function(params,commander,callback) {
this.params = params;
this.commander = commander;
this.callback = callback;
};
Command.prototype.execute = function() {
if(this.params.length < 1) {
return "Missing tiddler filter";
Command.prototype.execute = function() {
if(this.params.length < 1) {
return "Missing tiddler filter";
}
var self = this,
fs = require("fs"),
path = require("path"),
wiki = this.commander.wiki,
tiddlerFilter = this.params[0],
filenameFilter = this.params[1] || "[is[tiddler]addsuffix[.html]]",
type = this.params[2] || "text/html",
template = this.params[3],
variableList = this.params.slice(4),
tiddlers = wiki.filterTiddlers(tiddlerFilter),
variables = Object.create(null);
while(variableList.length >= 2) {
variables[variableList[0]] = variableList[1];
variableList = variableList.slice(2);
}
$tw.utils.each(tiddlers,function(title) {
var filenameResults = wiki.filterTiddlers(filenameFilter,$tw.rootWidget,wiki.makeTiddlerIterator([title]));
if(filenameResults.length > 0) {
var filepath = path.resolve(self.commander.outputPath,filenameResults[0]);
if(self.commander.verbose) {
console.log("Rendering \"" + title + "\" to \"" + filepath + "\"");
}
var parser = wiki.parseTiddler(template || title),
widgetNode = wiki.makeWidget(parser,{variables: $tw.utils.extend({},variables,{currentTiddler: title,storyTiddler: title})}),
container = $tw.fakeDocument.createElement("div");
widgetNode.render(container,null);
var text = type === "text/html" ? container.innerHTML : container.textContent;
$tw.utils.createFileDirectories(filepath);
fs.writeFileSync(filepath,text,"utf8");
} else {
console.log("Not rendering \"" + title + "\" because the filename filter returned an empty result");
}
var self = this,
fs = require("fs"),
path = require("path"),
wiki = this.commander.wiki,
tiddlerFilter = this.params[0],
filenameFilter = this.params[1] || "[is[tiddler]addsuffix[.html]]",
type = this.params[2] || "text/html",
template = this.params[3],
variableList = this.params.slice(4),
tiddlers = wiki.filterTiddlers(tiddlerFilter),
variables = Object.create(null);
while(variableList.length >= 2) {
variables[variableList[0]] = variableList[1];
variableList = variableList.slice(2);
}
$tw.utils.each(tiddlers,function(title) {
var filenameResults = wiki.filterTiddlers(filenameFilter,$tw.rootWidget,wiki.makeTiddlerIterator([title]));
if(filenameResults.length > 0) {
var filepath = path.resolve(self.commander.outputPath,filenameResults[0]);
if(self.commander.verbose) {
console.log("Rendering \"" + title + "\" to \"" + filepath + "\"");
}
var parser = wiki.parseTiddler(template || title),
widgetNode = wiki.makeWidget(parser,{variables: $tw.utils.extend({},variables,{currentTiddler: title,storyTiddler: title})}),
container = $tw.fakeDocument.createElement("div");
widgetNode.render(container,null);
var text = type === "text/html" ? container.innerHTML : container.textContent;
$tw.utils.createFileDirectories(filepath);
fs.writeFileSync(filepath,text,"utf8");
} else {
console.log("Not rendering \"" + title + "\" because the filename filter returned an empty result");
}
});
return null;
};
});
return null;
};
exports.Command = Command;
exports.Command = Command;

View File

@@ -9,8 +9,6 @@ Command to render several tiddlers to a folder of files
"use strict";
var widget = require("$:/core/modules/widgets/widget.js");
exports.info = {
name: "rendertiddlers",
synchronous: true

View File

@@ -7,57 +7,56 @@ Saves individual tiddlers in their raw text or binary format to the specified fi
\*/
"use strict";
"use strict";
exports.info = {
name: "save",
synchronous: true
};
exports.info = {
name: "save",
synchronous: true
};
var Command = function(params,commander,callback) {
this.params = params;
this.commander = commander;
this.callback = callback;
};
var Command = function(params,commander,callback) {
this.params = params;
this.commander = commander;
this.callback = callback;
};
Command.prototype.execute = function() {
if(this.params.length < 1) {
return "Missing filename filter";
}
var self = this,
fs = require("fs"),
path = require("path"),
result = null,
wiki = this.commander.wiki,
tiddlerFilter = this.params[0],
filenameFilter = this.params[1] || "[is[tiddler]]",
tiddlers = wiki.filterTiddlers(tiddlerFilter);
$tw.utils.each(tiddlers,function(title) {
if(!result) {
var tiddler = self.commander.wiki.getTiddler(title);
if(tiddler) {
var fileInfo = $tw.utils.generateTiddlerFileInfo(tiddler,{
directory: path.resolve(self.commander.outputPath),
pathFilters: [filenameFilter],
wiki: wiki,
fileInfo: {
overwrite: true
}
});
if(self.commander.verbose) {
console.log("Saving \"" + title + "\" to \"" + fileInfo.filepath + "\"");
Command.prototype.execute = function() {
if(this.params.length < 1) {
return "Missing filename filter";
}
var self = this,
path = require("path"),
result = null,
wiki = this.commander.wiki,
tiddlerFilter = this.params[0],
filenameFilter = this.params[1] || "[is[tiddler]]",
tiddlers = wiki.filterTiddlers(tiddlerFilter);
$tw.utils.each(tiddlers,function(title) {
if(!result) {
var tiddler = self.commander.wiki.getTiddler(title);
if(tiddler) {
var fileInfo = $tw.utils.generateTiddlerFileInfo(tiddler,{
directory: path.resolve(self.commander.outputPath),
pathFilters: [filenameFilter],
wiki: wiki,
fileInfo: {
overwrite: true
}
try {
$tw.utils.saveTiddlerToFileSync(tiddler,fileInfo);
} catch (err) {
result = "Error saving tiddler \"" + title + "\", to file: \"" + fileInfo.filepath + "\"";
}
} else {
result = "Tiddler '" + title + "' not found";
});
if(self.commander.verbose) {
console.log("Saving \"" + title + "\" to \"" + fileInfo.filepath + "\"");
}
try {
$tw.utils.saveTiddlerToFileSync(tiddler,fileInfo);
} catch (err) {
result = "Error saving tiddler \"" + title + "\", to file: \"" + fileInfo.filepath + "\"";
}
} else {
result = "Tiddler '" + title + "' not found";
}
});
return result;
};
}
});
return result;
};
exports.Command = Command;
exports.Command = Command;

View File

@@ -9,8 +9,6 @@ Command to save several tiddlers to a folder of files
"use strict";
var widget = require("$:/core/modules/widgets/widget.js");
exports.info = {
name: "savetiddlers",
synchronous: true

View File

@@ -43,7 +43,7 @@ Command.prototype.execute = function() {
namedParames,
tiddlerFilter,
options = {};
if (regFilter.test(this.params[1])) {
if(regFilter.test(this.params[1])) {
namedParames = this.commander.extractNamedParameters(this.params.slice(1));
tiddlerFilter = namedParames.filter || "[all[tiddlers]]";
} else {
@@ -177,13 +177,13 @@ WikiFolderMaker.prototype.saveCustomPlugin = function(pluginTiddler) {
$tw.utils.each(pluginTiddlers,function(tiddler,title) {
if(!tiddler.title) {
tiddler.title = title;
}
}
self.saveTiddler(directory,new $tw.Tiddler(tiddler));
});
};
WikiFolderMaker.prototype.saveTiddler = function(directory,tiddler) {
var title = tiddler.fields.title, fileInfo, pathFilters, extFilters;
var fileInfo, pathFilters, extFilters;
if(this.wiki.tiddlerExists("$:/config/FileSystemPaths")) {
pathFilters = this.wiki.getTiddlerText("$:/config/FileSystemPaths","").split("\n");
}

View File

@@ -17,7 +17,6 @@ exports.info = {
};
var Command = function(params,commander,callback) {
var self = this;
this.params = params;
this.commander = commander;
this.callback = callback;

View File

@@ -9,8 +9,6 @@ Command to modify selected tiddlers to set a field to the text of a template tid
"use strict";
var widget = require("$:/core/modules/widgets/widget.js");
exports.info = {
name: "setfield",
synchronous: true
@@ -26,8 +24,7 @@ Command.prototype.execute = function() {
if(this.params.length < 4) {
return "Missing parameters";
}
var self = this,
wiki = this.commander.wiki,
var wiki = this.commander.wiki,
filter = this.params[0],
fieldname = this.params[1] || "text",
templatetitle = this.params[2],

View File

@@ -26,7 +26,7 @@ exports.getSubdirectories = function(dirPath) {
}
});
return subdirs;
}
};
/*
Recursively (and synchronously) copy a directory and all its content
@@ -46,8 +46,7 @@ exports.copyDirectory = function(srcPath,dstPath) {
}
// Function to copy a folder full of files
var copy = function(srcPath,dstPath) {
var srcStats = fs.lstatSync(srcPath),
dstExists = fs.existsSync(dstPath);
var srcStats = fs.lstatSync(srcPath);
if(srcStats.isFile()) {
$tw.utils.copyFile(srcPath,dstPath);
} else if(srcStats.isDirectory()) {
@@ -83,7 +82,7 @@ exports.copyFile = function(srcPath,dstPath) {
dstFile = fs.openSync(dstPath,"w"),
bytesRead = 1,
pos = 0;
while (bytesRead > 0) {
while(bytesRead > 0) {
bytesRead = fs.readSync(srcFile,fileBuffer,0,FILE_BUFFER_LENGTH,pos);
fs.writeSync(dstFile,fileBuffer,0,bytesRead);
pos += bytesRead;
@@ -148,7 +147,7 @@ exports.deleteDirectory = function(dirPath) {
fs.unlinkSync(currPath);
}
}
fs.rmdirSync(dirPath);
fs.rmdirSync(dirPath);
}
return null;
};
@@ -255,7 +254,7 @@ exports.generateTiddlerFileInfo = function(tiddler,options) {
// Overriding to the .tid extension needs special handling
fileInfo.type = "application/x-tiddler";
fileInfo.hasMetaFile = false;
} else if (metaExt === ".json") {
} else if(metaExt === ".json") {
// Overriding to the .json extension needs special handling
fileInfo.type = "application/json";
fileInfo.hasMetaFile = false;
@@ -345,18 +344,18 @@ exports.generateTiddlerFilepath = function(title,options) {
// Replace any Windows control codes
filepath = filepath.replace(/^(con|prn|aux|nul|com[0-9]|lpt[0-9])$/i,"_$1_");
// Replace any leading spaces with the same number of underscores
filepath = filepath.replace(/^ +/,function (u) { return u.replace(/ /g, "_")});
filepath = filepath.replace(/^ +/,function (u) { return u.replace(/ /g, "_");});
//If the path does not start with "." or ".." && a path seperator, then
if(!/^\.{1,2}[/\\]/g.test(filepath)) {
// Don't let the filename start with any dots because such files are invisible on *nix
filepath = filepath.replace(/^\.+/g,function (u) { return u.replace(/\./g, "_")});
filepath = filepath.replace(/^\.+/g,function (u) { return u.replace(/\./g, "_");});
}
// Replace any Unicode control codes
filepath = filepath.replace(/[\x00-\x1f\x80-\x9f]/g,"_");
// Replace any characters that can't be used in cross-platform filenames
filepath = $tw.utils.transliterate(filepath.replace(/<|>|~|\:|\"|\||\?|\*|\^/g,"_"));
// Replace any dots or spaces at the end of the extension with the same number of underscores
extension = extension.replace(/[\. ]+$/, function (u) { return u.replace(/[\. ]/g, "_")});
extension = extension.replace(/[\. ]+$/, function (u) { return u.replace(/[\. ]/g, "_");});
// Truncate the extension if it is too long
if(extension.length > 32) {
extension = extension.substr(0,32);
@@ -382,9 +381,9 @@ exports.generateTiddlerFilepath = function(title,options) {
}
// Add a uniquifier if the file already exists (default)
var fullPath = path.resolve(directory, filepath + extension);
if (!overwrite) {
if(!overwrite) {
var oldPath = (options.fileInfo) ? options.fileInfo.filepath : undefined,
count = 0;
count = 0;
do {
fullPath = path.resolve(directory,filepath + (count ? "_" + count : "") + extension);
if(oldPath && oldPath == fullPath) break;
@@ -401,7 +400,7 @@ exports.generateTiddlerFilepath = function(title,options) {
writePath.indexOf(path.resolve(directory)) == 0 ||
writePath.indexOf(path.resolve($tw.boot.wikiPath)) == 0 ||
writePath.indexOf(path.resolve($tw.boot.wikiTiddlersPath,originalpath)) == 0 );
}
}
if(encode) {
writePath = path.resolve(directory,$tw.utils.encodeURIComponentExtended(fullPath));
}
@@ -521,12 +520,12 @@ Cleanup old files on disk, by comparing the options values:
*/
exports.cleanupTiddlerFiles = function(options,callback) {
var adaptorInfo = options.adaptorInfo || {},
bootInfo = options.bootInfo || {},
title = options.title || "undefined";
bootInfo = options.bootInfo || {},
title = options.title || "undefined";
if(adaptorInfo.filepath && bootInfo.filepath && adaptorInfo.filepath !== bootInfo.filepath) {
$tw.utils.deleteTiddlerFile(adaptorInfo,function(err) {
if(err) {
if ((err.code == "EPERM" || err.code == "EACCES") && err.syscall == "unlink") {
if((err.code == "EPERM" || err.code == "EACCES") && err.syscall == "unlink") {
// Error deleting the previous file on disk, should fail gracefully
$tw.syncer.displayError("Server desynchronized. Error cleaning up previous file for tiddler: \""+title+"\"",err);
return callback(null,bootInfo);

View File

@@ -10,9 +10,7 @@ Authenticator for WWW basic authentication
"use strict";
if($tw.node) {
var util = require("util"),
fs = require("fs"),
url = require("url"),
var fs = require("fs"),
path = require("path");
}

View File

@@ -19,7 +19,7 @@ exports.info = {
exports.handler = function(request,response,state) {
var text = state.wiki.renderTiddler(state.server.get("root-render-type"),state.server.get("root-tiddler")),
responseHeaders = {
"Content-Type": state.server.get("root-serve-type")
};
"Content-Type": state.server.get("root-serve-type")
};
state.sendResponse(200,responseHeaders,text);
};

View File

@@ -18,7 +18,7 @@ exports.info = {
exports.handler = function(request,response,state) {
var title = $tw.utils.decodeURIComponentSafe(state.params[0]),
fields = $tw.utils.parseJSONSafe(state.data);
fields = $tw.utils.parseJSONSafe(state.data);
// Pull up any subfields in the `fields` object
if(fields.fields) {
$tw.utils.each(fields.fields,function(field,name) {

View File

@@ -9,14 +9,15 @@ Serve tiddlers over http
"use strict";
let fs, url, path, querystring, crypto, zlib;
if($tw.node) {
var util = require("util"),
fs = require("fs"),
url = require("url"),
path = require("path"),
querystring = require("querystring"),
crypto = require("crypto"),
zlib = require("zlib");
fs = require("fs"),
url = require("url"),
path = require("path"),
querystring = require("querystring"),
crypto = require("crypto"),
zlib = require("zlib");
}
/*
@@ -41,7 +42,7 @@ function Server(options) {
}
}
// Setup the default required plugins
this.requiredPlugins = this.get("required-plugins").split(',');
this.requiredPlugins = this.get("required-plugins").split(",");
// Initialise CORS
this.corsEnable = this.get("cors-enable") === "yes";
// Initialise CSRF
@@ -62,9 +63,9 @@ function Server(options) {
this.authorizationPrincipals = {
readers: (this.get("readers") || authorizedUserName).split(",").map($tw.utils.trim),
writers: (this.get("writers") || authorizedUserName).split(",").map($tw.utils.trim)
}
};
if(this.get("admin") || authorizedUserName !== "(anon)") {
this.authorizationPrincipals["admin"] = (this.get("admin") || authorizedUserName).split(',').map($tw.utils.trim)
this.authorizationPrincipals["admin"] = (this.get("admin") || authorizedUserName).split(",").map($tw.utils.trim);
}
// Load and initialise authenticators
$tw.modules.forEachModuleOfType("authenticator", function(title,authenticatorDefinition) {
@@ -91,7 +92,7 @@ function Server(options) {
this.listenOptions = {
key: fs.readFileSync(path.resolve(this.boot.wikiPath,tlsKeyFilepath),"utf8"),
cert: fs.readFileSync(path.resolve(this.boot.wikiPath,tlsCertFilepath),"utf8"),
passphrase: tlsPassphrase || ''
passphrase: tlsPassphrase || ""
};
this.protocol = "https";
}
@@ -116,7 +117,7 @@ encoding: the encoding of the data to send (passed to the end method of the resp
*/
function sendResponse(request,response,statusCode,headers,data,encoding) {
if(this.enableBrowserCache && (statusCode == 200)) {
var hash = crypto.createHash('md5');
var hash = crypto.createHash("md5");
// Put everything into the hash that could change and invalidate the data that
// the browser already stored. The headers the data and the encoding.
hash.update(data);
@@ -211,7 +212,6 @@ Server.prototype.addAuthenticator = function(AuthenticatorClass) {
Server.prototype.findMatchingRoute = function(request,state) {
for(var t=0; t<this.routes.length; t++) {
var potentialRoute = this.routes[t],
pathRegExp = potentialRoute.path,
pathname = state.urlInfo.pathname,
match;
if(state.pathPrefix) {
@@ -250,7 +250,7 @@ Check whether a given user is authorized for the specified authorizationType ("r
Server.prototype.isAuthorized = function(authorizationType,username) {
var principals = this.authorizationPrincipals[authorizationType] || [];
return principals.indexOf("(anon)") !== -1 || (username && (principals.indexOf("(authenticated)") !== -1 || principals.indexOf(username) !== -1));
}
};
Server.prototype.requestHandler = function(request,response,options) {
options = options || {};
@@ -337,7 +337,7 @@ Server.prototype.requestHandler = function(request,response,options) {
request.on("end",function() {
state.data = Buffer.concat(data);
route.handler(request,response,state);
})
});
} else {
response.writeHead(400,"Invalid bodyFormat " + route.bodyFormat + " in route " + route.method + " " + route.path.source);
response.end();
@@ -362,8 +362,8 @@ Server.prototype.listen = function(port,host,prefix) {
}
// Warn if required plugins are missing
var missing = [];
for (var index=0; index<this.requiredPlugins.length; index++) {
if (!this.wiki.getTiddler(this.requiredPlugins[index])) {
for(var index=0; index<this.requiredPlugins.length; index++) {
if(!this.wiki.getTiddler(this.requiredPlugins[index])) {
missing.push(this.requiredPlugins[index]);
}
}

View File

@@ -9,22 +9,22 @@ Base64 UTF-8 utlity functions.
"use strict";
const{ TextEncoder, TextDecoder } = require("node:util");
const { TextEncoder, TextDecoder } = require("node:util");
exports.btoa = binstr => Buffer.from(binstr, "binary").toString("base64");
exports.btoa = (binstr) => Buffer.from(binstr, "binary").toString("base64");
exports.atob = b64 => Buffer.from(b64, "base64").toString("binary");
exports.atob = (b64) => Buffer.from(b64, "base64").toString("binary");
function base64ToBytes(base64) {
const binString = exports.atob(base64);
return Uint8Array.from(binString, m => m.codePointAt(0));
return Uint8Array.from(binString, (m) => m.codePointAt(0));
};
function bytesToBase64(bytes) {
const binString = Array.from(bytes, byte => String.fromCodePoint(byte)).join("");
const binString = Array.from(bytes, (byte) => String.fromCodePoint(byte)).join("");
return exports.btoa(binString);
};
exports.base64EncodeUtf8 = str => bytesToBase64(new TextEncoder().encode(str));
exports.base64EncodeUtf8 = (str) => bytesToBase64(new TextEncoder().encode(str));
exports.base64DecodeUtf8 = str => new TextDecoder().decode(base64ToBytes(str));
exports.base64DecodeUtf8 = (str) => new TextDecoder().decode(base64ToBytes(str));

View File

@@ -16,8 +16,7 @@ ignoreEnvironmentVariables: defaults to false
*/
exports.getAllPlugins = function(options) {
options = options || {};
var fs = require("fs"),
path = require("path"),
var path = require("path"),
tiddlers = {};
// Collect up the library plugins
var collectPlugins = function(folder) {

View File

@@ -15,6 +15,8 @@ Listing/Preview/TextRaw: Text (Raw)
Listing/Preview/Fields: Fields
Listing/Preview/Diff: Diff
Listing/Preview/DiffFields: Diff (Fields)
Listing/ImportOptions/Caption: Import options
Listing/ImportOptions/NoMatch: No import options apply to these files.
Listing/Rename/Tooltip: Rename tiddler before importing
Listing/Rename/Prompt: Rename to:
Listing/Rename/ConfirmRename: Rename tiddler

View File

@@ -10,7 +10,7 @@ Advanced/ShadowInfo/Shadow/Hint: The tiddler <$link to=<<infoTiddler>>><$text te
Advanced/ShadowInfo/Shadow/Source: It is defined in the plugin <$link to=<<pluginTiddler>>><$text text=<<pluginTiddler>>/></$link>
Advanced/ShadowInfo/OverriddenShadow/Hint: It is overridden by an ordinary tiddler
Advanced/CascadeInfo/Heading: Cascade Details
Advanced/CascadeInfo/Hint: These are the view template segments (tagged <<tag "$:/tags/ViewTemplate">>) using a cascade filter and their resulting template for the current tiddler.
Advanced/CascadeInfo/Hint: These are the view template segments that are resolved for each of the system view template cascades
Advanced/CascadeInfo/Detail/View: View
Advanced/CascadeInfo/Detail/ActiveCascadeFilter: Active cascade filter
Advanced/CascadeInfo/Detail/Template: Template

View File

@@ -18,13 +18,13 @@ class BackgroundActionDispatcher {
// Track the filter for the background actions
this.filterTracker.track({
filterString: "[all[tiddlers+shadows]tag[$:/tags/BackgroundAction]!is[draft]]",
fnEnter: title => this.trackFilter(title),
fnEnter: (title) => this.trackFilter(title),
fnLeave: (title, enterValue) => this.untrackFilter(enterValue),
fnChange: (title, enterValue) => {
this.untrackFilter(enterValue);
return this.trackFilter(title);
},
fnProcess: changes => this.process(changes)
fnProcess: (changes) => this.process(changes)
});
}
@@ -75,7 +75,7 @@ class BackgroundActionTracker {
filterString: this.trackFilter,
fnEnter: () => { this.hasChanged = true; },
fnLeave: () => { this.hasChanged = true; },
fnProcess: changes => {
fnProcess: (changes) => {
if(this.hasChanged) {
this.hasChanged = false;
console.log("Processing background action", this.title);

View File

@@ -197,7 +197,7 @@ FramedEngine.prototype.handleFocusEvent = function(event) {
Handle a keydown event
*/
FramedEngine.prototype.handleKeydownEvent = function(event) {
if ($tw.keyboardManager.handleKeydownEvent(event, {onlyPriority: true})) {
if($tw.keyboardManager.handleKeydownEvent(event, {onlyPriority: true})) {
return true;
}

View File

@@ -55,12 +55,12 @@ function editTextWidgetFactory(toolbarEngine,nonToolbarEngine) {
var editInfo = this.getEditInfo(),
Engine = this.editShowToolbar ? toolbarEngine : nonToolbarEngine;
this.engine = new Engine({
widget: this,
value: editInfo.value,
type: editInfo.type,
parentNode: parent,
nextSibling: nextSibling
});
widget: this,
value: editInfo.value,
type: editInfo.type,
parentNode: parent,
nextSibling: nextSibling
});
// Call the postRender hook
if(this.postRender) {
this.postRender();
@@ -220,7 +220,7 @@ function editTextWidgetFactory(toolbarEngine,nonToolbarEngine) {
if(changedAttributes.tiddler || changedAttributes.field || changedAttributes.index || changedAttributes["default"] || changedAttributes["class"] || changedAttributes.placeholder || changedAttributes.size || changedAttributes.autoHeight || changedAttributes.minHeight || changedAttributes.focusPopup || changedAttributes.rows || changedAttributes.tabindex || changedAttributes.cancelPopups || changedAttributes.inputActions || changedAttributes.refreshTitle || changedAttributes.autocomplete || changedTiddlers[HEIGHT_MODE_TITLE] || changedTiddlers[ENABLE_TOOLBAR_TITLE] || changedTiddlers["$:/palette"] || changedAttributes.disabled || changedAttributes.fileDrop) {
this.refreshSelf();
return true;
} else if (changedTiddlers[this.editRefreshTitle]) {
} else if(changedTiddlers[this.editRefreshTitle]) {
this.engine.updateDomNodeText(this.getEditInfo().value);
} else if(changedTiddlers[this.editTitle]) {
var editInfo = this.getEditInfo();
@@ -274,8 +274,8 @@ function editTextWidgetFactory(toolbarEngine,nonToolbarEngine) {
});
if($tw.keyboardManager.checkKeyDescriptors(event,keyInfoArray)) {
var clickEvent = this.document.createEvent("Events");
clickEvent.initEvent("click",true,false);
el.dispatchEvent(clickEvent);
clickEvent.initEvent("click",true,false);
el.dispatchEvent(clickEvent);
event.preventDefault();
event.stopPropagation();
return true;

View File

@@ -10,7 +10,7 @@ Text editor operation to excise the selection to a new tiddler
"use strict";
function isMarkdown(mediaType) {
return mediaType === 'text/markdown' || mediaType === 'text/x-markdown';
return mediaType === "text/markdown" || mediaType === "text/x-markdown";
}
exports["excise"] = function(event,operation) {

View File

@@ -19,7 +19,7 @@ exports["wrap-lines"] = function(event,operation) {
operation.cutStart = operation.selStart - (prefix.length + 1);
operation.cutEnd = operation.selEnd + suffix.length + 1;
// Also cut the following newline (if there is any)
if (operation.text[operation.cutEnd] === "\n") {
if(operation.text[operation.cutEnd] === "\n") {
operation.cutEnd++;
}
// Replace with selection

View File

@@ -44,7 +44,7 @@ exports["wrap-selection"] = function(event,operation) {
break;
}
return result;
}
};
function togglePrefixSuffix() {
if(o.text.substring(o.selStart - prefix.length, o.selStart + suffix.length) === prefix + suffix) {

View File

@@ -69,17 +69,17 @@ class FilterTracker {
if(!tracker) return;
const results = [];
// Evaluate the filter and remove duplicate results
$tw.utils.each(this.wiki.filterTiddlers(tracker.filterString), title => {
$tw.utils.each(this.wiki.filterTiddlers(tracker.filterString), (title) => {
$tw.utils.pushTop(results, title);
});
// Process the newly entered results
results.forEach(title => {
results.forEach((title) => {
if(!tracker.previousResults.includes(title) && !tracker.resultValues[title] && tracker.fnEnter) {
tracker.resultValues[title] = tracker.fnEnter(title) || true;
}
});
// Process the results that have just left
tracker.previousResults.forEach(title => {
tracker.previousResults.forEach((title) => {
if(!results.includes(title) && tracker.resultValues[title] && tracker.fnLeave) {
tracker.fnLeave(title, tracker.resultValues[title]);
delete tracker.resultValues[title];
@@ -91,7 +91,7 @@ class FilterTracker {
processChanges(changes) {
for(const tracker of this.trackers.values()) {
Object.keys(changes).forEach(title => {
Object.keys(changes).forEach((title) => {
if(title && tracker.previousResults.includes(title) && tracker.fnChange) {
tracker.resultValues[title] = tracker.fnChange(title, tracker.resultValues[title]) || tracker.resultValues[title];
}

View File

@@ -34,5 +34,5 @@ exports.cascade = function(operationSubFunction,options) {
results.push(result);
});
}
}
};
};

View File

@@ -30,5 +30,5 @@ exports.filter = function(operationSubFunction,options) {
});
results.remove(resultsToRemove);
}
}
};
};

View File

@@ -7,8 +7,6 @@ Assign a value to a variable
\*/
/*jslint node: true, browser: true */
/*global $tw: false */
"use strict";
/*

View File

@@ -28,12 +28,12 @@ exports.map = function(operationSubFunction,options) {
if(filtered.length && flatten) {
$tw.utils.each(filtered,function(value) {
results.push(value);
})
});
} else {
results.push(filtered[0]||"");
}
++index;
});
}
}
};
};

View File

@@ -31,5 +31,5 @@ exports.reduce = function(operationSubFunction,options) {
results.clear();
results.push(accumulator);
}
}
};
};

View File

@@ -36,12 +36,12 @@ exports.sort = function(operationSubFunction,options) {
// Sort the indexes
compareFn = $tw.utils.makeCompareFunction(sortType,{defaultType: "string", invert:invert, isCaseSensitive:isCaseSensitive});
indexes = indexes.sort(function(a,b) {
return compareFn(sortKeys[a],sortKeys[b]);
return compareFn(sortKeys[a],sortKeys[b]);
});
// Add to results in correct order
$tw.utils.each(indexes,function(index) {
results.push(inputTitles[index]);
});
}
}
};
};

View File

@@ -43,7 +43,7 @@ function parseFilterOperation(operators,filterString,p) {
var bracket = filterString.charAt(nextBracketPos);
operator.operator = filterString.substring(p,nextBracketPos);
// Any suffix?
var colon = operator.operator.indexOf(':');
var colon = operator.operator.indexOf(":");
if(colon > -1) {
// The raw suffix for older filters
operator.suffix = operator.operator.substring(colon + 1);
@@ -67,7 +67,7 @@ function parseFilterOperation(operators,filterString,p) {
operator.operands = [];
var parseOperand = function(bracketType) {
var operand = {};
switch (bracketType) {
switch(bracketType) {
case "{": // Curly brackets
operand.indirect = true;
nextBracketPos = filterString.indexOf("}",p);
@@ -88,8 +88,8 @@ function parseFilterOperation(operators,filterString,p) {
rexMatch = rex.exec(filterString.substring(p));
if(rexMatch) {
operator.regexp = new RegExp(rexMatch[1], rexMatch[2]);
// DEPRECATION WARNING
console.log("WARNING: Filter",operator.operator,"has a deprecated regexp operand",operator.regexp);
// DEPRECATION WARNING
console.log("WARNING: Filter",operator.operator,"has a deprecated regexp operand",operator.regexp);
nextBracketPos = p + rex.lastIndex - 1;
}
else {
@@ -108,7 +108,7 @@ function parseFilterOperation(operators,filterString,p) {
}
operator.operands.push(operand);
p = nextBracketPos + 1;
}
};
p = nextBracketPos + 1;
parseOperand(bracket);
@@ -228,7 +228,7 @@ exports.getFilterRunPrefixes = function() {
$tw.modules.applyMethods("filterrunprefix",this.filterRunPrefixes);
}
return this.filterRunPrefixes;
}
};
exports.filterTiddlers = function(filterString,widget,source) {
var fn = this.compileFilter(filterString);
@@ -314,19 +314,19 @@ exports.compileFilter = function(filterString) {
// Invoke the appropriate filteroperator module
results = operatorFunction(accumulator,{
operator: operator.operator,
operand: operands.length > 0 ? operands[0] : undefined,
operands: operands,
multiValueOperands: multiValueOperands,
isMultiValueOperand: isMultiValueOperand,
prefix: operator.prefix,
suffix: operator.suffix,
suffixes: operator.suffixes,
regexp: operator.regexp
},{
wiki: self,
widget: widget
});
operator: operator.operator,
operand: operands.length > 0 ? operands[0] : undefined,
operands: operands,
multiValueOperands: multiValueOperands,
isMultiValueOperand: isMultiValueOperand,
prefix: operator.prefix,
suffix: operator.suffix,
suffixes: operator.suffixes,
regexp: operator.regexp
},{
wiki: self,
widget: widget
});
if($tw.utils.isArray(results)) {
accumulator = self.makeTiddlerIterator(results);
} else {

View File

@@ -32,4 +32,4 @@ var modes = {
"gt": function(value) {return value > 0;},
"lteq": function(value) {return value <= 0;},
"lt": function(value) {return value < 0;}
}
};

View File

@@ -31,4 +31,4 @@ exports["deserialize"] = function(source,operator,options) {
return [$tw.language.getString("Error/DeserializeOperator/MissingOperand")];
}
return results;
}
};

View File

@@ -15,8 +15,8 @@ Export our filter function
*/
exports.each = function(source,operator,options) {
var results =[] ,
value,values = {},
field = operator.operand || "title";
value,values = {},
field = operator.operand || "title";
if(operator.suffix === "value" && field === "title") {
source(function(tiddler,title) {
if(!$tw.utils.hop(values,title)) {

View File

@@ -53,7 +53,7 @@ exports.field = function(source,operator,options) {
if(source.byField && operator.operand) {
indexedResults = source.byField(fieldname,operator.operand);
if(indexedResults) {
return indexedResults
return indexedResults;
}
}
source(function(tiddler,title) {

View File

@@ -24,7 +24,7 @@ exports.fields = function(source,operator,options) {
for(fieldName in tiddler.fields) {
(operand.indexOf(fieldName) !== -1) ? $tw.utils.pushTop(results,fieldName) : "";
}
} else if (suffixes.indexOf("exclude") !== -1) {
} else if(suffixes.indexOf("exclude") !== -1) {
for(fieldName in tiddler.fields) {
(operand.indexOf(fieldName) !== -1) ? "" : $tw.utils.pushTop(results,fieldName);
}

View File

@@ -12,7 +12,7 @@ Export our filter function
exports.timestamp = function(source,operand,options) {
var results = [];
source(function(tiddler,title) {
if (title.match(/^-?\d+$/)) {
if(title.match(/^-?\d+$/)) {
var value = new Date(Number(title));
results.push($tw.utils.formatDateString(value,operand || "[UTC]YYYY0MM0DD0hh0mm0ss0XXX"));
}

View File

@@ -13,7 +13,7 @@ returns the value at a given index of datatiddlers
Export our filter function
*/
exports.getindex = function(source,operator,options) {
var data,title,results = [];
var data,results = [];
if(operator.operand){
source(function(tiddler,title) {
title = tiddler ? tiddler.fields.title : title;

View File

@@ -157,13 +157,13 @@ function convertDataItemValueToStrings(item) {
if(item === undefined) {
return undefined;
} else if(item === null) {
return ["null"]
return ["null"];
} else if(typeof item === "object") {
var results = [],i,t;
if(Array.isArray(item)) {
// Return all the items in arrays recursively
for(i=0; i<item.length; i++) {
t = convertDataItemValueToStrings(item[i])
t = convertDataItemValueToStrings(item[i]);
if(t !== undefined) {
results.push.apply(results,t);
}
@@ -231,7 +231,7 @@ function getItemAtIndex(item,index) {
return item[index];
} else if(Array.isArray(item)) {
index = $tw.utils.parseInt(index);
if(index < 0) { index = index + item.length };
if(index < 0) { index = index + item.length; };
return item[index]; // Will be undefined if index was out-of-bounds
} else {
return undefined;
@@ -289,7 +289,7 @@ function setDataItem(data,indexes,value) {
var lastIndex = indexes[indexes.length - 1];
if(Array.isArray(current)) {
lastIndex = $tw.utils.parseInt(lastIndex);
if(lastIndex < 0) { lastIndex = lastIndex + current.length };
if(lastIndex < 0) { lastIndex = lastIndex + current.length; };
}
// Only set indexes on objects and arrays
if(typeof current === "object") {
@@ -316,7 +316,7 @@ function deleteDataItem(data,indexes) {
var lastIndex = indexes[indexes.length - 1];
if(Array.isArray(current) && current !== null) {
lastIndex = $tw.utils.parseInt(lastIndex);
if(lastIndex < 0) { lastIndex = lastIndex + current.length };
if(lastIndex < 0) { lastIndex = lastIndex + current.length; };
// Check if index is valid before splicing
if(lastIndex >= 0 && lastIndex < current.length) {
current.splice(lastIndex,1);

View File

@@ -25,7 +25,7 @@ exports.lookup = function(source,operator,options) {
indexSuffix = (suffixes[1] && suffixes[1][0] === "index") ? true : false,
target;
if(operator.operands.length == 2) {
target = operator.operands[1]
target = operator.operands[1];
} else {
target = indexSuffix ? "0": "text";
}

View File

@@ -17,35 +17,35 @@ Note that strings are converted to numbers automatically. Trailing non-digits ar
"use strict";
exports.negate = makeNumericBinaryOperator(
function(a) {return -a}
function(a) {return -a;}
);
exports.abs = makeNumericBinaryOperator(
function(a) {return Math.abs(a)}
function(a) {return Math.abs(a);}
);
exports.ceil = makeNumericBinaryOperator(
function(a) {return Math.ceil(a)}
function(a) {return Math.ceil(a);}
);
exports.floor = makeNumericBinaryOperator(
function(a) {return Math.floor(a)}
function(a) {return Math.floor(a);}
);
exports.round = makeNumericBinaryOperator(
function(a) {return Math.round(a)}
function(a) {return Math.round(a);}
);
exports.trunc = makeNumericBinaryOperator(
function(a) {return Math.trunc(a)}
function(a) {return Math.trunc(a);}
);
exports.untrunc = makeNumericBinaryOperator(
function(a) {return Math.ceil(Math.abs(a)) * Math.sign(a)}
function(a) {return Math.ceil(Math.abs(a)) * Math.sign(a);}
);
exports.sign = makeNumericBinaryOperator(
function(a) {return Math.sign(a)}
function(a) {return Math.sign(a);}
);
exports.add = makeNumericBinaryOperator(
@@ -103,29 +103,29 @@ exports.log = makeNumericBinaryOperator(
);
exports.sum = makeNumericReducingOperator(
function(accumulator,value) {return accumulator + value},
function(accumulator,value) {return accumulator + value;},
0 // Initial value
);
exports.product = makeNumericReducingOperator(
function(accumulator,value) {return accumulator * value},
function(accumulator,value) {return accumulator * value;},
1 // Initial value
);
exports.maxall = makeNumericReducingOperator(
function(accumulator,value) {return Math.max(accumulator,value)},
function(accumulator,value) {return Math.max(accumulator,value);},
-Infinity // Initial value
);
exports.minall = makeNumericReducingOperator(
function(accumulator,value) {return Math.min(accumulator,value)},
function(accumulator,value) {return Math.min(accumulator,value);},
Infinity // Initial value
);
exports.median = makeNumericArrayOperator(
function(values) {
var len = values.length, median;
values.sort(function(a,b) {return a-b});
values.sort(function(a,b) {return a-b;});
if(len % 2) {
// Odd, return the middle number
median = values[(len - 1) / 2];
@@ -138,7 +138,7 @@ exports.median = makeNumericArrayOperator(
);
exports.average = makeNumericReducingOperator(
function(accumulator,value) {return accumulator + value},
function(accumulator,value) {return accumulator + value;},
0, // Initial value
function(finalValue,numberOfValues) {
return finalValue/numberOfValues;
@@ -146,7 +146,7 @@ exports.average = makeNumericReducingOperator(
);
exports.variance = makeNumericReducingOperator(
function(accumulator,value) {return accumulator + value},
function(accumulator,value) {return accumulator + value;},
0,
function(finalValue,numberOfValues,originalValues) {
return getVarianceFromArray(originalValues,finalValue/numberOfValues);
@@ -154,7 +154,7 @@ exports.variance = makeNumericReducingOperator(
);
exports["standard-deviation"] = makeNumericReducingOperator(
function(accumulator,value) {return accumulator + value},
function(accumulator,value) {return accumulator + value;},
0,
function(finalValue,numberOfValues,originalValues) {
var variance = getVarianceFromArray(originalValues,finalValue/numberOfValues);
@@ -164,31 +164,31 @@ exports["standard-deviation"] = makeNumericReducingOperator(
//trigonometry
exports.cos = makeNumericBinaryOperator(
function(a) {return Math.cos(a)}
function(a) {return Math.cos(a);}
);
exports.sin = makeNumericBinaryOperator(
function(a) {return Math.sin(a)}
function(a) {return Math.sin(a);}
);
exports.tan = makeNumericBinaryOperator(
function(a) {return Math.tan(a)}
function(a) {return Math.tan(a);}
);
exports.acos = makeNumericBinaryOperator(
function(a) {return Math.acos(a)}
function(a) {return Math.acos(a);}
);
exports.asin = makeNumericBinaryOperator(
function(a) {return Math.asin(a)}
function(a) {return Math.asin(a);}
);
exports.atan = makeNumericBinaryOperator(
function(a) {return Math.atan(a)}
function(a) {return Math.atan(a);}
);
exports.atan2 = makeNumericBinaryOperator(
function(a,b) {return Math.atan2(a,b)}
function(a,b) {return Math.atan2(a,b);}
);
//Calculate the variance of a population of numbers in an array given its mean
@@ -222,8 +222,8 @@ function makeNumericReducingOperator(fnCalc,initialValue,fnFinal) {
return [];
}
var value = result.reduce(function(accumulator,currentValue) {
return fnCalc(accumulator,currentValue);
},initialValue);
return fnCalc(accumulator,currentValue);
},initialValue);
if(fnFinal) {
value = fnFinal(value,result.length,result);
}

View File

@@ -21,7 +21,7 @@ exports.range = function(source,operator,options) {
}
// Process the parts
var beg, end, inc, i, fixed = 0;
for (i=0; i<parts.length; i++) {
for(i=0; i<parts.length; i++) {
// Validate real number
if(!/^\s*[+-]?((\d+(\.\d*)?)|(\.\d+))\s*$/.test(parts[i])) {
return ["range: bad number \"" + parts[i] + "\""];
@@ -36,10 +36,10 @@ exports.range = function(source,operator,options) {
switch(parts.length) {
case 1:
end = parts[0];
if (end >= 1) {
if(end >= 1) {
beg = 1;
}
else if (end <= -1) {
else if(end <= -1) {
beg = -1;
}
else {
@@ -72,7 +72,7 @@ exports.range = function(source,operator,options) {
end += direction * 0.5 * Math.pow(0.1,fixed);
var safety = 10010;
// Enumerate the range
if (end<beg) {
if(end<beg) {
for(i=beg; i>end; i+=inc) {
results.push(i.toFixed(fixed));
if(--safety<0) {

View File

@@ -15,7 +15,7 @@ Export our filter function
exports.removesuffix = function(source,operator,options) {
var results = [],
suffixes = (operator.suffixes || [])[0] || [];
if (!operator.operand) {
if(!operator.operand) {
source(function(tiddler,title) {
results.push(title);
});

View File

@@ -14,31 +14,31 @@ Export our filter function
*/
exports.sort = function(source,operator,options) {
var results = prepare_results(source);
options.wiki.sortTiddlers(results,operator.operands[0] || "title",operator.prefix === "!",false,false,undefined,operator.operands[1]);
options.wiki.sortTiddlers(results,operator.operand || "title",operator.prefix === "!",false,false);
return results;
};
exports.nsort = function(source,operator,options) {
var results = prepare_results(source);
options.wiki.sortTiddlers(results,operator.operands[0] || "title",operator.prefix === "!",false,true,undefined,operator.operands[1]);
options.wiki.sortTiddlers(results,operator.operand || "title",operator.prefix === "!",false,true);
return results;
};
exports.sortan = function(source, operator, options) {
var results = prepare_results(source);
options.wiki.sortTiddlers(results, operator.operands[0] || "title", operator.prefix === "!",false,false,true,operator.operands[1]);
options.wiki.sortTiddlers(results, operator.operand || "title", operator.prefix === "!",false,false,true);
return results;
};
exports.sortcs = function(source,operator,options) {
var results = prepare_results(source);
options.wiki.sortTiddlers(results,operator.operands[0] || "title",operator.prefix === "!",true,false,undefined,operator.operands[1]);
options.wiki.sortTiddlers(results,operator.operand || "title",operator.prefix === "!",true,false);
return results;
};
exports.nsortcs = function(source,operator,options) {
var results = prepare_results(source);
options.wiki.sortTiddlers(results,operator.operands[0] || "title",operator.prefix === "!",true,true,undefined,operator.operands[1]);
options.wiki.sortTiddlers(results,operator.operand || "title",operator.prefix === "!",true,true);
return results;
};

View File

@@ -15,7 +15,7 @@ Export our filter function
exports.suffix = function(source,operator,options) {
var results = [],
suffixes = (operator.suffixes || [])[0] || [];
if (!operator.operand) {
if(!operator.operand) {
source(function(tiddler,title) {
results.push(title);
});

View File

@@ -7,224 +7,224 @@ Extended filter operators to manipulate the current list.
\*/
"use strict";
"use strict";
/*
/*
Fetch titles from the current list
*/
var prepare_results = function (source) {
var prepare_results = function (source) {
var results = [];
source(function (tiddler, title) {
results.push(title);
});
return results;
};
source(function (tiddler, title) {
results.push(title);
});
return results;
};
/*
/*
Moves a number of items from the tail of the current list before the item named in the operand
*/
exports.putbefore = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1);
return (index === -1) ?
results.slice(0, -1) :
results.slice(0, index).concat(results.slice(-count)).concat(results.slice(index, -count));
};
exports.putbefore = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1);
return (index === -1) ?
results.slice(0, -1) :
results.slice(0, index).concat(results.slice(-count)).concat(results.slice(index, -count));
};
/*
/*
Moves a number of items from the tail of the current list after the item named in the operand
*/
exports.putafter = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1);
return (index === -1) ?
results.slice(0, -1) :
results.slice(0, index + 1).concat(results.slice(-count)).concat(results.slice(index + 1, -count));
};
exports.putafter = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1);
return (index === -1) ?
results.slice(0, -1) :
results.slice(0, index + 1).concat(results.slice(-count)).concat(results.slice(index + 1, -count));
};
/*
/*
Replaces the item named in the operand with a number of items from the tail of the current list
*/
exports.replace = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1);
return (index === -1) ?
results.slice(0, -count) :
results.slice(0, index).concat(results.slice(-count)).concat(results.slice(index + 1, -count));
};
exports.replace = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1);
return (index === -1) ?
results.slice(0, -count) :
results.slice(0, index).concat(results.slice(-count)).concat(results.slice(index + 1, -count));
};
/*
/*
Moves a number of items from the tail of the current list to the head of the list
*/
exports.putfirst = function (source, operator) {
var results = prepare_results(source),
count = $tw.utils.getInt(operator.suffix,1);
return results.slice(-count).concat(results.slice(0, -count));
};
exports.putfirst = function (source, operator) {
var results = prepare_results(source),
count = $tw.utils.getInt(operator.suffix,1);
return results.slice(-count).concat(results.slice(0, -count));
};
/*
/*
Moves a number of items from the head of the current list to the tail of the list
*/
exports.putlast = function (source, operator) {
var results = prepare_results(source),
count = $tw.utils.getInt(operator.suffix,1);
return results.slice(count).concat(results.slice(0, count));
};
exports.putlast = function (source, operator) {
var results = prepare_results(source),
count = $tw.utils.getInt(operator.suffix,1);
return results.slice(count).concat(results.slice(0, count));
};
/*
/*
Moves the item named in the operand a number of places forward or backward in the list
*/
exports.move = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1),
marker = results.splice(index, 1),
offset = (index + count) > 0 ? index + count : 0;
return results.slice(0, offset).concat(marker).concat(results.slice(offset));
};
exports.move = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand),
count = $tw.utils.getInt(operator.suffix,1),
marker = results.splice(index, 1),
offset = (index + count) > 0 ? index + count : 0;
return results.slice(0, offset).concat(marker).concat(results.slice(offset));
};
/*
/*
Returns the items from the current list that are after the item named in the operand
*/
exports.allafter = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand);
return (index === -1) ? [] :
(operator.suffix) ? results.slice(index) :
exports.allafter = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand);
return (index === -1) ? [] :
(operator.suffix) ? results.slice(index) :
results.slice(index + 1);
};
};
/*
/*
Returns the items from the current list that are before the item named in the operand
*/
exports.allbefore = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand);
return (index === -1) ? [] :
(operator.suffix) ? results.slice(0, index + 1) :
exports.allbefore = function (source, operator) {
var results = prepare_results(source),
index = results.indexOf(operator.operand);
return (index === -1) ? [] :
(operator.suffix) ? results.slice(0, index + 1) :
results.slice(0, index);
};
};
/*
/*
Appends the items listed in the operand array to the tail of the current list
*/
exports.append = function (source, operator) {
var append = $tw.utils.parseStringArray(operator.operand, "true"),
results = prepare_results(source),
count = parseInt(operator.suffix) || append.length;
return (append.length === 0) ? results :
(operator.prefix) ? results.concat(append.slice(-count)) :
exports.append = function (source, operator) {
var append = $tw.utils.parseStringArray(operator.operand, "true"),
results = prepare_results(source),
count = parseInt(operator.suffix) || append.length;
return (append.length === 0) ? results :
(operator.prefix) ? results.concat(append.slice(-count)) :
results.concat(append.slice(0, count));
};
};
/*
/*
Prepends the items listed in the operand array to the head of the current list
*/
exports.prepend = function (source, operator) {
var prepend = $tw.utils.parseStringArray(operator.operand, "true"),
results = prepare_results(source),
count = $tw.utils.getInt(operator.suffix,prepend.length);
return (prepend.length === 0) ? results :
(operator.prefix) ? prepend.slice(-count).concat(results) :
exports.prepend = function (source, operator) {
var prepend = $tw.utils.parseStringArray(operator.operand, "true"),
results = prepare_results(source),
count = $tw.utils.getInt(operator.suffix,prepend.length);
return (prepend.length === 0) ? results :
(operator.prefix) ? prepend.slice(-count).concat(results) :
prepend.slice(0, count).concat(results);
};
};
/*
/*
Returns all items from the current list except the items listed in the operand array
*/
exports.remove = function (source, operator) {
var array = $tw.utils.parseStringArray(operator.operand, "true"),
results = prepare_results(source),
count = parseInt(operator.suffix) || array.length,
p,
len,
index;
len = array.length - 1;
for (p = 0; p < count; ++p) {
if (operator.prefix) {
index = results.indexOf(array[len - p]);
} else {
index = results.indexOf(array[p]);
}
if (index !== -1) {
results.splice(index, 1);
}
exports.remove = function (source, operator) {
var array = $tw.utils.parseStringArray(operator.operand, "true"),
results = prepare_results(source),
count = parseInt(operator.suffix) || array.length,
p,
len,
index;
len = array.length - 1;
for(p = 0; p < count; ++p) {
if(operator.prefix) {
index = results.indexOf(array[len - p]);
} else {
index = results.indexOf(array[p]);
}
return results;
};
if(index !== -1) {
results.splice(index, 1);
}
}
return results;
};
/*
/*
Returns all items from the current list sorted in the order of the items in the operand array
*/
exports.sortby = function (source, operator) {
var results = prepare_results(source);
if (!results || results.length < 2) {
return results;
}
var lookup = $tw.utils.parseStringArray(operator.operand, "true");
results.sort(function (a, b) {
return lookup.indexOf(a) - lookup.indexOf(b);
});
exports.sortby = function (source, operator) {
var results = prepare_results(source);
if(!results || results.length < 2) {
return results;
};
}
var lookup = $tw.utils.parseStringArray(operator.operand, "true");
results.sort(function (a, b) {
return lookup.indexOf(a) - lookup.indexOf(b);
});
return results;
};
/*
/*
Removes all duplicate items from the current list
*/
exports.unique = function (source, operator) {
var results = prepare_results(source);
var set = results.reduce(function (a, b) {
if (a.indexOf(b) < 0) {
a.push(b);
}
return a;
}, []);
return set;
};
var cycleValueInArray = function(results,operands,stepSize) {
var resultsIndex,
step = stepSize || 1,
i = 0,
opLength = operands.length,
nextOperandIndex;
for(i; i < opLength; i++) {
resultsIndex = results.indexOf(operands[i]);
if(resultsIndex !== -1) {
break;
}
exports.unique = function (source, operator) {
var results = prepare_results(source);
var set = results.reduce(function (a, b) {
if(a.indexOf(b) < 0) {
a.push(b);
}
return a;
}, []);
return set;
};
var cycleValueInArray = function(results,operands,stepSize) {
var resultsIndex,
step = stepSize || 1,
i = 0,
opLength = operands.length,
nextOperandIndex;
for(i; i < opLength; i++) {
resultsIndex = results.indexOf(operands[i]);
if(resultsIndex !== -1) {
i = i + step;
nextOperandIndex = (i < opLength ? i : i % opLength);
if(operands.length > 1) {
results.splice(resultsIndex,1,operands[nextOperandIndex]);
} else {
results.splice(resultsIndex,1);
}
} else {
results.push(operands[0]);
break;
}
return results;
}
if(resultsIndex !== -1) {
i = i + step;
nextOperandIndex = (i < opLength ? i : i % opLength);
if(operands.length > 1) {
results.splice(resultsIndex,1,operands[nextOperandIndex]);
} else {
results.splice(resultsIndex,1);
}
} else {
results.push(operands[0]);
}
return results;
};
/*
/*
Toggles an item in the current list.
*/
exports.toggle = function(source,operator) {
return cycleValueInArray(prepare_results(source),operator.operands);
}
exports.toggle = function(source,operator) {
return cycleValueInArray(prepare_results(source),operator.operands);
};
exports.cycle = function(source,operator) {
var results = prepare_results(source),
operands = (operator.operand.length ? $tw.utils.parseStringArray(operator.operand, "true") : [""]),
step = $tw.utils.getInt(operator.operands[1]||"",1);
if(step < 0) {
operands.reverse();
step = Math.abs(step);
}
return cycleValueInArray(results,operands,step);
exports.cycle = function(source,operator) {
var results = prepare_results(source),
operands = (operator.operand.length ? $tw.utils.parseStringArray(operator.operand, "true") : [""]),
step = $tw.utils.getInt(operator.operands[1]||"",1);
if(step < 0) {
operands.reverse();
step = Math.abs(step);
}
return cycleValueInArray(results,operands,step);
};

View File

@@ -46,7 +46,7 @@ function BackSubIndexer(indexer,extractor) {
BackSubIndexer.prototype.init = function() {
// lazy init until first lookup
this.index = null;
}
};
BackSubIndexer.prototype._init = function() {
this.index = Object.create(null);
@@ -60,11 +60,11 @@ BackSubIndexer.prototype._init = function() {
self.index[target][sourceTitle] = true;
});
});
}
};
BackSubIndexer.prototype.rebuild = function() {
this.index = null;
}
};
/*
* Get things that is being referenced in the text, e.g. tiddler names in the link syntax.
@@ -78,7 +78,7 @@ BackSubIndexer.prototype._getTarget = function(tiddler) {
return this.wiki[this.extractor](parser.tree, tiddler.fields.title);
}
return [];
}
};
BackSubIndexer.prototype.update = function(updateDescriptor) {
// lazy init/update until first lookup
@@ -86,8 +86,8 @@ BackSubIndexer.prototype.update = function(updateDescriptor) {
return;
}
var newTargets = [],
oldTargets = [],
self = this;
oldTargets = [],
self = this;
if(updateDescriptor.old.exists) {
oldTargets = this._getTarget(updateDescriptor.old.tiddler);
}
@@ -106,7 +106,7 @@ BackSubIndexer.prototype.update = function(updateDescriptor) {
}
self.index[target][updateDescriptor.new.tiddler.fields.title] = true;
});
}
};
BackSubIndexer.prototype.lookup = function(title) {
if(!this.index) {
@@ -117,6 +117,6 @@ BackSubIndexer.prototype.lookup = function(title) {
} else {
return [];
}
}
};
exports.BackIndexer = BackIndexer;

View File

@@ -19,7 +19,7 @@ FieldIndexer.prototype.init = function() {
this.index = null;
this.maxIndexedValueLength = DEFAULT_MAXIMUM_INDEXED_VALUE_LENGTH;
this.addIndexMethods();
}
};
// Provided for testing
FieldIndexer.prototype.setMaxIndexedValueLength = function(length) {
@@ -33,14 +33,14 @@ FieldIndexer.prototype.addIndexMethods = function() {
this.wiki.each.byField = function(name,value) {
var lookup = self.lookup(name,value);
return lookup && lookup.filter(function(title) {
return self.wiki.tiddlerExists(title)
return self.wiki.tiddlerExists(title);
});
};
// get shadow tiddlers, including shadow tiddlers that is overwritten
this.wiki.eachShadow.byField = function(name,value) {
var lookup = self.lookup(name,value);
return lookup && lookup.filter(function(title) {
return self.wiki.isShadowTiddler(title)
return self.wiki.isShadowTiddler(title);
});
};
this.wiki.eachTiddlerPlusShadows.byField = function(name,value) {

View File

@@ -14,12 +14,12 @@ exports.getInfoTiddlerFields = function(updateInfoTiddlersCallback) {
this.updateCallback = updateCallback;
this.resizeHandlers = new Map();
this.dimensionsInfo = [
["outer/width", win => win.outerWidth],
["outer/height", win => win.outerHeight],
["inner/width", win => win.innerWidth],
["inner/height", win => win.innerHeight],
["client/width", win => win.document.documentElement.clientWidth],
["client/height", win => win.document.documentElement.clientHeight]
["outer/width", (win) => win.outerWidth],
["outer/height", (win) => win.outerHeight],
["inner/width", (win) => win.innerWidth],
["inner/height", (win) => win.innerHeight],
["client/width", (win) => win.document.documentElement.clientWidth],
["client/height", (win) => win.document.documentElement.clientHeight]
];
}

View File

@@ -140,7 +140,7 @@ function KeyboardManager(options) {
this.shortcutParsedList = []; // Stores the parsed key descriptors
this.shortcutPriorityList = []; // Stores the parsed shortcut priority
this.lookupNames = ["shortcuts"];
this.lookupNames.push($tw.platform.isMac ? "shortcuts-mac" : "shortcuts-not-mac")
this.lookupNames.push($tw.platform.isMac ? "shortcuts-mac" : "shortcuts-not-mac");
this.lookupNames.push($tw.platform.isWindows ? "shortcuts-windows" : "shortcuts-not-windows");
this.lookupNames.push($tw.platform.isLinux ? "shortcuts-linux" : "shortcuts-not-linux");
this.updateShortcutLists(this.getShortcutTiddlerList());
@@ -161,7 +161,7 @@ KeyboardManager.prototype.getModifierKeys = function() {
91, // Meta (left)
93, // Meta (right)
224 // Meta (Firefox)
]
];
};
/*
@@ -187,8 +187,7 @@ KeyboardManager.prototype.parseKeyDescriptor = function(keyDescriptor,options) {
metaKey: false
};
for(var t=0; t<components.length; t++) {
var s = components[t].toLowerCase(),
c = s.charCodeAt(0);
var s = components[t].toLowerCase();
// Look for modifier keys
if(s === "ctrl") {
info.ctrlKey = true;
@@ -266,7 +265,7 @@ KeyboardManager.prototype.getPrintableShortcuts = function(keyInfoArray) {
}
});
return result;
}
};
KeyboardManager.prototype.checkKeyDescriptor = function(event,keyInfo) {
return keyInfo &&
@@ -293,15 +292,15 @@ KeyboardManager.prototype.getMatchingKeyDescriptor = function(event,keyInfoArray
KeyboardManager.prototype.getEventModifierKeyDescriptor = function(event) {
return event.ctrlKey && !event.shiftKey && !event.altKey && !event.metaKey ? "ctrl" :
event.shiftKey && !event.ctrlKey && !event.altKey && !event.metaKey ? "shift" :
event.ctrlKey && event.shiftKey && !event.altKey && !event.metaKey ? "ctrl-shift" :
event.altKey && !event.shiftKey && !event.ctrlKey && !event.metaKey ? "alt" :
event.altKey && event.shiftKey && !event.ctrlKey && !event.metaKey ? "alt-shift" :
event.altKey && event.ctrlKey && !event.shiftKey && !event.metaKey ? "ctrl-alt" :
event.altKey && event.shiftKey && event.ctrlKey && !event.metaKey ? "ctrl-alt-shift" :
event.metaKey && !event.ctrlKey && !event.shiftKey && !event.altKey ? "meta" :
event.metaKey && event.ctrlKey && !event.shiftKey && !event.altKey ? "meta-ctrl" :
event.metaKey && event.ctrlKey && event.shiftKey && !event.altKey ? "meta-ctrl-shift" :
event.metaKey && event.ctrlKey && event.shiftKey && event.altKey ? "meta-ctrl-alt-shift" : "normal";
event.ctrlKey && event.shiftKey && !event.altKey && !event.metaKey ? "ctrl-shift" :
event.altKey && !event.shiftKey && !event.ctrlKey && !event.metaKey ? "alt" :
event.altKey && event.shiftKey && !event.ctrlKey && !event.metaKey ? "alt-shift" :
event.altKey && event.ctrlKey && !event.shiftKey && !event.metaKey ? "ctrl-alt" :
event.altKey && event.shiftKey && event.ctrlKey && !event.metaKey ? "ctrl-alt-shift" :
event.metaKey && !event.ctrlKey && !event.shiftKey && !event.altKey ? "meta" :
event.metaKey && event.ctrlKey && !event.shiftKey && !event.altKey ? "meta-ctrl" :
event.metaKey && event.ctrlKey && event.shiftKey && !event.altKey ? "meta-ctrl-shift" :
event.metaKey && event.ctrlKey && event.shiftKey && event.altKey ? "meta-ctrl-alt-shift" : "normal";
};
KeyboardManager.prototype.getShortcutTiddlerList = function() {
@@ -371,8 +370,8 @@ KeyboardManager.prototype.handleShortcutChanges = function(changedTiddlers) {
var newList = this.getShortcutTiddlerList();
var hasChanged = $tw.utils.hopArray(changedTiddlers,this.shortcutTiddlers) ? true :
($tw.utils.hopArray(changedTiddlers,newList) ? true :
(this.detectNewShortcuts(changedTiddlers))
);
(this.detectNewShortcuts(changedTiddlers))
);
// Re-cache shortcuts if something changed
if(hasChanged) {
this.updateShortcutLists(newList);

View File

@@ -24,8 +24,7 @@ exports.params = [
Run the macro
*/
exports.run = function(filter,format) {
var self = this,
tiddlers = this.wiki.filterTiddlers(filter),
var tiddlers = this.wiki.filterTiddlers(filter),
tiddler,
fields = [],
t,f;
@@ -46,24 +45,24 @@ exports.run = function(filter,format) {
var p = fields.indexOf(value);
if(p !== -1) {
fields.splice(p,1);
fields.unshift(value)
fields.unshift(value);
}
});
// Output the column headings
var output = [], row = [];
fields.forEach(function(value) {
row.push(quoteAndEscape(value))
row.push(quoteAndEscape(value));
});
output.push(row.join(","));
// Output each tiddler
for(var t=0;t<tiddlers.length; t++) {
row = [];
tiddler = this.wiki.getTiddler(tiddlers[t]);
if(tiddler) {
for(f=0; f<fields.length; f++) {
row.push(quoteAndEscape(tiddler ? tiddler.getFieldString(fields[f]) || "" : ""));
}
}
if(tiddler) {
for(f=0; f<fields.length; f++) {
row.push(quoteAndEscape(tiddler ? tiddler.getFieldString(fields[f]) || "" : ""));
}
}
output.push(row.join(","));
}
return output.join("\n");

View File

@@ -31,8 +31,8 @@ exports.run = function(shortcuts,prefix,separator,suffix) {
}));
if(shortcutArray.length > 0) {
shortcutArray.sort(function(a,b) {
return a.toLowerCase().localeCompare(b.toLowerCase());
})
return a.toLowerCase().localeCompare(b.toLowerCase());
});
return prefix + shortcutArray.join(separator) + suffix;
} else {
return "";

View File

@@ -7,19 +7,17 @@ The audio parser parses an audio tiddler into an embeddable HTML element
\*/
/*jslint node: true, browser: true */
/*global $tw: false */
"use strict";
var AudioParser = function(type,text,options) {
var element = {
type: "element",
tag: "$audio", // Using $audio to enable widget interception
attributes: {
controls: {type: "string", value: "controls"},
style: {type: "string", value: "width: 100%; object-fit: contain"}
}
};
type: "element",
tag: "$audio", // Using $audio to enable widget interception
attributes: {
controls: {type: "string", value: "controls"},
style: {type: "string", value: "width: 100%; object-fit: contain"}
}
};
// Pass through source information
if(options._canonical_uri) {

View File

@@ -59,7 +59,7 @@ var BinaryParser = function(type,text,options) {
class: {type: "string", value: "tc-binary-warning"}
},
children: [warn, link]
}
};
this.tree = [element];
this.source = text;
this.type = type;

View File

@@ -45,7 +45,7 @@ var CsvParser = function(type,text,options) {
row.children.push({
"type": "element", "tag": tag, "children": [{
"type": "text",
"text": columns[column] || ''
"text": columns[column] || ""
}]
});
}

View File

@@ -45,7 +45,7 @@ exports.parseWhiteSpace = function(source,pos) {
type: "whitespace",
start: pos,
end: p
}
};
}
};
@@ -107,7 +107,7 @@ exports.parseStringLiteral = function(source,pos) {
type: "string",
start: pos
};
var reString = /(?:"""([\s\S]*?)"""|"([^"]*)")|(?:'([^']*)')|\[\[((?:[^\]]|\](?!\]))*)\]\]/g;
var reString = /(?:"""([\s\S]*?)"""|"([^"]*)")|(?:'([^']*)')|\[\[((?:[^\]]|\](?!\]))*)\]\]/y;
reString.lastIndex = pos;
var match = reString.exec(source);
if(match && match.index === pos) {
@@ -170,7 +170,7 @@ exports.parseMacroParameters = function(node,source,pos) {
}
node.end = pos;
return node;
}
};
/*
Look for a macro invocation parameter. Returns null if not found, or {type: "macro-parameter", name:, value:, start:, end:}
@@ -192,16 +192,16 @@ exports.parseMacroParameter = function(source,pos) {
pos = token.end;
// Get the parameter details
node.value = token.match[2] !== undefined ? token.match[2] : (
token.match[3] !== undefined ? token.match[3] : (
token.match[4] !== undefined ? token.match[4] : (
token.match[5] !== undefined ? token.match[5] : (
token.match[6] !== undefined ? token.match[6] : (
""
)
)
)
token.match[3] !== undefined ? token.match[3] : (
token.match[4] !== undefined ? token.match[4] : (
token.match[5] !== undefined ? token.match[5] : (
token.match[6] !== undefined ? token.match[6] : (
""
)
);
)
)
)
);
if(token.match[1]) {
node.name = token.match[1];
}
@@ -221,7 +221,7 @@ exports.parseMacroInvocationAsTransclusion = function(source,pos) {
orderedAttributes: []
};
// Define our regexps
var reVarName = /([^\s>"'=:]+)/g;
var reVarName = /([^\s>"'=:]+)/y;
// Skip whitespace
pos = $tw.utils.skipWhiteSpace(source,pos);
// Look for a double opening angle bracket
@@ -237,9 +237,11 @@ exports.parseMacroInvocationAsTransclusion = function(source,pos) {
}
$tw.utils.addAttributeToParseTreeNode(node,"$variable",token.match[1]);
pos = token.end;
// Check that the tag is terminated by a space or >>
if(!$tw.utils.parseWhiteSpace(source,pos) && !(source.charAt(pos) === ">" && source.charAt(pos + 1) === ">") ) {
return null;
// Check that the tag is terminated by a space or >>, and that there is a closing >> somewhere ahead
if(!(source.charAt(pos) === ">" && source.charAt(pos + 1) === ">") ) {
if(source.indexOf(">>",pos) === -1) {
return null;
}
}
// Process attributes
pos = $tw.utils.parseMacroParametersAsAttributes(node,source,pos);
@@ -267,7 +269,7 @@ exports.parseMVVReferenceAsTransclusion = function(source,pos) {
orderedAttributes: []
};
// Define our regexps
var reVarName = /([^\s>"'=:)]+)/g;
var reVarName = /([^\s>"'=:)]+)/y;
// Skip whitespace
pos = $tw.utils.skipWhiteSpace(source,pos);
// Look for a double opening parenthesis
@@ -323,18 +325,24 @@ exports.parseMacroParameterAsAttribute = function(source,pos) {
start: pos
};
// Define our regexps
var reAttributeName = /([^\/\s>"'`=:]+)/g,
reUnquotedAttribute = /((?:(?:>(?!>))|[^\s>"'])+)/g,
reFilteredValue = /\{\{\{([\S\s]+?)\}\}\}/g,
reIndirectValue = /\{\{([^\}]+)\}\}/g,
reSubstitutedValue = /(?:```([\s\S]*?)```|`([^`]|[\S\s]*?)`)/g;
var reAttributeName = /([^\/\s>"'`=:]+)/y,
reStrictIdentifier = /^[A-Za-z0-9\-_]+$/,
reUnquotedAttribute = /(?!<<)((?:(?:>(?!>))|[^\s>"'])+)/y,
reFilteredValue = /\{\{\{([\S\s]+?)\}\}\}/y,
reIndirectValue = /\{\{([^\}]+)\}\}/y,
reSubstitutedValue = /(?:```([\s\S]*?)```|`([^`]|[\S\s]*?)`)/y;
// Skip whitespace
pos = $tw.utils.skipWhiteSpace(source,pos);
// Get the attribute name and the separator token
var nameToken = $tw.utils.parseTokenRegExp(source,pos,reAttributeName),
namePos = nameToken && $tw.utils.skipWhiteSpace(source,nameToken.end),
separatorToken = nameToken && $tw.utils.parseTokenRegExp(source,namePos,/=|:/g),
separatorToken = nameToken && $tw.utils.parseTokenRegExp(source,namePos,/=|:/y),
isNewStyleSeparator = false; // If there is no separator then we don't allow new style values
// Colon separator requires a strict identifier name to avoid mis-parsing values like $:/foo
if(nameToken && separatorToken && separatorToken.match[0] === ":" && !reStrictIdentifier.test(nameToken.match[1])) {
nameToken = null;
separatorToken = null;
}
// If we have a name and a separator then we have a named attribute
if(nameToken && separatorToken) {
node.name = nameToken.match[1];
@@ -345,64 +353,78 @@ exports.parseMacroParameterAsAttribute = function(source,pos) {
}
// Skip whitespace
pos = $tw.utils.skipWhiteSpace(source,pos);
// Look for a string literal
var stringLiteral = $tw.utils.parseStringLiteral(source,pos);
if(stringLiteral) {
pos = stringLiteral.end;
node.type = "string";
node.value = stringLiteral.value;
// Mark the value as having been quoted in the source
node.quoted = true;
} else {
// Look for a filtered value
var filteredValue = $tw.utils.parseTokenRegExp(source,pos,reFilteredValue);
if(filteredValue && isNewStyleSeparator) {
pos = filteredValue.end;
node.type = "filtered";
node.filter = filteredValue.match[1];
} else {
do {
// Look for a string literal
var stringLiteral = $tw.utils.parseStringLiteral(source,pos);
if(stringLiteral) {
pos = stringLiteral.end;
node.type = "string";
node.value = stringLiteral.value;
// Mark the value as having been quoted in the source
node.quoted = true;
break;
}
if(isNewStyleSeparator) {
// Look for a filtered value
var filteredValue = $tw.utils.parseTokenRegExp(source,pos,reFilteredValue);
if(filteredValue) {
pos = filteredValue.end;
node.type = "filtered";
node.filter = filteredValue.match[1];
break;
}
// Look for an indirect value
var indirectValue = $tw.utils.parseTokenRegExp(source,pos,reIndirectValue);
if(indirectValue && isNewStyleSeparator) {
if(indirectValue) {
pos = indirectValue.end;
node.type = "indirect";
node.textReference = indirectValue.match[1];
} else {
// Look for a macro invocation value
var macroInvocation = $tw.utils.parseMacroInvocationAsTransclusion(source,pos);
if(macroInvocation && isNewStyleSeparator) {
pos = macroInvocation.end;
node.type = "macro";
node.value = macroInvocation;
} else {
// Look for an MVV reference value
var mvvReference = $tw.utils.parseMVVReferenceAsTransclusion(source,pos);
if(mvvReference && isNewStyleSeparator) {
pos = mvvReference.end;
node.type = "macro";
node.value = mvvReference;
node.isMVV = true;
} else {
var substitutedValue = $tw.utils.parseTokenRegExp(source,pos,reSubstitutedValue);
if(substitutedValue && isNewStyleSeparator) {
pos = substitutedValue.end;
node.type = "substituted";
node.rawValue = substitutedValue.match[1] || substitutedValue.match[2];
} else {
// Look for a unquoted value
var unquotedValue = $tw.utils.parseTokenRegExp(source,pos,reUnquotedAttribute);
if(unquotedValue) {
pos = unquotedValue.end;
node.type = "string";
node.value = unquotedValue.match[1];
} else {
}
}
}
}
break;
}
// Look for a macro invocation value
var macroInvocation = $tw.utils.parseMacroInvocationAsTransclusion(source,pos);
if(macroInvocation) {
pos = macroInvocation.end;
node.type = "macro";
node.value = macroInvocation;
break;
}
// Look for an MVV reference value
var mvvReference = $tw.utils.parseMVVReferenceAsTransclusion(source,pos);
if(mvvReference) {
pos = mvvReference.end;
node.type = "macro";
node.value = mvvReference;
node.isMVV = true;
break;
}
// Look for a substituted value
var substitutedValue = $tw.utils.parseTokenRegExp(source,pos,reSubstitutedValue);
if(substitutedValue) {
pos = substitutedValue.end;
node.type = "substituted";
node.rawValue = substitutedValue.match[1] || substitutedValue.match[2];
break;
}
}
}
// Look for a unquoted value
var unquotedValue = $tw.utils.parseTokenRegExp(source,pos,reUnquotedAttribute);
if(unquotedValue) {
pos = unquotedValue.end;
node.type = "string";
node.value = unquotedValue.match[1];
break; // redundant, but leaving for consistency
}
} while(false);
// Bail if we don't have a value
if(!node.type) {
return null;
@@ -554,6 +576,9 @@ exports.parseAttribute = function(source,pos) {
pos = unquotedValue.end;
node.type = "string";
node.value = unquotedValue.match[1];
} else if(source.charAt(pos) === "<" && source.charAt(pos + 1) === "<" && source.indexOf(">>",pos) !== -1) {
// Value looks like a macro invocation (starts with << with a closing >> ahead) but does not parse as one. Return null so the enclosing tag fails to parse rather than silently binding the attribute to "true" and treating the remainder as further attributes (restores v5.3.8 behaviour)
return null;
} else {
node.type = "string";
node.value = "true";

View File

@@ -11,11 +11,10 @@ The PDF parser embeds a PDF viewer
var ImageParser = function(type,text,options) {
var element = {
type: "element",
tag: "iframe",
attributes: {}
},
src;
type: "element",
tag: "iframe",
attributes: {}
};
if(options._canonical_uri) {
element.attributes.src = {type: "string", value: options._canonical_uri};
} else if(text) {

View File

@@ -11,14 +11,13 @@ The video parser parses a video tiddler into an embeddable HTML element
var VideoParser = function(type,text,options) {
var element = {
type: "element",
tag: "video",
attributes: {
controls: {type: "string", value: "controls"},
style: {type: "string", value: "width: 100%; object-fit: contain"}
}
},
src;
type: "element",
tag: "video",
attributes: {
controls: {type: "string", value: "controls"},
style: {type: "string", value: "width: 100%; object-fit: contain"}
}
};
if(options._canonical_uri) {
element.attributes.src = {type: "string", value: options._canonical_uri};
} else if(text) {

View File

@@ -46,10 +46,10 @@ exports.parse = function() {
}
// Return the $codeblock widget
return [{
type: "codeblock",
attributes: {
code: {type: "string", value: text, start: codeStart, end: this.parser.pos},
language: {type: "string", value: this.match[1], start: languageStart, end: languageEnd}
}
type: "codeblock",
attributes: {
code: {type: "string", value: text, start: codeStart, end: this.parser.pos},
language: {type: "string", value: this.match[1], start: languageStart, end: languageEnd}
}
}];
};

View File

@@ -51,10 +51,10 @@ exports.parse = function() {
var commentStart = this.match.index;
var commentEnd = this.endMatch.index + this.endMatch[0].length;
return [{
type: "void",
children: [],
text: this.parser.source.slice(commentStart, commentEnd),
start: commentStart,
end: commentEnd
type: "void",
children: [],
text: this.parser.source.slice(commentStart, commentEnd),
start: commentStart,
end: commentEnd
}];
};

View File

@@ -44,9 +44,9 @@ exports.parse = function() {
var commentStart = this.match.index;
var commentEnd = this.endMatch.index + this.endMatch[0].length;
return [{
type: "void",
text: this.parser.source.slice(commentStart, commentEnd),
start: commentStart,
end: commentEnd
type: "void",
text: this.parser.source.slice(commentStart, commentEnd),
start: commentStart,
end: commentEnd
}];
};

View File

@@ -95,7 +95,7 @@ exports.parseIfClause = function(filterCondition) {
hasLineBreak = !!$tw.utils.parseTokenRegExp(this.parser.source,this.parser.pos,/([^\S\n\r]*\r?\n(?:[^\S\n\r]*\r?\n|$))/g);
// If we found an else then we need to parse the body looking for the endif
var reEndString = "\\<\\%\\s*(endif)\\s*\\%\\>",
ex;
ex;
if(hasLineBreak) {
ex = this.parser.parseBlocksTerminatedExtended(reEndString);
} else {

View File

@@ -26,8 +26,6 @@ exports.init = function(parser) {
Parse the most recent match
*/
exports.parse = function() {
// Get all the details of the match
var entityString = this.match[1];
// Move past the macro call
this.parser.pos = this.matchRegExp.lastIndex;
// Return the entity

View File

@@ -29,7 +29,6 @@ exports.init = function(parser) {
Parse the most recent match
*/
exports.parse = function() {
var self = this;
// Move past the pragma invocation
this.parser.pos = this.matchRegExp.lastIndex;
// Parse the filter terminated by a line break

View File

@@ -93,7 +93,7 @@ exports.parseLink = function(source,pos) {
splitPos = null;
}
// Pull out the tooltip and URL
var tooltip, URL, urlStart;
var URL, urlStart;
textNode.start = pos;
if(splitPos) {
urlStart = splitPos + 1;

View File

@@ -67,5 +67,5 @@ exports.parse = function() {
return [{
type: "void",
children: tree
}]
}];
};

View File

@@ -60,7 +60,7 @@ var processRow = function(prevColumns) {
// End of row
if(prevCell && colSpanCount > 1) {
if(prevCell.attributes && prevCell.attributes && prevCell.attributes.colspan) {
colSpanCount += prevCell.attributes.colspan.value;
colSpanCount += prevCell.attributes.colspan.value;
} else {
colSpanCount -= 1;
}
@@ -163,7 +163,7 @@ exports.parse = function() {
table.children.splice(0,0,rowContainer); // Insert it at the bottom
}
// Set the alignment - TODO: figure out why TW did this
// rowContainer.attributes.align = rowCount === 0 ? "top" : "bottom";
// rowContainer.attributes.align = rowCount === 0 ? "top" : "bottom";
// Parse the caption
rowContainer.children = this.parser.parseInlineRun(rowTermRegExp,{eatTerminator: true});
} else {

View File

@@ -32,17 +32,17 @@ exports.parse = function() {
params = this.match[3] ? this.match[3].split("|") : [];
// Prepare the transclude widget
var transcludeNode = {
type: "transclude",
attributes: {},
isBlock: true
};
type: "transclude",
attributes: {},
isBlock: true
};
$tw.utils.each(params,function(paramValue,index) {
var name = "" + index;
transcludeNode.attributes[name] = {
name: name,
type: "string",
value: paramValue
}
};
});
// Prepare the tiddler widget
var tr, targetTitle, targetField, targetIndex, tiddlerNode;

View File

@@ -32,16 +32,16 @@ exports.parse = function() {
params = this.match[3] ? this.match[3].split("|") : [];
// Prepare the transclude widget
var transcludeNode = {
type: "transclude",
attributes: {}
};
type: "transclude",
attributes: {}
};
$tw.utils.each(params,function(paramValue,index) {
var name = "" + index;
transcludeNode.attributes[name] = {
name: name,
type: "string",
value: paramValue
}
};
});
// Prepare the tiddler widget
var tr, targetTitle, targetField, targetIndex, tiddlerNode;

View File

@@ -25,8 +25,6 @@ $$$
"use strict";
var widget = require("$:/core/modules/widgets/widget.js");
exports.name = "typedblock";
exports.types = {block: true};

View File

@@ -49,8 +49,7 @@ PluginSwitcher.prototype.switchPlugins = function() {
var tiddler = self.wiki.getTiddler(title);
if(tiddler && tiddler.isPlugin() && plugins.indexOf(title) === -1) {
plugins.push(title);
var pluginInfo = $tw.utils.parseJSONSafe(self.wiki.getTiddlerText(title)),
dependents = $tw.utils.parseStringArray(tiddler.fields.dependents || "");
var dependents = $tw.utils.parseStringArray(tiddler.fields.dependents || "");
$tw.utils.each(dependents,function(title) {
accumulatePlugin(title);
});
@@ -58,11 +57,11 @@ PluginSwitcher.prototype.switchPlugins = function() {
};
accumulatePlugin(selectedPluginTitle);
// Read the plugin info for the incoming plugins
var changes = $tw.wiki.readPluginInfo(plugins);
$tw.wiki.readPluginInfo(plugins);
// Unregister any existing theme tiddlers
var unregisteredTiddlers = $tw.wiki.unregisterPluginTiddlers(this.pluginType);
$tw.wiki.unregisterPluginTiddlers(this.pluginType);
// Register any new theme tiddlers
var registeredTiddlers = $tw.wiki.registerPluginTiddlers(this.pluginType,plugins);
$tw.wiki.registerPluginTiddlers(this.pluginType,plugins);
// Unpack the current theme tiddlers
$tw.wiki.unpackPluginTiddlers();
// Call the switch handler

View File

@@ -0,0 +1,54 @@
/*\
title: $:/core/modules/relinkers/tiddlers.js
type: application/javascript
module-type: relinker
Relinks the tags and list fields of tiddlers.
Calls a tw-relinking-tiddler hook for every altered tiddler.
\*/
exports.name = "tiddlers";
exports.relink = function(wiki,fromTitle,toTitle,options) {
wiki.each(function(tiddler,title) {
var type = tiddler.fields.type || "";
// Don't touch plugins or JavaScript modules
if(!tiddler.fields["plugin-type"] && type !== "application/javascript") {
var tags = tiddler.fields.tags ? tiddler.fields.tags.slice(0) : undefined,
list = tiddler.fields.list ? tiddler.fields.list.slice(0) : undefined,
isModified = false,
processList = function(listField) {
if(listField && listField.indexOf(fromTitle) !== -1) {
// Remove any existing instances of the toTitle
var p = listField.indexOf(toTitle);
while(p !== -1) {
listField.splice(p,1);
p = listField.indexOf(toTitle);
}
// Replace the fromTitle with toTitle
$tw.utils.each(listField,function (title,index) {
if(title === fromTitle) {
listField[index] = toTitle;
isModified = true;
}
});
}
};
if(!options.dontRenameInTags) {
// Rename tags
processList(tags);
}
if(!options.dontRenameInLists) {
// Rename lists
processList(list);
}
if(isModified) {
var newTiddler = new $tw.Tiddler(tiddler,{tags: tags, list: list},wiki.getModificationFields());
newTiddler = $tw.hooks.invokeHook("th-relinking-tiddler",newTiddler,tiddler);
wiki.addTiddler(newTiddler);
}
}
});
};

View File

@@ -32,10 +32,10 @@ function SaverHandler(options) {
this.filterFn = this.wiki.compileFilter(this.wiki.getTiddlerText(this.titleSyncFilter));
// Count of changes that have not yet been saved
var filteredChanges = self.filterFn.call(self.wiki,function(iterator) {
$tw.utils.each(self.preloadDirty,function(title) {
var tiddler = self.wiki.getTiddler(title);
iterator(tiddler,title);
});
$tw.utils.each(self.preloadDirty,function(title) {
var tiddler = self.wiki.getTiddler(title);
iterator(tiddler,title);
});
});
this.numChanges = filteredChanges.length;
// Listen out for changes to tiddlers

View File

@@ -15,27 +15,27 @@ var AndTidWiki = function(wiki) {
AndTidWiki.prototype.save = function(text,method,callback,options) {
var filename = options && options.variables ? options.variables.filename : null;
if (method === "download") {
if(method === "download") {
// Support download
if (window.twi.saveDownload) {
if(window.twi.saveDownload) {
try {
window.twi.saveDownload(text,filename);
} catch(err) {
if (err.message === "Method not found") {
if(err.message === "Method not found") {
window.twi.saveDownload(text);
}
}
} else {
var link = document.createElement("a");
link.setAttribute("href","data:text/plain," + encodeURIComponent(text));
if (filename) {
link.setAttribute("download",filename);
if(filename) {
link.setAttribute("download",filename);
}
document.body.appendChild(link);
link.click();
document.body.removeChild(link);
}
} else if (window.twi.saveWiki) {
} else if(window.twi.saveWiki) {
// Direct save in Tiddloid
window.twi.saveWiki(text);
} else {

View File

@@ -22,7 +22,7 @@ var findSaver = function(window) {
console.log({ msg: "custom saver is disabled", reason: err });
return null;
}
}
};
var saver = findSaver(window) || findSaver(window.parent) || {};
var CustomSaver = function(wiki) {

View File

@@ -80,7 +80,7 @@ GiteaSaver.prototype.save = function(text,method,callback) {
callback: function(err,getResponseDataJson,xhr) {
if(xhr.status === 404) {
callback("Please ensure the branch in the Gitea repo exists");
}else{
} else {
data["branch"] = branch;
self.upload(uri + filename, use_put?"PUT":"POST", headers, data, callback);
}
@@ -101,7 +101,6 @@ GiteaSaver.prototype.upload = function(uri,method,headers,data,callback) {
if(err) {
return callback(err);
}
var putResponseData = $tw.utils.parseJSONSafe(putResponseDataJson);
callback(null);
}
});

View File

@@ -17,8 +17,7 @@ var GitHubSaver = function(wiki) {
};
GitHubSaver.prototype.save = function(text,method,callback) {
var self = this,
username = this.wiki.getTiddlerText("$:/GitHub/Username"),
var username = this.wiki.getTiddlerText("$:/GitHub/Username"),
password = $tw.utils.getPassword("github"),
repo = this.wiki.getTiddlerText("$:/GitHub/Repo"),
path = this.wiki.getTiddlerText("$:/GitHub/Path",""),
@@ -81,7 +80,6 @@ GitHubSaver.prototype.save = function(text,method,callback) {
if(err) {
return callback(err);
}
var putResponseData = $tw.utils.parseJSONSafe(putResponseDataJson);
callback(null);
}
});

View File

@@ -18,8 +18,7 @@ var GitLabSaver = function(wiki) {
GitLabSaver.prototype.save = function(text,method,callback) {
/* See https://docs.gitlab.com/ee/api/repository_files.html */
var self = this,
username = this.wiki.getTiddlerText("$:/GitLab/Username"),
var username = this.wiki.getTiddlerText("$:/GitLab/Username"),
password = $tw.utils.getPassword("gitlab"),
repo = this.wiki.getTiddlerText("$:/GitLab/Repo"),
path = this.wiki.getTiddlerText("$:/GitLab/Path",""),
@@ -45,7 +44,7 @@ GitLabSaver.prototype.save = function(text,method,callback) {
var uri = endpoint + "/projects/" + encodeURIComponent(repo) + "/repository/";
// Perform a get request to get the details (inc shas) of files in the same path as our file
$tw.utils.httpRequest({
url: uri + "tree/?path=" + encodeURIComponent(path.replace(/^\/+|\/$/g, '')) + "&branch=" + encodeURIComponent(branch.replace(/^\/+|\/$/g, '')),
url: uri + "tree/?path=" + encodeURIComponent(path.replace(/^\/+|\/$/g, "")) + "&branch=" + encodeURIComponent(branch.replace(/^\/+|\/$/g, "")),
type: "GET",
headers: headers,
callback: function(err,getResponseDataJson,xhr) {
@@ -71,7 +70,7 @@ GitLabSaver.prototype.save = function(text,method,callback) {
};
// Perform a request to save the file
$tw.utils.httpRequest({
url: uri + "files/" + encodeURIComponent(path.replace(/^\/+/, '') + filename),
url: uri + "files/" + encodeURIComponent(path.replace(/^\/+/, "") + filename),
type: requestType,
headers: headers,
data: JSON.stringify(data),
@@ -79,7 +78,6 @@ GitLabSaver.prototype.save = function(text,method,callback) {
if(err) {
return callback(err);
}
var putResponseData = $tw.utils.parseJSONSafe(putResponseDataJson);
callback(null);
}
});

View File

@@ -94,7 +94,7 @@ PutSaver.prototype.save = function(text,method,callback) {
} else if(status === 403) { // permission denied
errorMsg = $tw.language.getString("Error/PutForbidden");
}
if (xhr.responseText) {
if(xhr.responseText) {
// treat any server response like a plain text error explanation
errorMsg = errorMsg + "\n\n" + xhr.responseText;
}

Some files were not shown because too many files have changed in this diff Show More