From eac584e9bdbfbf6e98a48e162636b7464d3ea058 Mon Sep 17 00:00:00 2001 From: Skiy Date: Fri, 26 Mar 2021 12:37:48 +0000 Subject: [PATCH 1/3] updated handling for indentation around comments --- ExampleCode/factorial.skiy | 13 ++++++++++ PySkiylia/Lexer.py | 9 +++++++ README.md | 49 ++++++++++++++++++++++++++++++++++---- 3 files changed, 67 insertions(+), 4 deletions(-) create mode 100644 ExampleCode/factorial.skiy diff --git a/ExampleCode/factorial.skiy b/ExampleCode/factorial.skiy new file mode 100644 index 0000000..7a12582 --- /dev/null +++ b/ExampleCode/factorial.skiy @@ -0,0 +1,13 @@ +///This section contains a small snippet of Skiylia +code that calculates the factorial of a number/// +def factorial(n): + if int(n) != n: + return null //can't compute factorial of a float this way + if n < 2: + return 1 + return n * factorial(n - 1) //recursion that makes this work + +var num = 6 +print("The factorial of", num, "is", factorial(num)) + +//output: The factorial of 6 is 720 diff --git a/PySkiylia/Lexer.py b/PySkiylia/Lexer.py index ed9104b..db0f96f 100644 --- a/PySkiylia/Lexer.py +++ b/PySkiylia/Lexer.py @@ -101,6 +101,8 @@ def tokenFromChar(self): elif c == "/": #as division and comments use the same character, check if the next is a comment if self.match("/"): + #as comments can mess with indentation, remove any leading up to it + self.removewhitespace() #as multi-line comments are ///, whereas a single line is //, we need to check for that too! if self.match("/"): #keep advancing until we find the tripple comment escape @@ -302,3 +304,10 @@ def advance(self, chars=1): def atEnd(self): #return if the current position s greater than the source length return self.current >= len(self.source) + + #match the indentation to any actual surrounding code + def removewhitespace(self): + #if we have a previous token + if self.tokens: + #then set our indent to that + self.indent = self.previousToken().indent diff --git a/README.md b/README.md index a5b1dca..a5d6ca4 100644 --- a/README.md +++ b/README.md @@ -1,5 +1,5 @@ # PySkiylia -Dynamically typed Object Oriented Program Language. +Dynamically typed Object Oriented Programming Language. [![forthebadge](https://forthebadge.com/images/badges/made-with-python.svg)](https://forthebadge.com) @@ -20,9 +20,10 @@ Dynamically typed Object Oriented Program Language. ![GitHub release (latest by date including pre-releases)](https://img.shields.io/github/v/release/SK1Y101/PySkiylia?include_prereleases) ![GitHub commits since latest release (by date including pre-releases)](https://img.shields.io/github/commits-since/SK1Y101/PySkiylia/latest/develop?include_prereleases) +![GitHub commit activity](https://img.shields.io/github/commit-activity/w/SK1Y101/PySkiylia) ![GitHub milestone](https://img.shields.io/github/milestones/progress/SK1Y101/PySkiylia/1) ![GitHub milestones](https://img.shields.io/github/milestones/open/SK1Y101/PySkiylia) -[![Percentage of issues still open](http://isitmaintained.com/badge/open/SK1Y101/PySkiylia.svg)](http://isitmaintained.com/project/SK1Y101/PySkiylia "Percentage of issues still open") +![GitHub issues](https://img.shields.io/github/issues-raw/SK1Y101/PySkiylia) ![GitHub pull requests](https://img.shields.io/github/issues-pr-raw/SK1Y101/PySkiylia) ![GitHub last commit](https://img.shields.io/github/last-commit/SK1Y101/PySkiylia) @@ -30,9 +31,49 @@ Dynamically typed Object Oriented Program Language. Support here: [issues] +# Skiylia + +Skiylia is dynamically typed, object oriented, and most importantly *interpreted*. While it may share many similarities with C derivatives, its heritage is definitely Pythonic. + +To that end, Skiylia is most aptly described as a Python-C# hybrid. + +## + ## Sample code -Within this [folder] is all the code examples that have been used to test the project. Feel free to play around and get a feel for the language! + ///This section contains a small snippet of Skiylia + code that calculates the factorial of a number/// + + def factorial(n): + if int(n) != n: + return null //can't compute factorial of a float this way + if x < 2: + return 1 + return x * factorial(n - 1) //recursion that makes this work + + var num = 6 + print("The factorial of", num, "is", factorial(num)) + + //output: The factorial of 6 is 720 + +Within this [folder] is a collection of code examples that have been used to test the project. While not exhaustive by any means, they should cover the basics. Feel free to play around and get a feel for the language! + +## Contributing + +Any contributions made are absolutely welcome. Checkout the issues area for any outstanding problems, or to file your own! + +Forking this repository is an excellent way to contribute to the code that makes this interpreter tick. Open a pull request (preferably to the develop branch) if you have anything to add, and it'll be looked over. + +# Acknowledgements + +I, [Jack](https://github.com/SK1Y101), definitely couldn't have created PySkiylia without any outside sources. + +I owe a huge debt to Bob Nystrom and his excellent book, [Crafting Interpreters]. Not only did he give me true inspiration to develop Skiylia, but also provided cleanly documented concepts and a delightful read. If there is *anyone* that hasn't yet read his implementation of Lox from cover to cover, I would thoroughly recommend doing so. + +## Tools + +Languages: [Python] (of course) + ## Contributors @@ -53,8 +94,8 @@ All the people who have contributed ([emoji key](https://allcontributors.org/doc This project follows the [all-contributors](https://allcontributors.org) specification. -Contributions of any kind are welcome! [Latest release]: https://github.com/SK1Y101/PySkiylia/releases [issues]: https://github.com/SK1Y101/PySkiylia/issues [folder]: https://github.com/SK1Y101/PySkiylia/tree/main/ExampleCode +[Crafting Interpreters]: https://craftinginterpreters.com/ From 5a935baed1a74dc5c460f6c6a72d45e23da85404 Mon Sep 17 00:00:00 2001 From: Skiy Date: Fri, 26 Mar 2021 14:56:37 +0000 Subject: [PATCH 2/3] PySkiylia now requires an explicit debugging tag to enable debug output --- PySkiylia/PySkiylia.py | 25 ++++++++++++++++--------- 1 file changed, 16 insertions(+), 9 deletions(-) diff --git a/PySkiylia/PySkiylia.py b/PySkiylia/PySkiylia.py index ec9550e..6ad32c8 100644 --- a/PySkiylia/PySkiylia.py +++ b/PySkiylia/PySkiylia.py @@ -15,9 +15,20 @@ class Skiylia: #set the default values here haderror = False version = "v0.6.1" - debug = True + debug = False #run this at initialisation def __init__(self, args=""): + #check if the user has asked for help + if args and args[-1] in ["--help", "-h", "-?", "/?"]: + #show them the default usage + print("Usage:\tPySkiylia [scriptname]") + sys.exit(0) + #or if they want to enable debug mode + elif args and args[-1] in ["-debug", "-d"]: + #enable debugging + self.debug = True + #ad remove the flag from the arguments list + args = args[:-1] #we won't support more than one argument if len(args) > 1: #tell the user and exit @@ -25,11 +36,6 @@ def __init__(self, args=""): sys.exit(1) #if we have been given a single argument elif len(args) == 1: - #check if te user has asked for help - if args[0] in ["--help", "-h", "-?", "/?"]: - #show them the default usage - print("Usage:\tPySkiylia [scriptname]") - sys.exit(0) #save the argument if it is valid self.args = self.checkValidFile(args[0]) else: @@ -61,7 +67,7 @@ def checkValidFile(self, path): #startup the prompt if no arguments have been given def runPrompt(self): #print some base information - print("PySkiylia "+self.version) + print("PySkiylia",self.version,"- debugging mode"*self.debug) #keep looping the code while True: #fetch the user input @@ -105,8 +111,8 @@ def run(self, source): tokens = lexer.scanTokens() #Lexer output for debugging if self.debug: - print("Tokenised source code:") - print([(token.type, token.indent) for token in tokens]) + print("\nTokenised source code:") + print([token.type for token in tokens]) #fetch the Parser class parser = Parser(self, tokens, lexer.primitives) @@ -120,6 +126,7 @@ def run(self, source): print("\nAbstracted source code:") astprinter = ASTPrinter() astprinter.display(statements) + print() #initialise the interpreter interpreter = Interpreter(self, parser.arglimit) From abe12a9522409f7e047e31147d57c92a3f77970e Mon Sep 17 00:00:00 2001 From: Skiy Date: Fri, 26 Mar 2021 16:50:24 +0000 Subject: [PATCH 3/3] more readme and fixed indent following comments on function declaration --- .all-contributorsrc | 3 +- ExampleCode/README.md | 56 ++++++++++++++++++++++++----------- ExampleCode/classExample.skiy | 23 ++++++++++++++ PySkiylia/Lexer.py | 6 +++- PySkiylia/PySkiylia.py | 4 +-- README.md | 36 ++++++++++++++-------- 6 files changed, 93 insertions(+), 35 deletions(-) create mode 100644 ExampleCode/classExample.skiy diff --git a/.all-contributorsrc b/.all-contributorsrc index a8fc808..47f5bab 100644 --- a/.all-contributorsrc +++ b/.all-contributorsrc @@ -1,7 +1,6 @@ { "files": [ - "README.md", - "ExampleCode/README.md" + "README.md" ], "imageSize": 100, "commit": false, diff --git a/ExampleCode/README.md b/ExampleCode/README.md index b3f0746..f4b9693 100644 --- a/ExampleCode/README.md +++ b/ExampleCode/README.md @@ -7,7 +7,6 @@ Dynamically typed Object Oriented Program Language. ![Snyk Vulnerabilities for GitHub Repo](https://img.shields.io/snyk/vulnerabilities/github/SK1Y101/PySkiylia) [![codecov](https://codecov.io/gh/SK1Y101/PySkiylia/branch/main/graph/badge.svg?token=DRJ67ZQA7M)](https://codecov.io/gh/SK1Y101/PySkiylia) [![time tracker](https://wakatime.com/badge/github/SK1Y101/PySkiylia.svg?style=flat-square)](https://wakatime.com/badge/github/SK1Y101/PySkiylia) - [![All Contributors](https://img.shields.io/badge/all_contributors-2-orange.svg?style=flat)](#contributors) @@ -20,26 +19,49 @@ This repository folder contains examples of Skiylia-specific code, and (possibly Support here: [issues] -## Contributors +## Sample Function code + + ///This section contains a small snippet of Skiylia + code that calculates the factorial of a number/// + + def factorial(n): + if int(n) != n: + return null //can't compute factorial of a float this way + if n < 2: + return 1 + return n * factorial(n - 1) //recursion that makes this work + + var num = 6 + print("The factorial of", num, "is", factorial(num)) + + //output: The factorial of 6 is 720 + +## Sample Class structure + + ///This section contains a small snippet of Skiylia + code that demonstrates class methods and properties/// + + class Person: + init(name, age): //executed on initialisation + self.name = name + self.age = age + + hello(): + print("Hi there, I'm", self.name, ", and I'm", self.age) + + birthday(): + self.age = self.age + 1 -All the people who have contributed ([emoji key](https://allcontributors.org/docs/en/emoji-key)): - - - - - - - - -

Jack Lloyd-Walters

💻 👀

Jack Lloyd-Walters

👀
+ var John = Person("John", 24) + John.hello() - - + John.birthday() + John.name = "Johnathon" + John.hello() - + ///Hi there, I'm John, and I'm 24 + Hi there, I'm Johnathon, and I'm 25/// -This project follows the [all-contributors](https://allcontributors.org) specification. -Contributions of any kind are welcome! [Latest release]: https://github.com/SK1Y101/PySkiylia/releases [issues]: https://github.com/SK1Y101/PySkiylia/issues diff --git a/ExampleCode/classExample.skiy b/ExampleCode/classExample.skiy new file mode 100644 index 0000000..3e6d58a --- /dev/null +++ b/ExampleCode/classExample.skiy @@ -0,0 +1,23 @@ +///This section contains a small snippet of Skiylia +code that demonstrates class methods and properties/// + +class Person: + init(name, age): //executed on initialisation + self.name = name + self.age = age + + hello(): + print("Hi there, I'm", self.name, ", and I'm", self.age) + + birthday(): + self.age = self.age + 1 + +var John = Person("John", 24) +John.hello() + +John.birthday() +John.name = "Johnathon" +John.hello() + +///Hi there, I'm John, and I'm 24 + Hi there, I'm Johnathon, and I'm 25/// diff --git a/PySkiylia/Lexer.py b/PySkiylia/Lexer.py index db0f96f..e396425 100644 --- a/PySkiylia/Lexer.py +++ b/PySkiylia/Lexer.py @@ -310,4 +310,8 @@ def removewhitespace(self): #if we have a previous token if self.tokens: #then set our indent to that - self.indent = self.previousToken().indent + lt = self.previousToken() + self.indent = lt.indent + #unless it was a colon, then we have to indent further + if lt.type == "Colon": + self.indent += 1 diff --git a/PySkiylia/PySkiylia.py b/PySkiylia/PySkiylia.py index 6ad32c8..0836007 100644 --- a/PySkiylia/PySkiylia.py +++ b/PySkiylia/PySkiylia.py @@ -14,7 +14,7 @@ class Skiylia: #set the default values here haderror = False - version = "v0.6.1" + version = "v0.6.3" debug = False #run this at initialisation def __init__(self, args=""): @@ -112,7 +112,7 @@ def run(self, source): #Lexer output for debugging if self.debug: print("\nTokenised source code:") - print([token.type for token in tokens]) + print(*["{} {},".format(token.type, token.indent) for token in tokens]) #fetch the Parser class parser = Parser(self, tokens, lexer.primitives) diff --git a/README.md b/README.md index a5d6ca4..47459cc 100644 --- a/README.md +++ b/README.md @@ -11,7 +11,6 @@ Dynamically typed Object Oriented Programming Language. ![GitHub top language](https://img.shields.io/github/languages/top/SK1Y101/PySkiylia) ![GitHub code size in bytes](https://img.shields.io/github/languages/code-size/SK1Y101/PySkiylia) ![Lines of code](https://img.shields.io/tokei/lines/github.com/SK1Y101/PySkiylia) - [![All Contributors](https://img.shields.io/badge/all_contributors-2-orange.svg?style=flat)](#contributors) @@ -29,27 +28,25 @@ Dynamically typed Object Oriented Programming Language. **PySkiylia: [Latest release]** -Support here: [issues] +Open issues can be found here: [issues] + +To create an issue, be it a bug, question, feature request, or other, use this link here: [Open an issue] # Skiylia Skiylia is dynamically typed, object oriented, and most importantly *interpreted*. While it may share many similarities with C derivatives, its heritage is definitely Pythonic. -To that end, Skiylia is most aptly described as a Python-C# hybrid. - -## - ## Sample code ///This section contains a small snippet of Skiylia code that calculates the factorial of a number/// def factorial(n): - if int(n) != n: - return null //can't compute factorial of a float this way - if x < 2: - return 1 - return x * factorial(n - 1) //recursion that makes this work + if int(n) != n: + return null //can't compute factorial of a float this way + if n < 2: + return 1 + return n * factorial(n - 1) //recursion that makes this work var num = 6 print("The factorial of", num, "is", factorial(num)) @@ -58,6 +55,12 @@ To that end, Skiylia is most aptly described as a Python-C# hybrid. Within this [folder] is a collection of code examples that have been used to test the project. While not exhaustive by any means, they should cover the basics. Feel free to play around and get a feel for the language! +Who knows, at some point in the future there may even be a link to a Skiylia tutorial. It's certainly an idea in the works. + +## Running Skiylia + +Under the [Latest release] you'll find the most up to date version of PySkiylia, containing all the python sub-modules. Running PySkiylia.py from the command line will open the interpreter in REPL mode, while passing a .skiy file as a second argument will allow execution of said script. + ## Contributing Any contributions made are absolutely welcome. Checkout the issues area for any outstanding problems, or to file your own! @@ -72,8 +75,12 @@ I owe a huge debt to Bob Nystrom and his excellent book, [Crafting Interpreters] ## Tools -Languages: [Python] (of course) - + - The interpreter was written in [Python](https://www.python.org/) 3.8, and can be ran on any machine with it installed. + - [Mergify](https://mergify.io/) has been automatically managing all of the repository branches. + - [All-contributors](https://allcontributors.org/) has been managing the contributors section. + - [Snyk](https://snyk.io/) has been monitoring for security concerns. + - [Release-drafter](https://github.com/release-drafter/release-drafter) has been compiling all pull requests into changelogs on each draft release, massively expediating the process. + - And while we don't have an dependencies (yet?) [Dependabot](https://dependabot.com/) has been keeping in the shadows. ## Contributors @@ -95,7 +102,10 @@ All the people who have contributed ([emoji key](https://allcontributors.org/doc This project follows the [all-contributors](https://allcontributors.org) specification. + + [Latest release]: https://github.com/SK1Y101/PySkiylia/releases [issues]: https://github.com/SK1Y101/PySkiylia/issues [folder]: https://github.com/SK1Y101/PySkiylia/tree/main/ExampleCode [Crafting Interpreters]: https://craftinginterpreters.com/ +[Open an issue]: https://github.com/SK1Y101/PySkiylia/issues/new/choose