{"id":34972046,"url":"https://github.com/20centaurifux/efind","last_synced_at":"2026-04-13T09:31:19.851Z","repository":{"id":30970422,"uuid":"34528619","full_name":"20centaurifux/efind","owner":"20centaurifux","description":"An extendable wrapper for GNU find with a self-explanatory expression syntax.","archived":false,"fork":false,"pushed_at":"2025-05-07T17:03:51.000Z","size":1838,"stargazers_count":1,"open_issues_count":0,"forks_count":0,"subscribers_count":2,"default_branch":"main","last_synced_at":"2025-05-07T18:02:45.600Z","etag":null,"topics":["bison","c","files","find","flex","linux","python"],"latest_commit_sha":null,"homepage":"https://efind.dixieflatline.de","language":"C","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":"gpl-3.0","status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/20centaurifux.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG","contributing":null,"funding":null,"license":"COPYING","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null,"governance":null}},"created_at":"2015-04-24T16:12:12.000Z","updated_at":"2025-05-07T17:00:22.000Z","dependencies_parsed_at":"2022-07-15T02:32:24.645Z","dependency_job_id":null,"html_url":"https://github.com/20centaurifux/efind","commit_stats":null,"previous_names":[],"tags_count":21,"template":false,"template_full_name":null,"purl":"pkg:github/20centaurifux/efind","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/20centaurifux%2Fefind","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/20centaurifux%2Fefind/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/20centaurifux%2Fefind/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/20centaurifux%2Fefind/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/20centaurifux","download_url":"https://codeload.github.com/20centaurifux/efind/tar.gz/refs/heads/main","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/20centaurifux%2Fefind/sbom","scorecard":null,"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":286080680,"owners_count":31746291,"icon_url":"https://github.com/github.png","version":null,"created_at":"2022-05-30T11:31:42.601Z","updated_at":"2026-04-13T09:16:15.125Z","status":"ssl_error","status_checked_at":"2026-04-13T09:16:05.023Z","response_time":93,"last_error":"SSL_connect returned=1 errno=0 peeraddr=140.82.121.6:443 state=error: 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":["bison","c","files","find","flex","linux","python"],"created_at":"2025-12-26T23:51:34.475Z","updated_at":"2026-04-13T09:31:19.845Z","avatar_url":"https://github.com/20centaurifux.png","language":"C","funding_links":[],"categories":[],"sub_categories":[],"readme":"# efind - README\n\n## Overview\n\n**efind** (extendable find) searches for files in a directory hierarchy.\n\nBasically it's a wrapper for [GNU find](https://www.gnu.org/software/findutils/) providing an easier and more intuitive\nexpression syntax. It can be extended by custom functions to filter search\nresults.\n\n## A quick example\n\nLet's assume you want to find all MP3 (\\*.mp3) and Ogg Vorbis (\\*.ogg) files\nthat were modified less than two days ago in your music folder. That's no\nproblem with **efind's** self-explanatory expression syntax:\n\n\t$ efind ~/music \"(name='*.mp3' or name='*.ogg') and mtime\u003c2 days\"\n\nAdditionally you can filter the search result by audio tags and properties with\nthe [taglib](https://github.com/20centaurifux/efind-taglib) extension:\n\n\t$ efind ~/music \"(name='*.mp3' or name='*.ogg') and mtime\u003c2 days \\\n\t  and artist_matches('Welle: Erdball') and audio_length()\u003e120\"\n\nUse the --order-by option to sort the search result. In this example we sort the\nfound files by size (descending) and path (ascending):\n\n\t$ efind ~/music \"(name='*.mp3' or name='*.ogg') and mtime\u003c2 days \\\n\t  and artist_matches('Welle: Erdball') and audio_length()\u003e120\" \\\n\t  --order-by \"-{bytes}{path}\"\n\n**efind** also provides options to limit the output:\n\n\t$ efind ~/music \"(name='*.mp3' or name='*.ogg') and mtime\u003c2 days \\\n\t  and artist_matches('Welle: Erdball') and audio_length()\u003e120\" \\\n\t  --limit 1\n\nThe example above prints the first file matching the search criteria and\naborts the search immediately.\n\n**efind's** --printf option supports user-friendly field names. Furthermore,\n--exec arguments are interpreted as format strings. The example below converts\nMP3 and Ogg Vorbis files to WAV using [SoX](http://sox.sourceforge.net/):\n\n\t$ efind ~/music \"(name='*.mp3' or name='*.ogg')\"\n\t  --exec sox \"%{path}\" \"%{name}.wav\" \\;\n\n## General Usage\n\nRunning **efind** without any argument the search expression is read from\nstandard input and files are searched in the user's home directory.\nA different directory and expression can be specified with the --dir\nand --expr options:\n\n\t$ efind --dir=/tmp --expr=\"size\u003e1M and type=file\"\n\n**efind** tries to handle the first arguments as path(s) and expression. It's\nvalid to run **efind** the following way:\n\n\t$ efind ~/git ~/code \"type=file and name='CHANGELOG'\"\n\nIf you want to show the translated arguments without running GNU find use the --print\noption. To quote special shell characters append --quote:\n\n\t$ efind . \"iregex='.*\\.txt' and writable\" --print --quote\n\n**efind** is shipped with a manpage, of course.\n\n\t$ man efind\n\n## Expression Syntax\n\nA search expression consists of at least one comparison or file flag to test. Multiple\nexpressions can be evaluated by using conditional operators:\n\n| Operator | Description                                                                                                                                                   |\n| :------- | :------------------------------------------------------------------------------------------------------------------------------------------------------------ |\n| and      | If an expression returns logical false it returns that value and doesn't evaluate the next expression. Otherwise it returns the value of the last expression. |\n| or       | If an expression returns logical true it returns that value and doesn't evaluate the next expression. Otherwise it returns the value of the last expression.  |\n\nExpressions are evaluated from left to right. Use parentheses to force precedence.\n\nThe following operators can be used to compare a file attribute to a value:\n\n| Operator                 | Description      |\n| :----------------------- | :--------------- |\n| =, equals, equal         | equals to        |\n| \u003e, greater than, greater | greater than     |\n| \u003e=, at least             | greater or equal |\n| \u003c, less than, less       | less than        |\n| \u003c=, at most              | less or equal    |\n\nUse the not operator to test if an expression evaluates to logical false.\n\nA value must be of one of the data types listed below:\n\n| Type          | Description                                                                                                           |\n| :------------ | :---------------------------------------------------------------------------------------------------------------------|\n| string        | Quoted sequence of characters.                                                                                        |\n| number        | Whole number.                                                                                                         |\n| time interval | Time interval (number) with suffix. Supported suffixes are \"minute(s)\", \"hour(s)\" and \"day(s)\".                       |\n| file size     | Units of space (number) with suffix. Supported suffixes are \"byte(s)\", \"kilobyte(s)\", megabyte(s)\" and \"gigabyte(s)\". |\n| file type     | \"file\", \"directory\", \"block\", \"character\", \"pipe\", \"link\" or \"socket\".                                                |\n\nThe following file attributes are searchable:\n\n| Attribute  | Description                           | Type            | Example     |\n| :--------- | :------------------------------------ | :-------------- | :---------- |\n| name       | case sensitive filename pattern       | string          | \"*.txt\"     |\n| iname      | case insensitive filename pattern     | string          | \"Foo.bar\"   |\n| regex      | case sensitive regular expression     | string          | \".*\\\\.html\" |\n| iregex     | case insensitive regular expression   | string          | \".*\\\\.TxT\"  |\n| atime      | last access time                      | time interval   | 1 minute    |\n| ctime      | last file status change               | time interval   | 15 hours    |\n| mtime      | last modification time                | time interval   | 30 days     |\n| size       | file size                             | size            | 10 megabyte |\n| group      | name of the group owning the file     | string          | \"users\"     |\n| gid        | id of the group owning the file       | number          | 1000        |\n| user       | name of the user owning the file      | string          | \"john\"      |\n| uid        | id of the user owning the file        | number          | 1000        |\n| type       | file type                             | file type       | pipe        |\n| filesystem | name of the filesystem the file is on | string          | \"ext4\"      |\n\nAdditionally you can test these flags:\n\n| Flag       | Description                                                   |\n| :--------- | :------------------------------------------------------------ |\n| readable   | the file can be read by the user                              |\n| writable   | the user can write to the file                                |\n| executable | the user is allowed to execute the file                       |\n| empty      | the file is empty and is either a regular file or a directory |\n\n## Advanced Features\n\n### Output Format\n\nYou can change the output format of **efind** with the --printf option.\n\nThe following escape sequences and directives are available:\n\n#### Escape Sequences\n\n| Sequence        | Description                                    |\n| :-------------- | :----------------------------------------------|\n| \\\\a             | Alarm bell.                                    |\n| \\\\b             | Backspace.                                     |\n| \\\\f             | Form feed.                                     |\n| \\\\n             | Newline.                                       |\n| \\\\r             | Carriage return.                               |\n| \\\\t             | Horizontal tab.                                |\n| \\\\v             | Vertical tab.                                  |\n| \\\\0             | ASCII NUL.                                     |\n| \\\\\\\\            | A literal backslash.                           |\n| \\\\NNN           | The character whose ASCII code is NNN (octal). |\n| \\\\XNN           | The character whose ASCII code is NN (hex).    |\n\nAny other character following a \\\\ is printed.\n\n#### Directives\n\n| Directive       | Description                                                                                             |\n| :-------------- | :-------------------------------------------------------------------------------------------------------|\n| %%              | A literal percent sign.                                                                                 |\n| %Ak             | File's last access time in the format specified by k or in the format returned by the C ctime function. |\n| %b              | The amount of disk space used for this file in 512-byte blocks.                                         |\n| %Ck             | File's last status change time in the format specified by k, which is the same as for %A.               |\n| %D              | The device number on which the file exists (the st\\_dev field of struct stat) in decimal.               |\n| %f              | File's name with any leading directories removed (only the last element).                               |\n| %F              | Type of the filesystem the file is on.                                                                  |\n| %g              | File's group name, or numeric group ID if the group has no name.                                        |\n| %G              | File's numeric group ID.                                                                                |\n| %h              | Leading  directories of file's name (all but the last element).                                         |\n| %H              | Starting-point under which file was found.                                                              |\n| %i              | File's inode number (in decimal).                                                                       |\n| %k              | The amount of disk space used for this file in 1K blocks.                                               |\n| %l              | Object of symbolic link (empty string if file is not a symbolic link).                                  |\n| %m              | File's permission bits (in octal).                                                                      |\n| %M              | File's permissions (in symbolic form, as for ls).                                                       |\n| %n              | Number of hard links to file.                                                                           |\n| %p              | File's name.                                                                                            |\n| %P              | File's name with the name of the starting-point under which it was found removed.                       |\n| %s              | File's size in bytes.                                                                                   |\n| %S              | File's sparseness. If the file size is zero, the value printed is undefined.                            |\n| %Tk             | File's last modification time in the format specified by k, which is the same as for %A.                |\n| %u              | File's user name, or numeric user ID if the user has no name.                                           |\n| %U              | File's numeric user ID.                                                                                 |\n\n#### Time/Date fields\n\nAvailable time and date fields are\n\n| Field       | Description                                                       |\n| :---------- | :-----------------------------------------------------------------|\n| H           | hour (00..23)                                                     |\n| I           | hour (01..12)                                                     |\n| k           | hour (0..23)                                                      |\n| l           | hour (1..12)                                                      |\n| M           | minute (00..59)                                                   |\n| p           | locale's AM or PM                                                 |\n| r           | time, 12-hour (hh:mm:ss AM\\|PM)                                   |\n| S           | second (00..60)                                                   |\n| T           | time, 24-hour (hh:mm:ss)                                          |\n| X           | locale's time representation (H:M:S)                              |\n| Z           | time zone (e.g. EDT), or nothing if no time zone is determinable  |\n| a           | locale's abbreviated weekday name (Sun..Sat)                      |\n| A           | locale's full weekday name, variable length (Sunday..Saturday)    |\n| b           | locale's abbreviated month name (Jan..Dec)                        |\n| B           | locale's full month name, variable length (January..December)     |\n| c           | locale's date and time (Sat Nov 04 12:02:33 EST 1989)             |\n| d           | day of month (01..31)                                             |\n| D           | date (mm/dd/yy)                                                   |\n| h           | same as b                                                         |\n| j           | day of year (001..366)                                            |\n| m           | month (01..12)                                                    |\n| U           | week number of year with Sunday as first day of week (00..53)     |\n| w           | day of week (0..6)                                                |\n| W           | week number of year with Monday as first day of week (00..53)     |\n| x           | locale's date representation (mm/dd/yy)                           |\n| y           | last two digits of year (00..99)                                  |\n| Y           | year (1970...)                                                    |\n\n### Sorting\n\nYou can use the same directives to sort the search result as with the --printf option.\n\n\t$ efind . \"type=file\" --order-by \"sp\"\n\nPrepend a minus sign to change direction:\n\n\t$ efind . \"type=file\" --order-by \"-{bytes}{path}\"\n\n## Differences to GNU find\n\nSometimes GNU find doesn't behave in a way an average user would expect. The following\nexpression finds all documents in the current folder with a file size less or equal than\n1G because every file with at least *one byte* is rounded up:\n\n\t$ find . -size 1G\n\n**efind** converts file sizes to byte to avoid this confusing behaviour:\n\n\t$ efind . \"size=1G\" --print\n\t$ find . -size 1073741824c\n\n**efind's** --printf option is not fully compatible with GNU find:\n\n* In contrast to GNU find numeric values like file size or group id are *not* converted\n  to string. This means that all number related flags work with **efind**.\n* Width and precision are interpreted *exactly the same way* as the printf C function does.\n* The fields %a, %c and %t print the timestamp in seconds.\n* Date format strings are not limited to a single field. The string \"%AHMS\" prints hour,\n  minute and second of the last file access, for example.\n* **efind's** printf format supports user-friendly field names like \"{path}\" or \"{group}\".\n* When printing an undefined escape sequence (e.g. \"\\P\") only the character following the\n  backslash is printed.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2F20centaurifux%2Fefind","html_url":"https://awesome.ecosyste.ms/projects/github.com%2F20centaurifux%2Fefind","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2F20centaurifux%2Fefind/lists"}