diff --git a/CHANGELOG.md b/CHANGELOG.md index bcb7e9230..fe07777de 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,28 +1,236 @@ # WIP -* fix opening links from temporary shared folders on iphone or other contexts that do not support shared workers -* add checkup test for disabling google FLoC -* update lodash devDependency +* Sheet export + * most exports broken by Chrome 92, mostly fixed + * we discovered that CSV export was not working in any major browser, though it's unclear why. We've disabled CSV export in the meantime + * updated translation to stop referring to Microsoft since we support OpenDocument formats + * some new browser-specific checkup tests to make it easier to detect future regressions in the APIs +* drive bug fixes + * guard against a few possible type errors + +# 4.9.0 + +## Goals and announcements + +We allocated most of this release cycle towards a schedule of one-on-one user interviews and some broad usage studies leveraging our new Form app. The remainder of our time was spent on some minor improvements. We'll continue at a slightly slower pace of implementation for the coming weeks while we complete our scheduled interviews and take some much-needed vacations. + +## Update notes + +It appears our promotion of the checkup page through our recent release notes and the inclusion of a link to it from the instance admin have been moderately successful. We've observed that more instance admins are noticing and fixing some common configuration issues. + +This release features some minor changes to one instance configuration test which incorrectly provided an exemption for the use of `http://localhost:3000` as an `httpUnsafeOrigin` value. This exemption was provided because this value is valid for local development. However, it suppressed errors when this configuration was used for production instances where it could cause a variety of problems. As usual, we recommend checking your instance's admin page after updating to confirm that you are passing the latest tests. Information about the checkup page is included in [our documentation](https://docs.cryptpad.fr/en/admin_guide/admin_panel.html#network). + +To update from 4.8.0 to 4.9.0: + +1. Stop your server +2. Get the latest code with git +3. Install the latest dependencies with `bower update` and `npm i` +4. Restart your server +5. Confirm that your instance is passing all the tests included on the `/checkup/` page + +## Features + +* We've added the ability to store URLs in user and team drives as requested in a private support ticket and [this issue](https://github.com/xwiki-labs/cryptpad/issues/732). Links can be shared directly with contacts. Unlike pads, links are not collaborative objects, so updating a link's name will not update the entry in another user's drive if you've already shared it with them. Links are integrated into our apps' _insert_ menu to facilitate quick insertion of links you've stored into your documents. We're interested in measuring how this functionality is used in practice so we can decide whether it's worth spending more time on it. We have added some telemetry to measure (in aggregate) how often its components are used. We anonymize IP addresses in the logs for CryptPad.fr, but as always, you can disable telemetry via your settings panel. +* Our rich text editor now supports indentation with the tab key, as per [issue #634](https://github.com/xwiki-labs/cryptpad/issues/634). +* Forms received another round of improvements to styles, workflows, and some basic survey functionality to yield more accurate results. + * Ordered lists are now shuffled for each survey participant so that their initial order has less effect on the final results. + * CSV export now uses one column for each option in polls, making them easier to read. + * Unregistered users can now add a name to their response. + * Form results are displayed automatically (when available) to those who have answered. + * Authors and auditors can now click on usernames in polls to jump directly to other answers from the same user. +* Users with very large drives might notice that their account loads slightly faster now, due to some minor optimizations in an integrity check that the client performs when loading accounts. + +## Bugs + +* We've added a guard against a type error that could be triggered when loading teams under certain rare conditions. +* Unregistered users' drives now show the "bread-crumb" UI for navigating between folders when viewing a shared folder in read-only mode. We've also suppressed the "Files" button for displaying the tree view which was non-functional for such users. +* A change in the format of support tickets caused tickets recently created by premium users to not be recognized as such. We've fixed the categorization in the admin panel's support ticket view. +* We've fixed a number of minor issues with forms: + * The maximum number of selectable choices for checkbox questions can no longer exceed the number of available choices. + * We guard against a type error that could occur when parsing dates. + * Forms imported from templates now have their initial title corrected. + * We've disabled the use of our indexedDB caching system for form results, since it was quietly dropping older responses when more than 100 responses had been submitted. We plan to re-enable caching for results once we've updated the eviction metric to better handle the response format. + +# 4.8.0 + +## Goals + +This release cycle we decided to give people a chance to try our forms app and provide feedback before we begin developing its second round of major features and improvements. In the meantime we planned to work mostly on the activities of our [NGI DAPSI](https://dapsi.ngi.eu/) project which concerns client-side file format conversions. Otherwise, we dedicated some of our independently funded time towards some internal code review and security best-practices as a follow-up to the recent quick-scan performed by [Radically Open Security](https://radicallyopensecurity.com/) that was funded by [NLnet](https://nlnet.nl) as a part of our now-closing _CryptPad for Communities_ project. + +## Update notes + +We are still accepting feedback concerning our Form application via [a form hosted on CryptPad.fr](https://cryptpad.fr/form/#/2/form/view/gYs4QS7DetInCXy0z2CQoUW6CwN6kaR2utGsftDzp58/). We will accept feedback here until July 12th, 2021, so if you'd like your opinions to be represented in the app's second round of development act quickly! + +Following our last release we sent out an email to the admins of each outdated instance that had included their addresses in the server's daily telemetry. This appears to have been successful, as more than half of the 700+ instances that provide this telemetry are now running **4.7.0**. Previously, only 15% of instances were running the latest version. It's worth noting that of those admins that are hosting the latest version, less than 10% have opted into future emails warning them of security issues. In case you missed it, this can be done on the admin panel's _Network_ tab. Unlike most companies, we consider excess data collection a liability rather than an asset. As such, administrator emails are no longer included in server telemetry unless the admin has consented to be contacted. + +The same HTTP request that communicates server telemetry will soon begin responding with the URL of our latest release notes if it is detected that the remote instance is running an older version. The admin panel's _Network_ tab for instances running 4.7.0 or later will begin prompting admins to view the release notes and update once 4.8.0 is available. + +The Network tab now includes a multiple choice form as well. If you have not disabled your instance's telemetry you can use this field to answer _why you run your instance_ (for a business, an academic institution, personal use, etc.). We intend to use this data to inform our development roadmap, though as always, the fastest way to get us to prioritize your needs is to contact us for a support contract (sales@cryptpad.fr). + +Server telemetry will also include an `installMethod` property. By default this is `"unspecified"`, but we are planning to work with packagers of alternate install methods to modify this property in their installation scripts. This will help us assess what proportion of instances are installed via the steps included in our installation guide vs other methods such as the various docker images. We hope that it will also allow us to determine the source of some common misconfigurations so we can propose some improvements to the root cause. + +Getting off the topic of telemetry: two types of data that were previously deleted outright (pin logs and login blocks) are now archived when the client sends a _remove_ command. This provides for the ability to restore old user credentials in cases where users claim that their new credentials do not work following a password change. Some discretion is required in such cases as a user might have intentionally invalidated their old credentials due to shoulder-surfing or the breach of another service's database where they'd reused credentials. Neither of these types of data are currently included in the scripts which evict old data as they are not likely to consume a significant amount of storage space. In any case, CryptPad's data is stored on the filesystem, so it's always possible to remove outdated files by removing them from `cryptpad/data/archive/*` or whatever path you've configured for your archives. + +This release introduces some minor changes to the provided NGINX configuration file to enable support for WebAssembly where it is required for client-side file format conversions. We've added some new tests on the /checkup/ page that determine whether these changes have been applied. This page can be found via a button on the admin panel. + +To update from 4.7.0 to 4.8.0: + +1. Apply the documented NGINX configuration +2. Stop your server +3. Get the latest code with git +4. Install the latest dependencies with `bower update` and `npm i` +5. Restart your server +6. Confirm that your instance is passing all the tests included on the `/checkup/` page + +## Features + +* Those who prefer using tools localized in Japanese can thank [@Suguru](https://mstdn.progressiv.dev/@suguru) for completing the Japanese translation of the platform's text! CryptPad is a fairly big platform with a lot of text to translate, so we really appreciate how much effort went into this. + * While we're on the topic, CryptPad's _Deutsch_ translation is kept up to date largely by a single member of the German Pirate Party (Piratenpartei Deutschland). This is a huge job and we appreciate your work too! + * Anyone else who wishes to give back to the project by doing the same can contribute translations on an ongoing basis through [our Weblate instance](https://weblate.cryptpad.fr/projects/cryptpad/app/). +* We've implemented a new app for file format conversions as a part of our _INTEROFFICE_ project. At this point this page is largely a test-case for the conversion engine that we hope to integrate more tightly into the rest of the platform. It allows users to load a variety of file formats into their browser and convert to any other format that has a defined conversion process from the original format. What's special about this is that files are converted entirely in your browser, unlike other platforms which do so in the cloud and expose their contents in the process. Currently we support conversion between the following formats in every browser that supports modern web standards (ie. not safari): + * XLSX and ODS + * DOCX and ODT and TXT + * PPTX and ODP +* In addition to the /convert/ page which supports office file formats, we also put some time into improving interoperability for our existing apps. We're introducing the ability to export rich text documents as Markdown (via the [turndown](https://github.com/mixmark-io/turndown) library), to import trello's JSON format into our Kanban app (with some loss of attributes because we don't support all the same features), and to export form summaries as CSV files. +* We've added another extension to our customized markdown renderer which replaces markdown images with a warning that CryptPad blocks remote content to prevent malicious users from tracking visitors to certain pages. Such images should already be blocked by our strict use of Content-Security-Policy headers, but this will provide a better indication why images are failing to load on instances that are correctly configured and a modest improvement to users' privacy on instances that aren't. +* Up until now it was possible to include style tags in markdown documents, which some of our more advanced users used in order to customize the appearance of their rendered documents. Unfortunately, these styles were not applied strictly to the markdown preview window, but to the page as a whole, making it possible to break the platform's interface (for that pad) through the use of overly broad and powerful style rules. As of this release style tags are now treated as special elements, such that their contents are compiled as [LESS](https://lesscss.org/) within a scope that is only applied to the preview pane. This was intended as a bug fix, but it's included here as a _feature_ because advanced users might see it as such and use it to do neat things. We have no funding for further work in this direction, however, and presently have no intent of providing documentation about this behaviour. +* The checkup page uses some slightly nicer methods of displaying values returned by tests when the expected value of `true` is not returned. Some tests have been revised to return the problematic value instead of `false` when the test fails, since there were some cases where it was not clear why the test was failing, such as when a header was present but duplicated. +* We've made some server requests related to _pinning files_ moderately faster by skipping an expensive calculation and omitting the value it returned. This value was meant to be used as a checksum to ensure that all of a user's documents were included in the list which should be associated with their account, however, clients used a separate command to fetch this checksum. The value provided in response to the other commands was never used by the client. +* We've implemented a system on the client for defining default templates for particular types of documents across an entire instance in addition to the use of documents in the _templates_ section of the users drive (or that of their teams). This is intended more as a generic system for us to reuse throughout the platform's source than an API for instance admins to use. If there is sufficient interest (and funding) from other admins we'll implement this as an instance configuration point. We now provide a _poll_ template to replicate the features of our old poll app which has been deprecated in favour of forms. +* We've included some more non-sensitive information about users' teams to the debugging data to which is automatically submitted along with support tickets, such as the id of the team's drive, roster, and how large the drive's contents are. +* The _Log out everywhere_ option that is displayed in the user admin menu in the top-right corner of the page for logged-in users now displays a confirmation before terminating all remote sessions. + +## Bug fixes + +* It was brought to our attention that the registration page was not trimming leading and trailing whitespace from usernames as intended. We've updated the page to do so, however, accounts created with such characters in their username field must enter their credentials exactly as they were at registration time in order to log in. We have no means of detecting such accounts on the server, as usernames are not visible to server admins. We'll consider this behaviour in the future if we introduce an option to change usernames as we do with passwords. +* We now double-check that login blocks (account credentials encrypted with a key derived from a username and password) can be accessed by the client when registering or changing passwords. It should be sufficient to rely on the server to report whether the encrypted credentials were stored successfully when uploading them, but in instances where these resources don't load due to a misbehaving browser extension it's better that we detect it at registration time rather than after the user creates content that will be difficult to access without assistance determining which extension or browser customization is to blame. +* We learned that the Javascript engine used on iOS has trouble parsing an alternative representation of data strings that every other platform seems to handle. This caused calendars to display incorrect data. Because Apple prevents third-party browsers from including their own JavaScript engines this means that users were affected by this Safari bug regardless of whether they used browsers branded as Safari, Firefox, Chrome, or otherwise. +* After some internal review we now guard against a variety of cases where user-crafted input could trigger a DOMException error and prevent a whole page worth of markdown content to fail to render. While there is no impact for users' privacy or security in this bug, a malicious user could exploit it to be annoying. +* Shortly after our last release a user reported being unable to access their account due to a typeError which we were able to [guard against](https://github.com/xwiki-labs/cryptpad/commit/abc9466abe71a76d1d31ef6a3c2c9bba4d2233e4). +* Images appearing in the 'lightbox' preview modal no longer appear stretched. +* Before applying actions that modify the team's membership we now confirm that server-enforced permissions match our local state. + +# 4.7.0 + +## Goals + +Our main goal for this release was to prepare a BETA version of our new forms app, however, it also includes a number of nice bug fixes and minor features. + +## Update notes + +As this release includes a new app you'll want to compare your current NGINX config against our example (`cryptpad/docs/example.nginx.conf`) and update yours to match the updated sections which rewrites URLs to include trailing slashes. We've also introduced a number of new variables to our color scheme which might conflict with customizations you've made to your stylesheets. As always, it's recommended that you test your customizations on a updated non-production instance before deploying. + +We've been steadily adding new tests to our recently developed checkup page each time we observe particular types of instance misconfigurations in the wild. Unfortunately, it seems the admins that have the most trouble with instance configuration are those that haven't read the numerous mentions of this page throughout the last few release notes. For that reason we've made it so the server prints a link to this page at launch time if it detects that some important value is left unconfigured. + +On the topic of instance configuration, admins that have enabled their instance's admin panel may notice that it contains a new "Network" tab. On this pane you may find a button that links to the instance's checkup page to make it even easier to identify configuration problems. You should also notice options for configuring a number of values, some of which could previously only be set by modifying the server's configuration file and restarting. + +* One checkbox allows you to opt out of the server telemetry which tells our server that your server exists. This is mostly so that we have a rough idea of how many admins are running CryptPad and what version they have installed. It was clearly documented in the config file, but now it's even easier to opt out if you don't want us to know you exist. In the interest of transparency, everything that is sent to our server as a part of this telemetry is also printed to your application server's logs, so you always check what information has been shared. +* Another setting opts in to listing your server in public directories. At present there is no public directory of CryptPad instances that are suitable for public use, but we plan to launch one in the coming months. For now this checkbox will serve to inform us how many instance admins are interested in offering their server to the public. This setting will have no effect if you've disabled telemetry as that is how your server informs ours of your preferences. We reserve the right to exclude instances from our listing for _any reason_. +* A third option allows admins to consent to be contacted by email. We aren't interested in spamming anyone with marketing email, rather, it's so that we can inform administrators of vulnerabilities in the software before they are publicly disclosed. Leave this unchecked if you prefer to be surprised by security flaws. +* The option to disable crowdfunding notices in the UI can be disabled via a simple checkbox. +* Starting with our next release (4.8.0) anyone running 4.7.0 should also notice that a button appears on this pane informing them that an update is available. We regularly fix security flaws and improve general safeguards against them, so if you aren't up to date you might be putting your users' data at risk. + +To update from 4.6.0 to 4.7.0: + +1. Apply the documented NGINX configuration +2. Stop your server +3. Get the latest code with git +4. Install the latest dependencies with `bower update` and `npm i` +5. Restart your server + +Please note that the new _Forms_ app depends on an update to our cryptography library. If you omit `bower update` from the upgrade sequence above, the app will not work. + +## Features + +* This release introduces our new _Forms_ app. This app allows users to create complex forms and to collect answers. Three roles are available with granular permissions: + + * Authors can collaboratively create surveys with different types of questions and generate links to share with participants. + * Participants can respond to forms and view responses if these are made public (this can be set by authors). + * Auditors can view responses, but cannot necessarily add their own answers unless they have the correct participant key. + + This new app addresses many of the shortcomings of our current _Polls_ and vastly expands the feature set. Polls are effectively one of the many question types now available in _Forms_. For this reason we are deprecating the _Polls_ app. It will remain available to view and respond to existing polls, but we discourage the creation of new polls and all future improvements will be focused on _Forms_. + +* In response to a GitHub issue we've added an option to the toolbar's _File_ menu to add the current pad to your drive regardless of whether it is already stored in one of your teams' drives. +* Likewise, we received some reports that some users found it frustrating that the home page automatically redirected them to their drive when they were logged in. We've disabled this behaviour by default but added an option in the settings page through which you may re-enable the old behaviour. This can be found at the top of the "CryptDrive" pane. +* Embedded markdown editors' toolbars (such as that in the kanban and form apps) now include an "embed file" option. +* We've revised some text on the checkup page to better explain what some headers do and how to correct them. +* Some error messages printed by the server under rare conditions now include a little more debugging information. +* We've improved some of the UI of the "report" page (which diagnoses possible reasons why your drive, shared folders, or teams might be failing to load now includes) so that users can now copy the output of the report directly to their clipboard instead of having to select that page's text and use their OS's copy to clipboard functionality. + +## Bug fixes + +* The home page now displays the appropriate text ("Features" or "Pricing") for the features page depending on whether the instance in question supports subscriptions. We had made some changes to this before but missed an instance where the text was displayed. +* The admin page will now display the "General" pane if for some reason the hash in its URL does not contain a supported value. +* We found that there were two cases where localForage (a library that manages an in-browser cache) could throw a DOMExceptionerror because we didn't supply a handler. This caused the calendar app's UI to incorrectly treat a newly created event as though it had not been saved. +* A user brought it to our attention that the share menu was returning incorrect URLs for password-protected files. This has now been fixed. +* The code that is responsible for preserving your cursor position when using the code editor collaboratively was capable of interfering with active scrolling when other users' edits were applied. This is now handled more gracefully. Another fix addresses an issue that prevented the markdown preview pane from being resized under certain conditions. +* Finally, as a part of a routine security scan funded by [NLnet](https://nlnet.nl/) and executed by [Radically Open Security](https://www.radicallyopensecurity.com/) it was discovered that an unsanitized _account name_ was displayed in the users own toolbar. As a consequence, users could trigger a cross-site scripting vulnerability on themself by entering `` for their username at registration time. On a correctly configured instance this was blocked everywhere except in the sheet editor due to its more lax Content-Security Policy. This unsanitized value was never displayed for remote accounts, so the impact is extremely limited. Even so, we recommend that you update. + +# 4.6.0 + +## Goals + +Our main goal for this release cycle was to get a strong start on our upcoming _Forms_ app. This is a big job which we didn't expect to finish in the course of a few weeks, so in the meantime we've taken the opportunity to address many minor issues, stabilize the codebase, and implement a number of new tests. + +## Update notes + +Over the years the example configuration file has grown to include a large number of parameters. We've seen that this can make it hard to pick out which configuration parameters are important for a newly installed or migrated instance. We're trying to address this by moving more configuration options to the admin panel. + +4.6.0 introduces the ability to generate credentials for your instance's support ticket mailbox and publish the corresponding public key with the push of a button. Previously it was necessary to run a script, copy its value, update the config file, restart the server, and enter the private component of the keypair into an input on the admin panel. The relevant button can be found in the admin panel's _Support_ tab. + +We've also introduced the ability to update your _adminEmail_ settings via a field on the _General_ tab of the admin panel. This value is used by the contact page so that your users can contact you (instead of us) in case they encounter any problems when using your instance. Both the `supportMailbox` and `adminEmail` values are distributed by the `/api/config` endpoint which is typically cached by clients. You probably need to use the _Flush cache_ button to ensure that everyone loads the latest value. This button can also found on the _General_ tab. + +One admin reported difficulty customizing their instance because they copy-pasted code from `cryptpad/www/common/application_config_internal.js` directly into `cryptpad/customize/application_config.js`. Unfortunately the internal variable name for the configuration object in the former did not match the value in the latter, so this led to a reference error. We've updated the variable name in the internal configuration file which provides the default options to match the customizable one, making it easier to copy-paste code examples without understanding what it's really doing. + +We also introduced a new configuration option in `application_config_internal.js` which prevents unregistered users from creating new pads. Add `AppConfig.disableAnonymousPadCreation = true;` to your `customize/application_config.js` to disable anonymous pad creation. If you read the adjacent comment above the default example you'll see that this barrier is only enforced on the client, so it will keep out honest users but won't stop malicious ones from messaging the server directly. + +This release also includes a number of new tests on the `/checkup/` page. Most notably it now checks for headers on certain assets which can only be checked from within the sandboxed iframe. These new tests automate the manual checks we were performing when admins reported that everything was working except for sheets, and go a little bit further to report which particular headers are incorrect. We also fixed some bugs that were checking headers on resources which could be cached, added a test for the recently added anti-FLoC header, fixed the styles on the page to respond to both light and dark mode, and made sure that websocket connections that were opened by tests were closed when they finished. + +Some of the tests we implemented checked the headers on resources that were particularly prone to misconfiguration because its headers were set by both NGINX and the NodeJS application server (see [#694](https://github.com/xwiki-labs/cryptpad/issues/694)). We tested in a variety of configurations and ultimately decided that the most resilient solution was to give up on using heuristics in the application server and just update the example NGINX config to use a patch proposed by another admin which fully overrides the settings of the application server. You can find this patch in the `/api/(config|broadcast)` section of the example config. + +Finally, we've made some minor changes to the provided `package-lock.json` file because `npm` reported some "Regular Expression Denial of Service" vulnerabilities. One of these was easy to fix, but another two were reported shortly thereafter. These "vulnerabilities" only affect some developer dependencies and will have no effect on regular usage of our software. The "risk" is essentially that malicious modifications to our source code can be tailored to make our style linting software run particularly slowly. This can only be triggered by integrating such malicious changes into your local repository and running `npm run lint:less`, so maybe don't do that. + +To update from 4.5.0 to 4.6.0: + +1. Apply the documented NGINX configuration +2. Stop your server +3. Get the latest code with git +4. Install the latest dependencies with `bower update` and `npm i` +5. Restart your server + +## Features + +This release includes very few new features aside from those already mentioned in the _Update notes_ section. One very minor improvement is that formatted code blocks in the code editor's markdown preview use the full width of their parent container instead of being indented. + +## Bug fixes + +* Once again we fixed a bug that only occurs on Safari because Apple refuses to implement APIs that make the web a viable competitor to their app store. This one was triggered by opening a shared folder from its link as an unregistered user, then trying to open a pad stored only in that folder and not elsewhere in your drive. Literally every other browser supports _SharedWorkers_, which allow tabs on the same domain to share a background process, reducing consumption of CPU, RAM, and electricity, as well as allowing the newly opened tab to read the document's credentials from the temporarily loaded shared folder. On Safari the new tab failed to load. We fixed it by checking whether the shared folder would be accessible from newly opened tabs, and choosing to use the document's "unsafe link" instead of its "safe link". +* We updated the "Features" page to be displayed as "Pricing" in the footer when some prospective clients reported that they couldn't find a mention of what they would get by creating a premium subscription. [#683](https://github.com/xwiki-labs/cryptpad/issues/683) had the opposite problem, that they didn't support payment and they wanted to only show features. Now the footer displays the appropriate string depending on your instance's configuration. +* We fixed some inconsistent UI in our recently introduced date picker. The time formats displayed in the text field and date picker interface should now match the localization settings provided to your browser by your OS. Previously it was possible for one of these elements to appear in 24 hour time while the other appeared in 12 hour time. +* Another time-related issue appeared in the calendar for users in Hawai'i, who reported that some events were displayed on the wrong day due to the incorrect initialization of a reference date. +* We've applied a minor optimization which should reduce the size of shared folders. +* Some functionality on the admin panel has been improved with some better error handling. +* Finally, one user reported that one of their PDFs was displaying only blank pages. After a short investigation we found that the problematic PDF was trying to run some scripts which were being blocked by our strict Content-Security-Policy headers. We've updated our PDF renderer to avoid compiling and running such scripts. As a result, such PDFs should not be prevented from rendering, though they may lack some dynamic functionality that you might be expecting. We'd welcome an example of such a PDF so we can assess if there is a safe way to load their embedded scripts and how much work would be required to do so. # 4.5.0 ## Goals -This release cycle we aimed to complete three major milestones: the official release of our calendar app, the ability for admins to close registration on their instance, and the deployment of the admin section of our [official documentation](https://docs.cryptpad.fr/en/admin_guide/index.html). We spent the remainder of our time addressing a growing backlog of issues on GitHub by fixing a number of weird bugs. +This release cycle we aimed to complete three major milestones: the official release of our calendar app, the ability for admins to close registration on their instance, and the deployment of the admin section of our [official documentation](https://docs.cryptpad.fr/en/admin_guide/index.html). We spent the remainder of our time addressing a growing backlog of issues on GitHub by fixing a number of weird bugs. ## Update notes -This release includes a new GitHub issue template (`cryptpad/.github/ISSUE_TEMPLATE/initial-instance-configuration.md`). The intent of this file is to make it clear that _Bug Reports_ are for intended for bugs in the software itself, not for soliciting help in configuring your personal server. Such issues take away time that we'd rather spend improving the platform for everybody's benefit, rather than for single administrators. +This release includes a new GitHub issue template (`cryptpad/.github/ISSUE_TEMPLATE/initial-instance-configuration.md`). The intent of this file is to make it clear that _Bug Reports_ are for intended for bugs in the software itself, not for soliciting help in configuring your personal server. Such issues take away time that we'd rather spend improving the platform for everybody's benefit, rather than for single administrators. -Sometimes difficulty configuring an instance does stem from an actual bug, however, most of the time these issues relate to the use of an unsupported configuration or failure to correctly follow installation instructions. The issue template includes some basic debugging steps which should identify the vast majority of problems. Beyond its primary goal of narrowing the scope of our issue tracker, we hope it will also be useful as an offline reference for administrators attempting to debug their instance. +Sometimes difficulty configuring an instance does stem from an actual bug, however, most of the time these issues relate to the use of an unsupported configuration or failure to correctly follow installation instructions. The issue template includes some basic debugging steps which should identify the vast majority of problems. Beyond its primary goal of narrowing the scope of our issue tracker, we hope it will also be useful as an offline reference for administrators attempting to debug their instance. -This template references the /checkup/ page that we've been steadily improving over the last few releases. It now includes even more tests to diagnose instance configuration problems, each with their own messages that provide some fairly detailed hints about what is wrong when an error is detected. This release introduces a number of tests that print _warnings_ that won't break an instance but might detract from users' experience. We recommend checking this page on your instance with each release as we will continue to improve it on an regular basis, and it might detect some errors of which you were unaware. +This template references the /checkup/ page that we've been steadily improving over the last few releases. It now includes even more tests to diagnose instance configuration problems, each with their own messages that provide some fairly detailed hints about what is wrong when an error is detected. This release introduces a number of tests that print _warnings_ that won't break an instance but might detract from users' experience. We recommend checking this page on your instance with each release as we will continue to improve it on an regular basis, and it might detect some errors of which you were unaware. -Otherwise, this release includes some changes to the provided example NGINX config file. It now includes a header designed to disable clients' participation in Google's [FLoC network](https://www.eff.org/deeplinks/2021/03/googles-floc-terrible-idea), as well as some basic rules related to the addition of our calendar app and OnlyOffice's two remaining editors (which are still not officially supported despite their inclusion here). +Otherwise, this release includes some changes to the provided example NGINX config file. It now includes a header designed to disable clients' participation in Google's [FLoC network](https://www.eff.org/deeplinks/2021/03/googles-floc-terrible-idea), as well as some basic rules related to the addition of our calendar app and OnlyOffice's two remaining editors (which are still not officially supported despite their inclusion here). -Lastly, any instance administrators that have had to customize their instance in order to disable registration can instead rely on a built-in feature that is available on the main page of the admin panel. Checking the "Close registration" checkbox will cause the application server to reject the creation of new "login blocks" (which store users' encrypted account credentials) while permitting existing users to change their passwords. Clients will be informed that registration is closed via the `/api/config` endpoint, causing the registration page to display a notice instead of the usual form. You may need to use the `FLUSH CACHE` button which can found on the same page of the admin panel in order to force clients to load the updated server config. +Lastly, any instance administrators that have had to customize their instance in order to disable registration can instead rely on a built-in feature that is available on the main page of the admin panel. Checking the "Close registration" checkbox will cause the application server to reject the creation of new "login blocks" (which store users' encrypted account credentials) while permitting existing users to change their passwords. Clients will be informed that registration is closed via the `/api/config` endpoint, causing the registration page to display a notice instead of the usual form. You may need to use the `FLUSH CACHE` button which can found on the same page of the admin panel in order to force clients to load the updated server config. -To update from 4.4.0 to 4.5.0: +To update from 4.4.0 to 4.5.0: 1. Apply the documented NGINX configuration 2. Stop your server @@ -54,21 +262,21 @@ To update from 4.4.0 to 4.5.0: ## Goals -Our main goal for this release was to complete the first steps of our ["Dialogue" project](https://nlnet.nl/project/CryptPadForms/), which will introduce surveys into CryptPad. We've also put considerable effort towards addressing some configuration issues, correcting some inconsistently translated UI, and writing some new documentation. +Our main goal for this release was to complete the first steps of our ["Dialogue" project](https://nlnet.nl/project/CryptPadForms/), which will introduce surveys into CryptPad. We've also put considerable effort towards addressing some configuration issues, correcting some inconsistently translated UI, and writing some new documentation. ## Update notes -This release removes the default privacy policy that has been included in CryptPad up until now. It included some assertions that were true of our own instance (CryptPad.fr) which we couldn't guarantee on third-party instances. We've updated our custom configuration to link to a privacy policy that was written in a rich text pad. You can do the same on your instance by editing `cryptpad/customize/application_config.js` to include the absolute URL of your instance, like so: `AppConfig.privacy = "https://cryptpad.your.website/privacy.html";`. +This release removes the default privacy policy that has been included in CryptPad up until now. It included some assertions that were true of our own instance (CryptPad.fr) which we couldn't guarantee on third-party instances. We've updated our custom configuration to link to a privacy policy that was written in a rich text pad. You can do the same on your instance by editing `cryptpad/customize/application_config.js` to include the absolute URL of your instance, like so: `AppConfig.privacy = "https://cryptpad.your.website/privacy.html";`. -We've clarified a point about telemetry in the notes of our 4.3.1 release. The text suggested that users on your instance would send telemetry to OUR webserver. It has been clarified to reflect that telemetry from your users is only ever sent to your instance. +We've clarified a point about telemetry in the notes of our 4.3.1 release. The text suggested that users on your instance would send telemetry to OUR webserver. It has been clarified to reflect that telemetry from your users is only ever sent to your instance. -We've spent some time working on improving our (officially) unreleased integrations of OnlyOffice's presentation and document editors. We've advised against enabling these editors on your instance. This release includes changes that may not be fully backwards compatible. If your users rely on either editor we advise that you not update until they have had an opportunity to back up their documents. We still aren't officially supporting either editor and we may make further breaking changes in the future. Consider this a warning and not an advertizement of their readiness! +We've spent some time working on improving our (officially) unreleased integrations of OnlyOffice's presentation and document editors. We've advised against enabling these editors on your instance. This release includes changes that may not be fully backwards compatible. If your users rely on either editor we advise that you not update until they have had an opportunity to back up their documents. We still aren't officially supporting either editor and we may make further breaking changes in the future. Consider this a warning and not an advertizement of their readiness! -This release also includes changes to the recommended NGINX configuration. Compare your instance's config against `cryptpad/docs/example.nginx.conf` and apply all the new changes before updating. In particular, you'll want to pay attention to the configuration for a newly exposed server API (`/api/broadcast`). This should work much the same as `/api/config`, so if you're using a non-standard configuration that uses more than one server you may want to proxy it in a similar fashion. +This release also includes changes to the recommended NGINX configuration. Compare your instance's config against `cryptpad/docs/example.nginx.conf` and apply all the new changes before updating. In particular, you'll want to pay attention to the configuration for a newly exposed server API (`/api/broadcast`). This should work much the same as `/api/config`, so if you're using a non-standard configuration that uses more than one server you may want to proxy it in a similar fashion. -Lastly, we've made some big improvements to the `/checkup/` page which performs some basic tests to confirm that your instance is configured correctly. It now provides some much more detailed descriptions of what might be wrong and how you can start debugging any issues that were identified. If you experience any problems after updating please review this page to assess your instance for any known issues before asking for help. +Lastly, we've made some big improvements to the `/checkup/` page which performs some basic tests to confirm that your instance is configured correctly. It now provides some much more detailed descriptions of what might be wrong and how you can start debugging any issues that were identified. If you experience any problems after updating please review this page to assess your instance for any known issues before asking for help. -To update from 4.3.1 to 4.4.0: +To update from 4.3.1 to 4.4.0: 1. Apply the documented NGINX configuration 2. Stop your server @@ -76,7 +284,7 @@ To update from 4.3.1 to 4.4.0: 4. Install the latest dependencies with `bower update` and `npm i` 5. Restart your server -This release requires updates to both clientside and serverside dependencies. **You will experience problems if you skip any of the above steps.** +This release requires updates to both clientside and serverside dependencies. **You will experience problems if you skip any of the above steps.** ## Features @@ -108,7 +316,7 @@ This release requires updates to both clientside and serverside dependencies. ** # 4.3.1 -This minor release addresses some bugs discovered after deploying and tagging 4.3.0 +This minor release addresses some bugs discovered after deploying and tagging 4.3.0 * We found that some browser extensions interfered with checks to determine whether a registered user was correctly logged in, which resulted in some disabled functionality. If you are running extensions that actively delete the tokens that keep you logged your session should now stay alive until you close all its active tabs, after which you will have to log back in. * Our 4.2.0 update introduced a new internal format for spreadsheets which broke support for spreadsheet templates using the older format. This release implements a compatibility layer. @@ -122,13 +330,13 @@ This minor release addresses some bugs discovered after deploying and tagging 4. ## Goals -This release is a continuation of our recent efforts to stabilize the platform, fixing small bugs and inconsistencies that we missed when developing larger features. In the meantime we've received reports of the platform performing poorly under various unusual circumstances, so we've developed some targeted fixes to both improve user experience and decrease the load on our server. +This release is a continuation of our recent efforts to stabilize the platform, fixing small bugs and inconsistencies that we missed when developing larger features. In the meantime we've received reports of the platform performing poorly under various unusual circumstances, so we've developed some targeted fixes to both improve user experience and decrease the load on our server. ## Update notes -This release should be fairly simple for admins. +This release should be fairly simple for admins. -To update from 4.2.1 to 4.3.0: +To update from 4.2.1 to 4.3.0: 1. Stop your server 2. Get the latest code with git @@ -162,7 +370,7 @@ To update from 4.2.1 to 4.3.0: # 4.2.1 -This minor release addresses a few bugs discovered after deploying 4.2.0: +This minor release addresses a few bugs discovered after deploying 4.2.0: * The 4.2.0 release included major improvements to the sheet application. This introduced breaking changes to the "lock" system in the application. Existing spreadsheets (before 4.2.0) that were closed by a user without "unlocking" all cells first became impossible to open after the 4.2.0 changes. This has been fixed. * Team owners can now properly upload a team avatar. @@ -176,21 +384,21 @@ This minor release addresses a few bugs discovered after deploying 4.2.0: ## Goals -We've made a lot of big changes to the platform lately. This release has largely been an attempt to stabilize the codebase by fixing bugs and merging features that we hadn't had a chance to test until now, all while updating our documentation and removing unused or outdated code. +We've made a lot of big changes to the platform lately. This release has largely been an attempt to stabilize the codebase by fixing bugs and merging features that we hadn't had a chance to test until now, all while updating our documentation and removing unused or outdated code. ## Update notes -This release includes an update to the sheet editor which is not backwards-compatible. Clients running the new version will not be able to correctly communicate with clients running older versions. Clients will automatically detect that a new version is available upon reconnecting to the server after a restart, so as long as you follow the steps recommended below this should be fine. +This release includes an update to the sheet editor which is not backwards-compatible. Clients running the new version will not be able to correctly communicate with clients running older versions. Clients will automatically detect that a new version is available upon reconnecting to the server after a restart, so as long as you follow the steps recommended below this should be fine. -We've also updated a server-side dependency that is not backwards-compatible. Failure to update both the platform and its dependencies together will result in errors. +We've also updated a server-side dependency that is not backwards-compatible. Failure to update both the platform and its dependencies together will result in errors. -The `scripts` directory now includes a script to identify unused translations. We used this to reduce the size of our localization files (`cryptpad/www/common/translations/*.json`). We reviewed the changes carefully and did our best to test, but it's always possible that a string was erroneously removed. If you notice any bugs in the UI where text seems to be missing, please let us (the developers) know via a GitHub issue. +The `scripts` directory now includes a script to identify unused translations. We used this to reduce the size of our localization files (`cryptpad/www/common/translations/*.json`). We reviewed the changes carefully and did our best to test, but it's always possible that a string was erroneously removed. If you notice any bugs in the UI where text seems to be missing, please let us (the developers) know via a GitHub issue. -CryptPad.fr now stores more than a terabyte of data, making it quite intensive to run the scripts to remove inactive files from the disk. To help alleviate this strain we've moved the code responsible for deleting files that have been archived for longer than the configured retention period into its own script (`./scripts/evict-archived.js`). For the moment this script is not integrated into the server and will not automatically run in the background as the main eviction script does. It's recommended that you run it manually if you find you are low on disk space. +CryptPad.fr now stores more than a terabyte of data, making it quite intensive to run the scripts to remove inactive files from the disk. To help alleviate this strain we've moved the code responsible for deleting files that have been archived for longer than the configured retention period into its own script (`./scripts/evict-archived.js`). For the moment this script is not integrated into the server and will not automatically run in the background as the main eviction script does. It's recommended that you run it manually if you find you are low on disk space. -Since early in the pandemic we've been serving a custom home page on CryptPad.fr to inform users that we've increased the amount of storage provided for free. This was originally intended as a temporary measure, but since almost a year has passed we figured it was about time we integrate this custom code into the platform itself. Admins can now add a custom note to the home page, using customized HTML in `customize/application_config.js`. To do this, define an `AppConfig.homeNotice` attribute like so: `AppConfig.homeNotice = "pewpew";`. +Since early in the pandemic we've been serving a custom home page on CryptPad.fr to inform users that we've increased the amount of storage provided for free. This was originally intended as a temporary measure, but since almost a year has passed we figured it was about time we integrate this custom code into the platform itself. Admins can now add a custom note to the home page, using customized HTML in `customize/application_config.js`. To do this, define an `AppConfig.homeNotice` attribute like so: `AppConfig.homeNotice = "pewpew";`. -To update from 4.1.0 to 4.2.0: +To update from 4.1.0 to 4.2.0: 1. Stop your server 2. Get the latest code from the 4.2.0 tag (`git fetch origin && git checkout 4.2.0`, or just `git pull origin main`) @@ -245,13 +453,13 @@ To update from 4.1.0 to 4.2.0: ## Goals -Our recent 4.0.0 release introduced major changes to CryptPad's style-sheets which likely caused some difficulty for admins who'd made extensive changes to their instance's appearance. We figure it's best to make more changes now instead of making small breaking changes more frequently, so we decided now is a good time to refactor a lot of our styles to implement an often-requested dark mode in CryptPad. +Our recent 4.0.0 release introduced major changes to CryptPad's style-sheets which likely caused some difficulty for admins who'd made extensive changes to their instance's appearance. We figure it's best to make more changes now instead of making small breaking changes more frequently, so we decided now is a good time to refactor a lot of our styles to implement an often-requested dark mode in CryptPad. ## Update notes -As noted above, this release introduces some major changes to CryptPad styles. If you have customized the look of your instance we recommend testing this new version locally before deploying it to your server to ensure that there are no critical conflicts. +As noted above, this release introduces some major changes to CryptPad styles. If you have customized the look of your instance we recommend testing this new version locally before deploying it to your server to ensure that there are no critical conflicts. -Otherwise, to update from 4.0.0 to 4.1.0: +Otherwise, to update from 4.0.0 to 4.1.0: 1. Stop your server 2. Get the latest code from the 4.1.0 tag (`git fetch origin && git checkout 4.1.0`, or just `git pull origin main`) @@ -288,25 +496,25 @@ Otherwise, to update from 4.0.0 to 4.1.0: # 4.0.0 (A) -We're very happy to introduce CryptPad v4.0! +We're very happy to introduce CryptPad v4.0! -This release is the culmination of a great deal of work over the last year, in which we searched for the right metaphors and imagery to clearly represent what CryptPad is all about. We've reworked our logo, color theme, text on our static pages, and the icons throughout the platform to convey the calm and safety we want our users to feel. +This release is the culmination of a great deal of work over the last year, in which we searched for the right metaphors and imagery to clearly represent what CryptPad is all about. We've reworked our logo, color theme, text on our static pages, and the icons throughout the platform to convey the calm and safety we want our users to feel. -Our release schedule typically follows an alphabetical naming scheme, ranging from A for the first (or zero-th) release of the cycle to Z for the last, with a thematic name for each letter. In the rush of preparing translations and double-checking all of our changes we never found time to settle on a theme for this release, but we do find there's some value in maintaining the otherwise arbitrary rhythm we've followed all this time. The progression through the alphabet gives a sense of pace to what can otherwise seem like a endless stream of problems that need solving, and the end of the alphabet prompts us to build towards major milestones like this one. +Our release schedule typically follows an alphabetical naming scheme, ranging from A for the first (or zero-th) release of the cycle to Z for the last, with a thematic name for each letter. In the rush of preparing translations and double-checking all of our changes we never found time to settle on a theme for this release, but we do find there's some value in maintaining the otherwise arbitrary rhythm we've followed all this time. The progression through the alphabet gives a sense of pace to what can otherwise seem like a endless stream of problems that need solving, and the end of the alphabet prompts us to build towards major milestones like this one. -With that in mind, you can expect 25 more major releases in this cycle before version 5.0, roughly every three weeks or so depending on circumstances. +With that in mind, you can expect 25 more major releases in this cycle before version 5.0, roughly every three weeks or so depending on circumstances. ## Goals -The main intent of this release was to deploy our `rebrand` branch which had been in development for some time. Along the way we also made notable improvements to the sheet editor which will be mentioned below. +The main intent of this release was to deploy our `rebrand` branch which had been in development for some time. Along the way we also made notable improvements to the sheet editor which will be mentioned below. ## Update notes -In the process of redesigning the platform we started using some new features of the LESS CSS pre-processor language that were not supported by the version of lesshint that we were using to scan for errors. We've updated that dev dependency to a newer version (4.5.0 => 6.3.7) which introduced a rather large number of minor dependencies. These are only used during development, not by the server itself, so this is unlikely to have any impact on the software itself. +In the process of redesigning the platform we started using some new features of the LESS CSS pre-processor language that were not supported by the version of lesshint that we were using to scan for errors. We've updated that dev dependency to a newer version (4.5.0 => 6.3.7) which introduced a rather large number of minor dependencies. These are only used during development, not by the server itself, so this is unlikely to have any impact on the software itself. -Otherwise, this release includes lots of changes to the platform's style sheets and static pages. If you've applied heavy customizations to your instance you might notice errors due to incompatibilities with your local changes. We recommend that you test your customizations against the latest release locally before updating a public instance to avoid service outages. +Otherwise, this release includes lots of changes to the platform's style sheets and static pages. If you've applied heavy customizations to your instance you might notice errors due to incompatibilities with your local changes. We recommend that you test your customizations against the latest release locally before updating a public instance to avoid service outages. -To update from 3.25.1 to 4.0.0: +To update from 3.25.1 to 4.0.0: 1. Stop your server 2. Get the latest code from the 4.0.0 tag @@ -319,7 +527,7 @@ To update from 3.25.1 to 4.0.0: * We found that certain issues reported via the built-in support ticket system were not easy to debug without knowing the id of the user's drive. Support tickets now include a `driveChannel` attribute to simplify this process. * We've added a variety of settings for the control of how your browser uses a local database to speed up loading times and display cached versions of documents even when disconnected from our server. These are available in the "confidentiality" section of the settings page (https://cryptpad.fr/settings/#security). -Finally, the "rebrand" part of this release: +Finally, the "rebrand" part of this release: * Our home page features our new logo, a cleaner layout, new text (notably dropping the use of "zero-knowledge" from our explanation), new app icons, softer colors, neater fonts, and a custom illustration of a document shredder that hints at how CryptPad works. * We no longer include a FAQ page with each instance, and instead link to relevant parts of our dedicated documentation platform (https://docs.cryptpad.fr) from any place that previously referenced the FAQ. This will make it easier for translators to focus on text for the platform's interface if they wish. An updated Frequently Asked Questions will be added to the documentation in the near future. @@ -337,9 +545,9 @@ Finally, the "rebrand" part of this release: # ZyzomysPedunculatus' revenge (3.25.1) -This minor release is primarily intended to fix some minor issues that were introduced or detected following our 3.25.0 release, but it also includes some major improvements that we want to test and stabilize before our upcoming 4.0.0 release. +This minor release is primarily intended to fix some minor issues that were introduced or detected following our 3.25.0 release, but it also includes some major improvements that we want to test and stabilize before our upcoming 4.0.0 release. -Features +Features * Our recent introduction of a clientside cache for document content now allows us to load and display a readable copy of a document before the most recent history has been fully loaded from the server. You might notice that your drive and some document typees are now displayed in a "DISCONNECTED" of "OFFLINE" state until they gets the latest history. For now this just means the loading screen is removed soon so you can start reading, but it's also an essential improvement that will become even more useful when we introduce the use of service-workers for offline usage. * We've added an `offline` mode to the server so that anyone developing features in CryptPad can test its offline and caching features by disabling the websocket components of the server. Use `npm run offline` to launch in this mode. @@ -348,7 +556,7 @@ Features * Errors that occur when loading teams now trigger some basic telemetry to the server to indicate the error code. This should help us determine the origin of some annoying teams issues that several users have reported. * Users of the rich text editor should now find that their scroll position is maintained when they are at the bottom of the document and a remote users adds more text. -Bug fixes +Bug fixes * Shortly after deploying 3.25.0 we identified several cases in which its cache invalidation logic was not correctly detecting corrupted cache entries. This caused some documents to fail to load. We quickly disabled most caching until we got the chance to review. Since then, we've tested it much more thoroughly under situations which made it more likely to become corrupt. Our new cache invalidation logic seems to catch all the known cases, so we're re-enabling the use of the cache for encrypted files and most of our supported document types. * We found that a race condition in the logout process prevented the document cache from being cleared correctly. We now wait until the asynchronous cache eviction process completes before redirecting users to the login page. @@ -360,7 +568,7 @@ Bug fixes * The recent replacement of a link to our faq with a link to our documentation platform violated some security headers and prevented the link from loading. We've fixed the inline link with some code to open this link in a compatible way. * Finally, we found a bug that caused custom colors in the slide app to revert to the default settings on page reloads. Custom slide colors should now be preserved. -To update from 3.25.0 to 3.25.1: +To update from 3.25.0 to 3.25.1: 1. Stop your server 2. Get the latest code with `git checkout 3.25.1` @@ -371,17 +579,17 @@ To update from 3.25.0 to 3.25.1: ## Goals -This is the last major release of our 3.0.0 release cycle. We wanted to mark the occasion with some big improvements to keep everyone happy in case we need to take some more time to prepare our upcoming 4.0.0 release. +This is the last major release of our 3.0.0 release cycle. We wanted to mark the occasion with some big improvements to keep everyone happy in case we need to take some more time to prepare our upcoming 4.0.0 release. ## Update notes -This update introduces some major database optimizations that should decrease both CPU and disk usage over time as users request resources and prime an on-disk cache for the next time. +This update introduces some major database optimizations that should decrease both CPU and disk usage over time as users request resources and prime an on-disk cache for the next time. -We've also introduce the ability to archive illegal or otherwise objectionable material from the admin panel assuming you possess the ability to load the content in question. It's also possible to restore archived content via an adjacent form field on the admin panel as long as it has not been permanently deleted. Due to a quirk in how ownership of uploaded files works, restored files will not retain their "owners" property. We hope to fix this in a future release. +We've also introduce the ability to archive illegal or otherwise objectionable material from the admin panel assuming you possess the ability to load the content in question. It's also possible to restore archived content via an adjacent form field on the admin panel as long as it has not been permanently deleted. Due to a quirk in how ownership of uploaded files works, restored files will not retain their "owners" property. We hope to fix this in a future release. -We've also made some minor changes to the example NGINX config file provided in `cryptpad/docs/example.nginx.confg`, specifically in [this commit](https://github.com/xwiki-labs/cryptpad/commit/2647acbb78643e651b71d2d4f74c2f66e264a258). CryptPad will probably work if you don't apply these changes to your nginx conf, but some functional improvements depend on the exposed headers. +We've also made some minor changes to the example NGINX config file provided in `cryptpad/docs/example.nginx.confg`, specifically in [this commit](https://github.com/xwiki-labs/cryptpad/commit/2647acbb78643e651b71d2d4f74c2f66e264a258). CryptPad will probably work if you don't apply these changes to your nginx conf, but some functional improvements depend on the exposed headers. -To upgrade from 3.24.0 to 3.25.0: +To upgrade from 3.24.0 to 3.25.0: 1. Update your NGINX config as mentioned above. 2. Stop your nodejs server. @@ -392,7 +600,7 @@ To upgrade from 3.24.0 to 3.25.0: ## Features * This release makes a lot of changes to how content is loaded over the network. - * Most notably, CryptPad now employs a client-side cache based on the the _indexedDB API_. Browsers that support this functionality will opportunistically store messages in a local cache for the next time they need them. This should make a considerable difference in how quickly you're able to load a pad, particularly if you accessing the server over a low-bandwidth network. + * Most notably, CryptPad now employs a client-side cache based on the _indexedDB API_. Browsers that support this functionality will opportunistically store messages in a local cache for the next time they need them. This should make a considerable difference in how quickly you're able to load a pad, particularly if you accessing the server over a low-bandwidth network. * Uploaded files (images, PDFs, etc.) are also cached in a similar way. Once you'd loaded an asset, your client will prefer to load its local copy instead of the server. * We've updated the code for our _full drive backup_ functionality so that it uses the local cache to load files more quickly. In addition to this, backing up the contents of your drive will also populate the cache as though you had loaded your documents in the normal fashion. This cache will persist until it is invalidated (due to the authoritative document having been deleted or had its history trimmed) or until you have logged out. * We've added the ability to configure the maximum size for automatically downloaded files. Any encrypted files that are above this size will instead require manual interaction to begin downloading. Files that are larger than this limit which are already loaded in your cache will still be automatically displayed. @@ -427,13 +635,13 @@ To upgrade from 3.24.0 to 3.25.0: ## Goals -We are once again working to develop some significant new features. This release is fairly small but includes some significant changes to detect and handle a variety of errors. +We are once again working to develop some significant new features. This release is fairly small but includes some significant changes to detect and handle a variety of errors. ## Update notes -This release includes some minor corrections the recommended NGINX configuration supplied in `cryptpad/docs/example.nginx.conf`. +This release includes some minor corrections the recommended NGINX configuration supplied in `cryptpad/docs/example.nginx.conf`. -To update from 3.23.2 to 3.24.0: +To update from 3.23.2 to 3.24.0: 1. Update your NGINX config to replicate the most recent changes and reload NGINX to apply them. 2. Stop the nodejs server. @@ -462,13 +670,13 @@ To update from 3.23.2 to 3.24.0: # XerusDaamsi reloaded (3.23.2) -A number of instance administrators reported issues following our 3.23.1 release. We suspect the issues were caused by applying the recommended update steps out of order which would result in the incorrect HTTP header values getting cached for the most recent version of a file. Since the most recently updated headers modified some security settings, this caused a catastrophic error on clients receiving the incorrect headers which caused them to fail to load under certain circumstances. +A number of instance administrators reported issues following our 3.23.1 release. We suspect the issues were caused by applying the recommended update steps out of order which would result in the incorrect HTTP header values getting cached for the most recent version of a file. Since the most recently updated headers modified some security settings, this caused a catastrophic error on clients receiving the incorrect headers which caused them to fail to load under certain circumstances. -Regardless of the reasons behind this, we want CryptPad to be resilient against misconfiguration. This minor release includes a number of measures to override the unruly caching mechanisms employed internally by two of our most stubborn dependencies (CKEditor and OnlyOffice). Deploying 3.23.2 should force these editors to load the most recent versions of these dependencies according to the same policies as the rest of CryptPad and instruct clients to ignore any incorrect server responses they might have cached over the last few updates. +Regardless of the reasons behind this, we want CryptPad to be resilient against misconfiguration. This minor release includes a number of measures to override the unruly caching mechanisms employed internally by two of our most stubborn dependencies (CKEditor and OnlyOffice). Deploying 3.23.2 should force these editors to load the most recent versions of these dependencies according to the same policies as the rest of CryptPad and instruct clients to ignore any incorrect server responses they might have cached over the last few updates. -This release also includes a number of bug fixes which had been tested in the meantime. +This release also includes a number of bug fixes which had been tested in the meantime. -Other bug fixes +Other bug fixes * We removed a hardcoded translation pertaining to the recently introduced "snapshot" functionality. * Inspection of our server logs revealed a number of rare race conditions and type errors that have since been addressed. These included: @@ -479,11 +687,11 @@ Other bug fixes * it was possible to click the buttons on the "team invitation response dialog" multiple times before the first action completed. In some cases this could result in attempting to join a single team multiple times. * it was also possible to activate trigger several actions that would modify your access rights for a team when the team had not fully synchronized with the server. Some of the time this was recoverable, but it could occasionally result in your team membership getting stuck in a bad state. -We've implemented some measures to correct any team data that might have become corrupted due to the issues described above. Access rights from duplicated teams should be merged back into one set of cryptographic keys wherever possible. In cases where this isn't possible your role in the team will be automatically downgraded to the rank conferred by the keys you still have. For instance, somebody listed as an administrator who only has the keys required to view the team will downgrade themself to be a viewer. Subsequent promotions back to your previous team role should restore your possession of the required keys. +We've implemented some measures to correct any team data that might have become corrupted due to the issues described above. Access rights from duplicated teams should be merged back into one set of cryptographic keys wherever possible. In cases where this isn't possible your role in the team will be automatically downgraded to the rank conferred by the keys you still have. For instance, somebody listed as an administrator who only has the keys required to view the team will downgrade themself to be a viewer. Subsequent promotions back to your previous team role should restore your possession of the required keys. -To update to 3.23.2 from 3.23.0 or 3.23.1: +To update to 3.23.2 from 3.23.0 or 3.23.1: -Perform the same upgrade steps listed for 3.23.0 including the most recent configuration changes listed in `cryptpad/docs/example.nginx.conf... +Perform the same upgrade steps listed for 3.23.0 including the most recent configuration changes listed in `cryptpad/docs/example.nginx.conf... 1. Modify your server's NGINX config file (but don't apply its changes until step 6) 2. Stop CryptPad's nodejs server @@ -495,9 +703,9 @@ Perform the same upgrade steps listed for 3.23.0 including the most recent confi # XerusDaamsi's revenge (3.23.1) -We discovered a number of minor bugs after deploying 3.23.0. This minor release addresses them. +We discovered a number of minor bugs after deploying 3.23.0. This minor release addresses them. -Features +Features * On instances with a lot of data (like our own) the background process responsible for evicting inactive data could time out. We've increased its permitted duration to a sufficient timeframe. * This process also aggregates some statistics about your database while it runs. Upon its completion a report is now stored in memory until it is overwritten by the next eviction process. This report will most likely be displayed on the admin panel in a future release. @@ -507,14 +715,14 @@ Features * When creating a shared folder we now indicate that the password field will be used to add a layer of protection to the folder. * The "destroy" button on the access modal now indicates that it will completely destroy the file or folder in question, rather than its access list or other parameters. -Bug fixes +Bug fixes * We received a number of support tickets related to users being unable to open rich text pads and sheets. We determined the issue to have been caused by our deployment of new HTTP headers to enable XLSX export on Firefox. These headers conflicted with the those on some cached files. The issue seemed to affect users randomly and did not occur when we tested the new features. We deployed some one-time cache-busting code to force clients to load the latest versions of these files (and their headers). * We addressed a regression introduced in 3.23.0 which incorrectly disabled the support ticket panels for users and admins. * We also fixed some layout issues on the admin panel's new _User storage_ pane. * Finally, we added a few guards against type errors in the drive which were most commonly triggered when viewing ranges of your drive's history which contained shared folders that had since been deleted. -To update from 3.23.0 to 3.23.1: +To update from 3.23.0 to 3.23.1: 0. Read the 3.23.0 release notes carefully and apply all configuration changes if you haven't already done so. 1. Stop your server @@ -526,23 +734,23 @@ To update from 3.23.0 to 3.23.1: ## Goals -We plan to produce an updated installation guide for CryptPad instance administrators to coincide with the release of our 4.0.0 release. As we get closer to the end of the alphabet we're working to simplify the process of configuring instances. This release features several new admin panel features intended to supersede the usage of the server configuration file and provide the ability to modify instance settings at runtime. +We plan to produce an updated installation guide for CryptPad instance administrators to coincide with the release of our 4.0.0 release. As we get closer to the end of the alphabet we're working to simplify the process of configuring instances. This release features several new admin panel features intended to supersede the usage of the server configuration file and provide the ability to modify instance settings at runtime. -We also spent some time finalizing some major improvements to the history mode which is available in most of our document editors. More on that in the _Features_ section. +We also spent some time finalizing some major improvements to the history mode which is available in most of our document editors. More on that in the _Features_ section. ## Update notes -This release introduces some behaviour which may require manual configuration on the part of the administrator. Read the following sections carefully or proceed at your own risk! +This release introduces some behaviour which may require manual configuration on the part of the administrator. Read the following sections carefully or proceed at your own risk! ### Automatic database maintenance -When a user employs the _destroy_ functionality to make a pad unavailable it isn't typically deleted. Instead it is made unavailable by moving it into the server's archive directory. Archived files are intended to be removed after another configurable amount of time (`archiveRetentionTime` in your config file). The deletion of old files from your archive is handled by `evict-inactive.js`, which can be found in `cryptpad/scripts/`. Up until now this script needed to be run manually (typically as a cron job) with `node ./scripts/evict-inactive.js`. Since this isn't widely known we decided to integrate it directly into the server by automatically running the script once per day. +When a user employs the _destroy_ functionality to make a pad unavailable it isn't typically deleted. Instead it is made unavailable by moving it into the server's archive directory. Archived files are intended to be removed after another configurable amount of time (`archiveRetentionTime` in your config file). The deletion of old files from your archive is handled by `evict-inactive.js`, which can be found in `cryptpad/scripts/`. Up until now this script needed to be run manually (typically as a cron job) with `node ./scripts/evict-inactive.js`. Since this isn't widely known we decided to integrate it directly into the server by automatically running the script once per day. -The same _eviction_ process is also responsible for scanning your server's database for inactive documents (defined as those which haven't been accessed in a number of days specified in your config under `inactiveTime`). Such inactive documents are archived unless they have been stored within a registered users drive. Starting with this release we have added the ability to specify the number of days before an account will be considered inactive (`accountRetentionTime`). This will take into account whether they added any new documents to their drive, or whether any of the existing documents were accessed or modified by other users. +The same _eviction_ process is also responsible for scanning your server's database for inactive documents (defined as those which haven't been accessed in a number of days specified in your config under `inactiveTime`). Such inactive documents are archived unless they have been stored within a registered users drive. Starting with this release we have added the ability to specify the number of days before an account will be considered inactive (`accountRetentionTime`). This will take into account whether they added any new documents to their drive, or whether any of the existing documents were accessed or modified by other users. -If you prefer to run the eviction script manually you can disable its integration into the server by adding `disableIntegratedEviction: true` to your config file. An example is given in `cryptpad/config/config.example.js`. If you want this process to run manually you may set the same value to `false`, or comment it out if you prefer. Likewise, if you prefer to never remove accounts and their data due to account inactivity, you may also comment it out. +If you prefer to run the eviction script manually you can disable its integration into the server by adding `disableIntegratedEviction: true` to your config file. An example is given in `cryptpad/config/config.example.js`. If you want this process to run manually you may set the same value to `false`, or comment it out if you prefer. Likewise, if you prefer to never remove accounts and their data due to account inactivity, you may also comment it out. -If you haven't been manually running the eviction scripts we recommend that you carefully review all of the values mentioned above to ensure that you will not be surprised by the sudden and unintended removal of any data. As a reminder, they are: +If you haven't been manually running the eviction scripts we recommend that you carefully review all of the values mentioned above to ensure that you will not be surprised by the sudden and unintended removal of any data. As a reminder, they are: * `inactiveTime` (number of days before a file is considered inactive) * `archiveRetentionTime` (number of days that an archived file will be retained before it is permanently deleted) @@ -551,19 +759,19 @@ If you haven't been manually running the eviction scripts we recommend that you ### NGINX Configuration update -After some testing on our part we've included an update to the example NGINX config file available in `cryptpad/docs/example.nginx.conf` which will enable a relatively new browser API which is required for XLSX export from our sheet editor. The relevant lines can be found beneath the comment `# Enable SharedArrayBuffer in Firefox (for .xlsx export)`. +After some testing on our part we've included an update to the example NGINX config file available in `cryptpad/docs/example.nginx.conf` which will enable a relatively new browser API which is required for XLSX export from our sheet editor. The relevant lines can be found beneath the comment `# Enable SharedArrayBuffer in Firefox (for .xlsx export)`. ### Quota management -Up until now the configuration file found in `cryptpad/config/config.js` has been the primary means of configuring a CryptPad instance. Unfortunately, as the server's behaviour becomes increasingly complex due to interest in a broad variety of use-cases this config file tends to grow. The kinds of questions that administrators ask via email, GitHub issues, and via our Matrix channel often suggest that admins haven't read through the comments in these files. Additionally, changes to the server's configuration can only be applied by restarting the server, which is increasingly disruptive as the service becomes more popular. To address these issues we've decided to start improving the instance admin panel such that it becomes the predominant means of modifying common server behaviours. +Up until now the configuration file found in `cryptpad/config/config.js` has been the primary means of configuring a CryptPad instance. Unfortunately, as the server's behaviour becomes increasingly complex due to interest in a broad variety of use-cases this config file tends to grow. The kinds of questions that administrators ask via email, GitHub issues, and via our Matrix channel often suggest that admins haven't read through the comments in these files. Additionally, changes to the server's configuration can only be applied by restarting the server, which is increasingly disruptive as the service becomes more popular. To address these issues we've decided to start improving the instance admin panel such that it becomes the predominant means of modifying common server behaviours. -We've started by making it possible to update storage settings from the _User storage_ section of the admin panel. Administrators can now update the default storage limit for users registered on the instance from the default quota of 50MB. It's also possible to allocate storage limits to particular users on the basis of their _Public Signing Key_, which can be found at the top of the _Accounts_ section on the settings page. +We've started by making it possible to update storage settings from the _User storage_ section of the admin panel. Administrators can now update the default storage limit for users registered on the instance from the default quota of 50MB. It's also possible to allocate storage limits to particular users on the basis of their _Public Signing Key_, which can be found at the top of the _Accounts_ section on the settings page. -Storage limits configured in this way will supercede those set via the server's config file, such that any modifications to a quota already set in the file will be ignored once you have modified or removed that user's quota via the admin panel. Admins are also able to view the parameters of all existing custom quotas loaded from either source. +Storage limits configured in this way will supercede those set via the server's config file, such that any modifications to a quota already set in the file will be ignored once you have modified or removed that user's quota via the admin panel. Admins are also able to view the parameters of all existing custom quotas loaded from either source. ### How to update -Once you've reviewed these settings and you're ready to update from 3.22.0 to 3.23.0: +Once you've reviewed these settings and you're ready to update from 3.22.0 to 3.23.0: 1. Modify your server's NGINX config file to include the new headers enabling XLSX export 2. Stop CryptPad's nodejs server @@ -575,7 +783,6 @@ Once you've reviewed these settings and you're ready to update from 3.22.0 to 3. ## Features - * As mentioned in the update notes, this release features a server update which will enable XLSX export from our sheet editor in Firefox. XLSX files are generated entirely on the client, so all information will remain confidential, it only required a server update to enable a feature in Firefox which is required to perform the conversion. * We've also made some considerable improvements to the _history mode_ available in most of our document editors. We now display a more detailed timeline of changes according to who was present in the session, and group contiguous modifications made by a single user. Our intent is to provide an overview of the document's history which exposes the details which are most relevant to humans, rather than only allowing users to step through each individual change. * Another change which is related to our history mode improvements is support for "version links", which allow you to link to a specific historical version of a document while you scroll through the timeline of its modifications. You can also create _named snapshots_ of documents which will subsequently be displayed as highlights in the document's timeline. @@ -595,11 +802,11 @@ Once you've reviewed these settings and you're ready to update from 3.22.0 to 3. ## Goals -We've been working on some long-term projects that we hope to deliver over the course of the next few releases. In the meantime, this release includes a number of minor improvements. +We've been working on some long-term projects that we hope to deliver over the course of the next few releases. In the meantime, this release includes a number of minor improvements. ## Update notes -To upgrade from 3.21.0 to 3.22.0: +To upgrade from 3.21.0 to 3.22.0: 1. Stop your server 2. Get the latest platform code with git @@ -623,21 +830,21 @@ To upgrade from 3.21.0 to 3.22.0: ## Goals -This release was developed over a longer period than usual due to holidays, our yearly company seminar, and generally working on some important software-adjacent projects. As such, we opted not to aim for any major features and instead introduce some minor improvements and address some users' complaints. +This release was developed over a longer period than usual due to holidays, our yearly company seminar, and generally working on some important software-adjacent projects. As such, we opted not to aim for any major features and instead introduce some minor improvements and address some users' complaints. ## Update notes -We've had a few disgruntled administrators contact us about our apparent _failure to provide a docker image_ or to otherwise support their preferred configuration. With that in mind, this is a periodic reminder that CryptPad is provided to the public under the terms of the AGPL (found within this repository in the [LICENSE file](./LICENSE)) which implies on our part no warranty, liability, or responsibility to configure your server for you. We do our best to provide the necessary information to correctly launch your own instance of the software given our limited budget, however, all such files are provided **AS IS** and are only intended to function under the narrow circumstances of usage which we recommend within the comments of the provided example configuration files. +We've had a few disgruntled administrators contact us about our apparent _failure to provide a docker image_ or to otherwise support their preferred configuration. With that in mind, this is a periodic reminder that CryptPad is provided to the public under the terms of the AGPL (found within this repository in the [LICENSE file](./LICENSE)) which implies on our part no warranty, liability, or responsibility to configure your server for you. We do our best to provide the necessary information to correctly launch your own instance of the software given our limited budget, however, all such files are provided **AS IS** and are only intended to function under the narrow circumstances of usage which we recommend within the comments of the provided example configuration files. -With that said, the vast majority of our community acts kindly and courteously towards us and each other. We really do appreciate it, and we'll continue to help you to the best of our ability. With that in mind, we're happy to announce that we've written and deployed a first version of our user guide, available at https://docs.cryptpad.fr. The work that went into this was funded by NLnet foundation as an NGI Zero PET (Privacy-Enhancing Technology) grant. We are currently working on two more guides intended for developers and administrators, and will deploy them to the same domain as they are completed. In the meantime we have begun to update our README, GitHub wiki, and other resources to reflect the current recommended practices and remove references to unsupported configurations. +With that said, the vast majority of our community acts kindly and courteously towards us and each other. We really do appreciate it, and we'll continue to help you to the best of our ability. With that in mind, we're happy to announce that we've written and deployed a first version of our user guide, available at https://docs.cryptpad.fr. The work that went into this was funded by NLnet foundation as an NGI Zero PET (Privacy-Enhancing Technology) grant. We are currently working on two more guides intended for developers and administrators, and will deploy them to the same domain as they are completed. In the meantime we have begun to update our README, GitHub wiki, and other resources to reflect the current recommended practices and remove references to unsupported configurations. -If you're only reading this for instructions on how to update your instance from 3.20.1 to 3.21.0: +If you're only reading this for instructions on how to update your instance from 3.20.1 to 3.21.0: 1. Stop your server 2. Get the latest platform code with git 3. Install client-side dependencies with `bower update` 4. Install server-side dependencies with `npm install` -4. Restart the CryptPad API server +5. Restart the CryptPad API server ## Features @@ -657,10 +864,10 @@ If you're only reading this for instructions on how to update your instance from # UplandMoa's revenge (3.20.1) -Once again we've decided to follow up our last major release with a minor "revenge" release that we wanted to make available as soon as possible. -We expect to deploy and release version 3.21.0 on Tuesday, July 28th, 2020. +Once again we've decided to follow up our last major release with a minor "revenge" release that we wanted to make available as soon as possible. +We expect to deploy and release version 3.21.0 on Tuesday, July 28th, 2020. -Features +Features * The _markmap_ rendering mode which was recently added to markdown preview pane implements some click event handlers which overlap with our existing handlers which open the embedded mindmap in our full screen "lightbox". You can now use _ctrl-click_ to trigger its built-in events (collapsing subtrees of the mindmap) without opening the lightbox. * We've made a few improvement to user and team drives: @@ -670,7 +877,7 @@ Features * Our rich text, code, slide, and poll apps now intercept pasted images and prompt the user to upload them, matching the existing experience of dragging an image into the same editable area. * We've received new contributions to our Romanian translation via [our weblate instance](https://weblate.cryptpad.fr/projects/cryptpad/app/). -Bug fixes +Bug fixes * We identified some race conditions in our spreadsheet app that were responsible for some corrupted data during the period leading up to our 3.20.0 release, however, we wanted to take a little more time to test before releasing the fixes. As of this release we're moving to a third version of our internal data format. This requires a client-side migration for each older sheet which will be performed by the first registered user to open a sheet in edit mode, after which a page reload will be required. Unregistered users with edit rights will only be able to view older sheets until they have been migrated by a registered user. * We now guard against empty _mathjax_ and _markmap_ code blocks in their respective markdown preview rendering extensions, as we discovered that empty inputs resulted in the display of "undefined" in the rendered element. @@ -680,26 +887,26 @@ Bug fixes * We've updated to a new version of `lodash` as a dependency of the linters that we use to validate our code. Unless you were actively using those linters while developing CryptPad this should have no effect for you. * Finally, when users open a link to a "self-destructing pad" we now check to make sure that the deletion key they possess has not been revoked before displaying a warning indicating that the pad in question will be deleted once they open it. -To update from 3.20.0 to 3.20.1: +To update from 3.20.0 to 3.20.1: 1. Stop your server 2. Get the latest code with `git checkout 3.20.1` 3. Install the latest dependencies with `bower update` and `npm i` -3. Restart your server +4. Restart your server # UplandMoa (3.20.0) ## Goals -We've held off on deploying any major features while we work towards deploying some documentation we've been busy organizing. This release features a wide range of minor features intended to address a number of github issues and frequent causes of support tickets. +We've held off on deploying any major features while we work towards deploying some documentation we've been busy organizing. This release features a wide range of minor features intended to address a number of github issues and frequent causes of support tickets. ## Update notes -This release features a modification to the recommended Content Security Policy headers as demonstrated in `./cryptpad/docs/example.nginx.conf`. CryptPad will work without making this change, however, we highly recommend updating your instance's nginx.conf as it will mitigate a variety of potential security vulnerabilities. +This release features a modification to the recommended Content Security Policy headers as demonstrated in `./cryptpad/docs/example.nginx.conf`. CryptPad will work without making this change, however, we highly recommend updating your instance's nginx.conf as it will mitigate a variety of potential security vulnerabilities. -Otherwise, we've introduced a new client-side dependency (_Mathjax_) and changed some server-side code that will require a server restart. +Otherwise, we've introduced a new client-side dependency (_Mathjax_) and changed some server-side code that will require a server restart. -To update from 3.19.1 to 3.20.0: +To update from 3.19.1 to 3.20.0: 1. Apply the recommended changes to your `nginx.conf` 2. Stop your server @@ -748,9 +955,9 @@ To update from 3.19.1 to 3.20.0: # Thylacine's revenge (3.19.1) -Our upcoming 3.20.0 release is planned for July 7th, 2020, but we are once again releasing a minor version featuring some nice bug fixes and usability improvements which are ready to be deployed now. In case you missed [our announcement](https://social.weho.st/@cryptpad/104360490068671089) we are phasing out our usage of the `master` and basing our releases on the `main` branch. For best results we recommend explicitly checking out code by its tag. +Our upcoming 3.20.0 release is planned for July 7th, 2020, but we are once again releasing a minor version featuring some nice bug fixes and usability improvements which are ready to be deployed now. In case you missed [our announcement](https://social.weho.st/@cryptpad/104360490068671089) we are phasing out our usage of the `master` and basing our releases on the `main` branch. For best results we recommend explicitly checking out code by its tag. -New features: +New features: * We've spent a little time making support tickets a little bit easier for both users and admins. * Users can now label their tickets with a set of predefined categories, making it easier for admins to sort through related reports. @@ -758,7 +965,7 @@ New features: * Teams now take advantage of the same "mailbox" functionality that powers user accounts' notification center. Team members with the "viewer" role can now use this feature to share documents with their team using the "share menu" as they already can with other users. Anyone with the ability to add a document to the team's drive will then be able to receive the notification and add the document to the team's drive for them. Going forward we'll use this functionality to implement more behaviour to make teams function more like shared user accounts. * The "pad creation screen" which is displayed to registered users when they first create a pad will no longer remember the settings used when they last created a pad. While this behaviour was intended to streamline the process of creating documents, in practice it led to some user's documents getting deleted because they didn't realize they were set to automatically expire. If you prefer not to use the defaults (owned, non-expiring) then you'll have to click a few more times to create a document, but we think that's a worthwhile tradeoff to avoid data loss. -Bug fixes: +Bug fixes: * Hitting _ctrl-A_ in the drive used to select lots of the page's elements which had no business being selected. Now it will select the contents of the directory currently being displayed. * Due to some complications in OnlyOffice (which we use for spreadsheets) remote updates made to a sheet were not displayed for users who had opened the document in "view mode". We still don't have the means to apply these remote changes in real-time, but we now prompt users to click a button to refresh the editor (not the full page) to display the latest document state. @@ -767,25 +974,25 @@ Bug fixes: * We noticed that the zip file constructed in the browser when you downloaded a subtree of a shared folder in your drive contained the correct directory structure but did not contain the files that were supposed to be there. This has been fixed. * Finally, we've tweaked our styles to use more specific CSS selectors to prevent a variety of styles from being accidentally applied to the wrong elements. This should make the platform a little easier to maintain and help us improve the visual consistency of a variety of elements on different pages. -To update from 3.19.0 to 3.19.1: +To update from 3.19.0 to 3.19.1: 1. Stop your server 2. Get the latest code with `git checkout 3.19.1` 3. Restart your server -If you're updating from anything other than 3.19.0 you may need other clientside dependencies (available with `bower update` and `npm i`). +If you're updating from anything other than 3.19.0 you may need other clientside dependencies (available with `bower update` and `npm i`). # Thylacine release (3.19.0) ## Goals -The intent of this release was to catch up on our backlog of bug fixes and minor usability improvements. +The intent of this release was to catch up on our backlog of bug fixes and minor usability improvements. ## Update notes -This release features an update to our clientside dependencies. +This release features an update to our clientside dependencies. -To update to 3.19.0 from 3.18.1: +To update to 3.19.0 from 3.18.1: 1. Stop your server 2. Get the latest code with git @@ -830,17 +1037,17 @@ To update to 3.19.0 from 3.18.1: # Smilodon's revenge (3.18.1) -Our next major release (3.19.0) is still a few weeks away. -In the meantime we've been working on some minor improvements and bug fixes that we wanted to ship as soon as possible. +Our next major release (3.19.0) is still a few weeks away. +In the meantime we've been working on some minor improvements and bug fixes that we wanted to ship as soon as possible. -New features: +New features: * Rich text pads can now be exported to .doc format. A few features don't translate well to the exported format (some fonts, embedded videos and pdfs), but for the most part your documents should work * Items in the "Recent pads" section of your drive can now be dragged to other folders via the filesystem tree UI * The user admin menu (found in the top-right corner) now includes an option to display the current version of the CryptPad instance you're using. We plan to add some more information here in the near future. * The kanban app now offers better support for editing markdown within cards with autocompleted parentheses. We've also added support for embedded media, allowing users to drag images and other content into the card content editor. -Bug fixes: +Bug fixes: * Account deletion via the settings page works once again * Some small layout and usability issues in the drive have been addressed @@ -852,7 +1059,7 @@ Bug fixes: * We've updated the parameters of the XLSX import/export functionality to prevent an "out of memory" error that primarily affected large spreadsheets. It should now allocate more memory instead of failing silently. * Finally, members of a team can now directly share or transfer ownership of a document owned by their team to their own account without having to go through the additional steps of offering it to themself and accepting the offer. -Updating from 3.18.0 to 3.18.1 is pretty standard: +Updating from 3.18.0 to 3.18.1 is pretty standard: 1. Stop your server 2. Get the latest code with git @@ -862,17 +1069,17 @@ Updating from 3.18.0 to 3.18.1 is pretty standard: ## Goals -This is a big one! A lot of people are going to love it and a few are probably going to hate it. +This is a big one! A lot of people are going to love it and a few are probably going to hate it. -This release introduces some major changes to our apps' appearances with the intent of making it easier to use, easier for us to support, and easier to maintain. +This release introduces some major changes to our apps' appearances with the intent of making it easier to use, easier for us to support, and easier to maintain. ## Update notes -If you're using a mostly standard CryptPad installation this should be a rather easy update. +If you're using a mostly standard CryptPad installation this should be a rather easy update. -If you've customized your styles, particularly for the purpose of overriding the default colors, you may encounter some problems. **We recommend that you test this version in a staging environment** before deploying to ensure that it is compatible with your modifications. +If you've customized your styles, particularly for the purpose of overriding the default colors, you may encounter some problems. **We recommend that you test this version in a staging environment** before deploying to ensure that it is compatible with your modifications. -Otherwise, update to 3.18.0 from 3.17.0 in the following manner: +Otherwise, update to 3.18.0 from 3.17.0 in the following manner: 1. stop your server 2. fetch the latest code with git @@ -899,13 +1106,13 @@ Otherwise, update to 3.18.0 from 3.17.0 in the following manner: # RedGazelle's revenge release (3.17.1) -In recent months a growing amount of our time has been going towards answering support tickets, emails, and GitHub issues. This has made it a little more difficult to also maintain a bi-weekly release schedule, since there's some overhead involved in deploying our latest code and producing release notes. +In recent months a growing amount of our time has been going towards answering support tickets, emails, and GitHub issues. This has made it a little more difficult to also maintain a bi-weekly release schedule, since there's some overhead involved in deploying our latest code and producing release notes. -To ease our workload, we've decided to switch to producing a full release every three weeks, with an optional patch release at some point in the middle. Patch releases may fix major issues that can't wait three weeks or may simply consist of a few minor fixes that are trivial to deploy. +To ease our workload, we've decided to switch to producing a full release every three weeks, with an optional patch release at some point in the middle. Patch releases may fix major issues that can't wait three weeks or may simply consist of a few minor fixes that are trivial to deploy. -This release fixes a few spreadsheet issues and introduces a more responsive layout for user drives in list mode. +This release fixes a few spreadsheet issues and introduces a more responsive layout for user drives in list mode. -Updating to 3.17.1 from 3.17.0 is pretty standard: +Updating to 3.17.1 from 3.17.0 is pretty standard: 1. Stop your server 2. Get the latest code with git @@ -915,25 +1122,25 @@ Updating to 3.17.1 from 3.17.0 is pretty standard: ## Goals -Our goal for this release was to introduce a first version of comments and mentions in our rich text editor as a part of a second R&D project funded by [NLnet](https://nlnet.nl/). We also received the results of an "accessibility audit" that was conducted as a part of our first NLnet PET project and so we've begun to integrate the auditor's feedback into the platform. +Our goal for this release was to introduce a first version of comments and mentions in our rich text editor as a part of a second R&D project funded by [NLnet](https://nlnet.nl/). We also received the results of an "accessibility audit" that was conducted as a part of our first NLnet PET project and so we've begun to integrate the auditor's feedback into the platform. -Otherwise we've continued with our major goal of continuing to support a growing number of users on our instance via server improvements (without introducing any regressions). +Otherwise we've continued with our major goal of continuing to support a growing number of users on our instance via server improvements (without introducing any regressions). ## Update notes -The most drastic change in this release is that we've removed all docker-related files from the platform's repository. These files were all added via community contributions. Having them in the main repo gave the impression that we support installation via docker (which we do not). +The most drastic change in this release is that we've removed all docker-related files from the platform's repository. These files were all added via community contributions. Having them in the main repo gave the impression that we support installation via docker (which we do not). -Docker-related files can now be found in the community-support [cryptpad-docker](https://github.com/xwiki-labs/cryptpad-docker/) repository. -If you have an existing instance that you've installed using docker and you'd like to update, you may review the [migration guide](https://github.com/xwiki-labs/cryptpad-docker/blob/master/MIGRATION.md). If you encounter any problems in the process we advise that you create an issue in the repository's issue-tracker. +Docker-related files can now be found in the community-support [cryptpad-docker](https://github.com/xwiki-labs/cryptpad-docker/) repository. +If you have an existing instance that you've installed using docker and you'd like to update, you may review the [migration guide](https://github.com/xwiki-labs/cryptpad-docker/blob/master/MIGRATION.md). If you encounter any problems in the process we advise that you create an issue in the repository's issue-tracker. -Once again, this repository is **community-maintained**. If you are using this repository then _you are a part of the community_! Bug reports are useful, but fixes are even better! +Once again, this repository is **community-maintained**. If you are using this repository then _you are a part of the community_! Bug reports are useful, but fixes are even better! -Otherwise, this is a fairly standard release. We've updated two of our client-side dependencies: +Otherwise, this is a fairly standard release. We've updated two of our client-side dependencies: 1. ChainPad features a memory management optimization which is particularly relevant to editing very large documents or loading a drive with a large number of files. In one test we were able to reduce memory consumption in Chrome from 1.7GB to 20MB. 2. CKEditor (the third-party library we use for our rich-text editor) has been updated so that we could make use of some more recent APIs for the _comments_ feature. -To update from **3.16.0** to **3.17.0**: +To update from **3.16.0** to **3.17.0**: 1. Stop your server 2. Fetch the latest source with git @@ -963,15 +1170,15 @@ To update from **3.16.0** to **3.17.0**: ## Goals -We've continued to keep a close eye on server performance since our last release while making minimal changes. Our goal for this release has been to improve server scalability further while also addressing user needs with updates to our client code. +We've continued to keep a close eye on server performance since our last release while making minimal changes. Our goal for this release has been to improve server scalability further while also addressing user needs with updates to our client code. -We were pleasantly surprised to receive a pull request implementing a basic version of [author colors](https://github.com/xwiki-labs/cryptpad/issues/41) in our code editor. Since it was nearly ready to go we set some time aside to polish it up a little bit to include it in this release. +We were pleasantly surprised to receive a pull request implementing a basic version of [author colors](https://github.com/xwiki-labs/cryptpad/issues/41) in our code editor. Since it was nearly ready to go we set some time aside to polish it up a little bit to include it in this release. ## Update notes -We've updated the example nginx config in order to include an `Access-Control-Allow-Origin` header that was not included. We've also added a new configuration point in response to [this issue](https://github.com/xwiki-labs/cryptpad/issues/529) about the server's child processes using too many threads. Administrators may not set a maximum number of child processes via `config.js` using `maxWorkers: `. We recommend using one less than the number of available cores, though one worker should be sufficient as long as your server is not under heavy load. +We've updated the example nginx config in order to include an `Access-Control-Allow-Origin` header that was not included. We've also added a new configuration point in response to [this issue](https://github.com/xwiki-labs/cryptpad/issues/529) about the server's child processes using too many threads. Administrators may not set a maximum number of child processes via `config.js` using `maxWorkers: `. We recommend using one less than the number of available cores, though one worker should be sufficient as long as your server is not under heavy load. -As usual, updating from the previous release can be accomplished by: +As usual, updating from the previous release can be accomplished by: 1. stopping your server 2. pulling the latest code with git @@ -1004,13 +1211,13 @@ As usual, updating from the previous release can be accomplished by: ## Goals -Our plan for this release was to allow our server's code to stabilize after a prologued period of major changes. The massive surge of new users on cryptpad.fr forced us to change our plans and focus instead on increasing performance and scalability of our serverside code and its supporting infrastructure. Most of this release's changes have been thoroughly tested as they've been deployed to our instance on an ongoing basis, however, we're still looking forward to stabilizing as planned. +Our plan for this release was to allow our server's code to stabilize after a prologued period of major changes. The massive surge of new users on cryptpad.fr forced us to change our plans and focus instead on increasing performance and scalability of our serverside code and its supporting infrastructure. Most of this release's changes have been thoroughly tested as they've been deployed to our instance on an ongoing basis, however, we're still looking forward to stabilizing as planned. -We also ended up making significant improvements to our clientside code, since the increased load on the server seemed to exacerbate a few race conditions which occurred less frequently under the previous circumstances. +We also ended up making significant improvements to our clientside code, since the increased load on the server seemed to exacerbate a few race conditions which occurred less frequently under the previous circumstances. ## Update notes -Updating from version 3.14.0 should follow the usual process: +Updating from version 3.14.0 should follow the usual process: 1. stop your server 2. fetch the latest code with git @@ -1018,7 +1225,7 @@ Updating from version 3.14.0 should follow the usual process: 4. install serverside dependencies with `npm i` 5. start your server -You may notice that the server now launches a number of child processes named `crypto-worker.js` and `db-worker.js`. These worker processes make use of however many cores your server has available to perform more CPU-intensive tasks in parallel. +You may notice that the server now launches a number of child processes named `crypto-worker.js` and `db-worker.js`. These worker processes make use of however many cores your server has available to perform more CPU-intensive tasks in parallel. ## Features @@ -1034,7 +1241,7 @@ You may notice that the server now launches a number of child processes named `c ## Bug fixes -This release contains fixes for a lot of bugs. We'll provide a brief overview, but in the interest of putting more time towards development I'll just put my strong recommendation that you update. +This release contains fixes for a lot of bugs. We'll provide a brief overview, but in the interest of putting more time towards development I'll just put my strong recommendation that you update. * The server process didn't always close file descriptors that it opened, resulting in an EMFILE error when the system ran out of available file descriptors. Now it closes them. * The server also kept an unbounded amount of data in an in-memory cache under certain circumstances. Now it doesn't. @@ -1051,15 +1258,15 @@ This release contains fixes for a lot of bugs. We'll provide a brief overview, b ## Goals -We planned a one-week release cycle in order to finish up some major features that were already in development during our last release. +We planned a one-week release cycle in order to finish up some major features that were already in development during our last release. -In the meantime, the reaction to the COVID-19 pandemic has resulted in a greatly increased load on our servers, so we've begun to focus on improving stability to ensure that we are able to keep up with demand. +In the meantime, the reaction to the COVID-19 pandemic has resulted in a greatly increased load on our servers, so we've begun to focus on improving stability to ensure that we are able to keep up with demand. ## Update notes -We had some trouble during the week of March 9th, 2020, as the CryptPad.fr server started throwing EMFILE errors. This means that it was trying to open new files (for reading or writing) but there were too many files open already. We've added some new code to help debug the issue, but there is not yet a fix in place. The maximum number of open files on our host OS had been increased by several orders of magnitude (several years ago) but we're now aware that the systemd service file that launches the API server does not respect this global limit. As such, we've updated the example service file to indicate how you can update this limit yourself. For an example of how to update this limit at the OS level, see this page: https://docs.oracle.com/cd/E19623-01/820-6168/file-descriptor-requirements.html +We had some trouble during the week of March 9th, 2020, as the CryptPad.fr server started throwing EMFILE errors. This means that it was trying to open new files (for reading or writing) but there were too many files open already. We've added some new code to help debug the issue, but there is not yet a fix in place. The maximum number of open files on our host OS had been increased by several orders of magnitude (several years ago) but we're now aware that the systemd service file that launches the API server does not respect this global limit. As such, we've updated the example service file to indicate how you can update this limit yourself. For an example of how to update this limit at the OS level, see this page: https://docs.oracle.com/cd/E19623-01/820-6168/file-descriptor-requirements.html -Otherwise, updating from 3.13.0 to 3.14.0 is as usual: +Otherwise, updating from 3.13.0 to 3.14.0 is as usual: 1. stop your server 2. fetch the latest source @@ -1069,7 +1276,7 @@ Otherwise, updating from 3.13.0 to 3.14.0 is as usual: ## Features -We're very happy to announce a major update to our kanban application! We've made a lot of changes, but the most notables ones are: +We're very happy to announce a major update to our kanban application! We've made a lot of changes, but the most notables ones are: * the ability to add markdown content to your cards and edit it collaboratively in real-time * tags on cards and the ability to filter cards by tags at the top of the application @@ -1079,7 +1286,7 @@ We're very happy to announce a major update to our kanban application! We've mad * a smaller palette of pre-chosen colors for cards and boards instead of a color-picker, to make it easier to choose matching colors for tasks * the ability to drag cards and boards to the trash instead of having to click a small X and confirm their deletion -We've also improved message throughput for our server by splitting cryptographic signature validation into separate processes. On a quad core server this means you should be able to handle (roughly) four times the messages. +We've also improved message throughput for our server by splitting cryptographic signature validation into separate processes. On a quad core server this means you should be able to handle (roughly) four times the messages. ## Bug fixes @@ -1098,39 +1305,39 @@ We've also improved message throughput for our server by splitting cryptographic ## Goals -This release cycle we prioritized the completion of "access lists", a major feature that we're excited to introduce. +This release cycle we prioritized the completion of "access lists", a major feature that we're excited to introduce. ## Update notes -Nearly every week (sometimes more than once) we end up taking time away from development to help administrators to configure their CryptPad instances. We're happy to see more instances popping up, but ideally we'd like to spend more of our time working on new features. With this in mind we devoted some time to simplify instance configuration and to clarify some points where people commonly have difficulty. +Nearly every week (sometimes more than once) we end up taking time away from development to help administrators to configure their CryptPad instances. We're happy to see more instances popping up, but ideally we'd like to spend more of our time working on new features. With this in mind we devoted some time to simplify instance configuration and to clarify some points where people commonly have difficulty. -If you review `cryptpad/config.example.js` you'll notice it is significantly smaller than it was last release. -Old configuration files should be backwards compatible (if you copied `config.example.js` to `config.js` in order to customize it). -The example has been reorganized so that the most important parts (which people seemed to miss most of the time) are at the top. -Most of the fields which were defined within the config file now have defaults defined within the server itself. -If you supply these values they will override the default, but for the most part they can be removed. +If you review `cryptpad/config.example.js` you'll notice it is significantly smaller than it was last release. +Old configuration files should be backwards compatible (if you copied `config.example.js` to `config.js` in order to customize it). +The example has been reorganized so that the most important parts (which people seemed to miss most of the time) are at the top. +Most of the fields which were defined within the config file now have defaults defined within the server itself. +If you supply these values they will override the default, but for the most part they can be removed. -We advise that you read the comments at the top of the example, in particular the points related to `httpUnsafeOrigin` and `httpSafeOrigin` which are used to protect users' cryptographic keys in the event of a cross-site scripting (XSS) vulnerability. -If these values are not correctly set then your users will not benefit from all the security measures we've spent lots of time implemented. +We advise that you read the comments at the top of the example, in particular the points related to `httpUnsafeOrigin` and `httpSafeOrigin` which are used to protect users' cryptographic keys in the event of a cross-site scripting (XSS) vulnerability. +If these values are not correctly set then your users will not benefit from all the security measures we've spent lots of time implemented. -A lot of the fields that were present as modifiable defaults have been removed or commented out in the example config. -If you supply them then they will override the default behaviour, however, you probably won't need to and doing so might break important functionality. -Content-Security Policy (CSP) definitions should be safe to remove, as should `httpAddress`, `httpPort`, and `httpSafePort` (unless you need to run the nodejs API server on an address other than `localhost` or port 3000. +A lot of the fields that were present as modifiable defaults have been removed or commented out in the example config. +If you supply them then they will override the default behaviour, however, you probably won't need to and doing so might break important functionality. +Content-Security Policy (CSP) definitions should be safe to remove, as should `httpAddress`, `httpPort`, and `httpSafePort` (unless you need to run the nodejs API server on an address other than `localhost` or port 3000. -Up until now it's been possible for administrators to allow users to pay for accounts (on their server) via https://accounts.cryptpad.fr. -Our intent was to securely handle payment and then split the proceeds between ourselves and the instance's administrator. -In practice this just created extra work for us because we ended up having to contact admins, all of whom have opted to treat the subscription as a donation to support development. -As such we have disabled the ability of users to pay for premium subscriptions (on https://accounts.cryptpad.fr) for any instance other than our own. +Up until now it's been possible for administrators to allow users to pay for accounts (on their server) via https://accounts.cryptpad.fr. +Our intent was to securely handle payment and then split the proceeds between ourselves and the instance's administrator. +In practice this just created extra work for us because we ended up having to contact admins, all of whom have opted to treat the subscription as a donation to support development. +As such we have disabled the ability of users to pay for premium subscriptions (on https://accounts.cryptpad.fr) for any instance other than our own. -Servers with premium subscriptions enabled were configured to check whether anyone had subscribed to a premium account by querying our accounts server on a daily basis. -We've left this daily check in place despite premium subscriptions being disabled because it informs us how many third-party instances exist and what versions they are running. -We don't sell or share this information with anyone, but it is useful to us because it informs us what older data structures we have to continue to support. -For instance, we retain code for migrating documents to newer data formats as long as we know that there are still instances that have not run those migrations. -We also cite the number of third-party instances when applying for grants as an indicator of the value of funding our project. -In any case, you can disable this daily check-in by setting `blockDailyCheck` to `true` in `config/config.js`. +Servers with premium subscriptions enabled were configured to check whether anyone had subscribed to a premium account by querying our accounts server on a daily basis. +We've left this daily check in place despite premium subscriptions being disabled because it informs us how many third-party instances exist and what versions they are running. +We don't sell or share this information with anyone, but it is useful to us because it informs us what older data structures we have to continue to support. +For instance, we retain code for migrating documents to newer data formats as long as we know that there are still instances that have not run those migrations. +We also cite the number of third-party instances when applying for grants as an indicator of the value of funding our project. +In any case, you can disable this daily check-in by setting `blockDailyCheck` to `true` in `config/config.js`. -Finally, we've implemented the ability to set a higher limit on the maximum size of uploaded files for premium users (paying users on CryptPad.fr and users with entries in `customLimits` on other instances). -Set this limit as a number (of bytes) with `premiumUploadSize` in your config file. +Finally, we've implemented the ability to set a higher limit on the maximum size of uploaded files for premium users (paying users on CryptPad.fr and users with entries in `customLimits` on other instances). +Set this limit as a number (of bytes) with `premiumUploadSize` in your config file. ## Features @@ -1152,21 +1359,21 @@ Set this limit as a number (of bytes) with `premiumUploadSize` in your config fi ## Goals -As of our last release our 'history trim' functionality was almost ready to go. We took this release period to do some extensive testing and to prepare the 'allow list' functionality which will be included in our next release. +As of our last release our 'history trim' functionality was almost ready to go. We took this release period to do some extensive testing and to prepare the 'allow list' functionality which will be included in our next release. -In the meantime, we also aimed to improve performance, add a few small but nice features, and fix a number of bugs. +In the meantime, we also aimed to improve performance, add a few small but nice features, and fix a number of bugs. ## Update notes -This release includes updates to: +This release includes updates to: 1. the server and its dependencies 2. the example nginx configuration which we recommend for production installations -4. the client code and its dependencies +3. the client code and its dependencies -Our ability to debug CryptPad's usage of shared workers (on the client) has been complicated by the fact that Firefox's shared worker debugging panel was not working for our instance. We finally traced the problem back to a Content-Security Policy setting in our configuration file. The issue can be addressed by adding a `resource:` entry in the `connect-src` header. We've updated the example nginx config to reflect this. You can deploy this version of CryptPad without this modification, but without it our ability to debug and fix issues related to shared worker will be extremely limited. +Our ability to debug CryptPad's usage of shared workers (on the client) has been complicated by the fact that Firefox's shared worker debugging panel was not working for our instance. We finally traced the problem back to a Content-Security Policy setting in our configuration file. The issue can be addressed by adding a `resource:` entry in the `connect-src` header. We've updated the example nginx config to reflect this. You can deploy this version of CryptPad without this modification, but without it our ability to debug and fix issues related to shared worker will be extremely limited. -Otherwise, updating from CryptPad v3.11.0 is pretty much the same as normal: +Otherwise, updating from CryptPad v3.11.0 is pretty much the same as normal: 1. stop your server 2. pull the latest code via git @@ -1208,21 +1415,21 @@ Otherwise, updating from CryptPad v3.11.0 is pretty much the same as normal: ## Goals -For this release we aimed to phase in two major features that we've been anticipating for a while: "history trim" and "safe links". +For this release we aimed to phase in two major features that we've been anticipating for a while: "history trim" and "safe links". -History trim will allow users to remove the old versions of their documents which continue to count against their storage quotas. It will be formally introduced in our next release, even though its server-side components are all ready. We had to reorganize and modify a lot of our server code, so we wanted to wait and make sure there were no regressions in our existing functionality before moving ahead. +History trim will allow users to remove the old versions of their documents which continue to count against their storage quotas. It will be formally introduced in our next release, even though its server-side components are all ready. We had to reorganize and modify a lot of our server code, so we wanted to wait and make sure there were no regressions in our existing functionality before moving ahead. -We're introducing the concept of "safe links" in CryptPad. Users can continue to share links to documents which include the cryptographic secrets necessary to read or edit them, but whenever possible we will replace those secrets with a document id. This will make it less likely for encryption keys to be exposed to third parties through invasive browser extensions or passive behaviour like history synchronization across devices. +We're introducing the concept of "safe links" in CryptPad. Users can continue to share links to documents which include the cryptographic secrets necessary to read or edit them, but whenever possible we will replace those secrets with a document id. This will make it less likely for encryption keys to be exposed to third parties through invasive browser extensions or passive behaviour like history synchronization across devices. ## Update notes -This release features a few changes to the server: +This release features a few changes to the server: 1. The "legal notice" feature which we included in the previous release turned out to be incorrect. We've since fixed it. We document this functionality [here](https://github.com/xwiki-labs/cryptpad/blob/e8b905282a2cde826ad9100dcad6b59a50c70e8b/www/common/application_config_internal.js#L35-L41), but you'll need to implement the recommended changes in `cryptpad/customize/application_config.js` for best effect. 2. We've dropped server-side support for the `retainData` attribute in `cryptpad/config/config.js`. Previously you could configure CryptPad to delete unpinned, inactive data immediately or to move it into an archive for a configurable retention period. We've removed the option to delete data outright, since it introduces additional complexity in the server which we don't regularly test. We also figure that administrators will appreciate this default in the event of a bug which incorrectly flags data as inactive. 3. We've fixed an incorrect line in [the example nginx configuration file](https://github.com/xwiki-labs/cryptpad/commit/1be01c07eee3431218d0b40a58164f60fec6df31). If you're using nginx as a reverse proxy for your CryptPad instance you should correct this line. It is used to set Content-Security Policy headers for the sandboxed-iframe which provides an additional layer of security for users in the event of a cross-site-scripting (XSS) vulnerability within CryptPad. If you find that your instance stops working after applying this change it is likely that you have not correctly configured your instance to use a secondary domain for its sandbox. See [this section of `cryptpad/config/config.example.js`](https://github.com/xwiki-labs/cryptpad/blob/c388641479128303363d8a4247f64230c08a7264/config/config.example.js#L94-L96) for more information. -Otherwise, deploying the new code should be fairly simple: +Otherwise, deploying the new code should be fairly simple: 1. stop your server 2. fetch the latest code from the git repository @@ -1254,22 +1461,24 @@ Otherwise, deploying the new code should be fairly simple: ## Goals -For this release we aimed to finish the last major feature of our CryptPad Teams project as well as some long-awaited features that we've planned to demo at FOSDEM 2020. +For this release we aimed to finish the last major feature of our CryptPad Teams project as well as some long-awaited features that we've planned to demo at FOSDEM 2020. ## Update notes -The CryptPad repository's _docs_ directory now includes a _systemd service file_ which you can use to ensure that CryptPad stays up and running. We're working on some step-by-step documentation to describe how to make use of it, but for now you can probably find some instructions by searching the web. +The CryptPad repository's _docs_ directory now includes a _systemd service file_ which you can use to ensure that CryptPad stays up and running. We're working on some step-by-step documentation to describe how to make use of it, but for now you can probably find some instructions by searching the web. -We've also updated the provided example.nginx.conf to include a minor but important change to the CSP settings for our OnlyOffice spreadsheet integration. +We've also updated the provided example.nginx.conf to include a minor but important change to the CSP settings for our OnlyOffice spreadsheet integration. -Up until now we have not been deleting unowned encrypted files from our server. As of this release `cryptpad/scripts/evict-inactive.js` includes logic to identify inactive, unpinned files. Identified files are first moved to your instance's _archive_ directory for a configurable period, after which they are deleted. This script is not run automatically, so if you haven't configured a cron job to run periodically then inactive files will not be removed. We recommend running the script once per day at a time when you expect your server to be relatively idle, since it consumes a non-negligible amount of server resources. +Up until now we have not been deleting unowned encrypted files from our server. As of this release `cryptpad/scripts/evict-inactive.js` includes logic to identify inactive, unpinned files. Identified files are first moved to your instance's _archive_ directory for a configurable period, after which they are deleted. This script is not run automatically, so if you haven't configured a cron job to run periodically then inactive files will not be removed. We recommend running the script once per day at a time when you expect your server to be relatively idle, since it consumes a non-negligible amount of server resources. -Finally, in case you live in a political jurisdiction that requires web site administrators to display their legal information, we've made it easier to add a link to a custom page. See `cryptpad/www/common/application_config_internal.js` for details, particularly the comments above `config.imprint`. +Finally, in case you live in a political jurisdiction that requires web site administrators to display their legal information, we've made it easier to add a link to a custom page. See `cryptpad/www/common/application_config_internal.js` for details, particularly the comments above `config.imprint`. -To update from v3.9.0: +To update from v3.9.0: 1. update the CSP settings in your reverse proxy's configuration file to match those in nginx.example.conf - * don't forget to reload your server to ensure that your changes are deployed + +* don't forget to reload your server to ensure that your changes are deployed + 2. stop your API server 3. pull the latest server/client code with `git pull origin master` 4. install the latest clientside dependencies with `bower update` @@ -1309,17 +1518,17 @@ To update from v3.9.0: ## Goals -Over time we've added many small configuration values to CryptPad's `config/config.js`. -As the number of possible variations grew it became increasingly difficult to test the platform and to provide clear documentation. -Ultimately this has made the platform more difficult to understand and consequently to host. +Over time we've added many small configuration values to CryptPad's `config/config.js`. +As the number of possible variations grew it became increasingly difficult to test the platform and to provide clear documentation. +Ultimately this has made the platform more difficult to understand and consequently to host. -This release features relatively few bug fixes or features. -Instead, we took the calm period of the northern winter holidays to simplify the process of running a server and to begin working on some comprehensive documentation. +This release features relatively few bug fixes or features. +Instead, we took the calm period of the northern winter holidays to simplify the process of running a server and to begin working on some comprehensive documentation. ## Update notes -We have chosen to drop support for a number of parameters which we believe are not widely used. -Read the following list carefully before updating, as you could be relying on behaviour which no longer exists. +We have chosen to drop support for a number of parameters which we believe are not widely used. +Read the following list carefully before updating, as you could be relying on behaviour which no longer exists. * Due to reasons of security and performance we have long advised that administrators make their instance available only over HTTPS provided by a reverse proxy such as nginx instead of loading TLS certificates via the node process itself. We have removed the option of serving HTTPS traffic directly from node by removing all support for HTTPS in this process. * Over the years many administrators have had to migrate their instance from one machine to another and have had difficulty identifying which directories were responsible for storing user data. We are beginning to migrate all user-generated data from the repository's root into the `data` directory as a new default, allowing for admins to migrate content by copying this single directory. @@ -1348,7 +1557,7 @@ Read the following list carefully before updating, as you could be relying on be * if your instance is configured in the default manner you shouldn't actually need this value, as it will default to using `/cryptpad_websocket`. * if you have configured your instance to serve all static assets over one domain and to host your API server on another, set `externalWebsocketURL` to `wss://your-domain.tld/cryptpad_websocket` or whatever URL will be correctly forwarded to your API server. -Once you have reviewed your configuration files and ensured that they are correct, update to 3.9.0 with the following steps: +Once you have reviewed your configuration files and ensured that they are correct, update to 3.9.0 with the following steps: 1. take your server down 2. get the latest code with `git pull origin master` @@ -1370,26 +1579,26 @@ Once you have reviewed your configuration files and ensured that they are correc # IsolobodonPortoricensis release (3.8.0) -We had some trouble finding an extinct animal whose name started with "I", and we had to resort to using a scientific name. -Despite this long name, this was a very short release cycle. -It's the last release of 2019, so we hope you like it! +We had some trouble finding an extinct animal whose name started with "I", and we had to resort to using a scientific name. +Despite this long name, this was a very short release cycle. +It's the last release of 2019, so we hope you like it! ## Goals -During this release cycle we prioritized the mitigation of some social abuse vectors and the ability to invite users to a team via a link. -We have more improvements planned for both features, but we wanted to release what we had before the end of the year as our team is taking a little time off to recharge for 2020. +During this release cycle we prioritized the mitigation of some social abuse vectors and the ability to invite users to a team via a link. +We have more improvements planned for both features, but we wanted to release what we had before the end of the year as our team is taking a little time off to recharge for 2020. ## Update notes -This is a small and simple release. We made a very minor improvement to the server which will require a restart, but everything will still work if you choose not to. +This is a small and simple release. We made a very minor improvement to the server which will require a restart, but everything will still work if you choose not to. -Update from 3.7.0 to 3.8.0 with the following procedure: +Update from 3.7.0 to 3.8.0 with the following procedure: 1. Take your server down 2. Get the latest code with `git pull origin master` 3. Bring your server back up -Or if you've set up your admin interface: +Or if you've set up your admin interface: 1. Pull the latest code 2. Click the admin panel's "Flush cache" button @@ -1419,22 +1628,22 @@ Or if you've set up your admin interface: ## Goals -As we are getting closer to the end of our CryptPad Teams project we planned to spend this release addressing some of the difficulties that users have reported regarding the usage of our newer social features. +As we are getting closer to the end of our CryptPad Teams project we planned to spend this release addressing some of the difficulties that users have reported regarding the usage of our newer social features. ## Update notes -This release includes an upgrade to a newer version of JQuery which mitigates a minor vulnerability which could have contributed to the presence of an XSS attack. We weren't using the affected methods in the library, but there's no harm in updating as it will protect against the vulnerability affecting user data in the future. +This release includes an upgrade to a newer version of JQuery which mitigates a minor vulnerability which could have contributed to the presence of an XSS attack. We weren't using the affected methods in the library, but there's no harm in updating as it will protect against the vulnerability affecting user data in the future. -We've also made some non-critical fixes to the server code, so you'll need to restart after pulling the latest code to take advantage of these improvements. +We've also made some non-critical fixes to the server code, so you'll need to restart after pulling the latest code to take advantage of these improvements. -Update to 3.7.0 from 3.6.0 using the normal update procedure: +Update to 3.7.0 from 3.6.0 using the normal update procedure: 1. stop your server 2. pull the latest code via git 3. run `bower update` 4. restart your server -If you're using an up-to-date version of NPM you should find that running `npm update` prints a notice that one of the packages you've installed is seeking funding. Entering `npm fund` will print information about our OpenCollective funding campaign. If you're running a slightly older version of NPM and you wish to support CryptPad's development you can do so by visiting https://opencollective.com/cryptpad . +If you're using an up-to-date version of NPM you should find that running `npm update` prints a notice that one of the packages you've installed is seeking funding. Entering `npm fund` will print information about our OpenCollective funding campaign. If you're running a slightly older version of NPM and you wish to support CryptPad's development you can do so by visiting https://opencollective.com/cryptpad . ## Features @@ -1466,11 +1675,11 @@ If you're using an up-to-date version of NPM you should find that running `npm u ## Goals -We're following up our last few releases of major core developments with an effort to improve reliability in some unstable areas and make some superficial tweaks to improve usability of some critical interfaces. +We're following up our last few releases of major core developments with an effort to improve reliability in some unstable areas and make some superficial tweaks to improve usability of some critical interfaces. ## Update notes -Update to 3.6.0 from 3.5.0 using the normal update procedure: +Update to 3.6.0 from 3.5.0 using the normal update procedure: 1. stop your server 2. pull the latest code via git @@ -1502,13 +1711,13 @@ Update to 3.6.0 from 3.5.0 using the normal update procedure: ## Goals -This release features work that we've been planning for a long time centered around sharing collections of documents in a more granular way. +This release features work that we've been planning for a long time centered around sharing collections of documents in a more granular way. -This is our first release since David Benqué joined our team, so in addition to these team-centric updates we also worked on integrating some UI/UX improvements. +This is our first release since David Benqué joined our team, so in addition to these team-centric updates we also worked on integrating some UI/UX improvements. ## Update notes -Updating to 3.5.0 from 3.4.0 is simple. +Updating to 3.5.0 from 3.4.0 is simple. 1. stop your server 2. pull the latest code via git @@ -1541,11 +1750,11 @@ Updating to 3.5.0 from 3.4.0 is simple. ## Goals -This is a small release, focused on bug fixes and UI improvements, while we're finalizing bigger team-centric features planned for the next release. +This is a small release, focused on bug fixes and UI improvements, while we're finalizing bigger team-centric features planned for the next release. ## Update notes -This is a pretty basic release: +This is a pretty basic release: 1. stop your server 2. pull the latest source code @@ -1575,11 +1784,11 @@ This is a pretty basic release: ## Goals -We've continued to prioritize the development of team-centric features in CryptPad. This release was focused on stabilizing the code for Teams and making them available to the users. +We've continued to prioritize the development of team-centric features in CryptPad. This release was focused on stabilizing the code for Teams and making them available to the users. ## Update notes -This is a pretty basic release: +This is a pretty basic release: 1. stop your server 2. pull the latest source code @@ -1587,7 +1796,7 @@ This is a pretty basic release: 4. install the latest clientside dependencies with `bower update` 5. restart your server -Note: we've updated our Nginx configuration to fix any missing trailing slash in the URL for the newest applications: https://github.com/xwiki-labs/cryptpad/commit/d4e5b98c140c28417e008379ec7af7cdc235792b +Note: we've updated our Nginx configuration to fix any missing trailing slash in the URL for the newest applications: https://github.com/xwiki-labs/cryptpad/commit/d4e5b98c140c28417e008379ec7af7cdc235792b ## Features @@ -1620,13 +1829,13 @@ Note: we've updated our Nginx configuration to fix any missing trailing slash in ## Goals -We've continued to prioritize the development of team-centric features in CryptPad. This release implements most of the core functionality for fully-functional teams as a core part of CryptPad, though they're not quite ready for use just yet. +We've continued to prioritize the development of team-centric features in CryptPad. This release implements most of the core functionality for fully-functional teams as a core part of CryptPad, though they're not quite ready for use just yet. -Beyond teams we did a little work to standardize some serverside APIs related to storage. +Beyond teams we did a little work to standardize some serverside APIs related to storage. ## Update notes -This is a pretty basic release: +This is a pretty basic release: 1. stop your server 2. pull the latest source code @@ -1658,7 +1867,7 @@ This is a pretty basic release: ## Goals -For CryptPad 3.1.0 we prioritized our work on team-centric features. In particular we wanted to finish some improvements to make our notifications system more private and start making use of our prior work on editable pad metadata. +For CryptPad 3.1.0 we prioritized our work on team-centric features. In particular we wanted to finish some improvements to make our notifications system more private and start making use of our prior work on editable pad metadata. ## Update notes @@ -1683,15 +1892,15 @@ For CryptPad 3.1.0 we prioritized our work on team-centric features. In particul * checking disk usage (global and for particular users) * loading a user's pin log -Baiji depends on updates to clientside and serverside dependencies. +Baiji depends on updates to clientside and serverside dependencies. -To update: +To update: 1. Take down your server 2. Pull the latest code -2. `npm install` -3. `bower update` -4. Launch your server +3. `npm install` +4. `bower update` +5. Launch your server ## Features @@ -1727,18 +1936,18 @@ To update: # Aurochs release (v3.0.0) -The move to 3.0 is mostly because we ran out of letters in the alphabet for our 2.0 release cycle. -Releases in this cycle will be named according to a theme of "extinct animals", a list which is unfortunately getting longer all the time. +The move to 3.0 is mostly because we ran out of letters in the alphabet for our 2.0 release cycle. +Releases in this cycle will be named according to a theme of "extinct animals", a list which is unfortunately getting longer all the time. ## Goals -In this release, we took more time than usual to make some big changes to the way the platform works, taking great care to maintain or improve stability. +In this release, we took more time than usual to make some big changes to the way the platform works, taking great care to maintain or improve stability. -Up until now it has been necessary to create documents with the whatever settings they might require in the future, after which point it was not possible to change them. This release introduces the ability of the server to store and read amendments to document metadata. This will soon allow users of owned documents to delegate that ownership to their friends, add or modify expiration times, and make other modifications that will greatly improve their control over their data. +Up until now it has been necessary to create documents with the whatever settings they might require in the future, after which point it was not possible to change them. This release introduces the ability of the server to store and read amendments to document metadata. This will soon allow users of owned documents to delegate that ownership to their friends, add or modify expiration times, and make other modifications that will greatly improve their control over their data. ## Update notes -During this development period we performed an extensive audit of our existing features and discovered a few potential security issues which we've addressed. We plan to announce the details of these flaws once administrators have had sufficient time to update their instances. If you are running a CryptPad instance, we advise you to update to 3.0.0 at your earliest opportunity. +During this development period we performed an extensive audit of our existing features and discovered a few potential security issues which we've addressed. We plan to announce the details of these flaws once administrators have had sufficient time to update their instances. If you are running a CryptPad instance, we advise you to update to 3.0.0 at your earliest opportunity. * It was brought to our attention that while expired pads were not being served beyond their expiration time, they were not being removed as intended. The cause was due to our failure to document a configuration point (`enableTaskScheduling`) that was added to make expiration optional in the example configuration file. We've removed this configuration point so that tasks like expiration will always be scheduled. Expiration of tasks was already integrated into the main server process, but we have added a new configuration point to the server in case any administrators would like to run the expiration tasks in a dedicated process for performance reasons. To disable the integration, change `disableIntegratedTasks` from `false` to `true` in the server configuration file. * This release depends on updates to three clientside libraries (`netflux-websocket@0.1.20`, `chainpad-netflux@0.9.0`, and `chainpad-listmap@0.7.0`). These changes are **not compatible with older versions of the server**. To update: @@ -1822,25 +2031,29 @@ During this development period we performed an extensive audit of our existing f ## Goals -This release coincided with XWiki's yearly seminar, so our regular schedule was interrupted a bit. We spent the time we had working towards implementing components of "editable metadata", which will allow pad owners to add new owners or transfer ownership to friends, among other things. +This release coincided with XWiki's yearly seminar, so our regular schedule was interrupted a bit. We spent the time we had working towards implementing components of "editable metadata", which will allow pad owners to add new owners or transfer ownership to friends, among other things. -Otherwise we wanted to deploy a built-in support system to improve our ability to debug issues as well as to make it easier for users to report problems. Along the way we did our best to improve usability and fix small annoying bugs. +Otherwise we wanted to deploy a built-in support system to improve our ability to debug issues as well as to make it easier for users to report problems. Along the way we did our best to improve usability and fix small annoying bugs. -As this is the last release in our 2.0 cycle, we're going to take some extra time to prepare some big features for our 3.0.0 release, which we expect to deploy on August 20th, 2019. +As this is the last release in our 2.0 cycle, we're going to take some extra time to prepare some big features for our 3.0.0 release, which we expect to deploy on August 20th, 2019. ## Update notes * We've updated some dependencies that are used to lint the CryptPad codebase to detect errors. Run `npm install` if you plan to develop for CryptPad and you want to use the linter * This release introduces a _support_ tab within the admin panel. If you generate an asymmetric keypair and add it to your server-side configuration file then users will have the option of opening support tickets if they encounter errors. Their support tickets will include some basic information about their account which might help you to solve their issues. To set up your _"encrypted support mailbox"_: + 1. run `node ./scripts/generate-admin-keys.js` 2. copy the "public key" and add it to your config.js file like so: - * `supportMailboxPublicKey: "BL3kgYBM0HNw5ms8ULWU1wMTb5ePBbxAPjDZKamkuB8=", + + * `supportMailboxPublicKey: "BL3kgYBM0HNw5ms8ULWU1wMTb5ePBbxAPjDZKamkuB8=", + 3. copy the private key and store it in a safe place 4. navigate to the "support" tab in the admin panel and enter the private key 5. share the private key with any other administrators who should be able to read the support tickets 6. restart so that your users receive the public key stored in your configuration file - * this will allow them to submit tickets via the support page - * if you don't know how to fix the issue and want to open a ticket on our public tracker, include the information submitted along with their ticket + + * this will allow them to submit tickets via the support page + * if you don't know how to fix the issue and want to open a ticket on our public tracker, include the information submitted along with their ticket ## Features @@ -1854,14 +2067,14 @@ As this is the last release in our 2.0 cycle, we're going to take some extra tim ## Goals -We've recently had an intern join our team, so this release and those until the end of summer are likely to feature a lot of small usability fixes. -Otherwise, we've continued to develop team-centric features, particularly the way that registered users share pads with friends. -Finally, we prioritized the ability to archive files for a period instead of deleting them, which we've been planning for a while. +We've recently had an intern join our team, so this release and those until the end of summer are likely to feature a lot of small usability fixes. +Otherwise, we've continued to develop team-centric features, particularly the way that registered users share pads with friends. +Finally, we prioritized the ability to archive files for a period instead of deleting them, which we've been planning for a while. ## Update notes * There are some important steps in this release: - * **make sure you read the full update notes before proceeding!** + * **make sure you read the full update notes before proceeding!** * [@zimbatm](https://github.com/zimbatm) added the ability to configure the location of your configuration file via environment variables when launching the server: * `CRYPTPAD_CONFIG=/home/cryptpad/cryptpad/cryptpad-config/config.js /home/cryptpad/cryptpad/server.js` * We discovered a bug in our Xenops release which resulted in the server's list of pads stored for each user to be incorrect. @@ -1892,7 +2105,7 @@ Finally, we prioritized the ability to archive files for a period instead of del 3. pull the latest clientside and serverside code via git 4. `npm update` to get the latest serverside dependencies 5. update the cache-busting string if you are handling the cache manually, otherwise allow the server to handle this as per its default - 5. restart the server: clients with open tabs should be prompted to reload instead of reconnecting because the server's version has changed + 6. restart the server: clients with open tabs should be prompted to reload instead of reconnecting because the server's version has changed * We recommend that you test a local version of CryptPad before deploying this latest code, as aspects of the above-mentioned migrations are not backwards-compatible. * you can roll back, but users' CryptDrives might have errors coping with data introduced by newer features. @@ -1907,7 +2120,7 @@ Finally, we prioritized the ability to archive files for a period instead of del * Users with existing friends on the platform will run a migration to allow them to share pads with friends directly instead of sending them a link. * they'll receive a notification indicating the title of the pad and who shared it * if you've already added friends on the platform, you can send them pads from the usual "sharing menu" -* Our code editor already offered the ability to set their color theme and highlighting mode, but now those values will be previewed when mousing over the the option in the dropdown. +* Our code editor already offered the ability to set their color theme and highlighting mode, but now those values will be previewed when mousing over the option in the dropdown. * Our slide editor now offers the same theme selection as the code editor * It's now possible to view the history of a shared folder by clicking the history button while viewing the shared folder's contents. @@ -1930,9 +2143,9 @@ Finally, we prioritized the ability to archive files for a period instead of del ## Goals -For this release we wanted to focus on releasing a small set of features built on top of some foundations established in our last release. Since we were able to complete this feature set in less than a week, we decided to bundle them together so users could take benefit from them sooner. +For this release we wanted to focus on releasing a small set of features built on top of some foundations established in our last release. Since we were able to complete this feature set in less than a week, we decided to bundle them together so users could take benefit from them sooner. -This work is being funded by the grant we received from NLnet foundation as a part of their PET (Privacy Enhancing Technology) fund. You can read all about this grant on our latest blog post (https://blog.cryptpad.fr/2019/05/27/Our-future-is-collaborative/). +This work is being funded by the grant we received from NLnet foundation as a part of their PET (Privacy Enhancing Technology) fund. You can read all about this grant on our latest blog post (https://blog.cryptpad.fr/2019/05/27/Our-future-is-collaborative/). ## Update notes @@ -1954,7 +2167,7 @@ This work is being funded by the grant we received from NLnet foundation as a pa ## Goals -This release coincided with a little time off for the team, so we planned to include only a few things. We recognized that the "Recent pads" view in the CryptDrive was not very useful for us because it did not include documents stored in _Shared folders_, so we decided to fix that. Otherwise, we're beginning a new project which we'll announce soon, so we've started working on some of its basic features. +This release coincided with a little time off for the team, so we planned to include only a few things. We recognized that the "Recent pads" view in the CryptDrive was not very useful for us because it did not include documents stored in _Shared folders_, so we decided to fix that. Otherwise, we're beginning a new project which we'll announce soon, so we've started working on some of its basic features. ## Update notes @@ -1977,7 +2190,7 @@ This release coincided with a little time off for the team, so we planned to inc ## Goals -For this release cycle we decided to fix some deep bugs and reduce the likelihood of regressions. This included not just errors in the code, but issues that were likely to arise from incorrect configuration. There's still some work to do, but the process of setting up a CryptPad server should be slightly easier now. +For this release cycle we decided to fix some deep bugs and reduce the likelihood of regressions. This included not just errors in the code, but issues that were likely to arise from incorrect configuration. There's still some work to do, but the process of setting up a CryptPad server should be slightly easier now. ## Update notes @@ -1993,7 +2206,7 @@ For this release cycle we decided to fix some deep bugs and reduce the likelihoo * `bower update` * restart your server * run the migration to optimize for expiring channels: - * From your CryptPad source directory, run `node scripts/migrations/migrate-tasks-v1.js` + * From your CryptPad source directory, run `node scripts/migrations/migrate-tasks-v1.js` * Administrators who want to restrict the translation languages available on their server can do so by defining an array of available language codes. * In your `cryptpad/customize/application_config.js`, define an array containing the langauges you want: * for Example: `AppConfig.availableLanguages = ['en', 'de', 'fr']` @@ -2022,11 +2235,11 @@ For this release cycle we decided to fix some deep bugs and reduce the likelihoo ## Goals -After all the features we've added over time, the root of the CryptPad repository had gotten to be something of a mess. We decided to spend a lot of this release period cleaning things up. We also prioritized some other features which make it easier to manage a CryptPad instance. +After all the features we've added over time, the root of the CryptPad repository had gotten to be something of a mess. We decided to spend a lot of this release period cleaning things up. We also prioritized some other features which make it easier to manage a CryptPad instance. ## Update notes -This release makes a number of serverside changes. Read the following notes carefully before updating from an earlier version of CryptPad! +This release makes a number of serverside changes. Read the following notes carefully before updating from an earlier version of CryptPad! * We realized that docker images persisted `config.js` by copying it into the `customize` volume. Since customize is exposed by the webserver, this meant that potentially private information in the configuration file would be accessible over the web. We've moved `config.js` to a `cryptpad/config/`, along with `config.example.js` and modified the docker setup so that nothing in this folder will be exposed to the web. * Consequently, you'll need to move your own `config.js` to the new location in order for your server to read it when you restart. @@ -2067,8 +2280,8 @@ This release makes a number of serverside changes. Read the following notes care ## Goals -As we're very busy wrapping up the project which has funded CryptPad's development so far, this release is very small. -We've requested assistance improving the state of our translations, and received some very helpful contributions. +As we're very busy wrapping up the project which has funded CryptPad's development so far, this release is very small. +We've requested assistance improving the state of our translations, and received some very helpful contributions. ## Update notes @@ -2092,8 +2305,8 @@ We've requested assistance improving the state of our translations, and received ## Goals -This release was developed during a busy period, so it contains fewer features than normal. -In particular we aimed to improve some aspects of our infrastructure, including finishing our deployment of _weblate_ for translations. +This release was developed during a busy period, so it contains fewer features than normal. +In particular we aimed to improve some aspects of our infrastructure, including finishing our deployment of _weblate_ for translations. ## Features @@ -2114,7 +2327,7 @@ In particular we aimed to improve some aspects of our infrastructure, including ## Goals -For this release we planned to resolve issues discovered in our beta release of encrypted spreadsheets, work towards providing an easier experience for contributors who wish to translate CryptPad, and resolve some minor usability issues that had been bothering us. +For this release we planned to resolve issues discovered in our beta release of encrypted spreadsheets, work towards providing an easier experience for contributors who wish to translate CryptPad, and resolve some minor usability issues that had been bothering us. ## Update notes @@ -2145,12 +2358,12 @@ For this release we planned to resolve issues discovered in our beta release of ## Goals -We set aside an additional week for this release in order to deploy _encrypted spreadsheets_, which we've been working toward for a long time. -This feature combines our usual focus on privacy with OnlyOffice's spreadsheet editor. +We set aside an additional week for this release in order to deploy _encrypted spreadsheets_, which we've been working toward for a long time. +This feature combines our usual focus on privacy with OnlyOffice's spreadsheet editor. -At least for this first release we're still considering this functionality to be **highly experimental**. -We've done our best to make this new application fun and easy to use, however, it will still require a lot of work before it supports all the features that you can expect from our other editors. -We welcome you to try it out and report any difficulties you encounter, though you may want to wait before you start using it for all your financial documents. +At least for this first release we're still considering this functionality to be **highly experimental**. +We've done our best to make this new application fun and easy to use, however, it will still require a lot of work before it supports all the features that you can expect from our other editors. +We welcome you to try it out and report any difficulties you encounter, though you may want to wait before you start using it for all your financial documents. ## Update notes @@ -2175,12 +2388,12 @@ We welcome you to try it out and report any difficulties you encounter, though y ## Goals -For this release we planned to improve upon last release's introduction of the display of other users' cursors in our code and slide editors by adding the same functionality to our rich text editor. +For this release we planned to improve upon last release's introduction of the display of other users' cursors in our code and slide editors by adding the same functionality to our rich text editor. -Beyond just producing software, the CryptPad team has also begun to produce peer-reviewed papers. -We have previously published [Private Document Editing with Some Trust](https://dl.acm.org/citation.cfm?doid=3209280.3209535) as a part of the 2018 proceedings of the ACM Symposium on Document Engineering. -We have recently been accepted for publication as a part of [HCI-CPT](http://2019.hci.international/hci-cpt): the first international conference on HCI (Human Computer Interaction) for cybersecurity, privacy and trust. -In preparation for this publication we've begun to collect additional usage data in order to inform the wider community of our findings regarding usability of cryptography-based collaboration systems. +Beyond just producing software, the CryptPad team has also begun to produce peer-reviewed papers. +We have previously published [Private Document Editing with Some Trust](https://dl.acm.org/citation.cfm?doid=3209280.3209535) as a part of the 2018 proceedings of the ACM Symposium on Document Engineering. +We have recently been accepted for publication as a part of [HCI-CPT](http://2019.hci.international/hci-cpt): the first international conference on HCI (Human Computer Interaction) for cybersecurity, privacy and trust. +In preparation for this publication we've begun to collect additional usage data in order to inform the wider community of our findings regarding usability of cryptography-based collaboration systems. ## Update notes @@ -2219,7 +2432,7 @@ In preparation for this publication we've begun to collect additional usage data ## Goals -For this release we chose to focus on our in-pad chat functionality and the ability to show your cursor's position to other users in the same pad. +For this release we chose to focus on our in-pad chat functionality and the ability to show your cursor's position to other users in the same pad. ## Update notes @@ -2246,8 +2459,8 @@ For this release we chose to focus on our in-pad chat functionality and the abil ## Goals -This release features long-awaited improvements to our Rich Text Pad. -This work was done over a short period, and we're releasing it now so that users can take advantage of the improvements as soon as possible. +This release features long-awaited improvements to our Rich Text Pad. +This work was done over a short period, and we're releasing it now so that users can take advantage of the improvements as soon as possible. ## Update notes @@ -2271,7 +2484,7 @@ This work was done over a short period, and we're releasing it now so that users ## Goals -For this release we aimed to address usability concerns in our Rich Text Pad, since it's our most widely used application. During this time we also received an unexpected security disclusure which we treated as being top priority. +For this release we aimed to address usability concerns in our Rich Text Pad, since it's our most widely used application. During this time we also received an unexpected security disclusure which we treated as being top priority. ## Update notes @@ -2296,7 +2509,7 @@ For this release we aimed to address usability concerns in our Rich Text Pad, si ## Goals -This release continued the work on better customization features for community instances. We also worked on usability improvements and UI issues. +This release continued the work on better customization features for community instances. We also worked on usability improvements and UI issues. ## Update notes @@ -2326,7 +2539,7 @@ This release continued the work on better customization features for community i ## Goals -This release continued to improve our _shared folder_ functionality, addressed user concerns about data portability, and implemented various features for customization for different CryptPad instances. +This release continued to improve our _shared folder_ functionality, addressed user concerns about data portability, and implemented various features for customization for different CryptPad instances. ## Update notes @@ -2337,15 +2550,15 @@ This release continued to improve our _shared folder_ functionality, addressed u * Administrators can now do more to customize their CryptPad server, most notably via the ability to override specific translations. For example, the home page now features a short message which, by default, says that the server is a community-hosted instance of the CryptPad open-source project. On CryptPad.fr, we have replaced this text to talk about our organization. You can do the same by modifying files in `cryptpad/customize/translations/`, like so: ``` -define(['/common/translations/messages.js'], function (Messages) { - // Replace the existing keys in your copied file here: - Messages.home_host = "CryptPad.fr is the official instance of the open-source CryptPad project. It is administered by XWiki SAS, the employee-owned French company which created and maintains the product."; +define(['/common/translations/messages.js'], function (Messages) { + // Replace the existing keys in your copied file here: + Messages.home_host = "CryptPad.fr is the official instance of the open-source CryptPad project. It is administered by XWiki SAS, the employee-owned French company which created and maintains the product."; - return Messages; -}); + return Messages; +}); ``` -Simply change the text assigned to `home_host` with a blurb about your own organization. We'll update the wiki soon with more info about customization. +Simply change the text assigned to `home_host` with a blurb about your own organization. We'll update the wiki soon with more info about customization. ### Features @@ -2373,11 +2586,11 @@ Simply change the text assigned to `home_host` with a blurb about your own organ ## Goals -Since last release introduced several big features, this release was allocated towards usability improvements largely related to those new features. +Since last release introduced several big features, this release was allocated towards usability improvements largely related to those new features. ## Update notes -This is a simple release. Just deploy the latest source. +This is a simple release. Just deploy the latest source. ### Features @@ -2394,8 +2607,8 @@ This is a simple release. Just deploy the latest source. ## Goals -We've been making use of some hidden features for a while, to make sure that they were safe to deploy. -This release, we worked on making _contextual chat_ and _shared folders_ available to everyone. +We've been making use of some hidden features for a while, to make sure that they were safe to deploy. +This release, we worked on making _contextual chat_ and _shared folders_ available to everyone. ## Update notes @@ -2421,12 +2634,12 @@ This release, we worked on making _contextual chat_ and _shared folders_ availab ## Goals -This release overlapped with the publication and presentation of a paper written about CryptPad's architecture. -As such, we didn't plan for any very ambitious new features, and instead focused on bug fixes and some new workflows. +This release overlapped with the publication and presentation of a paper written about CryptPad's architecture. +As such, we didn't plan for any very ambitious new features, and instead focused on bug fixes and some new workflows. ## Update notes -This is a fairly simple release. Just download the latest commits and update your cache-busting string. +This is a fairly simple release. Just download the latest commits and update your cache-busting string. ### Features @@ -2445,19 +2658,19 @@ This is a fairly simple release. Just download the latest commits and update you ## Goals -For this release we focused on deploying two very large changes in CryptPad. -For one, we'd worked on a large refactoring of the system we use to compile CSS from LESS, so as to make it more efficient. -Secondly, we reworked the architecture we use for implementing the CryptDrive functionality, so as to integrate support for shared folders. +For this release we focused on deploying two very large changes in CryptPad. +For one, we'd worked on a large refactoring of the system we use to compile CSS from LESS, so as to make it more efficient. +Secondly, we reworked the architecture we use for implementing the CryptDrive functionality, so as to integrate support for shared folders. ## Update notes -To test the _shared folders_ functionality, users can run the following command in their browser console: +To test the _shared folders_ functionality, users can run the following command in their browser console: -`localStorage.CryptPad_SF = "1";` +`localStorage.CryptPad_SF = "1";` -Alternatively, if the instance administrator would like to enable shared folders for all users, they can do so via their `/customize/application_config.js` file, by adding the following line: +Alternatively, if the instance administrator would like to enable shared folders for all users, they can do so via their `/customize/application_config.js` file, by adding the following line: -`config.disableSharedFolders = true;` +`config.disableSharedFolders = true;` ### Features @@ -2476,10 +2689,10 @@ Alternatively, if the instance administrator would like to enable shared folders ## Goals -This release took longer than usual - three weeks instead of two - due to our plans involving a complete redesign of how login and registration function. -Any time we rework a critical system within CryptPad we're very cautious about deploying it, however, this update should bring considerable value for users. -From now on, users will be able to change their passwords without losing access to their old data, however, this is very different from _password recovery_. -While we will still be unable to help you if you have forgotten your password, this update will address our inability up until this point to change your password in the event that it has been compromised in some way. +This release took longer than usual - three weeks instead of two - due to our plans involving a complete redesign of how login and registration function. +Any time we rework a critical system within CryptPad we're very cautious about deploying it, however, this update should bring considerable value for users. +From now on, users will be able to change their passwords without losing access to their old data, however, this is very different from _password recovery_. +While we will still be unable to help you if you have forgotten your password, this update will address our inability up until this point to change your password in the event that it has been compromised in some way. ## Update notes @@ -2507,7 +2720,7 @@ While we will still be unable to help you if you have forgotten your password, t ## Goals -For version 2.4.0 we chose to use our time to address difficulties that some users had, and to release some features which have been in development for some time. With the recent release of the _password-protected-pads_ feature, some users desired to be able to change the passwords that they'd already set, or to add a password to a pad retroactively. Other users wanted to recover information that had accidentally been deleted from their pads, but found that the history feature was difficult to use on networks with poor connectivity. Others still found that loading pads in general was too slow. +For version 2.4.0 we chose to use our time to address difficulties that some users had, and to release some features which have been in development for some time. With the recent release of the _password-protected-pads_ feature, some users desired to be able to change the passwords that they'd already set, or to add a password to a pad retroactively. Other users wanted to recover information that had accidentally been deleted from their pads, but found that the history feature was difficult to use on networks with poor connectivity. Others still found that loading pads in general was too slow. ## Update notes @@ -2549,7 +2762,7 @@ For version 2.4.0 we chose to use our time to address difficulties that some use ## Goals -For this release we wanted to deploy some new features related to our encrypted file functionality. +For this release we wanted to deploy some new features related to our encrypted file functionality. ## Update notes @@ -2577,7 +2790,7 @@ For this release we wanted to deploy some new features related to our encrypted ## Goals -For this release we wanted to continue our efforts towards improving CryptPad usability. We've also added a new Kanban application which was in its final stage for quite some time. +For this release we wanted to continue our efforts towards improving CryptPad usability. We've also added a new Kanban application which was in its final stage for quite some time. ## What's new @@ -2604,14 +2817,14 @@ For this release we wanted to continue our efforts towards improving CryptPad us ## Goals -This is a small release due to a surplus of holidays in France during the Month of May. -We'd been planning to implement _Password-protected Pads_ for a long time, but we had not found a good opportunity to do so within our roadmap. -After a generous donation from one of our users who considered this a critical feature, we were able to dedicate some resources towards delivering it to all of our users. +This is a small release due to a surplus of holidays in France during the Month of May. +We'd been planning to implement _Password-protected Pads_ for a long time, but we had not found a good opportunity to do so within our roadmap. +After a generous donation from one of our users who considered this a critical feature, we were able to dedicate some resources towards delivering it to all of our users. ## Update notes -This release depends on new APIs in our `chainpad-crypto` module. Additionally, we have fixed a critical bug in `chainpad-listmap`. -Admins will need to update their clientside dependencies with `bower update` when deploying. +This release depends on new APIs in our `chainpad-crypto` module. Additionally, we have fixed a critical bug in `chainpad-listmap`. +Admins will need to update their clientside dependencies with `bower update` when deploying. ## What's new @@ -2637,19 +2850,19 @@ Admins will need to update their clientside dependencies with `bower update` whe # Alpaca release (v2.0.0) -This is the first release of our 2.0 cycle. +This is the first release of our 2.0 cycle. -After careful consideration we've decided to name each release in this cycle after a cute animal, iterating through the letters of the Latin alphabet from A to Z. +After careful consideration we've decided to name each release in this cycle after a cute animal, iterating through the letters of the Latin alphabet from A to Z. ## Goals -We wanted to update CryptPad's appearance once more, adopting the colors from our logo throughout more of its interface. +We wanted to update CryptPad's appearance once more, adopting the colors from our logo throughout more of its interface. ## Update notes -This release coincides with the introduction of new APIs in ChainPad, so we recommend that adminstrators update their clientside dependencies by running `bower update`. +This release coincides with the introduction of new APIs in ChainPad, so we recommend that adminstrators update their clientside dependencies by running `bower update`. -As recent updates have updated serverside dependencies, we also recommend that you run `npm update` and _restart your server_. +As recent updates have updated serverside dependencies, we also recommend that you run `npm update` and _restart your server_. ## What's new @@ -2671,7 +2884,7 @@ As recent updates have updated serverside dependencies, we also recommend that y * we've updated the example configuration file (`config.example.js`) to no longer require a leading space before the domain, as we found it to be a common source of confusion. This will only affect newly generated config files. * our webserver has been configured to support HTTP access of the client datastore, to facilitate scripts which parse and decrypt history without having to go through our websocket infrastructure * we no longer use a single image for our favicon and our loading screen icon, allowing admins to customize either feature of their instance independently -* We've also moved the rest of the styles for the loading screen from `/common/` into `/customize.dist/`, +* We've also moved the rest of the styles for the loading screen from `/common/` into `/customize.dist/`, * move loading screen implementation from `/common/` to `/customize.dist/` ## Bug fixes @@ -2688,47 +2901,47 @@ As recent updates have updated serverside dependencies, we also recommend that y ## Goals -For this release we wanted to direct our effort towards improving user experience issues surrounding user accounts. +For this release we wanted to direct our effort towards improving user experience issues surrounding user accounts. ## Update notes -This release features breaking changes to some clientside dependencies. Administrators must make sure to deploy the -latest server with npm update before updating your clientside dependencies with bower update. +This release features breaking changes to some clientside dependencies. Administrators must make sure to deploy the +latest server with npm update before updating your clientside dependencies with bower update. ## What's new * newly registered users are now able to delete their accounts automatically, along with any personal - information which had been created: + information which had been created: * ToDo list data is automatically deleted, along with user profiles * all of a user's owned pads are also removed immediately in their account deletion process * users who predate account deletion will not benefit from automatic account deletion, since the server - does not have sufficient knowledge to guarantee that the information they could request to have deleted is strictly - their own. For this reason, we've started working on scripts for validating user requests, so as to enable manual - deletion by the server administrator. + does not have sufficient knowledge to guarantee that the information they could request to have deleted is strictly + their own. For this reason, we've started working on scripts for validating user requests, so as to enable manual + deletion by the server administrator. * the script can be found in cryptpad/check-account-deletion.js, and it will be a part of an ongoing - effort to improve administrator tooling for situations like this + effort to improve administrator tooling for situations like this * users who have not logged in, but wish to use their drive now see a ghost icon which they can use to create pads. - We hope this makes it easier to get started as a new user. -* registered users who have saved templates in their drives can now use those templates at any time, rather than only - using them to create new pads + We hope this makes it easier to get started as a new user. +* REGistered users who have saved templates in their drives can now use those templates at any time, rather than only + using them to create new pads * we've updated our file encryption code such that it does not interfere with other scripts which may be running at - the same time (synchronous blocking, for those who are interested) + the same time (synchronous blocking, for those who are interested) * we now validate message signatures clientside, except when they are coming from the history keeper because clients - trust that the server has already validated those signatures + trust that the server has already validated those signatures ## Bug fixes * we've removed some dependencies from our home page that were introduced when we updated to use bootstrap4 * we now import fontawesome as css, and not less, which saves processing time and saves room in our localStorage cache * templates which do not have a 'type' attribute set are migrated such that the pads which are created with their - content are valid + content are valid * thumbnail creation for pads is now disabled by default, due to poor performance * users can enable thumbnail creation in their settings page * we've fixed a significant bug in how our server handles checkpoints (special patches in history which contain the - entire pads content) + entire pads content) * it was possible for two users to independently create checkpoints in close proximity while the document was in a - forked state. New users joining while the session was in this state would get stuck on one side of the fork, - and could lose data if the users on the opposing fork overrode their changes + forked state. New users joining while the session was in this state would get stuck on one side of the fork, + and could lose data if the users on the opposing fork overrode their changes * we've updated our tests, which have been failing for some time because their success conditions were no longer valid * while trying to register a previously registered user, users could cancel the prompt to login as that user. - If they did so, the registration form remained locked. This has been fixed. + If they did so, the registration form remained locked. This has been fixed. diff --git a/config/config.example.js b/config/config.example.js index f53f3bb5b..96914fa92 100644 --- a/config/config.example.js +++ b/config/config.example.js @@ -122,46 +122,6 @@ module.exports = { ], */ - /* CryptPad's administration panel includes a "support" tab - * wherein administrators with a secret key can view messages - * sent from users via the encrypted forms on the /support/ page - * - * To enable this functionality: - * run `node ./scripts/generate-admin-keys.js` - * save the public key in your config in the value below - * add the private key via the admin panel - * and back it up in a secure manner - * - */ - // supportMailboxPublicKey: "", - - /* We're very proud that CryptPad is available to the public as free software! - * We do, however, still need to pay our bills as we develop the platform. - * - * By default CryptPad will prompt users to consider donating to - * our OpenCollective campaign. We publish the state of our finances periodically - * so you can decide for yourself whether our expenses are reasonable. - * - * You can disable any solicitations for donations by setting 'removeDonateButton' to true, - * but we'd appreciate it if you didn't! - */ - //removeDonateButton: false, - - /* CryptPad will display a point of contact for your instance on its contact page - * (/contact.html) if you provide it below. - */ - adminEmail: 'i.did.not.read.my.config@cryptpad.fr', - - /* - * By default, CryptPad contacts one of our servers once a day. - * This check-in will also send some very basic information about your instance including its - * version and the adminEmail so we can reach you if we are aware of a serious problem. - * We will never sell it or send you marketing mail. - * - * If you want to block this check-in and remain set 'blockDailyCheck' to true. - */ - //blockDailyCheck: false, - /* ===================== * STORAGE * ===================== */ @@ -316,4 +276,13 @@ module.exports = { * (false by default) */ verbose: false, + + /* Surplus information: + * + * 'installMethod' is included in server telemetry to voluntarily + * indicate how many instances are using unofficial installation methods + * such as Docker. + * + */ + installMethod: 'unspecified', }; diff --git a/customize.dist/favicon/alt-favicon-form.png b/customize.dist/favicon/alt-favicon-form.png new file mode 100644 index 000000000..2194e35b7 Binary files /dev/null and b/customize.dist/favicon/alt-favicon-form.png differ diff --git a/customize.dist/favicon/main-favicon-form.png b/customize.dist/favicon/main-favicon-form.png new file mode 100644 index 000000000..05c8ebf45 Binary files /dev/null and b/customize.dist/favicon/main-favicon-form.png differ diff --git a/customize.dist/fonts/cptools/fonts/cptools.svg b/customize.dist/fonts/cptools/fonts/cptools.svg index 776b66ba3..12d2fe9d6 100644 --- a/customize.dist/fonts/cptools/fonts/cptools.svg +++ b/customize.dist/fonts/cptools/fonts/cptools.svg @@ -23,9 +23,19 @@ + - + + + + + + + + + + \ No newline at end of file diff --git a/customize.dist/fonts/cptools/fonts/cptools.ttf b/customize.dist/fonts/cptools/fonts/cptools.ttf index cfc9d1e3c..788b7f881 100644 Binary files a/customize.dist/fonts/cptools/fonts/cptools.ttf and b/customize.dist/fonts/cptools/fonts/cptools.ttf differ diff --git a/customize.dist/fonts/cptools/fonts/cptools.woff b/customize.dist/fonts/cptools/fonts/cptools.woff index 80432d647..f2faf5aa2 100644 Binary files a/customize.dist/fonts/cptools/fonts/cptools.woff and b/customize.dist/fonts/cptools/fonts/cptools.woff differ diff --git a/customize.dist/fonts/cptools/style.css b/customize.dist/fonts/cptools/style.css index 7fad69146..874b6068f 100644 --- a/customize.dist/fonts/cptools/style.css +++ b/customize.dist/fonts/cptools/style.css @@ -1,9 +1,10 @@ @font-face { font-family: 'cptools'; - src: - url('fonts/cptools.ttf?n9y2kz') format('truetype'), - url('fonts/cptools.woff?n9y2kz') format('woff'), - url('fonts/cptools.svg?n9y2kz#cptools') format('svg'); + src: url('fonts/cptools.eot?chd5a1'); + src: url('fonts/cptools.eot?chd5a1#iefix') format('embedded-opentype'), + url('fonts/cptools.ttf?chd5a1') format('truetype'), + url('fonts/cptools.woff?chd5a1') format('woff'), + url('fonts/cptools.svg?chd5a1#cptools') format('svg'); font-weight: normal; font-style: normal; font-display: block; @@ -25,11 +26,38 @@ -moz-osx-font-smoothing: grayscale; } -.cptools-sheet:before { - content: "\e908"; +.cptools-form-poll:before { + content: "\e910"; } -.cptools-slide:before { - content: "\e907"; +.cptools-form-poll-maybe:before { + content: "\e91e"; +} +.cptools-form-list-check:before { + content: "\e916"; +} +.cptools-form-grid-check:before { + content: "\e917"; +} +.cptools-form-grid-radio:before { + content: "\e918"; +} +.cptools-form-list-radio:before { + content: "\e919"; +} +.cptools-form-page-break:before { + content: "\e91a"; +} +.cptools-form-paragraph:before { + content: "\e91b"; +} +.cptools-form-text:before { + content: "\e91c"; +} +.cptools-form-list-ordered:before { + content: "\e91d"; +} +.cptools-folder-no-color:before { + content: "\e900"; } .cptools-whiteboard:before { content: "\e901"; @@ -37,6 +65,9 @@ .cptools-new-template:before { content: "\e902"; } +.cptools-shared-folder:before { + content: "\e903"; +} .cptools-file-upload:before { content: "\e904"; } @@ -46,9 +77,24 @@ .cptools-poll:before { content: "\e906"; } +.cptools-slide:before { + content: "\e907"; +} +.cptools-sheet:before { + content: "\e908"; +} +.cptools-folder-open:before { + content: "\e909"; +} .cptools-kanban:before { content: "\e90a"; } +.cptools-folder:before { + content: "\e90b"; +} +.cptools-shared-folder-open:before { + content: "\e90c"; +} .cptools-code:before { content: "\e90d"; } @@ -58,8 +104,11 @@ .cptools-file:before { content: "\e90f"; } -.cptools-destroy:before { - content: "\e915"; +.cptools-palette:before { + content: "\e911"; +} +.cptools-folder-upload:before { + content: "\e912"; } .cptools-add-bottom:before { content: "\e913"; @@ -67,24 +116,6 @@ .cptools-add-top:before { content: "\e914"; } -.cptools-folder-upload:before { - content: "\e912"; -} -.cptools-folder-no-color:before { - content: "\e900"; -} -.cptools-shared-folder:before { - content: "\e903"; -} -.cptools-folder-open:before { - content: "\e909"; -} -.cptools-folder:before { - content: "\e90b"; -} -.cptools-shared-folder-open:before { - content: "\e90c"; -} -.cptools-palette:before { - content: "\e911"; +.cptools-destroy:before { + content: "\e915"; } diff --git a/customize.dist/images/YannFlory.jpg b/customize.dist/images/YannFlory.jpg deleted file mode 100644 index 9c358d1a6..000000000 Binary files a/customize.dist/images/YannFlory.jpg and /dev/null differ diff --git a/customize.dist/images/logo_white.png b/customize.dist/images/logo_white.png deleted file mode 100644 index 8219cc2b0..000000000 Binary files a/customize.dist/images/logo_white.png and /dev/null differ diff --git a/customize.dist/images/logo_white.svg b/customize.dist/images/logo_white.svg deleted file mode 100644 index d1cd2bc73..000000000 --- a/customize.dist/images/logo_white.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/customize.dist/login.js b/customize.dist/login.js index 74e5e86f6..3309190c0 100644 --- a/customize.dist/login.js +++ b/customize.dist/login.js @@ -153,7 +153,7 @@ define([ register: isRegister, }; - var RT, blockKeys, blockHash, Pinpad, rpc, userHash; + var RT, blockKeys, blockHash, blockUrl, Pinpad, rpc, userHash; nThen(function (waitFor) { // derive a predefined number of bytes from the user's inputs, @@ -171,7 +171,7 @@ define([ // the rest of their data // determine where a block for your set of keys would be stored - var blockUrl = Block.getBlockUrl(res.opt.blockKeys); + blockUrl = Block.getBlockUrl(res.opt.blockKeys); // Check whether there is a block at that location Util.fetch(blockUrl, waitFor(function (err, block) { @@ -412,12 +412,21 @@ define([ toPublish.edPublic = RT.proxy.edPublic; var blockRequest = Block.serialize(JSON.stringify(toPublish), res.opt.blockKeys); - rpc.writeLoginBlock(blockRequest, waitFor(function (e) { if (e) { console.error(e); + waitFor.abort(); return void cb(e); } + })); + }).nThen(function (waitFor) { + // confirm that the block was actually written before considering registration successful + Util.fetch(blockUrl, waitFor(function (err /*, block */) { + if (err) { + console.error(err); + waitFor.abort(); + return void cb(err); + } console.log("blockInfo available at:", blockHash); LocalStore.setBlockHash(blockHash); diff --git a/customize.dist/main.js b/customize.dist/main.js index 44ef51d0d..5969c6c71 100644 --- a/customize.dist/main.js +++ b/customize.dist/main.js @@ -12,7 +12,7 @@ define([ // Make sure we don't display non-translated content (empty button) $main.find('#data').removeClass('hidden'); - if (LocalStore.isLoggedIn()) { + if (LocalStore.isLoggedIn() && LocalStore.getDriveRedirectPreference()) { if (window.location.pathname === '/') { window.location = '/drive/'; return; diff --git a/customize.dist/messages.js b/customize.dist/messages.js index 977405db1..7d9af710a 100755 --- a/customize.dist/messages.js +++ b/customize.dist/messages.js @@ -9,6 +9,7 @@ var map = { 'fr': 'Français', //'hi': 'हिन्दी', 'it': 'Italiano', + 'ja': '日本語', 'nb': 'Norwegian Bokmål', //'pl': 'Polski', 'pt-br': 'Português do Brasil', diff --git a/customize.dist/old_logos/CryptPad-white-logo.svg b/customize.dist/old_logos/CryptPad-white-logo.svg deleted file mode 100644 index 26131b502..000000000 --- a/customize.dist/old_logos/CryptPad-white-logo.svg +++ /dev/null @@ -1 +0,0 @@ - \ No newline at end of file diff --git a/customize.dist/old_logos/CryptPad_logo_color.svg b/customize.dist/old_logos/CryptPad_logo_color.svg deleted file mode 100644 index 64fc86682..000000000 --- a/customize.dist/old_logos/CryptPad_logo_color.svg +++ /dev/null @@ -1 +0,0 @@ -CryptPad_logo_color \ No newline at end of file diff --git a/customize.dist/old_logos/CryptPadlogo_op5.svg b/customize.dist/old_logos/CryptPadlogo_op5.svg deleted file mode 100644 index aa5acb201..000000000 --- a/customize.dist/old_logos/CryptPadlogo_op5.svg +++ /dev/null @@ -1 +0,0 @@ -CryptPadlogo \ No newline at end of file diff --git a/customize.dist/old_logos/cryptofist_mini.png b/customize.dist/old_logos/cryptofist_mini.png deleted file mode 100644 index 73845e455..000000000 Binary files a/customize.dist/old_logos/cryptofist_mini.png and /dev/null differ diff --git a/customize.dist/old_logos/cryptofist_small.png b/customize.dist/old_logos/cryptofist_small.png deleted file mode 100644 index 9c818eb45..000000000 Binary files a/customize.dist/old_logos/cryptofist_small.png and /dev/null differ diff --git a/customize.dist/old_logos/cryptpad-new-logo-colors-logoonly.png b/customize.dist/old_logos/cryptpad-new-logo-colors-logoonly.png deleted file mode 100644 index 722438d54..000000000 Binary files a/customize.dist/old_logos/cryptpad-new-logo-colors-logoonly.png and /dev/null differ diff --git a/customize.dist/pages.js b/customize.dist/pages.js index e3ae2b83e..18d65c680 100644 --- a/customize.dist/pages.js +++ b/customize.dist/pages.js @@ -43,6 +43,17 @@ define([ return Pages.externalLink(el, Pages.localizeDocsLink(href)); }; + var accounts = Pages.accounts = { + donateURL: AppConfig.donateURL || "https://opencollective.com/cryptpad/", + upgradeURL: AppConfig.upgradeURL + }; + + Pages.areSubscriptionsAllowed = function () { + try { + return ApiConfig.allowSubscriptions && accounts.upgradeURL && !ApiConfig.restrictRegistration; + } catch (err) { return void console.error(err); } + }; + var languageSelector = function () { var options = []; var languages = Msg._languages; @@ -94,7 +105,7 @@ define([ var imprintUrl = AppConfig.imprint && (typeof(AppConfig.imprint) === "boolean" ? '/imprint.html' : AppConfig.imprint); - Pages.versionString = "v4.5.0"; + Pages.versionString = "v4.9.0"; // used for the about menu @@ -133,7 +144,7 @@ define([ footerCol('footer_product', [ footLink('/what-is-cryptpad.html', 'topbar_whatIsCryptpad'), Pages.docsLink, - footLink('/features.html', 'pricing'), + footLink('/features.html', Pages.areSubscriptionsAllowed()? 'pricing': 'features'), // Messages.pricing, Messages.features Pages.githubLink, footLink('https://opencollective.com/cryptpad/contribute/', 'footer_donate'), ]), @@ -204,7 +215,7 @@ define([ h('div.collapse.navbar-collapse.justify-content-end#menuCollapse', [ h('a.nav-item.nav-link', { href: '/what-is-cryptpad.html'}, Msg.about), h('a.nav-item.nav-link', { href: 'https://docs.cryptpad.fr'}, Msg.docs_link), - h('a.nav-item.nav-link', { href: '/features.html'}, Msg.pricing), + h('a.nav-item.nav-link', { href: '/features.html'}, Pages.areSubscriptionsAllowed()? Msg.pricing: Msg.features), ].concat(rightLinks)) ); }; diff --git a/customize.dist/pages/features.js b/customize.dist/pages/features.js index ee82d5d67..1dfd2417f 100644 --- a/customize.dist/pages/features.js +++ b/customize.dist/pages/features.js @@ -8,10 +8,7 @@ define([ '/api/config', '/common/common-ui-elements.js', ], function ($, h, Msg, AppConfig, LocalStore, Pages, Config, UIElements) { - var accounts = { - donateURL: AppConfig.donateURL || "https://opencollective.com/cryptpad/", - upgradeURL: AppConfig.upgradeURL - }; + var accounts = Pages.accounts; return function () { Msg.features_f_apps_note = AppConfig.availablePadTypes.map(function (app) { @@ -145,10 +142,11 @@ define([ ]), ]), ]); - var availableFeatures = - (Config.allowSubscriptions && accounts.upgradeURL && !Config.restrictRegistration) ? - [anonymousFeatures, registeredFeatures, premiumFeatures] : - [anonymousFeatures, registeredFeatures]; + var availableFeatures = [ + anonymousFeatures, + registeredFeatures, + Pages.areSubscriptionsAllowed() ? premiumFeatures: undefined, + ]; return h('div#cp-main', [ Pages.infopageTopbar(), diff --git a/customize.dist/pages/index.js b/customize.dist/pages/index.js index 3257126e9..8ea334667 100644 --- a/customize.dist/pages/index.js +++ b/customize.dist/pages/index.js @@ -31,7 +31,7 @@ define([ [ 'code', Msg.type.code], [ 'slide', Msg.type.slide], [ 'sheet', Msg.type.sheet], - [ 'poll', Msg.type.poll], + [ 'form', Msg.type.form], [ 'kanban', Msg.type.kanban], [ 'whiteboard', Msg.type.whiteboard], [ 'drive', Msg.type.drive] diff --git a/customize.dist/src/less2/include/colortheme-dark.less b/customize.dist/src/less2/include/colortheme-dark.less index 588d1888e..5c1649850 100644 --- a/customize.dist/src/less2/include/colortheme-dark.less +++ b/customize.dist/src/less2/include/colortheme-dark.less @@ -10,6 +10,7 @@ code: #EAA000; slide: #e57614; poll: #2c9e98; + form: #2c9e98; whiteboard: #a72ba7; kanban: #8C4; sheet: #40865c; @@ -52,7 +53,7 @@ @cryptpad_color_light_blue: #00b7d8; @cryptpad_color_red: #ff1100; @cryptpad_color_red_fade: fade(@cryptpad_color_red, 50%); -@cryptpad_color_red_fader: fade(@cryptpad_color_red, 25%); +@cryptpad_color_red_fader: fade(@cryptpad_color_red, 15%); @cryptpad_color_warn_red: @cryptpad_color_red_fade; @cryptpad_color_dark_red: #9e0000; @cryptpad_color_light_red: #FFD4D4; @@ -63,7 +64,8 @@ @cryptpad_color_light_green: #c5ffa8; @cryptpad_color_light_green_fade: fade(@cryptpad_color_light_green, 20%); @cryptpad_color_light_yellow: #FFE69C; -@cryptpad_color_yellow_fade: fade(#FFE69C, 15%); +@cryptpad_color_yellow_fade: fade(@cryptpad_color_light_yellow, 50%); +@cryptpad_color_yellow_fader: fade(#FFE69C, 15%); // not in light theme @cryptpad_color_lighter_blue: #d2e1f2; @cryptpad_color_link:@cryptpad_color_brand_300; @@ -114,7 +116,7 @@ @cp_forms-disabled: @cryptpad_color_grey_500; // Bootstrap alerts -@cp_alerts-warning-bg: @cryptpad_color_yellow_fade; +@cp_alerts-warning-bg: @cryptpad_color_yellow_fader; @cp_alerts-warning-fg: @cryptpad_color_light_yellow; @cp_alerts-warning-text: @cryptpad_color_light_yellow; @cp_alerts-danger-bg: @cryptpad_color_red_fader; @@ -426,3 +428,13 @@ @cp_calendar-now: @cryptpad_color_brand_300; @cp_calendar-now-fg: @cryptpad_color_grey_800; +// Forms +@cp_form-bg1: @cryptpad_color_grey_800; +@cp_form-bg2: @cryptpad_color_grey_900; +@cp_form-border: @cryptpad_color_grey_800; +@cp_form-poll-color: @cryptpad_color_grey_800; +@cp_form-poll-no: fade(@cryptpad_color_red, 25%); +@cp_form-poll-yes: fade(@cryptpad_color_green, 25%); +@cp_form-poll-maybe: @cryptpad_color_grey_700; +@cp_form-poll-yes-color: @cryptpad_color_green; +@cp_form-invalid: @cryptpad_color_light_red; diff --git a/customize.dist/src/less2/include/colortheme.less b/customize.dist/src/less2/include/colortheme.less index 3ab249f9f..18dcb1c0a 100644 --- a/customize.dist/src/less2/include/colortheme.less +++ b/customize.dist/src/less2/include/colortheme.less @@ -10,6 +10,7 @@ code: #EAA000; slide: #e57614; poll: #2c9e98; + form: #2c9e98; whiteboard: #a72ba7; kanban: #8C4; sheet: #40865c; @@ -52,7 +53,7 @@ @cryptpad_color_light_blue: #00b7d8; @cryptpad_color_red: #ff1100; @cryptpad_color_red_fade: fade(@cryptpad_color_red, 50%); -@cryptpad_color_red_fader: fade(@cryptpad_color_red, 25%); +@cryptpad_color_red_fader: fade(@cryptpad_color_red, 15%); @cryptpad_color_warn_red: @cryptpad_color_red_fade; @cryptpad_color_dark_red: #9e0000; @cryptpad_color_light_red: #FFD4D4; @@ -425,3 +426,14 @@ @cp_calendar-border: @cryptpad_color_grey_300; @cp_calendar-now: @cryptpad_color_brand; @cp_calendar-now-fg: @cryptpad_color_grey_200; + +// Forms +@cp_form-bg1: @cryptpad_color_grey_200; +@cp_form-bg2: @cryptpad_color_grey_100; +@cp_form-border: @cryptpad_color_grey_200; +@cp_form-poll-color: @cryptpad_color_grey_800; +@cp_form-poll-no: fade(@cryptpad_color_light_red, 75%); +@cp_form-poll-yes: fade(@cryptpad_color_light_green, 75%); +@cp_form-poll-maybe: @cryptpad_color_grey_300; +@cp_form-poll-yes-color: @cryptpad_color_green; +@cp_form-invalid: @cryptpad_color_red; diff --git a/customize.dist/src/less2/include/forms.less b/customize.dist/src/less2/include/forms.less index ffe061fa3..4fb799e13 100644 --- a/customize.dist/src/less2/include/forms.less +++ b/customize.dist/src/less2/include/forms.less @@ -71,6 +71,12 @@ div.cp-button-confirm { display: inline-block; + &.new { + vertical-align: top; + button { + height: 35px; + } + } button { margin: 0 !important; } @@ -85,7 +91,7 @@ } } } - button.cp-button-confirm-placeholder { + button.cp-button-confirm-placeholder:not(.new) { margin-bottom: 3px !important; } diff --git a/customize.dist/src/less2/include/markdown.less b/customize.dist/src/less2/include/markdown.less index 717b49990..43732187a 100644 --- a/customize.dist/src/less2/include/markdown.less +++ b/customize.dist/src/less2/include/markdown.less @@ -154,6 +154,38 @@ color: @cp_markdown-block-fg; text-align: left; } + + div.cp-inline-img-warning { + display: inline-block; + padding: 10px; + color: @cryptpad_text_col; + background-color: @cryptpad_color_red_fader; + border: 1px solid @cryptpad_color_red; + .cp-inline-img { + display: flex; + margin-bottom: 10px; + } + .cp-alt-txt { + margin-left: 10px; + font-family: monospace; + font-size: 0.8em; + color: fade(@cryptpad_text_col, 90%); + } + a { + color: @cryptpad_text_col; + font-size: 0.8em; + &.cp-remote-img::before { // .fa.fa-question-circle + font-family: FontAwesome; + //content: "\f08e\00a0"; + content: "\f08e\00a0\00a0"; + } + &.cp-learn-more::before { // .fa.fa-external-link + font-family: FontAwesome; + content: "\f059\00a0"; + //content: "\f059\00a0\00a0"; + } + } + } } .markdown_cryptpad() { @@ -194,7 +226,7 @@ pre > code { display: block; position: relative; - width: 90%; + width: 100%; margin: auto; padding: 5px; overflow-x: auto; diff --git a/customize.dist/src/less2/include/modals-ui-elements.less b/customize.dist/src/less2/include/modals-ui-elements.less index 92fef68d0..7ec19a699 100644 --- a/customize.dist/src/less2/include/modals-ui-elements.less +++ b/customize.dist/src/less2/include/modals-ui-elements.less @@ -221,6 +221,9 @@ button { line-height: 1.5; } + img { + align-self: center; + } & > iframe { width: 100%; height: 100%; diff --git a/customize.dist/src/less2/pages/page-report.less b/customize.dist/src/less2/pages/page-report.less index bd2cd6c60..220240237 100644 --- a/customize.dist/src/less2/pages/page-report.less +++ b/customize.dist/src/less2/pages/page-report.less @@ -12,6 +12,18 @@ html, body { background-color: @cp_static-bg !important; color: @cryptpad_text_col; font-family: "IBM Plex Mono"; + + #cp-report, #cp-report-ui { + max-width: 900px; + margin: auto; + padding: 15px; + } + #cp-report { + border: 1px solid @cryptpad_text_col; + } + #cp-report-ui { + text-align: right; + } } diff --git a/docs/example.nginx.conf b/docs/example.nginx.conf index 78e4f30ce..8bc47d9f8 100644 --- a/docs/example.nginx.conf +++ b/docs/example.nginx.conf @@ -64,7 +64,7 @@ server { add_header Permissions-Policy interest-cohort=(); set $coop ''; - if ($uri ~ ^\/(sheet|presentation|doc)\/.*$) { set $coop 'same-origin'; } + if ($uri ~ ^\/(sheet|presentation|doc|convert)\/.*$) { set $coop 'same-origin'; } # Enable SharedArrayBuffer in Firefox (for .xlsx export) add_header Cross-Origin-Resource-Policy cross-origin; @@ -167,6 +167,13 @@ server { proxy_set_header X-Real-IP $remote_addr; proxy_set_header Host $host; proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; + + # These settings prevent both NGINX and the API server + # from setting the same headers and creating duplicates + proxy_hide_header Cross-Origin-Resource-Policy; + add_header Cross-Origin-Resource-Policy cross-origin; + proxy_hide_header Cross-Origin-Embedder-Policy; + add_header Cross-Origin-Embedder-Policy require-corp; } # encrypted blobs are immutable and are thus cached for a year @@ -207,7 +214,7 @@ server { # The nodejs server has some built-in forwarding rules to prevent # URLs like /pad from resulting in a 404. This simply adds a trailing slash # to a variety of applications. - location ~ ^/(register|login|settings|user|pad|drive|poll|slide|code|whiteboard|file|media|profile|contacts|todo|filepicker|debug|kanban|sheet|support|admin|notifications|teams|calendar|presentation|doc)$ { + location ~ ^/(register|login|settings|user|pad|drive|poll|slide|code|whiteboard|file|media|profile|contacts|todo|filepicker|debug|kanban|sheet|support|admin|notifications|teams|calendar|presentation|doc|form|report|convert)$ { rewrite ^(.*)$ $1/ redirect; } diff --git a/lib/api.js b/lib/api.js index 7152f75b9..277d085fa 100644 --- a/lib/api.js +++ b/lib/api.js @@ -10,6 +10,7 @@ module.exports.create = function (Env) { nThen(function (w) { Decrees.load(Env, w(function (err) { + Env.flushCache(); if (err) { log.error('DECREES_LOADING', { error: err.code || err, diff --git a/lib/commands/admin-rpc.js b/lib/commands/admin-rpc.js index 9ab86bdf2..59750571e 100644 --- a/lib/commands/admin-rpc.js +++ b/lib/commands/admin-rpc.js @@ -317,6 +317,16 @@ var instanceStatus = function (Env, Server, cb) { maxUploadSize: Env.maxUploadSize, premiumUploadSize: Env.premiumUploadSize, + + consentToContact: Env.consentToContact, + listMyInstance: Env.listMyInstance, + provideAggregateStatistics: Env.provideAggregateStatistics, + + removeDonateButton: Env.removeDonateButton, + blockDailyCheck: Env.blockDailyCheck, + + updateAvailable: Env.updateAvailable, + instancePurpose: Env.instancePurpose, }); }; diff --git a/lib/commands/block.js b/lib/commands/block.js index 8180cb68e..4af32af70 100644 --- a/lib/commands/block.js +++ b/lib/commands/block.js @@ -1,14 +1,10 @@ /*jshint esversion: 6 */ /* globals Buffer*/ -var Block = module.exports; - -const Fs = require("fs"); -const Fse = require("fs-extra"); -const Path = require("path"); +const Block = module.exports; const Nacl = require("tweetnacl/nacl-fast"); const nThen = require("nthen"); - const Util = require("../common-util"); +const BlockStore = require("../storage/block"); /* We assume that the server is secured against MitM attacks @@ -31,7 +27,9 @@ const Util = require("../common-util"); author of the block, since we assume that the block will have been encrypted with xsalsa20-poly1305 which is authenticated. */ -var validateLoginBlock = function (Env, publicKey, signature, block, cb) { // FIXME BLOCKS +Block.validateLoginBlock = function (Env, publicKey, signature, block, _cb) { + var cb = Util.once(Util.mkAsync(_cb)); + // convert the public key to a Uint8Array and validate it if (typeof(publicKey) !== 'string') { return void cb('E_INVALID_KEY'); } @@ -69,21 +67,7 @@ var validateLoginBlock = function (Env, publicKey, signature, block, cb) { // FI // call back with (err) if unsuccessful if (!verified) { return void cb("E_COULD_NOT_VERIFY"); } - return void cb(null, u8_block); -}; - -var createLoginBlockPath = function (Env, publicKey) { // FIXME BLOCKS - // prepare publicKey to be used as a file name - var safeKey = Util.escapeKeyCharacters(publicKey); - - // validate safeKey - if (typeof(safeKey) !== 'string') { - return; - } - - // derive the full path - // /home/cryptpad/cryptpad/block/fg/fg32kefksjdgjkewrjksdfksjdfsdfskdjfsfd - return Path.join(Env.paths.block, safeKey.slice(0, 2), safeKey); + return void cb(null, block); }; Block.validateAncestorProof = function (Env, proof, _cb) { @@ -103,31 +87,26 @@ Block.validateAncestorProof = function (Env, proof, _cb) { return void cb('E_INVALID_ANCESTOR_PROOF'); } // else fall through to next step - }).nThen(function (w) { - var path = createLoginBlockPath(Env, pub); - Fs.access(path, Fs.constants.F_OK, w(function (err) { - if (!err) { return; } - w.abort(); // else - return void cb("E_MISSING_ANCESTOR"); - })); }).nThen(function () { - cb(void 0, pub); + BlockStore.check(Env, pub, function (err) { + if (err) { return void cb('E_MISSING_ANCESTOR'); } + cb(void 0, pub); + }); }); } catch (err) { return void cb(err); } }; -Block.writeLoginBlock = function (Env, safeKey, msg, _cb) { // FIXME BLOCKS +Block.writeLoginBlock = function (Env, safeKey, msg, _cb) { var cb = Util.once(Util.mkAsync(_cb)); - //console.log(msg); var publicKey = msg[0]; var signature = msg[1]; var block = msg[2]; var registrationProof = msg[3]; var previousKey; - var validatedBlock, parsed, path; + var validatedBlock, path; nThen(function (w) { if (Util.escapeKeyCharacters(publicKey) !== safeKey) { w.abort(); @@ -156,44 +135,26 @@ Block.writeLoginBlock = function (Env, safeKey, msg, _cb) { // FIXME BLOCKS previousKey = provenKey; })); }).nThen(function (w) { - validateLoginBlock(Env, publicKey, signature, block, w(function (e, _validatedBlock) { + Env.validateLoginBlock(publicKey, signature, block, w(function (e, _validatedBlock) { if (e) { w.abort(); return void cb(e); } - if (!(_validatedBlock instanceof Uint8Array)) { + if (typeof(_validatedBlock) !== 'string') { w.abort(); - return void cb('E_INVALID_BLOCK'); + return void cb('E_INVALID_BLOCK_RETURNED'); } validatedBlock = _validatedBlock; - - // derive the filepath - path = createLoginBlockPath(Env, publicKey); - - // make sure the path is valid - if (typeof(path) !== 'string') { - return void cb('E_INVALID_BLOCK_PATH'); - } - - parsed = Path.parse(path); - if (!parsed || typeof(parsed.dir) !== 'string') { - w.abort(); - return void cb("E_INVALID_BLOCK_PATH_2"); - } - })); - }).nThen(function (w) { - // make sure the path to the file exists - Fse.mkdirp(parsed.dir, w(function (e) { - if (e) { - w.abort(); - cb(e); - } })); }).nThen(function () { - // actually write the block - Fs.writeFile(path, Buffer.from(validatedBlock), { encoding: "binary", }, function (err) { - if (err) { return void cb(err); } + var buffer; + try { + buffer = Buffer.from(Nacl.util.decodeBase64(validatedBlock)); + } catch (err) { + return void cb('E_BLOCK_DESERIALIZATION'); + } + BlockStore.write(Env, publicKey, buffer, function (err) { Env.Log.info('BLOCK_WRITE_BY_OWNER', { safeKey: safeKey, blockId: publicKey, @@ -201,11 +162,13 @@ Block.writeLoginBlock = function (Env, safeKey, msg, _cb) { // FIXME BLOCKS previousKey: previousKey, path: path, }); - cb(); + cb(err); }); }); }; +const DELETE_BLOCK = Nacl.util.encodeBase64(Nacl.util.decodeUTF8('DELETE_BLOCK')); + /* When users write a block, they upload the block, and provide a signature proving that they deserve to be able to write to @@ -216,10 +179,11 @@ Block.writeLoginBlock = function (Env, safeKey, msg, _cb) { // FIXME BLOCKS information, we can just sign some constant and use that as proof. */ -Block.removeLoginBlock = function (Env, safeKey, msg, cb) { // FIXME BLOCKS +Block.removeLoginBlock = function (Env, safeKey, msg, _cb) { + var cb = Util.once(Util.mkAsync(_cb)); + var publicKey = msg[0]; var signature = msg[1]; - var block = Nacl.util.decodeUTF8('DELETE_BLOCK'); // clients and the server will have to agree on this constant nThen(function (w) { if (Util.escapeKeyCharacters(publicKey) !== safeKey) { @@ -227,26 +191,14 @@ Block.removeLoginBlock = function (Env, safeKey, msg, cb) { // FIXME BLOCKS return void cb("INCORRECT_KEY"); } }).nThen(function () { - validateLoginBlock(Env, publicKey, signature, block, function (e /*::, validatedBlock */) { + Env.validateLoginBlock(publicKey, signature, DELETE_BLOCK, function (e) { if (e) { return void cb(e); } - // derive the filepath - var path = createLoginBlockPath(Env, publicKey); - - // make sure the path is valid - if (typeof(path) !== 'string') { - return void cb('E_INVALID_BLOCK_PATH'); - } - - // FIXME COLDSTORAGE - Fs.unlink(path, function (err) { - Env.Log.info('DELETION_BLOCK_BY_OWNER_RPC', { + BlockStore.archive(Env, publicKey, function (err) { + Env.Log.info('ARCHIVAL_BLOCK_BY_OWNER_RPC', { publicKey: publicKey, - path: path, status: err? String(err): 'SUCCESS', }); - - if (err) { return void cb(err); } - cb(); + cb(err); }); }); }); diff --git a/lib/commands/pin-rpc.js b/lib/commands/pin-rpc.js index 93d922620..89afc4ee8 100644 --- a/lib/commands/pin-rpc.js +++ b/lib/commands/pin-rpc.js @@ -8,7 +8,7 @@ const nThen = require("nthen"); //const escapeKeyCharacters = Util.escapeKeyCharacters; const unescapeKeyCharacters = Util.unescapeKeyCharacters; -var sumChannelSizes = function (sizes) { +var sumChannelSizes = function (sizes) { // FIXME this synchronous code could be done by a worker return Object.keys(sizes).map(function (id) { return sizes[id]; }) .filter(function (x) { // only allow positive numbers @@ -115,8 +115,8 @@ Pinning.getTotalSize = function (Env, safeKey, cb) { */ Pinning.removePins = function (Env, safeKey, cb) { // FIXME respect the queue - Env.pinStore.removeChannel(safeKey, function (err) { - Env.Log.info('DELETION_PIN_BY_OWNER_RPC', { + Env.pinStore.archiveChannel(safeKey, function (err) { + Env.Log.info('ARCHIVAL_PIN_BY_OWNER_RPC', { safeKey: safeKey, status: err? String(err): 'SUCCESS', }); @@ -145,7 +145,7 @@ var getFreeSpace = Pinning.getFreeSpace = function (Env, safeKey, cb) { }); }; -var getHash = Pinning.getHash = function (Env, safeKey, cb) { +Pinning.getHash = function (Env, safeKey, cb) { getChannelList(Env, safeKey, function (channels) { Env.hashChannelList(channels, cb); }); @@ -166,12 +166,12 @@ Pinning.pinChannel = function (Env, safeKey, channels, cb) { }); if (toStore.length === 0) { - return void getHash(Env, safeKey, cb); + return void cb(); } getMultipleFileSize(Env, toStore, function (e, sizes) { if (typeof(sizes) === 'undefined') { return void cb(e); } - var pinSize = sumChannelSizes(sizes); + var pinSize = sumChannelSizes(sizes); // FIXME don't do this in the main thread... getFreeSpace(Env, safeKey, function (e, free) { if (typeof(free) === 'undefined') { @@ -186,7 +186,7 @@ Pinning.pinChannel = function (Env, safeKey, channels, cb) { toStore.forEach(function (channel) { session.channels[channel] = true; }); - getHash(Env, safeKey, cb); + cb(); }); }); }); @@ -208,7 +208,7 @@ Pinning.unpinChannel = function (Env, safeKey, channels, cb) { }); if (toStore.length === 0) { - return void getHash(Env, safeKey, cb); + return void cb(); } Env.pinStore.message(safeKey, JSON.stringify(['UNPIN', toStore, +new Date()]), @@ -217,20 +217,19 @@ Pinning.unpinChannel = function (Env, safeKey, channels, cb) { toStore.forEach(function (channel) { delete session.channels[channel]; }); - getHash(Env, safeKey, cb); + cb(); }); }); }; -Pinning.resetUserPins = function (Env, safeKey, channelList, cb) { +Pinning.resetUserPins = function (Env, safeKey, channelList, _cb) { + var cb = Util.once(Util.mkAsync(_cb)); if (!Array.isArray(channelList)) { return void cb('INVALID_PIN_LIST'); } var session = Core.getSession(Env.Sessions, safeKey); + if (!channelList.length) { - return void getHash(Env, safeKey, function (e, hash) { - if (e) { return cb(e); } - cb(void 0, hash); - }); + return void cb(); } var pins = {}; @@ -270,9 +269,7 @@ Pinning.resetUserPins = function (Env, safeKey, channelList, cb) { // update in-memory cache IFF the reset was allowed. session.channels = pins; - getHash(Env, safeKey, function (e, hash) { - cb(e, hash); - }); + cb(); }); }); }); diff --git a/lib/commands/quota.js b/lib/commands/quota.js index b779d8e56..1bf9203f6 100644 --- a/lib/commands/quota.js +++ b/lib/commands/quota.js @@ -4,9 +4,9 @@ const Quota = module.exports; //const Util = require("../common-util"); const Keys = require("../keys"); -const Package = require('../../package.json'); const Https = require("https"); const Util = require("../common-util"); +const Stats = require("../stats"); var validLimitFields = ['limit', 'plan', 'note', 'users', 'origin']; @@ -51,24 +51,66 @@ Quota.applyCustomLimits = function (Env) { // console.log(Env.limits); }; +var isRemoteVersionNewer = function (local, remote) { + try { + local = local.split('.').map(Number); + remote = remote.split('.').map(Number); + for (var i = 0; i < 3; i++) { + if (remote[i] < local[i]) { return false; } + if (remote[i] > local[i]) { return true; } + } + } catch (err) { + // if anything goes wrong just fall through and return false + // false negatives are better than false positives + } + return false; +}; + /* -Env = { - myDomain, - mySubdomain, - adminEmail, - Package.version, +var Assert = require("assert"); +[ +// remote versions + ['4.5.0', '4.5.0', false], // equal semver should not prompt + ['4.5.0', '4.5.1', true], // patch versions should prompt + ['4.5.0', '4.6.0', true], // minor versions should prompt + ['4.5.0', '5.0.0', true], // major versions should prompt +// local + ['5.3.1', '4.9.0', false], // newer major should not prompt + ['4.7.0', '4.6.0', false], // newer minor should not prompt + ['4.7.0', '4.6.1', false], // newer patch should not prompt if other values are greater +].forEach(function (x) { + var result = isRemoteVersionNewer(x[0], x[1]); + Assert.equal(result, x[2]); +}); +*/ +// check if the remote endpoint reported an available server version +// which is newer than your current version (Env.version) +// if so, set Env.updateAvailable to the URL of its release notes +var checkUpdateAvailability = function (Env, json) { + if (!(json && typeof(json.updateAvailable) === 'string' && typeof(json.version) === 'string')) { return; } + // expects {updateAvailable: 'https://github.com/xwiki-labs/cryptpad/releases/4.7.0', version: '4.7.0'} + // the version string is provided explicitly even though it could be parsed from GitHub's URL + // this will allow old instances to understand responses of arbitrary URLs + // as long as we keep using semver for 'version' + if (!isRemoteVersionNewer(Env.version, json.version)) { + Env.updateAvailable = undefined; + return; + } + Env.updateAvailable = json.updateAvailable; + Env.Log.info('AN_UPDATE_IS_AVAILABLE', { + version: json.version, + updateAvailable: json.updateAvaiable, + }); }; -*/ + var queryAccountServer = function (Env, cb) { var done = Util.once(Util.mkAsync(cb)); - var body = JSON.stringify({ - domain: Env.myDomain, - subdomain: Env.mySubdomain || null, - adminEmail: Env.adminEmail, - version: Package.version - }); + var rawBody = Stats.instanceData(Env); + Env.Log.info("SERVER_TELEMETRY", rawBody); + var body = JSON.stringify(rawBody); + var options = { host: 'accounts.cryptpad.fr', path: '/api/getauthorized', @@ -92,6 +134,7 @@ var queryAccountServer = function (Env, cb) { response.on('end', function () { try { var json = JSON.parse(str); + checkUpdateAvailability(Env, json); // don't overwrite the limits with junk data if (json && json.message === 'EINVAL') { return void cb(); } done(void 0, json); diff --git a/lib/decrees.js b/lib/decrees.js index eed840057..5f599705e 100644 --- a/lib/decrees.js +++ b/lib/decrees.js @@ -34,6 +34,13 @@ SET_MAINTENANCE SET_ADMIN_EMAIL SET_SUPPORT_MAILBOX +// COMMUNITY PARTICIPATION AND GOVERNANCE +CONSENT_TO_CONTACT +LIST_MY_INSTANCE +PROVIDE_AGGREGATE_STATISTICS +REMOVE_DONATE_BUTTON +BLOCK_DAILY_CHECK + NOT IMPLEMENTED: // RESTRICTED REGISTRATION @@ -89,6 +96,21 @@ commands.DISABLE_INTEGRATED_EVICTION = makeBooleanSetter('disableIntegratedEvict // CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['DISABLE_INTEGRATED_TASKS', [true]]], console.log) commands.DISABLE_INTEGRATED_TASKS = makeBooleanSetter('disableIntegratedTasks'); +// CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['CONSENT_TO_CONTACT', [true]]], console.log) +commands.CONSENT_TO_CONTACT = makeBooleanSetter('consentToContact'); + +// CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['LIST_MY_INSTANCE', [true]]], console.log) +commands.LIST_MY_INSTANCE = makeBooleanSetter('listMyInstance'); + +// CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['PROVIDE_AGGREGATE_STATISTICS', [true]]], console.log) +commands.PROVIDE_AGGREGATE_STATISTICS = makeBooleanSetter('provideAggregateStatistics'); + +// CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['REMOVE_DONATE_BUTTON', [true]]], console.log) +commands.REMOVE_DONATE_BUTTON = makeBooleanSetter('removeDonateButton'); + +// CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['BLOCK_DAILY_CHECK', [true]]], console.log) +commands.BLOCK_DAILY_CHECK = makeBooleanSetter('blockDailyCheck'); + /* var isNonNegativeNumber = function (n) { return !(typeof(n) !== 'number' || isNaN(n) || n < 0); @@ -151,6 +173,9 @@ commands.SET_SUPPORT_MAILBOX = makeGenericSetter('supportMailbox', function (arg return args_isString(args) && Core.isValidPublicKey(args[0]); }); +// CryptPad_AsyncStore.rpc.send('ADMIN', [ 'ADMIN_DECREE', ['SET_INSTANCE_PURPOSE', ["development"]]], console.log) +commands.SET_INSTANCE_PURPOSE = makeGenericSetter('instancePurpose', args_isString); + // Maintenance: Empty string or an object with a start and end time var isNumber = function (value) { return typeof(value) === "number" && !isNaN(value); diff --git a/lib/env.js b/lib/env.js index 389f059f6..4db282d77 100644 --- a/lib/env.js +++ b/lib/env.js @@ -10,10 +10,22 @@ const Core = require("./commands/core"); const Quota = require("./commands/quota"); const Util = require("./common-util"); +const Package = require("../package.json"); -module.exports.create = function (config) { +var canonicalizeOrigin = function (s) { + if (typeof(s) === 'undefined') { return; } + return (s || '').trim().replace(/\/+$/, ''); +}; +module.exports.create = function (config) { const Env = { + version: Package.version, + installMethod: config.installMethod || undefined, + + httpUnsafeOrigin: canonicalizeOrigin(config.httpUnsafeOrigin), + httpSafeOrigin: canonicalizeOrigin(config.httpSafeOrigin), + removeDonateButton: config.removeDonateButton, + OFFLINE_MODE: false, FRESH_KEY: '', FRESH_MODE: true, @@ -97,6 +109,11 @@ module.exports.create = function (config) { allowSubscriptions: config.allowSubscriptions === true, blockDailyCheck: config.blockDailyCheck === true, + consentToContact: false, + listMyInstance: false, + provideAggregateStatistics: false, + updateAvailable: undefined, + myDomain: config.myDomain, mySubdomain: config.mySubdomain, // only exists for the accounts integration customLimits: {}, @@ -106,7 +123,7 @@ module.exports.create = function (config) { maxWorkers: config.maxWorkers, disableIntegratedTasks: config.disableIntegratedTasks || false, - disableIntegratedEviction: config.disableIntegratedEviction || false, + disableIntegratedEviction: typeof(config.disableIntegratedEviction) === 'undefined'? true: config.disableIntegratedEviction, // XXX 4.10.0 false, lastEviction: +new Date(), evictionReport: {}, commandTimers: {}, diff --git a/lib/historyKeeper.js b/lib/historyKeeper.js index daa041b5f..44afe0ae0 100644 --- a/lib/historyKeeper.js +++ b/lib/historyKeeper.js @@ -123,6 +123,8 @@ module.exports.create = function (Env, cb) { Store.create({ filePath: pinPath, archivePath: Env.paths.archive, + // indicate that archives should be put in a 'pins' archvie folder + volumeId: 'pins', }, w(function (err, s) { if (err) { throw err; } Env.pinStore = s; diff --git a/lib/hk-util.js b/lib/hk-util.js index 7c244c174..276ac3e6f 100644 --- a/lib/hk-util.js +++ b/lib/hk-util.js @@ -701,6 +701,7 @@ const handleGetHistory = function (Env, Server, seq, userId, parsed) { } if (msgCount === 0 && !metadata_cache[channelName] && Server.channelContainsUser(channelName, userId)) { + // TODO this might be a good place to reject channel creation by anonymous users handleFirstMessage(Env, channelName, metadata); Server.send(userId, [0, HISTORY_KEEPER_ID, 'MSG', userId, JSON.stringify(metadata)]); } @@ -962,7 +963,11 @@ HK.onChannelMessage = function (Env, Server, channel, msgStruct, cb) { // validation can fail in multiple ways if (err === 'FAILED') { // we log this case, but not others for some reason - Log.info("HK_SIGNED_MESSAGE_REJECTED", 'Channel '+channel.id); + Log.info("HK_SIGNED_MESSAGE_REJECTED", { + channel: channel.id, + validateKey: metadata.validayKey, + message: signedMsg, + }); } // always abort if there was an error... cb('FAILED_VALIDATION'); diff --git a/lib/stats.js b/lib/stats.js new file mode 100644 index 000000000..1dbbb2ad9 --- /dev/null +++ b/lib/stats.js @@ -0,0 +1,68 @@ +/*jshint esversion: 6 */ +const Stats = module.exports; + +Stats.instanceData = function (Env) { + var data = { + version: Env.version, + installMethod: Env.installMethod, + + domain: Env.myDomain, + subdomain: Env.mySubdomain, + + httpUnsafeOrigin: Env.httpUnsafeOrigin, + httpSafeOrigin: Env.httpSafeOrigin, + + adminEmail: Env.consentToContact? Env.adminEmail: undefined, + consentToContact: Boolean(Env.consentToContact), + + instancePurpose: Env.instancePurpose === 'noanswer'? undefined: Env.instancePurpose, + }; + +/* We reserve the right to choose not to include instances + in our public directory at our discretion. + + The following details will be included in your telemetry + as factors that may contribute to that decision. + + These values are publicly available via /api/config + posting them to our server just makes it easier for us. +*/ + if (Env.listMyInstance) { + // clearly indicate that you want to be listed + data.listMyInstance = Env.listMyInstance; + + // you should have enabled your admin panel + data.adminKeys = Env.admins.length > 0; + + // we expect that you enable your support mailbox + data.supportMailbox = Boolean(Env.supportMailbox); + + // do you allow registration? + data.restrictRegistration = Boolean(Env.restrictRegistration); + + // have you removed the donate button? + data.removeDonateButton = Boolean(Env.removeDonateButton); + + // after how long do you consider a document to be inactive? + data.inactiveTime = Env.inactiveTime; + + // how much storage do you offer to registered users? + data.defaultStorageLimit = Env.defaultStorageLimit; + + // what size file upload do you permit + data.maxUploadSize = Env.maxUploadSize; + + // how long do you retain inactive accounts? + data.accountRetentionTime = Env.accountRetentionTime; + + // how long do you retain archived data? + //data.archiveRetentionTime = Env.archiveRetentionTime, + } + + // we won't consider instances for public listings + // unless they opt to provide more info about themselves + if (!Env.provideAggregateStatistics) { return data; } + + return data; +}; + diff --git a/lib/storage/block.js b/lib/storage/block.js new file mode 100644 index 000000000..1078f6d2e --- /dev/null +++ b/lib/storage/block.js @@ -0,0 +1,88 @@ +/*jshint esversion: 6 */ +const Block = module.exports; +const Util = require("../common-util"); +const Path = require("path"); +const Fs = require("fs"); +const Fse = require("fs-extra"); +const nThen = require("nthen"); + +Block.mkPath = function (Env, publicKey) { + // prepare publicKey to be used as a file name + var safeKey = Util.escapeKeyCharacters(publicKey); + + // validate safeKey + if (typeof(safeKey) !== 'string') { return; } + + // derive the full path + // /home/cryptpad/cryptpad/block/fg/fg32kefksjdgjkewrjksdfksjdfsdfskdjfsfd + return Path.join(Env.paths.block, safeKey.slice(0, 2), safeKey); +}; + +Block.mkArchivePath = function (Env, publicKey) { + // prepare publicKey to be used as a file name + var safeKey = Util.escapeKeyCharacters(publicKey); + + // validate safeKey + if (typeof(safeKey) !== 'string') { + return; + } + + // derive the full path + // /home/cryptpad/cryptpad/block/fg/fg32kefksjdgjkewrjksdfksjdfsdfskdjfsfd + return Path.join(Env.paths.archive, 'block', safeKey.slice(0, 2), safeKey); +}; + +Block.archive = function (Env, publicKey, _cb) { + var cb = Util.once(Util.mkAsync(_cb)); + + // derive the filepath + var currentPath = Block.mkPath(Env, publicKey); + + // make sure the path is valid + if (typeof(currentPath) !== 'string') { + return void cb('E_INVALID_BLOCK_PATH'); + } + + var archivePath = Block.mkArchivePath(Env, publicKey); + // make sure the path is valid + if (typeof(archivePath) !== 'string') { + return void cb('E_INVALID_BLOCK_ARCHIVAL_PATH'); + } + + Fse.move(currentPath, archivePath, { + overwrite: true, + }, cb); +}; + +Block.check = function (Env, publicKey, _cb) { // 'check' because 'exists' implies boolean + var cb = Util.once(Util.mkAsync(_cb)); + var path = Block.mkPath(Env, publicKey); + Fs.access(path, Fs.constants.F_OK, cb); +}; + +Block.write = function (Env, publicKey, buffer, _cb) { + var cb = Util.once(Util.mkAsync(_cb)); + var path = Block.mkPath(Env, publicKey); + if (typeof(path) !== 'string') { return void cb('INVALID_PATH'); } + var parsed = Path.parse(path); + + nThen(function (w) { + Fse.mkdirp(parsed.dir, w(function (err) { + if (!err) { return; } + w.abort(); + cb(err); + })); + }).nThen(function (w) { + Block.archive(Env, publicKey, w(function (/* err */) { + /* + we proceed even if there are errors. + it might be ENOENT (there is no file to archive) + or EACCES (bad filesystem permissions for the existing archived block?) + or lots of other things, none of which justify preventing the write + */ + })); + }).nThen(function () { + Fs.writeFile(path, buffer, { encoding: 'binary' }, cb); + }); +}; + diff --git a/lib/storage/file.js b/lib/storage/file.js index 825f14066..30e6c7644 100644 --- a/lib/storage/file.js +++ b/lib/storage/file.js @@ -51,7 +51,7 @@ var mkPath = function (env, channelId) { }; var mkArchivePath = function (env, channelId) { - return Path.join(env.archiveRoot, 'datastore', channelId.slice(0, 2), channelId) + '.ndjson'; + return Path.join(env.archiveRoot, env.volumeId, channelId.slice(0, 2), channelId) + '.ndjson'; }; var mkMetadataPath = function (env, channelId) { @@ -59,7 +59,7 @@ var mkMetadataPath = function (env, channelId) { }; var mkArchiveMetadataPath = function (env, channelId) { - return Path.join(env.archiveRoot, 'datastore', channelId.slice(0, 2), channelId) + '.metadata.ndjson'; + return Path.join(env.archiveRoot, env.volumeId, channelId.slice(0, 2), channelId) + '.metadata.ndjson'; }; var mkTempPath = function (env, channelId) { @@ -1044,6 +1044,9 @@ module.exports.create = function (conf, _cb) { var env = { root: conf.filePath || './datastore', archiveRoot: conf.archivePath || './data/archive', + // supply a volumeId if you want a store to archive channels to and from + // to its own subpath within the archive directory + volumeId: conf.volumeId || 'datastore', channels: { }, batchGetChannel: BatchRead('store_batch_channel'), }; @@ -1076,7 +1079,7 @@ module.exports.create = function (conf, _cb) { } })); // make sure the cold storage directory exists - Fse.mkdirp(env.archiveRoot, PERMISSIVE, w(function (err) { + Fse.mkdirp(Path.join(env.archiveRoot, env.volumeId), PERMISSIVE, w(function (err) { if (err && err.code !== 'EEXIST') { w.abort(); return void cb(err); diff --git a/lib/workers/db-worker.js b/lib/workers/db-worker.js index 8585cc3f6..2371240ec 100644 --- a/lib/workers/db-worker.js +++ b/lib/workers/db-worker.js @@ -66,6 +66,9 @@ const init = function (config, _cb) { Store.create({ filePath: config.pinPath, archivePath: config.archivePath, + // important to initialize the pinstore with its own volume id + // otherwise archived pin logs will get mixed in with channels + volumeId: 'pins', }, w(function (err, _pinStore) { if (err) { w.abort(); @@ -694,6 +697,10 @@ COMMANDS.VALIDATE_ANCESTOR_PROOF = function (data, cb) { Block.validateAncestorProof(Env, data && data.proof, cb); }; +COMMANDS.VALIDATE_LOGIN_BLOCK = function (data, cb) { + Block.validateLoginBlock(Env, data.publicKey, data.signature, data.block, cb); +}; + process.on('message', function (data) { if (!data || !data.txid || !data.pid) { return void process.send({ diff --git a/lib/workers/index.js b/lib/workers/index.js index 85c66eeb5..c2bfb5740 100644 --- a/lib/workers/index.js +++ b/lib/workers/index.js @@ -451,6 +451,15 @@ Workers.initialize = function (Env, config, _cb) { }, cb); }; + Env.validateLoginBlock = function (publicKey, signature, block, cb) { + sendCommand({ + command: 'VALIDATE_LOGIN_BLOCK', + publicKey: publicKey, + signature: signature, + block: block, + }, cb); + }; + cb(void 0); }); }; diff --git a/package-lock.json b/package-lock.json index 75b03cfe1..42136e238 100644 --- a/package-lock.json +++ b/package-lock.json @@ -1,6 +1,6 @@ { "name": "cryptpad", - "version": "4.5.0", + "version": "4.9.0", "lockfileVersion": 1, "requires": true, "dependencies": { @@ -36,15 +36,15 @@ } }, "@types/minimatch": { - "version": "3.0.3", - "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.3.tgz", - "integrity": "sha512-tHq6qdbT9U1IRSGf14CL0pUlULksvY9OZ+5eEgl1N7t+OA3tGvNpxJCzuKQlsNgCVwbAs670L1vcVQi8j9HjnA==", + "version": "3.0.4", + "resolved": "https://registry.npmjs.org/@types/minimatch/-/minimatch-3.0.4.tgz", + "integrity": "sha512-1z8k4wzFnNjVK/tlxvrWuK5WMt6mydWWP7+zvH5eFep4oj+UkrfiJTRtjCeBXNpwaA/FYqqtb4/QS4ianFpIRA==", "dev": true }, "@types/node": { - "version": "14.14.16", - "resolved": "https://registry.npmjs.org/@types/node/-/node-14.14.16.tgz", - "integrity": "sha512-naXYePhweTi+BMv11TgioE2/FXU4fSl29HAH1ffxVciNsH3rYXjNP2yM8wqmSm7jS20gM8TIklKiTen+1iVncw==", + "version": "15.12.2", + "resolved": "https://registry.npmjs.org/@types/node/-/node-15.12.2.tgz", + "integrity": "sha512-zjQ69G564OCIWIOHSXyQEEDpdpGl+G348RAKY0XXy9Z5kU9Vzv1GMNnkar/ZJ8dzXB3COzD9Mo9NtRZ4xfgUww==", "dev": true }, "accepts": { @@ -57,9 +57,9 @@ } }, "ajv": { - "version": "6.12.0", - "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.0.tgz", - "integrity": "sha512-D6gFiFA0RRLyUbvijN74DWAjXSFxWKaWP7mldxkVhyhAV3+SWA9HEJPHQ2c9soIeTFJqcSdFDGFgdqs1iUU2Hw==", + "version": "6.12.6", + "resolved": "https://registry.npmjs.org/ajv/-/ajv-6.12.6.tgz", + "integrity": "sha512-j3fVLgvTo527anyYyJOGTYJbG+vnnQYvE0m5mmkc1TK+nxAppkCLMIL0aZ4dblVCNoGShhm+kzE4ZUykBoMg4g==", "dev": true, "optional": true, "requires": { @@ -187,16 +187,16 @@ "optional": true }, "aws4": { - "version": "1.9.1", - "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.9.1.tgz", - "integrity": "sha512-wMHVg2EOHaMRxbzgFJ9gtjOOCrI80OHLG14rxi28XwOW8ux6IiEbRCGGGqCtdAIg4FQCbW20k9RsT4y3gJlFug==", + "version": "1.11.0", + "resolved": "https://registry.npmjs.org/aws4/-/aws4-1.11.0.tgz", + "integrity": "sha512-xh1Rl34h6Fi1DC2WWKfxUTVqRsNnr6LsKz2+hfwDxQJWmrx8+c7ylaqBMcHfl1U1r2dsifOvKX3LQuLNZ+XSvA==", "dev": true, "optional": true }, "balanced-match": { - "version": "1.0.0", - "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.0.tgz", - "integrity": "sha1-ibTRmasr7kneFk6gK4nORi1xt2c=", + "version": "1.0.2", + "resolved": "https://registry.npmjs.org/balanced-match/-/balanced-match-1.0.2.tgz", + "integrity": "sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==", "dev": true }, "base": { @@ -389,9 +389,9 @@ "optional": true }, "chainpad-crypto": { - "version": "0.2.5", - "resolved": "https://registry.npmjs.org/chainpad-crypto/-/chainpad-crypto-0.2.5.tgz", - "integrity": "sha512-K9vRsAspuX+uU1goXPz0CawpLIaOHq+1JP3WfDLqaz67LbCX/MLIUt9aMcSeIJcwZ9uMpqnbMGRktyVPoz6MCA==", + "version": "0.2.6", + "resolved": "https://registry.npmjs.org/chainpad-crypto/-/chainpad-crypto-0.2.6.tgz", + "integrity": "sha512-yk7bBj22rs9PaX6LiqQxiw+Vj/afBStsNP1xP/B4Uh9a8iyJ7JrSZJ2Hj3d6fyqxJlBrMAX82Aj5PCZb5dzzHw==", "requires": { "tweetnacl": "git+https://github.com/dchest/tweetnacl-js.git#v0.12.2" }, @@ -688,15 +688,15 @@ }, "dependencies": { "domelementtype": { - "version": "2.0.1", - "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.0.1.tgz", - "integrity": "sha512-5HOHUDsYZWV8FGWN0Njbr/Rn7f/eWSQi1v7+HsUVwXgn8nWWlL64zKDkS0n8ZmQ3mlWOMuXOnR+7Nx/5tMO5AQ==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/domelementtype/-/domelementtype-2.2.0.tgz", + "integrity": "sha512-DtBMo82pv1dFtUmHyr48beiuq792Sxohr+8Hm9zoxklYPfa6n0Z3Byjj2IV7bmr2IyqClnqEQhfgHJJ5QF0R5A==", "dev": true }, "entities": { - "version": "2.0.0", - "resolved": "https://registry.npmjs.org/entities/-/entities-2.0.0.tgz", - "integrity": "sha512-D9f7V0JSRwIxlRI2mjMqufDrRDnx8p+eEOz7aUM9SuvF8gsBzra0/6tbjl1m8eQHrZlYj6PxqE00hZ1SAIKPLw==", + "version": "2.2.0", + "resolved": "https://registry.npmjs.org/entities/-/entities-2.2.0.tgz", + "integrity": "sha512-p92if5Nz619I0w+akJrLZH0MX0Pb5DX39XOwQTtXSdQQOaYH03S1uIQp4mhOZtAXrxq4ViO67YTiLBo2638o9A==", "dev": true } } @@ -754,9 +754,9 @@ "dev": true }, "errno": { - "version": "0.1.7", - "resolved": "https://registry.npmjs.org/errno/-/errno-0.1.7.tgz", - "integrity": "sha512-MfrRBDWzIWifgq6tJj60gkAwtLNb6sQPlcFrSOflcP1aFmmruKQ2wRnze/8V6kgyz7H3FF8Npzv78mZ7XLLflg==", + "version": "0.1.8", + "resolved": "https://registry.npmjs.org/errno/-/errno-0.1.8.tgz", + "integrity": "sha512-dJ6oBr5SQ1VSd9qkk7ByRgb/1SH4JZjCHSW/mr63/QcXO9zLVxvJ6Oy13nio03rxpSnVDDjFor75SjVeZWPW/A==", "dev": true, "optional": true, "requires": { @@ -973,9 +973,9 @@ "optional": true }, "fast-deep-equal": { - "version": "3.1.1", - "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.1.tgz", - "integrity": "sha512-8UEa58QDLauDNfpbrX55Q9jrGHThw2ZMdOky5Gl1CDtVeJDPVrG4Jxx1N8jw2gkWaff5UUuX1KJd+9zGe2B+ZA==", + "version": "3.1.3", + "resolved": "https://registry.npmjs.org/fast-deep-equal/-/fast-deep-equal-3.1.3.tgz", + "integrity": "sha512-f3qQ9oQy9j2AhBe/H9VC91wLmKBCCU/gDOnKNAYG5hswO7BLKj09Hc5HYNz9cGI++xlpDCIgDaitVs03ATR84Q==", "dev": true, "optional": true }, @@ -1069,9 +1069,9 @@ } }, "forwarded": { - "version": "0.1.2", - "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.1.2.tgz", - "integrity": "sha1-mMI9qxF1ZXuMBXPozszZGw/xjIQ=" + "version": "0.2.0", + "resolved": "https://registry.npmjs.org/forwarded/-/forwarded-0.2.0.tgz", + "integrity": "sha512-buRG0fpBtRHSTCOASe6hD258tEubFoRLb4ZNA6NxMVHNw2gOcwHo9wyablzMzOA5z9xA9L1KNjk/Nt6MT9aYow==" }, "fragment-cache": { "version": "0.2.1", @@ -1134,9 +1134,9 @@ } }, "glob": { - "version": "7.1.6", - "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.6.tgz", - "integrity": "sha512-LwaxwyZ72Lk7vZINtNNrywX0ZuLyStrdDtabefZKAY5ZGJhVtgdznluResxNmPitE0SAO+O26sWTHeKSI2wMBA==", + "version": "7.1.7", + "resolved": "https://registry.npmjs.org/glob/-/glob-7.1.7.tgz", + "integrity": "sha512-OvD9ENzPLbegENnYP5UUfJIirTg4+XwMWGaQfQTY0JenxNvvIKP3U3/tAQSPIu/lHxXYSZmpXlUHeqAIdKzBLQ==", "dev": true, "requires": { "fs.realpath": "^1.0.0", @@ -1191,9 +1191,9 @@ } }, "graceful-fs": { - "version": "4.2.3", - "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.3.tgz", - "integrity": "sha512-a30VEBm4PEdx1dRB7MFK7BejejvCvBronbLjht+sHuGYj8PHs7M/5Z+rt5lw551vZ7yfTCj4Vuyy3mSJytDWRQ==" + "version": "4.2.6", + "resolved": "https://registry.npmjs.org/graceful-fs/-/graceful-fs-4.2.6.tgz", + "integrity": "sha512-nTnJ528pbqxYanhpDYsi4Rd8MAeaBA67+RZ10CM1m3bTAVFEDcd5AuA4a6W5YkGZ1iNXHzZz8T6TBKLeBuNriQ==" }, "har-schema": { "version": "2.0.0", @@ -1203,13 +1203,13 @@ "optional": true }, "har-validator": { - "version": "5.1.3", - "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.3.tgz", - "integrity": "sha512-sNvOCzEQNr/qrvJgc3UG/kD4QtlHycrzwS+6mfTrrSq97BvaYcPZZI1ZSqGSPR73Cxn4LKTD4PttRwfU7jWq5g==", + "version": "5.1.5", + "resolved": "https://registry.npmjs.org/har-validator/-/har-validator-5.1.5.tgz", + "integrity": "sha512-nmT2T0lljbxdQZfspsno9hgrG3Uir6Ks5afism62poxqBM6sDnMEuPmzTq8XN0OEwqKLLdh1jQI3qyE66Nzb3w==", "dev": true, "optional": true, "requires": { - "ajv": "^6.5.5", + "ajv": "^6.12.3", "har-schema": "^2.0.0" } }, @@ -1346,9 +1346,9 @@ "integrity": "sha1-Yzwsg+PaQqUC9SRmAiSA9CCCYd4=" }, "ipaddr.js": { - "version": "1.9.0", - "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.0.tgz", - "integrity": "sha512-M4Sjn6N/+O6/IXSJseKqHoFc+5FdGJ22sXqnjTpdZweHK64MzEPAyQZyEU3R/KRv2GLoa7nNtg/C2Ev6m7z+eA==" + "version": "1.9.1", + "resolved": "https://registry.npmjs.org/ipaddr.js/-/ipaddr.js-1.9.1.tgz", + "integrity": "sha512-0KI/607xoxSToH7GjN1FfSbLoU0+btTicjsQSWQlh/hZykN8KpmMf7uYwPW3R+akZ6R/w18ZlXSHBYXiYUPO3g==" }, "is-accessor-descriptor": { "version": "0.1.6", @@ -1527,16 +1527,16 @@ "optional": true }, "jshint": { - "version": "2.11.0", - "resolved": "https://registry.npmjs.org/jshint/-/jshint-2.11.0.tgz", - "integrity": "sha512-ooaD/hrBPhu35xXW4gn+o3SOuzht73gdBuffgJzrZBJZPGgGiiTvJEgTyxFvBO2nz0+X1G6etF8SzUODTlLY6Q==", + "version": "2.13.0", + "resolved": "https://registry.npmjs.org/jshint/-/jshint-2.13.0.tgz", + "integrity": "sha512-Nd+md9wIeyfDK+RGrbOBzwLONSTdihGMtyGYU/t7zYcN2EgUa4iuY3VK2oxtPYrW5ycTj18iC+UbhNTxe4C66g==", "dev": true, "requires": { "cli": "~1.0.0", "console-browserify": "1.1.x", "exit": "0.1.x", "htmlparser2": "3.8.x", - "lodash": "~4.17.11", + "lodash": "~4.17.21", "minimatch": "~3.0.2", "shelljs": "0.3.x", "strip-json-comments": "1.0.x" @@ -1591,9 +1591,9 @@ } }, "jszip": { - "version": "3.2.2", - "resolved": "https://registry.npmjs.org/jszip/-/jszip-3.2.2.tgz", - "integrity": "sha512-NmKajvAFQpbg3taXQXr/ccS2wcucR1AZ+NtyWp2Nq7HHVsXhcJFR8p0Baf32C2yVvBylFWVeKf+WI2AnvlPhpA==", + "version": "3.6.0", + "resolved": "https://registry.npmjs.org/jszip/-/jszip-3.6.0.tgz", + "integrity": "sha512-jgnQoG9LKnWO3mnVNBnfhkh0QknICd1FGSrXcgrl67zioyJ4wgx25o9ZqwNtrROSflGBCGYnJfjrIyRIby1OoQ==", "dev": true, "requires": { "lie": "~3.3.0", @@ -1654,15 +1654,6 @@ "promise": "^7.1.1", "request": "^2.83.0", "source-map": "~0.6.0" - }, - "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "dev": true, - "optional": true - } } }, "lesshint": { @@ -1791,16 +1782,16 @@ "integrity": "sha512-KI1+qOZu5DcW6wayYHSzR/tXKCDC5Om4s1z2QJjDULzLcmf3DvzS7oluY4HCTrc+9FiKmWUgeNLg7W3uIQvxtQ==" }, "mime-db": { - "version": "1.43.0", - "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.43.0.tgz", - "integrity": "sha512-+5dsGEEovYbT8UY9yD7eE4XTc4UwJ1jBYlgaQQF38ENsKR3wj/8q8RFZrF9WIZpB2V1ArTVFUva8sAul1NzRzQ==" + "version": "1.48.0", + "resolved": "https://registry.npmjs.org/mime-db/-/mime-db-1.48.0.tgz", + "integrity": "sha512-FM3QwxV+TnZYQ2aRqhlKBMHxk10lTbMt3bBkMAp54ddrNeVSfcQYOOKuGuy3Ddrm38I04If834fOUSq1yzslJQ==" }, "mime-types": { - "version": "2.1.26", - "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.26.tgz", - "integrity": "sha512-01paPWYgLrkqAyrlDorC1uDwl2p3qZT7yl806vW7DvDoxwXi46jsjFbg+WdwotBIk6/MbEhO/dh5aZ5sNj/dWQ==", + "version": "2.1.31", + "resolved": "https://registry.npmjs.org/mime-types/-/mime-types-2.1.31.tgz", + "integrity": "sha512-XGZnNzm3QvgKxa8dpzyhFTHmpP3l5YNusmne07VUOXxou9CqUqYa/HBy124RqtVh/O2pECas/MOcsDgpilPOPg==", "requires": { - "mime-db": "1.43.0" + "mime-db": "1.48.0" } }, "minimatch": { @@ -1841,9 +1832,9 @@ } }, "mkdirp": { - "version": "0.5.3", - "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.3.tgz", - "integrity": "sha512-P+2gwrFqx8lhew375MQHHeTlY8AuOJSrGf0R5ddkEndUkmwpgUob/vQuBD1V22/Cw1/lJr4x+EjllSezBThzBg==", + "version": "0.5.5", + "resolved": "https://registry.npmjs.org/mkdirp/-/mkdirp-0.5.5.tgz", + "integrity": "sha512-NKmAlESf6jMGym1++R0Ra7wvhV+wFW63FaSOFPwRahvea0gMUcGUhVeAg/0BC0wiv9ih5NYPB1Wn1UEI1/L+xQ==", "dev": true, "optional": true, "requires": { @@ -1880,9 +1871,9 @@ "integrity": "sha512-hZXc7K2e+PgeI1eDBe/10Ard4ekbfrrqG8Ep+8Jmf4JID2bNg7NvCPOZN+kfF574pFQI7mum2AUqDidoKqcTOw==" }, "netflux-websocket": { - "version": "0.1.20", - "resolved": "https://registry.npmjs.org/netflux-websocket/-/netflux-websocket-0.1.20.tgz", - "integrity": "sha512-svFkw4ol4gmkcXKnx5kF/8tR9mmtTCDzUlLy4mSlcNl/4iWlbDmgwp/+aJ3nqtv8fg12m+DAFGX2+fbC0//dcg==" + "version": "0.1.21", + "resolved": "https://registry.npmjs.org/netflux-websocket/-/netflux-websocket-0.1.21.tgz", + "integrity": "sha512-Zjl5lefg8urC0a0T7YCPGiUgRsISZBsTZl1STylmQz8Bq4ohcZ8cP3r6VoCpeVcvJ1Y/e3ZCXPxndWlNP9Jfug==" }, "nthen": { "version": "0.1.8", @@ -2049,22 +2040,14 @@ "dev": true }, "postcss": { - "version": "7.0.35", - "resolved": "https://registry.npmjs.org/postcss/-/postcss-7.0.35.tgz", - "integrity": "sha512-3QT8bBJeX/S5zKTTjTCIjRF3If4avAT6kqxcASlTWEtAFCb9NH0OUxNDfgZSWdP5fJnBYCMEWkIFfWeugjzYMg==", + "version": "7.0.36", + "resolved": "https://registry.npmjs.org/postcss/-/postcss-7.0.36.tgz", + "integrity": "sha512-BebJSIUMwJHRH0HAQoxN4u1CN86glsrwsW0q7T+/m44eXOUAxSNdHRkNZPYz5vVUbg17hFgOQDE7fZk7li3pZw==", "dev": true, "requires": { "chalk": "^2.4.2", "source-map": "^0.6.1", "supports-color": "^6.1.0" - }, - "dependencies": { - "source-map": { - "version": "0.6.1", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", - "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", - "dev": true - } } }, "postcss-less": { @@ -2115,12 +2098,12 @@ } }, "proxy-addr": { - "version": "2.0.5", - "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.5.tgz", - "integrity": "sha512-t/7RxHXPH6cJtP0pRG6smSr9QJidhB+3kXu0KgXnbGYMgzEnUxRQ4/LDdfOwZEMyIh3/xHb8PX3t+lfL9z+YVQ==", + "version": "2.0.7", + "resolved": "https://registry.npmjs.org/proxy-addr/-/proxy-addr-2.0.7.tgz", + "integrity": "sha512-llQsMLSUDUPT44jdrU/O37qlnifitDP+ZwrmmZcoSKyLKvtZxpyV0n2/bD/N4tBAAZ/gJEdZU7KMraoK1+XYAg==", "requires": { - "forwarded": "~0.1.2", - "ipaddr.js": "1.9.0" + "forwarded": "0.2.0", + "ipaddr.js": "1.9.1" } }, "prr": { @@ -2131,9 +2114,9 @@ "optional": true }, "psl": { - "version": "1.7.0", - "resolved": "https://registry.npmjs.org/psl/-/psl-1.7.0.tgz", - "integrity": "sha512-5NsSEDv8zY70ScRnOTn7bK7eanl2MvFrOrS/R6x+dBt5g1ghnj9Zv90kO8GwT8gxcu2ANyFprnFYB85IogIJOQ==", + "version": "1.8.0", + "resolved": "https://registry.npmjs.org/psl/-/psl-1.8.0.tgz", + "integrity": "sha512-RIdOzyoavK+hA18OGGWDqUTsCLhtA7IcZ/6NCs4fFJaHBDab+pDDmDIByWFRQJq2Cd7r1OoQxBGKOaztq+hjIQ==", "dev": true, "optional": true }, @@ -2193,9 +2176,9 @@ } }, "repeat-element": { - "version": "1.1.3", - "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.3.tgz", - "integrity": "sha512-ahGq0ZnV5m5XtZLMb+vP76kcAM5nkLqk0lpqAuojSKGgQtn4eRi4ZZGm2olo2zKFH+sMsWaqOCW1dqAnOru72g==", + "version": "1.1.4", + "resolved": "https://registry.npmjs.org/repeat-element/-/repeat-element-1.1.4.tgz", + "integrity": "sha512-LFiNfRcSu7KK3evMyYOuCzv3L10TW7yC1G2/+StMjK8Y6Vqd2MG7r/Qjw4ghtuCOjFvlnms/iMmLqpvW/ES/WQ==", "dev": true }, "repeat-string": { @@ -2412,6 +2395,12 @@ "requires": { "is-extendable": "^0.1.0" } + }, + "source-map": { + "version": "0.5.7", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", + "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "dev": true } } }, @@ -2495,9 +2484,9 @@ } }, "source-map": { - "version": "0.5.7", - "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.5.7.tgz", - "integrity": "sha1-igOdLRAh0i0eoUyA2OpGi6LvP8w=", + "version": "0.6.1", + "resolved": "https://registry.npmjs.org/source-map/-/source-map-0.6.1.tgz", + "integrity": "sha512-UjgapumWlbMhkBgzT7Ykc5YXUT46F0iKu8SGXq0bcwP5dz/h0Plj6enJqjz1Zbq2l5WaqYnrVbwWOWMyF3F47g==", "dev": true }, "source-map-resolve": { @@ -2514,9 +2503,9 @@ } }, "source-map-url": { - "version": "0.4.0", - "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.0.tgz", - "integrity": "sha1-PpNdfd1zYxuXZZlW1VEo6HtQhKM=", + "version": "0.4.1", + "resolved": "https://registry.npmjs.org/source-map-url/-/source-map-url-0.4.1.tgz", + "integrity": "sha512-cPiFOTLUKvJFIg4SKVScy4ilPPW6rFgMgfuZJPNoDuMs3nC1HbMUycBoJw77xFIp6z1UJQJOfx6C9GMH80DiTw==", "dev": true }, "split-string": { @@ -2793,9 +2782,9 @@ } }, "uri-js": { - "version": "4.2.2", - "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.2.2.tgz", - "integrity": "sha512-KY9Frmirql91X2Qgjry0Wd4Y+YTdrdZheS8TFwvkbLWf/G5KNJDCh6pKL5OZctEW4+0Baa5idK2ZQuELRwPznQ==", + "version": "4.4.1", + "resolved": "https://registry.npmjs.org/uri-js/-/uri-js-4.4.1.tgz", + "integrity": "sha512-7rKUyy33Q1yc98pQ1DAmLtwX109F7TIfWlW1Ydo8Wl1ii1SeHieeh0HHfPeL2fMXK6z0s8ecKs9frCuLJvndBg==", "dev": true, "optional": true, "requires": { diff --git a/package.json b/package.json index 3314ffd17..68a315891 100644 --- a/package.json +++ b/package.json @@ -1,7 +1,7 @@ { "name": "cryptpad", "description": "realtime collaborative visual editor with zero knowlege server", - "version": "4.5.0", + "version": "4.9.0", "license": "AGPL-3.0+", "repository": { "type": "git", diff --git a/readme.md b/readme.md index 2213b9e27..f4b979bf3 100644 --- a/readme.md +++ b/readme.md @@ -1,20 +1,18 @@ -[![An XWiki Labs Project](https://raw.githubusercontent.com/xwiki-labs/xwiki-labs-logo/master/projects/xwikilabs/xlabs-project.png "XWiki labs")](https://labs.xwiki.com/xwiki/bin/view/Main/WebHome) +# CryptPad + +CryptPad is a collaboration suite that is end-to-end-encrypted and open-source. It is built to enable collaboration, synchronizing changes to documents in real time. Because all data is encrypted, the service and its administrators have no way of seeing the content being edited and stored. ![CryptPad screenshot](screenshot.png "Private real-time collaboration on a Rich Text document.") -CryptPad is the **Zero Knowledge** realtime collaborative editor. +# Installation -Encryption carried out in your web browser protects the data from the server, the cloud -and the NSA. It relies on the [ChainPad] realtime engine. +## For development - +Our [developer guide](https://docs.cryptpad.fr/en/dev_guide/setup.html) provides instructions for setting up a local instance without HTTPS or our more advanced security features. -# Installation +## For production -Installing CryptPad is pretty straightforward. You can read all about it in the -[installation guide](https://github.com/xwiki-labs/cryptpad/wiki/Installation-guide). - -It also contains information on keeping your instance of CryptPad up to date. +Configuring CryptPad for production requires a little more work, but the process is described in our [admin installation guide](https://docs.cryptpad.fr/en/admin_guide/installation.html). From there you can find more information about customization and maintenance. ## Current version @@ -24,33 +22,40 @@ The most recent version and all past release notes can be found [here](https://g See [Cryptpad-Docker](https://github.com/xwiki-labs/cryptpad-docker) repository for details on how to get up-and-running with Cryptpad in Docker. This repository is maintained by the community and not officially supported. - # Security -CryptPad is *private*, not *anonymous*. Privacy protects your data, anonymity protects you. -As such, it is possible for a collaborator on the pad to include some silly/ugly/nasty things -in a CryptPad such as an image which reveals your IP address when your browser automatically -loads it or a script which plays Rick Astleys's greatest hits. It is possible for anyone -who does not have the key to be able to change anything in the pad or add anything, even the -server, however the clients will notice this because the content hashes in CryptPad will fail to -validate. - -The server does have a certain power, it can send you evil javascript which does the wrong -thing (leaks the key or the data back to the server or to someone else). This is however an -[active attack] which makes it detectable. The NSA really hates doing these because they might -get caught and laughed at and humiliated in front of the whole world (again). If you're making -the NSA mad enough for them to use an active attack against you, Great Success Highfive, now take -the battery out of your computer before it spawns Agent Smith. - -Still there are other low-lives in the world so using CryptPad over HTTPS is probably a good idea. +CryptPad offers a variety of collaborative tools that encrypt your data in your browser +before it is sent to the server and your collaborators. In the event that the server is +compromized the database holds encrypted data that is not of much value to attackers. + +The code which performs the encryption is still loaded from the host server like any +other web page, so you still need to trust the administrator to keep their server secure +and to send you the right code. An expert can download code from the server and check +that it isn't doing anything malicious like leaking your encryption keys, which is why +this is considered an [active attack]. + +The platform is designed to minimize what data is exposed to its operators. User registration +and account access is based on a cryptographic key that is derived from your username +and password so the server never needs to see either and you don't need to worry about +whether they are being stored securely. It is impossible to verify whether a server's +operators are logging your IP or other activity, so if you consider this information +sensitive it is safest to assume it is being recorded and access your preferred instance +via [Tor browser]. + +A correctly configured instance has safeguards to prevent collaborators from doing some +nasty things like injecting scripts into collaborative documents or uploads. The project +is actively maintained and bugs that our safeguards don't catch tend to get fixed quickly. +For this reason it is best to only use instances that are running the most recent version, +which is currently on a three-week release cycle. It is difficult for a non-expert to +determine whether an instance is otherwise configured correctly, so we are actively +working on allowing administrators to opt in to a public directory of servers that +meet our strict criteria for safety. # Translations -We'd like to make it easy for more people to use encryption in their routine activities. -As such, we've tried to make language-specific parts of CryptPad translatable. If you're -able to translate CryptPad's interface, and would like to help, please contact us! - -You can also see [our translation guide](/customize.dist/translations/README.md). +CryptPad can be translated with nothing more than a web browser via our +[Weblate instance](https://weblate.cryptpad.fr/projects/cryptpad/app/). +More information about this can be found in [our translation guide](/customize.dist/translations/README.md). # Contacting Us @@ -61,13 +66,13 @@ via our [GitHub issue tracker](https://github.com/xwiki-labs/cryptpad/issues/), # Team -CryptPad is actively developed by a team at [XWiki SAS](https://www.xwiki.com), a company that has been building Open-Source software since 2004 with contributors from around the world. Between 2015 and 2019 it was funded by a research grant from the French state through [BPI France](https://www.bpifrance.fr/). It is currently financed by [NLnet PET](https://nlnet.nl/PET/), subscribers of CryptPad.fr and donations to our [Open-Collective campaign](https://opencollective.com/cryptpad). +CryptPad is actively developed by a team at [XWiki SAS](https://www.xwiki.com), a company that has been building Open-Source software since 2004 with contributors from around the world. Between 2015 and 2019 it was funded by a research grant from the French state through [BPI France](https://www.bpifrance.fr/). In the years since we have been funded by [NLnet PET](https://nlnet.nl/PET/), [NGI TRUST](https://www.ngi.eu/ngi-projects/ngi-trust/), [NGI DAPSI](https://dapsi.ngi.eu/), subscribers of CryptPad.fr, and donations to our [Open-Collective campaign](https://opencollective.com/cryptpad). # Contributing We love Open Source and we love contribution. Learn more about [contributing](https://docs.cryptpad.fr/en/how_to_contribute.html). -If you have any questions or comments, or if you're interested in contributing to Cryptpad, come say hi on IRC, `#cryptpad` on Freenode. +If you have any questions or comments, or if you're interested in contributing to Cryptpad, come say hi in our [Matrix channel](https://app.element.io/#/room/#cryptpad:matrix.xwiki.com). # License @@ -78,5 +83,6 @@ published by the Free Software Foundation, either version 3 of the License, or ( any later version. If you wish to use this technology in a proprietary product, please contact sales@xwiki.com. -[ChainPad]: https://github.com/xwiki-contrib/chainpad +[Tor browser]: https://www.torproject.org/download/ [active attack]: https://en.wikipedia.org/wiki/Attack_(computing)#Types_of_attack + diff --git a/scripts/evict-archived.js b/scripts/evict-archived.js index 7f90f9ff5..255246e99 100644 --- a/scripts/evict-archived.js +++ b/scripts/evict-archived.js @@ -56,6 +56,8 @@ var prepareEnv = function (Env, cb) { Store.create({ filePath: config.pinPath, + // archive pin logs to their own subpath + volumeId: 'pins', }, w(function (err, _) { if (err) { w.abort(); diff --git a/scripts/evict-inactive.js b/scripts/evict-inactive.js index bf7e1ca5b..2521e014f 100644 --- a/scripts/evict-inactive.js +++ b/scripts/evict-inactive.js @@ -56,6 +56,8 @@ var prepareEnv = function (Env, cb) { Store.create({ filePath: config.pinPath, + // archive pin logs to their own subpath + volumeId: 'pins', }, w(function (err, _) { if (err) { w.abort(); diff --git a/scripts/find-html-translations.js b/scripts/find-html-translations.js index dabdbac4b..fc1d4a18e 100644 --- a/scripts/find-html-translations.js +++ b/scripts/find-html-translations.js @@ -9,6 +9,7 @@ var simpleTags = [ // FIXME "", + '', '

', '

', @@ -70,7 +71,7 @@ processLang(EN, 'en', true); [ 'ar', - 'bn_BD', + //'bn_BD', 'ca', 'de', 'es', @@ -86,11 +87,15 @@ processLang(EN, 'en', true); 'ro', 'ru', 'sv', - 'te', + //'te', 'tr', 'zh', ].forEach(function (lang) { - var map = require("../www/common/translations/messages." + lang + ".json"); - if (!Object.keys(map).length) { return; } - processLang(map, lang); + try { + var map = require("../www/common/translations/messages." + lang + ".json"); + if (!Object.keys(map).length) { return; } + processLang(map, lang); + } catch (err) { + console.error(err); + } }); diff --git a/scripts/lint-translations.js b/scripts/lint-translations.js new file mode 100644 index 000000000..a38cd615a --- /dev/null +++ b/scripts/lint-translations.js @@ -0,0 +1,8 @@ +// TODO unify the following scripts + // unused-translations.js + // find-html-translations + +// more linting + // Search for 'Cryptpad' string (should be 'CryptPad') + // Search English for -ise\s + diff --git a/scripts/tests/test-rpc.js b/scripts/tests/test-rpc.js index 0fd0abc37..b92cf6287 100644 --- a/scripts/tests/test-rpc.js +++ b/scripts/tests/test-rpc.js @@ -122,14 +122,11 @@ var createUser = function (config, cb) { }); })); }).nThen(function (w) { - user.rpc.reset([], w(function (err, hash) { + user.rpc.reset([], w(function (err) { if (err) { w.abort(); user.shutdown(); - return console.log("RESET_ERR"); - } - if (!hash || hash !== EMPTY_ARRAY_HASH) { - throw new Error("EXPECTED EMPTY ARRAY HASH"); + return console.log("TEST_RESET_ERR"); } })); }).nThen(function (w) { @@ -214,17 +211,17 @@ var createUser = function (config, cb) { // TODO check your quota usage }).nThen(function (w) { - user.rpc.unpin([user.mailboxChannel], w(function (err, hash) { + user.rpc.unpin([user.mailboxChannel], w(function (err) { if (err) { w.abort(); return void cb(err); } + })); + }).nThen(function (w) { + user.rpc.getServerHash(w(function (err, hash) { + console.log(hash); - if (hash[0] !== EMPTY_ARRAY_HASH) { - //console.log('UNPIN_RESPONSE', hash); - throw new Error("UNPIN_DIDNT_WORK"); - } - user.latestPinHash = hash[0]; + user.latestPinHash = hash; })); }).nThen(function (w) { // clean up the pin list to avoid lots of accounts on the server @@ -304,7 +301,8 @@ nThen(function (w) { }, w(function (err, roster) { if (err) { w.abort(); - return void console.trace(err); + console.error(err); + return void console.error("ROSTER_ERROR"); } oscar.roster = roster; oscar.destroy.reg(function () { diff --git a/server.js b/server.js index 3a71f83b8..3cea171c6 100644 --- a/server.js +++ b/server.js @@ -4,7 +4,6 @@ var Express = require('express'); var Http = require('http'); var Fs = require('fs'); -var Package = require('./package.json'); var Path = require("path"); var nThen = require("nthen"); var Util = require("./lib/common-util"); @@ -16,21 +15,20 @@ var Env = require("./lib/env").create(config); var app = Express(); -var canonicalizeOrigin = function (s) { - return (s || '').trim().replace(/\/+$/, ''); +var fancyURL = function (domain, path) { + try { + if (domain && path) { return new URL(path, domain).href; } + return new URL(domain); + } catch (err) {} + return false; }; (function () { - // you absolutely must provide an 'httpUnsafeOrigin' - if (typeof(config.httpUnsafeOrigin) !== 'string') { + // you absolutely must provide an 'httpUnsafeOrigin' (a truthy string) + if (!Env.httpUnsafeOrigin || typeof(Env.httpUnsafeOrigin) !== 'string') { throw new Error("No 'httpUnsafeOrigin' provided"); } - config.httpUnsafeOrigin = canonicalizeOrigin(config.httpUnsafeOrigin); - if (typeof(config.httpSafeOrigin) === 'string') { - config.httpSafeOrigin = canonicalizeOrigin(config.httpSafeOrigin); - } - // fall back to listening on a local address // if httpAddress is not a string if (typeof(config.httpAddress) !== 'string') { @@ -42,26 +40,11 @@ var canonicalizeOrigin = function (s) { config.httpPort = 3000; } - if (typeof(config.httpSafeOrigin) !== 'string') { + if (typeof(Env.httpSafeOrigin) !== 'string') { Env.NO_SANDBOX = true; if (typeof(config.httpSafePort) !== 'number') { config.httpSafePort = config.httpPort + 1; } - - if (Env.DEV_MODE) { return; } - console.log(` - m m mm mmmmm mm m mmmmm mm m mmm m - # # # ## # "# #"m # # #"m # m" " # - " #"# # # # #mmmm" # #m # # # #m # # mm # - ## ##" #mm# # "m # # # # # # # # # - # # # # # " # ## mm#mm # ## "mmm" # -`); - - console.log("\nNo 'httpSafeOrigin' provided."); - console.log("Your configuration probably isn't taking advantage of all of CryptPad's security features!"); - console.log("This is acceptable for development, otherwise your users may be at risk.\n"); - - console.log("Serving sandboxed content via port %s.\nThis is probably not what you want for a production instance!\n", config.httpSafePort); } }()); @@ -94,42 +77,35 @@ var setHeaders = (function () { } } else { // use the default CSP headers constructed with your domain - headers['Content-Security-Policy'] = Default.contentSecurity(config.httpUnsafeOrigin); + headers['Content-Security-Policy'] = Default.contentSecurity(Env.httpUnsafeOrigin); } const padHeaders = Util.clone(headers); if (typeof(config.padContentSecurity) === 'string') { padHeaders['Content-Security-Policy'] = config.padContentSecurity; } else { - padHeaders['Content-Security-Policy'] = Default.padContentSecurity(config.httpUnsafeOrigin); + padHeaders['Content-Security-Policy'] = Default.padContentSecurity(Env.httpUnsafeOrigin); } if (Object.keys(headers).length) { return function (req, res) { // apply a bunch of cross-origin headers for XLSX export in FF and printing elsewhere applyHeaderMap(res, { - "Cross-Origin-Opener-Policy": /^\/sheet\//.test(req.url)? 'same-origin': '', - "Cross-Origin-Embedder-Policy": 'require-corp', + "Cross-Origin-Opener-Policy": /^\/(sheet|presentation|doc|convert)\//.test(req.url)? 'same-origin': '', }); if (Env.NO_SANDBOX) { // handles correct configuration for local development // https://stackoverflow.com/questions/11531121/add-duplicate-http-response-headers-in-nodejs applyHeaderMap(res, { "Cross-Origin-Resource-Policy": 'cross-origin', + "Cross-Origin-Embedder-Policy": 'require-corp', }); } - // Don't set CSP headers on /api/config because they aren't necessary and they cause problems + // Don't set CSP headers on /api/ endpoints + // because they aren't necessary and they cause problems // when duplicated by NGINX in production environments - if (/^\/api\/(broadcast|config)/.test(req.url)) { - /* - if (Env.NO_SANDBOX) { - applyHeaderMap(res, { - "Cross-Origin-Resource-Policy": 'cross-origin', - }); - } - */ - return; - } + if (/^\/api\/(broadcast|config)/.test(req.url)) { return; } + applyHeaderMap(res, { "Cross-Origin-Resource-Policy": 'cross-origin', }); @@ -165,7 +141,7 @@ app.head(/^\/common\/feedback\.html/, function (req, res, next) { app.use('/blob', function (req, res, next) { if (req.method === 'HEAD') { - Express.static(Path.join(__dirname, (config.blobPath || './blob')), { + Express.static(Path.join(__dirname, Env.paths.blob), { setHeaders: function (res, path, stat) { res.set('Access-Control-Allow-Origin', '*'); res.set('Access-Control-Allow-Headers', 'Content-Length'); @@ -205,13 +181,13 @@ var mainPagePattern = new RegExp('^\/(' + mainPages.join('|') + ').html$'); app.get(mainPagePattern, Express.static(__dirname + '/customize')); app.get(mainPagePattern, Express.static(__dirname + '/customize.dist')); -app.use("/blob", Express.static(Path.join(__dirname, (config.blobPath || './blob')), { +app.use("/blob", Express.static(Path.join(__dirname, Env.paths.blob), { maxAge: Env.DEV_MODE? "0d": "365d" })); -app.use("/datastore", Express.static(Path.join(__dirname, (config.filePath || './datastore')), { +app.use("/datastore", Express.static(Path.join(__dirname, Env.paths.data), { maxAge: "0d" })); -app.use("/block", Express.static(Path.join(__dirname, (config.blockPath || '/block')), { +app.use("/block", Express.static(Path.join(__dirname, Env.paths.block), { maxAge: "0d", })); @@ -266,12 +242,12 @@ var serveConfig = makeRouteCache(function (host) { 'var obj = ' + JSON.stringify({ requireConf: { waitSeconds: 600, - urlArgs: 'ver=' + Package.version + cacheString(), + urlArgs: 'ver=' + Env.version + cacheString(), }, - removeDonateButton: (config.removeDonateButton === true), - allowSubscriptions: (config.allowSubscriptions === true), + removeDonateButton: (Env.removeDonateButton === true), + allowSubscriptions: (Env.allowSubscriptions === true), websocketPath: config.externalWebsocketURL, - httpUnsafeOrigin: config.httpUnsafeOrigin, + httpUnsafeOrigin: Env.httpUnsafeOrigin, adminEmail: Env.adminEmail, adminKeys: Env.admins, inactiveTime: Env.inactiveTime, @@ -279,10 +255,10 @@ var serveConfig = makeRouteCache(function (host) { defaultStorageLimit: Env.defaultStorageLimit, maxUploadSize: Env.maxUploadSize, premiumUploadSize: Env.premiumUploadSize, - restrictRegistration: Env.restrictRegistration, // FIXME see the race condition in env.js + restrictRegistration: Env.restrictRegistration, }, null, '\t'), 'obj.httpSafeOrigin = ' + (function () { - if (config.httpSafeOrigin) { return '"' + config.httpSafeOrigin + '"'; } + if (Env.httpSafeOrigin) { return '"' + Env.httpSafeOrigin + '"'; } if (config.httpSafePort) { return "(function () { return window.location.origin.replace(/\:[0-9]+$/, ':" + config.httpSafePort + "'); }())"; @@ -345,7 +321,19 @@ nThen(function (w) { var port = config.httpPort; var ps = port === 80? '': ':' + port; - console.log('[%s] server available http://%s%s', new Date().toISOString(), hostName, ps); + var roughAddress = 'http://' + hostName + ps; + var betterAddress = fancyURL(Env.httpUnsafeOrigin); + + if (betterAddress) { + console.log('Serving content for %s via %s.\n', betterAddress, roughAddress); + } else { + console.log('Serving content via %s.\n', roughAddress); + } + if (!Env.admins.length) { + console.log("Your instance is not correctly configured for safe use in production.\nSee %s for more information.\n", + fancyURL(Env.httpUnsafeOrigin, '/checkup/') || 'https://your-domain.com/checkup/' + ); + } }); if (config.httpSafePort) { diff --git a/www/admin/app-admin.less b/www/admin/app-admin.less index 17450361c..227792540 100644 --- a/www/admin/app-admin.less +++ b/www/admin/app-admin.less @@ -203,6 +203,17 @@ } } + .cp-admin-radio-container { + display: flex; + align-items: left; //center; + flex-wrap: wrap; + flex-direction: column; + label { + margin-right: 40px; + margin-top: 5px; + } + } + .cp-admin-broadcast-form { input.flatpickr-input { width: 307.875px !important; // same width as flatpickr calendar diff --git a/www/admin/inner.js b/www/admin/inner.js index ffc9a561c..e8d567d41 100644 --- a/www/admin/inner.js +++ b/www/admin/inner.js @@ -16,6 +16,7 @@ define([ '/support/ui.js', '/lib/datepicker/flatpickr.js', + '/bower_components/tweetnacl/nacl-fast.min.js', 'css!/lib/datepicker/flatpickr.min.css', 'css!/bower_components/bootstrap/dist/css/bootstrap.min.css', @@ -44,6 +45,7 @@ define([ 'instanceStatus': {} }; + var Nacl = window.nacl; var common; var sFrameChan; @@ -54,6 +56,7 @@ define([ 'cp-admin-archive', 'cp-admin-unarchive', 'cp-admin-registration', + 'cp-admin-email' ], 'quota': [ // Msg.admin_cat_quota 'cp-admin-defaultlimit', @@ -71,7 +74,8 @@ define([ ], 'support': [ // Msg.admin_cat_support 'cp-admin-support-list', - 'cp-admin-support-init' + 'cp-admin-support-init', + 'cp-admin-support-priv', ], 'broadcast': [ // Msg.admin_cat_broadcast 'cp-admin-maintenance', @@ -81,15 +85,28 @@ define([ 'performance': [ // Msg.admin_cat_performance 'cp-admin-refresh-performance', 'cp-admin-performance-profiling', - ] + ], + 'network': [ // Msg.admin_cat_network + 'cp-admin-update-available', + 'cp-admin-checkup', + 'cp-admin-block-daily-check', + //'cp-admin-provide-aggregate-statistics', + 'cp-admin-list-my-instance', + 'cp-admin-consent-to-contact', + 'cp-admin-remove-donate-button', + 'cp-admin-instance-purpose', + ], }; var create = {}; + var keyToCamlCase = function (key) { + return key.replace(/-([a-z])/g, function (g) { return g[1].toUpperCase(); }); + }; + var makeBlock = function (key, addButton) { // Title, Hint, maybeButton // Convert to camlCase for translation keys - var safeKey = key.replace(/-([a-z])/g, function (g) { return g[1].toUpperCase(); }); - + var safeKey = keyToCamlCase(key); var $div = $('
', {'class': 'cp-admin-' + key + ' cp-sidebarlayout-element'}); $('