Merge branch 'feature-55354/Studierendenverwaltung_Karteireiter_Archiv' into merge_FHC4_55354_55991_55992_60874_60875_61229_61230_61231

This commit is contained in:
Harald Bamberger
2025-05-21 13:29:21 +02:00
12 changed files with 1144 additions and 14 deletions
+1 -1
View File
@@ -6,4 +6,4 @@ $config['use_vuejs_dev_version'] = false;
// use bundled javascript
$config['use_bundled_javascript'] = false;
// systemerror_mailto use in FHC-Alert Plugin - if empty Link will not be rendered
$config['systemerror_mailto'] = '';
$config['systemerror_mailto'] = '';
@@ -43,7 +43,8 @@ class Documents extends FHCAPI_Controller
parent::__construct([
'permissionAlternativeFormat' => self::PERM_LOGGED,
'archive' => ['admin:rw', 'assistenz:rw'],
'archiveSigned' => ['admin:rw', 'assistenz:rw']
'archiveSigned' => ['admin:rw', 'assistenz:rw'],
'download' => ['admin:rw', 'assistenz:rw']
]);
// Load Phrases
@@ -66,7 +67,7 @@ class Documents extends FHCAPI_Controller
}
/**
* Download a not signed document.
* Archive a not signed document.
*
* @param string $xml (optional)
* @param string $xsl (optional)
@@ -79,7 +80,7 @@ class Documents extends FHCAPI_Controller
}
/**
* Download a signed document.
* Archive a signed document.
*
* @param string $xml (optional)
* @param string $xsl (optional)
@@ -91,6 +92,42 @@ class Documents extends FHCAPI_Controller
return $this->_archive($xml, $xsl, getAuthUID());
}
/**
*
* @return void
*/
public function download($xml, $xsl, $sign_user = null)
{
$akteExportData = $this->_getAkteExportData($xml, $xsl, $sign_user);
$akteData = $akteData['akteData'];
$exportData = $akteData['exportData'];
/**
* [
'vorlage' => $vorlage,
'xml_data' => $data,
'oe_kurzbz' => $xsl_oe_kurzbz,
'version' => $version,
'outputformat' => $outputformat,
'sign_user' => $sign_user
]
*/
// Output
$result = $this->documentexportlib->showContent(
$akteData['akteData']['inhalt'],
$exportData['vorlage'],
$exportData['xml_data'],
$exportData['oe_kurzbz'],
$exportData['version'],
$exportData['outputformat'],
$exportData['sign_user']
);
$this->terminateWithSuccess(true);
}
/**
* Helper function for archive() and archiveSigned()
*
@@ -100,16 +137,36 @@ class Documents extends FHCAPI_Controller
*
* @return void
*/
public function _archive($xml, $xsl, $sign_user = null)
private function _archive($xml, $xsl, $sign_user = null)
{
$akteData = $this->_getAkteExportData($xml, $xsl, $sign_user);
$this->load->model('crm/Akte_model', 'AkteModel');
$result = $this->AkteModel->insert($akteData['akteData']);
$this->getDataOrTerminateWithError($result);
$this->terminateWithSuccess(true);
}
/**
* @param string $xml
* @param string $xsl
* @param string $sign_user (optional)
*
* @return array with Akte data and export data
*/
private function _getAkteExportData($xml, $xsl, $sign_user = null)
{
if (!$xml || !$xsl) {
$this->load->library('form_validation');
if (!$xml) {
$xml = $this->input->post_get('xml');
$this->addMeta('xml', $xml);
$this->form_validation->set_rules('xml', 'xml', 'required');
}
if (!$xsl) {
$xsl = $this->input->post_get('xsl');
$this->addMeta('xsl', $xsl);
$this->form_validation->set_rules('xsl', 'xsl', 'required');
}
@@ -151,6 +208,7 @@ class Documents extends FHCAPI_Controller
$this->load->model('system/Vorlage_model', 'VorlageModel');
$result = $this->VorlageModel->load($xsl);
$this->addMeta("ress", $result);
$vorlage = current($this->getDataOrTerminateWithError($result));
if (!$vorlage)
show_404();
@@ -171,6 +229,7 @@ class Documents extends FHCAPI_Controller
$studiengang_kz = null;
if ($akteData['uid']) {
$this->load->model('crm/Student_model', 'StudentModel');
$this->StudentModel->addSelect('tbl_student.*, UPPER(typ || kurzbz) AS kuerzel');
$this->StudentModel->addJoin('public.tbl_studiengang', 'studiengang_kz', 'LEFT');
$result = $this->StudentModel->load([$akteData['uid']]);
$student = current($this->getDataOrTerminateWithError($result));
@@ -318,6 +377,7 @@ class Documents extends FHCAPI_Controller
$result = $this->VorlagestudiengangModel->getCurrent($xsl, $xsl_oe_kurzbz, $version);
$access_rights = current($this->getDataOrTerminateWithError($result));
// TODO: was bedeutet wenn keine berechtigung?
if (!$access_rights || !$access_rights->berechtigung)
return show_404();
@@ -413,10 +473,17 @@ class Documents extends FHCAPI_Controller
$akteData['titel'] .= '.pdf';
$akteData['inhalt'] = base64_encode($content);
$this->load->model('crm/Akte_model', 'AkteModel');
$result = $this->AkteModel->insert($akteData);
$this->getDataOrTerminateWithError($result);
$this->terminateWithSuccess(true);
return [
'akteData' => $akteData,
'exportData' =>
[
'vorlage' => $vorlage,
'xml_data' => $data,
'oe_kurzbz' => $xsl_oe_kurzbz,
'version' => $version,
'outputformat' => $outputformat,
'sign_user' => $sign_user
]
];
}
}
@@ -0,0 +1,70 @@
<?php
/**
* Copyright (C) 2024 fhcomplete.org
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
if (!defined('BASEPATH')) exit('No direct script access allowed');
/**
* Controller for downloading Akte
*/
class Akte extends Auth_Controller
{
/**
* Calls the parent's constructor and prepares libraries and phrases
*/
public function __construct()
{
parent::__construct([
'download' => ['admin:w', 'assistenz:w'],
]);
// Load models
$this->load->model('crm/Akte_model', 'AkteModel');
}
//------------------------------------------------------------------------------------------------------------------
// Public methods
/**
*
* Downloads an Akte
*/
public function download()
{
$akte_id = $this->input->get('akte_id');
if (!is_numeric($akte_id)) $this->terminateWithError('akte Id missing');
$result = $this->AkteModel->load($akte_id);
if (!hasData($result)) $this->terminateWithError('Akte not found');
$data = getData($result)[0];
if (isset($data->inhalt) && $data->inhalt != '')
{
header('Content-Description: File Transfer');
header('Content-Type: '. $data->mimetype);
header('Expires: 0');
header('Cache-Control: must-revalidate');
header('Pragma: public');
header('Content-Disposition: attachment; filename="'.$data->titel.'"');
echo base64_decode($data->inhalt);
die();
}
}
}
@@ -0,0 +1,272 @@
<?php
/**
* Copyright (C) 2024 fhcomplete.org
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
if (!defined('BASEPATH')) exit('No direct script access allowed');
use CI3_Events as Events;
/**
* This controller operates between (interface) the JS (GUI) and the back-end
* Provides data to the ajax get calls about archive documents
* Listens to ajax post calls to change the archive documents
* This controller works with JSON calls on the HTTP GET or POST and the output is always JSON
*/
class Archiv extends FHCAPI_Controller
{
/**
* Calls the parent's constructor and prepares libraries and phrases
*/
public function __construct()
{
parent::__construct([
'get' => ['admin:r', 'assistenz:r'],
'getArchivVorlagen' => ['admin:r', 'assistenz:r'],
'archive' => ['admin:w', 'assistenz:w'],
'download' => ['admin:w', 'assistenz:w'],
'update' => ['admin:w'],
'delete' => ['admin:w', 'assistenz:w']
]);
// Load models
$this->load->model('crm/Akte_model', 'AkteModel');
$this->load->model('system/Vorlage_model', 'VorlageModel');
// Load language phrases
$this->loadPhrases([
'archiv'
]);
}
//------------------------------------------------------------------------------------------------------------------
// Public methods
/**
* Get archive documents for a person
* @return void
*/
public function get()
{
$person_id = $this->input->post('person_id');
$this->load->library('form_validation');
if (!$person_id || !is_array($person_id))
{
$this->form_validation->set_rules('person_id', 'Person ID', 'required');
if (!$this->form_validation->run())
$this->terminateWithValidationErrors($this->form_validation->error_array());
}
$result = $this->AkteModel->getArchiv($person_id);
$data = $this->getDataOrTerminateWithError($result);
$this->terminateWithSuccess($data);
}
/**
* Get Vorlagen for archiving documents
* @return void
*/
public function getArchivVorlagen()
{
$result = $this->VorlageModel->getArchivVorlagen();
$data = $this->getDataOrTerminateWithError($result);
$this->terminateWithSuccess($data);
}
/**
*
* @param
* @return object success or error
*/
public function download()
{
$akte_id = $this->input->get('akte_id');
if (!is_numeric($akte_id)) $this->terminateWithError('akte Id missing');
$result = $this->AkteModel->load($akte_id);
if (!hasData($result)) $this->terminateWithError('Akte not found');
$data = $this->getDataOrTerminateWithError($result);
$data = getData($result)[0];
//$this->addMeta("daa", $data->inhalt);
$fileObj = new stdClass();
if (isset($data->inhalt) && $data->inhalt != '')
{
// Define handle to output stream
$tmpFilePointer = fopen("php://output", 'w');
$meta_data = stream_get_meta_data($tmpFilePointer);
$filename = $meta_data["uri"];
fwrite($tmpFilePointer, $data->inhalt);
header('Content-Description: File Transfer');
header('Content-Type: '. $data->mimetype);
header('Expires: 0');
header('Cache-Control: must-revalidate');
header('Pragma: public');
//header('Content-Length: ' . filesize($fileObj->file));
//header("Content-type: $data->mimetype");
header('Content-Disposition: attachment; filename="'.$data->titel.'"');
readfile($filename);
//echo base64_decode($data->inhalt);
die();
//~ $fileObj->file = $data->inhalt;
//~ $fileObj->name = $data->titel;
//~ $fileObj->mimetype = $data->mimetype;
//~ $fileObj->disposition = 'attachment';
}
else
{
$this->load->library('AkteLib');
$result = $this->aktelib->get($akte_id);
}
/* $fileObj->filename
* $fileObj->file
* $fileObj->name
* $fileObj->mimetype
* $fileObj->disposition*/
}
/**
* Updating an Akte
* @return void
*/
public function update()
{
$this->load->library('form_validation');
$this->form_validation->set_rules('akte_id', 'Akte Id', 'required');
$this->form_validation->set_rules('signiert', 'Signiert', 'is_bool');
$this->form_validation->set_rules('stud_selfservice', 'Self-Service', 'is_bool');
//Events::trigger('konto_update_validation', $this->form_validation);
if (!$this->form_validation->run())
$this->terminateWithValidationErrors($this->form_validation->error_array());
$id = $this->input->post('akte_id');
// get the akte
$result = $this->AkteModel->load($id);
if (!hasData($result)) $this->terminateWithError("Akte not found!");
$akte = getData($result)[0];
$allowed = [
'signiert',
'stud_selfservice'
];
$data = [
'updateamum' => date('c'),
'updatevon' => getAuthUID()
];
// if Akte has Inhalt directly in Akte table
if (isset($_FILES['datei']['tmp_name']))
{
$this->addMeta('read', "read");
// update inhalt directly
// get tmp file
$filename = $_FILES['datei']['tmp_name'];
// open it
$fp = fopen($filename,'r');
// read it
$content = fread($fp, filesize($filename));
fclose($fp);
// encode it
$data['inhalt'] = base64_encode($content);
$this->addMeta('content', base64_encode($content));
}
foreach ($allowed as $field)
if ($this->input->post($field) !== null)
$data[$field] = $this->input->post($field);
$this->addMeta("data", $data);
$result = $this->AkteModel->update($id, $data);
$this->getDataOrTerminateWithError($result);
$result = null;
$this->terminateWithSuccess($result);
}
/**
* Delete archived Akte
*
* @return void
*/
public function delete()
{
$this->load->library('form_validation');
$this->form_validation->set_rules('akte_id', 'Akte ID', 'required');
$this->form_validation->set_rules('studiengang_kz', 'Studiengang', 'has_permissions_for_stg[admin:rw,assistenz:rw]');
if (!$this->form_validation->run())
$this->terminateWithValidationErrors($this->form_validation->error_array());
$akte_id = $this->input->post('akte_id');
$result = $this->AkteModel->load($akte_id);
if (!hasData($result))
{
$this->terminateWithError($this->p->t('archiv', 'error_missing', [
'akte_id' => $akte_id
]));
}
$result = getData($result)[0];
if ($result->dokument_kurzbz == 'Ausbvert'
&& isset($result->akzeptiertamum)
&& !isEmptyString($result->akzeptiertamum)
&& !has_permissions_for_stg($this->input->post('studiengang_kz'), 'admin:rw')
)
{
$this->terminateWithError($this->p->t('archiv', 'nur_admins_loschen_ausbildungsvertraege', [
'akte_id' => $akte_id
]));
}
$result = $this->AkteModel->delete($akte_id);
if (isError($result)) $this->terminateWithError(getError($result));
$this->terminateWithSuccess();
}
}
@@ -128,6 +128,14 @@ class Config extends FHCAPI_Controller
'component' => './Stv/Studentenverwaltung/Details/Mobility.js'
];
$result['archive'] = [
'title' => $this->p->t('stv', 'tab_archive'),
'component' => './Stv/Studentenverwaltung/Details/Archiv.js',
'config' => [
'showEdit' => $this->permissionlib->isBerechtigt('admin')
]
];
Events::trigger('stv_conf_student', function & () use (&$result) {
return $result;
});
@@ -167,6 +175,13 @@ class Config extends FHCAPI_Controller
'component' => './Stv/Studentenverwaltung/Details/Abschlusspruefung.js',
'config' => $config['finalexam']
];
$result['archive'] = [
'title' => $this->p->t('stv', 'tab_archive'),
'component' => './Stv/Studentenverwaltung/Details/Archiv.js',
'config' => [
'showEdit' => $this->permissionlib->isBerechtigt('admin')
]
];
Events::trigger('stv_conf_students', function & () use (&$result) {
return $result;
+7 -3
View File
@@ -195,9 +195,9 @@ class Akte_model extends DB_Model
}
/**
* Liefert die Archivdokumente einer Person
* Liefert die Archivdokumente einer Person/mehrerer Personen
*
* @param integer $person_id
* @param integer/array $person_id
* @param boolean|null $signiert Wenn true werden nur Dokumente geliefert die digital signiert wurden.
* @param boolean|null $stud_selfservice Wenn true werden nur Dokumente geliefert die Studierende selbst herunterladen duerfen.
*
@@ -237,10 +237,14 @@ class Akte_model extends DB_Model
if ($stud_selfservice !== null)
$this->db->where('stud_selfservice', (boolean)$stud_selfservice);
if (is_array($person_id))
$this->db->where_in('person_id', $person_id);
else
$this->db->where('person_id', $person_id);
$this->addOrder('erstelltam', 'DESC');
return $this->loadWhere([
'person_id' => $person_id,
'archiv' => true
]);
}
+11 -1
View File
@@ -13,7 +13,7 @@ class Vorlage_model extends DB_Model
}
/**
* Returns mume types
* Returns mime types
*/
public function getMimeTypes()
{
@@ -21,4 +21,14 @@ class Vorlage_model extends DB_Model
return $this->execQuery($query);
}
/**
* Returns all Vorlagen for archive
*/
public function getArchivVorlagen()
{
$query ="SELECT * FROM public.tbl_vorlage WHERE archivierbar=true ORDER BY bezeichnung";
return $this->execQuery($query);
}
}
+2
View File
@@ -10,6 +10,7 @@ import exam from './stv/exam.js';
import abschlusspruefung from './stv/abschlusspruefung.js';
import grades from './stv/grades.js';
import mobility from './stv/mobility.js';
import archiv from './stv/archiv.js';
export default {
verband,
@@ -24,6 +25,7 @@ export default {
abschlusspruefung,
grades,
mobility,
archiv,
configStudent() {
return this.$fhcApi.get('api/frontend/v1/stv/config/student');
},
+36
View File
@@ -0,0 +1,36 @@
export default {
tabulatorConfig(config, self) {
config.ajaxURL = 'api/frontend/v1/stv/archiv/get';
config.ajaxParams = () => {
const params = {
person_id: self.modelValue.person_id || self.modelValue.map(e => e.person_id)
};
return params;
};
config.ajaxRequestFunc = (url, config, params) => this.$fhcApi.post(url, params, config);
config.ajaxResponse = (url, params, response) => response.data;
return config;
},
getArchivVorlagen() {
return this.$fhcApi.post('api/frontend/v1/stv/archiv/getArchivVorlagen');
},
archive(data) {
return this.$fhcApi.post(
'api/frontend/v1/documents/archive',
data
);
},
archiveSigned(data) {
return this.$fhcApi.post(
'api/frontend/v1/documents/archiveSigned',
data
);
},
update(data) {
return this.$fhcApi.post('api/frontend/v1/stv/archiv/update', data);
},
delete({akte_id, studiengang_kz}) {
return this.$fhcApi.post('api/frontend/v1/stv/archiv/delete', {akte_id, studiengang_kz});
}
};
@@ -0,0 +1,276 @@
import {CoreFilterCmpt} from "../../../filter/Filter.js";
import FormInput from "../../../Form/Input.js";
import AkteEdit from "./Archiv/Edit.js";
export default {
components: {
CoreFilterCmpt,
FormInput,
AkteEdit
},
inject: {
defaultSemester: {
from: 'defaultSemester'
}
},
props: {
modelValue: Object,
config: {
type: Object,
default: {}
}
},
data() {
return {
loading: false,
selectedVorlage: {},
vorlagenArchiv: [],
vorlageXmlXslMappings: {
'zeugnis.rdf.php': [
'Zeugnis',
'ZeugnisEng'
],
'abschlusspruefung.rdf.php': [
'PrProtokollBakk',
'PrProtBakkEng',
'PrProtBA',
'PrProtBAEng',
'PrProtokollDipl',
'PrProtDiplEng',
'PrProtMA',
'PrProtMAEng',
'Bescheid',
'BescheidEng',
'Bakkurkunde',
'BakkurkundeEng',
'Diplomurkunde',
'DiplomurkundeEng',
],
'diplomasupplement.xml.php': [
'DiplSupplement',
'SZeugnis'
],
'studienblatt.xml.php': [
'Studienblatt',
'StudienblattEng'
],
'ausbildungsvertrag.xml.php': [
'Ausbildungsver',
'AusbVerEng'
],
'abschlussdokument_lehrgaenge.xml.php': [
'AbschlussdokumentLehrgaenge'
]
}
//studiengang_kz: false
};
},
computed: {
//~ personIds() {
//~ if (this.modelValue.person_id)
//~ return [this.modelValue.person_id];
//~ return this.modelValue.map(e => e.person_id);
//~ },
tabulatorColumns() {
const columns = [
{title: "Akte Id", field: "akte_id", visible: false},
{title: this.$p.t('stv', 'archiv_title'), field: "titel"},
{title: this.$p.t('stv', 'archiv_description'), field: "bezeichnung"},
{title: this.$p.t('stv', 'archiv_creation_date'), field: "erstelltam"},
{
title: this.$p.t('stv', 'archiv_signiert'),
field: "signiert",
formatter:"tickCross",
hozAlign:"center",
formatterParams: {
tickElement: '<i class="fa fa-check text-success"></i>',
crossElement: '<i class="fa fa-xmark text-danger"></i>'
}
},
{
title: "Selfservice",
field: "stud_selfservice",
formatter:"tickCross",
hozAlign:"center",
formatterParams: {
tickElement: '<i class="fa fa-check text-success"></i>',
crossElement: '<i class="fa fa-xmark text-danger"></i>'
},
},
{title: this.$p.t('stv', 'archiv_accepted_on_at'), field: "akzeptiertamum"},
{
title: this.$p.t('stv', 'archiv_gedruckt'),
field: "gedruckt",
visible: false,
formatter:"tickCross",
hozAlign:"center",
formatterParams: {
tickElement: '<i class="fa fa-check text-success"></i>',
crossElement: '<i class="fa fa-xmark text-danger"></i>'
}
},
{
title: 'Aktionen', field: 'actions',
formatter: (cell, formatterParams, onRendered) => {
let container = document.createElement('div');
container.className = "d-flex gap-2";
if (this.config.showEdit)
{
let editButton = document.createElement('button');
editButton.className = 'btn btn-outline-secondary';
editButton.innerHTML = '<i class="fa fa-edit"></i>';
editButton.addEventListener('click', () =>
this.$refs.edit.open(cell.getData())
);
container.append(editButton);
}
let deleteButton = document.createElement('button');
deleteButton.className = 'btn btn-outline-secondary';
deleteButton.innerHTML = '<i class="fa fa-trash"></i>';
deleteButton.addEventListener('click', evt => {
evt.stopPropagation();
this.$fhcAlert
.confirmDelete()
.then(result => result ? {akte_id: cell.getData().akte_id, studiengang_kz: this.modelValue.studiengang_kz} : Promise.reject({handled:true}))
.then(this.$fhcApi.factory.stv.archiv.delete)
.then(() => {
//cell.getRow().delete();
this.reload();
})
.catch(this.$fhcAlert.handleSystemError);
});
container.append(deleteButton);
return container;
},
minWidth: 150, // Ensures Action-buttons will be always fully displayed
maxWidth: 150,
frozen: true
}
];
return Object.values(columns);
},
tabulatorOptions() {
return this.$fhcApi.factory.stv.archiv.tabulatorConfig({
layout:"fitDataTable",
columns: this.tabulatorColumns,
//selectable: true,
//selectableRangeMode: 'click',
index: 'akte_id',
persistenceID: 'stv-details-archiv'
}, this);
},
tabulatorEvents() {
const events = [
{
event: "rowDblClick",
handler: (e, row) => {
this.actionDownload(row.getData().akte_id);
}
}
];
return events;
}
},
watch: {
modelValue() {
this.$refs.table.reloadTable();
}
},
methods: {
reload() {
this.$refs.table.reloadTable();
},
updateData(data) {
if (!data)
return this.reload();
this.$refs.table.tabulator.updateOrAddData(data);
},
actionArchive() {
let archiveDataArr = Array.isArray(this.modelValue) ? this.modelValue : [this.modelValue];
for (let archiveData of archiveDataArr)
{
this.loading = true;
let archiveFunction =
this.selectedVorlage.signierbar
? this.$fhcApi.factory.stv.archiv.archiveSigned
: this.$fhcApi.factory.stv.archiv.archive;
archiveFunction({
xml: this.getXmlByXsl(this.selectedVorlage.vorlage_kurzbz),
xsl: this.selectedVorlage.vorlage_kurzbz,
ss: this.defaultSemester,
uid: archiveData.uid,
prestudent_id: archiveData.prestudent_id
})
.then(result => result.data)
.then(() => {
this.reload();
this.loading = false;
})
.then(() => this.$p.t('ui/gespeichert'))
.then(this.$fhcAlert.alertSuccess)
.catch(error => {
this.$fhcAlert.handleSystemError(error);
this.loading = false;
});
}
},
actionDownload(akte_id) {
window.open(
FHC_JS_DATA_STORAGE_OBJECT.app_root
+ FHC_JS_DATA_STORAGE_OBJECT.ci_router + '/api/frontend/v1/stv/akte/download?akte_id=' + encodeURIComponent(akte_id),
'_blank'
);
},
getXmlByXsl(xsl) {
for (let xml in this.vorlageXmlXslMappings) {
let xslArr = this.vorlageXmlXslMappings[xml];
if (xslArr.includes(xsl)) return xml;
}
return null;
}
},
created() {
this.$fhcApi
.factory.stv.archiv.getArchivVorlagen()
.then(result => {this.vorlagenArchiv = result.data; this.selectedVorlage = result.data.filter(o => o.vorlage_kurzbz == 'Zeugnis')[0];})
.catch(this.$fhcAlert.handleSystemError);
},
template: `
<div class="stv-details-konto h-100 d-flex flex-column">
<core-filter-cmpt
ref="table"
table-only
:side-menu="false"
:tabulator-options="tabulatorOptions"
:tabulator-events="tabulatorEvents"
reload
>
<template #actions>
<div class="input-group w-auto">
<select class="form-select" v-model="selectedVorlage">
<option v-for="vorlage in vorlagenArchiv" :key="vorlage.vorlage_kurzbz" :value="vorlage">
{{ vorlage.bezeichnung }}
</option>
</select>
<button
class="btn btn-primary"
@click="actionArchive()"
:disabled="loading"
>
<i v-if="loading" class="fa fa-spinner fa-spin"></i>
{{ $p.t('stv/archiv_dokument_archivieren') }}
</button>
</div>
</template>
</core-filter-cmpt>
<akte-edit ref="edit" :config="config" @saved="updateData"></akte-edit>
</div>`
};
@@ -0,0 +1,118 @@
import BsModal from "../../../../Bootstrap/Modal.js";
import CoreForm from "../../../../Form/Form.js";
import FormValidation from "../../../../Form/Validation.js";
import FormInput from "../../../../Form/Input.js";
import FormUploadDms from '../../../../Form/Upload/Dms.js';
export default {
components: {
BsModal,
CoreForm,
FormValidation,
FormInput,
FormUploadDms
},
inject: {
lists: {
from: 'lists'
}
},
props: {
config: {
type: Object,
default: {}
}
},
data() {
return {
loading: false,
//file: [],
data: {
datei: []
}
};
},
methods: {
save() {
this.$refs.form.clearValidation();
this.loading = true;
//~ const formData = new FormData();
//~ formData.append('data', JSON.stringify(this.data));
//Object.entries(this.data.anhang).forEach(([k, v]) => formData.append(k, v));
this.$refs.form
.factory.stv.archiv.update(this.data)
.then(result => {
this.$emit('saved', result.data);
this.loading = false;
this.$refs.modal.hide();
this.$fhcAlert.alertSuccess(this.$p.t('ui/gespeichert'));
})
.catch(error => {
this.$fhcAlert.handleSystemError(error);
this.loading = false;
});
},
open(data) {
this.data.datei = [];
this.data = {...this.data, ...data};
this.$refs.modal.show();
},
preventCloseOnLoading(ev) {
if (this.loading)
ev.returnValue = false;
}
},
template: `
<core-form ref="form" class="stv-details-archiv-edit" @submit.prevent="save">
<bs-modal ref="modal" @hide-bs-modal="preventCloseOnLoading">
<form-validation></form-validation>
<fieldset :disabled="loading">
<div class="mb-3">
{{ data.titel }} ({{ data.bezeichnung }})
</div>
<form-input
v-model="data.akte_id"
name="akte_id"
:label="$p.t('stv/archiv_akte_id')"
disabled
>
</form-input>
<div class="position-relative">
<label for="text" class="form-label col-sm-2">{{ $p.t('stv/archiv_new_file') }}</label>
<!--Upload Component-->
<FormUploadDms ref="upload" id="inhalt" v-model="data.datei"></FormUploadDms>
</div>
<div class="mt-3">
<form-input
container-class="form-check"
type="checkbox"
name="signiert"
:label="$p.t('stv/archiv_signiert')"
v-model="data.signiert"
>
</form-input>
<form-input
container-class="form-check"
type="checkbox"
name="stud_selfservice"
:label="'Selfservice'"
v-model="data.stud_selfservice"
>
</div>
</form-input>
</fieldset>
<template #title>
{{ $p.t('stv/archiv_title_edit', data) }}
</template>
<template #footer>
<button type="submit" class="btn btn-primary" :disabled="loading">
<i v-if="loading" class="fa fa-spinner fa-spin"></i>
{{ $p.t('ui/speichern') }}
</button>
</template>
</bs-modal>
</core-form>`
};
+260
View File
@@ -40692,6 +40692,266 @@ array(
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_dokument_archivieren',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Dokument archivieren',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Archive document',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'tab_archive',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Archiv',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Archive',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_title',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Titel',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Title',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_description',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Bezeichnung',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Description',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_creation_date',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Erstelldatum',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Creation date',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_accepted_on_at',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'AkzeptiertAmUm',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'AcceptionOnAt',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_gedruckt',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Gedruckt',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Printed',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_signiert',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Signiert',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Signed',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_title_edit',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Akte aktualisieren',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Edit document',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_akte',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Akte',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Document',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_new_file',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Neue Datei',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'New file',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_akte_id',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Akte ID',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Document ID',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'stv',
'phrase' => 'archiv_signed',
'insertvon' => 'system',
'phrases' => array(
array(
'sprache' => 'German',
'text' => 'Signiert',
'description' => '',
'insertvon' => 'system'
),
array(
'sprache' => 'English',
'text' => 'Signed',
'description' => '',
'insertvon' => 'system'
)
)
),
array(
'app' => 'core',
'category' => 'mobility',