{"id":16014946,"url":"https://github.com/thheller/timed-counter","last_synced_at":"2025-06-25T07:36:53.822Z","repository":{"id":140237910,"uuid":"1467924","full_name":"thheller/timed-counter","owner":"thheller","description":"simple Counters in redis","archived":false,"fork":false,"pushed_at":"2011-05-12T14:22:35.000Z","size":100,"stargazers_count":2,"open_issues_count":0,"forks_count":0,"subscribers_count":3,"default_branch":"master","last_synced_at":"2025-02-10T11:14:01.624Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":"","language":"Ruby","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/thheller.png","metadata":{"files":{"readme":"README","changelog":null,"contributing":null,"funding":null,"license":"MIT-LICENSE","code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2011-03-11T13:11:30.000Z","updated_at":"2021-07-06T14:19:51.000Z","dependencies_parsed_at":"2023-03-13T10:44:02.336Z","dependency_job_id":null,"html_url":"https://github.com/thheller/timed-counter","commit_stats":null,"previous_names":[],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thheller%2Ftimed-counter","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thheller%2Ftimed-counter/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thheller%2Ftimed-counter/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/thheller%2Ftimed-counter/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/thheller","download_url":"https://codeload.github.com/thheller/timed-counter/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":247280272,"owners_count":20912967,"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":[],"created_at":"2024-10-08T15:05:38.169Z","updated_at":"2025-04-05T03:13:31.356Z","avatar_url":"https://github.com/thheller.png","language":"Ruby","funding_links":[],"categories":[],"sub_categories":[],"readme":"Extremly simplistic time-based Counters in Redis\n\nredis = Redis.connect\n\ncounter = TimedCounter.new(redis)\n\ncounter.reset!(:test)\ncounter.incr(:test, 1)\n\n# get the last 5 minutes\n# returns [0, 0, 0, 0, 1]\np counter.minutes(:test, 5.minutes.ago, 5)\n\n# get the last 60 minutes\np counter.minutes(:test, 1.hour.ago, 60)\n\n# get the last 30 days\np counter.days(:test, 30.days.ago, 30)\n\n\nData is kept in Hashes in Redis (mostly to cut down on key sizes)\n\nper Key you'll get:\n\n- one total value\n- one years hash with a field per year eg. { 2010: value, 2011: value }\n- one hash per years with a field per month { 01: value, ...}\n- one hash per month with a field per day\n- one hash per day with a field per hour\n- one hash per hour with a field per minute\n\nKey Layout is: $tc:\u003ckey\u003e:\u003ctimestamp part\u003e\n\nKeys given may be arrays and will be joined with \"/\". eg. [:user, 1, :clicks] == \"user/1/clicks\"\n\nCurrently does not set any expires, probably should add some depending on the amount of counts kept. Might be sensible to delete the hour hashes after a few days. Performs all increments atomically instead of relying on rollups and other services. No Idea how well this scales, but should be able to increment a couple thousand counters per second.\n\nRedis Monitor Log:\n\n1299922276.799784 \"multi\"\n1299922276.800636 \"incrby\" \"$tc:test:1:total\" \"1\"\n1299922276.800728 \"hincrby\" \"$tc:test:1:years\" \"2011\" \"1\"\n1299922276.800762 \"hincrby\" \"$tc:test:1:2011\" \"03\" \"1\"\n1299922276.800789 \"hincrby\" \"$tc:test:1:201103\" \"12\" \"1\"\n1299922276.800817 \"hincrby\" \"$tc:test:1:20110312\" \"10\" \"1\"\n1299922276.800837 \"hincrby\" \"$tc:test:1:2011031210\" \"31\" \"1\"\n1299922276.800899 \"exec\"\n\nA hopefully accurate set of all counters keys is kept in \"$tc_list\" (\"SMEMBERS $tc_list\").\n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fthheller%2Ftimed-counter","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Fthheller%2Ftimed-counter","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Fthheller%2Ftimed-counter/lists"}