parent
a466a26bf1
commit
dc3c55e2f1
@ -1 +0,0 @@
|
||||
__author__ = 'mhiretskiy'
|
@ -0,0 +1,71 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Copyright 2015 Calculate Ltd. http://www.calculate-linux.org
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import sys
|
||||
from os import path
|
||||
from calculate.lib.utils.files import isMount
|
||||
from calculate.lib.utils.tools import Locker, LockError
|
||||
from calculate.lib.cl_lang import (setLocalTranslate, getLazyLocalTranslate, _)
|
||||
from .datavars import builder_data
|
||||
import hashlib
|
||||
import random
|
||||
|
||||
setLocalTranslate('cl_builder3', sys.modules[__name__])
|
||||
__ = getLazyLocalTranslate(_)
|
||||
|
||||
|
||||
class DriveSpool(object):
|
||||
"""
|
||||
Объект содержит спул устройств на которые можно устанавливать систему
|
||||
"""
|
||||
spool_data = path.join('/run/calculate/drives_lock')
|
||||
|
||||
def __init__(self, devices, shuf=True):
|
||||
self.devices = devices
|
||||
if shuf:
|
||||
random.shuffle(self.devices)
|
||||
self.devices = iter(self.devices)
|
||||
self.lockers = []
|
||||
|
||||
@staticmethod
|
||||
def device_id(device_name):
|
||||
return device_name.replace('/', "_").lstrip("_")
|
||||
|
||||
@staticmethod
|
||||
def check_device(device):
|
||||
return path.exists(device)
|
||||
|
||||
def lock_device(self, device):
|
||||
if self.check_device(device) and not isMount(device):
|
||||
device_hashfn = path.join(self.spool_data, self.device_id(device))
|
||||
locker = Locker(fn=device_hashfn, timeout=0)
|
||||
try:
|
||||
locker.acquire()
|
||||
self.lockers.append(locker)
|
||||
return True
|
||||
except LockError as e:
|
||||
return False
|
||||
|
||||
def get(self):
|
||||
for device in self.devices:
|
||||
if self.lock_device(device):
|
||||
return device
|
||||
return None
|
||||
|
||||
def close(self):
|
||||
for locker in self.lockers:
|
||||
locker.remove()
|
||||
self.lockers = []
|
@ -0,0 +1,47 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Copyright 2015 Calculate Ltd. http://www.calculate-linux.org
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import sys
|
||||
from calculate.core.server.func import Action, Tasks
|
||||
from calculate.lib.cl_lang import setLocalTranslate, getLazyLocalTranslate
|
||||
from calculate.lib.utils.files import FilesError
|
||||
from ..datavars import BuilderError
|
||||
from calculate.lib.utils.portage import GitError
|
||||
from calculate.install.distr import DistributiveError
|
||||
|
||||
setLocalTranslate('cl_builder3', sys.modules[__name__])
|
||||
__ = getLazyLocalTranslate(_)
|
||||
|
||||
|
||||
class ClBuilderBreakAction(Action):
|
||||
"""
|
||||
Действие обновление конфигурационных файлов
|
||||
"""
|
||||
# ошибки, которые отображаются без подробностей
|
||||
native_error = (DistributiveError, FilesError, BuilderError, GitError)
|
||||
|
||||
successMessage = __("Assemble broken successfully")
|
||||
failedMessage = __("Breaking the assemble is failed")
|
||||
interruptMessage = __("Breaking manually interrupted")
|
||||
|
||||
# список задач для действия
|
||||
tasks = [
|
||||
{'name': 'close_build',
|
||||
'message': __("Breaking {cl_builder_id} assemble"),
|
||||
'method': 'Builder.close_build(cl_builder_build,cl_builder_clear_set)',
|
||||
'condition': lambda Get: Get('cl_builder_build')
|
||||
}
|
||||
]
|
@ -0,0 +1,61 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Copyright 2015 Calculate Ltd. http://www.calculate-linux.org
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import sys
|
||||
from calculate.core.server.func import Action
|
||||
from calculate.lib.cl_lang import setLocalTranslate, getLazyLocalTranslate
|
||||
from calculate.lib.utils.files import FilesError
|
||||
from ..datavars import BuilderError
|
||||
from calculate.lib.utils.portage import GitError
|
||||
from calculate.install.distr import DistributiveError
|
||||
|
||||
setLocalTranslate('cl_builder3', sys.modules[__name__])
|
||||
__ = getLazyLocalTranslate(_)
|
||||
|
||||
|
||||
class ClBuilderRestoreAction(Action):
|
||||
"""
|
||||
Действие обновление конфигурационных файлов
|
||||
"""
|
||||
# ошибки, которые отображаются без подробностей
|
||||
native_error = (DistributiveError, FilesError, BuilderError, GitError)
|
||||
|
||||
successMessage = __("Assemble broken successfully")
|
||||
failedMessage = __("Breaking the assemble is failed")
|
||||
interruptMessage = __("Breaking manually interrupted")
|
||||
|
||||
# список задач для действия
|
||||
tasks = [
|
||||
{'name': 'restore_build',
|
||||
'message': __("Restoring {cl_builder_id} assemble"),
|
||||
'method': 'Builder.restore_build(cl_builder_build)'
|
||||
},
|
||||
# подмонтировать необходимые данные
|
||||
{'name': 'mount',
|
||||
'message': __("Mounting target"),
|
||||
'method': 'Builder.mount_target(cl_builder_target)',
|
||||
},
|
||||
# save
|
||||
{'name': 'save',
|
||||
'message': __("Save distro"),
|
||||
'method': 'Builder.save_build(cl_builder_build)',
|
||||
},
|
||||
# закрепить подключенные данные
|
||||
{'name': 'detach',
|
||||
'message': __("Detach target"),
|
||||
'method': 'Builder.detach_target(cl_builder_target)',
|
||||
},
|
||||
]
|
@ -0,0 +1,480 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Copyright 2015 Calculate Ltd. http://www.calculate-linux.org
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import sys
|
||||
from os import path
|
||||
from calculate.install.distr import (Distributive, DistributiveError,
|
||||
LayeredDistributive, DefaultMountPath, PartitionDistributive,
|
||||
DirectoryDistributive)
|
||||
from calculate.lib.utils.device import getUdevDeviceInfo, humanreadableSize
|
||||
from calculate.lib.utils.files import isMount, process
|
||||
from ..build_storage import BuildStorage, Build
|
||||
from ..drive_spool import DriveSpool
|
||||
from calculate.lib.datavars import Variable,VariableError,ReadonlyVariable
|
||||
|
||||
from calculate.lib.cl_lang import setLocalTranslate
|
||||
setLocalTranslate('cl_builder3',sys.modules[__name__])
|
||||
|
||||
|
||||
class VariableClBuilderStorage(ReadonlyVariable):
|
||||
type = "object"
|
||||
|
||||
def get(self):
|
||||
return BuildStorage()
|
||||
|
||||
|
||||
class VariableClBuilderAvailableDev(Variable):
|
||||
"""
|
||||
Список дисков, которые можно использовать для сборки
|
||||
"""
|
||||
type = "list"
|
||||
|
||||
|
||||
class VariableClBuilderDeviceSpool(ReadonlyVariable):
|
||||
"""
|
||||
Стэк дисков, которые можно использовать для сборки
|
||||
"""
|
||||
type = "object"
|
||||
|
||||
def get(self):
|
||||
ds = DriveSpool(self.Get('cl_builder_available_dev'))
|
||||
return ds
|
||||
|
||||
|
||||
class BaseBuildId(Variable):
|
||||
"""
|
||||
Базовый класс для переменной id
|
||||
"""
|
||||
opt = ["--id"]
|
||||
metavalue = "ID"
|
||||
|
||||
def init(self):
|
||||
self.label = _("Build ID")
|
||||
self.help = _("build ID")
|
||||
|
||||
|
||||
class VariableClBuilderSourceFilename(Variable):
|
||||
"""
|
||||
Названия файла исходного дистрибутива
|
||||
"""
|
||||
opt = ["--source"]
|
||||
value = ""
|
||||
metavalue = "SOURCE"
|
||||
|
||||
def init(self):
|
||||
self.label = _("Source distribution")
|
||||
self.help = _("source distribution")
|
||||
|
||||
def check(self, isoimage):
|
||||
"""Set image file"""
|
||||
if self.Get('cl_action') == 'create' and not isoimage:
|
||||
raise VariableError(_("You need to select a source image"))
|
||||
imageData = Distributive().getInfo(isoimage)
|
||||
if not("os_linux_shortname" in imageData and
|
||||
imageData.get('os_linux_build','') and
|
||||
"os_arch_machine" in imageData):
|
||||
raise VariableError(_("Wrong image file"))
|
||||
|
||||
def humanReadable(self):
|
||||
fullname = self.Get('os_builder_linux_name')
|
||||
subname = self.Get('os_builder_linux_subname')
|
||||
if subname:
|
||||
subname = " %s" % subname
|
||||
arch = self.Get('os_builder_arch_machine')
|
||||
build = self.Get('os_builder_linux_build')
|
||||
ver = self.Get('os_builder_linux_ver')
|
||||
|
||||
return "{fullname} {ver} {arch} {build}".format(
|
||||
fullname="%s%s" % (fullname, subname),
|
||||
build=build, ver=ver, arch=arch)
|
||||
|
||||
|
||||
class VariableClBuilderSource(ReadonlyVariable):
|
||||
"""
|
||||
Объект исходного дистрибутива для разворачивания сборки
|
||||
"""
|
||||
type = "object"
|
||||
|
||||
def get(self):
|
||||
"""Get image file from distributive repository"""
|
||||
try:
|
||||
filename = self.Get('cl_builder_source_filename')
|
||||
if filename:
|
||||
return Distributive.fromFile(filename)
|
||||
except DistributiveError:
|
||||
pass
|
||||
return ""
|
||||
|
||||
def humanReadable(self):
|
||||
filename = self.Get('cl_builder_source')
|
||||
if filename:
|
||||
return filename.getType()
|
||||
return filename
|
||||
|
||||
|
||||
class VariableClBuilderDiskDev(Variable):
|
||||
"""
|
||||
Диск или директория, куда будет развёрнут образ
|
||||
"""
|
||||
untrusted = True
|
||||
opt = ["-d", "--disk"]
|
||||
metavalue = "DEST"
|
||||
|
||||
def init(self):
|
||||
self.label = _("Assemble location")
|
||||
self.help = _("partition or directory intended for assemble")
|
||||
|
||||
def get(self):
|
||||
ds = self.Get('cl_builder_device_spool')
|
||||
return ds.get().next()
|
||||
|
||||
def check(self, value):
|
||||
if value.startswith("/dev"):
|
||||
cnDisk = getUdevDeviceInfo(name=value).get('DEVNAME', value)
|
||||
if cnDisk not in self.Get('install.os_disk_dev'):
|
||||
raise VariableError(_("Wrong device '%s'") % value)
|
||||
if not value.startswith('/'):
|
||||
raise VariableError(
|
||||
_("Wrong directory '%s'") % value)
|
||||
if isMount(value):
|
||||
raise VariableError(
|
||||
_("Destination '%s' is already in use") % value)
|
||||
|
||||
|
||||
class VariableClBuilderDiskSize(ReadonlyVariable):
|
||||
"""
|
||||
|
||||
"""
|
||||
type = "int"
|
||||
|
||||
def init(self):
|
||||
self.label = _("Free disk space")
|
||||
|
||||
def get_free_for(self, dn):
|
||||
try:
|
||||
for dfdn in (dn, path.dirname(dn)):
|
||||
dfProcess = process("/bin/df", "--output=avail", dfdn)
|
||||
data = dfProcess.readlines()
|
||||
if len(data) > 1:
|
||||
return int(data[1].strip()) * 1024
|
||||
except ValueError:
|
||||
return 0
|
||||
return 0
|
||||
|
||||
def get_create(self):
|
||||
device = self.Get('cl_builder_disk_dev')
|
||||
if device:
|
||||
if device.startswith('/dev/'):
|
||||
return self.Select('install.os_disk_size',
|
||||
where='install.os_disk_dev',
|
||||
eq=device, limit=1) or "0"
|
||||
else:
|
||||
return str(self.get_free_for(device))
|
||||
return "0"
|
||||
|
||||
def get(self):
|
||||
action = self.Get('cl_action')
|
||||
if action == 'create':
|
||||
return self.get_create()
|
||||
elif action in ('break', 'repair'):
|
||||
return
|
||||
|
||||
def humanReadable(self):
|
||||
return humanreadableSize(int(self.Get()))
|
||||
|
||||
class VariableClBuilderLayeredSet(Variable):
|
||||
"""
|
||||
Сборка будет выполняться в слое
|
||||
"""
|
||||
type = "bool"
|
||||
opt = ["--layered"]
|
||||
|
||||
def init(self):
|
||||
self.help = _("use layer for build")
|
||||
self.label = _("Use layer for build")
|
||||
|
||||
def get(self):
|
||||
return "off"
|
||||
|
||||
def check(self, value):
|
||||
if self.Get('cl_builder_disk_dev').startswith('/dev'):
|
||||
raise VariableError(
|
||||
_("Layers are used for building in a directory only"))
|
||||
|
||||
|
||||
class VariableClBuilderPath(ReadonlyVariable):
|
||||
"""
|
||||
Путь, где будет собираться дистрбутив
|
||||
"""
|
||||
def get(self):
|
||||
image = self.Get('cl_builder_target')
|
||||
if image:
|
||||
return image.getDirectory()
|
||||
return ""
|
||||
|
||||
|
||||
class VariableClBuilderTarget(Variable):
|
||||
"""
|
||||
Объект собираемого дистрибутива
|
||||
"""
|
||||
type = "object"
|
||||
|
||||
def get_create(self):
|
||||
builder_disk_dev = self.Get('cl_builder_disk_dev')
|
||||
if not builder_disk_dev:
|
||||
return ""
|
||||
buildid = self.Get('cl_builder_id')
|
||||
mountdir = path.join(DefaultMountPath.BaseMountPath, buildid)
|
||||
source = self.Get('cl_builder_source_filename')
|
||||
if self.GetBool('cl_builder_layered_set'):
|
||||
distr = LayeredDistributive(mountdir, builder_disk_dev, source)
|
||||
return distr
|
||||
else:
|
||||
if builder_disk_dev.startswith('/dev'):
|
||||
distr = PartitionDistributive(builder_disk_dev,
|
||||
mdirectory=mountdir)
|
||||
return distr
|
||||
else:
|
||||
distr = DirectoryDistributive(builder_disk_dev,
|
||||
mdirectory=mountdir)
|
||||
return distr
|
||||
|
||||
def get_worked(self):
|
||||
build = self.Get('cl_builder_build')
|
||||
if build:
|
||||
return build.distributive
|
||||
return ""
|
||||
|
||||
def get(self):
|
||||
if self.Get('cl_action') == 'create':
|
||||
return self.get_create()
|
||||
elif self.Get('cl_action') in ('break', 'restore'):
|
||||
return self.get_worked()
|
||||
else:
|
||||
return ""
|
||||
|
||||
|
||||
class VariableClBuilderClearSet(Variable):
|
||||
"""
|
||||
Очистить дистрибутив при отключении сборки
|
||||
"""
|
||||
type = "bool"
|
||||
value = "off"
|
||||
opt = ["--clear"]
|
||||
|
||||
def init(self):
|
||||
self.label = _("Clear after unmount")
|
||||
self.help = _("clear data after unmount")
|
||||
|
||||
|
||||
class VariableClBuilderBuild(Variable):
|
||||
"""
|
||||
Объект сборки
|
||||
"""
|
||||
type = "object"
|
||||
|
||||
def get_create(self):
|
||||
distr = self.Get('cl_builder_target')
|
||||
if not distr:
|
||||
return ""
|
||||
storage = self.Get('cl_builder_storage')
|
||||
buildid = self.Get('cl_builder_id')
|
||||
build = Build(buildid, distr, storage)
|
||||
return build
|
||||
|
||||
def get_worked(self):
|
||||
storage = self.Get('cl_builder_storage')
|
||||
buildid = self.Get('cl_builder_id')
|
||||
build = storage.get_build(buildid)
|
||||
return build or ""
|
||||
|
||||
def get(self):
|
||||
if self.Get('cl_action') == 'create':
|
||||
return self.get_create()
|
||||
if self.Get('cl_action') in ('break', 'restore'):
|
||||
return self.get_worked()
|
||||
return ""
|
||||
|
||||
|
||||
class VariableClBuilderNewId(BaseBuildId):
|
||||
"""
|
||||
Id сборки при развертывании
|
||||
"""
|
||||
value = ""
|
||||
untrusted = True
|
||||
|
||||
def check(self, value):
|
||||
if not value:
|
||||
raise VariableError(_("Please specify the id"))
|
||||
if value in self.Get('cl_builder_storage'):
|
||||
raise VariableError(_("Assemble %s already exists")%value)
|
||||
|
||||
|
||||
class VariableClBuilderPreparedId(BaseBuildId):
|
||||
"""
|
||||
Id развёрнутой сборки
|
||||
"""
|
||||
type = "choice"
|
||||
untrusted = True
|
||||
|
||||
def available(self):
|
||||
bs = self.Get('cl_builder_storage')
|
||||
action = self.Get('cl_action')
|
||||
for x in bs:
|
||||
build = bs.get_build(x)
|
||||
if action == 'break' or build.status == Build.Status.WORKED:
|
||||
yield x
|
||||
|
||||
def get(self):
|
||||
l = list(self.available())
|
||||
if l and len(l) == 1:
|
||||
return l[0]
|
||||
return ""
|
||||
|
||||
def choice(self):
|
||||
def generator():
|
||||
bs = self.Get('cl_builder_storage')
|
||||
for x in bs:
|
||||
build = bs.get_build(x)
|
||||
if build.status == Build.Status.BROKEN:
|
||||
yield (x, "%s (%s)" % (x, _("broken")))
|
||||
else:
|
||||
yield (x, x)
|
||||
|
||||
return list(generator())
|
||||
|
||||
def check(self, value):
|
||||
if not value:
|
||||
raise VariableError(_("Please select the assemble id"))
|
||||
l = self.available()
|
||||
if not l:
|
||||
raise VariableError(_("Assemble %s is not found") % value)
|
||||
if (self.Get('cl_builder_build').status == Build.Status.BROKEN and
|
||||
self.Get('cl_action') != 'break'):
|
||||
raise VariableError(
|
||||
_("Assemble %s is broken, try to restore build") % value)
|
||||
|
||||
|
||||
class VariableClBuilderBrokenId(BaseBuildId):
|
||||
"""
|
||||
Id развёрнутой сборки
|
||||
"""
|
||||
type = "choice"
|
||||
untrusted = True
|
||||
|
||||
def available(self):
|
||||
bs = self.Get('cl_builder_storage')
|
||||
for x in bs:
|
||||
build = bs.get_build(x)
|
||||
if build.status == Build.Status.BROKEN:
|
||||
yield x
|
||||
|
||||
def get(self):
|
||||
l = list(self.available())
|
||||
if l and len(l) == 1:
|
||||
return l[0]
|
||||
return ""
|
||||
|
||||
def choice(self):
|
||||
def generator():
|
||||
bs = self.Get('cl_builder_storage')
|
||||
for x in bs:
|
||||
build = bs.get_build(x)
|
||||
if build.status == Build.Status.BROKEN:
|
||||
yield (x, "%s (%s)" % (x, _("broken")))
|
||||
|
||||
return list(generator())
|
||||
|
||||
def check(self, value):
|
||||
if not value:
|
||||
raise VariableError(_("Please select the assemble id"))
|
||||
l = list(self.available())
|
||||
if not l:
|
||||
raise VariableError(_("Assemble %s is not found") % value)
|
||||
|
||||
|
||||
class VariableClBuilderId(ReadonlyVariable):
|
||||
"""
|
||||
Общий id сборки
|
||||
"""
|
||||
def get(self):
|
||||
action = self.Get('cl_action')
|
||||
if action == 'create':
|
||||
return self.Get('cl_builder_new_id')
|
||||
elif action == 'break':
|
||||
return self.Get('cl_builder_prepared_id')
|
||||
elif action == 'restore':
|
||||
return self.Get('cl_builder_broken_id')
|
||||
|
||||
|
||||
class VariableOsBuilderMakeopts(Variable):
|
||||
"""
|
||||
Параметры MAKEOPTS
|
||||
"""
|
||||
def get(self):
|
||||
return self.Get('install.os_install_makeopts')
|
||||
|
||||
|
||||
class VariableClBuilderBuildpkgSet(Variable):
|
||||
"""
|
||||
Собирать бинарные пакеты в сборке
|
||||
"""
|
||||
type = "bool"
|
||||
value = "off"
|
||||
|
||||
|
||||
class VariableClBuilderBasePath(Variable):
|
||||
"""
|
||||
Базовый путь до сборок (директория, куда будут помещены готовые
|
||||
iso образы, бинарные пакеты и т.д.)
|
||||
"""
|
||||
value = "/var/calculate/remote/assemble"
|
||||
|
||||
|
||||
class VariableClBuilderParentPath(ReadonlyVariable):
|
||||
"""
|
||||
Путь в ".." до родительской системы
|
||||
"""
|
||||
def get(self):
|
||||
builder_path = self.Get('cl_builder_path')
|
||||
return ("../"*len(filter(None,
|
||||
builder_path.split('/'))))[:-1]
|
||||
|
||||
|
||||
class VariableClBuilderPkgdir(Variable):
|
||||
"""
|
||||
Путь собираемых бинарных архивов
|
||||
"""
|
||||
def fallback(self):
|
||||
return path.join(self.Get('cl_builder_base_path'),
|
||||
self.Get('cl_builder_id'), "packages")
|
||||
|
||||
def get(self):
|
||||
action = self.Get('cl_action')
|
||||
if action == 'create':
|
||||
return self.fallback()
|
||||
elif action in ('restore',):
|
||||
build = self.Get('cl_builder_build')
|
||||
return build.pkgdir or self.fallback()
|
||||
else:
|
||||
return ""
|
||||
|
||||
|
||||
class VariableClBuilderAction(ReadonlyVariable):
|
||||
"""
|
||||
Дополнительное действие по созданию образа: iso, squash.
|
||||
"""
|
||||
value = ""
|
@ -0,0 +1,115 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
|
||||
# Copyright 2015 Calculate Ltd. http://www.calculate-linux.org
|
||||
#
|
||||
# Licensed under the Apache License, Version 2.0 (the "License");
|
||||
# you may not use this file except in compliance with the License.
|
||||
# You may obtain a copy of the License at
|
||||
#
|
||||
# http://www.apache.org/licenses/LICENSE-2.0
|
||||
#
|
||||
# Unless required by applicable law or agreed to in writing, software
|
||||
# distributed under the License is distributed on an "AS IS" BASIS,
|
||||
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
# See the License for the specific language governing permissions and
|
||||
# limitations under the License.
|
||||
|
||||
import sys
|
||||
import os
|
||||
from os import path
|
||||
from calculate.lib.datavars import ReadonlyVariable
|
||||
|
||||
from calculate.lib.cl_lang import setLocalTranslate
|
||||
|
||||
setLocalTranslate('cl_builder3', sys.modules[__name__])
|
||||
|
||||
|
||||
class BuilderLinux(ReadonlyVariable):
|
||||
# variable for get current system info (example: os_linux_shortname)
|
||||
variable = ""
|
||||
# field of distroinfo (name,ver,build,march and etc)
|
||||
distroinfo_field = ""
|
||||
|
||||
def source_data(self):
|
||||
image = self.Get('cl_builder_source')
|
||||
if image:
|
||||
d = image.getInfo()
|
||||
res = d.get(self.variable, "")
|
||||
return str(res()) if callable(res) else res
|
||||
else:
|
||||
return ""
|
||||
|
||||
def target_data(self):
|
||||
image = self.Get('cl_builder_target')
|
||||
if image:
|
||||
d = image.getInfo()
|
||||
res = d.get(self.variable, "")
|
||||
return str(res()) if callable(res) else res
|
||||
else:
|
||||
return ""
|
||||
|
||||
def get(self):
|
||||
"""Get by distroinfo or current info"""
|
||||
if self.Get('cl_action') == 'create':
|
||||
return self.source_data()
|
||||
elif self.Get('cl_action') in ('break', 'restore'):
|
||||
return self.target_data()
|
||||
return ""
|
||||
|
||||
|
||||
class VariableOsBuilderLinuxShortname(BuilderLinux):
|
||||
"""Shortname of system"""
|
||||
variable = "os_linux_shortname"
|
||||
|
||||
|
||||
class VariableOsBuilderLinuxVer(BuilderLinux):
|
||||
"""Shortname of system"""
|
||||
variable = "os_linux_ver"
|
||||
|
||||
def init(self):
|
||||
self.label = _("Building system version")
|
||||
|
||||
class VariableOsBuilderLinuxBuild(BuilderLinux):
|
||||
"""Shortname of system"""
|
||||
variable = "os_linux_build"
|
||||
|
||||
|
||||
class VariableOsBuilderArchMachine(BuilderLinux):
|
||||
"""Shortname of system"""
|
||||
variable = "os_arch_machine"
|
||||
|
||||
|
||||
class VariableOsBuilderLinuxFiles(BuilderLinux):
|
||||
"""Shortname of system"""
|
||||
variable = "os_linux_files"
|
||||
|
||||
|
||||
class VariableOsBuilderLinuxName(BuilderLinux):
|
||||
"""
|
||||
Install distro name
|
||||
"""
|
||||
variable = "os_linux_name"
|
||||
|
||||
|
||||
class VariableOsBuilderLinuxSystem(BuilderLinux):
|
||||
"""
|
||||
Install system name
|
||||
"""
|
||||
variable = "os_linux_system"
|
||||
|
||||
|
||||
class VariableOsBuilderLinuxSubname(BuilderLinux):
|
||||
"""
|
||||
Install subname
|
||||
"""
|
||||
variable = "os_linux_subname"
|
||||
|
||||
|
||||
class VariableClBuilderProfileName(BuilderLinux):
|
||||
"""
|
||||
Install subname
|
||||
"""
|
||||
def init(self):
|
||||
self.label = _("System profile")
|
||||
|
||||
variable = "cl_profile_name"
|
Loading…
Reference in new issue