https://github.com/AbhinavOmprakash/luna Skip to content Sign up * Why GitHub? + Features - + Mobile - + Actions - + Codespaces - + Packages - + Security - + Code review - + Issues - + Integrations - + GitHub Sponsors - + Customer stories - * Team * Enterprise * Explore + Explore GitHub - + Learn and contribute + Topics - + Collections - + Trending - + Learning Lab - + Open source guides - + Connect with others + The ReadME Project - + Events - + Community forum - + GitHub Education - + GitHub Stars program - * Marketplace * Pricing + Plans - + Compare plans - + Contact Sales - + Education - [ ] * # In this repository All GitHub | Jump to | * No suggested jump to results * # In this repository All GitHub | Jump to | * # In this user All GitHub | Jump to | * # In this repository All GitHub | Jump to | Sign in Sign up {{ message }} AbhinavOmprakash / luna Public * Notifications * Star 66 * Fork 2 * A DSL that translates to regex View license 66 stars 2 forks Star Notifications * Code * Issues 0 * Pull requests 0 * Actions * Projects 0 * Wiki * Security * Insights More * Code * Issues * Pull requests * Actions * Projects * Wiki * Security * Insights master Switch branches/tags [ ] Branches Tags Could not load branches Nothing to show Loading {{ refName }} default View all branches Could not load tags Nothing to show {{ refName }} default Loading View all tags 1 branch 1 tag Code Loading Latest commit @AbhinavOmprakash AbhinavOmprakash spacing ... 9fd0f32 Nov 10, 2021 spacing 9fd0f32 Git stats * 17 commits Files Permalink Failed to load latest commit information. Type Name Latest commit message Commit time .github/workflows Create clojure.yml Nov 10, 2021 doc created project Oct 16, 2021 src/luna changes Oct 17, 2021 test/luna Update Nov 10, 2021 .gitignore Add extensions Nov 10, 2021 CHANGELOG.md created project Oct 16, 2021 LICENSE created project Oct 16, 2021 README.md spacing Nov 10, 2021 luna.iml created project Oct 16, 2021 project.clj add cloverage Nov 10, 2021 View code [ ] luna About Why? Installing and Using Contributing If you'd like to contribute but don't know how Test cases Documentation Refactoring Grammar/language character class syntax for :match after the character class vector we have modifiers. :match-enc sets capture Anchors Match Capture Group constructs assertions Quantifiers A few practical examples Usage License README.md luna Clojars Project codecov No more regrets, wield the power of regex with the readability of English with luna. About luna is a Domain specific language (DSL) that is readable and translates into a Regex.Pattern object. luna is still in Beta but don't let this discourage you from using it, it has a good test suite and bug reports are key to improving it. Why? Readable code can be hard to maintain. Unreadable code can be impossible to maintain. Installing and Using add this to your project.clj file :dependencies [[org.clojars.abhinav/luna "0.1.0-SNAPSHOT"]] Luna has one function pre that does the heavy lifting. ;; import it (ns user.core (:require [luna.core :as luna])) (luna/pre [:match ["x" :digits :atleast 4 :times] :when :at-start]) ;;=> #"^x\d{4,}" Contributing I welcome contributions, even from first-timers. Feedbacks and suggestions are welcome too. If you'd like to contribute but don't know how Test cases The easiest thing you can do to contribute is write a test case, this project can never have too many test cases. Documentation Documentation is very important, more so than the code in the project, so I value these contributions highly. There will be some parts (hopefully not a lot) of the documentation that may not make sense, or maybe wrong, or can be worded differently. Refactoring I welcome refactors like * Variable and function renaming. * Extracting functions. * Moving things around to make more sense. Grammar/language the pre function is used to parse the dsl and return a regex.Pattern object. the arguments to pre can be plain strings, or vectors, or a Pattern object. => (pre "xy") #"xy" ; pre can take multiple args => (pre "a" #"b" [:match "c" :when :at-start]) #"ab^c" The first element in the vector determines how the rest is processed. There are two main and commonly used keywords :match (or :m) and :capture (or :c) that are valid first elements. => (pre [:match "xy"]) #"xy" => (pre [:capture "xy"]) #"(xy)" The next element is either a string or a vector, containing character classes. The valid syntax of the vector depends on whether :match or :capture was used. character class syntax for :match to be used as [:match ["xy"]] ;; ----char-class vector---- [:match ["x" :when :at-start "y"]] I will omit [:match ...] for brevity. examples of valid char-class vector ;; by default the elements in the char-class vector are evaluate to a string and separated by | in match ["xy"] => #"xy" ["x" "y"] => #"x|y" ["x" "y" "z"] => #"x|y|z" ;; if you would prefer to concatenate them, then use a nested vector [["x" "y" "z"]] => #"xyz" ;; using ranges in character classes [[1 :to 7]] => #"[1-7]" [1 [2 :to 5]] => #"[1[2-5]]" ;; using anchors inside vector ["x" :when :at-start] => #"^x" ["x" :when :at-start "y"] => #"^xy" ;; using quantifiers inside vector ["x" :atleast 5 :times "y"] => #"x{5,}y" ;; the :times can be omitted but helps with readability ["x" :atleast 5 "y"] => #"x{5,}y" ;;combining anchors and quantifiers ["x" :atleast 5 :times :when :at-start "y"] => #"^x{5,}y" after the character class vector we have modifiers. ;; -modifiers- [:match ["xy"] :atleast 2] => #"xy{2,}" ;; ---modifiers--- [:match ["xy"] :when :at-start] => #"^xy" Note! if you're using quantifiers and/or anchors inside the character class vector and outside then the result will be a "match everything enclosed" here's an example [:match ["x" :atleast 5 "y"] :atleast 2] => #"(?:x{5}y){2}" :match-enc :match-enc[closed] by default [:match ["x" :atleast 5 "y"] ] yields # "x{5}|y" instead if you want #"(?:x{5}|y) use :match-enc [:match-enc ["x" :atleast 5 "y"]] => #"(?:x{5}y)" sets if you wish to use set constructs like negation [^abc] or intersection [abc&&[ab]] you can use clojure's literal set notation ; negation [:match #{:not "abc"}] => #"[^abc]" [:match #{:not "abc" :upper [1 :to 5]}] => #"[^abcA-Z1-5]" ;; intersection [:match #{:and "abc" "ab"}] => #"[abc&&[ab]]" [:match #{:and "abc" :upper [1 :to 4]}] => #"[abc&&[A-Z]&&[1-4]]" ; combining both [:match #{:and "abc" #{:not "ab" :digits}}] => #"[abc&&[^ab1-9]]" capture the syntax of capture is similar to :match Anchors Match [:match "x" :when :at-start] ; #"^x" [:match "xy" :when :at-start] ; #"^xy" [:match ["xy"] :when :at-start] ; #"^xy" [:match ["x" :or "y"] :when :at-start] ; #"^x|y" [:match ["x" :when :at-start :or "y"]] ; #"^x|y" [:match [:digits] :when :at-end] ; #"\d$" Capture [:capture "x" :when :at-start] ; #"^(x)" [:capture "xy" :when :at-start] ; #"^(xy)" [:capture ["x" "y"] :when :at-start] ; #"^(xy)" [:capture [["x" "y"]] :when :at-start] ; #"^([xy])" [:capture :digits :when :at-end] ; #"$(\d)" [:capture "x" :when :at-word-start] ; #"\b(x)" [:capture "x" :when :not :at-word-start] ; #"\B(x)" Group constructs assertions ;; lookahead positive and negative [:match "x" :when :before "y"] ; #"x(?=y)" [:match "x" :when :not-before "y"] ; #"x(?!y)" ;; lookbehind positive and negative [:match "x" :when :after "y"] ; #"(?<=y)x" [:match "x" :when :not-after "y"] ; #"(?)[\s\S]*?(?=<)" (pre [:match [:everything] :lazily :between ">" :and "<"]) #"^[A-Z]{1,2}[0-9R][0-9A-Z]?[0-9][ABD-HJLNP-UW-Z]{2}$" (pre [:m :upper :between 1 :and 2 :when :at-start] [:m [[[0 :to 9] "R"]]] [:m [[[0 :to 9] :upper]] :0-or-1] [:m [[[0 :to 9]]]] [:m [["AB" ["D" :to "H"] "JLN" ["P" :to "U"] ["W" :to "Z"]]] :atleast 2 :when :at-end]) Usage FIXME License Copyright (c) 2021 FIXME This program and the accompanying materials are made available under the terms of the Eclipse Public License 2.0 which is available at http://www.eclipse.org/legal/epl-2.0. This Source Code may also be made available under the following Secondary Licenses when the conditions for such availability set forth in the Eclipse Public License, v. 2.0 are satisfied: GNU General Public License as published by the Free Software Foundation, either version 2 of the License, or (at your option) any later version, with the GNU Classpath Exception which is available at https://www.gnu.org/software/classpath/license.html. About A DSL that translates to regex Resources Readme License View license Releases 1 tags Packages 0 No packages published Languages * Clojure 100.0% * (c) 2021 GitHub, Inc. * Terms * Privacy * Security * Status * Docs * Contact GitHub * Pricing * API * Training * Blog * About You can't perform that action at this time. You signed in with another tab or window. Reload to refresh your session. You signed out in another tab or window. Reload to refresh your session.