canine-docs/assets/js/8a56e0ba.64aa9613.js
github-actions[bot] 43c85a0552 deploy: 285111f4e0
2023-08-14 18:01:09 +00:00

1 line
18 KiB
JavaScript

"use strict";(self.webpackChunkcanine_docs=self.webpackChunkcanine_docs||[]).push([[8957],{3905:(e,t,r)=>{r.d(t,{Zo:()=>d,kt:()=>h});var o=r(7294);function i(e,t,r){return t in e?Object.defineProperty(e,t,{value:r,enumerable:!0,configurable:!0,writable:!0}):e[t]=r,e}function n(e,t){var r=Object.keys(e);if(Object.getOwnPropertySymbols){var o=Object.getOwnPropertySymbols(e);t&&(o=o.filter((function(t){return Object.getOwnPropertyDescriptor(e,t).enumerable}))),r.push.apply(r,o)}return r}function s(e){for(var t=1;t<arguments.length;t++){var r=null!=arguments[t]?arguments[t]:{};t%2?n(Object(r),!0).forEach((function(t){i(e,t,r[t])})):Object.getOwnPropertyDescriptors?Object.defineProperties(e,Object.getOwnPropertyDescriptors(r)):n(Object(r)).forEach((function(t){Object.defineProperty(e,t,Object.getOwnPropertyDescriptor(r,t))}))}return e}function a(e,t){if(null==e)return{};var r,o,i=function(e,t){if(null==e)return{};var r,o,i={},n=Object.keys(e);for(o=0;o<n.length;o++)r=n[o],t.indexOf(r)>=0||(i[r]=e[r]);return i}(e,t);if(Object.getOwnPropertySymbols){var n=Object.getOwnPropertySymbols(e);for(o=0;o<n.length;o++)r=n[o],t.indexOf(r)>=0||Object.prototype.propertyIsEnumerable.call(e,r)&&(i[r]=e[r])}return i}var l=o.createContext({}),c=function(e){var t=o.useContext(l),r=t;return e&&(r="function"==typeof e?e(t):s(s({},t),e)),r},d=function(e){var t=c(e.components);return o.createElement(l.Provider,{value:t},e.children)},u="mdxType",p={inlineCode:"code",wrapper:function(e){var t=e.children;return o.createElement(o.Fragment,{},t)}},f=o.forwardRef((function(e,t){var r=e.components,i=e.mdxType,n=e.originalType,l=e.parentName,d=a(e,["components","mdxType","originalType","parentName"]),u=c(r),f=i,h=u["".concat(l,".").concat(f)]||u[f]||p[f]||n;return r?o.createElement(h,s(s({ref:t},d),{},{components:r})):o.createElement(h,s({ref:t},d))}));function h(e,t){var r=arguments,i=t&&t.mdxType;if("string"==typeof e||i){var n=r.length,s=new Array(n);s[0]=f;var a={};for(var l in t)hasOwnProperty.call(t,l)&&(a[l]=t[l]);a.originalType=e,a[u]="string"==typeof e?e:i,s[1]=a;for(var c=2;c<n;c++)s[c]=r[c];return o.createElement.apply(null,s)}return o.createElement.apply(null,r)}f.displayName="MDXCreateElement"},7109:(e,t,r)=>{r.r(t),r.d(t,{assets:()=>l,contentTitle:()=>s,default:()=>p,frontMatter:()=>n,metadata:()=>a,toc:()=>c});var o=r(7462),i=(r(7294),r(3905));const n={sidebar_position:8},s="Filetree Module",a={unversionedId:"protocol/modules/filetree",id:"protocol/modules/filetree",title:"Filetree Module",description:"Overview",source:"@site/docs/protocol/modules/filetree.md",sourceDirName:"protocol/modules",slug:"/protocol/modules/filetree",permalink:"/docs/protocol/modules/filetree",draft:!1,editUrl:"https://github.com/JackalLabs/canine-docs/blob/master/docs/protocol/modules/filetree.md",tags:[],version:"current",sidebarPosition:8,frontMatter:{sidebar_position:8},sidebar:"tutorialSidebar",previous:{title:"dsig Module",permalink:"/docs/protocol/modules/dsig"},next:{title:"Jackal Proof-of-Persistence Documentation",permalink:"/docs/protocol/p-o-p"}},l={},c=[{value:"Overview",id:"overview",level:2},{value:"Folder Abstraction",id:"folder-abstraction",level:2},{value:"File Entry Structure",id:"file-entry-structure",level:2},{value:"Encrypted Viewing Access",id:"encrypted-viewing-access",level:2}],d={toc:c},u="wrapper";function p(e){let{components:t,...n}=e;return(0,i.kt)(u,(0,o.Z)({},d,n,{components:t,mdxType:"MDXLayout"}),(0,i.kt)("h1",{id:"filetree-module"},"Filetree Module"),(0,i.kt)("h2",{id:"overview"},"Overview"),(0,i.kt)("p",null,"The Jackal Filetree module is responsible for organizing and managing user files in a secure and user-friendly way. When\na user uploads a file using the Storage module, the file is only accessible from the File ID (FID), which can be\nchallenging to remember for every file uploaded to Jackal. Additionally, every single upload would be required to be\npublic, or the user would need to keep track of every symmetric key used to encrypt the files and manually map them to\nthe FIDs. To address this issue, the File Tree module implements a tree structure to store each file as an entry in the\ntree. Organizing this structure is also trivial as we can assign children to pseudo files that we call folders. Finally,\nto keep track of encryption keys, the protocol maps every file to its respective key, emphasizing the security and\nprivacy posture that the File Tree module enables."),(0,i.kt)("p",null,(0,i.kt)("img",{alt:"Protocol Overview",src:r(96).Z,width:"542",height:"842"})),(0,i.kt)("h2",{id:"folder-abstraction"},"Folder Abstraction"),(0,i.kt)("p",null,"These, of course, are all abstractions of what's actually under the hood. The File Tree module doesn't actually handle\nany of the folder logic; the system believes it is storing files that act as metadata stores, which then update to\nreflect changes in folders. This gives the user experience the feeling that folders and files are separate entities in\nthe tree, but in reality, they are identical."),(0,i.kt)("h2",{id:"file-entry-structure"},"File Entry Structure"),(0,i.kt)("p",null,"Storing file entries on-chain is a challenge since the chain itself is public. This requires the use of client-side\nencryption before uploading data to the chain itself. The main component of a file is location (Address), allowing users\nto query the rest of the data from the file. You can think of the location as a key in a traditional key-value store or\na path in bucket-based storage. The address is hashed using SHA256 to ensure it is impossible to retrieve the plain-text\nrepresentation of the file name while still being able to query the file using its given name."),(0,i.kt)("p",null,(0,i.kt)("img",{alt:"Protocol Overview",src:r(4965).Z,width:"271",height:"220"})),(0,i.kt)("p",null,"The second most important data point in a file is the content of the file. This field is extremely versatile as it can\nstore any string. Traditionally this is used to store a JSON list of FIDs to point to a file on the Storage Module;\nhowever, the protocol can also theoretically use it to store short bits of text like encrypted passwords for a private\npassword manager. The owner tag is a hashed version of the owner, hiding what address owns each file. This field can be\nchanged to reflect the transferral of ownership. When making changes to the file such as deletion, movement, or\nadding/removing viewers/editors, the owner field is consulted to determine permissions. The same applies to edit access;\neditors can update the contents but nothing else."),(0,i.kt)("h2",{id:"encrypted-viewing-access"},"Encrypted Viewing Access"),(0,i.kt)("p",null,"For users to view files, they need access to the symmetric keys used to encrypt the files. To do this, the protocol has\na map of hashed addresses with each user's respective version of the symmetric key encrypted with that address's\ncorresponding public key. The protocol can then store that map in the file entry to act as an encryption key discovery\nlayer. The addresses in this viewing list are only able to access files and decrypt the data in their client; they have\nno privileges over the modification of the file entry in any way. This approach ensures that the File Tree module\nmaintains a strong security and privacy posture for user data."))}p.isMDXComponent=!0},96:(e,t,r)=>{r.d(t,{Z:()=>o});const o=r.p+"assets/images/filetree1-e947ab740b90156234b2fadb69a00533.png"},4965:(e,t,r)=>{r.d(t,{Z:()=>o});const o="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAAQ8AAADcCAYAAABu8iQLAAAenUlEQVR4Xu2dCbAcVRWGQVBxVzQaFwRBEERLUYFIkF0IiwbZFDcWSYDSgCABFQslyqaArHHDrVzADRcEERQsFClQBKOguCEoS9CgICK4tfVd607d15nbc1+/mfzv9fu/qqm86Znp02den7/vvf1y/pUqY4xpwUr1DcYYU4LFwxjTCouHMaYVFg9jTCssHsaYVlg8jDGtsHgYY1ph8TDGtMLiYYxphcXDGNMKi4cxphUWD2NMKywexphWWDyMMa2weBhjWmHxMMa0wuJhjGmFxcMY0wqLhzGmFRYPY0wrLB7GmFZYPIwxrbB4GGNaYfEwxrTC4mGMaYXFwxjTCouHMaYVFg9jTCssHsaYVsjEY6uttqpWWmklP/zwYwIP6kiFTDxI3BgzMZR1JIusTNqYrqCsI1lkZdLGdAVlHckiK5M2piso60gWWZm0MV1BWUeyyMqkjekKyjqSRVYmbUxXUNaRLLIyaWO6grKOZJGVSZuqmj17dvWQhzykWmWVVcY87rzzzuoDH/hA9aY3vSm873GPe1z1hz/8ofZpM1lQ1pEssjJp83/x+MxnPlPfHPj73/9e3XPPPeFni8fkRllHssjKpE2zeORGHt/85jer5z//+dVznvOcascdd6xuv/329GNGgLKOZJGVSZvxi8cdd9xRPf7xj69+9rOfhe0nn3xy9apXvSr9mBGgrCNZZGXS5v/igTA85SlP6T3WXnvt8Fo/8fj0pz9dzZkzp/f5v/3tb9Wqq65a/fvf/+5tMyseZR3JIiuTNv8Xj7POOiuMKOJj6dKl4bV+4sG2Rz3qUdWaa67ZezAS4XNGh7KOZJGVSZvxT1t479y5c2vvNGqUdSSLrEzajF88uIU7Y8aM6le/+lXYfs0111QLFixIP2YEKOtIFlmZtBm/eEC827LOOutUL3zhC6vvf//76ceMAGUdySIrkzamKyjrSBZZmbQxXUFZR7LIyqSN6QrKOpJFViZtTFdQ1pEssjJpY7qCso5kkZVJG9MVlHUki6xM2piuoKwjWWRl0sZ0BWUdySKvtdZaIXE//PCj/YM6UiETDxI3xkwMZR3JIiuTNqYrKOtIFlmZtDFdQVlHssjKpI3pCso6kkVWJm1MV1DWkSyyMmljuoKyjmSRlUkb0xWUdSSLrEzamK6grCNZ5GElvWzZstAeb968efWXxvDBD36w1x2rzmQ1Nrr00kuzx5V2+zLTl2HVURtkkUuS/spXvlLftBxnnnlmtWjRomAb8I9//KP+co/xisdksBR45StfWV111VX1zeHYUlc3M30pqaNRIYtckjS9Mgex8cYbV7/97W+r+fPnV+edd15vO0Ky9957V8985jNDv06a9UbxuPjii6tnP/vZwfkM4cFCAPG49tprqxe84AXV6173umqrrbYK7825pN18883Vy172srCfZz3rWdXxxx/fuP0Xv/hF8ILtB6MI3o8AbrbZZiGfE088sXr4wx8etiGip5xySrXvvvuG43vnO985ZuTB8X/4wx+uXv7yl4fv7Ljjjuvt+4QTTqjWWGON6sUvfnH1kY98JFgmmO5QUkejQha5JOlB4nHDDTcEYYArrrii2mmnnXqvLV68uNp8882rf/3rX9Vf//rXaoMNNgjFxlX7aU97WhCQ+D4MnxGPJUuWBG+SKEJNLmlvfvObq/e+973hZ/a/++67h39z2zFJ+vrXvx62p/zpT3+qnvCEJ1T33ntveP7JT36yOvvss8PPG264YW/kccYZZ4TpGcICqXg88YlPDIICf/zjH6uHPexhYWRy4403VquvvnrI48EHHwzfz6Dv1EwtSupoVMgi55L+xCc+EaYRPCjq+PNHP/rR+lurhQsXVh/60IfCz//973/D1RuLAHj1q19dnXrqqb33vv3tbw/FxgiA/UUYoXAsiAci8YhHPKL6z3/+E15rckl73/veV2255ZbV1Vdf3Xs/5LbnuP/++4NAkcef//znMa+l4sH0bIcddui9VhePn/zkJ73XEKPf/e53YTSSWkKee+65Fo+OkaujFYEscknSTSd6HEE89rGP7QkMw3yG98AQnqt45P3vf38otiuvvHK5ofsjH/nInniwz0iTSxojGqYETGmwaoxCldveBIW/5557hn1vt912ofChLh6vfe1re5+pi8evf/3r3mvxOdOXdJ2H3Ju+UzP1KKmjUSGLXJJ004l+0UUXjbkSA0XImgDstddeYZE08ra3vS0UEkP5dOTBaCIdeTz96U/vvVbqkoYREp9jzaRke45//vOf1dFHH1294hWvCM/r4sFaTKREPLCT3GOPPXrbmY41fadm6lFSR6NCFrkk6aYTHXGIU5YURgc//elPg3Cw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"}}]);