{"id":42333837,"url":"https://github.com/haxetink/tink_sql","last_synced_at":"2026-01-27T14:10:27.213Z","repository":{"id":10408584,"uuid":"12564423","full_name":"haxetink/tink_sql","owner":"haxetink","description":"SQL embedded into Haxe","archived":false,"fork":false,"pushed_at":"2025-12-22T20:31:49.000Z","size":917,"stargazers_count":56,"open_issues_count":43,"forks_count":18,"subscribers_count":9,"default_branch":"master","last_synced_at":"2025-12-24T09:49:47.334Z","etag":null,"topics":["database","haxe","sql","tink"],"latest_commit_sha":null,"homepage":"","language":"Haxe","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/haxetink.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,"zenodo":null,"notice":null,"maintainers":null,"copyright":null,"agents":null,"dco":null,"cla":null}},"created_at":"2013-09-03T13:26:06.000Z","updated_at":"2025-12-22T20:31:53.000Z","dependencies_parsed_at":"2023-01-11T20:14:33.636Z","dependency_job_id":"d6e75db8-bf06-4b6c-9e19-664d9f4ef2c5","html_url":"https://github.com/haxetink/tink_sql","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"purl":"pkg:github/haxetink/tink_sql","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/haxetink%2Ftink_sql","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/haxetink%2Ftink_sql/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/haxetink%2Ftink_sql/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/haxetink%2Ftink_sql/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/haxetink","download_url":"https://codeload.github.com/haxetink/tink_sql/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/haxetink%2Ftink_sql/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":28814450,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-01-27T12:25:15.069Z","status":"ssl_error","status_checked_at":"2026-01-27T12:25:05.297Z","response_time":168,"last_error":"SSL_read: unexpected eof while reading","robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":false,"can_crawl_api":true,"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":["database","haxe","sql","tink"],"created_at":"2026-01-27T14:10:26.651Z","updated_at":"2026-01-27T14:10:27.207Z","avatar_url":"https://github.com/haxetink.png","language":"Haxe","readme":"[![CI](https://github.com/haxetink/tink_sql/workflows/CI/badge.svg)](https://github.com/haxetink/tink_sql/actions)\n[![Gitter](https://badges.gitter.im/Join%20Chat.svg)](https://gitter.im/haxetink/public)\n\n# Tinkerbell SQL\n\nThis library embeds SQL right into the Haxe language. Think LINQ (not the syntax sugar, but the framework).\n\n**Breaking Change (2021-09-16)**\n\n[Transaction](#transactions) is now supported with a minor breaking change.\nMigration guide: https://github.com/haxetink/tink_sql/pull/130#issuecomment-822971910 \n\n## Motivation\n\nMost developers tend to dislike SQL, at least for a significant part of their career. A symptom of that are ever-repeating attempts to hide the database layer behind ORMs, with very limited success.\n\nRelational databases are however a very powerful concept, that was pioneered over 40 years ago.\n\nTink SQL has been built to embrace using SQL for your database interactions, but in a type safe way that fits with the Haxe ecosystem.\n\n## Defining your schema\n\nDefine a database like so:\n\n```haxe\nimport tink.sql.Types;\n\ntypedef User = {\n  var id:Id\u003cUser\u003e;\n  var name:VarChar\u003c255\u003e;\n  @:unique var email:VarChar\u003c255\u003e;\n  var password:VarChar\u003c255\u003e;\n}\n\ntypedef Post = {\n  var id:Id\u003cPost\u003e;\n  var author:Id\u003cUser\u003e;\n  var title:LongText;\n  var url:VarChar\u003c255\u003e;\n}\n\ntypedef Tag = {\n  var id:Id\u003cTag\u003e;\n  var name:VarChar\u003c20\u003e;\n  var desc:Null\u003cText\u003e;\n}\n\ntypedef PostTags = {\n  var post:Id\u003cPost\u003e;\n  var tag:Id\u003cTag\u003e;\n}\n\n@:tables(User, Post, Tag, PostTags)\nclass Db extends tink.sql.Database {}\n```\n\n## Redefining table names\n\n```haxe\nclass Db extends tink.sql.Database {\n  @:table(\"blog_users\") var user:User;\n  @:table(\"blog_posts\") var post:Post;\n  @:table(\"news_tags\") var tag:Tag;\n  @:table(\"post_tags\") var postTags:PostTags;\n}\n```\n\n## Connecting to the database\n\n```haxe\nimport tink.sql.drivers.MySql;\n\nvar driver = new tink.sql.drivers.MySql({\n  user: 'user',\n  password: 'pass'\n});\nvar db = new Db('db_name', driver);\n```\n\n## Tables API\n\n\n - Table setup\n    - `db.User.create(): Promise\u003cNoise\u003e;`\n    - `db.User.drop(): Promise\u003cNoise\u003e;`\n    - `db.User.truncate(): Promise\u003cNoise\u003e;`\n - Selecting\n    - `db.User.count(): Promise\u003cInt\u003e;`\n    - `db.User.all(limit, orderBy): Promise\u003cArray\u003cUser\u003e\u003e;`\n    - `db.User.first(orderBy): Promise\u003cUser\u003e;`\n    - `db.User.where(filter)`\n    - `db.User.select(f:Fields-\u003eSelection\u003cRow\u003e)`\n      - Example, select name of user: `db.User.select({name: User.name}).where(User.id == 1).first()`\n - Writing\n    - `db.User.insertOne(row: User): Promise\u003cId\u003cUser\u003e\u003e;`\n    - `db.User.insertMany(rows: Array\u003cUser\u003e): Promise\u003cId\u003cUser\u003e\u003e;`\n    - `db.User.update(f:Fields-\u003eUpdate\u003cRow\u003e, options:{ where: Filter, ?max:Int }): Promise\u003c{rowsAffected: Int}\u003e;`\n        - Example, rename all users called 'Dave' to 'Donald': `db.User.update(function (u) return [u.name.set('Donald')], { where: function (u) return u.name == 'Dave' } );`\n    - `db.User.delete(options:{ where: Filter, ?max:Int }): Promise\u003c{rowsAffected: Int}\u003e;`\n - Advanced Selecting\n    - `db.User.as(alias);`\n    - `db.User.join(db.User).on(id == copiedFrom).all();`\n    - `db.User.leftJoin(db.User);`\n    - `db.User.rightJoin(db.User);`\n    - `db.User.stream(limit, orderBy): tink.streams.RealStream\u003cUser\u003e;`\n\n... to be continued ...\n\n## Transactions\n\n```haxe\n// transaction with a commit\ndb.transaction(trx -\u003e {\n  trx.User.insertOne(...).next(id -\u003e Commit(id)); // user is inserted\n});\n\n// transaction with explicit rollback\ndb.transaction(trx -\u003e {\n  trx.User.insertOne(...).next(_ -\u003e Rollback); // user insert is rolled back\n});\n\n// transaction with implicit rollback upon error\ndb.transaction(trx -\u003e {\n  trx.User.insertOne(...).next(_ -\u003e new Error('Aborted')); // user insert is rolled back\n});\n```","funding_links":[],"categories":[],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhaxetink%2Ftink_sql","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fhaxetink%2Ftink_sql","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fhaxetink%2Ftink_sql/lists"}