dp_dump_anonym

develop
Ahmed Aly 2018-05-14 09:46:31 +02:00
parent 2a680be18d
commit 001811b96a
13 changed files with 588 additions and 1 deletions

View File

@ -17,7 +17,7 @@ timezone = Europe/Vienna
show_debug = 1
workers = 0
server_wide_modules = web,base_sparse_field,queue_job
server_wide_modules = web,base_sparse_field,queue_job,dp_dump_anonym
portal_url = https://dev-portal.tzaustria.info/
portal_secret = hH43413$74O0

View File

@ -0,0 +1,27 @@
Odoo Proprietary License v1.0
This software and associated files (the "Software") may only be used (executed,
modified, executed after modifications) if you have purchased a valid license
from the authors, typically via Odoo Apps, or if you have received a written
agreement from the authors of the Software (see the COPYRIGHT file).
You may develop Odoo modules that use the Software as a library (typically by
depending on it, importing it and using its resources), but without copying any
source code or material from the Software. You may distribute those modules
under the license of your choice, provided that this license is compatible with
the terms of the Odoo Proprietary License (For example: LGPL, MIT,
or proprietary licenses similar to this one).
It is forbidden to publish, distribute, sublicense, or sell copies of the Software
or modified copies of the Software.
The above copyright notice and this permission notice must be included
in all copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM,
DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
DEALINGS IN THE SOFTWARE.

View File

@ -0,0 +1,5 @@
# Copyright 2018-Today datenpol gmbh(<http://www.datenpol.at>)
# License OPL-1 or later (https://www.odoo.com/documentation/user/11.0/legal/licenses/licenses.html#licenses).
from . import service
from . import controllers

View File

@ -0,0 +1,26 @@
# Copyright 2018-Today datenpol gmbh(<http://www.datenpol.at>)
# License OPL-1 or later (https://www.odoo.com/documentation/user/11.0/legal/licenses/licenses.html#licenses).
# noinspection PyStatementEffect
{
'name': 'Ermöglicht die Anonymisierung der Datenbank-Backups',
'category': 'Administration',
'version': '11.0.1.0.0',
'license': 'OPL-1',
'author': 'datenpol gmbh',
'website': 'https://www.datenpol.at',
'summary': '',
'description': """
offen
""",
'depends': [
'web',
],
'auto_install': True,
'data': [
'security/ir.model.access.csv',
],
'demo': [
],
'bootstrap': True,
}

View File

@ -0,0 +1,4 @@
# Copyright 2018-Today datenpol gmbh(<http://www.datenpol.at>)
# License OPL-1 or later (https://www.odoo.com/documentation/user/11.0/legal/licenses/licenses.html#licenses).
from . import main

View File

@ -0,0 +1,66 @@
# Copyright 2018-Today datenpol gmbh(<http://www.datenpol.at>)
# License OPL-1 or later (https://www.odoo.com/documentation/user/11.0/legal/licenses/licenses.html#licenses).
import datetime
import json
import logging
import os
import sys
import jinja2
import werkzeug
from odoo.addons.web.controllers.main import DBNAME_PATTERN, db_monodb, Database
import odoo
from odoo import http
from odoo.http import content_disposition
_logger = logging.getLogger(__name__)
if hasattr(sys, 'frozen'):
# When running on compiled windows binary, we don't have access to package loader.
path = os.path.realpath(os.path.join(os.path.dirname(__file__), '..', 'views'))
loader = jinja2.FileSystemLoader(path)
else:
loader = jinja2.PackageLoader('odoo.addons.dp_dump_anonym', "views")
env = jinja2.Environment(loader=loader, autoescape=True)
env.filters["json"] = json.dumps
class DatabaseExtended(Database):
def _render_template(self, **d):
d.setdefault('manage', True)
d['insecure'] = odoo.tools.config.verify_admin_password('admin')
d['list_db'] = odoo.tools.config['list_db']
d['langs'] = odoo.service.db.exp_list_lang()
d['countries'] = odoo.service.db.exp_list_countries()
d['pattern'] = DBNAME_PATTERN
# databases list
d['databases'] = []
try:
d['databases'] = http.db_list()
d['incompatible_databases'] = odoo.service.db.list_db_incompatible(d['databases'])
except odoo.exceptions.AccessDenied:
monodb = db_monodb()
if monodb:
d['databases'] = [monodb]
return env.get_template("database_manager.html").render(d)
@http.route('/web/database/backup', type='http', auth="none", methods=['POST'], csrf=False)
def backup(self, master_pwd, name, backup_format='zip', raw=False):
try:
odoo.service.db.check_super(master_pwd)
ts = datetime.datetime.utcnow().strftime("%Y-%m-%d_%H-%M-%S")
filename = "%s_%s.%s" % (name, ts, backup_format)
headers = [
('Content-Type', 'application/octet-stream; charset=binary'),
('Content-Disposition', content_disposition(filename)),
]
dump_stream = odoo.service.db.dump_db(name, None, backup_format, raw)
response = werkzeug.wrappers.Response(dump_stream, headers=headers, direct_passthrough=True)
return response
except Exception as e:
_logger.exception('Database.backup')
error = "Database backup error: %s" % (str(e) or repr(e))
return self._render_template(error=error)

View File

@ -0,0 +1,12 @@
-- Set Admin password to 'x'
UPDATE res_users SET password_crypt = '$pbkdf2-sha512$25000$.r93rhUipFQKIYSQci6FcA$hesuvDYTEwTkjUYm/LSt6CH0B/oEMN3JUkpbL1K9gU3vnM3EEdojChU4cjSs21nCIjx88aoVJZ12PBahjM/0Yw' where id = 1;
-- Disable schedulers
UPDATE ir_cron SET active = FALSE where id > 4;
-- Corrupt E-Mail addresses
UPDATE res_partner SET email = replace(email, '@', '#');
-- Deactivate all mail servers
UPDATE ir_mail_server SET active = FALSE;
UPDATE fetchmail_server SET active = FALSE;

View File

@ -0,0 +1,12 @@
msgid ""
msgstr ""
"Project-Id-Version: Odoo Server 8.saas~6\n"
"Report-Msgid-Bugs-To: \n"
"POT-Creation-Date: 2016-05-02 13:28+0000\n"
"PO-Revision-Date: 2016-05-02 13:28+0000\n"
"Last-Translator: <>\n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: \n"
"Plural-Forms: \n"

View File

@ -0,0 +1 @@
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
1 id name model_id:id group_id:id perm_read perm_write perm_create perm_unlink

View File

@ -0,0 +1,4 @@
# Copyright 2018-Today datenpol gmbh(<http://www.datenpol.at>)
# License OPL-1 or later (https://www.odoo.com/documentation/user/11.0/legal/licenses/licenses.html#licenses).
from . import db

View File

@ -0,0 +1,64 @@
# Copyright 2018-Today datenpol gmbh(<http://www.datenpol.at>)
# License OPL-1 or later (https://www.odoo.com/documentation/user/11.0/legal/licenses/licenses.html#licenses).
import json
import logging
import os
import shutil
import tempfile
import base64
import odoo
from odoo.service.db import check_db_management_enabled, dump_db_manifest
_logger = logging.getLogger(__name__)
@check_db_management_enabled
def exp_dump(db_name, backup_format, raw):
with tempfile.TemporaryFile(mode='w+b') as t:
dump_db(db_name, t, backup_format, raw)
t.seek(0)
return base64.b64encode(t.read()).decode()
odoo.service.db.exp_dump = exp_dump
@check_db_management_enabled
def dump_db(db_name, stream, backup_format='zip', raw=None):
_logger.info('DUMP DB: %s format %s', db_name, backup_format)
self_dir = os.path.dirname(os.path.realpath(__file__))
anon_sql_file = os.path.join(self_dir, '..', 'data', 'anon.sql')
with odoo.tools.osutil.tempdir() as dump_dir:
if backup_format == 'zip':
filestore = odoo.tools.config.filestore(db_name)
if os.path.exists(filestore):
shutil.copytree(filestore, os.path.join(dump_dir, 'filestore'))
with open(os.path.join(dump_dir, 'manifest.json'), 'w') as fh:
db = odoo.sql_db.db_connect(db_name)
with db.cursor() as cr:
json.dump(dump_db_manifest(cr), fh, indent=4)
cmd = ['pg_dump', '--no-owner', db_name, '--file=' + os.path.join(dump_dir, 'dump.sql')]
odoo.tools.exec_pg_command(*cmd)
if not raw:
with open(os.path.join(dump_dir, 'dump.sql'), 'ab') as dump_file, open(anon_sql_file, 'rb') as anon:
shutil.copyfileobj(anon, dump_file)
if stream:
odoo.tools.osutil.zip_dir(dump_dir, stream, include_dir=False,
fnct_sort=lambda file_name: file_name != 'dump.sql')
else:
t = tempfile.TemporaryFile()
odoo.tools.osutil.zip_dir(dump_dir, t, include_dir=False,
fnct_sort=lambda file_name: file_name != 'dump.sql')
t.seek(0)
return t
odoo.service.db.dump_db = dump_db

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.2 KiB

View File

@ -0,0 +1,366 @@
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="content-type" content="text/html; charset=utf-8">
<title>Odoo</title>
<link rel="shortcut icon" href="/web/static/src/img/favicon.ico" type="image/x-icon">
<link rel="stylesheet" href="/web/static/lib/fontawesome/css/font-awesome.css">
<link rel="stylesheet" href="/web/static/lib/bootstrap/css/bootstrap.css">
<script src="/web/static/lib/jquery/jquery.js" type="text/javascript"></script>
<script src="/web/static/lib/bootstrap/js/modal.js"></script>
<script src="/web/static/lib/bootstrap/js/tooltip.js"></script>
<script src="/web/static/lib/bootstrap/js/dropdown.js"></script>
<script type="text/javascript">
$(function() {
// Little eye
$('body').on('mousedown','.o_little_eye',function(ev) {
$(ev.target).siblings('input').prop('type','text');
});
$('body').on('mouseup','.o_little_eye',function(ev) {
$(ev.target).siblings('input').prop('type','password');
});
// db modal
$('body').on('click','.o_database_action', function(ev) {
ev.preventDefault();
var db = $(ev.currentTarget).data('db');
var target = $(ev.currentTarget).data('target');
$(target).find('input[name=name]').val(db);
$(target).modal();
});
// close modal on submit
$('.modal').on('click','input[type="submit"]', function(ev) {
var modal = $(this).parentsUntil('body', '.modal');
if (modal.hasClass('o_database_backup')) {
$(modal).modal('hide');
if (!$('.alert-backup-long').length) {
$('.list-group').before("<div class='alert alert-info alert-backup-long'>The backup may take some time before being ready</div>");
}
}
});
});
</script>
</head>
{% macro master_input() -%}
<div class="form-group">
{% if insecure %}
<input type="hidden" name="master_pwd" class="form-control" value="admin"/>
{% else %}
<label for="master_pwd" class="control-label">Master Password</label>
<input id="master_pwd" type="password" name="master_pwd" class="form-control" required="required" autofocus="autofocus"/>
{% endif %}
</div>
{%- endmacro %}
{% macro create_form() -%}
<p>Odoo is up and running! <br />
Fill out this form to create a new database. You will install your first app afterwards.</p>
{{ master_input() }}
<div class="form-group">
<div class="row">
<div class="col-md-12">
<label for="name" class="control-label">Database Name</label>
<input id="name" type="text" name="name" class="form-control" required="required" autocomplete="off" pattern="{{ pattern }}" title="Only alphanumerical characters, underscore, hyphen and dot are allowed"/>
</div>
</div>
</div>
<div class="form-group">
<div class="row">
<div class="col-md-12">
<label for="login" class="control-label">Email</label>
<input id="login" type="text" name="login" class="form-control" required="required" autocomplete="off"/>
</div>
</div>
</div>
<div class="form-group has-feedback">
<label for="password" class="control-label">Password</label>
<input id="password" type="password" name="password" class="form-control" required="required" autocomplete="off"/>
<span class="fa fa-eye o_little_eye form-control-feedback" aria-hidden="true" style="cursor: pointer; pointer-events: auto"></span>
</div>
<div class="form-group">
<div class="row">
<div class="col-md-6">
<label for="lang" class="control-label">Language</label>
<select id="lang" name="lang" class="form-control" required="required" autocomplete="off">
{% for lang in langs %}
<option {% if lang[0] == "en_US" %}selected="selected" {% endif %}value="{{ lang[0] }}">{{ lang[1] }}</option>
{% endfor %}
</select>
</div>
<div class="col-md-6">
<label for="country" class="control-label">Country</label>
<select id="country" name="country_code" class="form-control" autocomplete="off">
<option value=""></option>
{% for country in countries %}
<option value="{{ country[0] }}">{{ country[1] }}</option>
{% endfor %}
</select>
</div>
</div>
</div>
<div class="form-group">
<div class="checkbox">
<label>
<input name="demo" type="checkbox" class="pull-right" value="1">
<span>Load demonstration data</span>
<span class="text-muted"> (Check this box to evaluate Odoo)</span>
</label>
</div>
</div>
{%- endmacro %}
<body class="container">
<!-- Database List -->
<div class="row">
<div class="col-md-6 col-md-offset-3 o_database_list">
<div class="text-center">
<img src="/web/static/src/img/logo2.png" class="img-responsive center-block"/>
</div>
{% if not list_db %}
<div class="alert alert-danger text-center">
The database manager has been disabled by the administrator
</div>
{% elif insecure and databases %}
<div class="alert alert-warning">
Warning, your Odoo database manager is not protected.
Please <a href="#" data-toggle="modal" data-target=".o_database_master">set a master password</a>
to secure it.
</div>
{% endif %}
{% if error %}
<div class="alert alert-danger">{{ error }}</div>
{% endif %}
{% if list_db and databases %}
<div class="list-group">
{% for db in databases %}
<a href="/web?db={{ db }}" class="list-group-item" >
{% if db in incompatible_databases %}
<i class="icon fa fa-warning pull-right text-warning" title="This database may not be compatible"></i>
{% endif %}
{{ db }}
{% if manage %}
<div class="text-right pull-right">
<span data-db="{{ db }}" data-target=".o_database_backup" class="o_database_action btn-link"><i class="fa fa-floppy-o fa-fw"></i> Backup</span>
<span data-db="{{ db }}" data-target=".o_database_duplicate" class="o_database_action btn-link"><i class="fa fa-files-o fa-fw"></i> Duplicate</span>
<span data-db="{{ db }}" data-target=".o_database_delete" class="o_database_action btn-link"><i class="fa fa-trash-o fa-fw"></i> Delete</span>
</div>
{% endif %}
</a>
{% endfor %}
</div>
{% if manage %}
<div class="text-left">
<button type="button" data-toggle="modal" data-target=".o_database_create" class="btn btn-sm btn-primary">
Create Database
</button>
<button type="button" data-toggle="modal" data-target=".o_database_restore" class="btn btn-sm btn-primary">
Restore Database
</button>
<button type="button" data-toggle="modal" data-target=".o_database_master" class="btn btn-sm btn-primary">
Set Master Password
</button>
</div>
{% else %}
<div class="text-center">
<a href="/web/database/manager">Manage databases</a>
</div>
{% endif %}
{% elif list_db %}
<form role="form" action="/web/database/create" method="post">
{{ create_form() }}
<input type="submit" value="Create database" class="btn btn-primary pull-left"/>
</form>
<a role="button" data-toggle="modal" data-target=".o_database_restore" class="btn btn-link">
or restore a database
</a>
{% endif %}
</div>
</div>
<!-- Create -->
<div class="modal fade o_database_create" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<form role="form" action="/web/database/create" method="post">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Create Database</h4>
</div>
<div class="modal-body">
{{ create_form() }}
</div>
<div class="modal-footer">
<input type="submit" value="Continue" class="btn btn-primary pull-right"/>
</div>
</form>
</div>
</div>
</div>
<!-- Restore -->
<div class="modal fade o_database_restore" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Restore Database</h4>
</div>
<form id="form_restore_db" role="form" action="/web/database/restore" method="post" enctype="multipart/form-data">
<div class="modal-body">
{{ master_input() }}
<div class="form-group">
<label for="backup_file" class="control-label">File</label>
<input id="backup_file" type="file" name="backup_file" class="required"/>
</div>
<div class="form-group">
<label for="name" class="control-label">Database Name</label>
<input id="name" type="text" name="name" class="form-control" required="required" pattern="{{ pattern }}" title="Only alphanumerical characters, underscore, hyphen and dot are allowed"/>
</div>
<div class="form-group">
<label for="copy">This database might have been moved or copied.</label>
<p class="help-block">In order to avoid conflicts between databases, Odoo needs to know if this database was moved or copied.
If you don't know, answer "This database is a copy".</p>
<div class="radio">
<label>
<input name="copy" type="radio" class="pull-right" value="true" checked="1">
This database is a copy
</label>
</div>
<div class="radio">
<label>
<input name="copy" type="radio" class="pull-right" value="false">
This database was moved
</label>
</div>
</div>
</div>
<div class="modal-footer">
<input type="submit" value="Continue" class="btn btn-primary pull-right"/>
</div>
</form>
</div>
</div>
</div>
<!-- Master password -->
<div class="modal fade o_database_master" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Set Master Password</h4>
</div>
<form id="form_change_pwd" role="form" action="/web/database/change_password" method="post">
<div class="modal-body">
<p>The master password is required to create, delete, dump or restore databases.</p>
{{ master_input() }}
<div class="form-group has-feedback">
<label for="master_pwd_new" class="control-label">New Master Password</label>
<input id="master_pwd_new" type="password" name="master_pwd_new" class="form-control" required="required" autocomplete="off"/>
<span class="fa fa-eye o_little_eye form-control-feedback" aria-hidden="true" style="cursor: pointer; pointer-events: auto"></span>
</div>
</div>
<div class="modal-footer">
<input type="submit" value="Continue" class="btn btn-primary pull-right"/>
</div>
</form>
</div>
</div>
</div>
<!-- Duplicate DB -->
<div class="modal fade o_database_duplicate" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Duplicate Database</h4>
</div>
<form id="form-duplicate-db" role="form" action="/web/database/duplicate" method="post">
<div class="modal-body">
{{ master_input() }}
<div class="form-group">
<label for="name" class="control-label">Database Name</label>
<input id="name" type="text" name="name" class="form-control" required="required" readonly="readonly"/>
</div>
<div class="form-group">
<label for="new_name" class="control-label">New Name</label>
<input id="new_name" type="text" name="new_name" class="form-control" required="required" pattern="{{ pattern }}" title="Only alphanumerical characters, underscore, hyphen and dot are allowed"/>
</div>
</div>
<div class="modal-footer">
<input type="submit" value="Continue" class="btn btn-primary pull-right"/>
</div>
</form>
</div>
</div>
</div>
<!-- Drop DB -->
<div class="modal fade o_database_delete" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Delete Database</h4>
</div>
<form id="form_drop_db" role="form" action="/web/database/drop" method="post">
<div class="modal-body">
{{ master_input() }}
<div class="form-group">
<label for="name" class="control-label">Database</label>
<input id="name" type="text" name="name" class="form-control" required="required" readonly="readonly"/>
</div>
</div>
<div class="modal-footer">
<input type="submit" value="Delete" class="btn btn-primary pull-right"/>
</div>
</form>
</div>
</div>
</div>
<!-- Backup DB -->
<div class="modal fade o_database_backup" role="dialog">
<div class="modal-dialog">
<div class="modal-content">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-label="Close"><span aria-hidden="true">&times;</span></button>
<h4 class="modal-title">Backup Database</h4>
</div>
<form id="form_backup_db" role="form" action="/web/database/backup" method="post">
<div class="modal-body">
{{ master_input() }}
<div class="form-group">
<label for="name" class="control-label">Database Name</label>
<input id="name" type="text" name="name" class="form-control" required="required" readonly="readonly"/>
</div>
<div class="form-group">
<label for="backup_format" class="control-label">Backup Format</label>
<select id="backup_format" name="backup_format" class="form-control" required="required">
<option value="zip">zip (mit filestore)</option>
<option value="dump">zip (OHNE filestore)</option>
</select>
</div>
<div class="form-group">
<label for="checkbox_container" class="control-label">"Raw" Dump</label>
<div id="checkbox_container" class="checkbox">
<label>
<input id="ra" name="raw" type="checkbox" class="pull-right" value="1">
<span class="text-muted">Dump ohne Anonymisierung erstellen</span>
</label>
</div>
</div>
</div>
<div class="modal-footer">
<input type="submit" value="Backup" class="btn btn-primary pull-right"/>
</div>
</form>
</div>
</div>
</div>
</body>
</html>