{"id":28523735,"url":"https://github.com/alex-werner/khal","last_synced_at":"2025-09-14T23:58:33.490Z","repository":{"id":75184498,"uuid":"71178657","full_name":"Alex-Werner/khal","owner":"Alex-Werner","description":"Utils for node project","archived":false,"fork":false,"pushed_at":"2017-04-03T17:12:36.000Z","size":45,"stargazers_count":5,"open_issues_count":1,"forks_count":1,"subscribers_count":1,"default_branch":"master","last_synced_at":"2025-08-17T13:10:04.547Z","etag":null,"topics":["clone","date","file","geolocation","helpers","levenshtein-distance","math","misc","nodejs","regex","sort","string-distance","utils"],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","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/Alex-Werner.png","metadata":{"files":{"readme":"README.md","changelog":"CHANGELOG.md","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}},"created_at":"2016-10-17T20:32:04.000Z","updated_at":"2021-10-27T01:20:40.000Z","dependencies_parsed_at":"2023-12-13T23:00:39.641Z","dependency_job_id":"9b83832b-6e11-463e-97a5-a0a421cca673","html_url":"https://github.com/Alex-Werner/khal","commit_stats":{"total_commits":35,"total_committers":4,"mean_commits":8.75,"dds":0.4571428571428572,"last_synced_commit":"8cefc0608d8d544d2c3c10271c22406d2aa6a977"},"previous_names":[],"tags_count":4,"template":false,"template_full_name":null,"purl":"pkg:github/Alex-Werner/khal","repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Alex-Werner%2Fkhal","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Alex-Werner%2Fkhal/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Alex-Werner%2Fkhal/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Alex-Werner%2Fkhal/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/Alex-Werner","download_url":"https://codeload.github.com/Alex-Werner/khal/tar.gz/refs/heads/master","sbom_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/Alex-Werner%2Fkhal/sbom","scorecard":{"id":10767,"data":{"date":"2025-08-11","repo":{"name":"github.com/Alex-Werner/khal","commit":"8cefc0608d8d544d2c3c10271c22406d2aa6a977"},"scorecard":{"version":"v5.2.1-40-gf6ed084d","commit":"f6ed084d17c9236477efd66e5b258b9d4cc7b389"},"score":3,"checks":[{"name":"Maintained","score":0,"reason":"0 commit(s) and 0 issue activity found in the last 90 days -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project is \"actively maintained\".","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#maintained"}},{"name":"Code-Review","score":0,"reason":"Found 0/30 approved changesets -- score normalized to 0","details":null,"documentation":{"short":"Determines if the project requires human code review before pull requests (aka merge requests) are merged.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#code-review"}},{"name":"Packaging","score":-1,"reason":"packaging workflow not detected","details":["Warn: no GitHub/GitLab publishing workflow detected."],"documentation":{"short":"Determines if the project is published as a package that others can easily download, install, easily update, and uninstall.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#packaging"}},{"name":"SAST","score":0,"reason":"no SAST tool detected","details":["Warn: no pull requests merged into dev branch"],"documentation":{"short":"Determines if the project uses static code analysis.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#sast"}},{"name":"Dangerous-Workflow","score":-1,"reason":"no workflows found","details":null,"documentation":{"short":"Determines if the project's GitHub Action workflows avoid dangerous patterns.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#dangerous-workflow"}},{"name":"Token-Permissions","score":-1,"reason":"No tokens found","details":null,"documentation":{"short":"Determines if the project's workflows follow the principle of least privilege.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#token-permissions"}},{"name":"Binary-Artifacts","score":10,"reason":"no binaries found in the repo","details":null,"documentation":{"short":"Determines if the project has generated executable (binary) artifacts in the source repository.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#binary-artifacts"}},{"name":"Pinned-Dependencies","score":-1,"reason":"no dependencies found","details":null,"documentation":{"short":"Determines if the project has declared and pinned the dependencies of its build process.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#pinned-dependencies"}},{"name":"CII-Best-Practices","score":0,"reason":"no effort to earn an OpenSSF best practices badge detected","details":null,"documentation":{"short":"Determines if the project has an OpenSSF (formerly CII) Best Practices Badge.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#cii-best-practices"}},{"name":"Security-Policy","score":0,"reason":"security policy file not detected","details":["Warn: no security policy file detected","Warn: no security file to analyze","Warn: no security file to analyze","Warn: no security file to analyze"],"documentation":{"short":"Determines if the project has published a security policy.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#security-policy"}},{"name":"Vulnerabilities","score":10,"reason":"0 existing vulnerabilities detected","details":null,"documentation":{"short":"Determines if the project has open, known unfixed vulnerabilities.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#vulnerabilities"}},{"name":"Fuzzing","score":0,"reason":"project is not fuzzed","details":["Warn: no fuzzer integrations found"],"documentation":{"short":"Determines if the project uses fuzzing.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#fuzzing"}},{"name":"License","score":10,"reason":"license file detected","details":["Info: project has a license file: LICENSE:0","Info: FSF or OSI recognized license: MIT License: LICENSE:0"],"documentation":{"short":"Determines if the project has defined a license.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#license"}},{"name":"Signed-Releases","score":-1,"reason":"no releases found","details":null,"documentation":{"short":"Determines if the project cryptographically signs release artifacts.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#signed-releases"}},{"name":"Branch-Protection","score":0,"reason":"branch protection not enabled on development/release branches","details":["Warn: branch protection not enabled for branch 'master'"],"documentation":{"short":"Determines if the default and release branches are protected with GitHub's branch protection settings.","url":"https://github.com/ossf/scorecard/blob/f6ed084d17c9236477efd66e5b258b9d4cc7b389/docs/checks.md#branch-protection"}}]},"last_synced_at":"2025-08-14T14:29:31.501Z","repository_id":75184498,"created_at":"2025-08-14T14:29:31.501Z","updated_at":"2025-08-14T14:29:31.501Z"},"host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":275185376,"owners_count":25419919,"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-09-14T02:00:10.474Z","response_time":75,"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":["clone","date","file","geolocation","helpers","levenshtein-distance","math","misc","nodejs","regex","sort","string-distance","utils"],"created_at":"2025-06-09T10:09:35.833Z","updated_at":"2025-09-14T23:58:33.482Z","avatar_url":"https://github.com/Alex-Werner.png","language":"JavaScript","funding_links":[],"categories":[],"sub_categories":[],"readme":"# Khal\n\nUtils for node project   \n\n#### Disclaimer   \n\nThere is a lot of other npm that do what I've done but in a better/more fashion/more optimized way. But well, I know what is inside this,\nand this is the one I used a lot in my project. So don't blame for all the duplicates bytes I've done here.   \nI might optimize theses function in the future, just for the lolz and the learning.\n\nMore info about what has changed in the last version : [Changelog](CHANGELOG.md)  \n\n# API\n\n- `cl(args)` - Works like console.log, but it return the args passed. If no arg passed, it just return the timestamp. If only one arg is passed, it return the arg, if many it return array\n- `ce(args)` - Same as above for console.error\n- `clone(obj)` - Make a clone of an object (useful is you don't want to keep ref)\n- `intersect(arr, arr)` - Return an array being the intersect of arrays given\n- `union(arr,arr)` - Return an array being the union of arrays given\n- `is` - Test a given argument being of type/state expected\n    - `arr`\n    - `int`\n    - `number`\n    - `float`\n    - `string`\n    - `bool`\n    - `obj`\n    - `fn`\n    - `def`\n    - `undef`\n    - `promise`\n    - `obs`\n    - `event`\n    - `stringified`\n    - `JSON`\n- `sort` - Handle sorting\n    - `by` (el, param) given an object el, will sort by param defined\n\nExemple :\n```\nlet obj = [{name:\"alex\",age:15},{name:\"jean\",age:10},{name:\"brice\",age:10},{name:\"charles\",age:50},{name:\"franck\",age:1}];\nsort.by(obj,{age:1}); //Will sort asc by age similar to sort.by(obj,{age:'asc'});\nsort.by(obj,{age:-1}); //Will sort desc by age similar to sort.by(obj,{age:'desc'});\n\nsort.by(obj,{name:1,age:1}); //Will first sort asc by name then by age (so brice will be before jean having same age)\n```\n\n- `file` - Handle file\n    - `create(filename, [cb])` - Create an empty file (sync if not cb passed, async in the other case)\n    - `delete(filename, [cb])` - Delete a file (sync if not cb passed, async in the other case)\n    - `append(filename, data, [cb])` - Append data in file (sync if not cb passed, async in the other case)\n    - `exist(filename, [cb])` - Check if a file exist  (sync if not cb passed, async in the other case)\n    - `sizeof(filename, [cb])` - Get bytes size of a file (sync if not cb passed, async in the other case)\n- `geo` - Handle geoCordinate\n    - `create(lat, lon)` - returns a GeoCordinate object\n    - `geocordinateStringToGeoCoordinateObject(str)` - transform a str \"43.597446,1.454469\" to a geoObject\n    - `calculateDistance(geoCordinate, geoCordinate, [unit{str}, [precision {int}]])` - get distance between two geoObject, can be in `km`,`m` or `miles`,\n    - `convert(float)`\n        - `toMiles()` - convert to Miles a value in meters\n        - `toMeters()` - convert to Meters a value in miles\n- `string` - Handle string\n    - `pad` - Handle Padding\n        - `left(string, length, [replacementString])` - Transform an input and adding in left the replacement value. Returns a string.\n        - `right(string, length, [replacementString])` - Transform an input and adding in right the replacement value. Returns a string.\n- `math` - Handle math\n    - `radianToDegree(rad)`\n    - `degreeToRadian(deg)`\n    - `randomBetweenMinAndMax(min,max,[precision])`\n    - `levenshtein(stringA, stringB)` - return an array as of levenshtein (string distance)\n    - `stringDistance(stringA, stringB)` - return an int, value of the distance between two strings\n    - `highest(numbersList)` - return the highest number from a list of numbers\n    - `lowest(numbersList)` - return the lowest number from a list of numbers\n    - `median(numbersList)` - return the median number from a list of numbers\n    - `mean(numbersList)` - return the mean number from a list of numbers\n    - `average(numbersList)` - return the average number from a list of numbers\n- `misc` - Handle stuff\n    - `formatByteSize(bytes,[isSIForm])` - Make bytes readable using IEEC (MB) or SI (MiB) form\n    - `sizeOfObject(obj)` - Get bytes size from obj (number, object or string)\n    - `sizeOfObjectReadable(obj,[isSIForm])` - Make bytes readable using IEEC (MB) or SI (MiB) form from obj\n    - `merge(obj,[obj[...]])` - merge object with priority from left to right (left is left untouched), see it like an extends of left.\n- `os` - Handle OS stuff\n    - `getServerIp([_family])` - Get server ip by his familly (IPv4 by default, IPv6 should be passed as arg)   \n       =\u003e `khal.os.getServerIP(\"IPv6\")` for IPv6  \n       =\u003e `khal.os.getServerIP()` or `khal.os.getServerIP(\"IPv4\")` for IPv4  \n- `regex`\n    - `regTest(reg, val)` - Handy shortcut for regex testing\n    - `isUUIDV4(uuid)` - Test a valid UUID V4\n    - `isUsername(username)` - Test a valid username\n    - `isBirthdate(birthday)` - Test a valid birthdate\n    - `isGender(gender)` - Test a valid gender\n    - `isPassword(password)` - Test a valid password\n    - `isEmail(email)` - Test a valid email\n    - `isUnicodeEmail(email)` - Test a valid unicode email\n- `date`\n    - `time`\n    - `date`\n    - `datetime`\n    - `UTCEpochMS`\n    - `UTCEpoch`\n    - `localEpochMS`\n    - `localEpoch`\n    - `calculateAge(dateString, [date])` - Given a date String (YYYY-MM-DD) return the year diff between today or the date given as second arg.\n    - `YYYYMMDDhhmmss([params]]` Return formatted date in specified form with specified separator.\n        Where params can be :\n        - separatorDate - Default \"-\", - Allow to set a separator between years, months, and date.\n        - separatorTime - Default \":\" - Allow to set a separator between Hours, minutes and seconds.\n        - separatorBetween - Default \" \" - Will allow to set a separateur between the Time block and the Date block.\n        - d - Default is Now Date. - Allow to use a specific Date object to format from.\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Falex-werner%2Fkhal","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Falex-werner%2Fkhal","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Falex-werner%2Fkhal/lists"}