Module: Dhall

Defined in:
lib/dhall.rb,
lib/dhall/ast.rb,
lib/dhall/util.rb,
lib/dhall/binary.rb,
lib/dhall/parser.rb,
lib/dhall/resolve.rb,
lib/dhall/visitor.rb,
lib/dhall/as_dhall.rb,
lib/dhall/builtins.rb,
lib/dhall/normalize.rb,
lib/dhall/typecheck.rb

Defined Under Namespace

Modules: AsDhall, Builtins, ExpressionVisitor, Parser, Resolvers, TypeChecker, Util Classes: Application, Bool, Builtin, Double, EmptyList, EmptyRecord, EmptyRecordProjection, EmptyRecordType, Expression, ExpressionResolver, Forall, Function, If, Import, ImportBannedException, ImportFailedException, ImportLoopException, Integer, Let, LetBlock, LetIn, List, Merge, Natural, Number, Operator, Optional, OptionalNone, Record, RecordProjection, RecordSelection, RecordType, Text, TextLiteral, TypeAnnotation, Union, UnionType, Variable, Visitor

Constant Summary collapse

BINARY =
{
  ::TrueClass    => ->(e) { Bool.new(value: e) },
  ::FalseClass   => ->(e) { Bool.new(value: e) },
  ::Float        => ->(e) { Double.new(value: e) },
  ::String       => ->(e) { Builtins::ALL[e]&.new || Variable.new(name: e) },
  ::Integer      => ->(e) { Variable.new(index: e) },
  ::Array        => lambda { |e|
    if e.length == 2 && e.first.is_a?(::String)
      Variable.new(name: e[0], index: e[1])
    else
      tag, *body = e
      BINARY_TAGS[tag]&.decode(*body) ||
        (raise "Unknown expression: #{e.inspect}")
    end
  },
  ::CBOR::Tagged => lambda { |e|
    return Dhall.decode(e.value) if e.tag == 55799

    raise "Unknown tag: #{e.inspect}"
  }
}.freeze
BINARY_TAGS =
[
  Application,
  Function,
  Forall,
  Operator,
  List,
  Optional,
  Merge,
  RecordType,
  Record,
  RecordSelection,
  RecordProjection,
  UnionType,
  Union,
  nil,
  If,
  Natural,
  Integer,
  nil,
  TextLiteral,
  nil,
  nil,
  nil,
  nil,
  nil,
  Import,
  LetBlock,
  TypeAnnotation
].freeze

Class Method Summary collapse

Class Method Details

.decode(expression) ⇒ Object



14
15
16
17
18
19
20
# File 'lib/dhall/binary.rb', line 14

def self.decode(expression)
  BINARY.each do |match, use|
    return use[expression] if expression.is_a?(match)
  end

  raise "Unknown expression: #{expression.inspect}"
end

.dump(o) ⇒ Object



34
35
36
# File 'lib/dhall.rb', line 34

def self.dump(o)
  CBOR.encode(o.as_dhall)
end

.from_binary(cbor_binary) ⇒ Object



10
11
12
# File 'lib/dhall/binary.rb', line 10

def self.from_binary(cbor_binary)
  decode(CBOR.decode(cbor_binary))
end

.load(source, resolver: Resolvers::Default.new) ⇒ Object



15
16
17
18
19
20
21
# File 'lib/dhall.rb', line 15

def self.load(source, resolver: Resolvers::Default.new)
  Promise.resolve(nil).then {
    load_raw(source).resolve(resolver: resolver)
  }.then do |resolved|
    TypeChecker.for(resolved).annotate(TypeChecker::Context.new).normalize
  end
end

.load_raw(source) ⇒ Object



23
24
25
26
27
28
29
30
31
32
# File 'lib/dhall.rb', line 23

def self.load_raw(source)
  begin
    return from_binary(source) if source.encoding == Encoding::BINARY
  rescue Exception # rubocop:disable Lint/RescueException
    # Parsing CBOR failed, so guess this is source text in standard UTF-8
    return load_raw(source.force_encoding("UTF-8"))
  end

  Parser.parse(source.encode("UTF-8")).value
end