AO Encoding Changelog


Release Notes

  • Added support for java.nio.charset.Charset.
  • Implemented CSS encoding.
  • Added EncodingContext.getCharacterEncoding() to get output character encoding.
  • Increased number of validation skips and substitutions through new tests that verify all characters.
  • Encoder suffix and validate now accept optional trim, when trimmed, validation is applied after trimming.
  • MediaWriter now unwraps the writer via Coercion.optimize(Writer, Encoder).
  • Now throws new InvalidCharacterException when invalid characters are detected instead of less specific IOException.
  • Removed self-referential generics that were emulating self-types. Instead, manually overloading all methods. Although a bit tedious in the implementation, this cleans-up the API by removing unnecessary type parameter.
  • Removed deprecated items:
    1. com.aoapps.encoding.Coercion
    2. com.aoapps.encoding.MediaValidator.validate()
    3. com.aoapps.encoding.Supplier
  • New ValidateOnlyEncoder that may be used for MediaWriter when no character encoding is required.
  • Per-type output interfaces with related per-type writer implementations:
    1. Renamed WhitespaceWriter to Whitespace
    2. Renamed TextWriter to Text
    3. Text no longer extends Whitespace, implementations that require both can either extend both or use the intersection type Text & Whitespace.
    4. Per-type interfaces provide writer/content-agnostic output while minimizing implementation boilerplate.
    5. Per-type MediaWriter implementations, with convenient per-content-type methods for all supported content types.
    6. Per-type MediaWritable functional interfaces.
  • Renamed lowerCamelCase from "javaScript" to "javascript" (so javascript reads as a single word), for example, is now "javascriptInXhtmlAttributeEncoder" and "textInJavascriptEncoder".

    We did not leave any deprecated compatibility methods. This is a major version bump that may require minor source changes to those upgrading.

  • Added support for translation markups to CharSequence encoders.
  • Implementation is now 100% thread-safe.
  • Indentation changed from tab to two-space for consistency with the new AO Checkstyle Config project, which itself is based on Google Java Style Guide.


Release Notes

  • Fixed bug in MediaWriter.text() that incorrectly encoded suffix.


Release Notes

  • New BufferedValidator that buffers all writes for a single final validation. This allows manipulation of the buffered content before validation, such as trimming URLs.
  • MediaValidators must now have validate() called when validation is completed.
  • URL encoders and validators now trim the URL before validation.
  • URL encoders and validators now support both RFC 3986 URI and RFC 3987 IRI.


Release Notes

  • MediaWriter now correctly runs newlines, indents, and spaces through the encoder. Previously, it was bypassing the encoder and writing directly.


Release Notes

  • Fixed NPE in streaming text encoding in MediaWriter.


Release Notes

  • Now supports Java 9+ modules with included module-info.class.
  • Maven artifact relocated from com.aoindustries:ao-encoding to com.aoapps:ao-encoding.
  • Package renamed from com.aoindustries.encoding to com.aoapps.encoding.


Release Notes

  • Doctype.xmlDeclaration(…) now returns a boolean whether written.
  • Doctype.doctype(…) now returns a boolean whether written.
  • Added TextWriter.text(CharSequence) and TextWriter.text(CharSequence,int,int), which allow for both optimizations and access to characters for automatic newline and indentation.
  • Added support for Optional to TextWriter.text(Object). This allows access to characters for automatic newline and indentation.
  • TextWriter.text(char[]) and TextWriter.text(char[],int,int) now accept null, and will simply perform no write.
  • TextWriter.text(Object) now supports Writable that isFastToString(), which allows for both optimizations and access to characters for automatic newline and indentation.
  • MediaType.toString() now returns the content type.


Release Notes

  • Added space-writing methods WhitespaceWriter.sp(…), which support writing any number of ASCII spaces while possibly bypassing character validation and/or encoding in some contexts.
  • Added non-breaking-space-writing methods TextWriter.nbsp(…), which support writing any number of non-breaking spaces while possibly bypassing character validation and/or encoding in some contexts.
  • Strings for writing whitespace are now public, static, fixed size, and reused. The previous implementation would dynamically allocate larger strings without any limit to size.


Release Notes

  • Despite seeming like a good idea after a programming binge, automatic indentation on newline was a flawed idea. Newline nl() and indentation indent() are now separate methods, with a shortcut nli() to perform both.


Release Notes

  • MediaWriter now supports tab indentation.


Release Notes

  • Deprecated Supplier in favor of new IOSupplierE.


Release Notes

  • Coercion moved out of this project:
    1. Non-localized parts moved to AO Lang.
    2. Localized parts moved to AO Hodgepodge and renamed to MarkupCoercion.
    3. New pluggable CoercionOptimizer to allow this decoupling.
    4. Servlet-specific optimizations moved to AO Servlet Util.


Release Notes

  • Updated dependencies.


Release Notes

  • Split development-only classes into a new sub-project in devel/. This sub-project is used only for development and is never deployed to artifact repositories.
  • Reverted a previous change made on 2020-03-01 that was released in version 3.0.0 on 2020-03-26. Encoding of in-context translation lookup markups is required after all.

    One example is the lookup IDs added inside alt attributes like alt="&lt;##&lt;value&gt;##&gt;". With this bug, this was incorrectly written as alt="<##<value>##>", which fails XML validation.

    This bug is unlikely to affect production systems for two reasons:

    1. Lookup markups are only performed when in-context translations are enabled, which is only when in development mode.
    2. Most production sites are served in SGML mode, where browsers will handle the incorrect HTML formatting. XML mode is used in development specifically for this stricter validation.


Release Notes

  • Moved a few date/time methods from ChainWriter to AOWeb Struts. This avoids adding a dependency on the new AO SQL project that has been split from AO Lang and AO Hodgepodge:

    1. Moved ChainWriter.writeDateJavaScript(…) to DateTag.
    2. Moved ChainWriter.writeDateTimeJavaScript(…) to DateTimeTag.
    3. Moved ChainWriter.writeTimeJavaScript(…) to TimeTag.

    Although technically a breaking change, we are only incrementing the minor version number. This is legacy code that is not central to this encoding API and is not widely used. In fact, ChainWriter should probably not be part of this API at all, but it has no better home at this time.


Release Notes

  • Minimum Java version changed from 1.7 to 1.8.
  • Reduced use of property substitutions in pom.xml. This is to help 3rd-party parsers that fail to perform full Maven-compatible substitutions.
  • Now outputting HTML or XHTML based on the current response content type. This should eliminate validator warnings when used as HTML.
  • ChainWriter no longer writes &#160; as a placeholder for null values. This technique was used for ancient browsers that would not display completely empty table cells. This has not been the case for a long time.
  • JSON doesn't support comments, avoiding bundle lookup markups.
  • Consolidated writeWithMarkup(…) methods into Coercion class directly.
  • New static encoding methods for writing Object via Coercion.toString(Object).
  • Implemented Coercion.append(…) methods for working with Appendable.
  • ChainWriter will never wrap a PrintWriter with another PrintWriter, even when autoFlush settings do not match.
  • Added Coercion support for CharSequence.
  • Added Coercion support for char[].
  • Coercion now trims String and CharSequence based on code points, with a value considered whitespace when it is either <= '\u0020' (for compatibility with String.trim()) or Character.isWhitespace(int).
  • Avoiding unnecessary coercion to String when there is no active in-context translation.
  • ChainWriter.encodeHtml(…) (deprecated) now require additional isXhtml flag.
  • ChainWriter.writeHtmlImagePreloadJavaScript(…) moved to new ao-fluent-html project at ImagePreload.writeImagePreloadScript(…).
  • New enums for encoding context: Doctype and Serialization, which can be used to affect the encoding based on context.
  • JavaScript default type changed from text/javascript to application/javascript.
  • JavaScript encoder now uses context to determine both type and when to use CDATA.
  • EncodingContext is now optional, with default behaviors defined.
  • Renamed ChainWriter.encode*(Object) methods to ChainWriter.textIn*(Object).

    Also, all implementations add encoder prefixes and suffixes where appropriate, such as double quotes around text in JavaScript.

    Furthermore, all implementations perform translation markup.

  • New methods MediaWriter.text(…) for writing arbitrary textual data with automatic encoding. Supports encoder prefixes and suffixes as well as in-context translation.
  • Removed MediaException, using UnsupportedEncodingException instead.
  • Completely removed NewEncodingUtils.


Release Notes

  • New method Coercion.trim(Object) that returns the provided value trimmed.
  • New method Coercion.trimNullIfEmpty(Object) that returns the provided value trimmed, or null if the value is empty after trimming.
  • Added application/javascript as an alias for text/javascript.


Release Notes

  • Removed long-deprecated method ChainWriter.printEU(String).
  • Removed long-deprecated method ChainWriter.printHTMLColor(int).
  • Removed long-deprecated method ChainWriter.printImagePreloadJS(String).
  • During coercion, XML Node will be output as UTF-8.
  • EncodingContext.encodeURL(String) no longer throws UnsupportedEncodingException.
  • UrlValidator now validates the entire URL versus RFC 3986.


Release Notes

  • Added variations of the javascript date and time printing in ChainWriter supporting dates and times represented by long and Long.
  • Updated for compatibility with aocode-public-3.1.0.


Release Notes

  • Using managed dependencies:
    1. This project uses managed dependencies.
    2. This project's managed dependencies may also be imported by other projects.


Release Notes

  • Minimum Java version changed from 1.6 to 1.7.
  • Implemented encodings for Bourne shell scripts, MySQL command mysql input, and PostgreSQL command psql input.


Release Notes

  • Bug fixes:
    1. ChainWriter.encodeJavaScriptStringInXmlAttribute was not quoting empty JavaScript string on null value.
    2. ChainWriter.encodeJavaScriptStringInXhtml was not quoting empty JavaScript string on null value.
  • Improvements:
    1. ChainWriter.flush() and ChainWriter.close() now call underlying PrintWriter.checkError() to avoid accidentally swallowing exceptions. Because PrintWriter.checkError() causes a flush, it is only invoked on flush/close and not on every print/write.
  • Updated dependencies.


Release Notes

  • New AO OSS Parent POM to simplify pom.xml files.
  • Project documentation moved to per-project book in SemanticCMS format.
  • Added changelog as top-level project link.
  • Added support for XML DOM Node in toString type coercion.


Release Notes

  • Improved Javadoc formatting.
  • Improved README formatting.
  • Added support for application/json and application/ld+json encoding.


Release Notes

  • Escape for ]]> didn't work as hoped.


Release Notes

  • Quick empty to null conversion.
  • Shortcut for Strings.
  • Additional type coercions.
  • Encoding ']' to avoid potential ]]> from escaping CDATA early.


Release Notes

  • Minor release, only a packaging change.


Release Notes

  • Efficient way to check if objects are empty.


Release Notes

  • Improved Javadoc formatting.


Release Notes

  • Reverted to Java 1.6 for Android and Java EE 6 compatibility.


Release Notes

  • Project moved to GitHub and Maven.