diff --git a/jbake-core/src/main/java/org/jbake/app/configuration/DefaultJBakeConfiguration.java b/jbake-core/src/main/java/org/jbake/app/configuration/DefaultJBakeConfiguration.java index 7a772acb8..8ee6816be 100644 --- a/jbake-core/src/main/java/org/jbake/app/configuration/DefaultJBakeConfiguration.java +++ b/jbake-core/src/main/java/org/jbake/app/configuration/DefaultJBakeConfiguration.java @@ -1,11 +1,5 @@ package org.jbake.app.configuration; -import org.apache.commons.configuration.CompositeConfiguration; -import org.apache.commons.configuration.Configuration; -import org.apache.commons.lang3.StringUtils; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - import java.io.File; import java.util.ArrayList; import java.util.Arrays; @@ -13,6 +7,11 @@ import java.util.List; import java.util.regex.Matcher; import java.util.regex.Pattern; +import org.apache.commons.configuration.CompositeConfiguration; +import org.apache.commons.configuration.Configuration; +import org.apache.commons.lang3.StringUtils; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; /** * The default implementation of a {@link JBakeConfiguration} @@ -32,6 +31,9 @@ public class DefaultJBakeConfiguration implements JBakeConfiguration { private Logger logger = LoggerFactory.getLogger(DefaultJBakeConfiguration.class); private CompositeConfiguration compositeConfiguration; + public static final int MAX_HEADER_LINES_DEFAULT = 50; + + /** * Some deprecated implementations just need access to the configuration without access to the source folder * @@ -468,6 +470,12 @@ public String getVersion() { return getAsString(JBakeProperty.VERSION); } + @Override + public int getMaxHeaderLinesScan() + { + return getAsInt(JBakeProperty.MAX_HEADER_LINES_SCAN, MAX_HEADER_LINES_DEFAULT); + } + public void setDestinationFolderName(String folderName) { setProperty(JBakeProperty.DESTINATION_FOLDER, folderName); setupDefaultDestination(); diff --git a/jbake-core/src/main/java/org/jbake/app/configuration/JBakeConfiguration.java b/jbake-core/src/main/java/org/jbake/app/configuration/JBakeConfiguration.java index 5e5435382..ca845a9ec 100644 --- a/jbake-core/src/main/java/org/jbake/app/configuration/JBakeConfiguration.java +++ b/jbake-core/src/main/java/org/jbake/app/configuration/JBakeConfiguration.java @@ -299,6 +299,12 @@ public interface JBakeConfiguration { */ String getVersion(); + /** + * @return Maximum lines to scan when looking for a JBake in-file header. + */ + int getMaxHeaderLinesScan(); + + /** * Set a property value for the given key * diff --git a/jbake-core/src/main/java/org/jbake/app/configuration/JBakeProperty.java b/jbake-core/src/main/java/org/jbake/app/configuration/JBakeProperty.java index 375d8f903..8992edfd0 100644 --- a/jbake-core/src/main/java/org/jbake/app/configuration/JBakeProperty.java +++ b/jbake-core/src/main/java/org/jbake/app/configuration/JBakeProperty.java @@ -46,6 +46,7 @@ public class JBakeProperty { public static final String IMG_PATH_UPDATE = "img.path.update"; public static final String IMG_PATH_PREPEND_HOST = "img.path.prepend.host"; public static final String VERSION = "version"; + public static final String MAX_HEADER_LINES_SCAN = "header.maxLines"; private JBakeProperty() {} diff --git a/jbake-core/src/main/java/org/jbake/parser/MarkupEngine.java b/jbake-core/src/main/java/org/jbake/parser/MarkupEngine.java index b0a4017df..7a493b009 100644 --- a/jbake-core/src/main/java/org/jbake/parser/MarkupEngine.java +++ b/jbake-core/src/main/java/org/jbake/parser/MarkupEngine.java @@ -1,15 +1,5 @@ package org.jbake.parser; -import org.apache.commons.configuration.CompositeConfiguration; -import org.apache.commons.configuration.Configuration; -import org.apache.commons.io.IOUtils; -import org.jbake.app.Crawler; -import org.jbake.app.configuration.DefaultJBakeConfiguration; -import org.jbake.app.configuration.JBakeConfiguration; -import org.json.simple.JSONValue; -import org.slf4j.Logger; -import org.slf4j.LoggerFactory; - import java.io.File; import java.io.FileInputStream; import java.io.IOException; @@ -17,9 +7,20 @@ import java.text.DateFormat; import java.text.ParseException; import java.text.SimpleDateFormat; +import java.util.ArrayList; import java.util.Date; import java.util.List; import java.util.Map; +import org.apache.commons.configuration.CompositeConfiguration; +import org.apache.commons.configuration.Configuration; +import org.apache.commons.io.IOUtils; +import org.apache.commons.lang3.StringUtils; +import org.jbake.app.Crawler; +import org.jbake.app.configuration.DefaultJBakeConfiguration; +import org.jbake.app.configuration.JBakeConfiguration; +import org.json.simple.JSONValue; +import org.slf4j.Logger; +import org.slf4j.LoggerFactory; /** * Base class for markup engine wrappers. A markup engine is responsible for rendering @@ -156,12 +157,59 @@ private void setModelDefaultsIfNotSetInHeader(ParserContext context) { } } + /** * Checks if the file has a meta-data header. * * @param contents Contents of file * @return true if header exists, false if not */ + private boolean hasHeader2(Configuration config, List contents) { + boolean headerSeparatorFound = false; + boolean statusFound = false; + boolean typeFound = false; + + List headerLines = new ArrayList<>(); + + int scanMaxLines = configuration.getMaxHeaderLinesScan(); + + //for (String line : contents) { + for (int i = 0; i < contents.size() && i < scanMaxLines; i++) { + String line = contents.get(i); + if (StringUtils.isBlank(line)) + continue; + + if (line.startsWith("#")) + continue; + + if (line.equals(configuration.getHeaderSeparator())) { + headerSeparatorFound = true; + break; + } + + if (!line.matches("^\\p{Graph}+\\p{Blank}*(=|:)\\p{Blank}*\\p{Graph}*")) + continue; + + headerLines.add(line); + + typeFound |= line.startsWith("type="); + statusFound |= line.startsWith("status="); + } + + if (headerSeparatorFound) { + for (String headerLine : headerLines) { + if (!headerLine.contains("=")) { + LOGGER.warn("Document has invalid header line (without '='):\n{}", headerLines); + return false; + } + } + } + + return (statusFound || null != configuration.getDefaultStatus()) + && (typeFound || null != configuration.getDefaultType()); + } + + private boolean hasHeader(List contents) { boolean headerValid = true; boolean statusFound = false; @@ -332,4 +380,4 @@ private void processDefaultBody(ParserContext context) { } context.setBody(body.toString()); } -} \ No newline at end of file +} diff --git a/jbake-core/src/main/resources/default.properties b/jbake-core/src/main/resources/default.properties index a6a66fa28..664268f56 100644 --- a/jbake-core/src/main/resources/default.properties +++ b/jbake-core/src/main/resources/default.properties @@ -116,4 +116,6 @@ header.separator=~~~~~~ # update image path img.path.update=false # Prepend site.host to image paths -img.path.prepend.host=true \ No newline at end of file +img.path.prepend.host=true +# JBake will only scan this number of lines for a headers block separator. +header.maxLines=50