Skip to content

takeshik/yacq

Repository files navigation

YACQ - Yet Another Compilable Query Language for .NET

YACQ (pronounced as yacc) is an application-embeddable programming language for querying and scripting, runs on .NET platform.

Features

YACQ is a library that provides run-time scripting and querying for .NET applications. YACQ has the following features mainly:

  • Extension of Expression Trees API. YACQ is based on Expression Trees API, a standard feature and one of basis of LINQ ecosystem. Since YACQ extends this and uses as its native syntax tree, YACQ fits with standard and other LINQ query providers.
  • Language Services. YACQ can construct expression trees from source code string by Parseq, a monadic parser combinator. There are no way to construct expression trees from string in run-time (without external processes) in vanilla environments. You can modify and extend the grammar of YACQ.
  • LINQ Support. YACQ contains wrapper class of querying interfaces such as IQueryable<T>. You can use (standard) query operators along with YACQ, in order to specify selectors, predicates, and other lambdas by code strings. Moreover, YACQ supports Rx (Reactive Extensions) and Ix (Interactive Extensions).
  • Extended Type System. YACQ not only can access to almost of .NET types, but also can extend the type system of .NET transparently. When you access to extension members, YACQ transforms to expression which is composed only of real member accesses. In short, YACQ can extend types without pollution of expression trees.
  • Type Generator. Since the power of Expression Trees API, YACQ can compile codes to delegate or emits to static method builders, furthermore, YACQ also can define types with instance and static members, and output assemblies.
  • Expression Tree Serializer. In vanilla environments, expression trees are not serializable. YACQ provides proxy types to support serialization. Proxy type describes the contents of the serialized expression tree more detailed and concisely than default Expression.ToString() outputs.

Usages

Construct an expression tree from YACQ code string.

Expression expr =
    YacqServices.Parse("(+ 1 2 3)");
    // same as ((1 + 2) + 3)

Lambdas which has only one argument can construct easily by the helper method.

Expression<Func<string, string>> lambda =
    YacqServices.ParseFunc<string, string>("it.(ToUpper).(Replace 'FOO' 'bar')");
    // same as (string it) => it.ToUpper().Replace("foo", "bar")

Constructed lambdas can compile and evaluate by standard feature in run-time.

Func<string, string> func = lambda.Compile();
func("foooo"); // returns "barOO"

You can use YACQ in LINQ queries.

var query = Enumerable.Range(1, 100)
    .Yacq()
    .Where("(== (% it 3) 0)")
    .GroupBy("(/ it 10)")
    .Select("it.(Average)")
    .OrderByDescending("it");

// Same as:
Enumerable.Range(1, 100)
    .Where(it => it % 3 == 0)
    .GroupBy(it => it / 10)
    .Select(it => it.Average())
    .OrderByDescending(it => it);

YACQ provides expression trees serializer. In vanilla environments, they are not serializable.

string xml = YacqServices.SaveText(lambda);
Expression lambda2 = YacqServices.LoadText(xml);

You can construct complex expression trees with YACQ-extended Expression Trees system.

Expression expr2 = YacqExpression.TypeCandidate(typeof(Enumerable))
    .Method("Range", Expression.Constant(1), Expression.Constant(100))
    .Method("Reverse")
    .Method("Take", Expression.Constant(10))
    .Method("Sum")
    .Reduce();

// Same as:
Expression.Call(typeof(Enumerable), "Sum", null,
    Expression.Call(typeof(Enumerable), "Take", new [] { typeof(int), },
        Expression.Call(typeof(Enumerable), "Reverse", new [] { typeof(int), },
            Expression.Call(typeof(Enumerable), "Range", null, Expression.Constant(1), Expression.Constant(100))
        ), Expression.Constant(10)));

Although the main use of YACQ is to embed in other applications, YACQ also can use in standalone. Complier frontend and REPL environment are bundled.

Get Started

To use YACQ, you have to refer Yacq.dll by your application. There are some way to get the system:

PM> Install-Package Yacq
  • Download binary archive: You can download the binary archive. This contains all libraries, executables, and documents. If you want compiler frontend or REPL environment, please download this.
  • Download source code in GitHub: You can get the source codes in GitHub.
    • Clone the repository: You can clone the Git repository.
    % git clone git://github.com/takeshik/yacq.git
    
    • Download snapshot: Snapshot archive of the repository is also available (.tar.gz | .zip).

Prerequisites

Licensing

Copyright © 2011-2013 Takeshi KIRIYA (aka takeshik) (Web | Mail | GitHub | Twitter), All rights reserved.

YACQ is Free Software. Its source codes, binaries, and all other resources are licensed under the MIT License.

About

Yet Another Compilable Query Language for .NET, based on Expression Trees API

Resources

License

Stars

Watchers

Forks

Packages

No packages published

Languages