{"id":33231761,"url":"https://github.com/digikar99/reader","last_synced_at":"2026-01-31T06:11:21.485Z","repository":{"id":113517232,"uuid":"217277540","full_name":"digikar99/reader","owner":"digikar99","description":"A utility library intended at providing reader macros for lambdas, arrays, accessors, hash-tables and hash-sets.","archived":false,"fork":false,"pushed_at":"2023-02-12T11:11:22.000Z","size":36,"stargazers_count":10,"open_issues_count":1,"forks_count":1,"subscribers_count":4,"default_branch":"master","last_synced_at":"2024-06-21T18:10:24.577Z","etag":null,"topics":["common-lisp","library","reader-macros"],"latest_commit_sha":null,"homepage":"","language":"Common Lisp","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/digikar99.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":"2019-10-24T10:58:04.000Z","updated_at":"2023-04-05T09:00:37.000Z","dependencies_parsed_at":"2023-07-08T18:45:50.889Z","dependency_job_id":null,"html_url":"https://github.com/digikar99/reader","commit_stats":null,"previous_names":[],"tags_count":2,"template":false,"template_full_name":null,"purl":"pkg:github/digikar99/reader","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/digikar99%2Freader","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/digikar99%2Freader/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/digikar99%2Freader/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/digikar99%2Freader/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/digikar99","download_url":"https://codeload.github.com/digikar99/reader/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/digikar99%2Freader/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":284759739,"owners_count":27058842,"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","status":"online","status_checked_at":"2025-11-16T02:00:05.974Z","response_time":65,"last_error":null,"robots_txt_status":"success","robots_txt_updated_at":"2025-07-24T06:49:26.215Z","robots_txt_url":"https://github.com/robots.txt","online":true,"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":["common-lisp","library","reader-macros"],"created_at":"2025-11-16T18:00:20.906Z","updated_at":"2025-11-16T19:01:17.962Z","avatar_url":"https://github.com/digikar99.png","language":"Common Lisp","readme":"# Installation\n\nDownload from the [Releases section](https://github.com/digikar99/reader/releases).\n\n\u003e I'll promote v0.10.0 to v1.0.0 if there are no significant changes over the next year.\n\n# Getting Started\n\n```lisp\n;; Enable reader macros using the following:\n(reader:enable-reader-syntax \u0026rest reader-macro-identifiers)\n;; OR\n(reader+swank:enable-package-local-reader-syntax \u0026rest reader-macro-identifiers)\n\n;; For instance, to enable reader macros for hash table and set:\n(reader:enable-reader-syntax 'hash-table 'set)\n\n;; The following gives you a list of identifiers:\n(documentation 'reader:enable-reader-syntax 'cl:function)\n\n;; Complementory macros\n;; (reader:disable-reader-syntax) ; is complementary\n;; OR\n;; (reader+swank-disable-package-local-reader-syntax)\n```\n\n# Examples\n\n```lisp\nCL-USER\u003e #[[1 2 3\n            4 5 6]\n           [3 2 1\n            7 8 9]]\n#3A(((1 2 3) (4 5 6)) ((3 2 1) (7 8 9)))        ; cleaner syntax for arrays\nCL-USER\u003e (gethash 'a {eq 'a 1 'b 2})            ; hash-tables\n1\nT\nCL-USER\u003e (let ((reader:*set-function* 'hash-set:list-to-hs))\n           (hash-set:hs-memberp (eval (read-from-string \"#{\\\"a\\\" \\\"b\\\" \\\"c\\\"}\"))\n                                \"c\"))\nT\nCL-USER\u003e #{'(1) '(1)} ; default is CL:REMOVE-DUPLICATES\n((1) (1))\nCL-USER\u003e #{'(1) '(1) :test #'equal}\n((1))\nCL-USER\u003e [#2A((1 2 3) (4 5 6)) 1 0]             ; accessors\n4\nCL-USER\u003e (setf reader:*get-val-array-function* 'select:select)\nSLCT:SELECT\nCL-USER\u003e (let ((arr #2A((1 2 3) (4 5 6))))\n           [arr t 0])\n#(1 4)\nCL-USER\u003e [{\"a\" 1 \"b\" 2} \"a\"]\n1\nT\nCL-USER\u003e [(cl-json:decode-json-from-string \"{\\\"a\\\":1, \\\"b\\\":2}\") :b] ; works with alists\n2\nCL-USER\u003e (-\u003e {\"a\" \"apple\" \"b\" \"ball\"} [\"b\"] [1]); accessors can be chained using -\u003e, an arrow\n                                                ; see https://github.com/hipeta/arrow-macros/\n#\\a\nCL-USER\u003e #!echo -n hello world\nhello world                                     ; Captures until the end of line\nNIL                                             ; Should be possible to capture into a string\nNIL                                             ; but not ideal for speed\n0\nCL-USER\u003e (let ((a t)) !a)                       ; not\nNIL\nCL-USER\u003e (let ((a 5.0d0)) $a)                   ; write-to-string\n\"5.0d0\"                   ; should this be \"ensure-string\"? raise an issue!\nCL-USER\u003e ?reader:enable-reader-syntax           ; variable use not intended\nREADER:ENABLE-READER-SYNTAX\n  [symbol]\nENABLE-READER-SYNTAX names a macro:\n  Lambda-list: (\u0026REST READER::READER-MACRO-IDENTIFIERS)\n  Documentation:\n    READER-MACRO-IDENTIFIERS are any of the following symbols:\n      GET-VAL, HASH-TABLE, NOT, STRING, DESCRIBE, ARRAY, SET, RUN-PROGRAM\n  Source file: /home/user/quicklisp/local-projects/reader/reader.lisp\n```\n## Notes\n\nThe functions used for constructing arrays, hash-tables, sets, accessing array elements or accessors in general can be specified by\n\n- `*array-function*`\n- `*hash-table-function*`\n- `*set-function*`\n- `*get-val-array-function*`\n- `*get-val-function*`\n\nThis should allow users to use [fset](https://github.com/slburson/fset) or [access](https://github.com/AccelerationNet/access) or other libraries for the respective functions.\n\nBy default, alists and plists are treated distinct from lists whenever possible (see the `get-val` method specialized on lists). To disable this behavior, set each of these to `T`:\n\n- `*alists-are-lists*`\n- `*plists-are-lists*`\n\n\n### Hash Tables\n\n- `{\"a\" 1 \"b\" 2}` - hash tables use `'equalp` as the default test. The intended test function  can be specified as the first element of the literal syntax. Besides providing with a choice, this also gets the indentation correct (see [Modification for emacs](#modifications-for-emacs).\n\n### Setting alists and plists\n\n- `(setf [] ...)` does not work with empty alists and plists. This seems to require setf-expanders with `get-val` generic-function.\n\n### array vs get-val\n\n- `[...]` (`get-val`) does not work inside `#[...]` (`array`) syntax. I do not have a plan or haven't figured out how to combine the two; and I find that okay since the `array` syntax is meant for cleaner representation in works involving matrices.\n\n## Notes for existing users upgrading to v0.10.0 from v0.9.1\n\n### Lambda\n\n- `lambda` with the following usage has been removed.\n\n```lisp\nCL-USER\u003e (mapcar λ(write-to-string -) '(2 3 4)) ; lambdas\n(\"2\" \"3\" \"4\")\n```\n\nThis begins to feel like line-noise after a while and is not ideal for readability; a better equivalent is the simple macro\n\n```lisp\nCL-USER\u003e (defmacro lm (\u0026rest var-body)\n           `(lambda ,(butlast var-body)\n              ,@(last var-body)))\nLM\nCL-USER\u003e (mapcar (lm o (write-to-string o)) '(2 3 4))\n(\"2\" \"3\" \"4\")\n```\n\n### Hash-table\n\nSince the function used for constructing hash-tables is now configurable (via `reader:*hash-table-function*`), the first input to the hash-table may be interpreted as the equality function. Thus, hash-table syntax can take an even (with default test `cl:equalp`) or odd (with the first symbol being interpreted as the equality function) number of arguments.\n\n\n### Setting alists and plists\n\nNow works for non-empty lists.\n\n## Testing\n\n```lisp\n(ql:quickload \"reader\")\n(5am:run :reader)\n;; OR\n(asdf:test-system \"reader\")\n```\n\n# Emacs Indentation Support\n\n```lisp\n(modify-syntax-entry ?\\[ \"(]\" lisp-mode-syntax-table)\n(modify-syntax-entry ?\\] \")[\" lisp-mode-syntax-table)\n(modify-syntax-entry ?\\{ \"(}\" lisp-mode-syntax-table)\n(modify-syntax-entry ?\\} \"){\" lisp-mode-syntax-table)\n(define-key paredit-mode-map (kbd \"{\") 'paredit-open-curly)\n(define-key paredit-mode-map (kbd \"}\") 'paredit-close-curly)\n(global-set-key (kbd \"C-S-l\") (lambda () ; for inserting lambda\n                                (interactive)\n                                (insert-char (aref (symbol-name 'λ) 0))))\n(setq paredit-space-for-delimiter-predicates\n      (list (lambda (endp delimiter)\n              (not (and (eql ?\\( delimiter)\n                        (member (char-before (point))\n                                '(?\\@ ?λ))))))))\n(set-language-environment \"UTF-8\")\n```\n\nMotivation: [paredit curly brace matching in swank-clojure repl - Stack OverFlow](https://stackoverflow.com/questions/8598116/paredit-curly-brace-matching-in-swank-clojure-repl)\n\n## Known Issues\n\nKnown issues include aligning hash-tables without first-element-as-key:\n\n```lisp\n{\"hello\" 1\n         \"world\" 2}\n```\n\nA work-around is to specify the test as the first element, and let that default exist for one-liners:\n\n```lisp\n{equal \"hello\" 1\n       \"world\" 2}\n{\"hello\" 1 \"world\" 2}\n```\n\n# Comments\n\n- [`cl-interpol`](http://edicl.github.io/cl-interpol/) is a prominent library providing perl / shell-like string interpolation facilities.\n- [`cl-json`](https://common-lisp.net/project/cl-json/cl-json.html) can be used for parsing JSON.\n","funding_links":[],"categories":["Python ##","Miscellaneous ##"],"sub_categories":[],"project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdigikar99%2Freader","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fdigikar99%2Freader","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fdigikar99%2Freader/lists"}