{"id":17651284,"url":"https://github.com/joetifa2003/windlang","last_synced_at":"2026-03-06T17:35:49.759Z","repository":{"id":57662000,"uuid":"471694966","full_name":"joetifa2003/windlang","owner":"joetifa2003","description":"WindLang, A simple programming language built with golang 🍃","archived":false,"fork":false,"pushed_at":"2023-08-02T21:45:12.000Z","size":2519,"stargazers_count":17,"open_issues_count":2,"forks_count":1,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-03-31T07:41:20.903Z","etag":null,"topics":["golang","interpreter","language","programming-language"],"latest_commit_sha":null,"homepage":"https://windlang.vercel.app/","language":"Go","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"mit","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/joetifa2003.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":"LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null,"roadmap":null,"authors":null,"dei":null,"publiccode":null,"codemeta":null}},"created_at":"2022-03-19T12:53:50.000Z","updated_at":"2025-01-12T16:49:09.000Z","dependencies_parsed_at":"2024-06-20T15:41:59.713Z","dependency_job_id":"1216983a-4936-4d5a-8174-5fc6e50b8551","html_url":"https://github.com/joetifa2003/windlang","commit_stats":null,"previous_names":[],"tags_count":13,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/joetifa2003%2Fwindlang","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/joetifa2003%2Fwindlang/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/joetifa2003%2Fwindlang/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/joetifa2003%2Fwindlang/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/joetifa2003","download_url":"https://codeload.github.com/joetifa2003/windlang/tar.gz/refs/heads/main","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":252833235,"owners_count":21811138,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2022-07-04T15:15:14.044Z","host_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub","repositories_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories","repository_names_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repository_names","owners_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners"}},"keywords":["golang","interpreter","language","programming-language"],"created_at":"2024-10-23T11:40:44.576Z","updated_at":"2026-03-06T17:35:44.732Z","avatar_url":"https://github.com/joetifa2003.png","language":"Go","funding_links":[],"categories":[],"sub_categories":[],"readme":"\u003cp align=\"center\"\u003e\n  \u003cimg src=\"assets/WindLogo.png\" /\u003e\n\u003c/p\u003e\n\n# WindLang, A simple programming language built with golang 🍃\n\n[![Go Report Card](https://goreportcard.com/badge/github.com/joetifa2003/windlang)](https://goreportcard.com/report/github.com/joetifa2003/windlang)\n\n-   [WindLang, A simple programming language built with golang 🍃](#windlang-a-simple-programming-language-built-with-golang-)\n    -   [What is wind?](#what-is-wind)\n    -   [Playground](#playground)\n    -   [Cool but why?](#cool-but-why)\n    -   [Why Golang, not Rust?](#why-golang-not-rust)\n    -   [How to use it?](#how-to-use-it)\n    -   [So what can it do?](#so-what-can-it-do)\n        -   [Hello world?](#hello-world)\n        -   [Variables](#variables)\n        -   [Data types](#data-types)\n        -   [Arrays](#arrays)\n            -   [Array.push(element) -\u003e any[]](#arraypushelement---any)\n            -   [Array.pop() -\u003e any](#arraypop---any)\n            -   [Array.removeAt(index) -\u003e any](#arrayremoveatindex---any)\n            -   [Array.len() -\u003e int](#arraylen---int)\n            -   [Array.join(separator) -\u003e string](#arrayjoinseparator---string)\n            -   [Array.map(function) -\u003e any[]](#arraymapfunction---any)\n            -   [Array.filter(function) -\u003e any[]](#arrayfilterfunction---any)\n            -   [Array.reduce(fn(accumulator, element), initialValue) -\u003e any](#arrayreducefnaccumulator-element-initialvalue---any)\n            -   [Array.contains(function) -\u003e boolean](#arraycontainsfunction---boolean)\n            -   [Array.count(function) -\u003e int](#arraycountfunction---int)\n            -   [Array.clone() -\u003e any[]](#arrayclone---any)\n        -   [Strings](#strings)\n            -   [String.len(separator) -\u003e int](#stringlenseparator---int)\n            -   [String.charAt(index) -\u003e string](#stringcharatindex---string)\n            -   [String.contains(substr) -\u003e boolean](#stringcontainssubstr---boolean)\n            -   [String.containsAny(substr) -\u003e boolean](#stringcontainsanysubstr---boolean)\n            -   [String.count(substr) -\u003e string](#stringcountsubstr---string)\n            -   [String.replace(old, new) -\u003e string](#stringreplaceold-new---string)\n            -   [String.replaceAll(old, new) -\u003e string](#stringreplaceallold-new---string)\n            -   [String.replaceN(old, new, n) -\u003e string](#stringreplacenold-new-n---string)\n            -   [String.changeAt(index, new) -\u003e string](#stringchangeatindex-new---string)\n            -   [String.indexOf(substr) -\u003e int](#stringindexofsubstr---int)\n            -   [String.lastIndexOf(substr) -\u003e int](#stringlastindexofsubstr---int)\n            -   [String.split(separator) -\u003e string[]](#stringsplitseparator---string)\n            -   [String.trim() -\u003e string](#stringtrim---string)\n            -   [String.toLowerCase() -\u003e string](#stringtolowercase---string)\n            -   [String.toUpperCase() -\u003e string](#stringtouppercase---string)\n        -   [Functions](#functions)\n        -   [Closures](#closures)\n        -   [If expressions](#if-expressions)\n        -   [Include statement](#include-statement)\n        -   [For loops](#for-loops)\n        -   [While loops](#while-loops)\n        -   [HashMaps](#hashmaps)\n    -   [Todos](#todos)\n\n## What is wind?\n\nWind is an interpreted language written in golang.\n\n## Playground\n\nThe easiest way to play with WindLang is to use the [playground](https://windlang.vercel.app/playground)\n\n## Cool but why?\n\nI'm working on this as a side project and it's the 5th attempt at writing my own programming language, And it got me my first job too! it's awesome 💙\n\n## Why Golang, not Rust?\n\nI already tried to build this with Rust, but I battled a lot with the Rust compiler and felt like golang is a better middle ground I got so much faster with golang, and it was surprising that the golang implementation was actually faster!\nNot because golang is faster than rust, it's my lack of knowledge, and the way I code is not \"Rusty\"\n\n## How to use it?\n\nHead up to the [releases](https://github.com/joetifa2003/windlang/releases) page and download Wind for your operating system\n\nAnd execute windlang executable\n\n```\nWindLang, A simple programming language written in golang\n\nUsage:\n  windlang [command]\n\nAvailable Commands:\n  completion  Generate the autocompletion script for the specified shell\n  help        Help about any command\n  run         Run a Wind script\n\nFlags:\n  -h, --help     help for windlang\n  -t, --toggle   Help message for toggle\n\nUse \"windlang [command] --help\" for more information about a command.\n```\n\nThis is the Wind cli you can use the run command to run a Wind script file\nInstall the vscode extension [here](https://marketplace.visualstudio.com/items?itemName=YoussefAhmed.windlang)!\n\n## So what can it do?\n\nLet me demonstrate the features implemented as of now\n\n### Hello world?\n\n```swift\nprintln(\"Hello world\");\n```\n\nYes, Wind can print Hello world, Surprising huh?\n\n### Variables\n\n```swift\nlet x = 1;\nprintln(x); // 1\n\n\nx = \"Hello world\";\nprintln(x); // Hello World\n```\n\nYou can declare variables in Wind with the `let` keyword, Variables in wind are dynamically typed and you can reassign them to any type.\n\n### Data types\n\n```swift\n1              // int\n3.14           // float\ntrue, false    // boolean\nnil            // null\n\"Hello World\"  // String\n[1, \"2\", true] // Arrays\n{\n    \"name\": \"Youssef\",\n    \"age\": 18\n}              // HashMaps\n```\n\n### Arrays\n\n```swift\nlet arr = [1, \"2\", true];\n\nprintln(arr[0]); // 1\nprintln(arr[1]); // 2\nprintln(arr[2]); // true\n\narr.push(\"3\") // [1, \"2\", true, \"3\"]\nprintln(arr[3]); // 3\narr.pop()     // [1, \"2\", true]\n```\n\nArrays in Wind can take any type of data, and can be of any size\nYou can append to an array by using the `append` function\nYou can remove an element by index using the `remove` function.\n\n#### Array.push(element) -\u003e any[]\n\n```swift\nlet x = [1, 2, 3];\nx.push(4) // [1, 2, 3, 4]\n```\n\nArray push function adds an element to the end of the array\n\n#### Array.pop() -\u003e any\n\n```swift\nlet x = [1, 2, 3, 4];\nx.push(4); // [1, 2, 3, 4]\n\nlet y = x.pop(); // [1, 2, 3]\nprintln(y); // 4\n```\n\nArray pop function removes the last element of the array and returns it\n\n#### Array.removeAt(index) -\u003e any\n\n```swift\nlet x = [1, 2, 3, 4];\nx.push(4); // [1, 2, 3, 4]\n\nlet y = x.removeAt(3); // [1, 2, 3]\nprintln(y); // 4\n```\n\nArray removeAt function removes an element at the index of the array and returns it\n\n#### Array.len() -\u003e int\n\n```swift\nlet x = [1, \"hi\", true];\nprintln(x.len()); // 3\n```\n\nArray len function returns the length of the array\n\n#### Array.join(separator) -\u003e string\n\n```swift\nlet x = [1, \"hi\", 3, 4];\n\nprintln(x.join(\"-\")); // 1-hi-3-4\n```\n\nArray join function returns a string with all the elements of the array separated by the separator\n\n#### Array.map(function) -\u003e any[]\n\n```swift\nlet x = [1, 2, 3];\n\nprintln(x.map(fn(x) {x * 2})); // [2, 4, 6]\n```\n\nArray map function applies the function to each element of the array and returns a new array with the results\n\n#### Array.filter(function) -\u003e any[]\n\n```swift\nlet x = [1, 2, 3, 4];\nlet even = x.filter(fn(x) { x % 2 == 0});\n\nprintln(even); // [2, 4]]\n```\n\nArray filter function applies the function to each element of the array and if the function returns true, the element is added to the new array\n\n#### Array.reduce(fn(accumulator, element), initialValue) -\u003e any\n\n```swift\nlet x = [1, 2, 3, 4, 5];\nlet sum = x.reduce(fn(acc, x) { acc + x}, 0);\n\nprintln(sum); // 15\n```\n\nArray reduce function applies the function to each element of the array and returns a single value\n\n#### Array.contains(function) -\u003e boolean\n\n```swift\nlet arr = [1, 3, 5];\nprintln(arr.contains(fn(x) { x % 2 == 0})); // false\n\narr = [1, 2, 3, 4, 5];\nprintln(arr.contains(fn(x) { x % 2 == 0})); // true\n```\n\nArray contains function applies the function to each element of the array and returns true if the function returns true for any element\n\n#### Array.count(function) -\u003e int\n\n```swift\nlet arr = [1, 3, 5];\nprintln(arr.count(fn(x) { x % 2 == 0})); // 0\n\narr = [1, 2, 3, 4, 5];\nprintln(arr.count(fn(x) { x % 2 == 0})); // 2\n```\n\nArray count function applies the function to each element of the array and returns the number of times the function returns true\n\n#### Array.clone() -\u003e any[]\n\n```swift\nlet x = [1, 2, 3];\nlet notCloned = x;\nlet cloned = x.clone();\n\nx[0] = \"changed\";\nprintln(notCloned[0]); // Changed\nprintln(cloned[0]); // 1\n```\n\nArray clone function returns a copy of the array\n\n### Strings\n\nStrings in Wind start and end with a double quote `\"` and can contain any character and can be multi-line\n\n#### String.len(separator) -\u003e int\n\n```swift\nlet x = \"Hello\";\n\nprintln(x.len()); // 5\n```\n\nString len function returns the length of the string\n\n#### String.charAt(index) -\u003e string\n\n```swift\nlet name = \"youssef\";\nprintln(name.charAt(0)); // y\n```\n\nString charAt function returns the character at the specified index\n\n#### String.contains(substr) -\u003e boolean\n\n```swift\nlet name = \"youssef\";\n\nprintln(name.contains(\"ss\")); // true\n```\n\nString contains function returns true if the string contains the exact substring\n\n#### String.containsAny(substr) -\u003e boolean\n\n```swift\nlet vowels = \"aeiou\";\nlet name = \"youssef\";\n\nprintln(name.containsAny(vowels)); // true\n```\n\nString contains function returns true if the string contains any character of the substring\n\n#### String.count(substr) -\u003e string\n\n```swift\nlet name = \"youssef\";\n\nprintln(name.count(\"s\")); // 2\n```\n\nString count function returns the number of times the substring appears in the string\n\n#### String.replace(old, new) -\u003e string\n\n```swift\nlet name = \"John Doe\";\n\nprintln(name.replace(\"o\", \"x\")); // Jxhn Doe\n```\n\nString replace function returns a new string after replacing one old substring with a new substring\n\n#### String.replaceAll(old, new) -\u003e string\n\n```swift\nlet name = \"John Doe\";\n\nprintln(name.replaceAll(\"o\", \"x\")); // Jxhn Dxe\n```\n\nString replace function returns a new string after replacing all old substring with a new substring\n\n#### String.replaceN(old, new, n) -\u003e string\n\n```swift\nlet name = \"Youssef\";\n\nprintln(name.replaceN(\"s\", \"x\", 1)); // Youxsef\nprintln(name.replaceN(\"s\", \"x\", 2)); // Youxxef\n```\n\nString replace function returns a new string after replacing n of old substring with a new substring\n\n#### String.changeAt(index, new) -\u003e string\n\n```swift\nlet name = \"Ahmed\";\n\nprintln(name.changeAt(0, \"a\")); // ahmed\n```\n\nString changeAt function returns a new string after changing the character at the specified index\n\n#### String.indexOf(substr) -\u003e int\n\n```swift\nlet name = \"John Doe\";\n\nprintln(name.indexOf(\"o\")); // 1\n```\n\nString indexOf function returns the index of the first occurrence of the substring\n\n#### String.lastIndexOf(substr) -\u003e int\n\n```swift\nlet name = \"John Doe\";\n\nprintln(name.lastIndexOf(\"o\")); // 6\n```\n\nString indexOf function returns the index of the last occurrence of the substring\n\n#### String.split(separator) -\u003e string[]\n\n```swift\nlet name = \"Youssef Ahmed\";\nlet names = name.split(\" \"); // [\"Youssef\", \"Ahmed\"]\nlet firstName = names[0];\nlet lastName = names[1];\n\nprintln(\"First name is: \" + firstName); // First name is: Youssef\nprintln(\"Last name is: \" + lastName); // Last name is: Ahmed\n```\n\nString join function returns an array of strings by splitting the string by the separator\n\n#### String.trim() -\u003e string\n\n```swift\nlet name = \" John Doe   \";\n\nprintln(name.trim()); // \"John Doe\"\n```\n\nString trim function removes whitespace from the start/end of the string and returns a new string\n\n#### String.toLowerCase() -\u003e string\n\n```swift\nlet name = \"JoHn dOe\";\n\nprintln(name.toLowerCase()); // john doe\n```\n\nString toLowerCase function returns a new string with all the characters in lower case\n\n#### String.toUpperCase() -\u003e string\n\n```swift\nlet name = \"JoHn dOe\";\n\nprintln(name.toUpperCase()); // JOHN DOE\n```\n\nString toLowerCase function returns a new string with all the characters in upper case\n\n### Functions\n\n```swift\nlet add = fn(x, y) { x + y; };\n\n\n// This is the same as\nlet add = fn(x, y) {\n    return x + y;\n};\n\nprintln(add(1, 2)); // 3\n```\n\nYes, this looks like Rust functions. The last expression in a function is implicitly returned\n\n### Closures\n\n```swift\nlet addConstructor = fn(x) {\n    fn(y) {\n        x + y;\n    };\n};\n\n\n// This is the same as\nlet addConstructor = fn(x) {\n    return fn(y) {\n        return x + y;\n    };\n};\n\n\nlet addTwo = addConstructor(2); // This will return a function\n\nprintln(addTwo(3)); // 5\n```\n\nThis is one of the coolest things implemented in Wind. As I said functions in Wind are expressions, so you can return a function or pass a function to another function.\n\n```swift\nlet welcome = fn(name, greeter) {\n    greeter() + \" \" + name\n};\n\nlet greeter = fn() { \"Hello 👋\"};\n\nprintln(welcome(\"Wind 🍃\", greeter)); // Hello 👋 Wind 🍃\n```\n\n### If expressions\n\n```swift\n// Use if as an expression\nlet grade = 85;\nlet msg = if (grade \u003e 50) { \"You passed\" } else { \"You didn't pass\" };\n\nprintln(msg); // You passed\n\n// Or use if as a statement\nif (grade \u003e 50) {\n    println(\"You passed\");\n} else {\n    println(\"You didn't pass\");\n}\n```\n\nAs you can see here we can use it as an expression or as a statement\n\nNote that after any expression the semicolon is optional. We can type `\"You passed\";` or `\"You passed\"` and it will implicitly return it\n\n### Include statement\n\n```swift\n// test.wind\n\nlet msg = \"Hello 👋\";\n\nlet greeter = fn() {\n    println(msg);\n};\n```\n\n```swift\n// main.wind\ninclude \"./test.wind\";\n\ngreeter(); // Hello 👋\n\n// You can also alias includes\ninclude \"./test.wind\" as test;\n\ntest.greeter(); // Hello 👋\n```\n\nInclude statements allow you to include other Wind scripts, It initializes them once and can be used by multiple files at the same time while preserving state.\n\n### For loops\n\n```swift\nlet names = [\"Youssef\", \"Ahmed\", \"Soren\", \"Morten\", \"Mads\", \"Jakob\"];\n\nfor (let i = 0; i \u003c len(names); i++) {\n    println(\"Hello \" + names[i]);\n}\n\n// Hello Youssef\n// Hello Ahmed\n// Hello Soren\n// Hello Morten\n// Hello Mads\n// Hello Jakob\n```\n\n### While loops\n\n```swift\nlet x = 0;\n\nwhile (x \u003c 5) {\n    println(x);\n    x++;\n}\n\n// 0\n// 1\n// 2\n// 3\n// 4\n```\n\n### HashMaps\n\n```swift\nlet person = {\n    \"name\": \"Youssef\",\n    \"age\": 18,\n    \"incrementAge\": fn() {\n        person.age++;\n    }\n};\n\nprintln(person[\"name\"]); // Youssef\nprintln(person.age); // 18\nperson.incrementAge();\nprintln(person.age); // 19\n```\n\nHashmaps are like js object and can store key value pairs, Keys can be integers, strings and booleans. Values can be any type.\n\n## Todos\n\n-   ~~Named include statements~~\n\n-   ~~HashMaps (Javascript objects~~\n\n-   A bytecode interpreter maybe\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjoetifa2003%2Fwindlang","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fjoetifa2003%2Fwindlang","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fjoetifa2003%2Fwindlang/lists"}