diff --git a/LICENSE b/LICENSE index dba13ed..be3f7b2 100644 --- a/LICENSE +++ b/LICENSE @@ -1,7 +1,7 @@ GNU AFFERO GENERAL PUBLIC LICENSE Version 3, 19 November 2007 - Copyright (C) 2007 Free Software Foundation, Inc. + Copyright (C) 2007 Free Software Foundation, Inc. Everyone is permitted to copy and distribute verbatim copies of this license document, but changing it is not allowed. @@ -643,7 +643,7 @@ the "copyright" line and a pointer to where the full notice is found. GNU Affero General Public License for more details. You should have received a copy of the GNU Affero General Public License - along with this program. If not, see . + along with this program. If not, see . Also add information on how to contact you by electronic and paper mail. @@ -658,4 +658,4 @@ specific requirements. You should also get your employer (if you work as a programmer) or school, if any, to sign a "copyright disclaimer" for the program, if necessary. For more information on this, and how to apply and follow the GNU AGPL, see -. +. diff --git a/README.md b/README.md index ab13b06..874c221 100644 --- a/README.md +++ b/README.md @@ -1,39 +1,51 @@ -ownCloud for YunoHost ---------------------- + -[![Integration level](https://dash.yunohost.org/integration/owncloud.svg)](https://dash.yunohost.org/appci/app/owncloud) ![](https://ci-apps.yunohost.org/ci/badges/owncloud.status.svg) ![](https://ci-apps.yunohost.org/ci/badges/owncloud.maintain.svg) +# ownCloud for YunoHost -[ownCloud](https://owncloud.org) gives you freedom and control over your -own data. A personal cloud which run on your own server. With owncloud -you can synchronize your files over your devices. +[![Integration level](https://dash.yunohost.org/integration/owncloud.svg)](https://dash.yunohost.org/appci/app/owncloud) ![Working status](https://ci-apps.yunohost.org/ci/badges/owncloud.status.svg) ![Maintenance status](https://ci-apps.yunohost.org/ci/badges/owncloud.maintain.svg) -**Shipped version:** 9.0.5 +[![Install ownCloud with YunoHost](https://install-app.yunohost.org/install-with-yunohost.svg)](https://install-app.yunohost.org/?app=owncloud) -![](https://github.com/owncloud/screenshots/blob/master/files/sidebar_1.png) +*[Lire ce readme en français.](./README_fr.md)* -## Features +> *This package allows you to install ownCloud quickly and simply on a YunoHost server. +If you don't have YunoHost, please consult [the guide](https://yunohost.org/#/install) to learn how to install it.* -In addition to ownCloud core features, the following are made available with -this package: +## Overview - * Integrate with YunoHost users and SSO - i logout button - * Allow one user to be the administrator (set at the installation) - * Optionally access the user home folder from ownCloud files (set at the installation) - * Serve `/.well-known` paths for CalDAV and CardDAV on the domain only if it's - not already served - i by Baïkal +ownCloud Infinite Scale (oCIS) is the new file sync & share platform that will be the foundation of your data management platform. -## Limitations +**Shipped version:** 4.0.1~ynh1 -To integrate the logout button to the SSO, we have to patch ownCloud sources. -Since this upstream [pull-request](https://github.com/owncloud/core/pull/24642) -will not be integrated, the code source integrity checking has been disabled to -prevent the warning message. +## Screenshots -Also, note we made the choice to disable third-parties applications at the -upgrade. It allows to prevent an unstable - and sometimes broken - ownCloud -installation. You will just have to manually activate them after the upgrade. +![Screenshot of ownCloud](./doc/screenshots/screenshot.png) -## Links +## :red_circle: Antifeatures - * ownCloud website: https://owncloud.org/ - * YunoHost website: https://yunohost.org/ +- **Package not maintained**: This YunoHost package is not maintained and needs adoption. + +## Documentation and resources + +* Official app website: +* Official admin documentation: +* Upstream app code repository: +* YunoHost documentation for this app: +* Report a bug: + +## Developer info + +Please send your pull request to the [testing branch](https://github.com/YunoHost-Apps/owncloud_ynh/tree/testing). + +To try the testing branch, please proceed like that. + +``` bash +sudo yunohost app install https://github.com/YunoHost-Apps/owncloud_ynh/tree/testing --debug +or +sudo yunohost app upgrade owncloud -u https://github.com/YunoHost-Apps/owncloud_ynh/tree/testing --debug +``` + +**More info regarding app packaging:** diff --git a/README_fr.md b/README_fr.md new file mode 100644 index 0000000..062acab --- /dev/null +++ b/README_fr.md @@ -0,0 +1,52 @@ + + +# ownCloud pour YunoHost + +[![Niveau d’intégration](https://dash.yunohost.org/integration/owncloud.svg)](https://dash.yunohost.org/appci/app/owncloud) ![Statut du fonctionnement](https://ci-apps.yunohost.org/ci/badges/owncloud.status.svg) ![Statut de maintenance](https://ci-apps.yunohost.org/ci/badges/owncloud.maintain.svg) + +[![Installer ownCloud avec YunoHost](https://install-app.yunohost.org/install-with-yunohost.svg)](https://install-app.yunohost.org/?app=owncloud) + +*[Read this readme in english.](./README.md)* + +> *Ce package vous permet d’installer ownCloud rapidement et simplement sur un serveur YunoHost. +Si vous n’avez pas YunoHost, regardez [ici](https://yunohost.org/#/install) pour savoir comment l’installer et en profiter.* + +## Vue d’ensemble + +ownCloud Infinite Scale (oCIS) est la nouvelle plateforme de synchronisation et de partage de fichiers qui constituera la base de votre plateforme de gestion de données. + + +**Version incluse :** 4.0.1~ynh1 + +## Captures d’écran + +![Capture d’écran de ownCloud](./doc/screenshots/screenshot.png) + +## :red_circle: Fonctions indésirables + +- **Package not maintained**: This YunoHost package is not maintained and needs adoption. + +## Documentations et ressources + +* Site officiel de l’app : +* Documentation officielle de l’admin : +* Dépôt de code officiel de l’app : +* Documentation YunoHost pour cette app : +* Signaler un bug : + +## Informations pour les développeurs + +Merci de faire vos pull request sur la [branche testing](https://github.com/YunoHost-Apps/owncloud_ynh/tree/testing). + +Pour essayer la branche testing, procédez comme suit. + +``` bash +sudo yunohost app install https://github.com/YunoHost-Apps/owncloud_ynh/tree/testing --debug +ou +sudo yunohost app upgrade owncloud -u https://github.com/YunoHost-Apps/owncloud_ynh/tree/testing --debug +``` + +**Plus d’infos sur le packaging d’applications :** \ No newline at end of file diff --git a/conf/.env b/conf/.env new file mode 100644 index 0000000..81ed846 --- /dev/null +++ b/conf/.env @@ -0,0 +1,15 @@ +OCIS_INSECURE=true + +OCIS_URL=https://__DOMAIN__ + +PROXY_HTTP_ADDR=127.0.0.1:__PORT__ + +OCIS_BASE_DATA_PATH=__DATA_DIR__ + +FORCE_CONFIG_OVERWRITE=true + +OCIS_LOG_LEVEL=warn + +OCIS_CONFIG_DIR=__INSTALL_DIR__ + +ADMIN_PASSWORD=__PASSWORD__ diff --git a/conf/config.json b/conf/config.json deleted file mode 100644 index 4f019e2..0000000 --- a/conf/config.json +++ /dev/null @@ -1,38 +0,0 @@ -{ - "system": { - "datadirectory": "#DATADIR#", - "trusted_domains": [ - "localhost", - "#DOMAIN#" - ], - "updatechecker": false, - "memcache.local": "\\OC\\Memcache\\APCu", - "integrity.check.disabled": true - }, - "apps": { - "user_ldap": { - "ldap_base": "dc=yunohost,dc=org", - "ldap_base_groups": "ou=groups,dc=yunohost,dc=org", - "ldap_base_users": "ou=users,dc=yunohost,dc=org", - "ldap_cache_ttl": "600", - "ldap_configuration_active": "1", - "ldap_display_name": "displayname", - "ldap_email_attr": "mail", - "ldap_expert_username_attr": "uid", - "ldap_group_display_name": "cn", - "ldap_group_filter": "objectClass=posixGroup", - "ldap_group_filter_mode": "0", - "ldap_groupfilter_objectclass": "posixGroup", - "ldap_host": "localhost", - "ldap_login_filter": "(&(|(objectclass=posixAccount))(uid=%uid))", - "ldap_login_filter_mode": "0", - "ldap_port": "389", - "ldap_quota_attr": "userquota", - "ldap_tls": "0", - "ldap_user_display_name": "cn", - "ldap_user_filter_mode": "0", - "ldap_userfilter_objectclass": "posixAccount", - "ldap_userlist_filter": "objectclass=posixAccount" - } - } -} diff --git a/conf/nginx.conf b/conf/nginx.conf index 445eca8..1bf9fb3 100644 --- a/conf/nginx.conf +++ b/conf/nginx.conf @@ -1,96 +1,17 @@ -location = /.well-known/carddav { - return 301 https://$server_name#PATH#/remote.php/dav; -} -location = /.well-known/caldav { - return 301 https://$server_name#PATH#/remote.php/dav; -} - -location ^~ #LOCATION# { - alias #DESTDIR#/; - - if ($scheme = http) { - rewrite ^ https://$server_name$request_uri? permanent; - } - - # Add headers to serve security related headers - add_header Strict-Transport-Security "max-age=15768000;"; - add_header X-Content-Type-Options nosniff; - add_header X-Frame-Options "SAMEORIGIN"; - add_header X-XSS-Protection "1; mode=block"; - add_header X-Robots-Tag none; - add_header X-Download-Options noopen; - add_header X-Permitted-Cross-Domain-Policies none; - - # Set max upload size - client_max_body_size 10G; - fastcgi_buffers 64 4K; - - # Disable gzip to avoid the removal of the ETag header - gzip off; - - # Errors pages - error_page 403 #PATH#/core/templates/403.php; - error_page 404 #PATH#/core/templates/404.php; - - # The following 2 rules are only needed for the user_webfinger app. - # Uncomment it if you're planning to use this app. - #rewrite ^/.well-known/host-meta #PATH#/public.php?service=host-meta last; - #rewrite ^/.well-known/host-meta.json #PATH#/public.php?service=host-meta-json last; - - location #LOCATION# { - rewrite ^ #PATH#/index.php$uri; - } - - location = #PATH#/robots.txt { - allow all; - log_not_found off; - access_log off; - } - - location ~ ^#PATH#/(?:build|tests|config|lib|3rdparty|templates|data)/ { - deny all; - } - location ~ ^#PATH#/(?:\.|autotest|occ|issue|indie|db_|console) { - deny all; - } - - location ~ ^#PATH#/(?:index|remote|public|cron|core/ajax/update|status|ocs/v[12]|updater/.+|ocs-provider/.+|core/templates/40[34])\.php(?:$|/) { - include fastcgi_params; - fastcgi_split_path_info ^(.+\.php)(/.+)$; - fastcgi_param SCRIPT_FILENAME $request_filename; - fastcgi_param PATH_INFO $fastcgi_path_info; - fastcgi_param HTTPS on; - fastcgi_param modHeadersAvailable true; - fastcgi_param REMOTE_USER $remote_user; - fastcgi_pass unix:/var/run/php5-fpm-#APP#.sock; - fastcgi_intercept_errors on; - } - - location ~ ^#PATH#/(?:updater|ocs-provider)(?:$|/) { - try_files $uri/ =404; - index index.php; - } - - # Adding the cache control header for js and css files - location ~* \.(?:css|js)$ { - add_header Cache-Control "public, max-age=7200"; - # Add headers to serve security related headers - add_header Strict-Transport-Security "max-age=15768000;"; - add_header X-Content-Type-Options nosniff; - add_header X-Frame-Options "SAMEORIGIN"; - add_header X-XSS-Protection "1; mode=block"; - add_header X-Robots-Tag none; - add_header X-Download-Options noopen; - add_header X-Permitted-Cross-Domain-Policies none; - # Optional: Don't log access to assets - access_log off; - } - - location ~* \.(?:svg|gif|png|html|ttf|woff|ico|jpg|jpeg)$ { - # Optional: Don't log access to other assets - access_log off; - } - - # show YunoHost panel access - include conf.d/yunohost_panel.conf.inc; +#sub_path_only rewrite ^__PATH__$ __PATH__/ permanent; +location __PATH__/ { + + proxy_pass https://127.0.0.1:__PORT__; + proxy_redirect off; + proxy_set_header Host $host; + proxy_set_header X-Real-IP $remote_addr; + proxy_set_header X-Forwarded-Proto $scheme; + proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for; + proxy_set_header X-Forwarded-Host $server_name; + + proxy_buffers 4 256k; + proxy_buffer_size 128k; + proxy_busy_buffers_size 256k; + + client_max_body_size 0; } diff --git a/conf/owncloud-deps.control b/conf/owncloud-deps.control deleted file mode 100644 index 4618e9e..0000000 --- a/conf/owncloud-deps.control +++ /dev/null @@ -1,16 +0,0 @@ -Section: misc -Priority: optional -Homepage: https://owncloud.org/ -Standards-Version: 3.9.2 - -Package: owncloud-deps -Version: 9.0.0-1 -Depends: acl, php5-cli, php5-apcu, tar, smbclient, php5-zip -Architecture: all -Description: meta package for owncloud dependencies - ownCloud gives you universal access to your files through a web - interface or WebDAV. It also provides a platform to easily view & sync - your contacts, calendars and bookmarks across all your devices and - enables basic editing right on the web. - . - This meta-package is only responsible of installing its dependencies. diff --git a/conf/owncloud.cron b/conf/owncloud.cron deleted file mode 100644 index 294325b..0000000 --- a/conf/owncloud.cron +++ /dev/null @@ -1 +0,0 @@ -*/15 * * * * #USER# /usr/bin/php -f #DESTDIR#/cron.php diff --git a/conf/php-fpm.conf b/conf/php-fpm.conf deleted file mode 100644 index 42216d9..0000000 --- a/conf/php-fpm.conf +++ /dev/null @@ -1,71 +0,0 @@ -[#POOLNAME#] -; The address on which to accept FastCGI requests. -listen = /var/run/php5-fpm-#POOLNAME#.sock - -; Set permissions for unix socket, if one is used. -listen.owner = www-data -listen.group = www-data -listen.mode = 0600 - -; Unix user/group of processes. -user = #USER# -group = #GROUP# - -; Choose how the process manager will control the number of child processes. -pm = dynamic - -; The number of child processes to be created when pm is set to 'static' and the -; maximum number of child processes to be created when pm is set to 'dynamic'. -pm.max_children = 6 - -; The number of child processes created on startup. -pm.start_servers = 3 - -; The desired minimum number of idle server processes. -pm.min_spare_servers = 3 - -; The desired maximum number of idle server processes. -pm.max_spare_servers = 5 - -; The number of requests each child process should execute before respawning. -pm.max_requests = 500 - -; The URI to view the FPM status page. If this value is not set, no URI will be -; recognized as a status page. -pm.status_path = /fpm-status - -; The ping URI to call the monitoring page of FPM. If this value is not set, no -; URI will be recognized as a ping page. -ping.path = /ping - -; The timeout for serving a single request after which the worker process will -; be killed. -request_terminate_timeout = 1d - -; The timeout for serving a single request after which a PHP backtrace will be -; dumped to the 'slowlog' file. A value of '0s' means 'off'. -request_slowlog_timeout = 5s - -; The log file for slow requests. -slowlog = /var/log/nginx/#POOLNAME#.slow.log - -; Set open file descriptor rlimit. -rlimit_files = 4096 - -; Set max core size rlimit. -rlimit_core = 0 - -; Chdir to this directory at the start. -chdir = #DESTDIR# - -; Redirect worker stdout and stderr into main error log. -catch_workers_output = yes - -; Do not clear environment in FPM workers. -clear_env = no - -; Additional php.ini defines, specific to this pool of workers. -php_value[upload_max_filesize] = 10G -php_value[post_max_size] = 10G -php_value[default_charset] = UTF-8 -php_value[always_populate_raw_post_data] = -1 diff --git a/conf/systemd.service b/conf/systemd.service new file mode 100644 index 0000000..947750d --- /dev/null +++ b/conf/systemd.service @@ -0,0 +1,48 @@ +[Unit] +Description=Owncloud server + +[Service] +Type=simple +User=__APP__ +Group=__APP__ +Environment=PROXY_HTTP_ADDR=127.0.0.1:__PORT__ +Environment=OCIS_URL=https://__DOMAIN__ +ExecStart=__INSTALL_DIR__/owncloud server +Restart=always + +# Sandboxing options to harden security +# Depending on specificities of your service/app, you may need to tweak these +# .. but this should be a good baseline +# Details for these options: https://www.freedesktop.org/software/systemd/man/systemd.exec.html +NoNewPrivileges=yes +PrivateTmp=yes +PrivateDevices=yes +RestrictAddressFamilies=AF_UNIX AF_INET AF_INET6 AF_NETLINK +RestrictNamespaces=yes +RestrictRealtime=yes +DevicePolicy=closed +ProtectClock=yes +ProtectHostname=yes +ProtectProc=invisible +ProtectSystem=full +ProtectControlGroups=yes +ProtectKernelModules=yes +ProtectKernelTunables=yes +LockPersonality=yes +SystemCallArchitectures=native +SystemCallFilter=~@clock @debug @module @mount @obsolete @reboot @setuid @swap @cpu-emulation @privileged + +# Denying access to capabilities that should not be relevant for webapps +# Doc: https://man7.org/linux/man-pages/man7/capabilities.7.html +CapabilityBoundingSet=~CAP_RAWIO CAP_MKNOD +CapabilityBoundingSet=~CAP_AUDIT_CONTROL CAP_AUDIT_READ CAP_AUDIT_WRITE +CapabilityBoundingSet=~CAP_SYS_BOOT CAP_SYS_TIME CAP_SYS_MODULE CAP_SYS_PACCT +CapabilityBoundingSet=~CAP_LEASE CAP_LINUX_IMMUTABLE CAP_IPC_LOCK +CapabilityBoundingSet=~CAP_BLOCK_SUSPEND CAP_WAKE_ALARM +CapabilityBoundingSet=~CAP_SYS_TTY_CONFIG +CapabilityBoundingSet=~CAP_MAC_ADMIN CAP_MAC_OVERRIDE +CapabilityBoundingSet=~CAP_NET_ADMIN CAP_NET_BROADCAST CAP_NET_RAW +CapabilityBoundingSet=~CAP_SYS_ADMIN CAP_SYS_PTRACE CAP_SYSLOG + +[Install] +WantedBy=multi-user.target diff --git a/config_panel.toml.example b/config_panel.toml.example new file mode 100644 index 0000000..c6bccd8 --- /dev/null +++ b/config_panel.toml.example @@ -0,0 +1,295 @@ + +## Config panel are available from webadmin > Apps > YOUR_APP > Config Panel Button +## Those panels let user configure some params on their apps using a friendly interface, +## and remove the need to manually edit files from the command line. + +## From a packager perspective, this .toml is coupled to the scripts/config script, +## which may be used to define custom getters/setters. However, most use cases +## should be covered automagically by the core, thus it may not be necessary +## to define a scripts/config at all! + +## ----------------------------------------------------------------------------- +## IMPORTANT: In accordance with YunoHost's spirit, please keep things simple and +## do not overwhelm the admin with tons of misunderstandable or advanced settings. +## ----------------------------------------------------------------------------- + +## The top level describe the entire config panels screen. + +## The version is a required property. +## Here a small reminder to associate config panel version with YunoHost version +## | Config | YNH | Config panel small change log | +## | ------ | --- | ------------------------------------------------------- | +## | 0.1 | 3.x | 0.1 config script not compatible with YNH >= 4.3 | +## | 1.0 | 4.3.x | The new config panel system with 'bind' property | +version = "1.0" + +## (optional) i18n property let you internationalize questions, however this feature +## is only available in core configuration panel (like yunohost domain config). +## So in app config panel this key is ignored for now, but you can internationalize +## by using a lang dictionary (see property name bellow) +# i18n = "prefix_translation_key" + +################################################################################ +#### ABOUT PANELS +################################################################################ + +## The next level describes web admin panels +## You have to choose an ID for each panel, in this example the ID is "main" +## Keep in mind this ID will be used in CLI to refer to your question, so choose +## something short and meaningfull. +## In the webadmin, each panel corresponds to a distinct tab / form +[main] + +## Define the label for your panel +## Internationalization works similarly to the 'description' and 'ask' questions in the manifest +# name.en = "Main configuration" +# name.fr = "Configuration principale" + +## (optional) If you need to trigger a service reload-or-restart after the user +## change a question in this panel, you can add your service in the list. +services = ["__APP__"] +# or services = ["nginx", "__APP__"] to also reload-or-restart nginx + +## (optional) This help properties is a short help displayed on the same line +## than the panel title but not displayed in the tab. +# help = "" + + ############################################################################ + #### ABOUT SECTIONS + ############################################################################ + + ## A panel is composed of one or several sections. + ## + ## Sections are meant to group questions together when they correspond to + ## a same subtopic. This impacts the rendering in terms of CLI prompts + ## and HTML forms + ## + ## You should choose an ID for your section, and prefix it with the panel ID + ## (Be sure to not make a typo in the panel ID, which would implicitly create + ## an other entire panel) + ## + ## We use the context of pepettes_ynh as an example, + ## which is a simple donation form app written in python, + ## and for which the admin will want to edit the configuration + [main.customization] + + ## (optional) Defining a proper title for sections is not mandatory + ## and depends on the exact rendering you're aiming for the CLI / webadmin + name = "" + + ## (optional) This help properties is a short help displayed on the same line + ## than the section title, meant to provide additional details + # help = "" + + ## (optional) As for panel, you can specify to trigger a service + ## reload-or-restart after the user change a question in this section. + ## This property is added to the panel property, it doesn't deactivate it. + ## So no need to replicate, the service list from panel services property. + # services = [] + + ## (optional) By default all questions are optionals, but you can specify a + ## default behaviour for question in the section + optional = false + + ## (optional) It's also possible with the 'visible' property to only + ## display the section depending on the user's answers to previous questions. + ## + ## Be careful that the 'visible' property should only refer to **previous** questions + ## Hence, it should not make sense to have a "visible" property on the very first section. + ## + ## Also, keep in mind that this feature only works in the webadmin and not in CLI + ## (therefore a user could be prompted in CLI for a question that may not be relevant) + # visible = true + + ######################################################################## + #### ABOUT QUESTIONS + ######################################################################## + + ## A section is compound of one or several questions. + + ## --------------------------------------------------------------------- + ## IMPORTANT: as for panel and section you have to choose an ID, but this + ## one should be unique in all this document, even if the question is in + ## an other panel. + ## --------------------------------------------------------------------- + + ## You can use same questions types and properties than in manifest.yml + ## install part. However, in YNH 4.3, a lot of change has been made to + ## extend availables questions types list. + ## See: TODO DOC LINK + + [main.customization.project_name] + + ## (required) The ask property is equivalent to the ask property in + ## the manifest. However, in config panels, questions are displayed on the + ## left side and therefore have less space to be rendered. Therefore, + ## it is better to use a short question, and use the "help" property to + ## provide additional details if necessary. + ask.en = "Name of the project" + + ## (required) The type property indicates how the question should be + ## displayed, validated and managed. Some types have specific properties. + ## + ## Types available: string, boolean, number, range, text, password, path + ## email, url, date, time, color, select, domain, user, tags, file. + ## + ## For a complete list with specific properties, see: TODO DOC LINK + type = "string" + + ######################################################################## + #### ABOUT THE BIND PROPERTY + ######################################################################## + + ## (recommended) 'bind' property is a powerful feature that let you + ## configure how and where the data will be read, validated and written. + + ## By default, 'bind property is in "settings" mode, it means it will + ## **only** read and write the value in application settings file. + ## bind = "settings" + + ## However, settings usually correspond to key/values in actual app configurations + ## Hence, a more useful mode is to have bind = ":FILENAME". In that case, YunoHost + ## will automagically find a line with "KEY=VALUE" in FILENAME + ## (with the adequate separator between KEY and VALUE) + ## + ## YunoHost will then use this value for the read/get operation. + ## During write/set operations, YunoHost will overwrite the value + ## in **both** FILENAME and in the app's settings.yml + + ## Configuration file format supported: yaml, toml, json, ini, env, php, + ## python. The feature probably works with others formats, but should be tested carefully. + + ## Note that this feature only works with relatively simple cases + ## such as `KEY: VALUE`, but won't properly work with + ## complex data structures like multilin array/lists or dictionnaries. + ## It also doesn't work with XML format, custom config function call, php define(), ... + + ## More info on TODO + # bind = ":/var/www/__APP__/settings.py" + + + ## By default, bind = ":FILENAME" will use the question ID as KEY + ## ... but the question ID may sometime not be the exact KEY name in the configuration file. + ## + ## In particular, in pepettes, the python variable is 'name' and not 'project_name' + ## (c.f. https://github.com/YunoHost-Apps/pepettes_ynh/blob/5cc2d3ffd6529cc7356ff93af92dbb6785c3ab9a/conf/settings.py##L11 ) + ## + ## In that case, the key name can be specified before the column ':' + + bind = "name:/var/www/__APP__/settings.py" + + ## --------------------------------------------------------------------- + ## IMPORTANT: other 'bind' mode exists: + ## + ## bind = "FILENAME" (with no column character before FILENAME) + ## may be used to bind to the **entire file content** (instead of a single KEY/VALUE) + ## This could be used to expose an entire configuration file, or binary files such as images + ## For example: + ## bind = "/var/www/__APP__/img/logo.png" + ## + ## bind = "null" can be used to disable reading / writing in settings. + ## This creates sort of a "virtual" or "ephemeral" question which is not related to any actual setting + ## In this mode, you are expected to define custom getter/setters/validators in scripts/config: + ## + ## getter: get__QUESTIONID() + ## setter: set__QUESTIONID() + ## validator: validate__QUESTIONID() + ## + ## You can also specify a common getter / setter / validator, with the + ## function 'bind' mode, for example here it will try to run + ## get__array_settings() first. + # bind = "array_settings()" + ## --------------------------------------------------------------------- + + ## --------------------------------------------------------------------- + ## IMPORTANT: with the exception of bind=null questions, + ## question IDs should almost **always** correspond to an app setting + ## initialized / reused during install/upgrade. + ## Not doing so may result in inconsistencies between the config panel mechanism + ## and the use of ynh_add_config + ## --------------------------------------------------------------------- + + ######################################################################## + #### OTHER GENERIC PROPERTY FOR QUESTIONS + ######################################################################## + + ## (optional) An help text for the question + help = "Fill the name of the project which will received donation" + + ## (optional) An example display as placeholder in web form + # example = "YunoHost" + + ## (optional) set to true in order to redact the value in operation logs + # redact = false + + ## (optional) A validation pattern + ## --------------------------------------------------------------------- + ## IMPORTANT: your pattern should be between simple quote, not double. + ## --------------------------------------------------------------------- + pattern.regexp = '^\w{3,30}$' + pattern.error = "The name should be at least 3 chars and less than 30 chars. Alphanumeric chars are accepted" + + ## Note: visible and optional properties are also available for questions + + + [main.customization.contact_url] + ask = "Contact url" + type = "url" + example = "mailto: contact@example.org" + help = "mailto: accepted" + pattern.regexp = '^mailto:[^@]+@[^@]+|https://$' + pattern.error = "Should be https or mailto:" + bind = ":/var/www/__APP__/settings.py" + + [main.customization.logo] + ask = "Logo" + type = "file" + accept = ".png" + help = "Fill with an already resized logo" + bind = "__FINALPATH__/img/logo.png" + + [main.customization.favicon] + ask = "Favicon" + type = "file" + accept = ".png" + help = "Fill with an already sized favicon" + bind = "__FINALPATH__/img/favicon.png" + + + [main.stripe] + name = "Stripe general info" + optional = false + + # The next alert is overwrited with a getter from the config script + [main.stripe.amount] + ask = "Donation in the month : XX € + type = "alert" + style = "success" + + [main.stripe.publishable_key] + ask = "Publishable key" + type = "string" + redact = true + help = "Indicate here the stripe publishable key" + bind = ":/var/www/__APP__/settings.py" + + [main.stripe.secret_key] + ask = "Secret key" + type = "string" + redact = true + help = "Indicate here the stripe secret key" + bind = ":/var/www/__APP__/settings.py" + + [main.stripe.prices] + ask = "Prices ID" + type = "tags" + help = """\ + Indicates here the prices ID of donation products you created in stripe interfaces. \ + Go on [Stripe products](https://dashboard.stripe.com/products) to create those donation products. \ + Fill it tag with 'FREQUENCY/CURRENCY/PRICE_ID' \ + FREQUENCY: 'one_time' or 'recuring' \ + CURRENCY: 'EUR' or 'USD' \ + PRICE_ID: ID from stripe interfaces starting with 'price_' \ + """ + pattern.regexp = '^(one_time|recuring)/(EUR|USD)/price_.*$' + pattern.error = "Please respect the format describe in help text for each price ID" diff --git a/doc/.gitkeep b/doc/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/doc/DESCRIPTION.md b/doc/DESCRIPTION.md new file mode 100644 index 0000000..f957a87 --- /dev/null +++ b/doc/DESCRIPTION.md @@ -0,0 +1 @@ +ownCloud Infinite Scale (oCIS) is the new file sync & share platform that will be the foundation of your data management platform. \ No newline at end of file diff --git a/doc/DESCRIPTION_fr.md b/doc/DESCRIPTION_fr.md new file mode 100644 index 0000000..9e28f59 --- /dev/null +++ b/doc/DESCRIPTION_fr.md @@ -0,0 +1 @@ +ownCloud Infinite Scale (oCIS) est la nouvelle plateforme de synchronisation et de partage de fichiers qui constituera la base de votre plateforme de gestion de données. diff --git a/doc/POST_INSTALL.md b/doc/POST_INSTALL.md new file mode 100644 index 0000000..6687031 --- /dev/null +++ b/doc/POST_INSTALL.md @@ -0,0 +1 @@ +Connect to ownCloud with `admin` as a username and the password selected at install. \ No newline at end of file diff --git a/doc/POST_INSTALL_fr.md b/doc/POST_INSTALL_fr.md new file mode 100644 index 0000000..cbee989 --- /dev/null +++ b/doc/POST_INSTALL_fr.md @@ -0,0 +1 @@ +Connectez-vous à ownCloud avec « admin » comme nom d'utilisateur et le mot de passe sélectionné lors de l'installation. \ No newline at end of file diff --git a/doc/screenshots/.gitkeep b/doc/screenshots/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/doc/screenshots/screenshot.png b/doc/screenshots/screenshot.png new file mode 100644 index 0000000..31145f4 Binary files /dev/null and b/doc/screenshots/screenshot.png differ diff --git a/hooks/post_user_create b/hooks/post_user_create deleted file mode 100644 index 24ebf8c..0000000 --- a/hooks/post_user_create +++ /dev/null @@ -1,6 +0,0 @@ -#!/bin/bash - -user=$1 - -sudo mkdir -p /home/$user -sudo setfacl -m g:#GROUP#:rwx /home/$user diff --git a/manifest.json b/manifest.json deleted file mode 100644 index 180f241..0000000 --- a/manifest.json +++ /dev/null @@ -1,66 +0,0 @@ -{ - "package_format": 1, - "id": "owncloud", - "name": "OwnCloud", - "description": { - "en": "Sync & share your files, pictures, music, contacts, calendars, and much more!", - "fr": "Synchronisez et partagez vos fichiers, images, musiques, contacts, calendriers, et bien plus !" - }, - "url": "https://owncloud.org", - "license": "AGPL-3", - "version": "9.0.5", - "maintainer": { - "name": "jerome", - "email": "jerome@yunohost.org" - }, - "multi_instance": "true", - "services": [ - "nginx", - "php5-fpm", - "mysql" - ], - "requirements": { - "yunohost": ">= 2.3.16" - }, - "arguments": { - "install" : [ - { - "name": "domain", - "type": "domain", - "ask": { - "en": "Choose a domain for ownCloud", - "fr": "Choisissez un domaine pour ownCloud" - }, - "example": "domain.org" - }, - { - "name": "path", - "type": "path", - "ask": { - "en": "Choose a path for ownCloud", - "fr": "Choisissez un chemin pour ownCloud" - }, - "example": "/owncloud", - "default": "/owncloud" - }, - { - "name": "admin", - "type": "user", - "ask": { - "en": "Choose the ownCloud administrator (must be an existing YunoHost user)", - "fr": "Choisissez l'administrateur d'ownCloud (doit être un utilisateur YunoHost déjà existant)" - }, - "example": "homer" - }, - { - "name": "user_home", - "type": "boolean", - "ask": { - "en": "Access the users home folder from ownCloud?", - "fr": "Accéder au dossier personnel des utilisateurs depuis ownCloud ?" - }, - "default": false - } - ] - } -} diff --git a/manifest.toml b/manifest.toml new file mode 100644 index 0000000..b302877 --- /dev/null +++ b/manifest.toml @@ -0,0 +1,63 @@ +packaging_format = 2 + +id = "owncloud" +name = "ownCloud" +description.en = "Online storage, file sharing platform and various other applications" +description.fr = "Stockage en ligne, plateforme de partage de fichiers et diverses autres applications" + +version = "4.0.1~ynh1" + +maintainers = [""] + +[upstream] +license = "Apache-2.0" +website = "https://owncloud.com" +admindoc = "https://doc.owncloud.com/ocis/next/" +code = "https://github.com/owncloud/ocis" + +[integration] +yunohost = ">= 11.2" +architectures = ["amd64", "arm64", "armhf", "i386"] +multi_instance = false +ldap = false +sso = false +disk = "50M" +ram.build = "300M" +ram.runtime = "50M" + +[install] + [install.domain] + type = "domain" + + [install.init_main_permission] + type = "group" + default = "visitors" + + [install.password] + type = "password" + +[resources] + + [resources.sources.main] + amd64.url = "https://download.owncloud.com/ocis/ocis/stable/4.0.1/ocis-4.0.1-linux-amd64" + amd64.sha256 = "91f21d74099f5ae24ea4686913e8c916b20736c3f6dd64b5536957af5a5e31ae" + i386.url = "https://download.owncloud.com/ocis/ocis/stable/4.0.1/ocis-4.0.1-linux-386" + i386.sha256 = "68f876f2f094e1c2f0056a39910c0a94751b4138d211ffeae11b56e53ff37998" + arm64.url = "https://download.owncloud.com/ocis/ocis/stable/4.0.1/ocis-4.0.1-linux-arm64" + arm64.sha256 = "0003cb8d81c8468397229e917ffdd25476d1355eb1258b08e855473880398da9" + armhf.url = "https://download.owncloud.com/ocis/ocis/stable/4.0.1/ocis-4.0.1-linux-arm" + armhf.sha256 = "d6cd4c21356f0ebaaa8bfda0e2b3bd481402248af4647c901141f85febc16106" + in_subdir = false + rename = "owncloud" + + [resources.ports] + main.default = 9200 + + [resources.system_user] + + [resources.install_dir] + + [resources.data_dir] + + [resources.permissions] + main.url = "/" diff --git a/patches/00-add-logout_url-conf.patch b/patches/00-add-logout_url-conf.patch deleted file mode 100644 index 54388e2..0000000 --- a/patches/00-add-logout_url-conf.patch +++ /dev/null @@ -1,15 +0,0 @@ ---- a/lib/base.php 2016-04-04 21:26:47.281448433 +0200 -+++ b/lib/base.php 2016-04-04 21:27:16.034283534 +0200 -@@ -920,8 +920,10 @@ - \OC::$server->getConfig()->deleteUserValue(OC_User::getUser(), 'login_token', $_COOKIE['oc_token']); - } - OC_User::logout(); -- // redirect to webroot and add slash if webroot is empty -- header("Location: " . \OC::$server->getURLGenerator()->getAbsoluteURL('/')); -+ // Use system config or redirect to webroot and add slash if webroot is empty -+ $redirect_url = $systemConfig->getValue('logout_url', -+ \OC::$server->getURLGenerator()->getAbsoluteURL('/')); -+ header("Location: " . $redirect_url); - } else { - // Redirect to default application - OC_Util::redirectToDefaultPage(); diff --git a/scripts/_common.sh b/scripts/_common.sh index d1a5e4b..1e47ce7 100644 --- a/scripts/_common.sh +++ b/scripts/_common.sh @@ -1,82 +1,19 @@ -# -# Common variables -# +#!/bin/bash -APPNAME="owncloud" +#================================================= +# COMMON VARIABLES +#================================================= +# PHP APP SPECIFIC +#================================================= -# ownCloud version -VERSION="9.0.5" +#================================================= +# PERSONAL HELPERS +#================================================= -# Package name for ownCloud dependencies -DEPS_PKG_NAME="owncloud-deps" +#================================================= +# EXPERIMENTAL HELPERS +#================================================= -# Remote URL to fetch ownCloud tarball -OWNCLOUD_SOURCE_URL="https://download.owncloud.org/community/owncloud-${VERSION}.tar.bz2" - -# Remote URL to fetch ownCloud tarball checksum -OWNCLOUD_SOURCE_SHA256="c8c2c4f7a06208f006762740ca6bb6a4c4d8362fc8d226dcccb82b970993f7c5" - -# App package root directory should be the parent folder -PKGDIR=$(cd ../; pwd) - -# -# Common helpers -# - -# Download and extract ownCloud sources to the given directory -# usage: extract_owncloud DESTDIR [AS_USER] -extract_owncloud() { - local DESTDIR=$1 - local AS_USER=${2:-admin} - - # retrieve and extract Roundcube tarball - oc_tarball="/tmp/owncloud.tar.bz2" - rm -f "$oc_tarball" - wget -q -O "$oc_tarball" "$OWNCLOUD_SOURCE_URL" \ - || ynh_die "Unable to download ownCloud tarball" - echo "$OWNCLOUD_SOURCE_SHA256 $oc_tarball" | sha256sum -c >/dev/null \ - || ynh_die "Invalid checksum of downloaded tarball" - exec_as "$AS_USER" tar xjf "$oc_tarball" -C "$DESTDIR" --strip-components 1 \ - || ynh_die "Unable to extract ownCloud tarball" - rm -f "$oc_tarball" - - # apply patches - (cd "$DESTDIR" \ - && for p in ${PKGDIR}/patches/*.patch; do \ - exec_as "$AS_USER" patch -p1 < $p; done) \ - || ynh_die "Unable to apply patches to ownCloud" -} - -# Execute a command as another user -# usage: exec_as USER COMMAND [ARG ...] -exec_as() { - local USER=$1 - shift 1 - - if [[ $USER = $(whoami) ]]; then - eval "$@" - else - # use sudo twice to be root and be allowed to use another user - sudo sudo -u "$USER" "$@" - fi -} - -# Execute a command with occ as a given user from a given directory -# usage: exec_occ WORKDIR AS_USER COMMAND [ARG ...] -exec_occ() { - local WORKDIR=$1 - local AS_USER=$2 - shift 2 - - (cd "$WORKDIR" && exec_as "$AS_USER" \ - php occ --no-interaction --no-ansi "$@") -} - -# Check if an URL is already handled -# usage: is_url_handled URL -is_url_handled() { - local OUTPUT=($(curl -k -s -o /dev/null \ - -w 'x%{redirect_url} %{http_code}' "$1")) - # it's handled if it does not redirect to the SSO nor return 404 - [[ ! ${OUTPUT[0]} =~ \/yunohost\/sso\/ && ${OUTPUT[1]} != 404 ]] -} +#================================================= +# FUTURE OFFICIAL HELPERS +#================================================= diff --git a/scripts/backup b/scripts/backup index 81606b8..cf2d1b6 100755 --- a/scripts/backup +++ b/scripts/backup @@ -1,39 +1,46 @@ #!/bin/bash -set -eu +#================================================= +# GENERIC START +#================================================= +# IMPORT GENERIC HELPERS +#================================================= -# Get multi-instances specific variables -app=$YNH_APP_INSTANCE_NAME +# Keep this path for calling _common.sh inside the execution's context of backup and restore scripts +source ../settings/scripts/_common.sh +source /usr/share/yunohost/helpers -# Set app specific variables -dbname=$app -dbuser=$app +#================================================= +# DECLARE DATA AND CONF FILES TO BACKUP +#================================================= +ynh_print_info --message="Declaring files to be backed up..." -# Source app helpers -. /usr/share/yunohost/helpers +#================================================= +# BACKUP THE APP MAIN DIR +#================================================= -# Retrieve app settings -domain=$(ynh_app_setting_get "$app" domain) -path=$(ynh_app_setting_get "$app" path) -dbpass=$(ynh_app_setting_get "$app" mysqlpwd) +ynh_backup --src_path="$install_dir" -# Copy the app source files -DESTDIR="/var/www/$app" -ynh_backup "$DESTDIR" "www" +#================================================= +# BACKUP THE DATA DIR +#================================================= -# Copy the data directory -DATADIR="/home/yunohost.app/${app}/data" -ynh_backup "$DATADIR" "data" 1 +ynh_backup --src_path="$data_dir" --is_big -# Copy the conf files -mkdir ./conf -ynh_backup "/etc/nginx/conf.d/${domain}.d/${app}.conf" "conf/nginx.conf" -ynh_backup "/etc/php5/fpm/pool.d/${app}.conf" "conf/php-fpm.conf" -ynh_backup "/etc/cron.d/${app}" "conf/cron" +#================================================= +# BACKUP THE NGINX CONFIGURATION +#================================================= -# Dump the database -mysqldump -u "$dbuser" -p"$dbpass" --no-create-db "$dbname" > ./db.sql +ynh_backup --src_path="/etc/nginx/conf.d/$domain.d/$app.conf" -# Copy the control file of the dependency package -# FIXME: find a way to retrieve package name from _common.sh? -dpkg-query -s owncloud-deps > ./owncloud-deps.control +#================================================= +# BACKUP SYSTEMD +#================================================= + +ynh_backup --src_path="/etc/systemd/system/$app.service" + +#================================================= +# END OF SCRIPT +#================================================= + +ynh_print_info --message="Backup script completed for $app. (YunoHost will then actually copy those files to the archive)." diff --git a/scripts/change_url b/scripts/change_url new file mode 100644 index 0000000..3a9b28d --- /dev/null +++ b/scripts/change_url @@ -0,0 +1,41 @@ +#!/bin/bash + +#================================================= +# GENERIC STARTING +#================================================= +# IMPORT GENERIC HELPERS +#================================================= + +source _common.sh +source /usr/share/yunohost/helpers + +#================================================= +# STANDARD MODIFICATIONS +#================================================= +# STOP SYSTEMD SERVICE +#================================================= +ynh_script_progression --message="Stopping a systemd service..." --weight=1 + +ynh_systemd_action --service_name=$app --action="stop" --log_path="systemd" + +#================================================= +# MODIFY URL IN NGINX CONF +#================================================= +ynh_script_progression --message="Updating NGINX web server configuration..." --weight=1 + +ynh_change_url_nginx_config + +#================================================= +# GENERIC FINALISATION +#================================================= +# START SYSTEMD SERVICE +#================================================= +ynh_script_progression --message="Starting a systemd service..." --weight=1 + +ynh_systemd_action --service_name=$app --action="start" --log_path="systemd" + +#================================================= +# END OF SCRIPT +#================================================= + +ynh_script_progression --message="Change of URL completed for $app" --last diff --git a/scripts/config b/scripts/config new file mode 100644 index 0000000..b9e79f8 --- /dev/null +++ b/scripts/config @@ -0,0 +1,102 @@ +#!/bin/bash +# In simple cases, you don't need a config script. + +# With a simple config_panel.toml, you can write in the app settings, in the +# upstream config file or replace complete files (logo ...) and restart services. + +# The config scripts allows you to go further, to handle specific cases +# (validation of several interdependent fields, specific getter/setter for a value, +# display dynamic informations or choices, pre-loading of config type .cube... ). + +#================================================= +# GENERIC STARTING +#================================================= +# IMPORT GENERIC HELPERS +#================================================= + +source /usr/share/yunohost/helpers + +ynh_abort_if_errors + +#================================================= +# RETRIEVE ARGUMENTS +#================================================= + +final_path=$(ynh_app_setting_get $app final_path) + +#================================================= +# SPECIFIC GETTERS FOR TOML SHORT KEY +#================================================= + +get__amount() { + # Here we can imagine to have an API call to stripe to know the amount of donation during a month + local amount = 200 + + # It's possible to change some properties of the question by overriding it: + if [ $amount -gt 100 ] + then + cat << EOF +style: success +value: $amount +ask: + en: A lot of donation this month: **$amount €** +EOF + else + cat << EOF +style: danger +value: $amount +ask: + en: Not so much donation this month: $amount € +EOF + fi +} + +get__prices() { + local prices = "$(grep "DONATION\['" "$final_path/settings.py" | sed -r "s@^DONATION\['([^']*)'\]\['([^']*)'\] = '([^']*)'@\1/\2/\3@g" | sed -z 's/\n/,/g;s/,$/\n/')" + if [ "$prices" == "," ]; + then + # Return YNH_NULL if you prefer to not return a value at all. + echo YNH_NULL + else + echo $prices + fi +} + + +#================================================= +# SPECIFIC VALIDATORS FOR TOML SHORT KEYS +#================================================= +validate__publishable_key() { + + # We can imagine here we test if the key is really a publisheable key + (is_secret_key $publishable_key) && + echo 'This key seems to be a secret key' +} + +#================================================= +# SPECIFIC SETTERS FOR TOML SHORT KEYS +#================================================= +set__prices() { + + #--------------------------------------------- + # IMPORTANT: setter are trigger only if a change is detected + #--------------------------------------------- + for price in $(echo $prices | sed "s/,/ /"); do + frequency=$(echo $price | cut -d/ -f1) + currency=$(echo $price | cut -d/ -f2) + price_id=$(echo $price | cut -d/ -f3) + sed "d/DONATION\['$frequency'\]\['$currency'\]" "$final_path/settings.py" + + echo "DONATION['$frequency']['$currency'] = '$price_id'" >> "$final_path/settings.py" + done + + #--------------------------------------------- + # IMPORTANT: to be able to upgrade properly, you have to saved the value in settings too + #--------------------------------------------- + ynh_app_setting_set $app prices $prices +} + +#================================================= +# GENERIC FINALIZATION +#================================================= +ynh_app_config_run $1 diff --git a/scripts/install b/scripts/install index 48c4b48..02b5e4d 100755 --- a/scripts/install +++ b/scripts/install @@ -1,178 +1,71 @@ #!/bin/bash -set -eu +#================================================= +# GENERIC START +#================================================= +# IMPORT GENERIC HELPERS +#================================================= -# Get multi-instances specific variables -app=$YNH_APP_INSTANCE_NAME +source _common.sh +source /usr/share/yunohost/helpers -# Retrieve arguments -domain=$1 -path=${2%/} -admin=$3 -user_home=$4 +#================================================= +# DOWNLOAD, CHECK AND UNPACK SOURCE +#================================================= +ynh_script_progression --message="Setting up source files..." --weight=1 -# Load common variables -. ./_common.sh +# Download, check integrity, uncompress and patch the source from app.src +ynh_setup_source --dest_dir="$install_dir" -# Set app specific variables -dbname=$app -dbuser=$app +chmod 750 "$install_dir" +chmod -R o-rwx "$install_dir" +chown -R $app:www-data "$install_dir" +chmod +x $install_dir/owncloud -# Source app helpers -. /usr/share/yunohost/helpers +#================================================= +# NGINX CONFIGURATION +#================================================= +ynh_script_progression --message="Configuring NGINX web server..." --weight=1 -# TODO: Check domain/path availability with app helper -sudo yunohost app checkurl $domain$path -a $app \ - || ynh_die "The path ${domain}${path} is not available for app installation." +# Create a dedicated NGINX config +ynh_add_nginx_config -# Check user parameter -ynh_user_exists "$admin" \ - || ynh_die "The chosen admin user does not exist." -ynh_app_setting_set $app admin_user $admin +# Create a dedicated systemd config +ynh_add_systemd_config -# Check destination directory -DESTDIR="/var/www/$app" -[[ -d $DESTDIR ]] && ynh_die \ -"The destination directory '$DESTDIR' already exists.\ - You should safely delete it before installing this app." +yunohost service add $app --description="File sharing platform" --log="/var/log/$app/$app.log" -# Define app's data directory -DATADIR="/home/yunohost.app/${app}/data" +#================================================= +# ADD A CONFIGURATION +#================================================= +#ynh_script_progression --message="Adding a configuration file..." --weight=1 -# Install dependencies -ynh_package_install_from_equivs ../conf/${DEPS_PKG_NAME}.control \ - || ynh_die "Unable to install dependencies" +#ynh_add_config --template="../conf/.env" --destination="$install_dir/.env" -# Generate random password -dbpass=$(ynh_string_random) +#chmod 600 "$install_dir/.env" +#chown $app:$app "$install_dir/.env" -# Initialize database -ynh_mysql_create_db $dbname $dbuser $dbpass +#================================================= +# INSTALL OWNCLOUD +#================================================= +ynh_script_progression --message="Installing $app..." --weight=3 -# Create a system account for ownCloud -sudo useradd -c "$app system account" \ - -d /var/lib/$app --system --user-group $app \ - || ynh_die "Unable to create $app system account" +(cd "$install_dir" && ./owncloud init --insecure=true --force-overwrite=true --admin-password=$password --config-path=$install_dir/.ocis/config) -# Set system group in hooks -sed -i "s@#GROUP#@${app}@g" ../hooks/post_user_create +chmod 750 "$install_dir" +chmod -R o-rwx "$install_dir" +chown -R $app:www-data "$install_dir" -# Create app folders -sudo mkdir -p "$DESTDIR" "$DATADIR" +#================================================= +# START SYSTEMD SERVICE +#================================================= +ynh_script_progression --message="Starting a systemd service..." --weight=1 -# Copy ownCloud configuration file -oc_conf="${DESTDIR}/config.json" -sed -i "s@#DOMAIN#@${domain}@g" ../conf/config.json -sed -i "s@#DATADIR#@${DATADIR}@g" ../conf/config.json -sudo cp ../conf/config.json "$oc_conf" +# Start a systemd service +ynh_systemd_action --service_name=$app --action="start" --log_path="systemd" -# Copy and set nginx configuration -nginx_conf="/etc/nginx/conf.d/${domain}.d/${app}.conf" -sed -i "s@#APP#@${app}@g" ../conf/nginx.conf -sed -i "s@#PATH#@${path}@g" ../conf/nginx.conf -sed -i "s@#LOCATION#@${path:-/}@g" ../conf/nginx.conf -sed -i "s@#DESTDIR#@${DESTDIR}@g" ../conf/nginx.conf -# do not serve .well-known if it's already served on the domain -if is_url_handled "https://${domain}/.well-known/caldav" ; then - sed -ri '/^location = \/\.well\-known\/(caldav|carddav) \{/,/\}/d' \ - ../conf/nginx.conf -fi -sudo cp ../conf/nginx.conf "$nginx_conf" +#================================================= +# END OF SCRIPT +#================================================= -# Copy and set php-fpm configuration -phpfpm_conf="/etc/php5/fpm/pool.d/${app}.conf" -sed -i "s@#USER#@${app}@g" ../conf/php-fpm.conf -sed -i "s@#GROUP#@${app}@g" ../conf/php-fpm.conf -sed -i "s@#POOLNAME#@${app}@g" ../conf/php-fpm.conf -sed -i "s@#DESTDIR#@${DESTDIR}/@g" ../conf/php-fpm.conf -sudo cp ../conf/php-fpm.conf "$phpfpm_conf" -sudo chown root: $phpfpm_conf -sudo chmod 644 $phpfpm_conf - -# occ helper for the current installation -_exec_occ() { - exec_occ "$DESTDIR" "$app" $@ -} - -# Set app folders ownership -sudo chown -R $app: "$DESTDIR" "$DATADIR" - -# Retrieve ownCloud sources -extract_owncloud "$DESTDIR" "$app" - -# Install ownCloud using a temporary admin user -_exec_occ maintenance:install \ - --database "mysql" --database-name "$dbname" \ - --database-user "$dbuser" --database-pass "$dbpass" \ - --admin-user "admin" --admin-pass "$(ynh_string_random 6)" \ - --data-dir "$DATADIR" \ - || ynh_die "Unable to install ownCloud" - -# Enable plugins and set ownCloud configuration -_exec_occ app:enable user_ldap -_exec_occ ldap:create-empty-config -_exec_occ config:import "$oc_conf" -sudo rm -f "$oc_conf" - -# Check LDAP configuratio to see if everything worked well -_exec_occ ldap:test-config \'\' \ - || ynh_die "An error occured during LDAP configuration" - -# Enable External Storage and create local mount to home folder -if [[ $user_home -eq 1 ]]; then - _exec_occ app:enable files_external - _exec_occ files_external:create \ - 'Home' 'local' 'null::null' -c 'datadir=/home/$user' -fi - -# Add dynamic logout URL to the config -_exec_occ config:system:get logout_url >/dev/null 2>&1 \ - || sudo su -c "echo \" -//-YunoHost- -// set logout_url according to main domain -\\\$main_domain = exec('cat /etc/yunohost/current_host'); -\\\$CONFIG['logout_url'] = 'https://'.\\\$main_domain.'/yunohost/sso/?action=logout'; -//-YunoHost- -\" >> ${DESTDIR}/config/config.php" -- $app - -# Set the user as admin and delete admin user -ynh_mysql_connect_as $dbuser $dbpass $dbname \ - <<< "INSERT INTO oc_group_user VALUES ('admin','$admin');" -_exec_occ user:delete admin - -# Iterate over users to extend their home folder permissions - for the external -# storage plugin usage - and create relevant ownCloud directories -for u in $(ynh_user_list); do - sudo mkdir -p "${DATADIR}/${u}" - sudo setfacl -m g:$app:rwx "/home/$u" || true -done - -# Fix app ownerships & permissions -sudo chown -R $app: "$DESTDIR" "$DATADIR" -sudo find ${DESTDIR}/ -type f -print0 | sudo xargs -0 chmod 0644 -sudo find ${DESTDIR}/ -type d -print0 | sudo xargs -0 chmod 0755 -sudo find ${DATADIR}/ -type f -print0 | sudo xargs -0 chmod 0640 -sudo find ${DATADIR}/ -type d -print0 | sudo xargs -0 chmod 0750 -sudo chmod 640 "${DESTDIR}/config/config.php" -sudo chmod 755 /home/yunohost.app - -# Store app settings -ynh_app_setting_set "$app" user_home "$user_home" -ynh_app_setting_set "$app" mysqlpwd "$dbpass" - -# Set SSOwat rules -ynh_app_setting_set "$app" unprotected_uris "/" -ynh_app_setting_set "$app" skipped_regex \ - "$(sed 's/[\.\-]/\%&/g' <<< $domain)/%.well%-known/.*" - -# Reload services -sudo service php5-fpm restart || true -sudo service nginx reload || true - -# Add cron job -cron_path="/etc/cron.d/$app" -sed -i "s@#USER#@${app}@g" ../conf/owncloud.cron -sed -i "s@#DESTDIR#@${DESTDIR}@g" ../conf/owncloud.cron -sudo cp ../conf/owncloud.cron "$cron_path" -sudo chmod 644 "$cron_path" -_exec_occ background:cron +ynh_script_progression --message="Installation of $app completed" --last diff --git a/scripts/remove b/scripts/remove index d1957f5..57324bf 100755 --- a/scripts/remove +++ b/scripts/remove @@ -1,48 +1,35 @@ #!/bin/bash -# Get multi-instances specific variables -app=$YNH_APP_INSTANCE_NAME +#================================================= +# GENERIC START +#================================================= +# IMPORT GENERIC HELPERS +#================================================= -# Set app specific variables -dbname=$app -dbuser=$app +source _common.sh +source /usr/share/yunohost/helpers -# Load common variables and helpers -. ./_common.sh +#================================================= +# STANDARD REMOVE +#================================================= +# REMOVE SERVICE INTEGRATION IN YUNOHOST +#================================================= -# Source app helpers -. /usr/share/yunohost/helpers +# Remove the service from the list of services known by YunoHost (added from `yunohost service add`) +if ynh_exec_warn_less yunohost service status $app >/dev/null +then + ynh_script_progression --message="Removing $app service integration..." --weight=1 + yunohost service remove $app +fi -# Remove cron job -# TODO: Ensure that cron job is not running -sudo rm -f "/etc/cron.d/${app}" +# Remove the dedicated systemd config +ynh_remove_systemd_config -# Drop MySQL database and user -ynh_mysql_drop_db "$dbname" 2>/dev/null || true -ynh_mysql_drop_user "$dbuser" 2>/dev/null || true +# Remove the dedicated NGINX config +ynh_remove_nginx_config -# Retrieve domain from app settings -domain=$(ynh_app_setting_get $app domain) +#================================================= +# END OF SCRIPT +#================================================= -# Delete app directory and configurations -sudo rm -rf "/var/www/${app}" -sudo rm -f "/etc/php5/fpm/pool.d/${app}.conf" -[[ -n $domain ]] && sudo rm -f "/etc/nginx/conf.d/${domain}.d/${app}.conf" - -# Reload services -sudo service php5-fpm restart || true -sudo service nginx reload || true - -# Remove app dependencies -ynh_package_autoremove "$DEPS_PKG_NAME" || true - -# Clean home folders ACLs -for i in $(ls /home); do - [[ ! $i == yunohost.* ]] \ - && sudo setfacl -x g:$app:rwx >/dev/null 2>&1 -done - -# Remove the user account -id "$app" >/dev/null 2>&1 \ - && sudo deluser --quiet --remove-home "$app" >/dev/null \ - || true +ynh_script_progression --message="Removal of $app completed" --last diff --git a/scripts/restore b/scripts/restore index 39d540f..57d2014 100755 --- a/scripts/restore +++ b/scripts/restore @@ -1,86 +1,66 @@ #!/bin/bash -set -eu +#================================================= +# GENERIC START +#================================================= +# IMPORT GENERIC HELPERS +#================================================= -# Get multi-instances specific variables -app=$YNH_APP_INSTANCE_NAME +# Keep this path for calling _common.sh inside the execution's context of backup and restore scripts +source ../settings/scripts/_common.sh +source /usr/share/yunohost/helpers -# Set app specific variables -dbname=$app -dbuser=$app +#================================================= +# RESTORE THE APP MAIN DIR +#================================================= +ynh_script_progression --message="Restoring the app main directory..." --weight=1 -# Source app helpers -. /usr/share/yunohost/helpers +ynh_restore_file --origin_path="$install_dir" -# Retrieve old app settings -domain=$(ynh_app_setting_get $app domain) -path=$(ynh_app_setting_get $app path) -dbpass=$(ynh_app_setting_get $app mysqlpwd) +chmod 750 "$install_dir" +chmod -R o-rwx "$install_dir" +chown -R $app:www-data "$install_dir" +chmod +x $install_dir/owncloud -# TODO: Check domain/path availability with app helper -sudo yunohost app checkurl $domain$path -a $app \ - || ynh_die "The path ${domain}${path} is not available for app installation." +#================================================= +# RESTORE THE DATA DIRECTORY +#================================================= +ynh_script_progression --message="Restoring the data directory..." --weight=1 -# Check destination directory -DESTDIR="/var/www/$app" -[[ -d $DESTDIR ]] && ynh_die \ -"The destination directory '$DESTDIR' already exists.\ - You should safely delete it before restoring this app." +ynh_restore_file --origin_path="$data_dir" --not_mandatory -# Define app's data directory -DATADIR="/home/yunohost.app/${app}/data" +chown -R $app:www-data "$data_dir" -# Check configuration files -nginx_conf="/etc/nginx/conf.d/${domain}.d/${app}.conf" -[[ -f $nginx_conf ]] && ynh_die \ -"The NGINX configuration already exists at '${nginx_conf}'. - You should safely delete it before restoring this app." -phpfpm_conf="/etc/php5/fpm/pool.d/${app}.conf" -[[ -f $phpfpm_conf ]] && ynh_die \ -"The PHP FPM configuration already exists at '${phpfpm_conf}'. - You should safely delete it before restoring this app." +#================================================= +# RESTORE THE NGINX CONFIGURATION +#================================================= +ynh_script_progression --message="Restoring the NGINX web server configuration..." --weight=1 -# Install dependencies -ynh_package_install_from_equivs ./owncloud-deps.control \ - || ynh_die "Unable to install dependencies" +ynh_restore_file --origin_path="/etc/nginx/conf.d/$domain.d/$app.conf" -# Create a system account for ownCloud -sudo useradd -c "$app system account" \ - -d /var/lib/$app --system --user-group $app \ - || ynh_die "Unable to create $app system account" +ynh_restore_file --origin_path="/etc/systemd/system/$app.service" +systemctl enable $app.service --quiet -# Restore the app files -sudo cp -a ./www "$DESTDIR" -sudo mkdir -p "$DATADIR" -sudo cp -a ./data/. "$DATADIR" +yunohost service add $app --description="File sharing platform" --log="/var/log/$app/$app.log" -# Create and restore the database -ynh_mysql_create_db $dbname $dbuser $dbpass -ynh_mysql_connect_as $dbuser $dbpass $dbname < ./db.sql +#================================================= +# START SYSTEMD SERVICE +#================================================= +ynh_script_progression --message="Starting a systemd service..." --weight=1 -# Iterate over users to extend their home folder permissions - for the external -# storage plugin usage - and create relevant ownCloud directories -for u in $(ynh_user_list); do - sudo mkdir -p "${DATADIR}/${u}" - sudo setfacl -m g:$app:rwx "/home/$u" || true -done +ynh_systemd_action --service_name=$app --action="start" --log_path="systemd" -# Fix app ownerships & permissions -sudo chown -R $app: "$DESTDIR" "$DATADIR" -sudo find ${DESTDIR}/ -type f -print0 | sudo xargs -0 chmod 0644 -sudo find ${DESTDIR}/ -type d -print0 | sudo xargs -0 chmod 0755 -sudo find ${DATADIR}/ -type f -print0 | sudo xargs -0 chmod 0640 -sudo find ${DATADIR}/ -type d -print0 | sudo xargs -0 chmod 0750 -sudo chmod 640 "${DESTDIR}/config/config.php" -sudo chmod 755 /home/yunohost.app +#================================================= +# GENERIC FINALIZATION +#================================================= +# RELOAD NGINX AND PHP-FPM +#================================================= +ynh_script_progression --message="Reloading NGINX web server..." --weight=1 -# Restore configuration files -sudo cp -a ./conf/nginx.conf "$nginx_conf" -sudo cp -a ./conf/php-fpm.conf "$phpfpm_conf" +ynh_systemd_action --service_name=nginx --action=reload -# Restore cron job -sudo cp -a ./conf/cron "/etc/cron.d/${app}" +#================================================= +# END OF SCRIPT +#================================================= -# Reload services -sudo service php5-fpm restart || true -sudo service nginx reload || true +ynh_script_progression --message="Restoration completed for $app" --last diff --git a/scripts/upgrade b/scripts/upgrade old mode 100755 new mode 100644 index 6896935..fd8edb1 --- a/scripts/upgrade +++ b/scripts/upgrade @@ -1,177 +1,68 @@ #!/bin/bash -set -eu +#================================================= +# GENERIC START +#================================================= +# IMPORT GENERIC HELPERS +#================================================= -# Get multi-instances specific variables -app=$YNH_APP_INSTANCE_NAME +source _common.sh +source /usr/share/yunohost/helpers -# Load common variables and helpers -. ./_common.sh +#================================================= +# CHECK VERSION +#================================================= -# Set app specific variables -dbname=$app -dbuser=$app +upgrade_type=$(ynh_check_app_version_changed) -# Source app helpers -. /usr/share/yunohost/helpers +#================================================= +# STANDARD UPGRADE STEPS +#================================================= +# STOP SYSTEMD SERVICE +#================================================= +ynh_script_progression --message="Stopping a systemd service..." --weight=1 -# Retrieve app settings -domain=$(ynh_app_setting_get "$app" domain) -path=$(ynh_app_setting_get "$app" path) -path=${path%/} -dbpass=$(ynh_app_setting_get "$app" mysqlpwd) -user_home=$(ynh_app_setting_get "$app" user_home) +ynh_systemd_action --service_name=$app --action="stop" --log_path="systemd" -# Check destination directory -DESTDIR="/var/www/$app" -[[ ! -d $DESTDIR ]] && ynh_die \ -"The destination directory '$DESTDIR' does not exist.\ - The app is not correctly installed, you should remove it first." +#================================================= +# DOWNLOAD, CHECK AND UNPACK SOURCE +#================================================= -# Check app's data directory -DATADIR="/home/yunohost.app/${app}/data" -[[ ! -d $DATADIR ]] && ynh_die \ -"The data directory '$DATADIR' does not exist.\ - The app is not correctly installed, you should remove it first." +if [ "$upgrade_type" == "UPGRADE_APP" ] +then + ynh_script_progression --message="Upgrading source files..." --weight=1 -# Upgrade dependencies -ynh_package_install_from_equivs ../conf/${DEPS_PKG_NAME}.control \ - || ynh_die "Unable to upgrade dependencies" - -# FIXME: Delete current nginx configuration to be able to check if -# .well-known is already served. See https://dev.yunohost.org/issues/400 -nginx_conf="/etc/nginx/conf.d/${domain}.d/${app}.conf" -sudo rm -f "$nginx_conf" -sudo service nginx reload - -# Copy and set nginx configuration -sed -i "s@#APP#@${app}@g" ../conf/nginx.conf -sed -i "s@#PATH#@${path}@g" ../conf/nginx.conf -sed -i "s@#LOCATION#@${path:-/}@g" ../conf/nginx.conf -sed -i "s@#DESTDIR#@${DESTDIR}@g" ../conf/nginx.conf -# do not serve .well-known if it's already served on the domain -if is_url_handled "https://${domain}/.well-known/caldav" ; then - sed -ri '/^location = \/\.well\-known\/(caldav|carddav) \{/,/\}/d' \ - ../conf/nginx.conf -fi -sudo cp ../conf/nginx.conf "$nginx_conf" - -# Copy and set php-fpm configuration -phpfpm_conf="/etc/php5/fpm/pool.d/${app}.conf" -sed -i "s@#USER#@${app}@g" ../conf/php-fpm.conf -sed -i "s@#GROUP#@${app}@g" ../conf/php-fpm.conf -sed -i "s@#POOLNAME#@${app}@g" ../conf/php-fpm.conf -sed -i "s@#DESTDIR#@${DESTDIR}/@g" ../conf/php-fpm.conf -sudo cp ../conf/php-fpm.conf "$phpfpm_conf" -sudo chown root: $phpfpm_conf -sudo chmod 644 $phpfpm_conf - -# Set system group in hooks -sed -i "s@#GROUP#@${app}@g" ../hooks/post_user_create - -# occ helper for the current installation -_exec_occ() { - exec_occ "$DESTDIR" "$app" $@ -} - -# Retrieve new ownCloud sources in a temporary directory -TMPDIR=$(ynh_mkdir_tmp) -extract_owncloud "$TMPDIR" - -# Copy ownCloud configuration file -oc_conf="${DESTDIR}/config.json" -sed -i "s@#DOMAIN#@${domain}@g" ../conf/config.json -sed -i "s@#DATADIR#@${DATADIR}@g" ../conf/config.json -sudo cp ../conf/config.json "${TMPDIR}/config.json" - -# Enable maintenance mode -_exec_occ maintenance:mode --on - -# Copy config and 3rd party applications from current directory -sudo cp -a "${DESTDIR}/config/config.php" "${TMPDIR}/config/config.php" -for a in $(sudo ls "${DESTDIR}/apps"); do - [[ ! -d "${TMPDIR}/apps/$a" ]] \ - && sudo cp -a "${DESTDIR}/apps/$a" "${TMPDIR}/apps/$a" -done - -# Rename existing app directory and move new one -sudo rm -rf "${DESTDIR}" -sudo mv "$TMPDIR" "$DESTDIR" - -# Set app folders ownership -sudo chown -R $app: "$DESTDIR" "$DATADIR" - -# Upgrade ownCloud (SUCCESS = 0, UP_TO_DATE = 3) -# TODO: Restore old directory in case of failure? -_exec_occ maintenance:mode --off -_exec_occ upgrade \ - || ([[ $? -eq 3 ]] || ynh_die "Unable to upgrade ownCloud") - -# Enable plugins and set ownCloud configuration -_exec_occ app:enable user_ldap -_exec_occ config:import "$oc_conf" -sudo rm -f "$oc_conf" - -# Guess user_home value if empty -if [[ -z "${user_home:-}" ]]; then - sudo cat "${DATADIR}/mount.json" >/dev/null 2>&1 \ - && user_home=1 \ - || user_home=0 - ynh_app_setting_set "$app" user_home "$user_home" + # Download, check integrity, uncompress and patch the source from app.src + ynh_setup_source --dest_dir="$install_dir" --keep=".ocis" fi -# Enable External Storage and create local mount to home folder as needed -if [[ ${user_home} -eq 1 ]]; then - _exec_occ app:enable files_external - _exec_occ files_external:list --output=json \ - | grep -q '"storage":"\\\\OC\\\\Files\\\\Storage\\\\Local"' \ - || _exec_occ files_external:create \ - 'Home' 'local' 'null::null' -c 'datadir=/home/$user' -fi +chmod 750 "$install_dir" +chmod -R o-rwx "$install_dir" +chown -R $app:www-data "$install_dir" +chmod +x $install_dir/owncloud -# Add dynamic logout URL to the config -# TODO: if changes are made to this section, replace it with new one. -_exec_occ config:system:get logout_url >/dev/null 2>&1 \ - || sudo su -c "echo \" -//-YunoHost- -// set logout_url according to main domain -\\\$main_domain = exec('cat /etc/yunohost/current_host'); -\\\$CONFIG['logout_url'] = 'https://'.\\\$main_domain.'/yunohost/sso/?action=logout'; -//-YunoHost- -\" >> ${DESTDIR}/config/config.php" -- $app +#================================================= +# PHP-FPM CONFIGURATION +#================================================= +ynh_script_progression --message="Upgrading PHP-FPM configuration..." --weight=1 -# Iterate over users to extend their home folder permissions - for the external -# storage plugin usage - and create relevant ownCloud directories -for u in $(ynh_user_list); do - sudo mkdir -p "${DATADIR}/${u}" - sudo setfacl -m g:$app:rwx "/home/$u" || true -done +# Create a dedicated NGINX config +ynh_add_nginx_config -# Fix app ownerships & permissions -sudo find ${DESTDIR}/ -type f -print0 | sudo xargs -0 chmod 0644 -sudo find ${DESTDIR}/ -type d -print0 | sudo xargs -0 chmod 0755 -sudo find ${DATADIR}/ -type f -print0 | sudo xargs -0 chmod 0640 -sudo find ${DATADIR}/ -type d -print0 | sudo xargs -0 chmod 0750 -sudo chmod 640 "${DESTDIR}/config/config.php" -sudo chmod 755 /home/yunohost.app +# Create a dedicated systemd config +ynh_add_systemd_config -# Set SSOwat rules -ynh_app_setting_set "$app" unprotected_uris "/" -ynh_app_setting_set "$app" skipped_regex \ - "$(sed 's/[\.\-]/\%&/g' <<< $domain)/%.well%-known/.*" +yunohost service add $app --description="File sharing platform" --log="/var/log/$app/$app.log" -# Reload services -sudo service php5-fpm restart || true -sudo service nginx reload || true +#================================================= +# START SYSTEMD SERVICE +#================================================= +ynh_script_progression --message="Starting a systemd service..." --weight=1 -# Add cron job -cron_path="/etc/cron.d/$app" -sed -i "s@#USER#@${app}@g" ../conf/owncloud.cron -sed -i "s@#DESTDIR#@${DESTDIR}@g" ../conf/owncloud.cron -sudo cp ../conf/owncloud.cron "$cron_path" -sudo chmod 644 "$cron_path" -_exec_occ background:cron +ynh_systemd_action --service_name=$app --action="start" --log_path="systemd" -# Warn about possible disabled apps -echo "Note that if you've installed some third-parties ownCloud applications, \ -they are probably disabled and you'll have to manually activate them again." >&2 +#================================================= +# END OF SCRIPT +#================================================= + +ynh_script_progression --message="Upgrade of $app completed" --last diff --git a/sources/extra_files/app/.gitignore b/sources/extra_files/app/.gitignore new file mode 100644 index 0000000..783a4ae --- /dev/null +++ b/sources/extra_files/app/.gitignore @@ -0,0 +1,2 @@ +*~ +*.sw[op] diff --git a/sources/patches/.gitignore b/sources/patches/.gitignore new file mode 100644 index 0000000..783a4ae --- /dev/null +++ b/sources/patches/.gitignore @@ -0,0 +1,2 @@ +*~ +*.sw[op] diff --git a/tests.toml b/tests.toml new file mode 100644 index 0000000..e76d57c --- /dev/null +++ b/tests.toml @@ -0,0 +1,9 @@ +test_format = 1.0 + +[default] + + # ------------ + # Tests to run + # ------------ + + exclude = ["install.subdir", "install.multi"] \ No newline at end of file