You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
105 lines
3.3 KiB
105 lines
3.3 KiB
# -*- coding: utf-8 -*-
|
|
|
|
import os
|
|
import random
|
|
import shutil
|
|
import string
|
|
import subprocess
|
|
try:
|
|
import git
|
|
except ImportError:
|
|
pass
|
|
|
|
|
|
from odoo import models, fields, api, http
|
|
from odoo.exceptions import ValidationError
|
|
from odoo.tools import config, which
|
|
|
|
class Repository(models.Model):
|
|
_name = 'galicea_git.repository'
|
|
|
|
state = fields.Selection(
|
|
[('draft', 'Draft'), ('created', 'Created')],
|
|
default='draft'
|
|
)
|
|
|
|
name = fields.Char('User-friendly name', required=True)
|
|
system_name = fields.Char(
|
|
'Directory name',
|
|
required=True,
|
|
readonly=True,
|
|
index=True,
|
|
states={'draft': [('readonly', False)]}
|
|
)
|
|
collaborator_ids = fields.Many2many(
|
|
'res.users',
|
|
string='Collaborators'
|
|
)
|
|
|
|
local_directory = fields.Char(
|
|
'Local directory on server',
|
|
compute='_compute_local_directory',
|
|
groups='galicea_git.group_admin'
|
|
)
|
|
url = fields.Char(
|
|
'Clone',
|
|
compute='_compute_url'
|
|
)
|
|
|
|
@api.one
|
|
@api.depends('system_name')
|
|
def _compute_url(self):
|
|
base_url = http.request.httprequest.host_url if http.request \
|
|
else env['ir.config_parameter'].get_param('web.base.url') + '/'
|
|
self.url = u'{}git/{}'.format(base_url, self.system_name)
|
|
|
|
@api.one
|
|
@api.depends('system_name')
|
|
def _compute_local_directory(self):
|
|
if self.system_name:
|
|
self.local_directory = os.path.join(config['data_dir'], 'git', self.system_name)
|
|
|
|
@api.constrains('system_name')
|
|
def _validate_system_name(self):
|
|
allowed_characters = string.ascii_lowercase + string.digits + '-_'
|
|
if not all(c in allowed_characters for c in self.system_name):
|
|
raise ValidationError(
|
|
'Only lowercase, digits and hyphens (-) are allowed in directory name'
|
|
)
|
|
|
|
@api.constrains('collaborator_ids')
|
|
def _validate_collaborator_ids(self):
|
|
invalid_collaborators = self.collaborator_ids.filtered(lambda c: not c.has_group('galicea_git.group_collaborator'))
|
|
if invalid_collaborators:
|
|
raise ValidationError(
|
|
'User {} does not have the {} role. Contact your Administrator'.format(
|
|
invalid_collaborators[0].name,
|
|
self.env.ref('galicea_git.group_collaborator').full_name
|
|
)
|
|
)
|
|
|
|
@api.model
|
|
def create(self, values):
|
|
values['state'] = 'created'
|
|
ret = super(Repository, self).create(values)
|
|
ret.__initialize_repo()
|
|
return ret
|
|
|
|
@api.multi
|
|
def unlink(selfs):
|
|
directories_to_move = selfs.mapped(lambda r: r.local_directory)
|
|
ret = super(Repository, selfs).unlink()
|
|
for directory in directories_to_move:
|
|
if os.path.exists(directory):
|
|
suffix = ''.join(random.choice(string.ascii_lowercase) for _ in range(8))
|
|
new_directory = directory + '-deleted-' + suffix
|
|
shutil.move(directory, new_directory)
|
|
|
|
@api.multi
|
|
def __initialize_repo(self):
|
|
self.ensure_one()
|
|
if os.path.exists(self.local_directory):
|
|
raise ValidationError(
|
|
'Repository {} already exists, choose a different name!'.format(self.system_name)
|
|
)
|
|
subprocess.check_call([which('git'), 'init', '--bare', self.local_directory])
|