From eb203ee412604a85f41f667fa37c14403845d700 Mon Sep 17 00:00:00 2001 From: skodak Date: Mon, 16 Jun 2008 16:39:09 +0000 Subject: [PATCH] MDL-14898 upgraded html purifier to 3.1.0 in HEAD --- lib/htmlpurifier/HTMLPurifier.auto.php | 9 - lib/htmlpurifier/HTMLPurifier.func.php | 20 - lib/htmlpurifier/HTMLPurifier.php | 131 +++--- .../HTMLPurifier.safe-includes.php | 183 ++++++++ .../HTMLPurifier/AttrCollections.php | 10 +- lib/htmlpurifier/HTMLPurifier/AttrDef.php | 27 +- lib/htmlpurifier/HTMLPurifier/AttrDef/CSS.php | 5 +- .../HTMLPurifier/AttrDef/CSS/AlphaValue.php | 19 + .../HTMLPurifier/AttrDef/CSS/Background.php | 9 +- .../AttrDef/CSS/BackgroundPosition.php | 12 +- .../HTMLPurifier/AttrDef/CSS/Border.php | 8 +- .../HTMLPurifier/AttrDef/CSS/Color.php | 29 +- .../HTMLPurifier/AttrDef/CSS/Composite.php | 8 +- .../AttrDef/CSS/DenyElementDecorator.php | 8 +- .../HTMLPurifier/AttrDef/CSS/Filter.php | 52 ++ .../HTMLPurifier/AttrDef/CSS/Font.php | 8 +- .../HTMLPurifier/AttrDef/CSS/FontFamily.php | 7 +- .../AttrDef/CSS/ImportantDecorator.php | 38 ++ .../HTMLPurifier/AttrDef/CSS/Length.php | 11 +- .../HTMLPurifier/AttrDef/CSS/ListStyle.php | 8 +- .../HTMLPurifier/AttrDef/CSS/Multiple.php | 12 +- .../HTMLPurifier/AttrDef/CSS/Number.php | 16 +- .../HTMLPurifier/AttrDef/CSS/Percentage.php | 9 +- .../AttrDef/CSS/TextDecoration.php | 4 +- .../HTMLPurifier/AttrDef/CSS/URI.php | 8 +- .../HTMLPurifier/AttrDef/Enum.php | 13 +- .../HTMLPurifier/AttrDef/HTML/Bool.php | 12 +- .../HTMLPurifier/AttrDef/HTML/Color.php | 5 +- .../HTMLPurifier/AttrDef/HTML/FrameTarget.php | 21 +- .../HTMLPurifier/AttrDef/HTML/ID.php | 53 +-- .../HTMLPurifier/AttrDef/HTML/Length.php | 5 +- .../HTMLPurifier/AttrDef/HTML/LinkTypes.php | 23 +- .../HTMLPurifier/AttrDef/HTML/MultiLength.php | 5 +- .../HTMLPurifier/AttrDef/HTML/Nmtokens.php | 5 +- .../HTMLPurifier/AttrDef/HTML/Pixels.php | 4 +- .../HTMLPurifier/AttrDef/Integer.php | 12 +- .../HTMLPurifier/AttrDef/Lang.php | 4 +- .../HTMLPurifier/AttrDef/Text.php | 4 +- lib/htmlpurifier/HTMLPurifier/AttrDef/URI.php | 71 +-- .../HTMLPurifier/AttrDef/URI/Email.php | 5 +- .../AttrDef/URI/Email/SimpleCheck.php | 20 + .../HTMLPurifier/AttrDef/URI/Host.php | 12 +- .../HTMLPurifier/AttrDef/URI/IPv4.php | 9 +- .../HTMLPurifier/AttrDef/URI/IPv6.php | 4 +- .../HTMLPurifier/AttrTransform.php | 10 +- .../HTMLPurifier/AttrTransform/BdoDir.php | 14 +- .../HTMLPurifier/AttrTransform/BgColor.php | 7 +- .../HTMLPurifier/AttrTransform/BoolToCSS.php | 13 +- .../HTMLPurifier/AttrTransform/Border.php | 4 +- .../HTMLPurifier/AttrTransform/EnumToCSS.php | 12 +- .../AttrTransform/ImgRequired.php | 19 +- .../HTMLPurifier/AttrTransform/ImgSpace.php | 13 +- .../HTMLPurifier/AttrTransform/Lang.php | 4 +- .../HTMLPurifier/AttrTransform/Length.php | 10 +- .../HTMLPurifier/AttrTransform/Name.php | 4 +- .../AttrTransform/ScriptRequired.php | 14 + lib/htmlpurifier/HTMLPurifier/AttrTypes.php | 22 +- .../HTMLPurifier/AttrValidator.php | 7 +- lib/htmlpurifier/HTMLPurifier/Bootstrap.php | 96 ++++ .../HTMLPurifier/CSSDefinition.php | 106 +++-- lib/htmlpurifier/HTMLPurifier/ChildDef.php | 30 +- .../HTMLPurifier/ChildDef/Chameleon.php | 14 +- .../HTMLPurifier/ChildDef/Custom.php | 20 +- .../HTMLPurifier/ChildDef/Empty.php | 10 +- .../HTMLPurifier/ChildDef/Optional.php | 8 +- .../HTMLPurifier/ChildDef/Required.php | 22 +- .../ChildDef/StrictBlockquote.php | 27 +- .../HTMLPurifier/ChildDef/Table.php | 18 +- lib/htmlpurifier/HTMLPurifier/Config.php | 196 ++++---- lib/htmlpurifier/HTMLPurifier/ConfigDef.php | 4 +- .../HTMLPurifier/ConfigDef/Directive.php | 44 +- .../HTMLPurifier/ConfigDef/DirectiveAlias.php | 10 +- .../HTMLPurifier/ConfigDef/Namespace.php | 18 +- .../HTMLPurifier/ConfigSchema.php | 443 ++++-------------- .../ConfigSchema/Builder/ConfigSchema.php | 49 ++ .../HTMLPurifier/ConfigSchema/Builder/Xml.php | 106 +++++ .../HTMLPurifier/ConfigSchema/Exception.php | 9 + .../HTMLPurifier/ConfigSchema/Interchange.php | 55 +++ .../ConfigSchema/Interchange/Directive.php | 75 +++ .../ConfigSchema/Interchange/Id.php | 29 ++ .../ConfigSchema/Interchange/Namespace.php | 19 + .../ConfigSchema/InterchangeBuilder.php | 175 +++++++ .../HTMLPurifier/ConfigSchema/Validator.php | 222 +++++++++ .../ConfigSchema/ValidatorAtom.php | 66 +++ .../HTMLPurifier/ConfigSchema/schema.ser | 1 + .../schema/Attr.AllowedFrameTargets.txt | 11 + .../ConfigSchema/schema/Attr.AllowedRel.txt | 8 + .../ConfigSchema/schema/Attr.AllowedRev.txt | 8 + .../schema/Attr.DefaultInvalidImage.txt | 8 + .../schema/Attr.DefaultInvalidImageAlt.txt | 7 + .../schema/Attr.DefaultTextDir.txt | 9 + .../ConfigSchema/schema/Attr.EnableID.txt | 15 + .../ConfigSchema/schema/Attr.IDBlacklist.txt | 4 + .../schema/Attr.IDBlacklistRegexp.txt | 8 + .../ConfigSchema/schema/Attr.IDPrefix.txt | 11 + .../schema/Attr.IDPrefixLocal.txt | 13 + .../HTMLPurifier/ConfigSchema/schema/Attr.txt | 2 + .../schema/AutoFormat.AutoParagraph.txt | 30 ++ .../ConfigSchema/schema/AutoFormat.Custom.txt | 12 + .../schema/AutoFormat.Linkify.txt | 12 + .../schema/AutoFormat.PurifierLinkify.txt | 12 + .../ConfigSchema/schema/AutoFormat.txt | 2 + .../AutoFormatParam.PurifierLinkifyDocURL.txt | 12 + .../ConfigSchema/schema/AutoFormatParam.txt | 2 + .../schema/CSS.AllowImportant.txt | 7 + .../ConfigSchema/schema/CSS.AllowTricky.txt | 10 + .../schema/CSS.AllowedProperties.txt | 17 + .../ConfigSchema/schema/CSS.DefinitionRev.txt | 11 + .../ConfigSchema/schema/CSS.Proprietary.txt | 10 + .../HTMLPurifier/ConfigSchema/schema/CSS.txt | 2 + .../schema/Cache.DefinitionImpl.txt | 13 + .../schema/Cache.SerializerPath.txt | 13 + .../ConfigSchema/schema/Cache.txt | 2 + .../schema/Core.AggressivelyFixLt.txt | 13 + .../schema/Core.CollectErrors.txt | 11 + .../schema/Core.ColorKeywords.txt | 29 ++ .../schema/Core.ConvertDocumentToFragment.txt | 13 + .../Core.DirectLexLineNumberSyncInterval.txt | 17 + .../ConfigSchema/schema/Core.Encoding.txt | 14 + .../schema/Core.EscapeInvalidChildren.txt | 9 + .../schema/Core.EscapeInvalidTags.txt | 6 + .../schema/Core.EscapeNonASCIICharacters.txt | 12 + .../schema/Core.HiddenElements.txt | 19 + .../ConfigSchema/schema/Core.Language.txt | 11 + .../ConfigSchema/schema/Core.LexerImpl.txt | 33 ++ .../schema/Core.MaintainLineNumbers.txt | 16 + .../schema/Core.RemoveInvalidImg.txt | 12 + .../schema/Core.RemoveScriptContents.txt | 11 + .../HTMLPurifier/ConfigSchema/schema/Core.txt | 2 + .../ConfigSchema/schema/Filter.Custom.txt | 10 + .../schema/Filter.ExtractStyleBlocks.txt | 37 ++ .../ConfigSchema/schema/Filter.YouTube.txt | 10 + .../ConfigSchema/schema/Filter.txt | 2 + ...FilterParam.ExtractStyleBlocksEscaping.txt | 14 + .../FilterParam.ExtractStyleBlocksScope.txt | 28 ++ ...FilterParam.ExtractStyleBlocksTidyImpl.txt | 14 + .../ConfigSchema/schema/FilterParam.txt | 2 + .../ConfigSchema/schema/HTML.Allowed.txt | 22 + .../schema/HTML.AllowedAttributes.txt | 19 + .../schema/HTML.AllowedElements.txt | 18 + .../schema/HTML.AllowedModules.txt | 20 + .../ConfigSchema/schema/HTML.BlockWrapper.txt | 18 + .../ConfigSchema/schema/HTML.CoreModules.txt | 23 + .../schema/HTML.CustomDoctype.txt | 10 + .../ConfigSchema/schema/HTML.DefinitionID.txt | 33 ++ .../schema/HTML.DefinitionRev.txt | 16 + .../ConfigSchema/schema/HTML.Doctype.txt | 10 + .../schema/HTML.ForbiddenAttributes.txt | 20 + .../schema/HTML.ForbiddenElements.txt | 19 + .../ConfigSchema/schema/HTML.Parent.txt | 12 + .../ConfigSchema/schema/HTML.Proprietary.txt | 11 + .../ConfigSchema/schema/HTML.Strict.txt | 8 + .../ConfigSchema/schema/HTML.TidyAdd.txt | 8 + .../ConfigSchema/schema/HTML.TidyLevel.txt | 23 + .../ConfigSchema/schema/HTML.TidyRemove.txt | 8 + .../ConfigSchema/schema/HTML.Trusted.txt | 7 + .../ConfigSchema/schema/HTML.XHTML.txt | 10 + .../HTMLPurifier/ConfigSchema/schema/HTML.txt | 2 + .../schema/Output.CommentScriptContents.txt | 9 + .../ConfigSchema/schema/Output.Newline.txt | 13 + .../ConfigSchema/schema/Output.TidyFormat.txt | 24 + .../ConfigSchema/schema/Output.txt | 2 + .../ConfigSchema/schema/Test.ForceNoIconv.txt | 6 + .../HTMLPurifier/ConfigSchema/schema/Test.txt | 2 + .../schema/URI.AllowedSchemes.txt | 14 + .../ConfigSchema/schema/URI.Base.txt | 17 + .../ConfigSchema/schema/URI.DefaultScheme.txt | 10 + .../ConfigSchema/schema/URI.DefinitionID.txt | 11 + .../ConfigSchema/schema/URI.DefinitionRev.txt | 11 + .../ConfigSchema/schema/URI.Disable.txt | 13 + .../schema/URI.DisableExternal.txt | 10 + .../schema/URI.DisableExternalResources.txt | 12 + .../schema/URI.DisableResources.txt | 12 + .../ConfigSchema/schema/URI.Host.txt | 19 + .../ConfigSchema/schema/URI.HostBlacklist.txt | 8 + .../ConfigSchema/schema/URI.MakeAbsolute.txt | 12 + .../ConfigSchema/schema/URI.Munge.txt | 31 ++ .../schema/URI.OverrideAllowedSchemes.txt | 8 + .../HTMLPurifier/ConfigSchema/schema/URI.txt | 2 + .../HTMLPurifier/ConfigSchema/schema/info.ini | 1 + lib/htmlpurifier/HTMLPurifier/ContentSets.php | 30 +- lib/htmlpurifier/HTMLPurifier/Context.php | 17 +- lib/htmlpurifier/HTMLPurifier/Definition.php | 12 +- .../HTMLPurifier/DefinitionCache.php | 60 +-- .../DefinitionCache/Decorator.php | 26 +- .../DefinitionCache/Decorator/Cleanup.php | 14 +- .../DefinitionCache/Decorator/Memory.php | 16 +- .../HTMLPurifier/DefinitionCache/Null.php | 18 +- .../DefinitionCache/Serializer.php | 57 +-- .../HTMLPurifier/DefinitionCacheFactory.php | 39 +- lib/htmlpurifier/HTMLPurifier/Doctype.php | 23 +- .../HTMLPurifier/DoctypeRegistry.php | 42 +- lib/htmlpurifier/HTMLPurifier/ElementDef.php | 52 +- lib/htmlpurifier/HTMLPurifier/Encoder.php | 87 +--- .../HTMLPurifier/EntityLookup.php | 8 +- .../HTMLPurifier/EntityParser.php | 29 +- lib/htmlpurifier/HTMLPurifier/Error.php | 7 - .../HTMLPurifier/ErrorCollector.php | 22 +- lib/htmlpurifier/HTMLPurifier/Exception.php | 11 + lib/htmlpurifier/HTMLPurifier/Filter.php | 13 +- .../Filter/ExtractStyleBlocks.php | 134 ++++++ .../HTMLPurifier/Filter/YouTube.php | 8 +- lib/htmlpurifier/HTMLPurifier/Generator.php | 182 +++---- .../HTMLPurifier/HTMLDefinition.php | 316 +++++-------- lib/htmlpurifier/HTMLPurifier/HTMLModule.php | 65 +-- .../HTMLPurifier/HTMLModule/Bdo.php | 13 +- .../HTMLModule/CommonAttributes.php | 6 +- .../HTMLPurifier/HTMLModule/Edit.php | 15 +- .../HTMLPurifier/HTMLModule/Hypertext.php | 11 +- .../HTMLPurifier/HTMLModule/Image.php | 13 +- .../HTMLPurifier/HTMLModule/Legacy.php | 60 ++- .../HTMLPurifier/HTMLModule/List.php | 20 +- .../HTMLModule/NonXMLCommonAttributes.php | 6 +- .../HTMLPurifier/HTMLModule/Object.php | 11 +- .../HTMLPurifier/HTMLModule/Presentation.php | 22 +- .../HTMLPurifier/HTMLModule/Proprietary.php | 32 ++ .../HTMLPurifier/HTMLModule/Ruby.php | 18 +- .../HTMLPurifier/HTMLModule/Scripting.php | 32 +- .../HTMLModule/StyleAttribute.php | 9 +- .../HTMLPurifier/HTMLModule/Tables.php | 27 +- .../HTMLPurifier/HTMLModule/Target.php | 8 +- .../HTMLPurifier/HTMLModule/Text.php | 64 ++- .../HTMLPurifier/HTMLModule/Tidy.php | 68 +-- .../HTMLModule/Tidy/Proprietary.php | 11 +- .../HTMLPurifier/HTMLModule/Tidy/Strict.php | 19 + .../HTMLModule/Tidy/Transitional.php | 8 + .../HTMLPurifier/HTMLModule/Tidy/XHTML.php | 12 +- .../HTMLModule/Tidy/XHTMLAndHTML4.php | 46 +- .../HTMLModule/Tidy/XHTMLStrict.php | 26 - .../HTMLModule/XMLCommonAttributes.php | 6 +- .../HTMLPurifier/HTMLModuleManager.php | 232 +++------ .../HTMLPurifier/IDAccumulator.php | 20 +- lib/htmlpurifier/HTMLPurifier/Injector.php | 26 +- .../HTMLPurifier/Injector/AutoParagraph.php | 71 +-- .../HTMLPurifier/Injector/Linkify.php | 17 +- .../HTMLPurifier/Injector/PurifierLinkify.php | 31 +- lib/htmlpurifier/HTMLPurifier/Language.php | 40 +- .../HTMLPurifier/LanguageFactory.php | 38 +- lib/htmlpurifier/HTMLPurifier/Lexer.php | 153 ++---- .../HTMLPurifier/Lexer/DOMLex.php | 20 +- .../HTMLPurifier/Lexer/DirectLex.php | 59 +-- .../HTMLPurifier/Lexer/PEARSax3.php | 18 +- lib/htmlpurifier/HTMLPurifier/Lexer/PH5P.php | 44 +- .../HTMLPurifier/PercentEncoder.php | 8 +- lib/htmlpurifier/HTMLPurifier/Printer.php | 38 +- .../HTMLPurifier/Printer/CSSDefinition.php | 6 +- .../HTMLPurifier/Printer/ConfigForm.php | 59 ++- .../HTMLPurifier/Printer/HTMLDefinition.php | 26 +- lib/htmlpurifier/HTMLPurifier/Strategy.php | 11 +- .../HTMLPurifier/Strategy/Composite.php | 13 +- .../HTMLPurifier/Strategy/Core.php | 9 +- .../HTMLPurifier/Strategy/FixNesting.php | 13 +- .../HTMLPurifier/Strategy/MakeWellFormed.php | 91 ++-- .../Strategy/RemoveForeignElements.php | 62 +-- .../Strategy/ValidateAttributes.php | 10 +- lib/htmlpurifier/HTMLPurifier/StringHash.php | 37 ++ .../HTMLPurifier/StringHashParser.php | 104 ++++ .../HTMLPurifier/TagTransform.php | 13 +- .../HTMLPurifier/TagTransform/Font.php | 14 +- .../HTMLPurifier/TagTransform/Simple.php | 12 +- lib/htmlpurifier/HTMLPurifier/Token.php | 163 +------ .../HTMLPurifier/Token/Comment.php | 19 + lib/htmlpurifier/HTMLPurifier/Token/Empty.php | 9 + lib/htmlpurifier/HTMLPurifier/Token/End.php | 13 + lib/htmlpurifier/HTMLPurifier/Token/Start.php | 9 + lib/htmlpurifier/HTMLPurifier/Token/Tag.php | 53 +++ lib/htmlpurifier/HTMLPurifier/Token/Text.php | 30 ++ .../HTMLPurifier/TokenFactory.php | 20 +- lib/htmlpurifier/HTMLPurifier/URI.php | 22 +- .../HTMLPurifier/URIDefinition.php | 97 +--- lib/htmlpurifier/HTMLPurifier/URIFilter.php | 14 +- .../URIFilter/DisableExternal.php | 20 +- .../URIFilter/DisableExternalResources.php | 19 +- .../HTMLPurifier/URIFilter/HostBlacklist.php | 18 +- .../HTMLPurifier/URIFilter/MakeAbsolute.php | 28 +- lib/htmlpurifier/HTMLPurifier/URIParser.php | 8 +- lib/htmlpurifier/HTMLPurifier/URIScheme.php | 10 +- .../HTMLPurifier/URIScheme/ftp.php | 10 +- .../HTMLPurifier/URIScheme/http.php | 10 +- .../HTMLPurifier/URIScheme/https.php | 4 +- .../HTMLPurifier/URIScheme/mailto.php | 6 +- .../HTMLPurifier/URIScheme/news.php | 6 +- .../HTMLPurifier/URIScheme/nntp.php | 8 +- .../HTMLPurifier/URISchemeRegistry.php | 42 +- lib/htmlpurifier/HTMLPurifier/VarParser.php | 125 +++++ .../HTMLPurifier/VarParser/Flexible.php | 94 ++++ .../HTMLPurifier/VarParser/Native.php | 25 + .../HTMLPurifier/VarParserException.php | 9 + lib/htmlpurifier/readme_moodle.txt | 5 +- lib/weblib.php | 7 +- 290 files changed, 4770 insertions(+), 3422 deletions(-) delete mode 100644 lib/htmlpurifier/HTMLPurifier.auto.php delete mode 100644 lib/htmlpurifier/HTMLPurifier.func.php create mode 100644 lib/htmlpurifier/HTMLPurifier.safe-includes.php create mode 100644 lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/AlphaValue.php create mode 100644 lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Filter.php create mode 100644 lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php create mode 100644 lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Email/SimpleCheck.php create mode 100644 lib/htmlpurifier/HTMLPurifier/AttrTransform/ScriptRequired.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Bootstrap.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/Xml.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Exception.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Directive.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Id.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Namespace.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/InterchangeBuilder.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/Validator.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/ValidatorAtom.php create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema.ser create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.PurifierLinkifyDocURL.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Language.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksEscaping.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksScope.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksTidyImpl.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Base.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Host.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.txt create mode 100644 lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/info.ini delete mode 100644 lib/htmlpurifier/HTMLPurifier/Error.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Exception.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Filter/ExtractStyleBlocks.php create mode 100644 lib/htmlpurifier/HTMLPurifier/HTMLModule/Proprietary.php create mode 100644 lib/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/Strict.php create mode 100644 lib/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/Transitional.php delete mode 100644 lib/htmlpurifier/HTMLPurifier/HTMLModule/Tidy/XHTMLStrict.php create mode 100644 lib/htmlpurifier/HTMLPurifier/StringHash.php create mode 100644 lib/htmlpurifier/HTMLPurifier/StringHashParser.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Token/Comment.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Token/Empty.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Token/End.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Token/Start.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Token/Tag.php create mode 100644 lib/htmlpurifier/HTMLPurifier/Token/Text.php create mode 100644 lib/htmlpurifier/HTMLPurifier/VarParser.php create mode 100644 lib/htmlpurifier/HTMLPurifier/VarParser/Flexible.php create mode 100644 lib/htmlpurifier/HTMLPurifier/VarParser/Native.php create mode 100644 lib/htmlpurifier/HTMLPurifier/VarParserException.php diff --git a/lib/htmlpurifier/HTMLPurifier.auto.php b/lib/htmlpurifier/HTMLPurifier.auto.php deleted file mode 100644 index cb6a84265d..0000000000 --- a/lib/htmlpurifier/HTMLPurifier.auto.php +++ /dev/null @@ -1,9 +0,0 @@ -purify($html, $config); -} - diff --git a/lib/htmlpurifier/HTMLPurifier.php b/lib/htmlpurifier/HTMLPurifier.php index a7bba317e5..03709f1268 100644 --- a/lib/htmlpurifier/HTMLPurifier.php +++ b/lib/htmlpurifier/HTMLPurifier.php @@ -1,7 +1,6 @@ Warning: -Currently this feature is very patchy and experimental, with lots of -possible error messages not yet implemented. It will not cause any problems, -but it may not help your users either. This directive has been available -since 2.0.0. -'); - /** * Facade that coordinates HTML Purifier's subsystems in order to purify HTML. * @@ -75,27 +46,36 @@ since 2.0.0. * -# Instance: new HTMLPurifier($config) * -# Invocation: purify($html, $config) * These configurations are entirely independent of each other and - * are *not* merged. + * are *not* merged (this behavior may change in the future). * - * @todo We need an easier way to inject strategies, it'll probably end - * up getting done through config though. + * @todo We need an easier way to inject strategies using the configuration + * object. */ class HTMLPurifier { - var $version = '2.1.4'; + /** Version of HTML Purifier */ + public $version = '3.1.0'; + + /** Constant with version of HTML Purifier */ + const VERSION = '3.1.0'; + + /** Global configuration object */ + public $config; - var $config; - var $filters = array(); + /** Array of extra HTMLPurifier_Filter objects to run on HTML, for backwards compatibility */ + private $filters = array(); - var $strategy, $generator; + /** Single instance of HTML Purifier */ + private static $instance; + + protected $strategy, $generator; /** * Resultant HTMLPurifier_Context of last run purification. Is an array * of contexts if the last called method was purifyArray(). - * @public */ - var $context; + public $context; /** * Initializes the purifier. @@ -105,12 +85,11 @@ class HTMLPurifier * The parameter can also be any type that * HTMLPurifier_Config::create() supports. */ - function HTMLPurifier($config = null) { + public function __construct($config = null) { $this->config = HTMLPurifier_Config::create($config); $this->strategy = new HTMLPurifier_Strategy_Core(); - $this->generator = new HTMLPurifier_Generator(); } @@ -118,7 +97,8 @@ class HTMLPurifier * Adds a filter to process the output. First come first serve * @param $filter HTMLPurifier_Filter object */ - function addFilter($filter) { + public function addFilter($filter) { + trigger_error('HTMLPurifier->addFilter() is deprecated, use configuration directives in the Filter namespace or Filter.Custom', E_USER_WARNING); $this->filters[] = $filter; } @@ -132,8 +112,9 @@ class HTMLPurifier * that HTMLPurifier_Config::create() supports. * @return Purified HTML */ - function purify($html, $config = null) { + public function purify($html, $config = null) { + // :TODO: make the config merge in, instead of replace $config = $config ? HTMLPurifier_Config::create($config) : $this->config; // implementation is partially environment dependant, partially @@ -142,8 +123,8 @@ class HTMLPurifier $context = new HTMLPurifier_Context(); - // our friendly neighborhood generator, all primed with configuration too! - $this->generator->generateFromTokens(array(), $config, $context); + // setup HTML generator + $this->generator = new HTMLPurifier_Generator($config, $context); $context->register('Generator', $this->generator); // set up global context variables @@ -164,8 +145,25 @@ class HTMLPurifier $html = HTMLPurifier_Encoder::convertToUTF8($html, $config, $context); - for ($i = 0, $size = count($this->filters); $i < $size; $i++) { - $html = $this->filters[$i]->preFilter($html, $config, $context); + // setup filters + $filter_flags = $config->getBatch('Filter'); + $custom_filters = $filter_flags['Custom']; + unset($filter_flags['Custom']); + $filters = array(); + foreach ($filter_flags as $filter => $flag) { + if (!$flag) continue; + $class = "HTMLPurifier_Filter_$filter"; + $filters[] = new $class; + } + foreach ($custom_filters as $filter) { + // maybe "HTMLPurifier_Filter_$filter", but be consistent with AutoFormat + $filters[] = $filter; + } + $filters = array_merge($filters, $this->filters); + // maybe prepare(), but later + + for ($i = 0, $filter_size = count($filters); $i < $filter_size; $i++) { + $html = $filters[$i]->preFilter($html, $config, $context); } // purified HTML @@ -179,12 +177,11 @@ class HTMLPurifier $html, $config, $context ), $config, $context - ), - $config, $context + ) ); - for ($i = $size - 1; $i >= 0; $i--) { - $html = $this->filters[$i]->postFilter($html, $config, $context); + for ($i = $filter_size - 1; $i >= 0; $i--) { + $html = $filters[$i]->postFilter($html, $config, $context); } $html = HTMLPurifier_Encoder::convertFromUTF8($html, $config, $context); @@ -198,7 +195,7 @@ class HTMLPurifier * See HTMLPurifier::purify() for more details. * @return Array of purified HTML */ - function purifyArray($array_of_html, $config = null) { + public function purifyArray($array_of_html, $config = null) { $context_array = array(); foreach ($array_of_html as $key => $html) { $array_of_html[$key] = $this->purify($html, $config); @@ -211,25 +208,27 @@ class HTMLPurifier /** * Singleton for enforcing just one HTML Purifier in your system * @param $prototype Optional prototype HTMLPurifier instance to - * overload singleton with. + * overload singleton with, or HTMLPurifier_Config + * instance to configure the generated version with. */ - function &instance($prototype = null) { - static $htmlpurifier; - if (!$htmlpurifier || $prototype) { - if (is_a($prototype, 'HTMLPurifier')) { - $htmlpurifier = $prototype; + public static function instance($prototype = null) { + if (!self::$instance || $prototype) { + if ($prototype instanceof HTMLPurifier) { + self::$instance = $prototype; } elseif ($prototype) { - $htmlpurifier = new HTMLPurifier($prototype); + self::$instance = new HTMLPurifier($prototype); } else { - $htmlpurifier = new HTMLPurifier(); + self::$instance = new HTMLPurifier(); } } - return $htmlpurifier; + return self::$instance; } - function &getInstance($prototype = null) { + /** + * @note Backwards compatibility, see instance() + */ + public static function getInstance($prototype = null) { return HTMLPurifier::instance($prototype); } } - diff --git a/lib/htmlpurifier/HTMLPurifier.safe-includes.php b/lib/htmlpurifier/HTMLPurifier.safe-includes.php new file mode 100644 index 0000000000..4273da369e --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier.safe-includes.php @@ -0,0 +1,183 @@ +attr_collections as $coll_i => $coll) { @@ -53,7 +51,7 @@ class HTMLPurifier_AttrCollections * all inclusions specified by the zero index. * @param &$attr Reference to attribute array */ - function performInclusions(&$attr) { + public function performInclusions(&$attr) { if (!isset($attr[0])) return; $merge = $attr[0]; $seen = array(); // recursion guard @@ -81,7 +79,7 @@ class HTMLPurifier_AttrCollections * @param &$attr Reference to attribute array * @param $attr_types HTMLPurifier_AttrTypes instance */ - function expandIdentifiers(&$attr, $attr_types) { + public function expandIdentifiers(&$attr, $attr_types) { // because foreach will process new elements we add, make sure we // skip duplicates diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef.php b/lib/htmlpurifier/HTMLPurifier/AttrDef.php index e94ee713d2..2c59a8d73a 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef.php @@ -10,32 +10,29 @@ * subclasses are also responsible for cleaning the code if possible. */ -class HTMLPurifier_AttrDef +abstract class HTMLPurifier_AttrDef { /** * Tells us whether or not an HTML attribute is minimized. Has no * meaning in other contexts. */ - var $minimized = false; + public $minimized = false; /** * Tells us whether or not an HTML attribute is required. Has no * meaning in other contexts */ - var $required = false; + public $required = false; /** * Validates and cleans passed string according to a definition. * - * @public * @param $string String to be validated and cleaned. * @param $config Mandatory HTMLPurifier_Config object. * @param $context Mandatory HTMLPurifier_AttrContext object. */ - function validate($string, $config, &$context) { - trigger_error('Cannot call abstract function', E_USER_ERROR); - } + abstract public function validate($string, $config, $context); /** * Convenience method that parses a string as if it were CDATA. @@ -59,10 +56,8 @@ class HTMLPurifier_AttrDef * function. Trim and whitespace collapsing are supposed to only * occur in NMTOKENs. However, note that we are NOT necessarily * parsing XML, thus, this behavior may still be correct. - * - * @public */ - function parseCDATA($string) { + public function parseCDATA($string) { $string = trim($string); $string = str_replace("\n", '', $string); $string = str_replace(array("\r", "\t"), ' ', $string); @@ -73,12 +68,12 @@ class HTMLPurifier_AttrDef * Factory method for creating this class from a string. * @param $string String construction info * @return Created AttrDef object corresponding to $string - * @public */ - function make($string) { - // default implementation, return flyweight of this object - // if overloaded, it is *necessary* for you to clone the - // object (usually by instantiating a new copy) and return that + public function make($string) { + // default implementation, return a flyweight of this object. + // If $string has an effect on the returned object (i.e. you + // need to overload this method), it is best + // to clone or instantiate new copies. (Instantiation is safer.) return $this; } @@ -86,7 +81,7 @@ class HTMLPurifier_AttrDef * Removes spaces from rgb(0, 0, 0) so that shorthand CSS properties work * properly. THIS IS A HACK! */ - function mungeRgb($string) { + protected function mungeRgb($string) { return preg_replace('/rgb\((\d+)\s*,\s*(\d+)\s*,\s*(\d+)\)/', 'rgb(\1,\2,\3)', $string); } diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS.php index 71523be1f1..128158e19c 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS.php @@ -1,8 +1,5 @@ parseCDATA($css); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/AlphaValue.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/AlphaValue.php new file mode 100644 index 0000000000..701e7e4413 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/AlphaValue.php @@ -0,0 +1,19 @@ + 1.0) $result = '1'; + return $result; + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Background.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Background.php index a5c1046a82..76afa44041 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Background.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Background.php @@ -1,8 +1,5 @@ getCSSDefinition(); $this->info['background-color'] = $def->info['background-color']; $this->info['background-image'] = $def->info['background-image']; @@ -25,7 +22,7 @@ class HTMLPurifier_AttrDef_CSS_Background extends HTMLPurifier_AttrDef $this->info['background-position'] = $def->info['background-position']; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { // regular pre-processing $string = $this->parseCDATA($string); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php index 0d10ab681d..7e424e12f4 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/BackgroundPosition.php @@ -1,9 +1,5 @@ length = new HTMLPurifier_AttrDef_CSS_Length(); $this->percentage = new HTMLPurifier_AttrDef_CSS_Percentage(); } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $string = $this->parseCDATA($string); $bits = explode(' ', $string); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Border.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Border.php index 4eb3e25abd..ec0249ef3e 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Border.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Border.php @@ -1,7 +1,5 @@ getCSSDefinition(); $this->info['border-width'] = $def->info['border-width']; $this->info['border-style'] = $def->info['border-style']; $this->info['border-top-color'] = $def->info['border-top-color']; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $string = $this->parseCDATA($string); $string = $this->mungeRgb($string); $bits = explode(' ', $string); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Color.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Color.php index a6711f7175..e47eac6982 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Color.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Color.php @@ -1,39 +1,12 @@ '#800000', - 'red' => '#FF0000', - 'orange' => '#FFA500', - 'yellow' => '#FFFF00', - 'olive' => '#808000', - 'purple' => '#800080', - 'fuchsia' => '#FF00FF', - 'white' => '#FFFFFF', - 'lime' => '#00FF00', - 'green' => '#008000', - 'navy' => '#000080', - 'blue' => '#0000FF', - 'aqua' => '#00FFFF', - 'teal' => '#008080', - 'black' => '#000000', - 'silver' => '#C0C0C0', - 'gray' => '#808080' - ), 'hash', ' -Lookup array of color names to six digit hexadecimal number corresponding -to color, with preceding hash mark. Used when parsing colors. -This directive has been available since 2.0.0. -'); - /** * Validates Color as defined by CSS. */ class HTMLPurifier_AttrDef_CSS_Color extends HTMLPurifier_AttrDef { - function validate($color, $config, &$context) { + public function validate($color, $config, $context) { static $colors = null; if ($colors === null) $colors = $config->get('Core', 'ColorKeywords'); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Composite.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Composite.php index 44ad542153..c96506995c 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Composite.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Composite.php @@ -14,18 +14,18 @@ class HTMLPurifier_AttrDef_CSS_Composite extends HTMLPurifier_AttrDef /** * List of HTMLPurifier_AttrDef objects that may process strings - * @protected + * @todo Make protected */ - var $defs; + public $defs; /** * @param $defs List of HTMLPurifier_AttrDef objects */ - function HTMLPurifier_AttrDef_CSS_Composite($defs) { + public function __construct($defs) { $this->defs = $defs; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { foreach ($this->defs as $i => $def) { $result = $this->defs[$i]->validate($string, $config, $context); if ($result !== false) return $result; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php index b0a6db9dee..756dec3ce8 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/DenyElementDecorator.php @@ -5,20 +5,20 @@ */ class HTMLPurifier_AttrDef_CSS_DenyElementDecorator extends HTMLPurifier_AttrDef { - var $def, $element; + protected $def, $element; /** * @param $def Definition to wrap * @param $element Element to deny */ - function HTMLPurifier_AttrDef_CSS_DenyElementDecorator(&$def, $element) { - $this->def =& $def; + public function __construct($def, $element) { + $this->def = $def; $this->element = $element; } /** * Checks if CurrentToken is set and equal to $this->element */ - function validate($string, $config, $context) { + public function validate($string, $config, $context) { $token = $context->get('CurrentToken', true); if ($token && $token->name == $this->element) return false; return $this->def->validate($string, $config, $context); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Filter.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Filter.php new file mode 100644 index 0000000000..3fe5e589f6 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Filter.php @@ -0,0 +1,52 @@ +intValidator = new HTMLPurifier_AttrDef_Integer(); + } + + public function validate($value, $config, $context) { + $value = $this->parseCDATA($value); + if ($value === 'none') return $value; + // if we looped this we could support multiple filters + $function_length = strcspn($value, '('); + $function = trim(substr($value, 0, $function_length)); + if ($function !== 'alpha' && + $function !== 'Alpha' && + $function !== 'progid:DXImageTransform.Microsoft.Alpha' + ) return false; + $cursor = $function_length + 1; + $parameters_length = strcspn($value, ')', $cursor); + $parameters = substr($value, $cursor, $parameters_length); + $params = explode(',', $parameters); + $ret_params = array(); + $lookup = array(); + foreach ($params as $param) { + list($key, $value) = explode('=', $param); + $key = trim($key); + $value = trim($value); + if (isset($lookup[$key])) continue; + if ($key !== 'opacity') continue; + $value = $this->intValidator->validate($value, $config, $context); + if ($value === false) continue; + $int = (int) $value; + if ($int > 100) $value = '100'; + if ($int < 0) $value = '0'; + $ret_params[] = "$key=$value"; + $lookup[$key] = true; + } + $ret_parameters = implode(',', $ret_params); + $ret_function = "$function($ret_parameters)"; + return $ret_function; + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Font.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Font.php index 6ce18efb80..a4a74b4381 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Font.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Font.php @@ -1,7 +1,5 @@ getCSSDefinition(); $this->info['font-style'] = $def->info['font-style']; $this->info['font-variant'] = $def->info['font-variant']; @@ -28,7 +26,7 @@ class HTMLPurifier_AttrDef_CSS_Font extends HTMLPurifier_AttrDef $this->info['font-family'] = $def->info['font-family']; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { static $system_fonts = array( 'caption' => true, diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/FontFamily.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/FontFamily.php index dfd89b9584..51f83ac5bf 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/FontFamily.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/FontFamily.php @@ -1,16 +1,13 @@ true, 'sans-serif' => true, diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php new file mode 100644 index 0000000000..97b414c770 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ImportantDecorator.php @@ -0,0 +1,38 @@ +def = $def; + $this->allow = $allow; + } + /** + * Intercepts and removes !important if necessary + */ + public function validate($string, $config, $context) { + // test for ! and important tokens + $string = trim($string); + $is_important = false; + // :TODO: optimization: test directly for !important and ! important + if (strlen($string) >= 9 && substr($string, -9) === 'important') { + $temp = rtrim(substr($string, 0, -9)); + // use a temp, because we might want to restore important + if (strlen($temp) >= 1 && substr($temp, -1) === '!') { + $string = rtrim(substr($temp, 0, -1)); + $is_important = true; + } + } + $string = $this->def->validate($string, $config, $context); + if ($this->allow && $is_important) $string .= ' !important'; + return $string; + } +} diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Length.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Length.php index 095eaade3f..2684f8ccf4 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Length.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Length.php @@ -1,8 +1,5 @@ true, 'ex' => true, 'px' => true, 'in' => true, + protected $units = array('em' => true, 'ex' => true, 'px' => true, 'in' => true, 'cm' => true, 'mm' => true, 'pt' => true, 'pc' => true); /** * Instance of HTMLPurifier_AttrDef_Number to defer number validation to */ - var $number_def; + protected $number_def; /** * @param $non_negative Bool indication whether or not negative values are * allowed. */ - function HTMLPurifier_AttrDef_CSS_Length($non_negative = false) { + public function __construct($non_negative = false) { $this->number_def = new HTMLPurifier_AttrDef_CSS_Number($non_negative); } - function validate($length, $config, &$context) { + public function validate($length, $config, $context) { $length = $this->parseCDATA($length); if ($length === '') return false; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ListStyle.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ListStyle.php index a89d679274..836cb465ab 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ListStyle.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/ListStyle.php @@ -1,7 +1,5 @@ getCSSDefinition(); $this->info['list-style-type'] = $def->info['list-style-type']; $this->info['list-style-position'] = $def->info['list-style-position']; $this->info['list-style-image'] = $def->info['list-style-image']; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { // regular pre-processing $string = $this->parseCDATA($string); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Multiple.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Multiple.php index 9a818d108a..878940dbbf 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Multiple.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Multiple.php @@ -1,7 +1,5 @@ single = $single; $this->max = $max; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $string = $this->parseCDATA($string); if ($string === '') return false; $parts = explode(' ', $string); // parseCDATA replaced \r, \t and \n diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Number.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Number.php index 4f22f82907..3d4028ee8c 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Number.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Number.php @@ -9,20 +9,21 @@ class HTMLPurifier_AttrDef_CSS_Number extends HTMLPurifier_AttrDef /** * Bool indicating whether or not only positive values allowed. */ - var $non_negative = false; + protected $non_negative = false; /** * @param $non_negative Bool indicating whether negatives are forbidden */ - function HTMLPurifier_AttrDef_CSS_Number($non_negative = false) { + public function __construct($non_negative = false) { $this->non_negative = $non_negative; } - function validate($number, $config, &$context) { + public function validate($number, $config, $context) { $number = $this->parseCDATA($number); if ($number === '') return false; + if ($number === '0') return '0'; $sign = ''; switch ($number[0]) { @@ -37,13 +38,16 @@ class HTMLPurifier_AttrDef_CSS_Number extends HTMLPurifier_AttrDef $number = ltrim($number, '0'); return $number ? $sign . $number : '0'; } - if (!strpos($number, '.')) return false; + + // Period is the only non-numeric character allowed + if (strpos($number, '.') === false) return false; list($left, $right) = explode('.', $number, 2); - if (!ctype_digit($left)) return false; - $left = ltrim($left, '0'); + if ($left === '' && $right === '') return false; + if ($left !== '' && !ctype_digit($left)) return false; + $left = ltrim($left, '0'); $right = rtrim($right, '0'); if ($right === '') { diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Percentage.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Percentage.php index 4625bde6d7..8b0fcd51a8 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Percentage.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/Percentage.php @@ -1,8 +1,5 @@ number_def = new HTMLPurifier_AttrDef_CSS_Number($non_negative); } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $string = $this->parseCDATA($string); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/TextDecoration.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/TextDecoration.php index 501ab2616f..2108f80492 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/TextDecoration.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/TextDecoration.php @@ -1,7 +1,5 @@ true, diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/URI.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/URI.php index b71a858572..c7dae50376 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/URI.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/CSS/URI.php @@ -1,7 +1,5 @@ valid_values = array_flip($valid_values); $this->case_sensitive = $case_sensitive; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $string = trim($string); if (!$this->case_sensitive) { // we may want to do full case-insensitive libraries @@ -50,7 +49,7 @@ class HTMLPurifier_AttrDef_Enum extends HTMLPurifier_AttrDef * valid values. Example: "foo,bar,baz". Prepend "s:" to make * case sensitive */ - function make($string) { + public function make($string) { if (strlen($string) > 2 && $string[0] == 's' && $string[1] == ':') { $string = substr($string, 2); $sensitive = true; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Bool.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Bool.php index ff6f0a8649..c88702790f 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Bool.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Bool.php @@ -1,19 +1,17 @@ name = $name;} + public function __construct($name = false) {$this->name = $name;} - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { if (empty($string)) return false; return $this->name; } @@ -21,7 +19,7 @@ class HTMLPurifier_AttrDef_HTML_Bool extends HTMLPurifier_AttrDef /** * @param $string Name of attribute */ - function make($string) { + public function make($string) { return new HTMLPurifier_AttrDef_HTML_Bool($string); } diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Color.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Color.php index d6fa6749fb..3aa193e96a 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Color.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Color.php @@ -1,15 +1,12 @@ get('Core', 'ColorKeywords'); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/FrameTarget.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/FrameTarget.php index fdca8cb2ce..0bc80432a3 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/FrameTarget.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/FrameTarget.php @@ -1,30 +1,17 @@ valid_values === false) $this->valid_values = $config->get('Attr', 'AllowedFrameTargets'); return parent::validate($string, $config, $context); } diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/ID.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/ID.php index 641749cea0..9c6aa37e71 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/ID.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/ID.php @@ -1,56 +1,5 @@ get('Attr', 'EnableID')) return false; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Length.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Length.php index c4f98436ae..3f995047b2 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Length.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/Length.php @@ -1,8 +1,5 @@ 'AllowedRel', 'rev' => 'AllowedRev' @@ -42,7 +25,7 @@ class HTMLPurifier_AttrDef_HTML_LinkTypes extends HTMLPurifier_AttrDef $this->name = $configLookup[$name]; } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $allowed = $config->get('Attr', $this->name); if (empty($allowed)) return false; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/MultiLength.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/MultiLength.php index 4c0c88c8ba..b7b9e0570a 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/MultiLength.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/HTML/MultiLength.php @@ -1,8 +1,5 @@ negative = $negative; @@ -40,7 +38,7 @@ class HTMLPurifier_AttrDef_Integer extends HTMLPurifier_AttrDef $this->positive = $positive; } - function validate($integer, $config, &$context) { + public function validate($integer, $config, $context) { $integer = $this->parseCDATA($integer); if ($integer === '') return false; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/Lang.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/Lang.php index e9cdda7adf..7eaccec4ca 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/Lang.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/Lang.php @@ -1,7 +1,5 @@ parseCDATA($string); } diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI.php index 52b4193b98..9c632f1ae7 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI.php @@ -1,66 +1,5 @@ - Munges all browsable (usually http, https and ftp) - absolute URI\'s into another URI, usually a URI redirection service. - This directive accepts a URI, formatted with a %s where - the url-encoded original URI should be inserted (sample: - http://www.google.com/url?q=%s). -

-

- Uses for this directive: -

- -

- This directive has been available since 1.3.0. -

-'); - -// disabling directives - -HTMLPurifier_ConfigSchema::define( - 'URI', 'Disable', false, 'bool', ' -

- Disables all URIs in all forms. Not sure why you\'d want to do that - (after all, the Internet\'s founded on the notion of a hyperlink). - This directive has been available since 1.3.0. -

-'); -HTMLPurifier_ConfigSchema::defineAlias('Attr', 'DisableURI', 'URI', 'Disable'); - -HTMLPurifier_ConfigSchema::define( - 'URI', 'DisableResources', false, 'bool', ' -

- Disables embedding resources, essentially meaning no pictures. You can - still link to them though. See %URI.DisableExternalResources for why - this might be a good idea. This directive has been available since 1.3.0. -

-'); - /** * Validates a URI as defined by RFC 3986. * @note Scheme-specific mechanics deferred to HTMLPurifier_URIScheme @@ -68,18 +7,18 @@ HTMLPurifier_ConfigSchema::define( class HTMLPurifier_AttrDef_URI extends HTMLPurifier_AttrDef { - var $parser; - var $embedsResource; + protected $parser; + protected $embedsResource; /** * @param $embeds_resource_resource Does the URI here result in an extra HTTP request? */ - function HTMLPurifier_AttrDef_URI($embeds_resource = false) { + public function __construct($embeds_resource = false) { $this->parser = new HTMLPurifier_URIParser(); $this->embedsResource = (bool) $embeds_resource; } - function validate($uri, $config, &$context) { + public function validate($uri, $config, $context) { if ($config->get('URI', 'Disable')) return false; @@ -100,7 +39,7 @@ class HTMLPurifier_AttrDef_URI extends HTMLPurifier_AttrDef if (!$result) break; // chained filtering - $uri_def =& $config->getDefinition('URI'); + $uri_def = $config->getDefinition('URI'); $result = $uri_def->filter($uri, $config, $context); if (!$result) break; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Email.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Email.php index 31c3add51c..98d984c39e 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Email.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Email.php @@ -1,8 +1,6 @@ " + // that needs more percent encoding to be done + if ($string == '') return false; + $string = trim($string); + $result = preg_match('/^[A-Z0-9._%-]+@[A-Z0-9.-]+\.[A-Z]{2,4}$/i', $string); + return $result ? $string : false; + } + +} + diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Host.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Host.php index 4812ad1d3d..8d1a7b2c38 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Host.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/Host.php @@ -1,9 +1,5 @@ ipv4 = new HTMLPurifier_AttrDef_URI_IPv4(); $this->ipv6 = new HTMLPurifier_AttrDef_URI_IPv6(); } - function validate($string, $config, &$context) { + public function validate($string, $config, $context) { $length = strlen($string); if ($string === '') return ''; if ($length > 1 && $string[0] === '[' && $string[$length-1] === ']') { diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv4.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv4.php index 9a1af293ba..107e0605ab 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv4.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv4.php @@ -1,7 +1,5 @@ ip4) $this->_loadRegex(); @@ -32,7 +29,7 @@ class HTMLPurifier_AttrDef_URI_IPv4 extends HTMLPurifier_AttrDef * Lazy load function to prevent regex from being stuffed in * cache. */ - function _loadRegex() { + protected function _loadRegex() { $oct = '(?:25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]|[0-9])'; // 0-255 $this->ip4 = "(?:{$oct}\\.{$oct}\\.{$oct}\\.{$oct})"; } diff --git a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv6.php b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv6.php index f48b803dd7..28fb8f5ba8 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv6.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrDef/URI/IPv6.php @@ -1,7 +1,5 @@ ip4) $this->_loadRegex(); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform.php index ce69fcbe82..a295c985da 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform.php @@ -14,7 +14,7 @@ * more details. */ -class HTMLPurifier_AttrTransform +abstract class HTMLPurifier_AttrTransform { /** @@ -26,9 +26,7 @@ class HTMLPurifier_AttrTransform * @param $context Mandatory HTMLPurifier_Context object * @returns Processed attribute array. */ - function transform($attr, $config, &$context) { - trigger_error('Cannot call abstract function', E_USER_ERROR); - } + abstract public function transform($attr, $config, $context); /** * Prepends CSS properties to the style attribute, creating the @@ -36,7 +34,7 @@ class HTMLPurifier_AttrTransform * @param $attr Attribute array to process (passed by reference) * @param $css CSS to prepend */ - function prependCSS(&$attr, $css) { + public function prependCSS(&$attr, $css) { $attr['style'] = isset($attr['style']) ? $attr['style'] : ''; $attr['style'] = $css . $attr['style']; } @@ -46,7 +44,7 @@ class HTMLPurifier_AttrTransform * @param $attr Attribute array to process (passed by reference) * @param $key Key of attribute to confiscate */ - function confiscateAttr(&$attr, $key) { + public function confiscateAttr(&$attr, $key) { if (!isset($attr[$key])) return null; $value = $attr[$key]; unset($attr[$key]); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/BdoDir.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/BdoDir.php index f127feb2b2..bf108bbbf1 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/BdoDir.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/BdoDir.php @@ -1,26 +1,14 @@ get('Attr', 'DefaultTextDir'); return $attr; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/BgColor.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/BgColor.php index de2867efdd..5bc213676f 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/BgColor.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/BgColor.php @@ -1,14 +1,11 @@ attr = $attr; $this->css = $css; } - function transform($attr, $config, &$context) { + public function transform($attr, $config, $context) { if (!isset($attr[$this->attr])) return $attr; unset($attr[$this->attr]); $this->prependCSS($attr, $this->css); diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/Border.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/Border.php index 7da4f6a804..b72c019e99 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/Border.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/Border.php @@ -1,13 +1,11 @@ confiscateAttr($attr, 'border'); // some validation should happen here diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/EnumToCSS.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/EnumToCSS.php index 0470413dd4..5d36b6de7c 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/EnumToCSS.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/EnumToCSS.php @@ -1,7 +1,5 @@ attr = $attr; $this->enumToCSS = $enum_to_css; $this->caseSensitive = (bool) $case_sensitive; } - function transform($attr, $config, &$context) { + public function transform($attr, $config, $context) { if (!isset($attr[$this->attr])) return $attr; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/ImgRequired.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/ImgRequired.php index d042805538..52c716759a 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/ImgRequired.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/ImgRequired.php @@ -1,24 +1,7 @@ array('left', 'right'), 'vspace' => array('top', 'bottom') ); - function HTMLPurifier_AttrTransform_ImgSpace($attr) { + public function __construct($attr) { $this->attr = $attr; if (!isset($this->css[$attr])) { trigger_error(htmlspecialchars($attr) . ' is not valid space attribute'); } } - function transform($attr, $config, &$context) { + public function transform($attr, $config, $context) { if (!isset($attr[$this->attr])) return $attr; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/Lang.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/Lang.php index 899f5c8dc5..960f489e68 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/Lang.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/Lang.php @@ -1,7 +1,5 @@ name = $name; $this->cssName = $css_name ? $css_name : $name; } - function transform($attr, $config, &$context) { + public function transform($attr, $config, $context) { if (!isset($attr[$this->name])) return $attr; $length = $this->confiscateAttr($attr, $this->name); if(ctype_digit($length)) $length .= 'px'; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/Name.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/Name.php index 248d0e02fe..8de8c6ba38 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTransform/Name.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/Name.php @@ -1,14 +1,12 @@ confiscateAttr($attr, 'name'); if ( isset($attr['id'])) return $attr; diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTransform/ScriptRequired.php b/lib/htmlpurifier/HTMLPurifier/AttrTransform/ScriptRequired.php new file mode 100644 index 0000000000..cc18b7e9e2 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/AttrTransform/ScriptRequired.php @@ -0,0 +1,14 @@ + + */ +class HTMLPurifier_AttrTransform_ScriptRequired extends HTMLPurifier_AttrTransform +{ + public function transform($attr, $config, $context) { + if (!isset($attr['type'])) { + $attr['type'] = 'text/javascript'; + } + return $attr; + } +} diff --git a/lib/htmlpurifier/HTMLPurifier/AttrTypes.php b/lib/htmlpurifier/HTMLPurifier/AttrTypes.php index 93abb0d02b..9262a098c1 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrTypes.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrTypes.php @@ -1,18 +1,5 @@ info['Enum'] = new HTMLPurifier_AttrDef_Enum(); $this->info['Bool'] = new HTMLPurifier_AttrDef_HTML_Bool(); @@ -57,7 +43,7 @@ class HTMLPurifier_AttrTypes * @param $type String type name * @return Object AttrDef for type */ - function get($type) { + public function get($type) { // determine if there is any extra info tacked on if (strpos($type, '#') !== false) list($type, $string) = explode('#', $type, 2); @@ -77,7 +63,7 @@ class HTMLPurifier_AttrTypes * @param $type String type name * @param $impl Object AttrDef for type */ - function set($type, $impl) { + public function set($type, $impl) { $this->info[$type] = $impl; } } diff --git a/lib/htmlpurifier/HTMLPurifier/AttrValidator.php b/lib/htmlpurifier/HTMLPurifier/AttrValidator.php index a471b09379..3b2bd4b375 100644 --- a/lib/htmlpurifier/HTMLPurifier/AttrValidator.php +++ b/lib/htmlpurifier/HTMLPurifier/AttrValidator.php @@ -18,7 +18,7 @@ class HTMLPurifier_AttrValidator * @param $config Instance of HTMLPurifier_Config * @param $context Instance of HTMLPurifier_Context */ - function validateToken(&$token, &$config, &$context) { + public function validateToken(&$token, &$config, $context) { $definition = $config->getHTMLDefinition(); $e =& $context->get('ErrorCollector', true); @@ -34,7 +34,10 @@ class HTMLPurifier_AttrValidator $current_token =& $context->get('CurrentToken', true); if (!$current_token) $context->register('CurrentToken', $token); - if ($token->type !== 'start' && $token->type !== 'empty') return $token; + if ( + !$token instanceof HTMLPurifier_Token_Start && + !$token instanceof HTMLPurifier_Token_Empty + ) return $token; // create alias to global definition array, see also $defs // DEFINITION CALL diff --git a/lib/htmlpurifier/HTMLPurifier/Bootstrap.php b/lib/htmlpurifier/HTMLPurifier/Bootstrap.php new file mode 100644 index 0000000000..09dcb5019d --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/Bootstrap.php @@ -0,0 +1,96 @@ + +if (!defined('PHP_EOL')) { + switch (strtoupper(substr(PHP_OS, 0, 3))) { + case 'WIN': + define('PHP_EOL', "\r\n"); + break; + case 'DAR': + define('PHP_EOL', "\r"); + break; + default: + define('PHP_EOL', "\n"); + } +} + +/** + * Bootstrap class that contains meta-functionality for HTML Purifier such as + * the autoload function. + * + * @note + * This class may be used without any other files from HTML Purifier. + */ +class HTMLPurifier_Bootstrap +{ + + /** + * Autoload function for HTML Purifier + * @param $class Class to load + */ + public static function autoload($class) { + $file = HTMLPurifier_Bootstrap::getPath($class); + if (!$file) return false; + require HTMLPURIFIER_PREFIX . '/' . $file; + return true; + } + + /** + * Returns the path for a specific class. + */ + public static function getPath($class) { + if (strncmp('HTMLPurifier', $class, 12) !== 0) return false; + // Custom implementations + if (strncmp('HTMLPurifier_Language_', $class, 22) === 0) { + $code = str_replace('_', '-', substr($class, 22)); + $file = 'HTMLPurifier/Language/classes/' . $code . '.php'; + } else { + $file = str_replace('_', '/', $class) . '.php'; + } + if (!file_exists(HTMLPURIFIER_PREFIX . '/' . $file)) return false; + return $file; + } + + /** + * "Pre-registers" our autoloader on the SPL stack. + */ + public static function registerAutoload() { + $autoload = array('HTMLPurifier_Bootstrap', 'autoload'); + if ( ($funcs = spl_autoload_functions()) === false ) { + spl_autoload_register($autoload); + } elseif (function_exists('spl_autoload_unregister')) { + $compat = version_compare(PHP_VERSION, '5.1.2', '<=') && + version_compare(PHP_VERSION, '5.1.0', '>='); + foreach ($funcs as $func) { + if (is_array($func)) { + // :TRICKY: There are some compatibility issues and some + // places where we need to error out + $reflector = new ReflectionMethod($func[0], $func[1]); + if (!$reflector->isStatic()) { + throw new Exception(' + HTML Purifier autoloader registrar is not compatible + with non-static object methods due to PHP Bug #44144; + Please do not use HTMLPurifier.autoload.php (or any + file that includes this file); instead, place the code: + spl_autoload_register(array(\'HTMLPurifier_Bootstrap\', \'autoload\')) + after your own autoloaders. + '); + } + // Suprisingly, spl_autoload_register supports the + // Class::staticMethod callback format, although call_user_func doesn't + if ($compat) $func = implode('::', $func); + } + spl_autoload_unregister($func); + } + spl_autoload_register($autoload); + foreach ($funcs as $func) spl_autoload_register($func); + } + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/CSSDefinition.php b/lib/htmlpurifier/HTMLPurifier/CSSDefinition.php index 2fc73b905d..0d42ed42e6 100644 --- a/lib/htmlpurifier/HTMLPurifier/CSSDefinition.php +++ b/lib/htmlpurifier/HTMLPurifier/CSSDefinition.php @@ -1,32 +1,5 @@ - Revision identifier for your custom definition. See - %HTML.DefinitionRev for details. This directive has been available - since 2.0.0. -

-'); - /** * Defines allowed CSS attributes and what their values are. * @see HTMLPurifier_HTMLDefinition @@ -34,17 +7,17 @@ HTMLPurifier_ConfigSchema::define( class HTMLPurifier_CSSDefinition extends HTMLPurifier_Definition { - var $type = 'CSS'; + public $type = 'CSS'; /** * Assoc array of attribute name to definition object. */ - var $info = array(); + public $info = array(); /** * Constructs the info array. The meat of this class. */ - function doSetup($config) { + protected function doSetup($config) { $this->info['text-align'] = new HTMLPurifier_AttrDef_Enum( array('left', 'right', 'center', 'justify'), false); @@ -226,7 +199,80 @@ class HTMLPurifier_CSSDefinition extends HTMLPurifier_Definition // partial support $this->info['white-space'] = new HTMLPurifier_AttrDef_Enum(array('nowrap')); + if ($config->get('CSS', 'Proprietary')) { + $this->doSetupProprietary($config); + } + + if ($config->get('CSS', 'AllowTricky')) { + $this->doSetupTricky($config); + } + + $allow_important = $config->get('CSS', 'AllowImportant'); + // wrap all attr-defs with decorator that handles !important + foreach ($this->info as $k => $v) { + $this->info[$k] = new HTMLPurifier_AttrDef_CSS_ImportantDecorator($v, $allow_important); + } + + $this->setupConfigStuff($config); + } + + protected function doSetupProprietary($config) { + // Internet Explorer only scrollbar colors + $this->info['scrollbar-arrow-color'] = new HTMLPurifier_AttrDef_CSS_Color(); + $this->info['scrollbar-base-color'] = new HTMLPurifier_AttrDef_CSS_Color(); + $this->info['scrollbar-darkshadow-color'] = new HTMLPurifier_AttrDef_CSS_Color(); + $this->info['scrollbar-face-color'] = new HTMLPurifier_AttrDef_CSS_Color(); + $this->info['scrollbar-highlight-color'] = new HTMLPurifier_AttrDef_CSS_Color(); + $this->info['scrollbar-shadow-color'] = new HTMLPurifier_AttrDef_CSS_Color(); + + // technically not proprietary, but CSS3, and no one supports it + $this->info['opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue(); + $this->info['-moz-opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue(); + $this->info['-khtml-opacity'] = new HTMLPurifier_AttrDef_CSS_AlphaValue(); + + // only opacity, for now + $this->info['filter'] = new HTMLPurifier_AttrDef_CSS_Filter(); + } + protected function doSetupTricky($config) { + $this->info['display'] = new HTMLPurifier_AttrDef_Enum(array( + 'inline', 'block', 'list-item', 'run-in', 'compact', + 'marker', 'table', 'inline-table', 'table-row-group', + 'table-header-group', 'table-footer-group', 'table-row', + 'table-column-group', 'table-column', 'table-cell', 'table-caption', 'none' + )); + $this->info['visibility'] = new HTMLPurifier_AttrDef_Enum(array( + 'visible', 'hidden', 'collapse' + )); + } + + + /** + * Performs extra config-based processing. Based off of + * HTMLPurifier_HTMLDefinition. + * @todo Refactor duplicate elements into common class (probably using + * composition, not inheritance). + */ + protected function setupConfigStuff($config) { + + // setup allowed elements + $support = "(for information on implementing this, see the ". + "support forums) "; + $allowed_attributes = $config->get('CSS', 'AllowedProperties'); + if ($allowed_attributes !== null) { + foreach ($this->info as $name => $d) { + if(!isset($allowed_attributes[$name])) unset($this->info[$name]); + unset($allowed_attributes[$name]); + } + // emit errors + foreach ($allowed_attributes as $name => $d) { + // :TODO: Is this htmlspecialchars() call really necessary? + $name = htmlspecialchars($name); + trigger_error("Style attribute '$name' is not supported $support", E_USER_WARNING); + } + } + + } } diff --git a/lib/htmlpurifier/HTMLPurifier/ChildDef.php b/lib/htmlpurifier/HTMLPurifier/ChildDef.php index 5236d266c5..0cc345674d 100644 --- a/lib/htmlpurifier/HTMLPurifier/ChildDef.php +++ b/lib/htmlpurifier/HTMLPurifier/ChildDef.php @@ -1,50 +1,32 @@ inline = new HTMLPurifier_ChildDef_Optional($inline); $this->block = new HTMLPurifier_ChildDef_Optional($block); $this->elements = $this->block->elements; } - function validateChildren($tokens_of_children, $config, &$context) { + public function validateChildren($tokens_of_children, $config, $context) { if ($context->get('IsInline') === false) { return $this->block->validateChildren( $tokens_of_children, $config, $context); diff --git a/lib/htmlpurifier/HTMLPurifier/ChildDef/Custom.php b/lib/htmlpurifier/HTMLPurifier/ChildDef/Custom.php index ba722d0595..4ba0788858 100644 --- a/lib/htmlpurifier/HTMLPurifier/ChildDef/Custom.php +++ b/lib/htmlpurifier/HTMLPurifier/ChildDef/Custom.php @@ -1,7 +1,5 @@ dtd_regex = $dtd_regex; $this->_compileRegex(); } /** * Compiles the PCRE regex from a DTD regex ($dtd_regex to $_pcre_regex) */ - function _compileRegex() { + protected function _compileRegex() { $raw = str_replace(' ', '', $this->dtd_regex); if ($raw{0} != '(') { $raw = "($raw)"; @@ -61,7 +59,7 @@ class HTMLPurifier_ChildDef_Custom extends HTMLPurifier_ChildDef $this->_pcre_regex = $reg; } - function validateChildren($tokens_of_children, $config, &$context) { + public function validateChildren($tokens_of_children, $config, $context) { $list_of_children = ''; $nesting = 0; // depth into the nest foreach ($tokens_of_children as $token) { @@ -69,9 +67,9 @@ class HTMLPurifier_ChildDef_Custom extends HTMLPurifier_ChildDef $is_child = ($nesting == 0); // direct - if ($token->type == 'start') { + if ($token instanceof HTMLPurifier_Token_Start) { $nesting++; - } elseif ($token->type == 'end') { + } elseif ($token instanceof HTMLPurifier_Token_End) { $nesting--; } diff --git a/lib/htmlpurifier/HTMLPurifier/ChildDef/Empty.php b/lib/htmlpurifier/HTMLPurifier/ChildDef/Empty.php index 6e63730770..ad4dc0b7cd 100644 --- a/lib/htmlpurifier/HTMLPurifier/ChildDef/Empty.php +++ b/lib/htmlpurifier/HTMLPurifier/ChildDef/Empty.php @@ -1,7 +1,5 @@ elements = $elements; } - var $allow_empty = false; - var $type = 'required'; - function validateChildren($tokens_of_children, $config, &$context) { + public $allow_empty = false; + public $type = 'required'; + public function validateChildren($tokens_of_children, $config, $context) { // if there are no tokens, delete parent node if (empty($tokens_of_children)) return false; @@ -59,7 +57,7 @@ class HTMLPurifier_ChildDef_Required extends HTMLPurifier_ChildDef // generator static $gen = null; if ($gen === null) { - $gen = new HTMLPurifier_Generator(); + $gen = new HTMLPurifier_Generator($config, $context); } foreach ($tokens_of_children as $token) { @@ -71,9 +69,9 @@ class HTMLPurifier_ChildDef_Required extends HTMLPurifier_ChildDef $is_child = ($nesting == 0); - if ($token->type == 'start') { + if ($token instanceof HTMLPurifier_Token_Start) { $nesting++; - } elseif ($token->type == 'end') { + } elseif ($token instanceof HTMLPurifier_Token_End) { $nesting--; } @@ -81,7 +79,7 @@ class HTMLPurifier_ChildDef_Required extends HTMLPurifier_ChildDef $is_deleting = false; if (!isset($this->elements[$token->name])) { $is_deleting = true; - if ($pcdata_allowed && $token->type == 'text') { + if ($pcdata_allowed && $token instanceof HTMLPurifier_Token_Text) { $result[] = $token; } elseif ($pcdata_allowed && $escape_invalid_children) { $result[] = new HTMLPurifier_Token_Text( @@ -91,7 +89,7 @@ class HTMLPurifier_ChildDef_Required extends HTMLPurifier_ChildDef continue; } } - if (!$is_deleting || ($pcdata_allowed && $token->type == 'text')) { + if (!$is_deleting || ($pcdata_allowed && $token instanceof HTMLPurifier_Token_Text)) { $result[] = $token; } elseif ($pcdata_allowed && $escape_invalid_children) { $result[] = diff --git a/lib/htmlpurifier/HTMLPurifier/ChildDef/StrictBlockquote.php b/lib/htmlpurifier/HTMLPurifier/ChildDef/StrictBlockquote.php index 60dcbc4a15..ecdb17ff64 100644 --- a/lib/htmlpurifier/HTMLPurifier/ChildDef/StrictBlockquote.php +++ b/lib/htmlpurifier/HTMLPurifier/ChildDef/StrictBlockquote.php @@ -1,19 +1,16 @@ getHTMLDefinition(); if (!$this->init) { @@ -45,8 +42,8 @@ extends HTMLPurifier_ChildDef_Required if (!$is_inline) { if (!$depth) { if ( - ($token->type == 'text' && !$token->is_whitespace) || - ($token->type != 'text' && !isset($this->elements[$token->name])) + ($token instanceof HTMLPurifier_Token_Text && !$token->is_whitespace) || + (!$token instanceof HTMLPurifier_Token_Text && !isset($this->elements[$token->name])) ) { $is_inline = true; $ret[] = $block_wrap_start; @@ -55,7 +52,7 @@ extends HTMLPurifier_ChildDef_Required } else { if (!$depth) { // starting tokens have been inline text / empty - if ($token->type == 'start' || $token->type == 'empty') { + if ($token instanceof HTMLPurifier_Token_Start || $token instanceof HTMLPurifier_Token_Empty) { if (isset($this->elements[$token->name])) { // ended $ret[] = $block_wrap_end; @@ -65,8 +62,8 @@ extends HTMLPurifier_ChildDef_Required } } $ret[] = $token; - if ($token->type == 'start') $depth++; - if ($token->type == 'end') $depth--; + if ($token instanceof HTMLPurifier_Token_Start) $depth++; + if ($token instanceof HTMLPurifier_Token_End) $depth--; } if ($is_inline) $ret[] = $block_wrap_end; return $ret; diff --git a/lib/htmlpurifier/HTMLPurifier/ChildDef/Table.php b/lib/htmlpurifier/HTMLPurifier/ChildDef/Table.php index ca3c83cc0e..d9d45bad95 100644 --- a/lib/htmlpurifier/HTMLPurifier/ChildDef/Table.php +++ b/lib/htmlpurifier/HTMLPurifier/ChildDef/Table.php @@ -1,18 +1,16 @@ true, 'tbody' => true, 'thead' => true, + public $allow_empty = false; + public $type = 'table'; + public $elements = array('tr' => true, 'tbody' => true, 'thead' => true, 'tfoot' => true, 'caption' => true, 'colgroup' => true, 'col' => true); - function HTMLPurifier_ChildDef_Table() {} - function validateChildren($tokens_of_children, $config, &$context) { + public function __construct() {} + public function validateChildren($tokens_of_children, $config, $context) { if (empty($tokens_of_children)) return false; // this ensures that the loop gets run one last time before closing @@ -41,9 +39,9 @@ class HTMLPurifier_ChildDef_Table extends HTMLPurifier_ChildDef if ($token === false) { // terminating sequence started - } elseif ($token->type == 'start') { + } elseif ($token instanceof HTMLPurifier_Token_Start) { $nesting++; - } elseif ($token->type == 'end') { + } elseif ($token instanceof HTMLPurifier_Token_End) { $nesting--; } @@ -112,7 +110,7 @@ class HTMLPurifier_ChildDef_Table extends HTMLPurifier_ChildDef $collection[] = $token; continue; default: - if ($token->type == 'text' && $token->is_whitespace) { + if ($token instanceof HTMLPurifier_Token_Text && $token->is_whitespace) { $collection[] = $token; $tag_index++; } diff --git a/lib/htmlpurifier/HTMLPurifier/Config.php b/lib/htmlpurifier/HTMLPurifier/Config.php index 1c043aeb71..be264a6250 100644 --- a/lib/htmlpurifier/HTMLPurifier/Config.php +++ b/lib/htmlpurifier/HTMLPurifier/Config.php @@ -1,29 +1,5 @@ -if (!defined('PHP_EOL')) { - switch (strtoupper(substr(PHP_OS, 0, 3))) { - case 'WIN': - define('PHP_EOL', "\r\n"); - break; - case 'DAR': - define('PHP_EOL', "\r"); - break; - default: - define('PHP_EOL', "\n"); - } -} - /** * Configuration object that triggers customizable behavior. * @@ -35,6 +11,8 @@ if (!defined('PHP_EOL')) { * because a configuration object should always be forwarded, * otherwise, you run the risk of missing a parameter and then * being stumped when a configuration directive doesn't work. + * + * @todo Reconsider some of the public member variables */ class HTMLPurifier_Config { @@ -42,69 +20,83 @@ class HTMLPurifier_Config /** * HTML Purifier's version */ - var $version = '2.1.4'; + public $version = '3.1.0'; /** - * Two-level associative array of configuration directives + * Bool indicator whether or not to automatically finalize + * the object if a read operation is done */ - var $conf; + public $autoFinalize = true; + + // protected member variables /** - * Reference HTMLPurifier_ConfigSchema for value checking + * Namespace indexed array of serials for specific namespaces (see + * getSerial() for more info). */ - var $def; + protected $serials = array(); /** - * Indexed array of definitions + * Serial for entire configuration object */ - var $definitions; + protected $serial; /** - * Bool indicator whether or not config is finalized + * Two-level associative array of configuration directives */ - var $finalized = false; + protected $conf; /** - * Bool indicator whether or not to automatically finalize - * the object if a read operation is done + * Parser for variables */ - var $autoFinalize = true; + protected $parser; /** - * Namespace indexed array of serials for specific namespaces (see - * getSerial for more info). + * Reference HTMLPurifier_ConfigSchema for value checking + * @note This is public for introspective purposes. Please don't + * abuse! */ - var $serials = array(); + public $def; /** - * Serial for entire configuration object + * Indexed array of definitions + */ + protected $definitions; + + /** + * Bool indicator whether or not config is finalized */ - var $serial; + protected $finalized = false; /** * @param $definition HTMLPurifier_ConfigSchema that defines what directives * are allowed. */ - function HTMLPurifier_Config(&$definition) { + public function __construct($definition) { $this->conf = $definition->defaults; // set up, copy in defaults $this->def = $definition; // keep a copy around for checking + $this->parser = new HTMLPurifier_VarParser_Flexible(); } /** * Convenience constructor that creates a config object based on a mixed var - * @static * @param mixed $config Variable that defines the state of the config * object. Can be: a HTMLPurifier_Config() object, * an array of directives based on loadArray(), * or a string filename of an ini file. + * @param HTMLPurifier_ConfigSchema Schema object * @return Configured HTMLPurifier_Config object */ - function create($config) { - if (is_a($config, 'HTMLPurifier_Config')) { + public static function create($config, $schema = null) { + if ($config instanceof HTMLPurifier_Config) { // pass-through return $config; } - $ret = HTMLPurifier_Config::createDefault(); + if (!$schema) { + $ret = HTMLPurifier_Config::createDefault(); + } else { + $ret = new HTMLPurifier_Config($schema); + } if (is_string($config)) $ret->loadIni($config); elseif (is_array($config)) $ret->loadArray($config); return $ret; @@ -112,11 +104,10 @@ class HTMLPurifier_Config /** * Convenience constructor that creates a default configuration object. - * @static * @return Default HTMLPurifier_Config object. */ - function createDefault() { - $definition =& HTMLPurifier_ConfigSchema::instance(); + public static function createDefault() { + $definition = HTMLPurifier_ConfigSchema::instance(); $config = new HTMLPurifier_Config($definition); return $config; } @@ -126,7 +117,7 @@ class HTMLPurifier_Config * @param $namespace String namespace * @param $key String key */ - function get($namespace, $key, $from_alias = false) { + public function get($namespace, $key) { if (!$this->finalized && $this->autoFinalize) $this->finalize(); if (!isset($this->def->info[$namespace][$key])) { // can't add % due to SimpleTest bug @@ -147,7 +138,7 @@ class HTMLPurifier_Config * Retreives an array of directives to values from a given namespace * @param $namespace String namespace */ - function getBatch($namespace) { + public function getBatch($namespace) { if (!$this->finalized && $this->autoFinalize) $this->finalize(); if (!isset($this->def->info[$namespace])) { trigger_error('Cannot retrieve undefined namespace ' . htmlspecialchars($namespace), @@ -164,7 +155,7 @@ class HTMLPurifier_Config * before processing! * @param $namespace Namespace to get serial for */ - function getBatchSerial($namespace) { + public function getBatchSerial($namespace) { if (empty($this->serials[$namespace])) { $batch = $this->getBatch($namespace); unset($batch['DefinitionRev']); @@ -177,7 +168,7 @@ class HTMLPurifier_Config * Returns a md5 signature for the entire configuration object * that uniquely identifies that particular configuration */ - function getSerial() { + public function getSerial() { if (empty($this->serial)) { $this->serial = md5(serialize($this->getAll())); } @@ -187,7 +178,7 @@ class HTMLPurifier_Config /** * Retrieves all directives, organized by namespace */ - function getAll() { + public function getAll() { if (!$this->finalized && $this->autoFinalize) $this->finalize(); return $this->conf; } @@ -198,7 +189,7 @@ class HTMLPurifier_Config * @param $key String key * @param $value Mixed value */ - function set($namespace, $key, $value, $from_alias = false) { + public function set($namespace, $key, $value, $from_alias = false) { if ($this->isFinalized('Cannot set directive after finalization')) return; if (!isset($this->def->info[$namespace][$key])) { trigger_error('Cannot set undefined directive ' . htmlspecialchars("$namespace.$key") . ' to value', @@ -208,18 +199,25 @@ class HTMLPurifier_Config if ($this->def->info[$namespace][$key]->class == 'alias') { if ($from_alias) { trigger_error('Double-aliases not allowed, please fix '. - 'ConfigSchema bug with' . "$namespace.$key"); + 'ConfigSchema bug with' . "$namespace.$key", E_USER_ERROR); + return; } - $this->set($this->def->info[$namespace][$key]->namespace, - $this->def->info[$namespace][$key]->name, + $this->set($new_ns = $this->def->info[$namespace][$key]->namespace, + $new_dir = $this->def->info[$namespace][$key]->name, $value, true); + trigger_error("$namespace.$key is an alias, preferred directive name is $new_ns.$new_dir", E_USER_NOTICE); + return; + } + try { + $value = $this->parser->parse( + $value, + $type = $this->def->info[$namespace][$key]->type, + $this->def->info[$namespace][$key]->allow_null + ); + } catch (HTMLPurifier_VarParserException $e) { + trigger_error('Value for ' . "$namespace.$key" . ' is of invalid type, should be ' . $type, E_USER_WARNING); return; } - $value = $this->def->validate( - $value, - $type = $this->def->info[$namespace][$key]->type, - $this->def->info[$namespace][$key]->allow_null - ); if (is_string($value)) { // resolve value alias if defined if (isset($this->def->info[$namespace][$key]->aliases[$value])) { @@ -234,10 +232,6 @@ class HTMLPurifier_Config } } } - if ($this->def->isError($value)) { - trigger_error('Value for ' . "$namespace.$key" . ' is of invalid type, should be ' . $type, E_USER_WARNING); - return; - } $this->conf[$namespace][$key] = $value; // reset definitions if the directives they depend on changed @@ -252,30 +246,29 @@ class HTMLPurifier_Config /** * Convenience function for error reporting - * @private */ - function _listify($lookup) { + private function _listify($lookup) { $list = array(); foreach ($lookup as $name => $b) $list[] = $name; return implode(', ', $list); } /** - * Retrieves reference to the HTML definition. + * Retrieves object reference to the HTML definition. * @param $raw Return a copy that has not been setup yet. Must be * called before it's been setup, otherwise won't work. */ - function &getHTMLDefinition($raw = false) { - $def =& $this->getDefinition('HTML', $raw); - return $def; // prevent PHP 4.4.0 from complaining + public function getHTMLDefinition($raw = false) { + return $this->getDefinition('HTML', $raw); } /** - * Retrieves reference to the CSS definition + * Retrieves object reference to the CSS definition + * @param $raw Return a copy that has not been setup yet. Must be + * called before it's been setup, otherwise won't work. */ - function &getCSSDefinition($raw = false) { - $def =& $this->getDefinition('CSS', $raw); - return $def; + public function getCSSDefinition($raw = false) { + return $this->getDefinition('CSS', $raw); } /** @@ -283,7 +276,7 @@ class HTMLPurifier_Config * @param $type Type of definition: HTML, CSS, etc * @param $raw Whether or not definition should be returned raw */ - function &getDefinition($type, $raw = false) { + public function getDefinition($type, $raw = false) { if (!$this->finalized && $this->autoFinalize) $this->finalize(); $factory = HTMLPurifier_DefinitionCacheFactory::instance(); $cache = $factory->create($type, $this); @@ -317,17 +310,13 @@ class HTMLPurifier_Config } elseif ($type == 'URI') { $this->definitions[$type] = new HTMLPurifier_URIDefinition(); } else { - trigger_error("Definition of $type type not supported"); - $false = false; - return $false; + throw new HTMLPurifier_Exception("Definition of $type type not supported"); } // quick abort if raw if ($raw) { if (is_null($this->get($type, 'DefinitionID'))) { // fatally error out if definition ID not set - trigger_error("Cannot retrieve raw version without specifying %$type.DefinitionID", E_USER_ERROR); - $false = new HTMLPurifier_Error(); - return $false; + throw new HTMLPurifier_Exception("Cannot retrieve raw version without specifying %$type.DefinitionID"); } return $this->definitions[$type]; } @@ -343,7 +332,7 @@ class HTMLPurifier_Config * Namespace.Directive => Value * @param $config_array Configuration associative array */ - function loadArray($config_array) { + public function loadArray($config_array) { if ($this->isFinalized('Cannot load directives after finalization')) return; foreach ($config_array as $key => $value) { $key = str_replace('_', '.', $key); @@ -366,10 +355,11 @@ class HTMLPurifier_Config * that are allowed in a web-form context as per an allowed * namespaces/directives list. * @param $allowed List of allowed namespaces/directives - * @static */ - function getAllowedDirectivesForForm($allowed) { - $schema = HTMLPurifier_ConfigSchema::instance(); + public static function getAllowedDirectivesForForm($allowed, $schema = null) { + if (!$schema) { + $schema = HTMLPurifier_ConfigSchema::instance(); + } if ($allowed !== true) { if (is_string($allowed)) $allowed = array($allowed); $allowed_ns = array(); @@ -411,11 +401,11 @@ class HTMLPurifier_Config * @param $index Index/name that the config variables are in * @param $allowed List of allowed namespaces/directives * @param $mq_fix Boolean whether or not to enable magic quotes fix - * @static + * @param $schema Instance of HTMLPurifier_ConfigSchema to use, if not global copy */ - function loadArrayFromForm($array, $index, $allowed = true, $mq_fix = true) { - $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix); - $config = HTMLPurifier_Config::create($ret); + public static function loadArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true, $schema = null) { + $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix, $schema); + $config = HTMLPurifier_Config::create($ret, $schema); return $config; } @@ -423,21 +413,20 @@ class HTMLPurifier_Config * Merges in configuration values from $_GET/$_POST to object. NOT STATIC. * @note Same parameters as loadArrayFromForm */ - function mergeArrayFromForm($array, $index, $allowed = true, $mq_fix = true) { - $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix); + public function mergeArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true) { + $ret = HTMLPurifier_Config::prepareArrayFromForm($array, $index, $allowed, $mq_fix, $this->def); $this->loadArray($ret); } /** * Prepares an array from a form into something usable for the more * strict parts of HTMLPurifier_Config - * @static */ - function prepareArrayFromForm($array, $index, $allowed = true, $mq_fix = true) { - $array = (isset($array[$index]) && is_array($array[$index])) ? $array[$index] : array(); - $mq = get_magic_quotes_gpc() && $mq_fix; + public static function prepareArrayFromForm($array, $index = false, $allowed = true, $mq_fix = true, $schema = null) { + if ($index !== false) $array = (isset($array[$index]) && is_array($array[$index])) ? $array[$index] : array(); + $mq = $mq_fix && function_exists('get_magic_quotes_gpc') && get_magic_quotes_gpc(); - $allowed = HTMLPurifier_Config::getAllowedDirectivesForForm($allowed); + $allowed = HTMLPurifier_Config::getAllowedDirectivesForForm($allowed, $schema); $ret = array(); foreach ($allowed as $key) { list($ns, $directive) = $key; @@ -457,7 +446,7 @@ class HTMLPurifier_Config * Loads configuration values from an ini file * @param $filename Name of ini file */ - function loadIni($filename) { + public function loadIni($filename) { if ($this->isFinalized('Cannot load directives after finalization')) return; $array = parse_ini_file($filename, true); $this->loadArray($array); @@ -467,7 +456,7 @@ class HTMLPurifier_Config * Checks whether or not the configuration object is finalized. * @param $error String error message, or false for no error */ - function isFinalized($error = false) { + public function isFinalized($error = false) { if ($this->finalized && $error) { trigger_error($error, E_USER_ERROR); } @@ -478,17 +467,18 @@ class HTMLPurifier_Config * Finalizes configuration only if auto finalize is on and not * already finalized */ - function autoFinalize() { + public function autoFinalize() { if (!$this->finalized && $this->autoFinalize) $this->finalize(); } /** * Finalizes a configuration object, prohibiting further change */ - function finalize() { + public function finalize() { $this->finalized = true; } } + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigDef.php b/lib/htmlpurifier/HTMLPurifier/ConfigDef.php index 21825e01b8..fe35e7a6cf 100644 --- a/lib/htmlpurifier/HTMLPurifier/ConfigDef.php +++ b/lib/htmlpurifier/HTMLPurifier/ConfigDef.php @@ -3,7 +3,7 @@ /** * Base class for configuration entity */ -class HTMLPurifier_ConfigDef { - var $class = false; +abstract class HTMLPurifier_ConfigDef { + public $class = false; } diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigDef/Directive.php b/lib/htmlpurifier/HTMLPurifier/ConfigDef/Directive.php index 21c33fae8d..cb1329108c 100644 --- a/lib/htmlpurifier/HTMLPurifier/ConfigDef/Directive.php +++ b/lib/htmlpurifier/HTMLPurifier/ConfigDef/Directive.php @@ -1,7 +1,5 @@ type = $type; - if ($descriptions !== null) $this->descriptions = $descriptions; - if ( $allow_null !== null) $this->allow_null = $allow_null; - if ( $allowed !== null) $this->allowed = $allowed; - if ( $aliases !== null) $this->aliases = $aliases; + if ( $type !== null) $this->type = $type; + if ( $allow_null !== null) $this->allow_null = $allow_null; + if ( $allowed !== null) $this->allowed = $allowed; + if ( $aliases !== null) $this->aliases = $aliases; } /** @@ -37,43 +33,23 @@ class HTMLPurifier_ConfigDef_Directive extends HTMLPurifier_ConfigDef * - hash (array of key => value) * - mixed (anything goes) */ - var $type = 'mixed'; - - /** - * Plaintext descriptions of the configuration entity is. Organized by - * file and line number, so multiple descriptions are allowed. - */ - var $descriptions = array(); + public $type = 'mixed'; /** * Is null allowed? Has no effect for mixed type. * @bool */ - var $allow_null = false; + public $allow_null = false; /** * Lookup table of allowed values of the element, bool true if all allowed. */ - var $allowed = true; + public $allowed = true; /** * Hash of value aliases, i.e. values that are equivalent. */ - var $aliases = array(); - - /** - * Advisory list of directive aliases, i.e. other directives that - * redirect here - */ - var $directiveAliases = array(); - - /** - * Adds a description to the array - */ - function addDescription($file, $line, $description) { - if (!isset($this->descriptions[$file])) $this->descriptions[$file] = array(); - $this->descriptions[$file][$line] = $description; - } + public $aliases = array(); } diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigDef/DirectiveAlias.php b/lib/htmlpurifier/HTMLPurifier/ConfigDef/DirectiveAlias.php index 6637802621..98b8edd1ce 100644 --- a/lib/htmlpurifier/HTMLPurifier/ConfigDef/DirectiveAlias.php +++ b/lib/htmlpurifier/HTMLPurifier/ConfigDef/DirectiveAlias.php @@ -1,24 +1,22 @@ namespace = $namespace; $this->name = $name; } diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigDef/Namespace.php b/lib/htmlpurifier/HTMLPurifier/ConfigDef/Namespace.php index 21d732114f..f282065b0a 100644 --- a/lib/htmlpurifier/HTMLPurifier/ConfigDef/Namespace.php +++ b/lib/htmlpurifier/HTMLPurifier/ConfigDef/Namespace.php @@ -1,22 +1,10 @@ description = $description; - } - - var $class = 'namespace'; - - /** - * String description of what kinds of directives go in this namespace. - */ - var $description; - +class HTMLPurifier_ConfigDef_Namespace extends HTMLPurifier_ConfigDef +{ + public $class = 'namespace'; } diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema.php index d6700e6ec1..bfa84a1b7e 100644 --- a/lib/htmlpurifier/HTMLPurifier/ConfigSchema.php +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema.php @@ -1,31 +1,7 @@ 'String', - 'istring' => 'Case-insensitive string', - 'text' => 'Text', - 'itext' => 'Case-insensitive text', - 'int' => 'Integer', - 'float' => 'Float', - 'bool' => 'Boolean', - 'lookup' => 'Lookup array', - 'list' => 'Array list', - 'hash' => 'Associative array', - 'mixed' => 'Mixed' - ); + protected $parser; + + public function __construct() { + $this->parser = new HTMLPurifier_VarParser_Flexible(); + } /** - * Initializes the default namespaces. + * Unserializes the default ConfigSchema. */ - function initialize() { - $this->defineNamespace('Core', 'Core features that are always available.'); - $this->defineNamespace('Attr', 'Features regarding attribute validation.'); - $this->defineNamespace('URI', 'Features regarding Uniform Resource Identifiers.'); - $this->defineNamespace('HTML', 'Configuration regarding allowed HTML.'); - $this->defineNamespace('CSS', 'Configuration regarding allowed CSS.'); - $this->defineNamespace('AutoFormat', 'Configuration for activating auto-formatting functionality (also known as Injectors)'); - $this->defineNamespace('AutoFormatParam', 'Configuration for customizing auto-formatting functionality'); - $this->defineNamespace('Output', 'Configuration relating to the generation of (X)HTML.'); - $this->defineNamespace('Cache', 'Configuration for DefinitionCache and related subclasses.'); - $this->defineNamespace('Test', 'Developer testing configuration for our unit tests.'); + public static function makeFromSerial() { + return unserialize(file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/ConfigSchema/schema.ser')); } /** * Retrieves an instance of the application-wide configuration definition. - * @static */ - function &instance($prototype = null) { - static $instance; + public static function instance($prototype = null) { if ($prototype !== null) { - $instance = $prototype; - } elseif ($instance === null || $prototype === true) { - $instance = new HTMLPurifier_ConfigSchema(); - $instance->initialize(); + HTMLPurifier_ConfigSchema::$singleton = $prototype; + } elseif (HTMLPurifier_ConfigSchema::$singleton === null || $prototype === true) { + HTMLPurifier_ConfigSchema::$singleton = HTMLPurifier_ConfigSchema::makeFromSerial(); } - return $instance; + return HTMLPurifier_ConfigSchema::$singleton; } /** * Defines a directive for configuration - * @static - * @warning Will fail of directive's namespace is defined + * @warning Will fail of directive's namespace is defined. + * @warning This method's signature is slightly different from the legacy + * define() static method! Beware! * @param $namespace Namespace the directive is in * @param $name Key of directive * @param $default Default value of directive * @param $type Allowed type of the directive. See * HTMLPurifier_DirectiveDef::$type for allowed values - * @param $description Description of directive for documentation + * @param $allow_null Whether or not to allow null values */ - function define($namespace, $name, $default, $type, $description) { - $def =& HTMLPurifier_ConfigSchema::instance(); - - // basic sanity checks - if (HTMLPURIFIER_SCHEMA_STRICT) { - if (!isset($def->info[$namespace])) { - trigger_error('Cannot define directive for undefined namespace', - E_USER_ERROR); - return; - } - if (!ctype_alnum($name)) { - trigger_error('Directive name must be alphanumeric', - E_USER_ERROR); - return; - } - if (empty($description)) { - trigger_error('Description must be non-empty', - E_USER_ERROR); - return; - } - } - - if (isset($def->info[$namespace][$name])) { - // already defined - if ( - $def->info[$namespace][$name]->type !== $type || - $def->defaults[$namespace][$name] !== $default - ) { - trigger_error('Inconsistent default or type, cannot redefine'); - return; - } - } else { - // needs defining - - // process modifiers (OPTIMIZE!) - $type_values = explode('/', $type, 2); - $type = $type_values[0]; - $modifier = isset($type_values[1]) ? $type_values[1] : false; - $allow_null = ($modifier === 'null'); - - if (HTMLPURIFIER_SCHEMA_STRICT) { - if (!isset($def->types[$type])) { - trigger_error('Invalid type for configuration directive', - E_USER_ERROR); - return; - } - $default = $def->validate($default, $type, $allow_null); - if ($def->isError($default)) { - trigger_error('Default value does not match directive type', - E_USER_ERROR); - return; - } - } - - $def->info[$namespace][$name] = - new HTMLPurifier_ConfigDef_Directive(); - $def->info[$namespace][$name]->type = $type; - $def->info[$namespace][$name]->allow_null = $allow_null; - $def->defaults[$namespace][$name] = $default; - } - if (!HTMLPURIFIER_SCHEMA_STRICT) return; - $backtrace = debug_backtrace(); - $file = $def->mungeFilename($backtrace[0]['file']); - $line = $backtrace[0]['line']; - $def->info[$namespace][$name]->addDescription($file,$line,$description); + public function add($namespace, $name, $default, $type, $allow_null) { + $default = $this->parser->parse($default, $type, $allow_null); + $this->info[$namespace][$name] = new HTMLPurifier_ConfigDef_Directive(); + $this->info[$namespace][$name]->type = $type; + $this->info[$namespace][$name]->allow_null = $allow_null; + $this->defaults[$namespace][$name] = $default; } /** * Defines a namespace for directives to be put into. - * @static + * @warning This is slightly different from the corresponding static + * method. * @param $namespace Namespace's name - * @param $description Description of the namespace */ - function defineNamespace($namespace, $description) { - $def =& HTMLPurifier_ConfigSchema::instance(); - if (HTMLPURIFIER_SCHEMA_STRICT) { - if (isset($def->info[$namespace])) { - trigger_error('Cannot redefine namespace', E_USER_ERROR); - return; - } - if (!ctype_alnum($namespace)) { - trigger_error('Namespace name must be alphanumeric', - E_USER_ERROR); - return; - } - if (empty($description)) { - trigger_error('Description must be non-empty', - E_USER_ERROR); - return; - } - } - $def->info[$namespace] = array(); - $def->info_namespace[$namespace] = new HTMLPurifier_ConfigDef_Namespace(); - $def->info_namespace[$namespace]->description = $description; - $def->defaults[$namespace] = array(); + public function addNamespace($namespace) { + $this->info[$namespace] = array(); + $this->defaults[$namespace] = array(); } /** @@ -206,231 +85,99 @@ class HTMLPurifier_ConfigSchema { * * Directive value aliases are convenient for developers because it lets * them set a directive to several values and get the same result. - * @static * @param $namespace Directive's namespace * @param $name Name of Directive - * @param $alias Name of aliased value - * @param $real Value aliased value will be converted into + * @param $aliases Hash of aliased values to the real alias */ - function defineValueAliases($namespace, $name, $aliases) { - $def =& HTMLPurifier_ConfigSchema::instance(); - if (HTMLPURIFIER_SCHEMA_STRICT && !isset($def->info[$namespace][$name])) { - trigger_error('Cannot set value alias for non-existant directive', - E_USER_ERROR); - return; - } + public function addValueAliases($namespace, $name, $aliases) { foreach ($aliases as $alias => $real) { - if (HTMLPURIFIER_SCHEMA_STRICT) { - if (!$def->info[$namespace][$name] !== true && - !isset($def->info[$namespace][$name]->allowed[$real]) - ) { - trigger_error('Cannot define alias to value that is not allowed', - E_USER_ERROR); - return; - } - if (isset($def->info[$namespace][$name]->allowed[$alias])) { - trigger_error('Cannot define alias over allowed value', - E_USER_ERROR); - return; - } - } - $def->info[$namespace][$name]->aliases[$alias] = $real; + $this->info[$namespace][$name]->aliases[$alias] = $real; } } /** * Defines a set of allowed values for a directive. - * @static + * @warning This is slightly different from the corresponding static + * method definition. * @param $namespace Namespace of directive * @param $name Name of directive - * @param $allowed_values Arraylist of allowed values + * @param $allowed Lookup array of allowed values */ - function defineAllowedValues($namespace, $name, $allowed_values) { - $def =& HTMLPurifier_ConfigSchema::instance(); - if (HTMLPURIFIER_SCHEMA_STRICT && !isset($def->info[$namespace][$name])) { - trigger_error('Cannot define allowed values for undefined directive', - E_USER_ERROR); - return; - } - $directive =& $def->info[$namespace][$name]; - $type = $directive->type; - if (HTMLPURIFIER_SCHEMA_STRICT && $type != 'string' && $type != 'istring') { - trigger_error('Cannot define allowed values for directive whose type is not string', - E_USER_ERROR); - return; - } - if ($directive->allowed === true) { - $directive->allowed = array(); - } - foreach ($allowed_values as $value) { - $directive->allowed[$value] = true; - } - if ( - HTMLPURIFIER_SCHEMA_STRICT && - $def->defaults[$namespace][$name] !== null && - !isset($directive->allowed[$def->defaults[$namespace][$name]]) - ) { - trigger_error('Default value must be in allowed range of variables', - E_USER_ERROR); - $directive->allowed = true; // undo undo! - return; - } + public function addAllowedValues($namespace, $name, $allowed) { + $type = $this->info[$namespace][$name]->type; + $this->info[$namespace][$name]->allowed = $allowed; } /** * Defines a directive alias for backwards compatibility - * @static * @param $namespace * @param $name Directive that will be aliased * @param $new_namespace * @param $new_name Directive that the alias will be to */ - function defineAlias($namespace, $name, $new_namespace, $new_name) { - $def =& HTMLPurifier_ConfigSchema::instance(); - if (HTMLPURIFIER_SCHEMA_STRICT) { - if (!isset($def->info[$namespace])) { - trigger_error('Cannot define directive alias in undefined namespace', - E_USER_ERROR); - return; - } - if (!ctype_alnum($name)) { - trigger_error('Directive name must be alphanumeric', - E_USER_ERROR); - return; - } - if (isset($def->info[$namespace][$name])) { - trigger_error('Cannot define alias over directive', - E_USER_ERROR); - return; - } - if (!isset($def->info[$new_namespace][$new_name])) { - trigger_error('Cannot define alias to undefined directive', - E_USER_ERROR); - return; - } - if ($def->info[$new_namespace][$new_name]->class == 'alias') { - trigger_error('Cannot define alias to alias', - E_USER_ERROR); - return; - } - } - $def->info[$namespace][$name] = - new HTMLPurifier_ConfigDef_DirectiveAlias( - $new_namespace, $new_name); - $def->info[$new_namespace][$new_name]->directiveAliases[] = "$namespace.$name"; + public function addAlias($namespace, $name, $new_namespace, $new_name) { + $this->info[$namespace][$name] = new HTMLPurifier_ConfigDef_DirectiveAlias($new_namespace, $new_name); } - /** - * Validate a variable according to type. Return null if invalid. - */ - function validate($var, $type, $allow_null = false) { - if (!isset($this->types[$type])) { - trigger_error('Invalid type', E_USER_ERROR); - return; - } - if ($allow_null && $var === null) return null; - switch ($type) { - case 'mixed': - //if (is_string($var)) $var = unserialize($var); - return $var; - case 'istring': - case 'string': - case 'text': // no difference, just is longer/multiple line string - case 'itext': - if (!is_string($var)) break; - if ($type === 'istring' || $type === 'itext') $var = strtolower($var); - return $var; - case 'int': - if (is_string($var) && ctype_digit($var)) $var = (int) $var; - elseif (!is_int($var)) break; - return $var; - case 'float': - if (is_string($var) && is_numeric($var)) $var = (float) $var; - elseif (!is_float($var)) break; - return $var; - case 'bool': - if (is_int($var) && ($var === 0 || $var === 1)) { - $var = (bool) $var; - } elseif (is_string($var)) { - if ($var == 'on' || $var == 'true' || $var == '1') { - $var = true; - } elseif ($var == 'off' || $var == 'false' || $var == '0') { - $var = false; - } else { - break; - } - } elseif (!is_bool($var)) break; - return $var; - case 'list': - case 'hash': - case 'lookup': - if (is_string($var)) { - // special case: technically, this is an array with - // a single empty string item, but having an empty - // array is more intuitive - if ($var == '') return array(); - if (strpos($var, "\n") === false && strpos($var, "\r") === false) { - // simplistic string to array method that only works - // for simple lists of tag names or alphanumeric characters - $var = explode(',',$var); - } else { - $var = preg_split('/(,|[\n\r]+)/', $var); - } - // remove spaces - foreach ($var as $i => $j) $var[$i] = trim($j); - if ($type === 'hash') { - // key:value,key2:value2 - $nvar = array(); - foreach ($var as $keypair) { - $c = explode(':', $keypair, 2); - if (!isset($c[1])) continue; - $nvar[$c[0]] = $c[1]; - } - $var = $nvar; - } - } - if (!is_array($var)) break; - $keys = array_keys($var); - if ($keys === array_keys($keys)) { - if ($type == 'list') return $var; - elseif ($type == 'lookup') { - $new = array(); - foreach ($var as $key) { - $new[$key] = true; - } - return $new; - } else break; - } - if ($type === 'lookup') { - foreach ($var as $key => $value) { - $var[$key] = true; - } - } - return $var; + // DEPRECATED METHODS + + /** @see HTMLPurifier_ConfigSchema->set() */ + public static function define($namespace, $name, $default, $type, $description) { + HTMLPurifier_ConfigSchema::deprecated(__METHOD__); + // process modifiers (OPTIMIZE!) + $type_values = explode('/', $type, 2); + $type = $type_values[0]; + $modifier = isset($type_values[1]) ? $type_values[1] : false; + $allow_null = ($modifier === 'null'); + $def = HTMLPurifier_ConfigSchema::instance(); + $def->add($namespace, $name, $default, $type, $allow_null); + } + + /** @see HTMLPurifier_ConfigSchema->addNamespace() */ + public static function defineNamespace($namespace, $description) { + HTMLPurifier_ConfigSchema::deprecated(__METHOD__); + $def = HTMLPurifier_ConfigSchema::instance(); + $def->addNamespace($namespace); + } + + /** @see HTMLPurifier_ConfigSchema->addValueAliases() */ + public static function defineValueAliases($namespace, $name, $aliases) { + HTMLPurifier_ConfigSchema::deprecated(__METHOD__); + $def = HTMLPurifier_ConfigSchema::instance(); + $def->addValueAliases($namespace, $name, $aliases); + } + + /** @see HTMLPurifier_ConfigSchema->addAllowedValues() */ + public static function defineAllowedValues($namespace, $name, $allowed_values) { + HTMLPurifier_ConfigSchema::deprecated(__METHOD__); + $allowed = array(); + foreach ($allowed_values as $value) { + $allowed[$value] = true; } - $error = new HTMLPurifier_Error(); - return $error; + $def = HTMLPurifier_ConfigSchema::instance(); + $def->addAllowedValues($namespace, $name, $allowed); } - /** - * Takes an absolute path and munges it into a more manageable relative path - */ - function mungeFilename($filename) { - if (!HTMLPURIFIER_SCHEMA_STRICT) return $filename; - $offset = strrpos($filename, 'HTMLPurifier'); - $filename = substr($filename, $offset); - $filename = str_replace('\\', '/', $filename); - return $filename; + /** @see HTMLPurifier_ConfigSchema->addAlias() */ + public static function defineAlias($namespace, $name, $new_namespace, $new_name) { + HTMLPurifier_ConfigSchema::deprecated(__METHOD__); + $def = HTMLPurifier_ConfigSchema::instance(); + $def->addAlias($namespace, $name, $new_namespace, $new_name); + } + + /** @deprecated, use HTMLPurifier_VarParser->parse() */ + public function validate($a, $b, $c = false) { + trigger_error("HTMLPurifier_ConfigSchema->validate deprecated, use HTMLPurifier_VarParser->parse instead", E_USER_NOTICE); + return $this->parser->parse($a, $b, $c); } /** - * Checks if var is an HTMLPurifier_Error object + * Throws an E_USER_NOTICE stating that a method is deprecated. */ - function isError($var) { - if (!is_object($var)) return false; - if (!is_a($var, 'HTMLPurifier_Error')) return false; - return true; + private static function deprecated($method) { + trigger_error("Static HTMLPurifier_ConfigSchema::$method deprecated, use add*() method instead", E_USER_NOTICE); } + } diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php new file mode 100644 index 0000000000..69b71387d6 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/ConfigSchema.php @@ -0,0 +1,49 @@ +namespaces as $n) { + $schema->addNamespace($n->namespace); + } + foreach ($interchange->directives as $d) { + $schema->add( + $d->id->namespace, + $d->id->directive, + $d->default, + $d->type, + $d->typeAllowsNull + ); + if ($d->allowed !== null) { + $schema->addAllowedValues( + $d->id->namespace, + $d->id->directive, + $d->allowed + ); + } + foreach ($d->aliases as $alias) { + $schema->addAlias( + $alias->namespace, + $alias->directive, + $d->id->namespace, + $d->id->directive + ); + } + if ($d->valueAliases !== null) { + $schema->addValueAliases( + $d->id->namespace, + $d->id->directive, + $d->valueAliases + ); + } + } + return $schema; + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/Xml.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/Xml.php new file mode 100644 index 0000000000..3c398d667e --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Builder/Xml.php @@ -0,0 +1,106 @@ +startElement('div'); + + $purifier = HTMLPurifier::getInstance(); + $html = $purifier->purify($html); + $this->writeAttribute('xmlns', 'http://www.w3.org/1999/xhtml'); + $this->writeRaw($html); + + $this->endElement(); // div + } + + protected function export($var) { + if ($var === array()) return 'array()'; + return var_export($var, true); + } + + public function build($interchange) { + // global access, only use as last resort + $this->interchange = $interchange; + + $this->setIndent(true); + $this->startDocument('1.0', 'UTF-8'); + $this->startElement('configdoc'); + $this->writeElement('title', $interchange->name); + + foreach ($interchange->namespaces as $namespace) { + $this->buildNamespace($namespace); + } + + $this->endElement(); // configdoc + $this->flush(); + } + + public function buildNamespace($namespace) { + $this->startElement('namespace'); + $this->writeAttribute('id', $namespace->namespace); + + $this->writeElement('name', $namespace->namespace); + $this->startElement('description'); + $this->writeHTMLDiv($namespace->description); + $this->endElement(); // description + + foreach ($this->interchange->directives as $directive) { + if ($directive->id->namespace !== $namespace->namespace) continue; + $this->buildDirective($directive); + } + + $this->endElement(); // namespace + } + + public function buildDirective($directive) { + $this->startElement('directive'); + $this->writeAttribute('id', $directive->id->toString()); + + $this->writeElement('name', $directive->id->directive); + + $this->startElement('aliases'); + foreach ($directive->aliases as $alias) $this->writeElement('alias', $alias->toString()); + $this->endElement(); // aliases + + $this->startElement('constraints'); + if ($directive->version) $this->writeElement('version', $directive->version); + $this->startElement('type'); + if ($directive->typeAllowsNull) $this->writeAttribute('allow-null', 'yes'); + $this->text($directive->type); + $this->endElement(); // type + if ($directive->allowed) { + $this->startElement('allowed'); + foreach ($directive->allowed as $value => $x) $this->writeElement('value', $value); + $this->endElement(); // allowed + } + $this->writeElement('default', $this->export($directive->default)); + $this->writeAttribute('xml:space', 'preserve'); + if ($directive->external) { + $this->startElement('external'); + foreach ($directive->external as $project) $this->writeElement('project', $project); + $this->endElement(); + } + $this->endElement(); // constraints + + if ($directive->deprecatedVersion) { + $this->startElement('deprecated'); + $this->writeElement('version', $directive->deprecatedVersion); + $this->writeElement('use', $directive->deprecatedUse->toString()); + $this->endElement(); // deprecated + } + + $this->startElement('description'); + $this->writeHTMLDiv($directive->description); + $this->endElement(); // description + + $this->endElement(); // directive + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Exception.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Exception.php new file mode 100644 index 0000000000..4c51d67013 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Exception.php @@ -0,0 +1,9 @@ + array(namespace info) + */ + public $namespaces = array(); + + /** + * Array of Directive ID => array(directive info) + */ + public $directives = array(); + + /** + * Adds a namespace array to $namespaces + */ + public function addNamespace($namespace) { + if (isset($this->namespaces[$i = $namespace->namespace])) { + throw new HTMLPurifier_ConfigSchema_Exception("Cannot redefine namespace '$i'"); + } + $this->namespaces[$i] = $namespace; + } + + /** + * Adds a directive array to $directives + */ + public function addDirective($directive) { + if (isset($this->directives[$i = $directive->id->toString()])) { + throw new HTMLPurifier_ConfigSchema_Exception("Cannot redefine directive '$i'"); + } + $this->directives[$i] = $directive; + } + + /** + * Convenience function to perform standard validation. Throws exception + * on failed validation. + */ + public function validate() { + $validator = new HTMLPurifier_ConfigSchema_Validator(); + return $validator->validate($this); + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Directive.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Directive.php new file mode 100644 index 0000000000..5c8c4797eb --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Directive.php @@ -0,0 +1,75 @@ + true). + * Null if all values are allowed. + */ + public $allowed; + + /** + * List of aliases for the directive, + * e.g. array(new HTMLPurifier_ConfigSchema_Interchange_Id('Ns', 'Dir'))). + */ + public $aliases = array(); + + /** + * Hash of value aliases, e.g. array('alt' => 'real'). Null if value + * aliasing is disabled (necessary for non-scalar types). + */ + public $valueAliases; + + /** + * Version of HTML Purifier the directive was introduced, e.g. '1.3.1'. + * Null if the directive has always existed. + */ + public $version; + + /** + * ID of directive that supercedes this old directive, is an instance + * of HTMLPurifier_ConfigSchema_Interchange_Id. Null if not deprecated. + */ + public $deprecatedUse; + + /** + * Version of HTML Purifier this directive was deprecated. Null if not + * deprecated. + */ + public $deprecatedVersion; + + /** + * List of external projects this directive depends on, e.g. array('CSSTidy'). + */ + public $external = array(); + +} diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Id.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Id.php new file mode 100644 index 0000000000..40a5fe3cc5 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Id.php @@ -0,0 +1,29 @@ +namespace = $namespace; + $this->directive = $directive; + } + + /** + * @warning This is NOT magic, to ensure that people don't abuse SPL and + * cause problems for PHP 5.0 support. + */ + public function toString() { + return $this->namespace . '.' . $this->directive; + } + + public static function make($id) { + list($namespace, $directive) = explode('.', $id); + return new HTMLPurifier_ConfigSchema_Interchange_Id($namespace, $directive); + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Namespace.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Namespace.php new file mode 100644 index 0000000000..8fe8158191 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Interchange/Namespace.php @@ -0,0 +1,19 @@ +varParser = $varParser ? $varParser : new HTMLPurifier_VarParser_Native(); + } + + public static function buildFromDirectory($dir = null) { + $parser = new HTMLPurifier_StringHashParser(); + $builder = new HTMLPurifier_ConfigSchema_InterchangeBuilder(); + $interchange = new HTMLPurifier_ConfigSchema_Interchange(); + + if (!$dir) $dir = HTMLPURIFIER_PREFIX . '/HTMLPurifier/ConfigSchema/schema/'; + $info = parse_ini_file($dir . 'info.ini'); + $interchange->name = $info['name']; + + $files = array(); + $dh = opendir($dir); + while (false !== ($file = readdir($dh))) { + if (!$file || $file[0] == '.' || strrchr($file, '.') !== '.txt') { + continue; + } + $files[] = $file; + } + closedir($dh); + + sort($files); + foreach ($files as $file) { + $builder->build( + $interchange, + new HTMLPurifier_StringHash( $parser->parseFile($dir . $file) ) + ); + } + + return $interchange; + } + + /** + * Builds an interchange object based on a hash. + * @param $interchange HTMLPurifier_ConfigSchema_Interchange object to build + * @param $hash HTMLPurifier_ConfigSchema_StringHash source data + */ + public function build($interchange, $hash) { + if (!$hash instanceof HTMLPurifier_StringHash) { + $hash = new HTMLPurifier_StringHash($hash); + } + if (!isset($hash['ID'])) { + throw new HTMLPurifier_ConfigSchema_Exception('Hash does not have any ID'); + } + if (strpos($hash['ID'], '.') === false) { + $this->buildNamespace($interchange, $hash); + } else { + $this->buildDirective($interchange, $hash); + } + $this->_findUnused($hash); + } + + public function buildNamespace($interchange, $hash) { + $namespace = new HTMLPurifier_ConfigSchema_Interchange_Namespace(); + $namespace->namespace = $hash->offsetGet('ID'); + if (isset($hash['DESCRIPTION'])) { + $namespace->description = $hash->offsetGet('DESCRIPTION'); + } + $interchange->addNamespace($namespace); + } + + public function buildDirective($interchange, $hash) { + $directive = new HTMLPurifier_ConfigSchema_Interchange_Directive(); + + // These are required elements: + $directive->id = $this->id($hash->offsetGet('ID')); + $id = $directive->id->toString(); // convenience + + if (isset($hash['TYPE'])) { + $type = explode('/', $hash->offsetGet('TYPE')); + if (isset($type[1])) $directive->typeAllowsNull = true; + $directive->type = $type[0]; + } else { + throw new HTMLPurifier_ConfigSchema_Exception("TYPE in directive hash '$id' not defined"); + } + + if (isset($hash['DEFAULT'])) { + try { + $directive->default = $this->varParser->parse($hash->offsetGet('DEFAULT'), $directive->type, $directive->typeAllowsNull); + } catch (HTMLPurifier_VarParserException $e) { + throw new HTMLPurifier_ConfigSchema_Exception($e->getMessage() . " in DEFAULT in directive hash '$id'"); + } + } + + if (isset($hash['DESCRIPTION'])) { + $directive->description = $hash->offsetGet('DESCRIPTION'); + } + + if (isset($hash['ALLOWED'])) { + $directive->allowed = $this->lookup($this->evalArray($hash->offsetGet('ALLOWED'))); + } + + if (isset($hash['VALUE-ALIASES'])) { + $directive->valueAliases = $this->evalArray($hash->offsetGet('VALUE-ALIASES')); + } + + if (isset($hash['ALIASES'])) { + $raw_aliases = trim($hash->offsetGet('ALIASES')); + $aliases = preg_split('/\s*,\s*/', $raw_aliases); + foreach ($aliases as $alias) { + $directive->aliases[] = $this->id($alias); + } + } + + if (isset($hash['VERSION'])) { + $directive->version = $hash->offsetGet('VERSION'); + } + + if (isset($hash['DEPRECATED-USE'])) { + $directive->deprecatedUse = $this->id($hash->offsetGet('DEPRECATED-USE')); + } + + if (isset($hash['DEPRECATED-VERSION'])) { + $directive->deprecatedVersion = $hash->offsetGet('DEPRECATED-VERSION'); + } + + if (isset($hash['EXTERNAL'])) { + $directive->external = preg_split('/\s*,\s*/', trim($hash->offsetGet('EXTERNAL'))); + } + + $interchange->addDirective($directive); + } + + /** + * Evaluates an array PHP code string without array() wrapper + */ + protected function evalArray($contents) { + return eval('return array('. $contents .');'); + } + + /** + * Converts an array list into a lookup array. + */ + protected function lookup($array) { + $ret = array(); + foreach ($array as $val) $ret[$val] = true; + return $ret; + } + + /** + * Convenience function that creates an HTMLPurifier_ConfigSchema_Interchange_Id + * object based on a string Id. + */ + protected function id($id) { + return HTMLPurifier_ConfigSchema_Interchange_Id::make($id); + } + + /** + * Triggers errors for any unused keys passed in the hash; such keys + * may indicate typos, missing values, etc. + * @param $hash Instance of ConfigSchema_StringHash to check. + */ + protected function _findUnused($hash) { + $accessed = $hash->getAccessed(); + foreach ($hash as $k => $v) { + if (!isset($accessed[$k])) { + trigger_error("String hash key '$k' not used by builder", E_USER_NOTICE); + } + } + } + +} + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Validator.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Validator.php new file mode 100644 index 0000000000..e36ef8f130 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/Validator.php @@ -0,0 +1,222 @@ +parser = new HTMLPurifier_VarParser(); + } + + /** + * Validates a fully-formed interchange object. Throws an + * HTMLPurifier_ConfigSchema_Exception if there's a problem. + */ + public function validate($interchange) { + $this->interchange = $interchange; + $this->aliases = array(); + // PHP is a bit lax with integer <=> string conversions in + // arrays, so we don't use the identical !== comparison + foreach ($interchange->namespaces as $i => $namespace) { + if ($i != $namespace->namespace) $this->error(false, "Integrity violation: key '$i' does not match internal id '{$namespace->namespace}'"); + $this->validateNamespace($namespace); + } + foreach ($interchange->directives as $i => $directive) { + $id = $directive->id->toString(); + if ($i != $id) $this->error(false, "Integrity violation: key '$i' does not match internal id '$id'"); + $this->validateDirective($directive); + } + return true; + } + + /** + * Validates a HTMLPurifier_ConfigSchema_Interchange_Namespace object. + */ + public function validateNamespace($n) { + $this->context[] = "namespace '{$n->namespace}'"; + $this->with($n, 'namespace') + ->assertNotEmpty() + ->assertAlnum(); // implicit assertIsString handled by InterchangeBuilder + $this->with($n, 'description') + ->assertNotEmpty() + ->assertIsString(); // handled by InterchangeBuilder + array_pop($this->context); + } + + /** + * Validates a HTMLPurifier_ConfigSchema_Interchange_Id object. + */ + public function validateId($id) { + $id_string = $id->toString(); + $this->context[] = "id '$id_string'"; + if (!$id instanceof HTMLPurifier_ConfigSchema_Interchange_Id) { + // handled by InterchangeBuilder + $this->error(false, 'is not an instance of HTMLPurifier_ConfigSchema_Interchange_Id'); + } + if (!isset($this->interchange->namespaces[$id->namespace])) { + $this->error('namespace', 'does not exist'); // assumes that the namespace was validated already + } + $this->with($id, 'directive') + ->assertNotEmpty() + ->assertAlnum(); // implicit assertIsString handled by InterchangeBuilder + array_pop($this->context); + } + + /** + * Validates a HTMLPurifier_ConfigSchema_Interchange_Directive object. + */ + public function validateDirective($d) { + $id = $d->id->toString(); + $this->context[] = "directive '$id'"; + $this->validateId($d->id); + + $this->with($d, 'description') + ->assertNotEmpty(); + + // BEGIN - handled by InterchangeBuilder + $this->with($d, 'type') + ->assertNotEmpty(); + $this->with($d, 'typeAllowsNull') + ->assertIsBool(); + try { + // This also tests validity of $d->type + $this->parser->parse($d->default, $d->type, $d->typeAllowsNull); + } catch (HTMLPurifier_VarParserException $e) { + $this->error('default', 'had error: ' . $e->getMessage()); + } + // END - handled by InterchangeBuilder + + if (!is_null($d->allowed) || !empty($d->valueAliases)) { + // allowed and valueAliases require that we be dealing with + // strings, so check for that early. + if (!isset(HTMLPurifier_VarParser::$stringTypes[$d->type])) { + $this->error('type', 'must be a string type when used with allowed or value aliases'); + } + } + + $this->validateDirectiveAllowed($d); + $this->validateDirectiveValueAliases($d); + $this->validateDirectiveAliases($d); + + array_pop($this->context); + } + + /** + * Extra validation if $allowed member variable of + * HTMLPurifier_ConfigSchema_Interchange_Directive is defined. + */ + public function validateDirectiveAllowed($d) { + if (is_null($d->allowed)) return; + $this->with($d, 'allowed') + ->assertNotEmpty() + ->assertIsLookup(); // handled by InterchangeBuilder + if (is_string($d->default) && !isset($d->allowed[$d->default])) { + $this->error('default', 'must be an allowed value'); + } + $this->context[] = 'allowed'; + foreach ($d->allowed as $val => $x) { + if (!is_string($val)) $this->error("value $val", 'must be a string'); + } + array_pop($this->context); + } + + /** + * Extra validation if $valueAliases member variable of + * HTMLPurifier_ConfigSchema_Interchange_Directive is defined. + */ + public function validateDirectiveValueAliases($d) { + if (is_null($d->valueAliases)) return; + $this->with($d, 'valueAliases') + ->assertIsArray(); // handled by InterchangeBuilder + $this->context[] = 'valueAliases'; + foreach ($d->valueAliases as $alias => $real) { + if (!is_string($alias)) $this->error("alias $alias", 'must be a string'); + if (!is_string($real)) $this->error("alias target $real from alias '$alias'", 'must be a string'); + if ($alias === $real) { + $this->error("alias '$alias'", "must not be an alias to itself"); + } + } + if (!is_null($d->allowed)) { + foreach ($d->valueAliases as $alias => $real) { + if (isset($d->allowed[$alias])) { + $this->error("alias '$alias'", 'must not be an allowed value'); + } elseif (!isset($d->allowed[$real])) { + $this->error("alias '$alias'", 'must be an alias to an allowed value'); + } + } + } + array_pop($this->context); + } + + /** + * Extra validation if $aliases member variable of + * HTMLPurifier_ConfigSchema_Interchange_Directive is defined. + */ + public function validateDirectiveAliases($d) { + $this->with($d, 'aliases') + ->assertIsArray(); // handled by InterchangeBuilder + $this->context[] = 'aliases'; + foreach ($d->aliases as $alias) { + $this->validateId($alias); + $s = $alias->toString(); + if (isset($this->interchange->directives[$s])) { + $this->error("alias '$s'", 'collides with another directive'); + } + if (isset($this->aliases[$s])) { + $other_directive = $this->aliases[$s]; + $this->error("alias '$s'", "collides with alias for directive '$other_directive'"); + } + $this->aliases[$s] = $d->id->toString(); + } + array_pop($this->context); + } + + // protected helper functions + + /** + * Convenience function for generating HTMLPurifier_ConfigSchema_ValidatorAtom + * for validating simple member variables of objects. + */ + protected function with($obj, $member) { + return new HTMLPurifier_ConfigSchema_ValidatorAtom($this->getFormattedContext(), $obj, $member); + } + + /** + * Emits an error, providing helpful context. + */ + protected function error($target, $msg) { + if ($target !== false) $prefix = ucfirst($target) . ' in ' . $this->getFormattedContext(); + else $prefix = ucfirst($this->getFormattedContext()); + throw new HTMLPurifier_ConfigSchema_Exception(trim($prefix . ' ' . $msg)); + } + + /** + * Returns a formatted context string. + */ + protected function getFormattedContext() { + return implode(' in ', array_reverse($this->context)); + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/ValidatorAtom.php b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/ValidatorAtom.php new file mode 100644 index 0000000000..2bb9967611 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/ValidatorAtom.php @@ -0,0 +1,66 @@ +context = $context; + $this->obj = $obj; + $this->member = $member; + $this->contents =& $obj->$member; + } + + public function assertIsString() { + if (!is_string($this->contents)) $this->error('must be a string'); + return $this; + } + + public function assertIsBool() { + if (!is_bool($this->contents)) $this->error('must be a boolean'); + return $this; + } + + public function assertIsArray() { + if (!is_array($this->contents)) $this->error('must be an array'); + return $this; + } + + public function assertNotNull() { + if ($this->contents === null) $this->error('must not be null'); + return $this; + } + + public function assertAlnum() { + $this->assertIsString(); + if (!ctype_alnum($this->contents)) $this->error('must be alphanumeric'); + return $this; + } + + public function assertNotEmpty() { + if (empty($this->contents)) $this->error('must not be empty'); + return $this; + } + + public function assertIsLookup() { + $this->assertIsArray(); + foreach ($this->contents as $v) { + if ($v !== true) $this->error('must be a lookup array'); + } + return $this; + } + + protected function error($msg) { + throw new HTMLPurifier_ConfigSchema_Exception(ucfirst($this->member) . ' in ' . $this->context . ' ' . $msg); + } + +} + + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema.ser b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema.ser new file mode 100644 index 0000000000..619cf532bf --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema.ser @@ -0,0 +1 @@ +O:25:"HTMLPurifier_ConfigSchema":3:{s:8:"defaults";a:12:{s:4:"Attr";a:11:{s:19:"AllowedFrameTargets";a:0:{}s:10:"AllowedRel";a:0:{}s:10:"AllowedRev";a:0:{}s:19:"DefaultInvalidImage";s:0:"";s:22:"DefaultInvalidImageAlt";s:13:"Invalid image";s:14:"DefaultTextDir";s:3:"ltr";s:8:"EnableID";b:0;s:11:"IDBlacklist";a:0:{}s:17:"IDBlacklistRegexp";N;s:8:"IDPrefix";s:0:"";s:13:"IDPrefixLocal";s:0:"";}s:10:"AutoFormat";a:4:{s:13:"AutoParagraph";b:0;s:6:"Custom";a:0:{}s:7:"Linkify";b:0;s:15:"PurifierLinkify";b:0;}s:15:"AutoFormatParam";a:1:{s:21:"PurifierLinkifyDocURL";s:3:"#%s";}s:3:"CSS";a:5:{s:14:"AllowImportant";b:0;s:11:"AllowTricky";b:0;s:17:"AllowedProperties";N;s:13:"DefinitionRev";i:1;s:11:"Proprietary";b:0;}s:5:"Cache";a:2:{s:14:"DefinitionImpl";s:10:"Serializer";s:14:"SerializerPath";N;}s:4:"Core";a:15:{s:17:"AggressivelyFixLt";b:0;s:13:"CollectErrors";b:0;s:13:"ColorKeywords";a:17:{s:6:"maroon";s:7:"#800000";s:3:"red";s:7:"#FF0000";s:6:"orange";s:7:"#FFA500";s:6:"yellow";s:7:"#FFFF00";s:5:"olive";s:7:"#808000";s:6:"purple";s:7:"#800080";s:7:"fuchsia";s:7:"#FF00FF";s:5:"white";s:7:"#FFFFFF";s:4:"lime";s:7:"#00FF00";s:5:"green";s:7:"#008000";s:4:"navy";s:7:"#000080";s:4:"blue";s:7:"#0000FF";s:4:"aqua";s:7:"#00FFFF";s:4:"teal";s:7:"#008080";s:5:"black";s:7:"#000000";s:6:"silver";s:7:"#C0C0C0";s:4:"gray";s:7:"#808080";}s:25:"ConvertDocumentToFragment";b:1;s:31:"DirectLexLineNumberSyncInterval";i:0;s:8:"Encoding";s:5:"utf-8";s:21:"EscapeInvalidChildren";b:0;s:17:"EscapeInvalidTags";b:0;s:24:"EscapeNonASCIICharacters";b:0;s:14:"HiddenElements";a:2:{s:6:"script";b:1;s:5:"style";b:1;}s:8:"Language";s:2:"en";s:9:"LexerImpl";N;s:19:"MaintainLineNumbers";N;s:16:"RemoveInvalidImg";b:1;s:20:"RemoveScriptContents";N;}s:6:"Filter";a:3:{s:6:"Custom";a:0:{}s:18:"ExtractStyleBlocks";b:0;s:7:"YouTube";b:0;}s:11:"FilterParam";a:3:{s:26:"ExtractStyleBlocksEscaping";b:1;s:23:"ExtractStyleBlocksScope";N;s:26:"ExtractStyleBlocksTidyImpl";N;}s:4:"HTML";a:20:{s:7:"Allowed";N;s:17:"AllowedAttributes";N;s:15:"AllowedElements";N;s:14:"AllowedModules";N;s:12:"BlockWrapper";s:1:"p";s:11:"CoreModules";a:7:{s:9:"Structure";b:1;s:4:"Text";b:1;s:9:"Hypertext";b:1;s:4:"List";b:1;s:22:"NonXMLCommonAttributes";b:1;s:19:"XMLCommonAttributes";b:1;s:16:"CommonAttributes";b:1;}s:13:"CustomDoctype";N;s:12:"DefinitionID";N;s:13:"DefinitionRev";i:1;s:7:"Doctype";N;s:19:"ForbiddenAttributes";a:0:{}s:17:"ForbiddenElements";a:0:{}s:6:"Parent";s:3:"div";s:11:"Proprietary";b:0;s:6:"Strict";b:0;s:7:"TidyAdd";a:0:{}s:9:"TidyLevel";s:6:"medium";s:10:"TidyRemove";a:0:{}s:7:"Trusted";b:0;s:5:"XHTML";b:1;}s:6:"Output";a:3:{s:21:"CommentScriptContents";b:1;s:7:"Newline";N;s:10:"TidyFormat";b:0;}s:4:"Test";a:1:{s:12:"ForceNoIconv";b:0;}s:3:"URI";a:14:{s:14:"AllowedSchemes";a:6:{s:4:"http";b:1;s:5:"https";b:1;s:6:"mailto";b:1;s:3:"ftp";b:1;s:4:"nntp";b:1;s:4:"news";b:1;}s:4:"Base";N;s:13:"DefaultScheme";s:4:"http";s:12:"DefinitionID";N;s:13:"DefinitionRev";i:1;s:7:"Disable";b:0;s:15:"DisableExternal";b:0;s:24:"DisableExternalResources";b:0;s:16:"DisableResources";b:0;s:4:"Host";N;s:13:"HostBlacklist";a:0:{}s:12:"MakeAbsolute";b:0;s:5:"Munge";N;s:22:"OverrideAllowedSchemes";b:1;}}s:4:"info";a:12:{s:4:"Attr";a:12:{s:19:"AllowedFrameTargets";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:10:"AllowedRel";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:10:"AllowedRev";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:19:"DefaultInvalidImage";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:22:"DefaultInvalidImageAlt";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:14:"DefaultTextDir";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";a:2:{s:3:"ltr";b:1;s:3:"rtl";b:1;}s:7:"aliases";a:0:{}}s:8:"EnableID";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:11:"IDBlacklist";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"list";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:17:"IDBlacklistRegexp";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:8:"IDPrefix";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"IDPrefixLocal";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:10:"DisableURI";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:3:"URI";s:4:"name";s:7:"Disable";}}s:10:"AutoFormat";a:4:{s:13:"AutoParagraph";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:6:"Custom";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"list";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"Linkify";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:15:"PurifierLinkify";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:15:"AutoFormatParam";a:1:{s:21:"PurifierLinkifyDocURL";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:3:"CSS";a:5:{s:14:"AllowImportant";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:11:"AllowTricky";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:17:"AllowedProperties";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"DefinitionRev";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:3:"int";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:11:"Proprietary";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:5:"Cache";a:2:{s:14:"DefinitionImpl";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:14:"SerializerPath";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:4:"Core";a:20:{s:15:"DefinitionCache";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:5:"Cache";s:4:"name";s:14:"DefinitionImpl";}s:17:"AggressivelyFixLt";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"CollectErrors";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"ColorKeywords";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"hash";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:25:"ConvertDocumentToFragment";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:19:"AcceptFullDocuments";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:4:"Core";s:4:"name";s:25:"ConvertDocumentToFragment";}s:31:"DirectLexLineNumberSyncInterval";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:3:"int";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:8:"Encoding";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:7:"istring";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:21:"EscapeInvalidChildren";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:17:"EscapeInvalidTags";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:24:"EscapeNonASCIICharacters";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:14:"HiddenElements";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:8:"Language";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:9:"LexerImpl";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:5:"mixed";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:19:"MaintainLineNumbers";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:16:"RemoveInvalidImg";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:20:"RemoveScriptContents";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:5:"XHTML";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:4:"HTML";s:4:"name";s:5:"XHTML";}s:21:"CommentScriptContents";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:6:"Output";s:4:"name";s:21:"CommentScriptContents";}s:10:"TidyFormat";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:6:"Output";s:4:"name";s:10:"TidyFormat";}}s:6:"Filter";a:5:{s:6:"Custom";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"list";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:18:"ExtractStyleBlocks";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"YouTube";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:26:"ExtractStyleBlocksEscaping";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:11:"FilterParam";s:4:"name";s:26:"ExtractStyleBlocksEscaping";}s:23:"ExtractStyleBlocksScope";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:11:"FilterParam";s:4:"name";s:23:"ExtractStyleBlocksScope";}}s:11:"FilterParam";a:3:{s:26:"ExtractStyleBlocksEscaping";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:23:"ExtractStyleBlocksScope";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:26:"ExtractStyleBlocksTidyImpl";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:5:"mixed";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:4:"HTML";a:21:{s:12:"EnableAttrID";O:37:"HTMLPurifier_ConfigDef_DirectiveAlias":3:{s:5:"class";s:5:"alias";s:9:"namespace";s:4:"Attr";s:4:"name";s:8:"EnableID";}s:7:"Allowed";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:5:"itext";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:17:"AllowedAttributes";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:15:"AllowedElements";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:14:"AllowedModules";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:12:"BlockWrapper";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:11:"CoreModules";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"CustomDoctype";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:12:"DefinitionID";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"DefinitionRev";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:3:"int";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"Doctype";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";a:5:{s:22:"HTML 4.01 Transitional";b:1;s:16:"HTML 4.01 Strict";b:1;s:22:"XHTML 1.0 Transitional";b:1;s:16:"XHTML 1.0 Strict";b:1;s:9:"XHTML 1.1";b:1;}s:7:"aliases";a:0:{}}s:19:"ForbiddenAttributes";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:17:"ForbiddenElements";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:6:"Parent";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:11:"Proprietary";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:6:"Strict";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"TidyAdd";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:9:"TidyLevel";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";a:4:{s:4:"none";b:1;s:5:"light";b:1;s:6:"medium";b:1;s:5:"heavy";b:1;}s:7:"aliases";a:0:{}}s:10:"TidyRemove";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"Trusted";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:5:"XHTML";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:6:"Output";a:3:{s:21:"CommentScriptContents";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"Newline";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:10:"TidyFormat";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:4:"Test";a:1:{s:12:"ForceNoIconv";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}s:3:"URI";a:14:{s:14:"AllowedSchemes";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"lookup";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:4:"Base";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"DefaultScheme";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:12:"DefinitionID";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"DefinitionRev";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:3:"int";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:7:"Disable";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:15:"DisableExternal";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:24:"DisableExternalResources";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:16:"DisableResources";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:4:"Host";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:13:"HostBlacklist";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"list";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:12:"MakeAbsolute";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:5:"Munge";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:6:"string";s:10:"allow_null";b:1;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}s:22:"OverrideAllowedSchemes";O:32:"HTMLPurifier_ConfigDef_Directive":5:{s:5:"class";s:9:"directive";s:4:"type";s:4:"bool";s:10:"allow_null";b:0;s:7:"allowed";b:1;s:7:"aliases";a:0:{}}}}s:9:"*parser";O:31:"HTMLPurifier_VarParser_Flexible":0:{}} \ No newline at end of file diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt new file mode 100644 index 0000000000..6cecfa2f00 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedFrameTargets.txt @@ -0,0 +1,11 @@ +Attr.AllowedFrameTargets +TYPE: lookup +DEFAULT: array() +--DESCRIPTION-- +Lookup table of all allowed link frame targets. Some commonly used link +targets include _blank, _self, _parent and _top. Values should be +lowercase, as validation will be done in a case-sensitive manner despite +W3C's recommendation. XHTML 1.0 Strict does not permit the target attribute +so this directive will have no effect in that doctype. XHTML 1.1 does not +enable the Target module by default, you will have to manually enable it +(see the module documentation for more details.) diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt new file mode 100644 index 0000000000..26bbc37130 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRel.txt @@ -0,0 +1,8 @@ +Attr.AllowedRel +TYPE: lookup +VERSION: 1.6.0 +DEFAULT: array() +--DESCRIPTION-- +List of allowed forward document relationships in the rel attribute. Common +values may be nofollow or print. By default, this is empty, meaning that no +document relationships are allowed. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt new file mode 100644 index 0000000000..b007bc58ac --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.AllowedRev.txt @@ -0,0 +1,8 @@ +Attr.AllowedRev +TYPE: lookup +VERSION: 1.6.0 +DEFAULT: array() +--DESCRIPTION-- +List of allowed reverse document relationships in the rev attribute. This +attribute is a bit of an edge-case; if you don't know what it is for, stay +away. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt new file mode 100644 index 0000000000..3d5c45d4ff --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImage.txt @@ -0,0 +1,8 @@ +Attr.DefaultInvalidImage +TYPE: string +DEFAULT: '' +--DESCRIPTION-- +This is the default image an img tag will be pointed to if it does not have +a valid src attribute. In future versions, we may allow the image tag to +be removed completely, but due to design issues, this is not possible right +now. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt new file mode 100644 index 0000000000..cfc9f904be --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultInvalidImageAlt.txt @@ -0,0 +1,7 @@ +Attr.DefaultInvalidImageAlt +TYPE: string +DEFAULT: 'Invalid image' +--DESCRIPTION-- +This is the content of the alt tag of an invalid image if the user had not +previously specified an alt attribute. It has no effect when the image is +valid but there was no alt attribute present. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt new file mode 100644 index 0000000000..80296fccf4 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.DefaultTextDir.txt @@ -0,0 +1,9 @@ +Attr.DefaultTextDir +TYPE: string +DEFAULT: 'ltr' +--DESCRIPTION-- +Defines the default text direction (ltr or rtl) of the document being +parsed. This generally is the same as the value of the dir attribute in +HTML, or ltr if that is not specified. +--ALLOWED-- +'ltr', 'rtl' diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt new file mode 100644 index 0000000000..358d6d07a6 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.EnableID.txt @@ -0,0 +1,15 @@ +Attr.EnableID +TYPE: bool +DEFAULT: false +VERSION: 1.2.0 +--DESCRIPTION-- +Allows the ID attribute in HTML. This is disabled by default due to the +fact that without proper configuration user input can easily break the +validation of a webpage by specifying an ID that is already on the +surrounding HTML. If you don't mind throwing caution to the wind, enable +this directive, but I strongly recommend you also consider blacklisting IDs +you use (%Attr.IDBlacklist) or prefixing all user supplied IDs +(%Attr.IDPrefix). When set to true HTML Purifier reverts to the behavior of +pre-1.2.0 versions. +--ALIASES-- +HTML.EnableAttrID diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt new file mode 100644 index 0000000000..16fc46e16b --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklist.txt @@ -0,0 +1,4 @@ +Attr.IDBlacklist +TYPE: list +DEFAULT: array() +DESCRIPTION: Array of IDs not allowed in the document. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt new file mode 100644 index 0000000000..98f7c5a632 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDBlacklistRegexp.txt @@ -0,0 +1,8 @@ +Attr.IDBlacklistRegexp +TYPE: string/null +VERSION: 1.6.0 +DEFAULT: NULL +--DESCRIPTION-- +PCRE regular expression to be matched against all IDs. If the expression is +matches, the ID is rejected. Use this with care: may cause significant +degradation. ID matching is done after all other validation. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt new file mode 100644 index 0000000000..f996c08436 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefix.txt @@ -0,0 +1,11 @@ +Attr.IDPrefix +TYPE: string +VERSION: 1.2.0 +DEFAULT: '' +--DESCRIPTION-- +String to prefix to IDs. If you have no idea what IDs your pages may use, +you may opt to simply add a prefix to all user-submitted ID attributes so +that they are still usable, but will not conflict with core page IDs. +Example: setting the directive to 'user_' will result in a user submitted +'foo' to become 'user_foo' Be sure to set %HTML.EnableAttrID to true +before using this. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt new file mode 100644 index 0000000000..b403fa9cd2 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.IDPrefixLocal.txt @@ -0,0 +1,13 @@ +Attr.IDPrefixLocal +TYPE: string +VERSION: 1.2.0 +DEFAULT: '' +--DESCRIPTION-- +Temporary prefix for IDs used in conjunction with %Attr.IDPrefix. If you +need to allow multiple sets of user content on web page, you may need to +have a seperate prefix that changes with each iteration. This way, +seperately submitted user content displayed on the same page doesn't +clobber each other. Ideal values are unique identifiers for the content it +represents (i.e. the id of the row in the database). Be sure to add a +seperator (like an underscore) at the end. Warning: this directive will +not work unless %Attr.IDPrefix is set to a non-empty value! diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.txt new file mode 100644 index 0000000000..fb18894fe9 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Attr.txt @@ -0,0 +1,2 @@ +Attr +DESCRIPTION: Features regarding attribute validation. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt new file mode 100644 index 0000000000..e1f7a475ec --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.AutoParagraph.txt @@ -0,0 +1,30 @@ +AutoFormat.AutoParagraph +TYPE: bool +VERSION: 2.0.1 +DEFAULT: false +--DESCRIPTION-- + +

+ This directive turns on auto-paragraphing, where double newlines are + converted in to paragraphs whenever possible. Auto-paragraphing: +

+ +

+ p tags must be allowed for this directive to take effect. + We do not use br tags for paragraphing, as that is + semantically incorrect. +

+

+ To prevent auto-paragraphing as a content-producer, refrain from using + double-newlines except to specify a new paragraph or in contexts where + it has special meaning (whitespace usually has no meaning except in + tags like pre, so this should not be difficult.) To prevent + the paragraphing of inline text adjacent to block elements, wrap them + in div tags (the behavior is slightly different outside of + the root node.) +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt new file mode 100644 index 0000000000..c5a363b399 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Custom.txt @@ -0,0 +1,12 @@ +AutoFormat.Custom +TYPE: list +VERSION: 2.0.1 +DEFAULT: array() +--DESCRIPTION-- + +

+ This directive can be used to add custom auto-format injectors. + Specify an array of injector names (class name minus the prefix) + or concrete implementations. Injector class must exist. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt new file mode 100644 index 0000000000..554086f359 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.Linkify.txt @@ -0,0 +1,12 @@ +AutoFormat.Linkify +TYPE: bool +VERSION: 2.0.1 +DEFAULT: false +--DESCRIPTION-- + +

+ This directive turns on linkification, auto-linking http, ftp and + https URLs. a tags with the href attribute + must be allowed. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt new file mode 100644 index 0000000000..c7bcaf283e --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.PurifierLinkify.txt @@ -0,0 +1,12 @@ +AutoFormat.PurifierLinkify +TYPE: bool +VERSION: 2.0.1 +DEFAULT: false +--DESCRIPTION-- + +

+ Internal auto-formatter that converts configuration directives in + syntax %Namespace.Directive to links. a tags + with the href attribute must be allowed. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.txt new file mode 100644 index 0000000000..4a7b5521f7 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormat.txt @@ -0,0 +1,2 @@ +AutoFormat +DESCRIPTION: Configuration for activating auto-formatting functionality (also known as Injectors) diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.PurifierLinkifyDocURL.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.PurifierLinkifyDocURL.txt new file mode 100644 index 0000000000..79d3358061 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.PurifierLinkifyDocURL.txt @@ -0,0 +1,12 @@ +AutoFormatParam.PurifierLinkifyDocURL +TYPE: string +VERSION: 2.0.1 +DEFAULT: '#%s' +--DESCRIPTION-- + +

+ Location of configuration documentation to link to, let %s substitute + into the configuration's namespace and directive names sans the percent + sign. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.txt new file mode 100644 index 0000000000..0ed78846ed --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/AutoFormatParam.txt @@ -0,0 +1,2 @@ +AutoFormatParam +DESCRIPTION: Configuration for customizing auto-formatting functionality diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt new file mode 100644 index 0000000000..68fcde1bc8 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowImportant.txt @@ -0,0 +1,7 @@ +CSS.AllowImportant +TYPE: bool +DEFAULT: false +VERSION: 3.1.0 +--DESCRIPTION-- +This parameter determines whether or not !important cascade modifiers should +be allowed in user CSS. If false, !important will stripped. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt new file mode 100644 index 0000000000..1b4f524b11 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowTricky.txt @@ -0,0 +1,10 @@ +CSS.AllowTricky +TYPE: bool +DEFAULT: false +VERSION: 3.1.0 +--DESCRIPTION-- +This parameter determines whether or not to allow "tricky" CSS properties and +values. Tricky CSS properties/values can drastically modify page layout or +be used for deceptive practices but do not directly constitute a security risk. +For example, display:none; is considered a tricky property that +will only be allowed if this directive is set to true. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt new file mode 100644 index 0000000000..b06689745a --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.AllowedProperties.txt @@ -0,0 +1,17 @@ +CSS.AllowedProperties +TYPE: lookup/null +VERSION: 3.1.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ If HTML Purifier's style attributes set is unsatisfactory for your needs, + you can overload it with your own list of tags to allow. Note that this + method is subtractive: it does its job by taking away from HTML Purifier + usual feature set, so you cannot add an attribute that HTML Purifier never + supported in the first place. +

+

+ Warning: If another directive conflicts with the + elements here, that directive will win and override. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt new file mode 100644 index 0000000000..e1e5992680 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.DefinitionRev.txt @@ -0,0 +1,11 @@ +CSS.DefinitionRev +TYPE: int +VERSION: 2.0.0 +DEFAULT: 1 +--DESCRIPTION-- + +

+ Revision identifier for your custom definition. See + %HTML.DefinitionRev for details. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt new file mode 100644 index 0000000000..c9c068fc39 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.Proprietary.txt @@ -0,0 +1,10 @@ +CSS.Proprietary +TYPE: bool +VERSION: 3.0.0 +DEFAULT: false +--DESCRIPTION-- + +

+ Whether or not to allow safe, proprietary CSS values. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.txt new file mode 100644 index 0000000000..060f5d3715 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/CSS.txt @@ -0,0 +1,2 @@ +CSS +DESCRIPTION: Configuration regarding allowed CSS. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt new file mode 100644 index 0000000000..e9fa699ae8 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.DefinitionImpl.txt @@ -0,0 +1,13 @@ +Cache.DefinitionImpl +TYPE: string/null +VERSION: 2.0.0 +DEFAULT: 'Serializer' +--DESCRIPTION-- + +This directive defines which method to use when caching definitions, +the complex data-type that makes HTML Purifier tick. Set to null +to disable caching (not recommended, as you will see a definite +performance degradation). + +--ALIASES-- +Core.DefinitionCache diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt new file mode 100644 index 0000000000..3682cbb37e --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.SerializerPath.txt @@ -0,0 +1,13 @@ +Cache.SerializerPath +TYPE: string/null +VERSION: 2.0.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ Absolute path with no trailing slash to store serialized definitions in. + Default is within the + HTML Purifier library inside DefinitionCache/Serializer. This + path must be writable by the webserver. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.txt new file mode 100644 index 0000000000..2f7aaa268e --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Cache.txt @@ -0,0 +1,2 @@ +Cache +DESCRIPTION: Configuration for DefinitionCache and related subclasses. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt new file mode 100644 index 0000000000..0d60b89f6b --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.AggressivelyFixLt.txt @@ -0,0 +1,13 @@ +Core.AggressivelyFixLt +TYPE: bool +VERSION: 2.1.0 +DEFAULT: false +--DESCRIPTION-- + +This directive enables aggressive pre-filter fixes HTML Purifier can +perform in order to ensure that open angled-brackets do not get killed +during parsing stage. Enabling this will result in two preg_replace_callback +calls and one preg_replace call for every bit of HTML passed through here. +It is not necessary and will have no effect for PHP 4. + + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt new file mode 100644 index 0000000000..dcf20563d2 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.CollectErrors.txt @@ -0,0 +1,11 @@ +Core.CollectErrors +TYPE: bool +VERSION: 2.0.0 +DEFAULT: false +--DESCRIPTION-- + +Whether or not to collect errors found while filtering the document. This +is a useful way to give feedback to your users. Warning: +Currently this feature is very patchy and experimental, with lots of +possible error messages not yet implemented. It will not cause any +problems, but it may not help your users either. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt new file mode 100644 index 0000000000..28c9682107 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ColorKeywords.txt @@ -0,0 +1,29 @@ +Core.ColorKeywords +TYPE: hash +VERSION: 2.0.0 +--DEFAULT-- +array ( + 'maroon' => '#800000', + 'red' => '#FF0000', + 'orange' => '#FFA500', + 'yellow' => '#FFFF00', + 'olive' => '#808000', + 'purple' => '#800080', + 'fuchsia' => '#FF00FF', + 'white' => '#FFFFFF', + 'lime' => '#00FF00', + 'green' => '#008000', + 'navy' => '#000080', + 'blue' => '#0000FF', + 'aqua' => '#00FFFF', + 'teal' => '#008080', + 'black' => '#000000', + 'silver' => '#C0C0C0', + 'gray' => '#808080', +) +--DESCRIPTION-- + +Lookup array of color names to six digit hexadecimal number corresponding +to color, with preceding hash mark. Used when parsing colors. + + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt new file mode 100644 index 0000000000..0f03d3aada --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.ConvertDocumentToFragment.txt @@ -0,0 +1,13 @@ +Core.ConvertDocumentToFragment +TYPE: bool +DEFAULT: true +--DESCRIPTION-- + +This parameter determines whether or not the filter should convert +input that is a full document with html and body tags to a fragment +of just the contents of a body tag. This parameter is simply something +HTML Purifier can do during an edge-case: for most inputs, this +processing is not necessary. + +--ALIASES-- +Core.AcceptFullDocuments diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt new file mode 100644 index 0000000000..392adb5a18 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.DirectLexLineNumberSyncInterval.txt @@ -0,0 +1,17 @@ +Core.DirectLexLineNumberSyncInterval +TYPE: int +VERSION: 2.0.0 +DEFAULT: 0 +--DESCRIPTION-- + +

+ Specifies the number of tokens the DirectLex line number tracking + implementations should process before attempting to resyncronize the + current line count by manually counting all previous new-lines. When + at 0, this functionality is disabled. Lower values will decrease + performance, and this is only strictly necessary if the counting + algorithm is buggy (in which case you should report it as a bug). + This has no effect when %Core.MaintainLineNumbers is disabled or DirectLex is + not being used. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt new file mode 100644 index 0000000000..9bca95c7c7 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Encoding.txt @@ -0,0 +1,14 @@ +Core.Encoding +TYPE: istring +DEFAULT: 'utf-8' +--DESCRIPTION-- +If for some reason you are unable to convert all webpages to UTF-8, you can +use this directive as a stop-gap compatibility change to let HTML Purifier +deal with non UTF-8 input. This technique has notable deficiencies: +absolutely no characters outside of the selected character encoding will be +preserved, not even the ones that have been ampersand escaped (this is due +to a UTF-8 specific feature that automatically resolves all +entities), making it pretty useless for anything except the most I18N-blind +applications, although %Core.EscapeNonASCIICharacters offers fixes this +trouble with another tradeoff. This directive only accepts ISO-8859-1 if +iconv is not enabled. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt new file mode 100644 index 0000000000..cca96c6018 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidChildren.txt @@ -0,0 +1,9 @@ +Core.EscapeInvalidChildren +TYPE: bool +DEFAULT: false +--DESCRIPTION-- +When true, a child is found that is not allowed in the context of the +parent element will be transformed into text as if it were ASCII. When +false, that element and all internal tags will be dropped, though text will +be preserved. There is no option for dropping the element but preserving +child nodes. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt new file mode 100644 index 0000000000..6e02a19bb4 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeInvalidTags.txt @@ -0,0 +1,6 @@ +Core.EscapeInvalidTags +TYPE: bool +DEFAULT: false +--DESCRIPTION-- +When true, invalid tags will be written back to the document as plain text. +Otherwise, they are silently dropped. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt new file mode 100644 index 0000000000..f8b7d38bfb --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.EscapeNonASCIICharacters.txt @@ -0,0 +1,12 @@ +Core.EscapeNonASCIICharacters +TYPE: bool +VERSION: 1.4.0 +DEFAULT: false +--DESCRIPTION-- +This directive overcomes a deficiency in %Core.Encoding by blindly +converting all non-ASCII characters into decimal numeric entities before +converting it to its native encoding. This means that even characters that +can be expressed in the non-UTF-8 encoding will be entity-ized, which can +be a real downer for encodings like Big5. It also assumes that the ASCII +repetoire is available, although this is the case for almost all encodings. +Anyway, use UTF-8! diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt new file mode 100644 index 0000000000..0a86d96a02 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.HiddenElements.txt @@ -0,0 +1,19 @@ +Core.HiddenElements +TYPE: lookup +--DEFAULT-- +array ( + 'script' => true, + 'style' => true, +) +--DESCRIPTION-- + +

+ This directive is a lookup array of elements which should have their + contents removed when they are not allowed by the HTML definition. + For example, the contents of a script tag are not + normally shown in a document, so if script tags are to be removed, + their contents should be removed to. This is opposed to a b + tag, which defines some presentational changes but does not hide its + contents. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Language.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Language.txt new file mode 100644 index 0000000000..1be60037fc --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.Language.txt @@ -0,0 +1,11 @@ +Core.Language +TYPE: string +VERSION: 2.0.0 +DEFAULT: 'en' +--DESCRIPTION-- + +ISO 639 language code for localizable things in HTML Purifier to use, +which is mainly error reporting. There is currently only an English (en) +translation, so this directive is currently useless. + + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt new file mode 100644 index 0000000000..62125a4710 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.LexerImpl.txt @@ -0,0 +1,33 @@ +Core.LexerImpl +TYPE: mixed/null +VERSION: 2.0.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ This parameter determines what lexer implementation can be used. The + valid values are: +

+
+
null
+
+ Recommended, the lexer implementation will be auto-detected based on + your PHP-version and configuration. +
+
string lexer identifier
+
+ This is a slim way of manually overridding the implementation. + Currently recognized values are: DOMLex (the default PHP5 +implementation) + and DirectLex (the default PHP4 implementation). Only use this if + you know what you are doing: usually, the auto-detection will + manage things for cases you aren't even aware of. +
+
object lexer instance
+
+ Super-advanced: you can specify your own, custom, implementation that + implements the interface defined by HTMLPurifier_Lexer. + I may remove this option simply because I don't expect anyone + to use it. +
+
diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt new file mode 100644 index 0000000000..de10208f85 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.MaintainLineNumbers.txt @@ -0,0 +1,16 @@ +Core.MaintainLineNumbers +TYPE: bool/null +VERSION: 2.0.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ If true, HTML Purifier will add line number information to all tokens. + This is useful when error reporting is turned on, but can result in + significant performance degradation and should not be used when + unnecessary. This directive must be used with the DirectLex lexer, + as the DOMLex lexer does not (yet) support this functionality. + If the value is null, an appropriate value will be selected based + on other configuration. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt new file mode 100644 index 0000000000..7ac86b3169 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveInvalidImg.txt @@ -0,0 +1,12 @@ +Core.RemoveInvalidImg +TYPE: bool +DEFAULT: true +VERSION: 1.3.0 +--DESCRIPTION-- + +

+ This directive enables pre-emptive URI checking in img + tags, as the attribute validation strategy is not authorized to + remove elements from the document. Revert to pre-1.3.0 behavior by setting to false. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt new file mode 100644 index 0000000000..531718ba7b --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.RemoveScriptContents.txt @@ -0,0 +1,11 @@ +Core.RemoveScriptContents +TYPE: bool/null +DEFAULT: NULL +VERSION: 2.0.0 +DEPRECATED-VERSION: 2.1.0 +DEPRECATED-USE: Core.HiddenElements +--DESCRIPTION-- +

+ This directive enables HTML Purifier to remove not only script tags + but all of their contents. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.txt new file mode 100644 index 0000000000..3240014d19 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Core.txt @@ -0,0 +1,2 @@ +Core +DESCRIPTION: Core features that are always available. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt new file mode 100644 index 0000000000..83d9ebc210 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.Custom.txt @@ -0,0 +1,10 @@ +Filter.Custom +TYPE: list +VERSION: 3.1.0 +DEFAULT: array() +--DESCRIPTION-- +

+ This directive can be used to add custom filters; it is nearly the + equivalent of the now deprecated HTMLPurifier->addFilter() + method. Specify an array of concrete implementations. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt new file mode 100644 index 0000000000..36d11e9594 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.ExtractStyleBlocks.txt @@ -0,0 +1,37 @@ +Filter.ExtractStyleBlocks +TYPE: bool +VERSION: 3.1.0 +DEFAULT: false +EXTERNAL: CSSTidy +--DESCRIPTION-- +

+ This directive turns on the style block extraction filter, which removes + style blocks from input HTML, cleans them up with CSSTidy, + and places them in the StyleBlocks context variable, for further + use by you, usually to be placed in an external stylesheet, or a + style block in the head of your document. +

+

+ Sample usage: +

+
set('Filter', 'ExtractStyleBlocks', true);
+$purifier = new HTMLPurifier($config);
+$styles = $purifier->context->get('StyleBlocks');
+foreach ($styles as $style) {
+    echo '\n";
+}]]>
+

+ Warning: It is possible for a user to mount an + imagecrash attack using this CSS. Counter-measures are difficult; + it is not simply enough to limit the range of CSS lengths (using + relative lengths with many nesting levels allows for large values + to be attained without actually specifying them in the stylesheet), + and the flexible nature of selectors makes it difficult to selectively + disable lengths on image tags (HTML Purifier, however, does disable + CSS width and height in inline styling). There are probably two effective + counter measures: an explicit width and height set to auto in all + images in your document (unlikely) or the disabling of width and + height (somewhat reasonable). Whether or not these measures should be + used is left to the reader. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt new file mode 100644 index 0000000000..cbdc0068ca --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.YouTube.txt @@ -0,0 +1,10 @@ +Filter.YouTube +TYPE: bool +VERSION: 3.1.0 +DEFAULT: false +--DESCRIPTION-- +

+ This directive enables YouTube video embedding in HTML Purifier. Check + this document + on embedding videos for more information on what this filter does. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.txt new file mode 100644 index 0000000000..9fad43a8fa --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Filter.txt @@ -0,0 +1,2 @@ +Filter +DESCRIPTION: Directives for turning filters on and off, or specifying custom filters. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksEscaping.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksEscaping.txt new file mode 100644 index 0000000000..d20010c7a6 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksEscaping.txt @@ -0,0 +1,14 @@ +FilterParam.ExtractStyleBlocksEscaping +TYPE: bool +VERSION: 3.0.0 +DEFAULT: true +ALIASES: Filter.ExtractStyleBlocksEscaping +--DESCRIPTION-- + +

+ Whether or not to escape the dangerous characters <, > and & + as \3C, \3E and \26, respectively. This is can be safely set to false + if the contents of StyleBlocks will be placed in an external stylesheet, + where there is no risk of it being interpreted as HTML. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksScope.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksScope.txt new file mode 100644 index 0000000000..ec29078d85 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksScope.txt @@ -0,0 +1,28 @@ +FilterParam.ExtractStyleBlocksScope +TYPE: string/null +VERSION: 3.0.0 +DEFAULT: NULL +ALIASES: Filter.ExtractStyleBlocksScope +--DESCRIPTION-- + +

+ If you would like users to be able to define external stylesheets, but + only allow them to specify CSS declarations for a specific node and + prevent them from fiddling with other elements, use this directive. + It accepts any valid CSS selector, and will prepend this to any + CSS declaration extracted from the document. For example, if this + directive is set to #user-content and a user uses the + selector a:hover, the final selector will be + #user-content a:hover. +

+

+ The comma shorthand may be used; consider the above example, with + #user-content, #user-content2, the final selector will + be #user-content a:hover, #user-content2 a:hover. +

+

+ Warning: It is possible for users to bypass this measure + using a naughty + selector. This is a bug in CSS Tidy 1.3, not HTML + Purifier, and I am working to get it fixed. Until then, HTML Purifier + performs a basic check to prevent this. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksTidyImpl.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksTidyImpl.txt new file mode 100644 index 0000000000..78e69cbb5e --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.ExtractStyleBlocksTidyImpl.txt @@ -0,0 +1,14 @@ +FilterParam.ExtractStyleBlocksTidyImpl +TYPE: mixed/null +VERSION: 3.1.0 +DEFAULT: NULL +--DESCRIPTION-- +

+ If left NULL, HTML Purifier will attempt to instantiate a csstidy + class to use for internal cleaning. This will usually be good enough. +

+

+ However, for trusted user input, you can set this to false to + disable cleaning. In addition, you can supply your own concrete implementation + of Tidy's interface to use, although I don't know why you'd want to do that. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.txt new file mode 100644 index 0000000000..8e2bbe7c3d --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/FilterParam.txt @@ -0,0 +1,2 @@ +FilterParam +DESCRIPTION: Configuration for filters. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt new file mode 100644 index 0000000000..9329eb1544 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Allowed.txt @@ -0,0 +1,22 @@ +HTML.Allowed +TYPE: itext/null +VERSION: 2.0.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ This is a convenience directive that rolls the functionality of + %HTML.AllowedElements and %HTML.AllowedAttributes into one directive. + Specify elements and attributes that are allowed using: + element1[attr1|attr2],element2.... You can also use + newlines instead of commas to separate elements. +

+

+ Warning: + All of the constraints on the component directives are still enforced. + The syntax is a subset of TinyMCE's valid_elements + whitelist: directly copy-pasting it here will probably result in + broken whitelists. If %HTML.AllowedElements or %HTML.AllowedAttributes + are set, this directive has no effect. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt new file mode 100644 index 0000000000..6ff12fc5fa --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedAttributes.txt @@ -0,0 +1,19 @@ +HTML.AllowedAttributes +TYPE: lookup/null +VERSION: 1.3.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ If HTML Purifier's attribute set is unsatisfactory, overload it! + The syntax is "tag.attr" or "*.attr" for the global attributes + (style, id, class, dir, lang, xml:lang). +

+

+ Warning: If another directive conflicts with the + elements here, that directive will win and override. For + example, %HTML.EnableAttrID will take precedence over *.id in this + directive. You must set that directive to true before you can use + IDs at all. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt new file mode 100644 index 0000000000..031a300678 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedElements.txt @@ -0,0 +1,18 @@ +HTML.AllowedElements +TYPE: lookup/null +VERSION: 1.3.0 +DEFAULT: NULL +--DESCRIPTION-- +

+ If HTML Purifier's tag set is unsatisfactory for your needs, you + can overload it with your own list of tags to allow. Note that this + method is subtractive: it does its job by taking away from HTML Purifier + usual feature set, so you cannot add a tag that HTML Purifier never + supported in the first place (like embed, form or head). If you + change this, you probably also want to change %HTML.AllowedAttributes. +

+

+ Warning: If another directive conflicts with the + elements here, that directive will win and override. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt new file mode 100644 index 0000000000..7b8367e1b8 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.AllowedModules.txt @@ -0,0 +1,20 @@ +HTML.AllowedModules +TYPE: lookup/null +VERSION: 2.0.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ A doctype comes with a set of usual modules to use. Without having + to mucking about with the doctypes, you can quickly activate or + disable these modules by specifying which modules you wish to allow + with this directive. This is most useful for unit testing specific + modules, although end users may find it useful for their own ends. +

+

+ If you specify a module that does not exist, the manager will silently + fail to use it, so be careful! User-defined modules are not affected + by this directive. Modules defined in %HTML.CoreModules are not + affected by this directive. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt new file mode 100644 index 0000000000..47fe1433f4 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.BlockWrapper.txt @@ -0,0 +1,18 @@ +HTML.BlockWrapper +TYPE: string +VERSION: 1.3.0 +DEFAULT: 'p' +--DESCRIPTION-- + +

+ String name of element to wrap inline elements that are inside a block + context. This only occurs in the children of blockquote in strict mode. +

+

+ Example: by default value, + <blockquote>Foo</blockquote> would become + <blockquote><p>Foo</p></blockquote>. + The <p> tags can be replaced with whatever you desire, + as long as it is a block level element. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt new file mode 100644 index 0000000000..78bffdbe08 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CoreModules.txt @@ -0,0 +1,23 @@ +HTML.CoreModules +TYPE: lookup +VERSION: 2.0.0 +--DEFAULT-- +array ( + 'Structure' => true, + 'Text' => true, + 'Hypertext' => true, + 'List' => true, + 'NonXMLCommonAttributes' => true, + 'XMLCommonAttributes' => true, + 'CommonAttributes' => true, +) +--DESCRIPTION-- + +

+ Certain modularized doctypes (XHTML, namely), have certain modules + that must be included for the doctype to be an conforming document + type: put those modules here. By default, XHTML's core modules + are used. You can set this to a blank array to disable core module + protection, but this is not recommended. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt new file mode 100644 index 0000000000..4b6d39cfbf --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.CustomDoctype.txt @@ -0,0 +1,10 @@ +HTML.CustomDoctype +TYPE: string/null +VERSION: 2.0.1 +DEFAULT: NULL +--DESCRIPTION-- + +A custom doctype for power-users who defined there own document +type. This directive only applies when %HTML.Doctype is blank. + + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt new file mode 100644 index 0000000000..07f6b67cf9 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionID.txt @@ -0,0 +1,33 @@ +HTML.DefinitionID +TYPE: string/null +DEFAULT: NULL +VERSION: 2.0.0 +--DESCRIPTION-- + +

+ Unique identifier for a custom-built HTML definition. If you edit + the raw version of the HTMLDefinition, introducing changes that the + configuration object does not reflect, you must specify this variable. + If you change your custom edits, you should change this directive, or + clear your cache. Example: +

+
+$config = HTMLPurifier_Config::createDefault();
+$config->set('HTML', 'DefinitionID', '1');
+$def = $config->getHTMLDefinition();
+$def->addAttribute('a', 'tabindex', 'Number');
+
+

+ In the above example, the configuration is still at the defaults, but + using the advanced API, an extra attribute has been added. The + configuration object normally has no way of knowing that this change + has taken place, so it needs an extra directive: %HTML.DefinitionID. + If someone else attempts to use the default configuration, these two + pieces of code will not clobber each other in the cache, since one has + an extra directive attached to it. +

+

+ You must specify a value to this directive to use the + advanced API features. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt new file mode 100644 index 0000000000..dfee8e7741 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.DefinitionRev.txt @@ -0,0 +1,16 @@ +HTML.DefinitionRev +TYPE: int +VERSION: 2.0.0 +DEFAULT: 1 +--DESCRIPTION-- + +

+ Revision identifier for your custom definition specified in + %HTML.DefinitionID. This serves the same purpose: uniquely identifying + your custom definition, but this one does so in a chronological + context: revision 3 is more up-to-date then revision 2. Thus, when + this gets incremented, the cache handling is smart enough to clean + up any older revisions of your definition as well as flush the + cache. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt new file mode 100644 index 0000000000..1c58e2a371 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Doctype.txt @@ -0,0 +1,10 @@ +HTML.Doctype +TYPE: string/null +DEFAULT: NULL +--DESCRIPTION-- +Doctype to use during filtering. Technically speaking this is not actually +a doctype (as it does not identify a corresponding DTD), but we are using +this name for sake of simplicity. When non-blank, this will override any +older directives like %HTML.XHTML or %HTML.Strict. +--ALLOWED-- +'HTML 4.01 Transitional', 'HTML 4.01 Strict', 'XHTML 1.0 Transitional', 'XHTML 1.0 Strict', 'XHTML 1.1' diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt new file mode 100644 index 0000000000..68c49cd616 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenAttributes.txt @@ -0,0 +1,20 @@ +HTML.ForbiddenAttributes +TYPE: lookup +VERSION: 3.1.0 +DEFAULT: array() +--DESCRIPTION-- +

+ While this directive is similar to %HTML.AllowedAttributes, for + forwards-compatibility with XML, this attribute has a different syntax. Instead of + tag.attr, use tag@attr. To disallow href + attributes in a tags, set this directive to + a@href. You can also disallow an attribute globally with + attr or *@attr (either syntax is fine; the latter + is provided for consistency with %HTML.AllowedAttributes). +

+

+ Warning: This directive complements %HTML.ForbiddenElements, + accordingly, check + out that directive for a discussion of why you + should think twice before using this directive. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt new file mode 100644 index 0000000000..1a9c90f4ab --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.ForbiddenElements.txt @@ -0,0 +1,19 @@ +HTML.ForbiddenElements +TYPE: lookup +VERSION: 3.1.0 +DEFAULT: array() +--DESCRIPTION-- +

+ This was, perhaps, the most requested feature ever in HTML + Purifier. Please don't abuse it! This is the logical inverse of + %HTML.AllowedElements, and it will override that directive, or any + other directive. +

+

+ If possible, %HTML.Allowed is recommended over this directive, because it + can sometimes be difficult to tell whether or not you've forbidden all of + the behavior you would like to disallow. If you forbid img + with the expectation of preventing images on your site, you'll be in for + a nasty surprise when people start using the background-image + CSS property. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt new file mode 100644 index 0000000000..0e680f62e9 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Parent.txt @@ -0,0 +1,12 @@ +HTML.Parent +TYPE: string +VERSION: 1.3.0 +DEFAULT: 'div' +--DESCRIPTION-- + +

+ String name of element that HTML fragment passed to library will be + inserted in. An interesting variation would be using span as the + parent element, meaning that only inline tags would be allowed. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt new file mode 100644 index 0000000000..9784c1c42d --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Proprietary.txt @@ -0,0 +1,11 @@ +HTML.Proprietary +TYPE: bool +VERSION: 3.1.0 +DEFAULT: false +--DESCRIPTION-- +

+ Whether or not to allow proprietary elements and attributes in your + documents, as per HTMLPurifier_HTMLModule_Proprietary. + Warning: This can cause your documents to stop + validating! +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt new file mode 100644 index 0000000000..39f8179634 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Strict.txt @@ -0,0 +1,8 @@ +HTML.Strict +TYPE: bool +VERSION: 1.3.0 +DEFAULT: false +DEPRECATED-VERSION: 1.7.0 +DEPRECATED-USE: HTML.Doctype +--DESCRIPTION-- +Determines whether or not to use Transitional (loose) or Strict rulesets. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt new file mode 100644 index 0000000000..7bf3c6d409 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyAdd.txt @@ -0,0 +1,8 @@ +HTML.TidyAdd +TYPE: lookup +VERSION: 2.0.0 +DEFAULT: array() +--DESCRIPTION-- + +Fixes to add to the default set of Tidy fixes as per your level. + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt new file mode 100644 index 0000000000..7b98bc7e93 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyLevel.txt @@ -0,0 +1,23 @@ +HTML.TidyLevel +TYPE: string +VERSION: 2.0.0 +DEFAULT: 'medium' +--DESCRIPTION-- + +

General level of cleanliness the Tidy module should enforce. +There are four allowed values:

+
+
none
+
No extra tidying should be done
+
light
+
Only fix elements that would be discarded otherwise due to + lack of support in doctype
+
medium
+
Enforce best practices
+
heavy
+
Transform all deprecated elements and attributes to standards + compliant equivalents
+
+ +--ALLOWED-- +'none', 'light', 'medium', 'heavy' diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt new file mode 100644 index 0000000000..1e220695e0 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.TidyRemove.txt @@ -0,0 +1,8 @@ +HTML.TidyRemove +TYPE: lookup +VERSION: 2.0.0 +DEFAULT: array() +--DESCRIPTION-- + +Fixes to remove from the default set of Tidy fixes as per your level. + diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt new file mode 100644 index 0000000000..9785137dc9 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.Trusted.txt @@ -0,0 +1,7 @@ +HTML.Trusted +TYPE: bool +VERSION: 2.0.0 +DEFAULT: false +--DESCRIPTION-- +Indicates whether or not the user input is trusted or not. If the input is +trusted, a more expansive set of allowed tags and attributes will be used. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt new file mode 100644 index 0000000000..7909203ef5 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.XHTML.txt @@ -0,0 +1,10 @@ +HTML.XHTML +TYPE: bool +DEFAULT: true +VERSION: 1.1.0 +DEPRECATED-VERSION: 1.7.0 +DEPRECATED-USE: HTML.Doctype +--DESCRIPTION-- +Determines whether or not output is XHTML 1.0 or HTML 4.01 flavor. +--ALIASES-- +Core.XHTML diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.txt new file mode 100644 index 0000000000..9b8b3a74a4 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/HTML.txt @@ -0,0 +1,2 @@ +HTML +DESCRIPTION: Configuration regarding allowed HTML. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt new file mode 100644 index 0000000000..171b0fff6c --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.CommentScriptContents.txt @@ -0,0 +1,9 @@ +Output.CommentScriptContents +TYPE: bool +VERSION: 2.0.0 +DEFAULT: true +--DESCRIPTION-- +Determines whether or not HTML Purifier should attempt to fix up the +contents of script tags for legacy browsers with comments. +--ALIASES-- +Core.CommentScriptContents diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt new file mode 100644 index 0000000000..2021572516 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.Newline.txt @@ -0,0 +1,13 @@ +Output.Newline +TYPE: string/null +VERSION: 2.0.1 +DEFAULT: NULL +--DESCRIPTION-- + +

+ Newline string to format final output with. If left null, HTML Purifier + will auto-detect the default newline type of the system and use that; + you can manually override it here. Remember, \r\n is Windows, \r + is Mac, and \n is Unix. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt new file mode 100644 index 0000000000..5d7f29d3f8 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.TidyFormat.txt @@ -0,0 +1,24 @@ +Output.TidyFormat +TYPE: bool +VERSION: 1.1.1 +DEFAULT: false +--DESCRIPTION-- +

+ Determines whether or not to run Tidy on the final output for pretty + formatting reasons, such as indentation and wrap. +

+

+ This can greatly improve readability for editors who are hand-editing + the HTML, but is by no means necessary as HTML Purifier has already + fixed all major errors the HTML may have had. Tidy is a non-default + extension, and this directive will silently fail if Tidy is not + available. +

+

+ If you are looking to make the overall look of your page's source + better, I recommend running Tidy on the entire page rather than just + user-content (after all, the indentation relative to the containing + blocks will be incorrect). +

+--ALIASES-- +Core.TidyFormat diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.txt new file mode 100644 index 0000000000..134e141f09 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Output.txt @@ -0,0 +1,2 @@ +Output +DESCRIPTION: Configuration relating to the generation of (X)HTML. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt new file mode 100644 index 0000000000..99337628db --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.ForceNoIconv.txt @@ -0,0 +1,6 @@ +Test.ForceNoIconv +TYPE: bool +DEFAULT: false +--DESCRIPTION-- +When set to true, HTMLPurifier_Encoder will act as if iconv does not exist +and use only pure PHP implementations. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.txt new file mode 100644 index 0000000000..fec6f8d8f8 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/Test.txt @@ -0,0 +1,2 @@ +Test +DESCRIPTION: Developer testing configuration for our unit tests. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt new file mode 100644 index 0000000000..2686bac420 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.AllowedSchemes.txt @@ -0,0 +1,14 @@ +URI.AllowedSchemes +TYPE: lookup +--DEFAULT-- +array ( + 'http' => true, + 'https' => true, + 'mailto' => true, + 'ftp' => true, + 'nntp' => true, + 'news' => true, +) +--DESCRIPTION-- +Whitelist that defines the schemes that a URI is allowed to have. This +prevents XSS attacks from using pseudo-schemes like javascript or mocha. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Base.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Base.txt new file mode 100644 index 0000000000..a0f8d97b05 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Base.txt @@ -0,0 +1,17 @@ +URI.Base +TYPE: string/null +VERSION: 2.1.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ The base URI is the URI of the document this purified HTML will be + inserted into. This information is important if HTML Purifier needs + to calculate absolute URIs from relative URIs, such as when %URI.MakeAbsolute + is on. You may use a non-absolute URI for this value, but behavior + may vary (%URI.MakeAbsolute deals nicely with both absolute and + relative paths, but forwards-compatibility is not guaranteed). + Warning: If set, the scheme on this URI + overrides the one specified by %URI.DefaultScheme. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt new file mode 100644 index 0000000000..2f39c2fad3 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefaultScheme.txt @@ -0,0 +1,10 @@ +URI.DefaultScheme +TYPE: string +DEFAULT: 'http' +--DESCRIPTION-- + +

+ Defines through what scheme the output will be served, in order to + select the proper object validator when no scheme information is present. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt new file mode 100644 index 0000000000..20bfc1db77 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionID.txt @@ -0,0 +1,11 @@ +URI.DefinitionID +TYPE: string/null +VERSION: 2.1.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ Unique identifier for a custom-built URI definition. If you want + to add custom URIFilters, you must specify this value. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt new file mode 100644 index 0000000000..7dabdc6d7f --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DefinitionRev.txt @@ -0,0 +1,11 @@ +URI.DefinitionRev +TYPE: int +VERSION: 2.1.0 +DEFAULT: 1 +--DESCRIPTION-- + +

+ Revision identifier for your custom definition. See + %HTML.DefinitionRev for details. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt new file mode 100644 index 0000000000..a97b2e29e2 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Disable.txt @@ -0,0 +1,13 @@ +URI.Disable +TYPE: bool +VERSION: 1.3.0 +DEFAULT: false +--DESCRIPTION-- + +

+ Disables all URIs in all forms. Not sure why you'd want to do that + (after all, the Internet's founded on the notion of a hyperlink). +

+ +--ALIASES-- +Attr.DisableURI diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt new file mode 100644 index 0000000000..6d3ceba86f --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternal.txt @@ -0,0 +1,10 @@ +URI.DisableExternal +TYPE: bool +VERSION: 1.2.0 +DEFAULT: false +--DESCRIPTION-- +Disables links to external websites. This is a highly effective anti-spam +and anti-pagerank-leech measure, but comes at a hefty price: nolinks or +images outside of your domain will be allowed. Non-linkified URIs will +still be preserved. If you want to be able to link to subdomains or use +absolute URIs, specify %URI.Host for your website. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt new file mode 100644 index 0000000000..37f5d13f8a --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableExternalResources.txt @@ -0,0 +1,12 @@ +URI.DisableExternalResources +TYPE: bool +VERSION: 1.3.0 +DEFAULT: false +--DESCRIPTION-- +Disables the embedding of external resources, preventing users from +embedding things like images from other hosts. This prevents access +tracking (good for email viewers), bandwidth leeching, cross-site request +forging, goatse.cx posting, and other nasties, but also results in a loss +of end-user functionality (they can't directly post a pic they posted from +Flickr anymore). Use it if you don't have a robust user-content moderation +team. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt new file mode 100644 index 0000000000..a456051451 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.DisableResources.txt @@ -0,0 +1,12 @@ +URI.DisableResources +TYPE: bool +VERSION: 1.3.0 +DEFAULT: false +--DESCRIPTION-- + +

+ Disables embedding resources, essentially meaning no pictures. You can + still link to them though. See %URI.DisableExternalResources for why + this might be a good idea. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Host.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Host.txt new file mode 100644 index 0000000000..15356ac206 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Host.txt @@ -0,0 +1,19 @@ +URI.Host +TYPE: string/null +VERSION: 1.2.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ Defines the domain name of the server, so we can determine whether or + an absolute URI is from your website or not. Not strictly necessary, + as users should be using relative URIs to reference resources on your + website. It will, however, let you use absolute URIs to link to + subdomains of the domain you post here: i.e. example.com will allow + sub.example.com. However, higher up domains will still be excluded: + if you set %URI.Host to sub.example.com, example.com will be blocked. + Note: This directive overrides %URI.Base because + a given page may be on a sub-domain, but you wish HTML Purifier to be + more relaxed and allow some of the parent domains too. +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt new file mode 100644 index 0000000000..5f5cbc5693 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.HostBlacklist.txt @@ -0,0 +1,8 @@ +URI.HostBlacklist +TYPE: list +VERSION: 1.3.0 +DEFAULT: array() +--DESCRIPTION-- +List of strings that are forbidden in the host of any URI. Use it to kill +domain names of spam, etc. Note that it will catch anything in the domain, +so moo.com will catch moo.com.example.com. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt new file mode 100644 index 0000000000..2d2b40a5e4 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.MakeAbsolute.txt @@ -0,0 +1,12 @@ +URI.MakeAbsolute +TYPE: bool +VERSION: 2.1.0 +DEFAULT: false +--DESCRIPTION-- + +

+ Converts all URIs into absolute forms. This is useful when the HTML + being filtered assumes a specific base path, but will actually be + viewed in a different context (and setting an alternate base URI is + not possible). %URI.Base must be set for this directive to work. +

diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt new file mode 100644 index 0000000000..b1207aab79 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.Munge.txt @@ -0,0 +1,31 @@ +URI.Munge +TYPE: string/null +VERSION: 1.3.0 +DEFAULT: NULL +--DESCRIPTION-- + +

+ Munges all browsable (usually http, https and ftp) + absolute URI's into another URI, usually a URI redirection service. + This directive accepts a URI, formatted with a %s where + the url-encoded original URI should be inserted (sample: + http://www.google.com/url?q=%s). +

+

+ Uses for this directive: +

+ diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt new file mode 100644 index 0000000000..c75b133142 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.OverrideAllowedSchemes.txt @@ -0,0 +1,8 @@ +URI.OverrideAllowedSchemes +TYPE: bool +DEFAULT: true +--DESCRIPTION-- +If this is set to true (which it is by default), you can override +%URI.AllowedSchemes by simply registering a HTMLPurifier_URIScheme to the +registry. If false, you will also have to update that directive in order +to add more schemes. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.txt b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.txt new file mode 100644 index 0000000000..114ecb17f3 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/URI.txt @@ -0,0 +1,2 @@ +URI +DESCRIPTION: Features regarding Uniform Resource Identifiers. diff --git a/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/info.ini b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/info.ini new file mode 100644 index 0000000000..cd67189232 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/ConfigSchema/schema/info.ini @@ -0,0 +1 @@ +name = "HTML Purifier" diff --git a/lib/htmlpurifier/HTMLPurifier/ContentSets.php b/lib/htmlpurifier/HTMLPurifier/ContentSets.php index 7baf7a3101..16438fda44 100644 --- a/lib/htmlpurifier/HTMLPurifier/ContentSets.php +++ b/lib/htmlpurifier/HTMLPurifier/ContentSets.php @@ -1,45 +1,37 @@ true) indexed by name. * @note This is in HTMLPurifier_HTMLDefinition->info_content_sets - * @public */ - var $lookup = array(); + public $lookup = array(); /** * Synchronized list of defined content sets (keys of info) */ - var $keys = array(); + protected $keys = array(); /** * Synchronized list of defined content values (values of info) */ - var $values = array(); + protected $values = array(); /** * Merges in module's content sets, expands identifiers in the content * sets and populates the keys, values and lookup member variables. * @param $modules List of HTMLPurifier_HTMLModule */ - function HTMLPurifier_ContentSets($modules) { + public function __construct($modules) { if (!is_array($modules)) $modules = array($modules); // populate content_sets based on module hints // sorry, no way of overloading @@ -79,7 +71,7 @@ class HTMLPurifier_ContentSets * @param $def HTMLPurifier_ElementDef reference * @param $module Module that defined the ElementDef */ - function generateChildDef(&$def, $module) { + public function generateChildDef(&$def, $module) { if (!empty($def->child)) return; // already done! $content_model = $def->content_model; if (is_string($content_model)) { @@ -97,7 +89,7 @@ class HTMLPurifier_ContentSets * @param $def HTMLPurifier_ElementDef to have ChildDef extracted * @return HTMLPurifier_ChildDef corresponding to ElementDef */ - function getChildDef($def, $module) { + public function getChildDef($def, $module) { $value = $def->content_model; if (is_object($value)) { trigger_error( @@ -137,7 +129,7 @@ class HTMLPurifier_ContentSets * @param $string List of elements * @return Lookup array of elements */ - function convertToLookup($string) { + protected function convertToLookup($string) { $array = explode('|', str_replace(' ', '', $string)); $ret = array(); foreach ($array as $i => $k) { diff --git a/lib/htmlpurifier/HTMLPurifier/Context.php b/lib/htmlpurifier/HTMLPurifier/Context.php index a78a6fb6f6..151a68eda8 100644 --- a/lib/htmlpurifier/HTMLPurifier/Context.php +++ b/lib/htmlpurifier/HTMLPurifier/Context.php @@ -4,22 +4,23 @@ * Registry object that contains information about the current context. * @warning Is a bit buggy when variables are set to null: it thinks * they don't exist! So use false instead, please. + * @note Since the variables Context deals with may not be objects, + * references are very important here! Do not remove! */ class HTMLPurifier_Context { /** * Private array that stores the references. - * @private */ - var $_storage = array(); + private $_storage = array(); /** * Registers a variable into the context. * @param $name String name - * @param $ref Variable to be registered + * @param $ref Reference to variable to be registered */ - function register($name, &$ref) { + public function register($name, &$ref) { if (isset($this->_storage[$name])) { trigger_error("Name $name produces collision, cannot re-register", E_USER_ERROR); @@ -33,7 +34,7 @@ class HTMLPurifier_Context * @param $name String name * @param $ignore_error Boolean whether or not to ignore error */ - function &get($name, $ignore_error = false) { + public function &get($name, $ignore_error = false) { if (!isset($this->_storage[$name])) { if (!$ignore_error) { trigger_error("Attempted to retrieve non-existent variable $name", @@ -49,7 +50,7 @@ class HTMLPurifier_Context * Destorys a variable in the context. * @param $name String name */ - function destroy($name) { + public function destroy($name) { if (!isset($this->_storage[$name])) { trigger_error("Attempted to destroy non-existent variable $name", E_USER_ERROR); @@ -62,7 +63,7 @@ class HTMLPurifier_Context * Checks whether or not the variable exists. * @param $name String name */ - function exists($name) { + public function exists($name) { return isset($this->_storage[$name]); } @@ -70,7 +71,7 @@ class HTMLPurifier_Context * Loads a series of variables from an associative array * @param $context_array Assoc array of variables to load */ - function loadArray(&$context_array) { + public function loadArray($context_array) { foreach ($context_array as $key => $discard) { $this->register($key, $context_array[$key]); } diff --git a/lib/htmlpurifier/HTMLPurifier/Definition.php b/lib/htmlpurifier/HTMLPurifier/Definition.php index 8f958e4798..7de8b73d7f 100644 --- a/lib/htmlpurifier/HTMLPurifier/Definition.php +++ b/lib/htmlpurifier/HTMLPurifier/Definition.php @@ -4,33 +4,31 @@ * Super-class for definition datatype objects, implements serialization * functions for the class. */ -class HTMLPurifier_Definition +abstract class HTMLPurifier_Definition { /** * Has setup() been called yet? */ - var $setup = false; + public $setup = false; /** * What type of definition is it? */ - var $type; + public $type; /** * Sets up the definition object into the final form, something * not done by the constructor * @param $config HTMLPurifier_Config instance */ - function doSetup($config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract protected function doSetup($config); /** * Setup function that aborts if already setup * @param $config HTMLPurifier_Config instance */ - function setup($config) { + public function setup($config) { if ($this->setup) return; $this->setup = true; $this->doSetup($config); diff --git a/lib/htmlpurifier/HTMLPurifier/DefinitionCache.php b/lib/htmlpurifier/HTMLPurifier/DefinitionCache.php index 5b14fdfe4d..f81af0c56a 100644 --- a/lib/htmlpurifier/HTMLPurifier/DefinitionCache.php +++ b/lib/htmlpurifier/HTMLPurifier/DefinitionCache.php @@ -1,34 +1,23 @@ type = $type; } @@ -36,9 +25,9 @@ class HTMLPurifier_DefinitionCache * Generates a unique identifier for a particular configuration * @param Instance of HTMLPurifier_Config */ - function generateKey($config) { - return $config->version . '-' . // possibly replace with function calls - $config->getBatchSerial($this->type) . '-' . + public function generateKey($config) { + return $config->version . ',' . // possibly replace with function calls + $config->getBatchSerial($this->type) . ',' . $config->get($this->type, 'DefinitionRev'); } @@ -48,9 +37,9 @@ class HTMLPurifier_DefinitionCache * @param $key Key to test * @param $config Instance of HTMLPurifier_Config to test against */ - function isOld($key, $config) { - if (substr_count($key, '-') < 2) return true; - list($version, $hash, $revision) = explode('-', $key, 3); + public function isOld($key, $config) { + if (substr_count($key, ',') < 2) return true; + list($version, $hash, $revision) = explode(',', $key, 3); $compare = version_compare($version, $config->version); // version mismatch, is always old if ($compare != 0) return true; @@ -68,7 +57,7 @@ class HTMLPurifier_DefinitionCache * @param $def Definition object to check * @return Boolean true if good, false if not */ - function checkDefType($def) { + public function checkDefType($def) { if ($def->type !== $this->type) { trigger_error("Cannot use definition of type {$def->type} in cache for {$this->type}"); return false; @@ -79,44 +68,32 @@ class HTMLPurifier_DefinitionCache /** * Adds a definition object to the cache */ - function add($def, $config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function add($def, $config); /** * Unconditionally saves a definition object to the cache */ - function set($def, $config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function set($def, $config); /** * Replace an object in the cache */ - function replace($def, $config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function replace($def, $config); /** * Retrieves a definition object from the cache */ - function get($config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function get($config); /** * Removes a definition object to the cache */ - function remove($config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function remove($config); /** * Clears all objects from cache */ - function flush($config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function flush($config); /** * Clears all expired (older version or revision) objects from cache @@ -124,8 +101,7 @@ class HTMLPurifier_DefinitionCache * not interfere with other Definition types, and cleanup() * should not be repeatedly called by userland code. */ - function cleanup($config) { - trigger_error('Cannot call abstract method', E_USER_ERROR); - } + abstract public function cleanup($config); + } diff --git a/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator.php b/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator.php index 14fca85974..39eb474f9a 100644 --- a/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator.php +++ b/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator.php @@ -1,22 +1,20 @@ copy(); // reference is necessary for mocks in PHP 4 $decorator->cache =& $cache; @@ -27,31 +25,35 @@ class HTMLPurifier_DefinitionCache_Decorator extends HTMLPurifier_DefinitionCach /** * Cross-compatible clone substitute */ - function copy() { + public function copy() { return new HTMLPurifier_DefinitionCache_Decorator(); } - function add($def, $config) { + public function add($def, $config) { return $this->cache->add($def, $config); } - function set($def, $config) { + public function set($def, $config) { return $this->cache->set($def, $config); } - function replace($def, $config) { + public function replace($def, $config) { return $this->cache->replace($def, $config); } - function get($config) { + public function get($config) { return $this->cache->get($config); } - function flush($config) { + public function remove($config) { + return $this->cache->remove($config); + } + + public function flush($config) { return $this->cache->flush($config); } - function cleanup($config) { + public function cleanup($config) { return $this->cache->cleanup($config); } diff --git a/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php b/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php index eb47c433fb..842382e417 100644 --- a/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php +++ b/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Decorator/Cleanup.php @@ -1,7 +1,5 @@ definitions[$this->generateKey($config)] = $def; return $status; } - function set($def, $config) { + public function set($def, $config) { $status = parent::set($def, $config); if ($status) $this->definitions[$this->generateKey($config)] = $def; return $status; } - function replace($def, $config) { + public function replace($def, $config) { $status = parent::replace($def, $config); if ($status) $this->definitions[$this->generateKey($config)] = $def; return $status; } - function get($config) { + public function get($config) { $key = $this->generateKey($config); if (isset($this->definitions[$key])) return $this->definitions[$key]; $this->definitions[$key] = parent::get($config); diff --git a/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Null.php b/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Null.php index 559fc9ba0d..8e39e69d7b 100644 --- a/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Null.php +++ b/lib/htmlpurifier/HTMLPurifier/DefinitionCache/Null.php @@ -1,34 +1,36 @@ - Absolute path with no trailing slash to store serialized definitions in. - Default is within the - HTML Purifier library inside DefinitionCache/Serializer. This - path must be writable by the webserver. This directive has been - available since 2.0.0. -

-'); - class HTMLPurifier_DefinitionCache_Serializer extends HTMLPurifier_DefinitionCache { - function add($def, $config) { + public function add($def, $config) { if (!$this->checkDefType($def)) return; $file = $this->generateFilePath($config); if (file_exists($file)) return false; @@ -25,14 +12,14 @@ class HTMLPurifier_DefinitionCache_Serializer extends return $this->_write($file, serialize($def)); } - function set($def, $config) { + public function set($def, $config) { if (!$this->checkDefType($def)) return; $file = $this->generateFilePath($config); if (!$this->_prepareDir($config)) return false; return $this->_write($file, serialize($def)); } - function replace($def, $config) { + public function replace($def, $config) { if (!$this->checkDefType($def)) return; $file = $this->generateFilePath($config); if (!file_exists($file)) return false; @@ -40,19 +27,19 @@ class HTMLPurifier_DefinitionCache_Serializer extends return $this->_write($file, serialize($def)); } - function get($config) { + public function get($config) { $file = $this->generateFilePath($config); if (!file_exists($file)) return false; return unserialize(file_get_contents($file)); } - function remove($config) { + public function remove($config) { $file = $this->generateFilePath($config); if (!file_exists($file)) return false; return unlink($file); } - function flush($config) { + public function flush($config) { if (!$this->_prepareDir($config)) return false; $dir = $this->generateDirectoryPath($config); $dh = opendir($dir); @@ -63,7 +50,7 @@ class HTMLPurifier_DefinitionCache_Serializer extends } } - function cleanup($config) { + public function cleanup($config) { if (!$this->_prepareDir($config)) return false; $dir = $this->generateDirectoryPath($config); $dh = opendir($dir); @@ -78,8 +65,9 @@ class HTMLPurifier_DefinitionCache_Serializer extends /** * Generates the file path to the serial file corresponding to * the configuration and definition name + * @todo Make protected */ - function generateFilePath($config) { + public function generateFilePath($config) { $key = $this->generateKey($config); return $this->generateDirectoryPath($config) . '/' . $key . '.ser'; } @@ -87,8 +75,9 @@ class HTMLPurifier_DefinitionCache_Serializer extends /** * Generates the path to the directory contain this cache's serial files * @note No trailing slash + * @todo Make protected */ - function generateDirectoryPath($config) { + public function generateDirectoryPath($config) { $base = $this->generateBaseDirectoryPath($config); return $base . '/' . $this->type; } @@ -96,8 +85,9 @@ class HTMLPurifier_DefinitionCache_Serializer extends /** * Generates path to base directory that contains all definition type * serials + * @todo Make protected */ - function generateBaseDirectoryPath($config) { + public function generateBaseDirectoryPath($config) { $base = $config->get('Cache', 'SerializerPath'); $base = is_null($base) ? HTMLPURIFIER_PREFIX . '/HTMLPurifier/DefinitionCache/Serializer' : $base; return $base; @@ -109,26 +99,15 @@ class HTMLPurifier_DefinitionCache_Serializer extends * @param $data Data to write into file * @return Number of bytes written if success, or false if failure. */ - function _write($file, $data) { - static $file_put_contents; - if ($file_put_contents === null) { - $file_put_contents = function_exists('file_put_contents'); - } - if ($file_put_contents) { - return file_put_contents($file, $data); - } - $fh = fopen($file, 'w'); - if (!$fh) return false; - $status = fwrite($fh, $data); - fclose($fh); - return $status; + private function _write($file, $data) { + return file_put_contents($file, $data); } /** * Prepares the directory that this type stores the serials in * @return True if successful */ - function _prepareDir($config) { + private function _prepareDir($config) { $directory = $this->generateDirectoryPath($config); if (!is_dir($directory)) { $base = $this->generateBaseDirectoryPath($config); @@ -140,7 +119,9 @@ class HTMLPurifier_DefinitionCache_Serializer extends } elseif (!$this->_testPermissions($base)) { return false; } + $old = umask(0022); // disable group and world writes mkdir($directory); + umask($old); } elseif (!$this->_testPermissions($directory)) { return false; } @@ -151,7 +132,7 @@ class HTMLPurifier_DefinitionCache_Serializer extends * Tests permissions on a directory and throws out friendly * error messages and attempts to chmod it itself if possible */ - function _testPermissions($dir) { + private function _testPermissions($dir) { // early abort, if it is writable, everything is hunky-dory if (is_writable($dir)) return true; if (!is_dir($dir)) { diff --git a/lib/htmlpurifier/HTMLPurifier/DefinitionCacheFactory.php b/lib/htmlpurifier/HTMLPurifier/DefinitionCacheFactory.php index dead92a32e..fca1b6c40e 100644 --- a/lib/htmlpurifier/HTMLPurifier/DefinitionCacheFactory.php +++ b/lib/htmlpurifier/HTMLPurifier/DefinitionCacheFactory.php @@ -1,44 +1,26 @@ array()); - var $implementations = array(); - var $decorators = array(); + protected $caches = array('Serializer' => array()); + protected $implementations = array(); + protected $decorators = array(); /** * Initialize default decorators */ - function setup() { + public function setup() { $this->addDecorator('Cleanup'); } /** * Retrieves an instance of global definition cache factory. - * @static */ - function &instance($prototype = null) { + public static function instance($prototype = null) { static $instance; if ($prototype !== null) { $instance = $prototype; @@ -54,7 +36,7 @@ class HTMLPurifier_DefinitionCacheFactory * @param $short Short name of cache object, for reference * @param $long Full class name of cache object, for construction */ - function register($short, $long) { + public function register($short, $long) { $this->implementations[$short] = $long; } @@ -63,18 +45,17 @@ class HTMLPurifier_DefinitionCacheFactory * @param $name Name of definitions handled by cache * @param $config Instance of HTMLPurifier_Config */ - function &create($type, $config) { + public function create($type, $config) { $method = $config->get('Cache', 'DefinitionImpl'); if ($method === null) { - $null = new HTMLPurifier_DefinitionCache_Null($type); - return $null; + return new HTMLPurifier_DefinitionCache_Null($type); } if (!empty($this->caches[$method][$type])) { return $this->caches[$method][$type]; } if ( isset($this->implementations[$method]) && - class_exists($class = $this->implementations[$method]) + class_exists($class = $this->implementations[$method], false) ) { $cache = new $class($type); } else { @@ -97,7 +78,7 @@ class HTMLPurifier_DefinitionCacheFactory * Registers a decorator to add to all new cache objects * @param */ - function addDecorator($decorator) { + public function addDecorator($decorator) { if (is_string($decorator)) { $class = "HTMLPurifier_DefinitionCache_Decorator_$decorator"; $decorator = new $class; diff --git a/lib/htmlpurifier/HTMLPurifier/Doctype.php b/lib/htmlpurifier/HTMLPurifier/Doctype.php index 7afdcd74a2..5e83a86989 100644 --- a/lib/htmlpurifier/HTMLPurifier/Doctype.php +++ b/lib/htmlpurifier/HTMLPurifier/Doctype.php @@ -11,40 +11,40 @@ class HTMLPurifier_Doctype /** * Full name of doctype */ - var $name; + public $name; /** * List of standard modules (string identifiers or literal objects) * that this doctype uses */ - var $modules = array(); + public $modules = array(); /** * List of modules to use for tidying up code */ - var $tidyModules = array(); + public $tidyModules = array(); /** * Is the language derived from XML (i.e. XHTML)? */ - var $xml = true; + public $xml = true; /** * List of aliases for this doctype */ - var $aliases = array(); + public $aliases = array(); /** * Public DTD identifier */ - var $dtdPublic; + public $dtdPublic; /** * System DTD identifier */ - var $dtdSystem; + public $dtdSystem; - function HTMLPurifier_Doctype($name = null, $xml = true, $modules = array(), + public function __construct($name = null, $xml = true, $modules = array(), $tidyModules = array(), $aliases = array(), $dtd_public = null, $dtd_system = null ) { $this->name = $name; @@ -55,12 +55,5 @@ class HTMLPurifier_Doctype $this->dtdPublic = $dtd_public; $this->dtdSystem = $dtd_system; } - - /** - * Clones the doctype, use before resolving modes and the like - */ - function copy() { - return unserialize(serialize($this)); - } } diff --git a/lib/htmlpurifier/HTMLPurifier/DoctypeRegistry.php b/lib/htmlpurifier/HTMLPurifier/DoctypeRegistry.php index e657b3da4b..6c969efc5b 100644 --- a/lib/htmlpurifier/HTMLPurifier/DoctypeRegistry.php +++ b/lib/htmlpurifier/HTMLPurifier/DoctypeRegistry.php @@ -1,37 +1,17 @@ doctypes[$doctype->name] =& $doctype; + $this->doctypes[$doctype->name] = $doctype; $name = $doctype->name; // hookup aliases foreach ($doctype->aliases as $alias) { @@ -71,9 +51,9 @@ class HTMLPurifier_DoctypeRegistry * @note This function resolves aliases * @note When possible, use the more fully-featured make() * @param $doctype Name of doctype - * @return Reference to doctype object + * @return Editable doctype object */ - function &get($doctype) { + public function get($doctype) { if (isset($this->aliases[$doctype])) $doctype = $this->aliases[$doctype]; if (!isset($this->doctypes[$doctype])) { trigger_error('Doctype ' . htmlspecialchars($doctype) . ' does not exist', E_USER_ERROR); @@ -91,16 +71,14 @@ class HTMLPurifier_DoctypeRegistry * Generator whether or not the current document is XML * based or not). */ - function make($config) { - $original_doctype = $this->get($this->getDoctypeFromConfig($config)); - $doctype = $original_doctype->copy(); - return $doctype; + public function make($config) { + return clone $this->get($this->getDoctypeFromConfig($config)); } /** * Retrieves the doctype from the configuration object */ - function getDoctypeFromConfig($config) { + public function getDoctypeFromConfig($config) { // recommended test $doctype = $config->get('HTML', 'Doctype'); if (!empty($doctype)) return $doctype; diff --git a/lib/htmlpurifier/HTMLPurifier/ElementDef.php b/lib/htmlpurifier/HTMLPurifier/ElementDef.php index b6439d1a5b..341ce349d6 100644 --- a/lib/htmlpurifier/HTMLPurifier/ElementDef.php +++ b/lib/htmlpurifier/HTMLPurifier/ElementDef.php @@ -13,7 +13,7 @@ class HTMLPurifier_ElementDef * Does the definition work by itself, or is it created solely * for the purpose of merging into another definition? */ - var $standalone = true; + public $standalone = true; /** * Associative array of attribute name to HTMLPurifier_AttrDef @@ -25,29 +25,23 @@ class HTMLPurifier_ElementDef * contain string indentifiers in lieu of HTMLPurifier_AttrDef, * see HTMLPurifier_AttrTypes on how they are expanded during * HTMLPurifier_HTMLDefinition->setup() processing. - * @public */ - var $attr = array(); + public $attr = array(); /** * Indexed list of tag's HTMLPurifier_AttrTransform to be done before validation - * @public */ - var $attr_transform_pre = array(); + public $attr_transform_pre = array(); /** * Indexed list of tag's HTMLPurifier_AttrTransform to be done after validation - * @public */ - var $attr_transform_post = array(); - - + public $attr_transform_post = array(); /** * HTMLPurifier_ChildDef of this tag. - * @public */ - var $child; + public $child; /** * Abstract string representation of internal ChildDef rules. See @@ -55,9 +49,8 @@ class HTMLPurifier_ElementDef * into an HTMLPurifier_ChildDef. * @warning This is a temporary variable that is not available after * being processed by HTMLDefinition - * @public */ - var $content_model; + public $content_model; /** * Value of $child->type, used to determine which ChildDef to use, @@ -65,9 +58,8 @@ class HTMLPurifier_ElementDef * @warning This must be lowercase * @warning This is a temporary variable that is not available after * being processed by HTMLDefinition - * @public */ - var $content_model_type; + public $content_model_type; @@ -76,16 +68,14 @@ class HTMLPurifier_ElementDef * is important for chameleon ins and del processing in * HTMLPurifier_ChildDef_Chameleon. Dynamically set: modules don't * have to worry about this one. - * @public */ - var $descendants_are_inline = false; + public $descendants_are_inline = false; /** * List of the names of required attributes this element has. Dynamically * populated by HTMLPurifier_HTMLDefinition::getElement - * @public */ - var $required_attr = array(); + public $required_attr = array(); /** * Lookup table of tags excluded from all descendants of this tag. @@ -97,22 +87,14 @@ class HTMLPurifier_ElementDef * all descendants and not just children. Note that the XHTML * Modularization Abstract Modules are blithely unaware of such * distinctions. - * @public - */ - var $excludes = array(); - - /** - * Is this element safe for untrusted users to use? */ - var $safe; + public $excludes = array(); /** * Low-level factory constructor for creating new standalone element defs - * @static */ - function create($safe, $content_model, $content_model_type, $attr) { + public static function create($content_model, $content_model_type, $attr) { $def = new HTMLPurifier_ElementDef(); - $def->safe = (bool) $safe; $def->content_model = $content_model; $def->content_model_type = $content_model_type; $def->attr = $attr; @@ -124,7 +106,7 @@ class HTMLPurifier_ElementDef * Values from the new element def take precedence if a value is * not mergeable. */ - function mergeIn($def) { + public function mergeIn($def) { // later keys takes precedence foreach($def->attr as $k => $v) { @@ -156,7 +138,6 @@ class HTMLPurifier_ElementDef } if(!is_null($def->child)) $this->child = $def->child; if($def->descendants_are_inline) $this->descendants_are_inline = $def->descendants_are_inline; - if(!is_null($def->safe)) $this->safe = $def->safe; } @@ -165,7 +146,7 @@ class HTMLPurifier_ElementDef * @param $a1 Array by reference that is merged into * @param $a2 Array that merges into $a1 */ - function _mergeAssocArray(&$a1, $a2) { + private function _mergeAssocArray(&$a1, $a2) { foreach ($a2 as $k => $v) { if ($v === false) { if (isset($a1[$k])) unset($a1[$k]); @@ -175,13 +156,6 @@ class HTMLPurifier_ElementDef } } - /** - * Retrieves a copy of the element definition - */ - function copy() { - return unserialize(serialize($this)); - } - } diff --git a/lib/htmlpurifier/HTMLPurifier/Encoder.php b/lib/htmlpurifier/HTMLPurifier/Encoder.php index 31ebb785ff..763684f789 100644 --- a/lib/htmlpurifier/HTMLPurifier/Encoder.php +++ b/lib/htmlpurifier/HTMLPurifier/Encoder.php @@ -1,53 +1,5 @@ feature '. - 'that automatically resolves all entities), making it pretty useless '. - 'for anything except the most I18N-blind applications, although '. - '%Core.EscapeNonASCIICharacters offers fixes this trouble with '. - 'another tradeoff. This directive '. - 'only accepts ISO-8859-1 if iconv is not enabled.' -); - -HTMLPurifier_ConfigSchema::define( - 'Core', 'EscapeNonASCIICharacters', false, 'bool', - 'This directive overcomes a deficiency in %Core.Encoding by blindly '. - 'converting all non-ASCII characters into decimal numeric entities before '. - 'converting it to its native encoding. This means that even '. - 'characters that can be expressed in the non-UTF-8 encoding will '. - 'be entity-ized, which can be a real downer for encodings like Big5. '. - 'It also assumes that the ASCII repetoire is available, although '. - 'this is the case for almost all encodings. Anyway, use UTF-8! This '. - 'directive has been available since 1.4.0.' -); - -if ( !function_exists('iconv') ) { - // only encodings with native PHP support - HTMLPurifier_ConfigSchema::defineAllowedValues( - 'Core', 'Encoding', array( - 'utf-8', - 'iso-8859-1' - ) - ); - HTMLPurifier_ConfigSchema::defineValueAliases( - 'Core', 'Encoding', array( - 'iso8859-1' => 'iso-8859-1' - ) - ); -} - -HTMLPurifier_ConfigSchema::define( - 'Test', 'ForceNoIconv', false, 'bool', - 'When set to true, HTMLPurifier_Encoder will act as if iconv does not '. - 'exist and use only pure PHP implementations.' -); - /** * A UTF-8 specific character encoder that handles cleaning and transforming. * @note All functions in this class should be static. @@ -58,14 +10,14 @@ class HTMLPurifier_Encoder /** * Constructor throws fatal error if you attempt to instantiate class */ - function HTMLPurifier_Encoder() { + private function __construct() { trigger_error('Cannot instantiate encoder, call methods statically', E_USER_ERROR); } /** * Error-handler that mutes errors, alternative to shut-up operator. */ - function muteErrorHandler() {} + private static function muteErrorHandler() {} /** * Cleans a UTF-8 string for well-formedness and SGML validity @@ -73,7 +25,6 @@ class HTMLPurifier_Encoder * It will parse according to UTF-8 and return a valid UTF8 string, with * non-SGML codepoints excluded. * - * @static * @note Just for reference, the non-SGML code points are 0 to 31 and * 127 to 159, inclusive. However, we allow code points 9, 10 * and 13, which are the tab, line feed and carriage return @@ -93,7 +44,7 @@ class HTMLPurifier_Encoder * would need that, and I'm probably not going to implement them. * Once again, PHP 6 should solve all our problems. */ - function cleanUTF8($str, $force_php = false) { + public static function cleanUTF8($str, $force_php = false) { static $non_sgml_chars = array(); if (empty($non_sgml_chars)) { @@ -260,7 +211,6 @@ class HTMLPurifier_Encoder /** * Translates a Unicode codepoint into its corresponding UTF-8 character. - * @static * @note Based on Feyd's function at * , * which is in public domain. @@ -285,7 +235,7 @@ class HTMLPurifier_Encoder // | 00000000 | 00010000 | 11111111 | 11111111 | Defined upper limit of legal scalar codes // +----------+----------+----------+----------+ - function unichr($code) { + public static function unichr($code) { if($code > 1114111 or $code < 0 or ($code >= 55296 and $code <= 57343) ) { // bits are set outside the "valid" range as defined @@ -324,28 +274,32 @@ class HTMLPurifier_Encoder /** * Converts a string to UTF-8 based on configuration. - * @static */ - function convertToUTF8($str, $config, &$context) { + public static function convertToUTF8($str, $config, $context) { static $iconv = null; if ($iconv === null) $iconv = function_exists('iconv'); $encoding = $config->get('Core', 'Encoding'); if ($encoding === 'utf-8') return $str; if ($iconv && !$config->get('Test', 'ForceNoIconv')) { - return @iconv($encoding, 'utf-8//IGNORE', $str); + set_error_handler(array('HTMLPurifier_Encoder', 'muteErrorHandler')); + $str = iconv($encoding, 'utf-8//IGNORE', $str); + restore_error_handler(); + return $str; } elseif ($encoding === 'iso-8859-1') { - return @utf8_encode($str); + set_error_handler(array('HTMLPurifier_Encoder', 'muteErrorHandler')); + $str = utf8_encode($str); + restore_error_handler(); + return $str; } trigger_error('Encoding not supported', E_USER_ERROR); } /** * Converts a string from UTF-8 based on configuration. - * @static * @note Currently, this is a lossy conversion, with unexpressable * characters being omitted. */ - function convertFromUTF8($str, $config, &$context) { + public static function convertFromUTF8($str, $config, $context) { static $iconv = null; if ($iconv === null) $iconv = function_exists('iconv'); $encoding = $config->get('Core', 'Encoding'); @@ -354,16 +308,21 @@ class HTMLPurifier_Encoder $str = HTMLPurifier_Encoder::convertToASCIIDumbLossless($str); } if ($iconv && !$config->get('Test', 'ForceNoIconv')) { - return @iconv('utf-8', $encoding . '//IGNORE', $str); + set_error_handler(array('HTMLPurifier_Encoder', 'muteErrorHandler')); + $str = iconv('utf-8', $encoding . '//IGNORE', $str); + restore_error_handler(); + return $str; } elseif ($encoding === 'iso-8859-1') { - return @utf8_decode($str); + set_error_handler(array('HTMLPurifier_Encoder', 'muteErrorHandler')); + $str = utf8_decode($str); + restore_error_handler(); + return $str; } trigger_error('Encoding not supported', E_USER_ERROR); } /** * Lossless (character-wise) conversion of HTML to ASCII - * @static * @param $str UTF-8 string to be converted to ASCII * @returns ASCII encoded string with non-ASCII character entity-ized * @warning Adapted from MediaWiki, claiming fair use: this is a common @@ -378,7 +337,7 @@ class HTMLPurifier_Encoder * @note Sort of with cleanUTF8() but it assumes that $str is * well-formed UTF-8 */ - function convertToASCIIDumbLossless($str) { + public static function convertToASCIIDumbLossless($str) { $bytesleft = 0; $result = ''; $working = 0; diff --git a/lib/htmlpurifier/HTMLPurifier/EntityLookup.php b/lib/htmlpurifier/HTMLPurifier/EntityLookup.php index 8204867be3..f9252a2ea5 100644 --- a/lib/htmlpurifier/HTMLPurifier/EntityLookup.php +++ b/lib/htmlpurifier/HTMLPurifier/EntityLookup.php @@ -7,9 +7,8 @@ class HTMLPurifier_EntityLookup { /** * Assoc array of entity name to character represented. - * @public */ - var $table; + public $table; /** * Sets up the entity lookup table from the serialized file contents. @@ -17,7 +16,7 @@ class HTMLPurifier_EntityLookup { * using the maintenance script generate_entity_file.php * @warning This is not in constructor to help enforce the Singleton */ - function setup($file = false) { + public function setup($file = false) { if (!$file) { $file = HTMLPURIFIER_PREFIX . '/HTMLPurifier/EntityLookup/entities.ser'; } @@ -26,10 +25,9 @@ class HTMLPurifier_EntityLookup { /** * Retrieves sole instance of the object. - * @static * @param Optional prototype of custom lookup table to overload with. */ - function instance($prototype = false) { + public static function instance($prototype = false) { // no references, since PHP doesn't copy unless modified static $instance = null; if ($prototype) { diff --git a/lib/htmlpurifier/HTMLPurifier/EntityParser.php b/lib/htmlpurifier/HTMLPurifier/EntityParser.php index 2547241350..cb4c5082ef 100644 --- a/lib/htmlpurifier/HTMLPurifier/EntityParser.php +++ b/lib/htmlpurifier/HTMLPurifier/EntityParser.php @@ -1,8 +1,5 @@ '"', 38 => '&', @@ -43,9 +37,8 @@ class HTMLPurifier_EntityParser /** * Stripped entity names to decimal conversion table for special entities. - * @protected */ - var $_special_ent2dec = + protected $_special_ent2dec = array( 'quot' => 34, 'amp' => 38, @@ -58,11 +51,10 @@ class HTMLPurifier_EntityParser * running this whenever you have parsed character is t3h 5uck, we run * it before everything else. * - * @protected * @param $string String to have non-special entities parsed. * @returns Parsed string. */ - function substituteNonSpecialEntities($string) { + public function substituteNonSpecialEntities($string) { // it will try to detect missing semicolons, but don't rely on it return preg_replace_callback( $this->_substituteEntitiesRegex, @@ -74,15 +66,13 @@ class HTMLPurifier_EntityParser /** * Callback function for substituteNonSpecialEntities() that does the work. * - * @warning Though this is public in order to let the callback happen, - * calling it directly is not recommended. * @param $matches PCRE matches array, with 0 the entire match, and * either index 1, 2 or 3 set with a hex value, dec value, * or string (respectively). * @returns Replacement string. */ - function nonSpecialEntityCallback($matches) { + protected function nonSpecialEntityCallback($matches) { // replaces all but big five $entity = $matches[0]; $is_num = (@$matches[0][1] === '#'); @@ -113,11 +103,10 @@ class HTMLPurifier_EntityParser * @notice We try to avoid calling this function because otherwise, it * would have to be called a lot (for every parsed section). * - * @protected * @param $string String to have non-special entities parsed. * @returns Parsed string. */ - function substituteSpecialEntities($string) { + public function substituteSpecialEntities($string) { return preg_replace_callback( $this->_substituteEntitiesRegex, array($this, 'specialEntityCallback'), @@ -129,14 +118,12 @@ class HTMLPurifier_EntityParser * * This callback has same syntax as nonSpecialEntityCallback(). * - * @warning Though this is public in order to let the callback happen, - * calling it directly is not recommended. * @param $matches PCRE-style matches array, with 0 the entire match, and * either index 1, 2 or 3 set with a hex value, dec value, * or string (respectively). * @returns Replacement string. */ - function specialEntityCallback($matches) { + protected function specialEntityCallback($matches) { $entity = $matches[0]; $is_num = (@$matches[0][1] === '#'); if ($is_num) { diff --git a/lib/htmlpurifier/HTMLPurifier/Error.php b/lib/htmlpurifier/HTMLPurifier/Error.php deleted file mode 100644 index 2ca4d7323c..0000000000 --- a/lib/htmlpurifier/HTMLPurifier/Error.php +++ /dev/null @@ -1,7 +0,0 @@ -locale =& $context->get('Locale'); + public function __construct($context) { + $this->locale =& $context->get('Locale'); $this->generator =& $context->get('Generator'); - $this->context =& $context; + $this->context = $context; } /** @@ -26,7 +24,7 @@ class HTMLPurifier_ErrorCollector * @param $severity int Error severity, PHP error style (don't use E_USER_) * @param $msg string Error message text */ - function send($severity, $msg) { + public function send($severity, $msg) { $args = array(); if (func_num_args() > 2) { @@ -65,7 +63,7 @@ class HTMLPurifier_ErrorCollector * @param List of arrays in format of array(Error message text, * token that caused error, tokens surrounding token) */ - function getRaw() { + public function getRaw() { return $this->errors; } @@ -73,7 +71,7 @@ class HTMLPurifier_ErrorCollector * Default HTML formatting implementation for error messages * @param $config Configuration array, vital for HTML output nature */ - function getHTMLFormatted($config) { + public function getHTMLFormatted($config) { $ret = array(); $errors = $this->errors; diff --git a/lib/htmlpurifier/HTMLPurifier/Exception.php b/lib/htmlpurifier/HTMLPurifier/Exception.php new file mode 100644 index 0000000000..d36d88e0a8 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/Exception.php @@ -0,0 +1,11 @@ +preFilter, * 2->preFilter, 3->preFilter, purify, 3->postFilter, 2->postFilter, * 1->postFilter. + * + * @note Methods are not declared abstract as it is perfectly legitimate + * for an implementation not to want anything to happen on a step */ class HTMLPurifier_Filter @@ -22,17 +25,21 @@ class HTMLPurifier_Filter /** * Name of the filter for identification purposes */ - var $name; + public $name; /** * Pre-processor function, handles HTML before HTML Purifier */ - function preFilter($html, $config, &$context) {} + public function preFilter($html, $config, $context) { + return $html; + } /** * Post-processor function, handles HTML after HTML Purifier */ - function postFilter($html, $config, &$context) {} + public function postFilter($html, $config, $context) { + return $html; + } } diff --git a/lib/htmlpurifier/HTMLPurifier/Filter/ExtractStyleBlocks.php b/lib/htmlpurifier/HTMLPurifier/Filter/ExtractStyleBlocks.php new file mode 100644 index 0000000000..438d7b79bb --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/Filter/ExtractStyleBlocks.php @@ -0,0 +1,134 @@ + blocks from input HTML, cleans them up + * using CSSTidy, and then places them in $purifier->context->get('StyleBlocks') + * so they can be used elsewhere in the document. + * + * @note + * See tests/HTMLPurifier/Filter/ExtractStyleBlocksTest.php for + * sample usage. + * + * @note + * This filter can also be used on stylesheets not included in the + * document--something purists would probably prefer. Just directly + * call HTMLPurifier_Filter_ExtractStyleBlocks->cleanCSS() + */ +class HTMLPurifier_Filter_ExtractStyleBlocks extends HTMLPurifier_Filter +{ + + public $name = 'ExtractStyleBlocks'; + private $_styleMatches = array(); + private $_tidy; + + public function __construct() { + $this->_tidy = new csstidy(); + } + + /** + * Save the contents of CSS blocks to style matches + * @param $matches preg_replace style $matches array + */ + protected function styleCallback($matches) { + $this->_styleMatches[] = $matches[1]; + } + + /** + * Removes inline #isU', array($this, 'styleCallback'), $html); + $style_blocks = $this->_styleMatches; + $this->_styleMatches = array(); // reset + $context->register('StyleBlocks', $style_blocks); // $context must not be reused + if ($this->_tidy) { + foreach ($style_blocks as &$style) { + $style = $this->cleanCSS($style, $config, $context); + } + } + return $html; + } + + /** + * Takes CSS (the stuff found in in a font-family prop). + if ($config->get('FilterParam', 'ExtractStyleBlocksEscaping')) { + $css = str_replace( + array('<', '>', '&'), + array('\3C ', '\3E ', '\26 '), + $css + ); + } + return $css; + } + +} + diff --git a/lib/htmlpurifier/HTMLPurifier/Filter/YouTube.php b/lib/htmlpurifier/HTMLPurifier/Filter/YouTube.php index 4f63ad6d56..cf3d0cc2c2 100644 --- a/lib/htmlpurifier/HTMLPurifier/Filter/YouTube.php +++ b/lib/htmlpurifier/HTMLPurifier/Filter/YouTube.php @@ -1,20 +1,18 @@ ]+>.+?'. 'http://www.youtube.com/v/([A-Za-z0-9\-_]+).+?#s'; $pre_replace = '\1'; return preg_replace($pre_regex, $pre_replace, $html); } - function postFilter($html, $config, &$context) { + public function postFilter($html, $config, $context) { $post_regex = '#([A-Za-z0-9\-_]+)#'; $post_replace = ''. diff --git a/lib/htmlpurifier/HTMLPurifier/Generator.php b/lib/htmlpurifier/HTMLPurifier/Generator.php index 5322b8c20b..e35ce8cf35 100644 --- a/lib/htmlpurifier/HTMLPurifier/Generator.php +++ b/lib/htmlpurifier/HTMLPurifier/Generator.php @@ -1,74 +1,47 @@ - Determines whether or not to run Tidy on the final output for pretty - formatting reasons, such as indentation and wrap. -

-

- This can greatly improve readability for editors who are hand-editing - the HTML, but is by no means necessary as HTML Purifier has already - fixed all major errors the HTML may have had. Tidy is a non-default - extension, and this directive will silently fail if Tidy is not - available. -

-

- If you are looking to make the overall look of your page's source - better, I recommend running Tidy on the entire page rather than just - user-content (after all, the indentation relative to the containing - blocks will be incorrect). -

-

- This directive was available since 1.1.1. -

-HTML -); -HTMLPurifier_ConfigSchema::defineAlias('Core', 'TidyFormat', 'Output', 'TidyFormat'); - -HTMLPurifier_ConfigSchema::define('Output', 'Newline', null, 'string/null', ' -

- Newline string to format final output with. If left null, HTML Purifier - will auto-detect the default newline type of the system and use that; - you can manually override it here. Remember, \r\n is Windows, \r - is Mac, and \n is Unix. This directive was available since 2.0.1. -

-'); - /** * Generates HTML from tokens. * @todo Refactor interface so that configuration/context is determined - * upon instantiation, no need for messy generateFromTokens() calls + * upon instantiation, no need for messy generateFromTokens() calls + * @todo Make some of the more internal functions protected, and have + * unit tests work around that */ class HTMLPurifier_Generator { /** - * Bool cache of %HTML.XHTML - * @private + * Whether or not generator should produce XML output + */ + private $_xhtml = true; + + /** + * :HACK: Whether or not generator should comment the insides of )#si', - array('HTMLPurifier_Lexer_DirectLex', 'scriptCallback'), $html); + array($this, 'scriptCallback'), $html); } $html = $this->normalize($html, $config, $context); @@ -81,16 +63,10 @@ class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer $e =& $context->get('ErrorCollector'); } - // infinite loop protection - // has to be pretty big, since html docs can be big - // we're allow two hundred thousand tags... more than enough? - // NOTE: this is also used for synchronization, so watch out + // for testing synchronization $loops = 0; - while(true) { - - // infinite loop protection - if (++$loops > 200000) return array(); + while(++$loops) { // recalculate lines if ( @@ -168,7 +144,7 @@ class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer // Check if it's a comment if ( - strncmp('!--', $segment, 3) === 0 + substr($segment, 0, 3) === '!--' ) { // re-determine segment length, looking for --> $position_comment_end = strpos($html, '-->', $cursor); @@ -184,7 +160,12 @@ class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer } $strlen_segment = $position_comment_end - $cursor; $segment = substr($html, $cursor, $strlen_segment); - $token = new HTMLPurifier_Token_Comment(substr($segment, 3)); + $token = new + HTMLPurifier_Token_Comment( + substr( + $segment, 3, $strlen_segment - 3 + ) + ); if ($maintain_line_numbers) { $token->line = $current_line; $current_line += $this->substrCount($html, $nl, $cursor, $strlen_segment); @@ -316,9 +297,9 @@ class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer } /** - * PHP 4 compatible substr_count that implements offset and length + * PHP 5.0.x compatible substr_count that implements offset and length */ - function substrCount($haystack, $needle, $offset, $length) { + protected function substrCount($haystack, $needle, $offset, $length) { static $oldVersion; if ($oldVersion === null) { $oldVersion = version_compare(PHP_VERSION, '5.1', '<'); @@ -337,7 +318,7 @@ class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer * @param $string Inside of tag excluding name. * @returns Assoc array of attributes. */ - function parseAttributeString($string, $config, &$context) { + public function parseAttributeString($string, $config, $context) { $string = (string) $string; // quick typecast if ($string == '') return array(); // no attributes @@ -394,16 +375,8 @@ class HTMLPurifier_Lexer_DirectLex extends HTMLPurifier_Lexer // space, so let's guarantee that there's always a terminating space. $string .= ' '; - // infinite loop protection - $loops = 0; while(true) { - // infinite loop protection - if (++$loops > 1000) { - trigger_error('Infinite loop detected in attribute parsing', E_USER_WARNING); - return array(); - } - if ($cursor >= $size) { break; } diff --git a/lib/htmlpurifier/HTMLPurifier/Lexer/PEARSax3.php b/lib/htmlpurifier/HTMLPurifier/Lexer/PEARSax3.php index 3888229b07..0716a049f1 100644 --- a/lib/htmlpurifier/HTMLPurifier/Lexer/PEARSax3.php +++ b/lib/htmlpurifier/HTMLPurifier/Lexer/PEARSax3.php @@ -1,8 +1,5 @@ tokens = array(); @@ -55,7 +51,7 @@ class HTMLPurifier_Lexer_PEARSax3 extends HTMLPurifier_Lexer /** * Open tag event handler, interface is defined by PEAR package. */ - function openHandler(&$parser, $name, $attrs, $closed) { + public function openHandler(&$parser, $name, $attrs, $closed) { // entities are not resolved in attrs foreach ($attrs as $key => $attr) { $attrs[$key] = $this->parseData($attr); @@ -71,11 +67,11 @@ class HTMLPurifier_Lexer_PEARSax3 extends HTMLPurifier_Lexer /** * Close tag event handler, interface is defined by PEAR package. */ - function closeHandler(&$parser, $name) { + public function closeHandler(&$parser, $name) { // HTMLSax3 seems to always send empty tags an extra close tag // check and ignore if you see it: // [TESTME] to make sure it doesn't overreach - if ($this->tokens[count($this->tokens)-1]->type == 'empty') { + if ($this->tokens[count($this->tokens)-1] instanceof HTMLPurifier_Token_Empty) { return true; } $this->tokens[] = new HTMLPurifier_Token_End($name); @@ -85,7 +81,7 @@ class HTMLPurifier_Lexer_PEARSax3 extends HTMLPurifier_Lexer /** * Data event handler, interface is defined by PEAR package. */ - function dataHandler(&$parser, $data) { + public function dataHandler(&$parser, $data) { $this->tokens[] = new HTMLPurifier_Token_Text($data); return true; } @@ -93,7 +89,7 @@ class HTMLPurifier_Lexer_PEARSax3 extends HTMLPurifier_Lexer /** * Escaped text handler, interface is defined by PEAR package. */ - function escapeHandler(&$parser, $data) { + public function escapeHandler(&$parser, $data) { if (strpos($data, '--') === 0) { $this->tokens[] = new HTMLPurifier_Token_Comment($data); } diff --git a/lib/htmlpurifier/HTMLPurifier/Lexer/PH5P.php b/lib/htmlpurifier/HTMLPurifier/Lexer/PH5P.php index b676237914..81659e5051 100644 --- a/lib/htmlpurifier/HTMLPurifier/Lexer/PH5P.php +++ b/lib/htmlpurifier/HTMLPurifier/Lexer/PH5P.php @@ -1,20 +1,29 @@ normalize($html, $config, $context); - $html = $this->wrapHTML( $html, $config, $context); - $parser = new HTML5($html); - $doc = $parser->save(); + public function tokenizeHTML($html, $config, $context) { + $new_html = $this->normalize($html, $config, $context); + $new_html = $this->wrapHTML($new_html, $config, $context); + try { + $parser = new HTML5($new_html); + $doc = $parser->save(); + } catch (DOMException $e) { + // Uh oh, it failed. Punt to DirectLex. + $lexer = new HTMLPurifier_Lexer_DirectLex(); + $context->register('PH5PError', $e); // save the error, so we can detect it + return $lexer->tokenizeHTML($html, $config, $context); // use original HTML + } $tokens = array(); $this->tokenizeDOM( $doc->getElementsByTagName('html')->item(0)-> // @@ -117,7 +126,7 @@ class HTML5 { public function __construct($data) { $data = str_replace("\r\n", "\n", $data); - $date = str_replace("\r", null, $data); + $data = str_replace("\r", null, $data); $this->data = $data; $this->char = -1; @@ -2145,7 +2154,7 @@ class HTML5TreeConstructer { /* Reconstruct the active formatting elements, if any. */ $this->reconstructActiveFormattingElements(); - $this->insertElement($token); + $this->insertElement($token, true, true); break; } break; @@ -3526,7 +3535,18 @@ class HTML5TreeConstructer { } } - private function insertElement($token, $append = true) { + private function insertElement($token, $append = true, $check = false) { + // Proprietary workaround for libxml2's limitations with tag names + if ($check) { + // Slightly modified HTML5 tag-name modification, + // removing anything that's not an ASCII letter, digit, or hyphen + $token['name'] = preg_replace('/[^a-z0-9-]/i', '', $token['name']); + // Remove leading hyphens and numbers + $token['name'] = ltrim($token['name'], '-0..9'); + // In theory, this should ever be needed, but just in case + if ($token['name'] === '') $token['name'] = 'span'; // arbitrary generic choice + } + $el = $this->dom->createElement($token['name']); foreach($token['attr'] as $attr) { diff --git a/lib/htmlpurifier/HTMLPurifier/PercentEncoder.php b/lib/htmlpurifier/HTMLPurifier/PercentEncoder.php index c3b6c8e679..e1358675b1 100644 --- a/lib/htmlpurifier/HTMLPurifier/PercentEncoder.php +++ b/lib/htmlpurifier/HTMLPurifier/PercentEncoder.php @@ -14,12 +14,12 @@ class HTMLPurifier_PercentEncoder /** * Reserved characters to preserve when using encode(). */ - var $preserve = array(); + protected $preserve = array(); /** * String of characters that should be preserved while using encode(). */ - function HTMLPurifier_PercentEncoder($preserve = false) { + public function __construct($preserve = false) { // unreserved letters, ought to const-ify for ($i = 48; $i <= 57; $i++) $this->preserve[$i] = true; // digits for ($i = 65; $i <= 90; $i++) $this->preserve[$i] = true; // upper-case @@ -47,7 +47,7 @@ class HTMLPurifier_PercentEncoder * @param $string String to be encoded * @return Encoded string. */ - function encode($string) { + public function encode($string) { $ret = ''; for ($i = 0, $c = strlen($string); $i < $c; $i++) { if ($string[$i] !== '%' && !isset($this->preserve[$int = ord($string[$i])]) ) { @@ -66,7 +66,7 @@ class HTMLPurifier_PercentEncoder * characters. Be careful when reusing instances of PercentEncoder! * @param $string String to normalize */ - function normalize($string) { + public function normalize($string) { if ($string == '') return ''; $parts = explode('%', $string); $ret = array_shift($parts); diff --git a/lib/htmlpurifier/HTMLPurifier/Printer.php b/lib/htmlpurifier/HTMLPurifier/Printer.php index 7e20daafe3..680ffa1d1a 100644 --- a/lib/htmlpurifier/HTMLPurifier/Printer.php +++ b/lib/htmlpurifier/HTMLPurifier/Printer.php @@ -1,10 +1,7 @@ generator = new HTMLPurifier_Generator(); } /** * Give generator necessary configuration if possible */ - function prepareGenerator($config) { + public function prepareGenerator($config) { // hack for smoketests/configForm.php - if (empty($config->conf['HTML'])) return; + $all = $config->getAll(); + if (empty($all['HTML'])) return; $context = new HTMLPurifier_Context(); $this->generator->generateFromTokens(array(), $config, $context); } @@ -47,7 +45,7 @@ class HTMLPurifier_Printer * @param $tag Tag name * @param $attr Attribute array */ - function start($tag, $attr = array()) { + protected function start($tag, $attr = array()) { return $this->generator->generateFromToken( new HTMLPurifier_Token_Start($tag, $attr ? $attr : array()) ); @@ -57,7 +55,7 @@ class HTMLPurifier_Printer * Returns an end teg * @param $tag Tag name */ - function end($tag) { + protected function end($tag) { return $this->generator->generateFromToken( new HTMLPurifier_Token_End($tag) ); @@ -70,19 +68,19 @@ class HTMLPurifier_Printer * @param $attr Tag attributes * @param $escape Bool whether or not to escape contents */ - function element($tag, $contents, $attr = array(), $escape = true) { + protected function element($tag, $contents, $attr = array(), $escape = true) { return $this->start($tag, $attr) . ($escape ? $this->escape($contents) : $contents) . $this->end($tag); } - function elementEmpty($tag, $attr = array()) { + protected function elementEmpty($tag, $attr = array()) { return $this->generator->generateFromToken( new HTMLPurifier_Token_Empty($tag, $attr) ); } - function text($text) { + protected function text($text) { return $this->generator->generateFromToken( new HTMLPurifier_Token_Text($text) ); @@ -93,7 +91,7 @@ class HTMLPurifier_Printer * @param $name Key * @param $value Value */ - function row($name, $value) { + protected function row($name, $value) { if (is_bool($value)) $value = $value ? 'On' : 'Off'; return $this->start('tr') . "\n" . @@ -107,7 +105,7 @@ class HTMLPurifier_Printer * Escapes a string for HTML output. * @param $string String to escape */ - function escape($string) { + protected function escape($string) { $string = HTMLPurifier_Encoder::cleanUTF8($string); $string = htmlspecialchars($string, ENT_COMPAT, 'UTF-8'); return $string; @@ -118,7 +116,7 @@ class HTMLPurifier_Printer * @param $array List of strings * @param $polite Bool whether or not to add an end before the last */ - function listify($array, $polite = false) { + protected function listify($array, $polite = false) { if (empty($array)) return 'None'; $ret = ''; $i = count($array); @@ -136,7 +134,7 @@ class HTMLPurifier_Printer * @param $obj Object to determine class of * @param $prefix Further prefix to remove */ - function getClass($obj, $sec_prefix = '') { + protected function getClass($obj, $sec_prefix = '') { static $five = null; if ($five === null) $five = version_compare(PHP_VERSION, '5', '>='); $prefix = 'HTMLPurifier_' . $sec_prefix; @@ -152,14 +150,14 @@ class HTMLPurifier_Printer } $class .= implode(', ', $values); break; - case 'composite': + case 'css_composite': $values = array(); foreach ($obj->defs as $def) { $values[] = $this->getClass($def, $sec_prefix); } $class .= implode(', ', $values); break; - case 'multiple': + case 'css_multiple': $class .= $this->getClass($obj->single, $sec_prefix) . ', '; $class .= $obj->max; break; diff --git a/lib/htmlpurifier/HTMLPurifier/Printer/CSSDefinition.php b/lib/htmlpurifier/HTMLPurifier/Printer/CSSDefinition.php index 7d3ad61e98..bf43b020cb 100644 --- a/lib/htmlpurifier/HTMLPurifier/Printer/CSSDefinition.php +++ b/lib/htmlpurifier/HTMLPurifier/Printer/CSSDefinition.php @@ -1,13 +1,11 @@ def = $config->getCSSDefinition(); $ret = ''; diff --git a/lib/htmlpurifier/HTMLPurifier/Printer/ConfigForm.php b/lib/htmlpurifier/HTMLPurifier/Printer/ConfigForm.php index 21b8314bc5..172d7bb48e 100644 --- a/lib/htmlpurifier/HTMLPurifier/Printer/ConfigForm.php +++ b/lib/htmlpurifier/HTMLPurifier/Printer/ConfigForm.php @@ -1,45 +1,39 @@ docURL = $doc_url; $this->name = $name; $this->compress = $compress; @@ -53,7 +47,7 @@ class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer * @param $cols Integer columns of textarea, null to use default * @param $rows Integer rows of textarea, null to use default */ - function setTextareaDimensions($cols = null, $rows = null) { + public function setTextareaDimensions($cols = null, $rows = null) { if ($cols) $this->fields['default']->cols = $cols; if ($rows) $this->fields['default']->rows = $rows; } @@ -61,14 +55,14 @@ class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer /** * Retrieves styling, in case it is not accessible by webserver */ - function getCSS() { + public static function getCSS() { return file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/Printer/ConfigForm.css'); } /** * Retrieves JavaScript, in case it is not accessible by webserver */ - function getJavaScript() { + public static function getJavaScript() { return file_get_contents(HTMLPURIFIER_PREFIX . '/HTMLPurifier/Printer/ConfigForm.js'); } @@ -77,7 +71,7 @@ class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer * @param $config Configuration object of current form state * @param $allowed Optional namespace(s) and directives to restrict form to. */ - function render($config, $allowed = true, $render_controls = true) { + public function render($config, $allowed = true, $render_controls = true) { $this->config = $config; $this->prepareGenerator($config); @@ -92,8 +86,8 @@ class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer $ret .= $this->start('table', array('class' => 'hp-config')); $ret .= $this->start('thead'); $ret .= $this->start('tr'); - $ret .= $this->element('th', 'Directive'); - $ret .= $this->element('th', 'Value'); + $ret .= $this->element('th', 'Directive', array('class' => 'hp-directive')); + $ret .= $this->element('th', 'Value', array('class' => 'hp-value')); $ret .= $this->end('tr'); $ret .= $this->end('thead'); foreach ($all as $ns => $directives) { @@ -117,9 +111,8 @@ class HTMLPurifier_Printer_ConfigForm extends HTMLPurifier_Printer * Renders a single namespace * @param $ns String namespace name * @param $directive Associative array of directives to values - * @protected */ - function renderNamespace($ns, $directives) { + protected function renderNamespace($ns, $directives) { $ret = ''; $ret .= $this->start('tbody', array('class' => 'namespace')); $ret .= $this->start('tr'); @@ -178,15 +171,15 @@ class HTMLPurifier_Printer_ConfigForm_NullDecorator extends HTMLPurifier_Printer /** * Printer being decorated */ - var $obj; + protected $obj; /** * @param $obj Printer to decorate */ - function HTMLPurifier_Printer_ConfigForm_NullDecorator($obj) { - parent::HTMLPurifier_Printer(); + public function __construct($obj) { + parent::__construct(); $this->obj = $obj; } - function render($ns, $directive, $value, $name, $config) { + public function render($ns, $directive, $value, $name, $config) { $this->prepareGenerator($config); $ret = ''; $ret .= $this->start('label', array('for' => "$name:Null_$ns.$directive")); @@ -201,6 +194,10 @@ class HTMLPurifier_Printer_ConfigForm_NullDecorator extends HTMLPurifier_Printer 'id' => "$name:Null_$ns.$directive", 'onclick' => "toggleWriteability('$name:$ns.$directive',checked)" // INLINE JAVASCRIPT!!!! ); + if ($this->obj instanceof HTMLPurifier_Printer_ConfigForm_bool) { + // modify inline javascript slightly + $attr['onclick'] = "toggleWriteability('$name:Yes_$ns.$directive',checked);toggleWriteability('$name:No_$ns.$directive',checked)"; + } if ($value === null) $attr['checked'] = 'checked'; $ret .= $this->elementEmpty('input', $attr); $ret .= $this->text(' or '); @@ -214,9 +211,9 @@ class HTMLPurifier_Printer_ConfigForm_NullDecorator extends HTMLPurifier_Printer * Swiss-army knife configuration form field printer */ class HTMLPurifier_Printer_ConfigForm_default extends HTMLPurifier_Printer { - var $cols = 18; - var $rows = 5; - function render($ns, $directive, $value, $name, $config) { + public $cols = 18; + public $rows = 5; + public function render($ns, $directive, $value, $name, $config) { $this->prepareGenerator($config); // this should probably be split up a little $ret = ''; @@ -282,7 +279,7 @@ class HTMLPurifier_Printer_ConfigForm_default extends HTMLPurifier_Printer { * Bool form field printer */ class HTMLPurifier_Printer_ConfigForm_bool extends HTMLPurifier_Printer { - function render($ns, $directive, $value, $name, $config) { + public function render($ns, $directive, $value, $name, $config) { $this->prepareGenerator($config); $ret = ''; $ret .= $this->start('div', array('id' => "$name:$ns.$directive")); @@ -298,7 +295,8 @@ class HTMLPurifier_Printer_ConfigForm_bool extends HTMLPurifier_Printer { 'id' => "$name:Yes_$ns.$directive", 'value' => '1' ); - if ($value) $attr['checked'] = 'checked'; + if ($value === true) $attr['checked'] = 'checked'; + if ($value === null) $attr['disabled'] = 'disabled'; $ret .= $this->elementEmpty('input', $attr); $ret .= $this->start('label', array('for' => "$name:No_$ns.$directive")); @@ -312,7 +310,8 @@ class HTMLPurifier_Printer_ConfigForm_bool extends HTMLPurifier_Printer { 'id' => "$name:No_$ns.$directive", 'value' => '0' ); - if (!$value) $attr['checked'] = 'checked'; + if ($value === false) $attr['checked'] = 'checked'; + if ($value === null) $attr['disabled'] = 'disabled'; $ret .= $this->elementEmpty('input', $attr); $ret .= $this->end('div'); diff --git a/lib/htmlpurifier/HTMLPurifier/Printer/HTMLDefinition.php b/lib/htmlpurifier/HTMLPurifier/Printer/HTMLDefinition.php index 4a0a90f152..a209b89821 100644 --- a/lib/htmlpurifier/HTMLPurifier/Printer/HTMLDefinition.php +++ b/lib/htmlpurifier/HTMLPurifier/Printer/HTMLDefinition.php @@ -1,16 +1,14 @@ config =& $config; @@ -31,7 +29,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer /** * Renders the Doctype table */ - function renderDoctype() { + protected function renderDoctype() { $doctype = $this->def->doctype; $ret = ''; $ret .= $this->start('table'); @@ -48,7 +46,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer /** * Renders environment table, which is miscellaneous info */ - function renderEnvironment() { + protected function renderEnvironment() { $def = $this->def; $ret = ''; @@ -92,7 +90,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer /** * Renders the Content Sets table */ - function renderContentSets() { + protected function renderContentSets() { $ret = ''; $ret .= $this->start('table'); $ret .= $this->element('caption', 'Content Sets'); @@ -109,7 +107,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer /** * Renders the Elements ($info) table */ - function renderInfo() { + protected function renderInfo() { $ret = ''; $ret .= $this->start('table'); $ret .= $this->element('caption', 'Elements ($info)'); @@ -120,7 +118,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer $ret .= $this->end('tr'); foreach ($this->def->info as $name => $def) { $ret .= $this->start('tr'); - $ret .= $this->element('th', "<$name>" . ($def->safe ? '' : ' (unsafe)'), array('class'=>'heavy' . ($def->safe ? '' : ' unsafe'), 'colspan' => 2)); + $ret .= $this->element('th', "<$name>", array('class'=>'heavy', 'colspan' => 2)); $ret .= $this->end('tr'); $ret .= $this->start('tr'); $ret .= $this->element('th', 'Inline content'); @@ -169,7 +167,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer * Renders a row describing the allowed children of an element * @param $def HTMLPurifier_ChildDef of pertinent element */ - function renderChildren($def) { + protected function renderChildren($def) { $context = new HTMLPurifier_Context(); $ret = ''; $ret .= $this->start('tr'); @@ -220,7 +218,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer * Listifies a tag lookup table. * @param $array Tag lookup array in form of array('tagname' => true) */ - function listifyTagLookup($array) { + protected function listifyTagLookup($array) { ksort($array); $list = array(); foreach ($array as $name => $discard) { @@ -235,7 +233,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer * @param $array List of objects * @todo Also add information about internal state */ - function listifyObjectList($array) { + protected function listifyObjectList($array) { ksort($array); $list = array(); foreach ($array as $discard => $obj) { @@ -248,7 +246,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer * Listifies a hash of attributes to AttrDef classes * @param $array Array hash in form of array('attrname' => HTMLPurifier_AttrDef) */ - function listifyAttr($array) { + protected function listifyAttr($array) { ksort($array); $list = array(); foreach ($array as $name => $obj) { @@ -261,7 +259,7 @@ class HTMLPurifier_Printer_HTMLDefinition extends HTMLPurifier_Printer /** * Creates a heavy header row */ - function heavyHeader($text, $num = 1) { + protected function heavyHeader($text, $num = 1) { $ret = ''; $ret .= $this->start('tr'); $ret .= $this->element('th', $text, array('colspan' => $num, 'class' => 'heavy')); diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy.php b/lib/htmlpurifier/HTMLPurifier/Strategy.php index a6ab7e8bca..db71fc565f 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy.php @@ -8,13 +8,8 @@ * features, such as custom tags, custom parsing of text, etc. */ -HTMLPurifier_ConfigSchema::define( - 'Core', 'EscapeInvalidTags', false, 'bool', - 'When true, invalid tags will be written back to the document as plain '. - 'text. Otherwise, they are silently dropped.' -); -class HTMLPurifier_Strategy +abstract class HTMLPurifier_Strategy { /** @@ -24,9 +19,7 @@ class HTMLPurifier_Strategy * @param $config Configuration options * @returns Processed array of token objects. */ - function execute($tokens, $config, &$context) { - trigger_error('Cannot call abstract function', E_USER_ERROR); - } + abstract public function execute($tokens, $config, $context); } diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy/Composite.php b/lib/htmlpurifier/HTMLPurifier/Strategy/Composite.php index fcd230f472..b4a2924932 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy/Composite.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy/Composite.php @@ -1,24 +1,19 @@ strategies as $strategy) { $tokens = $strategy->execute($tokens, $config, $context); } diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy/Core.php b/lib/htmlpurifier/HTMLPurifier/Strategy/Core.php index 93d051046a..53dfde3255 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy/Core.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy/Core.php @@ -1,19 +1,12 @@ strategies[] = new HTMLPurifier_Strategy_RemoveForeignElements(); $this->strategies[] = new HTMLPurifier_Strategy_MakeWellFormed(); $this->strategies[] = new HTMLPurifier_Strategy_FixNesting(); diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy/FixNesting.php b/lib/htmlpurifier/HTMLPurifier/Strategy/FixNesting.php index 25e9f8acbc..69a6b50393 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy/FixNesting.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy/FixNesting.php @@ -1,8 +1,5 @@ type == 'start') { + if ($tokens[$j] instanceof HTMLPurifier_Token_Start) { $depth++; // skip token assignment on first iteration, this is the // token we currently are on if ($depth == 1) continue; - } elseif ($tokens[$j]->type == 'end') { + } elseif ($tokens[$j] instanceof HTMLPurifier_Token_End) { $depth--; // skip token assignment on last iteration, this is the // end token of the token we're currently on @@ -287,8 +284,8 @@ class HTMLPurifier_Strategy_FixNesting extends HTMLPurifier_Strategy // Test if the token indeed is a start tag, if not, move forward // and test again. $size = count($tokens); - while ($i < $size and $tokens[$i]->type != 'start') { - if ($tokens[$i]->type == 'end') { + while ($i < $size and !$tokens[$i] instanceof HTMLPurifier_Token_Start) { + if ($tokens[$i] instanceof HTMLPurifier_Token_End) { // pop a token index off the stack if we ended a node array_pop($stack); // pop an exclusion lookup off exclusion stack if diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy/MakeWellFormed.php b/lib/htmlpurifier/HTMLPurifier/Strategy/MakeWellFormed.php index 30208ba147..8843627f13 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy/MakeWellFormed.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy/MakeWellFormed.php @@ -1,24 +1,5 @@ - This directive can be used to add custom auto-format injectors. - Specify an array of injector names (class name minus the prefix) - or concrete implementations. Injector class must exist. This directive - has been available since 2.0.1. -

-' -); - /** * Takes tokens makes them well-formed (balance end tags, etc.) */ @@ -27,20 +8,19 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy /** * Locally shared variable references - * @private */ - var $inputTokens, $inputIndex, $outputTokens, $currentNesting, + protected $inputTokens, $inputIndex, $outputTokens, $currentNesting, $currentInjector, $injectors; - function execute($tokens, $config, &$context) { + public function execute($tokens, $config, $context) { $definition = $config->getHTMLDefinition(); // local variables $result = array(); - $generator = new HTMLPurifier_Generator(); + $generator = new HTMLPurifier_Generator($config, $context); $escape_invalid_tags = $config->get('Core', 'EscapeInvalidTags'); - $e =& $context->get('ErrorCollector', true); + $e = $context->get('ErrorCollector', true); // member variables $this->currentNesting = array(); @@ -50,8 +30,8 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy // context variables $context->register('CurrentNesting', $this->currentNesting); - $context->register('InputIndex', $this->inputIndex); - $context->register('InputTokens', $tokens); + $context->register('InputIndex', $this->inputIndex); + $context->register('InputTokens', $tokens); // -- begin INJECTOR -- @@ -82,23 +62,22 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy // give the injectors references to the definition and context // variables for performance reasons - foreach ($this->injectors as $i => $x) { - $error = $this->injectors[$i]->prepare($config, $context); + foreach ($this->injectors as $i => $injector) { + $error = $injector->prepare($config, $context); if (!$error) continue; - list($injector) = array_splice($this->injectors, $i, 1); - $name = $injector->name; - trigger_error("Cannot enable $name injector because $error is not allowed", E_USER_WARNING); + array_splice($this->injectors, $i, 1); // rm the injector + trigger_error("Cannot enable {$injector->name} injector because $error is not allowed", E_USER_WARNING); } - // warning: most foreach loops follow the convention $i => $x. - // be sure, for PHP4 compatibility, to only perform write operations - // directly referencing the object using $i: $x is only safe for reads + // warning: most foreach loops follow the convention $i => $injector. + // Don't define these as loop-wide variables, please! // -- end INJECTOR -- $token = false; $context->register('CurrentToken', $token); + // isset is in loop because $tokens size changes during loop exec for ($this->inputIndex = 0; isset($tokens[$this->inputIndex]); $this->inputIndex++) { // if all goes well, this token will be passed through unharmed @@ -106,16 +85,16 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy //printTokens($tokens, $this->inputIndex); - foreach ($this->injectors as $i => $x) { - if ($x->skip > 0) $this->injectors[$i]->skip--; + foreach ($this->injectors as $injector) { + if ($injector->skip > 0) $injector->skip--; } // quick-check: if it's not a tag, no need to process if (empty( $token->is_tag )) { - if ($token->type === 'text') { + if ($token instanceof HTMLPurifier_Token_Text) { // injector handler code; duplicated for performance reasons - foreach ($this->injectors as $i => $x) { - if (!$x->skip) $this->injectors[$i]->handleText($token); + foreach ($this->injectors as $i => $injector) { + if (!$injector->skip) $injector->handleText($token); if (is_array($token)) { $this->currentInjector = $i; break; @@ -130,21 +109,21 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy // quick tag checks: anything that's *not* an end tag $ok = false; - if ($info->type == 'empty' && $token->type == 'start') { + if ($info->type === 'empty' && $token instanceof HTMLPurifier_Token_Start) { // test if it claims to be a start tag but is empty $token = new HTMLPurifier_Token_Empty($token->name, $token->attr); $ok = true; - } elseif ($info->type != 'empty' && $token->type == 'empty' ) { + } elseif ($info->type !== 'empty' && $token instanceof HTMLPurifier_Token_Empty) { // claims to be empty but really is a start tag $token = array( new HTMLPurifier_Token_Start($token->name, $token->attr), new HTMLPurifier_Token_End($token->name) ); $ok = true; - } elseif ($token->type == 'empty') { + } elseif ($token instanceof HTMLPurifier_Token_Empty) { // real empty token $ok = true; - } elseif ($token->type == 'start') { + } elseif ($token instanceof HTMLPurifier_Token_Start) { // start tag // ...unless they also have to close their parent @@ -171,8 +150,8 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy // injector handler code; duplicated for performance reasons if ($ok) { - foreach ($this->injectors as $i => $x) { - if (!$x->skip) $this->injectors[$i]->handleElement($token); + foreach ($this->injectors as $i => $injector) { + if (!$injector->skip) $injector->handleElement($token); if (is_array($token)) { $this->currentInjector = $i; break; @@ -183,7 +162,7 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy } // sanity check: we should be dealing with a closing tag - if ($token->type != 'end') continue; + if (!$token instanceof HTMLPurifier_Token_End) continue; // make sure that we have something open if (empty($this->currentNesting)) { @@ -202,8 +181,8 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy $current_parent = array_pop($this->currentNesting); if ($current_parent->name == $token->name) { $result[] = $token; - foreach ($this->injectors as $i => $x) { - $this->injectors[$i]->notifyEnd($token); + foreach ($this->injectors as $i => $injector) { + $injector->notifyEnd($token); } continue; } @@ -242,12 +221,13 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy // okay, we found it, close all the skipped tags // note that skipped tags contains the element we need closed for ($i = count($skipped_tags) - 1; $i >= 0; $i--) { + // please don't redefine $i! if ($i && $e && !isset($skipped_tags[$i]->armor['MakeWellFormed_TagClosedError'])) { $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag closed by element end', $skipped_tags[$i]); } $result[] = $new_token = new HTMLPurifier_Token_End($skipped_tags[$i]->name); - foreach ($this->injectors as $j => $x) { // $j, not $i!!! - $this->injectors[$j]->notifyEnd($new_token); + foreach ($this->injectors as $injector) { + $injector->notifyEnd($new_token); } } @@ -263,12 +243,13 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy // not using $skipped_tags since it would invariably be all of them if (!empty($this->currentNesting)) { for ($i = count($this->currentNesting) - 1; $i >= 0; $i--) { + // please don't redefine $i! if ($e && !isset($this->currentNesting[$i]->armor['MakeWellFormed_TagClosedError'])) { $e->send(E_NOTICE, 'Strategy_MakeWellFormed: Tag closed by document end', $this->currentNesting[$i]); } $result[] = $new_token = new HTMLPurifier_Token_End($this->currentNesting[$i]->name); - foreach ($this->injectors as $j => $x) { // $j, not $i!!! - $this->injectors[$j]->notifyEnd($new_token); + foreach ($this->injectors as $injector) { + $injector->notifyEnd($new_token); } } } @@ -279,7 +260,7 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy return $result; } - function processToken($token, $config, &$context) { + function processToken($token, $config, $context) { if (is_array($token)) { // the original token was overloaded by an injector, time // to some fancy acrobatics @@ -304,9 +285,9 @@ class HTMLPurifier_Strategy_MakeWellFormed extends HTMLPurifier_Strategy } elseif ($token) { // regular case $this->outputTokens[] = $token; - if ($token->type == 'start') { + if ($token instanceof HTMLPurifier_Token_Start) { $this->currentNesting[] = $token; - } elseif ($token->type == 'end') { + } elseif ($token instanceof HTMLPurifier_Token_End) { array_pop($this->currentNesting); // not actually used } } diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy/RemoveForeignElements.php b/lib/htmlpurifier/HTMLPurifier/Strategy/RemoveForeignElements.php index 5d26e4f570..9de69a1185 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy/RemoveForeignElements.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy/RemoveForeignElements.php @@ -1,49 +1,5 @@ - This directive enables pre-emptive URI checking in img - tags, as the attribute validation strategy is not authorized to - remove elements from the document. This directive has been available - since 1.3.0, revert to pre-1.3.0 behavior by setting to false. -

-' -); - -HTMLPurifier_ConfigSchema::define( - 'Core', 'RemoveScriptContents', null, 'bool/null', ' -

- This directive enables HTML Purifier to remove not only script tags - but all of their contents. This directive has been deprecated since 2.1.0, - and when not set the value of %Core.HiddenElements will take - precedence. This directive has been available since 2.0.0, and can be used to - revert to pre-2.0.0 behavior by setting it to false. -

-' -); - -HTMLPurifier_ConfigSchema::define( - 'Core', 'HiddenElements', array('script' => true, 'style' => true), 'lookup', ' -

- This directive is a lookup array of elements which should have their - contents removed when they are not allowed by the HTML definition. - For example, the contents of a script tag are not - normally shown in a document, so if script tags are to be removed, - their contents should be removed to. This is opposed to a b - tag, which defines some presentational changes but does not hide its - contents. -

-' -); - /** * Removes all unrecognized tags from the list of tokens. * @@ -55,9 +11,9 @@ HTMLPurifier_ConfigSchema::define( class HTMLPurifier_Strategy_RemoveForeignElements extends HTMLPurifier_Strategy { - function execute($tokens, $config, &$context) { + public function execute($tokens, $config, $context) { $definition = $config->getHTMLDefinition(); - $generator = new HTMLPurifier_Generator(); + $generator = new HTMLPurifier_Generator($config, $context); $result = array(); $escape_invalid_tags = $config->get('Core', 'EscapeInvalidTags'); @@ -116,7 +72,7 @@ class HTMLPurifier_Strategy_RemoveForeignElements extends HTMLPurifier_Strategy // mostly everything's good, but // we need to make sure required attributes are in order if ( - ($token->type === 'start' || $token->type === 'empty') && + ($token instanceof HTMLPurifier_Token_Start || $token instanceof HTMLPurifier_Token_Empty) && $definition->info[$token->name]->required_attr && ($token->name != 'img' || $remove_invalid_img) // ensure config option still works ) { @@ -135,9 +91,9 @@ class HTMLPurifier_Strategy_RemoveForeignElements extends HTMLPurifier_Strategy $token->armor['ValidateAttributes'] = true; } - if (isset($hidden_elements[$token->name]) && $token->type == 'start') { + if (isset($hidden_elements[$token->name]) && $token instanceof HTMLPurifier_Token_Start) { $textify_comments = $token->name; - } elseif ($token->name === $textify_comments && $token->type == 'end') { + } elseif ($token->name === $textify_comments && $token instanceof HTMLPurifier_Token_End) { $textify_comments = false; } @@ -151,9 +107,9 @@ class HTMLPurifier_Strategy_RemoveForeignElements extends HTMLPurifier_Strategy // check if we need to destroy all of the tag's children // CAN BE GENERICIZED if (isset($hidden_elements[$token->name])) { - if ($token->type == 'start') { + if ($token instanceof HTMLPurifier_Token_Start) { $remove_until = $token->name; - } elseif ($token->type == 'empty') { + } elseif ($token instanceof HTMLPurifier_Token_Empty) { // do nothing: we're still looking } else { $remove_until = false; @@ -164,7 +120,7 @@ class HTMLPurifier_Strategy_RemoveForeignElements extends HTMLPurifier_Strategy } continue; } - } elseif ($token->type == 'comment') { + } elseif ($token instanceof HTMLPurifier_Token_Comment) { // textify comments in script tags when they are allowed if ($textify_comments !== false) { $data = $token->data; @@ -174,7 +130,7 @@ class HTMLPurifier_Strategy_RemoveForeignElements extends HTMLPurifier_Strategy if ($e) $e->send(E_NOTICE, 'Strategy_RemoveForeignElements: Comment removed'); continue; } - } elseif ($token->type == 'text') { + } elseif ($token instanceof HTMLPurifier_Token_Text) { } else { continue; } diff --git a/lib/htmlpurifier/HTMLPurifier/Strategy/ValidateAttributes.php b/lib/htmlpurifier/HTMLPurifier/Strategy/ValidateAttributes.php index 6debcc336b..d2273ee925 100644 --- a/lib/htmlpurifier/HTMLPurifier/Strategy/ValidateAttributes.php +++ b/lib/htmlpurifier/HTMLPurifier/Strategy/ValidateAttributes.php @@ -1,11 +1,5 @@ type !== 'start' && $token->type !== 'empty') continue; + if (!$token instanceof HTMLPurifier_Token_Start && !$token instanceof HTMLPurifier_Token_Empty) continue; // skip tokens that are armored if (!empty($token->armor['ValidateAttributes'])) continue; diff --git a/lib/htmlpurifier/HTMLPurifier/StringHash.php b/lib/htmlpurifier/HTMLPurifier/StringHash.php new file mode 100644 index 0000000000..86cda25ef6 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/StringHash.php @@ -0,0 +1,37 @@ +accessed[$index] = true; + return parent::offsetGet($index); + } + + /** + * Returns a lookup array of all array indexes that have been accessed. + * @return Array in form array($index => true). + */ + public function getAccessed() { + return $this->accessed; + } + + /** + * Resets the access array. + */ + public function resetAccessed() { + $this->accessed = array(); + } +} diff --git a/lib/htmlpurifier/HTMLPurifier/StringHashParser.php b/lib/htmlpurifier/HTMLPurifier/StringHashParser.php new file mode 100644 index 0000000000..e96897d136 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/StringHashParser.php @@ -0,0 +1,104 @@ + 'DefaultKeyValue', + * 'KEY' => 'Value', + * 'KEY2' => 'Value2', + * 'MULTILINE-KEY' => "Multiline\nvalue.\n", + * ) + * + * We use this as an easy to use file-format for configuration schema + * files, but the class itself is usage agnostic. + * + * You can use ---- to forcibly terminate parsing of a single string-hash; + * this marker is used in multi string-hashes to delimit boundaries. + */ +class HTMLPurifier_StringHashParser +{ + + public $default = 'ID'; + + /** + * Parses a file that contains a single string-hash. + */ + public function parseFile($file) { + if (!file_exists($file)) return false; + $fh = fopen($file, 'r'); + if (!$fh) return false; + $ret = $this->parseHandle($fh); + fclose($fh); + return $ret; + } + + /** + * Parses a file that contains multiple string-hashes delimited by '----' + */ + public function parseMultiFile($file) { + if (!file_exists($file)) return false; + $ret = array(); + $fh = fopen($file, 'r'); + if (!$fh) return false; + while (!feof($fh)) { + $ret[] = $this->parseHandle($fh); + } + fclose($fh); + return $ret; + } + + /** + * Internal parser that acepts a file handle. + * @note While it's possible to simulate in-memory parsing by using + * custom stream wrappers, if such a use-case arises we should + * factor out the file handle into its own class. + * @param $fh File handle with pointer at start of valid string-hash + * block. + */ + protected function parseHandle($fh) { + $state = false; + $single = false; + $ret = array(); + do { + $line = fgets($fh); + if ($line === false) break; + $line = rtrim($line, "\n\r"); + if (!$state && $line === '') continue; + if ($line === '----') break; + if (strncmp('--', $line, 2) === 0) { + // Multiline declaration + $state = trim($line, '- '); + continue; + } elseif (!$state) { + $single = true; + if (strpos($line, ':') !== false) { + // Single-line declaration + list($state, $line) = explode(': ', $line, 2); + } else { + // Use default declaration + $state = $this->default; + } + } + if ($single) { + $ret[$state] = $line; + $single = false; + $state = false; + } else { + if (!isset($ret[$state])) $ret[$state] = ''; + $ret[$state] .= "$line\n"; + } + } while (!feof($fh)); + return $ret; + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/TagTransform.php b/lib/htmlpurifier/HTMLPurifier/TagTransform.php index f5de99ce49..6cdbdc1b50 100644 --- a/lib/htmlpurifier/HTMLPurifier/TagTransform.php +++ b/lib/htmlpurifier/HTMLPurifier/TagTransform.php @@ -1,18 +1,15 @@ 'xx-small', '1' => 'xx-small', '2' => 'small', @@ -36,10 +34,10 @@ class HTMLPurifier_TagTransform_Font extends HTMLPurifier_TagTransform '+4' => '300%' ); - function transform($tag, $config, &$context) { + public function transform($tag, $config, $context) { - if ($tag->type == 'end') { - $new_tag = $tag->copy(); + if ($tag instanceof HTMLPurifier_Token_End) { + $new_tag = clone $tag; $new_tag->name = $this->transform_to; return $new_tag; } @@ -83,7 +81,7 @@ class HTMLPurifier_TagTransform_Font extends HTMLPurifier_TagTransform $prepend_style; } - $new_tag = $tag->copy(); + $new_tag = clone $tag; $new_tag->name = $this->transform_to; $new_tag->attr = $attr; diff --git a/lib/htmlpurifier/HTMLPurifier/TagTransform/Simple.php b/lib/htmlpurifier/HTMLPurifier/TagTransform/Simple.php index 0b5a84d480..f68c6c2813 100644 --- a/lib/htmlpurifier/HTMLPurifier/TagTransform/Simple.php +++ b/lib/htmlpurifier/HTMLPurifier/TagTransform/Simple.php @@ -1,7 +1,5 @@ transform_to = $transform_to; $this->style = $style; } - function transform($tag, $config, &$context) { - $new_tag = $tag->copy(); + public function transform($tag, $config, $context) { + $new_tag = clone $tag; $new_tag->name = $this->transform_to; if (!is_null($this->style) && - ($new_tag->type == 'start' || $new_tag->type == 'empty') + ($new_tag instanceof HTMLPurifier_Token_Start || $new_tag instanceof HTMLPurifier_Token_Empty) ) { $this->prependCSS($new_tag->attr, $this->style); } diff --git a/lib/htmlpurifier/HTMLPurifier/Token.php b/lib/htmlpurifier/HTMLPurifier/Token.php index bd859d7f47..fd2ba53f25 100644 --- a/lib/htmlpurifier/HTMLPurifier/Token.php +++ b/lib/htmlpurifier/HTMLPurifier/Token.php @@ -1,163 +1,30 @@ is_a(). @public */ - var $line; /**< Line number node was on in source document. Null if unknown. @public */ + public $type; /**< Type of node to bypass is_a(). */ + public $line; /**< Line number node was on in source document. Null if unknown. */ /** * Lookup array of processing that this token is exempt from. * Currently, valid values are "ValidateAttributes" and * "MakeWellFormed_TagClosedError" */ - var $armor = array(); - - /** - * Copies the tag into a new one (clone substitute). - * @return Copied token - */ - function copy() { - return unserialize(serialize($this)); - } -} - -/** - * Abstract class of a tag token (start, end or empty), and its behavior. - */ -class HTMLPurifier_Token_Tag extends HTMLPurifier_Token // abstract -{ - /** - * Static bool marker that indicates the class is a tag. - * - * This allows us to check objects with !empty($obj->is_tag) - * without having to use a function call is_a(). - * - * @public - */ - var $is_tag = true; - - /** - * The lower-case name of the tag, like 'a', 'b' or 'blockquote'. - * - * @note Strictly speaking, XML tags are case sensitive, so we shouldn't - * be lower-casing them, but these tokens cater to HTML tags, which are - * insensitive. - * - * @public - */ - var $name; - - /** - * Associative array of the tag's attributes. - */ - var $attr = array(); - - /** - * Non-overloaded constructor, which lower-cases passed tag name. - * - * @param $name String name. - * @param $attr Associative array of attributes. - */ - function HTMLPurifier_Token_Tag($name, $attr = array(), $line = null) { - $this->name = ctype_lower($name) ? $name : strtolower($name); - foreach ($attr as $key => $value) { - // normalization only necessary when key is not lowercase - if (!ctype_lower($key)) { - $new_key = strtolower($key); - if (!isset($attr[$new_key])) { - $attr[$new_key] = $attr[$key]; - } - if ($new_key !== $key) { - unset($attr[$key]); - } - } + public $armor = array(); + + public function __get($n) { + if ($n === 'type') { + trigger_error('Deprecated type property called; use instanceof', E_USER_NOTICE); + switch (get_class($this)) { + case 'HTMLPurifier_Token_Start': return 'start'; + case 'HTMLPurifier_Token_Empty': return 'empty'; + case 'HTMLPurifier_Token_End': return 'end'; + case 'HTMLPurifier_Token_Text': return 'text'; + case 'HTMLPurifier_Token_Comment': return 'comment'; + default: return null; } - $this->attr = $attr; - $this->line = $line; - } -} - -/** - * Concrete start token class. - */ -class HTMLPurifier_Token_Start extends HTMLPurifier_Token_Tag -{ - var $type = 'start'; -} - -/** - * Concrete empty token class. - */ -class HTMLPurifier_Token_Empty extends HTMLPurifier_Token_Tag -{ - var $type = 'empty'; -} - -/** - * Concrete end token class. - * - * @warning This class accepts attributes even though end tags cannot. This - * is for optimization reasons, as under normal circumstances, the Lexers - * do not pass attributes. - */ -class HTMLPurifier_Token_End extends HTMLPurifier_Token_Tag -{ - var $type = 'end'; -} - -/** - * Concrete text token class. - * - * Text tokens comprise of regular parsed character data (PCDATA) and raw - * character data (from the CDATA sections). Internally, their - * data is parsed with all entities expanded. Surprisingly, the text token - * does have a "tag name" called #PCDATA, which is how the DTD represents it - * in permissible child nodes. - */ -class HTMLPurifier_Token_Text extends HTMLPurifier_Token -{ - - var $name = '#PCDATA'; /**< PCDATA tag name compatible with DTD. @public */ - var $type = 'text'; - var $data; /**< Parsed character data of text. @public */ - var $is_whitespace; /**< Bool indicating if node is whitespace. @public */ - - /** - * Constructor, accepts data and determines if it is whitespace. - * - * @param $data String parsed character data. - */ - function HTMLPurifier_Token_Text($data, $line = null) { - $this->data = $data; - $this->is_whitespace = ctype_space($data); - $this->line = $line; + } } - } - -/** - * Concrete comment token class. Generally will be ignored. - */ -class HTMLPurifier_Token_Comment extends HTMLPurifier_Token -{ - var $data; /**< Character data within comment. @public */ - var $type = 'comment'; - /** - * Transparent constructor. - * - * @param $data String comment data. - */ - function HTMLPurifier_Token_Comment($data, $line = null) { - $this->data = $data; - $this->line = $line; - } -} - diff --git a/lib/htmlpurifier/HTMLPurifier/Token/Comment.php b/lib/htmlpurifier/HTMLPurifier/Token/Comment.php new file mode 100644 index 0000000000..1571a40dc1 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/Token/Comment.php @@ -0,0 +1,19 @@ +data = $data; + $this->line = $line; + } +} + diff --git a/lib/htmlpurifier/HTMLPurifier/Token/Empty.php b/lib/htmlpurifier/HTMLPurifier/Token/Empty.php new file mode 100644 index 0000000000..0623f7ac25 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/Token/Empty.php @@ -0,0 +1,9 @@ +!empty($obj->is_tag) + * without having to use a function call is_a(). + */ + public $is_tag = true; + + /** + * The lower-case name of the tag, like 'a', 'b' or 'blockquote'. + * + * @note Strictly speaking, XML tags are case sensitive, so we shouldn't + * be lower-casing them, but these tokens cater to HTML tags, which are + * insensitive. + */ + public $name; + + /** + * Associative array of the tag's attributes. + */ + public $attr = array(); + + /** + * Non-overloaded constructor, which lower-cases passed tag name. + * + * @param $name String name. + * @param $attr Associative array of attributes. + */ + public function __construct($name, $attr = array(), $line = null) { + $this->name = ctype_lower($name) ? $name : strtolower($name); + foreach ($attr as $key => $value) { + // normalization only necessary when key is not lowercase + if (!ctype_lower($key)) { + $new_key = strtolower($key); + if (!isset($attr[$new_key])) { + $attr[$new_key] = $attr[$key]; + } + if ($new_key !== $key) { + unset($attr[$key]); + } + } + } + $this->attr = $attr; + $this->line = $line; + } +} diff --git a/lib/htmlpurifier/HTMLPurifier/Token/Text.php b/lib/htmlpurifier/HTMLPurifier/Token/Text.php new file mode 100644 index 0000000000..3942f8a0ae --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/Token/Text.php @@ -0,0 +1,30 @@ +data = $data; + $this->is_whitespace = ctype_space($data); + $this->line = $line; + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/TokenFactory.php b/lib/htmlpurifier/HTMLPurifier/TokenFactory.php index d15ee1a9e1..bff693f418 100644 --- a/lib/htmlpurifier/HTMLPurifier/TokenFactory.php +++ b/lib/htmlpurifier/HTMLPurifier/TokenFactory.php @@ -1,17 +1,15 @@ p_start; - $p->HTMLPurifier_Token_Tag($name, $attr); + $p->__construct($name, $attr); return $p; } @@ -53,7 +51,7 @@ class HTMLPurifier_TokenFactory */ public function createEnd($name) { $p = clone $this->p_end; - $p->HTMLPurifier_Token_Tag($name); + $p->__construct($name); return $p; } @@ -65,7 +63,7 @@ class HTMLPurifier_TokenFactory */ public function createEmpty($name, $attr = array()) { $p = clone $this->p_empty; - $p->HTMLPurifier_Token_Tag($name, $attr); + $p->__construct($name, $attr); return $p; } @@ -76,7 +74,7 @@ class HTMLPurifier_TokenFactory */ public function createText($data) { $p = clone $this->p_text; - $p->HTMLPurifier_Token_Text($data); + $p->__construct($data); return $p; } @@ -87,7 +85,7 @@ class HTMLPurifier_TokenFactory */ public function createComment($data) { $p = clone $this->p_comment; - $p->HTMLPurifier_Token_Comment($data); + $p->__construct($data); return $p; } diff --git a/lib/htmlpurifier/HTMLPurifier/URI.php b/lib/htmlpurifier/HTMLPurifier/URI.php index c68fc48866..43f1b19287 100644 --- a/lib/htmlpurifier/HTMLPurifier/URI.php +++ b/lib/htmlpurifier/HTMLPurifier/URI.php @@ -1,8 +1,5 @@ scheme = is_null($scheme) || ctype_lower($scheme) ? $scheme : strtolower($scheme); $this->userinfo = $userinfo; $this->host = $host; @@ -35,8 +32,8 @@ class HTMLPurifier_URI * @param $context Instance of HTMLPurifier_Context * @return Scheme object appropriate for validating this URI */ - function getSchemeObj($config, &$context) { - $registry =& HTMLPurifier_URISchemeRegistry::instance(); + public function getSchemeObj($config, $context) { + $registry = HTMLPurifier_URISchemeRegistry::instance(); if ($this->scheme !== null) { $scheme_obj = $registry->getScheme($this->scheme, $config, $context); if (!$scheme_obj) return false; // invalid scheme, clean it out @@ -63,7 +60,7 @@ class HTMLPurifier_URI * @param $context Instance of HTMLPurifier_Context * @return True if validation/filtering succeeds, false if failure */ - function validate($config, &$context) { + public function validate($config, $context) { // ABNF definitions from RFC 3986 $chars_sub_delims = '!$&\'()*+,;='; @@ -139,7 +136,7 @@ class HTMLPurifier_URI * Convert URI back to string * @return String URI appropriate for output */ - function toString() { + public function toString() { // reconstruct authority $authority = null; if (!is_null($this->host)) { @@ -160,12 +157,5 @@ class HTMLPurifier_URI return $result; } - /** - * Returns a copy of the URI object - */ - function copy() { - return unserialize(serialize($this)); - } - } diff --git a/lib/htmlpurifier/HTMLPurifier/URIDefinition.php b/lib/htmlpurifier/HTMLPurifier/URIDefinition.php index 45c505edb0..390d97ec15 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIDefinition.php +++ b/lib/htmlpurifier/HTMLPurifier/URIDefinition.php @@ -1,118 +1,49 @@ - Unique identifier for a custom-built URI definition. If you want - to add custom URIFilters, you must specify this value. - This directive has been available since 2.1.0. -

-'); - -HTMLPurifier_ConfigSchema::define( - 'URI', 'DefinitionRev', 1, 'int', ' -

- Revision identifier for your custom definition. See - %HTML.DefinitionRev for details. This directive has been available - since 2.1.0. -

-'); - -// informative URI directives - -HTMLPurifier_ConfigSchema::define( - 'URI', 'DefaultScheme', 'http', 'string', ' -

- Defines through what scheme the output will be served, in order to - select the proper object validator when no scheme information is present. -

-'); - -HTMLPurifier_ConfigSchema::define( - 'URI', 'Host', null, 'string/null', ' -

- Defines the domain name of the server, so we can determine whether or - an absolute URI is from your website or not. Not strictly necessary, - as users should be using relative URIs to reference resources on your - website. It will, however, let you use absolute URIs to link to - subdomains of the domain you post here: i.e. example.com will allow - sub.example.com. However, higher up domains will still be excluded: - if you set %URI.Host to sub.example.com, example.com will be blocked. - Note: This directive overrides %URI.Base because - a given page may be on a sub-domain, but you wish HTML Purifier to be - more relaxed and allow some of the parent domains too. - This directive has been available since 1.2.0. -

-'); - -HTMLPurifier_ConfigSchema::define( - 'URI', 'Base', null, 'string/null', ' -

- The base URI is the URI of the document this purified HTML will be - inserted into. This information is important if HTML Purifier needs - to calculate absolute URIs from relative URIs, such as when %URI.MakeAbsolute - is on. You may use a non-absolute URI for this value, but behavior - may vary (%URI.MakeAbsolute deals nicely with both absolute and - relative paths, but forwards-compatibility is not guaranteed). - Warning: If set, the scheme on this URI - overrides the one specified by %URI.DefaultScheme. This directive has - been available since 2.1.0. -

-'); - class HTMLPurifier_URIDefinition extends HTMLPurifier_Definition { - var $type = 'URI'; - var $filters = array(); - var $registeredFilters = array(); + public $type = 'URI'; + protected $filters = array(); + protected $registeredFilters = array(); /** * HTMLPurifier_URI object of the base specified at %URI.Base */ - var $base; + public $base; /** - * String host to consider "home" base + * String host to consider "home" base, derived off of $base */ - var $host; + public $host; /** * Name of default scheme based on %URI.DefaultScheme and %URI.Base */ - var $defaultScheme; + public $defaultScheme; - function HTMLPurifier_URIDefinition() { + public function __construct() { $this->registerFilter(new HTMLPurifier_URIFilter_DisableExternal()); $this->registerFilter(new HTMLPurifier_URIFilter_DisableExternalResources()); $this->registerFilter(new HTMLPurifier_URIFilter_HostBlacklist()); $this->registerFilter(new HTMLPurifier_URIFilter_MakeAbsolute()); } - function registerFilter($filter) { + public function registerFilter($filter) { $this->registeredFilters[$filter->name] = $filter; } - function addFilter($filter, $config) { + public function addFilter($filter, $config) { $filter->prepare($config); $this->filters[$filter->name] = $filter; } - function doSetup($config) { + protected function doSetup($config) { $this->setupMemberVariables($config); $this->setupFilters($config); } - function setupFilters($config) { + protected function setupFilters($config) { foreach ($this->registeredFilters as $name => $filter) { $conf = $config->get('URI', $name); if ($conf !== false && $conf !== null) { @@ -122,7 +53,7 @@ class HTMLPurifier_URIDefinition extends HTMLPurifier_Definition unset($this->registeredFilters); } - function setupMemberVariables($config) { + protected function setupMemberVariables($config) { $this->host = $config->get('URI', 'Host'); $base_uri = $config->get('URI', 'Base'); if (!is_null($base_uri)) { @@ -134,7 +65,7 @@ class HTMLPurifier_URIDefinition extends HTMLPurifier_Definition if (is_null($this->defaultScheme)) $this->defaultScheme = $config->get('URI', 'DefaultScheme'); } - function filter(&$uri, $config, &$context) { + public function filter(&$uri, $config, $context) { foreach ($this->filters as $name => $x) { $result = $this->filters[$name]->filter($uri, $config, $context); if (!$result) return false; diff --git a/lib/htmlpurifier/HTMLPurifier/URIFilter.php b/lib/htmlpurifier/HTMLPurifier/URIFilter.php index ca000ea5a2..0108258f7e 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIFilter.php +++ b/lib/htmlpurifier/HTMLPurifier/URIFilter.php @@ -11,30 +11,28 @@ * you check that it exists. This allows filters to convert * proprietary URI schemes into regular ones. */ -class HTMLPurifier_URIFilter +abstract class HTMLPurifier_URIFilter { /** * Unique identifier of filter */ - var $name; + public $name; /** * Performs initialization for the filter */ - function prepare($config) {} + public function prepare($config) {} /** * Filter a URI object - * @param &$uri Reference to URI object + * @param $uri Reference to URI object variable * @param $config Instance of HTMLPurifier_Config - * @param &$context Instance of HTMLPurifier_Context + * @param $context Instance of HTMLPurifier_Context * @return bool Whether or not to continue processing: false indicates * URL is no good, true indicates continue processing. Note that * all changes are committed directly on the URI object */ - function filter(&$uri, $config, &$context) { - trigger_error('Cannot call abstract function', E_USER_ERROR); - } + abstract public function filter(&$uri, $config, $context); } diff --git a/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternal.php b/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternal.php index 4e6dc187c8..d48bce06bd 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternal.php +++ b/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternal.php @@ -1,26 +1,14 @@ get('URI', 'Host'); if ($our_host !== null) $this->ourHostParts = array_reverse(explode('.', $our_host)); } - function filter(&$uri, $config, &$context) { + public function filter(&$uri, $config, $context) { if (is_null($uri->host)) return true; if ($this->ourHostParts === false) return false; $host_parts = array_reverse(explode('.', $uri->host)); diff --git a/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternalResources.php b/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternalResources.php index dc00e74110..9e4e7bdd2a 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternalResources.php +++ b/lib/htmlpurifier/HTMLPurifier/URIFilter/DisableExternalResources.php @@ -1,24 +1,9 @@ get('EmbeddedURI', true)) return true; return parent::filter($uri, $config, $context); } diff --git a/lib/htmlpurifier/HTMLPurifier/URIFilter/HostBlacklist.php b/lib/htmlpurifier/HTMLPurifier/URIFilter/HostBlacklist.php index d3429d5cbf..bd71970103 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIFilter/HostBlacklist.php +++ b/lib/htmlpurifier/HTMLPurifier/URIFilter/HostBlacklist.php @@ -1,23 +1,13 @@ moo.com will catch moo.com.example.com. '. - 'This directive has been available since 1.3.0.' -); - class HTMLPurifier_URIFilter_HostBlacklist extends HTMLPurifier_URIFilter { - var $name = 'HostBlacklist'; - var $blacklist = array(); - function prepare($config) { + public $name = 'HostBlacklist'; + protected $blacklist = array(); + public function prepare($config) { $this->blacklist = $config->get('URI', 'HostBlacklist'); } - function filter(&$uri, $config, &$context) { + public function filter(&$uri, $config, $context) { foreach($this->blacklist as $blacklisted_host_fragment) { if (strpos($uri->host, $blacklisted_host_fragment) !== false) { return false; diff --git a/lib/htmlpurifier/HTMLPurifier/URIFilter/MakeAbsolute.php b/lib/htmlpurifier/HTMLPurifier/URIFilter/MakeAbsolute.php index 8fe4f73e61..647f779e9a 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIFilter/MakeAbsolute.php +++ b/lib/htmlpurifier/HTMLPurifier/URIFilter/MakeAbsolute.php @@ -2,25 +2,12 @@ // does not support network paths -require_once 'HTMLPurifier/URIFilter.php'; - -HTMLPurifier_ConfigSchema::define( - 'URI', 'MakeAbsolute', false, 'bool', ' -

- Converts all URIs into absolute forms. This is useful when the HTML - being filtered assumes a specific base path, but will actually be - viewed in a different context (and setting an alternate base URI is - not possible). %URI.Base must be set for this directive to work. - This directive has been available since 2.1.0. -

-'); - class HTMLPurifier_URIFilter_MakeAbsolute extends HTMLPurifier_URIFilter { - var $name = 'MakeAbsolute'; - var $base; - var $basePathStack = array(); - function prepare($config) { + public $name = 'MakeAbsolute'; + protected $base; + protected $basePathStack = array(); + public function prepare($config) { $def = $config->getDefinition('URI'); $this->base = $def->base; if (is_null($this->base)) { @@ -33,14 +20,14 @@ class HTMLPurifier_URIFilter_MakeAbsolute extends HTMLPurifier_URIFilter $stack = $this->_collapseStack($stack); // do pre-parsing $this->basePathStack = $stack; } - function filter(&$uri, $config, &$context) { + public function filter(&$uri, $config, $context) { if (is_null($this->base)) return true; // abort early if ( $uri->path === '' && is_null($uri->scheme) && is_null($uri->host) && is_null($uri->query) && is_null($uri->fragment) ) { // reference to current document - $uri = $this->base->copy(); + $uri = clone $this->base; return true; } if (!is_null($uri->scheme)) { @@ -80,9 +67,8 @@ class HTMLPurifier_URIFilter_MakeAbsolute extends HTMLPurifier_URIFilter /** * Resolve dots and double-dots in a path stack - * @private */ - function _collapseStack($stack) { + private function _collapseStack($stack) { $result = array(); for ($i = 0; isset($stack[$i]); $i++) { $is_folder = false; diff --git a/lib/htmlpurifier/HTMLPurifier/URIParser.php b/lib/htmlpurifier/HTMLPurifier/URIParser.php index 8ba485cf35..0ea51762b8 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIParser.php +++ b/lib/htmlpurifier/HTMLPurifier/URIParser.php @@ -1,7 +1,5 @@ percentEncoder = new HTMLPurifier_PercentEncoder(); } @@ -24,7 +22,7 @@ class HTMLPurifier_URIParser * @return HTMLPurifier_URI representation of URI. This representation has * not been validated yet and may not conform to RFC. */ - function parse($uri) { + public function parse($uri) { $uri = $this->percentEncoder->normalize($uri); diff --git a/lib/htmlpurifier/HTMLPurifier/URIScheme.php b/lib/htmlpurifier/HTMLPurifier/URIScheme.php index 41c02f70d2..fada38700f 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIScheme.php +++ b/lib/htmlpurifier/HTMLPurifier/URIScheme.php @@ -8,22 +8,20 @@ class HTMLPurifier_URIScheme /** * Scheme's default port (integer) - * @public */ - var $default_port = null; + public $default_port = null; /** * Whether or not URIs of this schem are locatable by a browser * http and ftp are accessible, while mailto and news are not. - * @public */ - var $browsable = false; + public $browsable = false; /** * Whether or not the URI always uses , resolves edge cases * with making relative URIs absolute */ - var $hierarchical = false; + public $hierarchical = false; /** * Validates the components of a URI @@ -34,7 +32,7 @@ class HTMLPurifier_URIScheme * @param $context HTMLPurifier_Context object * @return Bool success or failure */ - function validate(&$uri, $config, &$context) { + public function validate(&$uri, $config, $context) { if ($this->default_port == $uri->port) $uri->port = null; return true; } diff --git a/lib/htmlpurifier/HTMLPurifier/URIScheme/ftp.php b/lib/htmlpurifier/HTMLPurifier/URIScheme/ftp.php index 5555ef33a1..2d7580f33c 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIScheme/ftp.php +++ b/lib/htmlpurifier/HTMLPurifier/URIScheme/ftp.php @@ -1,17 +1,15 @@ query = null; diff --git a/lib/htmlpurifier/HTMLPurifier/URIScheme/http.php b/lib/htmlpurifier/HTMLPurifier/URIScheme/http.php index 7abc6680fd..10d89c0ffe 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIScheme/http.php +++ b/lib/htmlpurifier/HTMLPurifier/URIScheme/http.php @@ -1,17 +1,15 @@ userinfo = null; return true; diff --git a/lib/htmlpurifier/HTMLPurifier/URIScheme/https.php b/lib/htmlpurifier/HTMLPurifier/URIScheme/https.php index bbd69b9c42..bd670401b9 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIScheme/https.php +++ b/lib/htmlpurifier/HTMLPurifier/URIScheme/https.php @@ -1,13 +1,11 @@ userinfo = null; $uri->host = null; diff --git a/lib/htmlpurifier/HTMLPurifier/URIScheme/news.php b/lib/htmlpurifier/HTMLPurifier/URIScheme/news.php index 87bda63c7f..d862e2e13e 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIScheme/news.php +++ b/lib/htmlpurifier/HTMLPurifier/URIScheme/news.php @@ -1,15 +1,13 @@ userinfo = null; $uri->host = null; diff --git a/lib/htmlpurifier/HTMLPurifier/URIScheme/nntp.php b/lib/htmlpurifier/HTMLPurifier/URIScheme/nntp.php index caa85b260f..88b613b6ae 100644 --- a/lib/htmlpurifier/HTMLPurifier/URIScheme/nntp.php +++ b/lib/htmlpurifier/HTMLPurifier/URIScheme/nntp.php @@ -1,16 +1,14 @@ userinfo = null; $uri->query = null; diff --git a/lib/htmlpurifier/HTMLPurifier/URISchemeRegistry.php b/lib/htmlpurifier/HTMLPurifier/URISchemeRegistry.php index 6837fadaaf..349fa0f6f7 100644 --- a/lib/htmlpurifier/HTMLPurifier/URISchemeRegistry.php +++ b/lib/htmlpurifier/HTMLPurifier/URISchemeRegistry.php @@ -1,35 +1,5 @@ true, // "Hypertext Transfer Protocol", nuf' said - 'https' => true, // HTTP over SSL (Secure Socket Layer) - // quite useful, but not necessary - 'mailto' => true,// Email - 'ftp' => true, // "File Transfer Protocol" - // for Usenet, these two are similar, but distinct - 'nntp' => true, // individual Netnews articles - 'news' => true // newsgroup or individual Netnews articles - ), 'lookup', - 'Whitelist that defines the schemes that a URI is allowed to have. This '. - 'prevents XSS attacks from using pseudo-schemes like javascript or mocha.' -); - -HTMLPurifier_ConfigSchema::define( - 'URI', 'OverrideAllowedSchemes', true, 'bool', - 'If this is set to true (which it is by default), you can override '. - '%URI.AllowedSchemes by simply registering a HTMLPurifier_URIScheme '. - 'to the registry. If false, you will also have to update that directive '. - 'in order to add more schemes.' -); - /** * Registry for retrieving specific URI scheme validator objects. */ @@ -38,13 +8,12 @@ class HTMLPurifier_URISchemeRegistry /** * Retrieve sole instance of the registry. - * @static * @param $prototype Optional prototype to overload sole instance with, * or bool true to reset to default registry. * @note Pass a registry object $prototype with a compatible interface and * the function will copy it and return it all further times. */ - function &instance($prototype = null) { + public static function instance($prototype = null) { static $instance = null; if ($prototype !== null) { $instance = $prototype; @@ -56,9 +25,8 @@ class HTMLPurifier_URISchemeRegistry /** * Cache of retrieved schemes. - * @protected */ - var $schemes = array(); + protected $schemes = array(); /** * Retrieves a scheme validator object @@ -66,7 +34,7 @@ class HTMLPurifier_URISchemeRegistry * @param $config HTMLPurifier_Config object * @param $config HTMLPurifier_Context object */ - function &getScheme($scheme, $config, &$context) { + public function getScheme($scheme, $config, $context) { if (!$config) $config = HTMLPurifier_Config::createDefault(); $null = null; // for the sake of passing by reference @@ -92,8 +60,8 @@ class HTMLPurifier_URISchemeRegistry * @param $scheme Scheme name * @param $scheme_obj HTMLPurifier_URIScheme object */ - function register($scheme, &$scheme_obj) { - $this->schemes[$scheme] =& $scheme_obj; + public function register($scheme, $scheme_obj) { + $this->schemes[$scheme] = $scheme_obj; } } diff --git a/lib/htmlpurifier/HTMLPurifier/VarParser.php b/lib/htmlpurifier/HTMLPurifier/VarParser.php new file mode 100644 index 0000000000..418622be55 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/VarParser.php @@ -0,0 +1,125 @@ + true, + 'istring' => true, + 'text' => true, + 'itext' => true, + 'int' => true, + 'float' => true, + 'bool' => true, + 'lookup' => true, + 'list' => true, + 'hash' => true, + 'mixed' => true + ); + + /** + * Lookup table of types that are string, and can have aliases or + * allowed value lists. + */ + static public $stringTypes = array( + 'string' => true, + 'istring' => true, + 'text' => true, + 'itext' => true, + ); + + /** + * Validate a variable according to type. Throws + * HTMLPurifier_VarParserException if invalid. + * It may return NULL as a valid type if $allow_null is true. + * + * @param $var Variable to validate + * @param $type Type of variable, see HTMLPurifier_VarParser->types + * @param $allow_null Whether or not to permit null as a value + * @return Validated and type-coerced variable + */ + final public function parse($var, $type, $allow_null = false) { + if (!isset(HTMLPurifier_VarParser::$types[$type])) { + throw new HTMLPurifier_VarParserException("Invalid type '$type'"); + } + $var = $this->parseImplementation($var, $type, $allow_null); + if ($allow_null && $var === null) return null; + // These are basic checks, to make sure nothing horribly wrong + // happened in our implementations. + switch ($type) { + case 'string': + case 'istring': + case 'text': + case 'itext': + if (!is_string($var)) break; + if ($type[0] == 'i') $var = strtolower($var); + return $var; + case 'int': + if (!is_int($var)) break; + return $var; + case 'float': + if (!is_float($var)) break; + return $var; + case 'bool': + if (!is_bool($var)) break; + return $var; + case 'lookup': + case 'list': + case 'hash': + if (!is_array($var)) break; + if ($type === 'lookup') { + foreach ($var as $k) if ($k !== true) $this->error('Lookup table contains value other than true'); + } elseif ($type === 'list') { + $keys = array_keys($var); + if (array_keys($keys) !== $keys) $this->error('Indices for list are not uniform'); + } + return $var; + case 'mixed': + return $var; + default: + $this->errorInconsistent(get_class($this), $type); + } + $this->errorGeneric($var, $type); + } + + /** + * Actually implements the parsing. Base implementation is to not + * do anything to $var. Subclasses should overload this! + */ + protected function parseImplementation($var, $type, $allow_null) { + return $var; + } + + /** + * Throws an exception. + */ + protected function error($msg) { + throw new HTMLPurifier_VarParserException($msg); + } + + /** + * Throws an inconsistency exception. + * @note This should not ever be called. It would be called if we + * extend the allowed values of HTMLPurifier_VarParser without + * updating subclasses. + */ + protected function errorInconsistent($class, $type) { + throw new HTMLPurifier_Exception("Inconsistency in $class: $type not implemented"); + } + + /** + * Generic error for if a type didn't work. + */ + protected function errorGeneric($var, $type) { + $vtype = gettype($var); + $this->error("Expected type $type, got $vtype"); + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/VarParser/Flexible.php b/lib/htmlpurifier/HTMLPurifier/VarParser/Flexible.php new file mode 100644 index 0000000000..a2041fdd34 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/VarParser/Flexible.php @@ -0,0 +1,94 @@ + $j) $var[$i] = trim($j); + if ($type === 'hash') { + // key:value,key2:value2 + $nvar = array(); + foreach ($var as $keypair) { + $c = explode(':', $keypair, 2); + if (!isset($c[1])) continue; + $nvar[$c[0]] = $c[1]; + } + $var = $nvar; + } + } + if (!is_array($var)) break; + $keys = array_keys($var); + if ($keys === array_keys($keys)) { + if ($type == 'list') return $var; + elseif ($type == 'lookup') { + $new = array(); + foreach ($var as $key) { + $new[$key] = true; + } + return $new; + } else break; + } + if ($type === 'lookup') { + foreach ($var as $key => $value) { + $var[$key] = true; + } + } + return $var; + default: + $this->errorInconsistent(__CLASS__, $type); + } + $this->errorGeneric($var, $type); + } + +} diff --git a/lib/htmlpurifier/HTMLPurifier/VarParser/Native.php b/lib/htmlpurifier/HTMLPurifier/VarParser/Native.php new file mode 100644 index 0000000000..3bfa90ae5c --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/VarParser/Native.php @@ -0,0 +1,25 @@ +evalExpression($var); + } + + protected function evalExpression($expr) { + $var = null; + $result = eval("\$var = $expr;"); + if ($result === false) { + throw new HTMLPurifier_VarParserException("Fatal error in evaluated code"); + } + return $var; + } + +} + diff --git a/lib/htmlpurifier/HTMLPurifier/VarParserException.php b/lib/htmlpurifier/HTMLPurifier/VarParserException.php new file mode 100644 index 0000000000..fc415d4637 --- /dev/null +++ b/lib/htmlpurifier/HTMLPurifier/VarParserException.php @@ -0,0 +1,9 @@ +, , and tags * HMLTModule/XMLCommonAttributes.php - remove xml:lang - needed for multilang * AttrDef/Lang.php - relax lang check - needed for multilang - * AttrDef/URI/Email/SimpleCheck.php - deleted to prevent errors on some systems, not used anyway + + * temporary work dir fix from http://htmlpurifier.org/phorum/read.php?2,1809,1809#msg-1809 skodak diff --git a/lib/weblib.php b/lib/weblib.php index 16d987d24f..9e2bbf21dd 100644 --- a/lib/weblib.php +++ b/lib/weblib.php @@ -1890,14 +1890,15 @@ function purify_html($text) { global $CFG; // this can not be done only once because we sometimes need to reset the cache - $cachedir = $CFG->dataroot.'/cache/htmlpurifier/'; + $cachedir = $CFG->dataroot.'/cache/htmlpurifier'; $status = check_dir_exists($cachedir, true, true); static $purifier = false; + static $config; if ($purifier === false) { - require_once $CFG->libdir.'/htmlpurifier/HTMLPurifier.auto.php'; + require_once $CFG->libdir.'/htmlpurifier/HTMLPurifier.safe-includes.php'; $config = HTMLPurifier_Config::createDefault(); - $config->set('Core', 'AcceptFullDocuments', false); + $config->set('Core', 'ConvertDocumentToFragment', true); $config->set('Core', 'Encoding', 'UTF-8'); $config->set('HTML', 'Doctype', 'XHTML 1.0 Transitional'); $config->set('Cache', 'SerializerPath', $cachedir); -- 2.39.5