mirror of
https://github.com/Shopify/liquid.git
synced 2026-09-15 00:40:40 -07:00
* Remove development helpers from parse context * Simplify strict_parse_with_error_mode_fallback and update documentation * Add unit tests for `Liquid::Expression` and `Liquid::ParseContext` * Update test helpers to work better with the `:rigid` mode
93 lines
2.7 KiB
Ruby
93 lines
2.7 KiB
Ruby
# frozen_string_literal: true
|
|
|
|
module Liquid
|
|
class ParseContext
|
|
attr_accessor :locale, :line_number, :trim_whitespace, :depth
|
|
attr_reader :partial, :warnings, :error_mode, :environment
|
|
|
|
def initialize(options = Const::EMPTY_HASH)
|
|
@environment = options.fetch(:environment, Environment.default)
|
|
@template_options = options ? options.dup : {}
|
|
|
|
@locale = @template_options[:locale] ||= I18n.new
|
|
@warnings = []
|
|
|
|
# constructing new StringScanner in Lexer, Tokenizer, etc is expensive
|
|
# This StringScanner will be shared by all of them
|
|
@string_scanner = StringScanner.new("")
|
|
|
|
@expression_cache = if options[:expression_cache].nil?
|
|
{}
|
|
elsif options[:expression_cache].respond_to?(:[]) && options[:expression_cache].respond_to?(:[]=)
|
|
options[:expression_cache]
|
|
elsif options[:expression_cache]
|
|
{}
|
|
end
|
|
|
|
self.depth = 0
|
|
self.partial = false
|
|
end
|
|
|
|
def [](option_key)
|
|
@options[option_key]
|
|
end
|
|
|
|
def new_block_body
|
|
Liquid::BlockBody.new
|
|
end
|
|
|
|
def new_parser(input)
|
|
@string_scanner.string = input
|
|
Parser.new(@string_scanner)
|
|
end
|
|
|
|
def new_tokenizer(source, start_line_number: nil, for_liquid_tag: false)
|
|
Tokenizer.new(
|
|
source: source,
|
|
string_scanner: @string_scanner,
|
|
line_number: start_line_number,
|
|
for_liquid_tag: for_liquid_tag,
|
|
)
|
|
end
|
|
|
|
def safe_parse_expression(parser)
|
|
Expression.safe_parse(parser, @string_scanner, @expression_cache)
|
|
end
|
|
|
|
def parse_expression(markup, safe: false)
|
|
if !safe && @error_mode == :rigid
|
|
# parse_expression is a widely used API. To maintain backward
|
|
# compatibility while raising awareness about rigid parser standards,
|
|
# the safe flag supports API users make a deliberate decision.
|
|
#
|
|
# In rigid mode, markup MUST come from a string returned by the parser
|
|
# (e.g., parser.expression). We're not calling the parser here to
|
|
# prevent redundant parser overhead.
|
|
raise Liquid::InternalError, "unsafe parse_expression cannot be used in rigid mode"
|
|
end
|
|
|
|
Expression.parse(markup, @string_scanner, @expression_cache)
|
|
end
|
|
|
|
def partial=(value)
|
|
@partial = value
|
|
@options = value ? partial_options : @template_options
|
|
|
|
@error_mode = @options[:error_mode] || @environment.error_mode
|
|
end
|
|
|
|
def partial_options
|
|
@partial_options ||= begin
|
|
dont_pass = @template_options[:include_options_blacklist]
|
|
if dont_pass == true
|
|
{ locale: locale }
|
|
elsif dont_pass.is_a?(Array)
|
|
@template_options.reject { |k, _v| dont_pass.include?(k) }
|
|
else
|
|
@template_options
|
|
end
|
|
end
|
|
end
|
|
end
|
|
end
|