{"id":13990012,"url":"https://github.com/rbren/gitback","last_synced_at":"2025-03-27T06:31:14.613Z","repository":{"id":143879923,"uuid":"41437690","full_name":"rbren/gitback","owner":"rbren","description":null,"archived":false,"fork":false,"pushed_at":"2015-10-19T21:28:55.000Z","size":299,"stargazers_count":13,"open_issues_count":7,"forks_count":0,"subscribers_count":2,"default_branch":"master","last_synced_at":"2025-03-23T07:51:13.776Z","etag":null,"topics":[],"latest_commit_sha":null,"homepage":null,"language":"JavaScript","has_issues":true,"has_wiki":null,"has_pages":null,"mirror_url":null,"source_name":null,"license":null,"status":null,"scm":"git","pull_requests_enabled":true,"icon_url":"https://github.com/rbren.png","metadata":{"files":{"readme":"README.md","changelog":null,"contributing":null,"funding":null,"license":null,"code_of_conduct":null,"threat_model":null,"audit":null,"citation":null,"codeowners":null,"security":null,"support":null}},"created_at":"2015-08-26T16:48:06.000Z","updated_at":"2020-07-10T15:42:28.000Z","dependencies_parsed_at":"2023-03-21T08:55:51.829Z","dependency_job_id":null,"html_url":"https://github.com/rbren/gitback","commit_stats":null,"previous_names":["bobby-brennan/gitback"],"tags_count":0,"template":false,"template_full_name":null,"repository_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rbren%2Fgitback","tags_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rbren%2Fgitback/tags","releases_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rbren%2Fgitback/releases","manifests_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/repositories/rbren%2Fgitback/manifests","owner_url":"https://repos.ecosyste.ms/api/v1/hosts/GitHub/owners/rbren","download_url":"https://codeload.github.com/rbren/gitback/tar.gz/refs/heads/master","host":{"name":"GitHub","url":"https://github.com","kind":"github","repositories_count":245797453,"owners_count":20673857,"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-08-09T13:02:16.587Z","updated_at":"2025-03-27T06:31:13.804Z","avatar_url":"https://github.com/rbren.png","language":"JavaScript","funding_links":[],"categories":["JavaScript"],"sub_categories":[],"readme":"# GitBack\n\n[![Build Status](https://travis-ci.org/bobby-brennan/gitback.svg?branch=master)](https://travis-ci.org/bobby-brennan/gitback)\n[![npm version](https://badge.fury.io/js/gitback.svg)](http://badge.fury.io/js/gitback)\n\n## Installation\n\n```bash\nnpm install --save gitback\n```\n\n## About\n\nGitBack is a (currently experimental) attempt to use Git as a datastore for NodeJS. \nData is stored as files (generally JSON documents) inside a Git repository, and is exposed\nvia a RESTful API. This may seem insane, and it many ways it is. But there are a number of positives.\n\nWe get, for free:\n* A **history of every revision** to the datastore\n* Easy **versioning** via branches\n* The ability to **roll back** any single change, or **revert** to any point in time\n* The ability to store **aribitrary data** without dealing with encoding/decoding. Images are just images, .zips are just .zips\n* A **beautiful GUI** for viewing and editing the datastore, thanks to GitHub\n\nThat last point is particularly important if you want to collaborate with less-technical folks.\nWhat would normally involve database queries can now be done in a point-and-click interface.\n\n### Objections\n* Each write will cause two separate disk writes (one locally, one in the remote)\n* Concurrent writes to the same document will frequently fail\n* We need to make frequent calls to ```git pull``` to keep the local repository in line with the remote\n* These issues compound when using multiple replicas (e.g. for loadbalancing)\n\nSo when should you use GitBack, and when should you use a more traditional datastore?\n\nUse GitBack if:\n* You want a quick and dirty solution for storing data\n* You anticipate making relatively few writes to the datastore\n* You're dealing with a relatively small amount of data (as a rule of thumb, less than 100MB)\n* You want non-technical people to be able to edit the datastore\n\nDON'T use GitBack if:\n* You anticipate making frequent writes to the datastore\n* You anticipate many concurrent writes to the same documents\n* You need to perform complex operations/queries on your data\n* You need to store gigabytes of data\n* You can't deal with slow writes (\u003e 1s)\n \nGitBack is great for small projects, or for getting an idea off the ground quickly.\nIt doesn't scale well at all, but we're working on ways to export to and sync with a\nMongoDB instance.\n\nAs an example, I'm maintaining my blog using GitBack. You can\n[see the repository here](https://github.com/bobby-brennan/gitback-blog)\n\n## Usage\n\n### Quickstart\n* [Create a new repository](https://github.com/new)\n* Add a collection to that repository:\n**./myCollection.js**\n```js\n{\n  access: {\n    get: 'all',\n    post: 'all',\n  }\n}\n```\n* Create a GitBack server with Express, passing in the URL of the repository you created.\n```bash\n$ npm install express gitback\n```\n\n**./server.js**\n```js\nvar App = require('express')();\nvar GitBack = require('gitback');\nvar DB = new GitBack({\n  directory: __dirname + '/database',\n  remote: \"https://username:password@github.com/username/repository.git\",\n  refreshRate: 30000, // Check remote for changes every 30s\n});\nDB.initialize(function(err) {\n  App.use('/api', DB.router);\n});\nApp.listen(3000);\n```\n* Use it!\n```bash\n$ node server.js \u0026\n$ curl -X POST localhost:3000/api/myCollection -d '{\"id\": \"foo\", \"bar\": \"baz\"}' -H \"Content-Type: application/json\" \n{\"success\": true}\n$ curl localhost:3000/api/myCollection\n[{\"id\": \"foo\", \"bar\": \"baz\"}]\n```\n\nYou'll see the changes immediately reflected in the repository you created in step 1.\n\n### Authorization\n\nYou'll need to make sure your machine has read and write access to the repository.\nThere are a few strategies for this:\n\n#### Use your Username and Password\nThe best way to do this is to use an environment variable:\n```bash\nexport GITBACK_REMOTE_URL=\"https://username:password@github.com/username/repository.git\"\n```\n```js\nvar GitBack = require('gitback');\nvar DB = new GitBack({\n  directory: __dirname + '/database',\n  remote: process.env.GITBACK_REMOTE_URL,\n});\n```\n\n#### Store your Git credentials\nGit provies a way for you to permanently stash your credentials on the current machine\n\n[Instructions](http://git-scm.com/docs/git-credential-store)\n```js\nvar GitBack = require('gitback');\nvar DB = new GitBack({\n  directory: __dirname + '/database',\n  remote: 'https://github.com/username/repository.git',\n});\n```\n\n#### Use Deploy Keys\nProbably the most secure option. Deploy keys are specific to a particular\nrepository, so if they're compromised attackers won't have access to your whole account.\nBe sure to enable write access.\n\n[Instructions](https://developer.github.com/guides/managing-deploy-keys/#deploy-keys)\n```js\nvar GitBack = require('gitback');\nvar DB = new GitBack({\n  directory: __dirname + '/database',\n  remote: 'git@github.com:username/repository.git',\n});\n```\n\n## The Datastore\n\nFor each collection in the datastore, we'll have:\n* ```./{collection}.js``` - a file that describes the collection, e.g. it's schema and access control\n* ```./{collection}/``` - a directory containing all the items in the collection\n* ```./{collection}/{itemID}/``` - a directory containing the all the data for a particular item\n* ```./{collection}/{itemID}/_item.json``` - the JSON describing the details of the item.\n\nWe can also associate additional data with the item by adding files to its folder.\n\nHere's an example:\n\n```\n./\n  pets.js\n  pets/\n    Rover/\n      _item.json\n      photo.png\n    Spot/\n      _item.json\n      photo.png\n```\n\nLet's have a look at pets.js, which tells us about the collection:\n\n**./pets.js**\n```js\n{\n  id: \"name\",\n  schema: {\n    type: \"object\",\n    properties: {\n      name: {type: \"string\"},\n      age: {type: \"number\"},\n      type: {type: \"string\"},\n      owners: {type: \"array\", items: {type: \"string\"}},\n    }\n    additionalProperties: false,\n  },\n  attachments: {\n    photo: {\n      extension: 'png',\n      strategy: 'link',\n    }\n  },\n  access: {\n    get: \"all\",\n    post: \"all\",\n  },\n}\n```\n\nThere's a lot going on here. Let's take it field by field.\n* ```id```: This specifies the field to use as a unique id for this collection. Default is 'id'.\n* ```schema```: [JSON schema](http://json-schema.org/) for validating new items. You can leave this unspecified if you want to accept arbitrary JSON.\n* ```attachments```: Additional files that will be stored alongside _item.json.  ```strategy``` can be one of\n  * 'string' (default): GitBack will make this field a string with the contents of the file\n  * 'link': GitBack will make this field a link that retrieves the file\n* ```access```: GitBack will expose a RESTful API for manipulating your database. You can set access control for each HTTP verb to 'all' to grant world access, or to a function that validates the request (see 'Authentication' below). The verbs are:\n  * get: retrieves objects\n  * post: creates new objects\n  * put: overwrites an object\n  * patch: edits an object\n  * delete: deletes an object\n  \n## Contributing\nContributions, issues, and pull requests are welcome!\n\n  \n","project_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frbren%2Fgitback","html_url":"https://awesome.ecosyste.ms/projects/github.com%2Frbren%2Fgitback","lists_url":"https://awesome.ecosyste.ms/api/v1/projects/github.com%2Frbren%2Fgitback/lists"}