dbmsv2_init...1

This commit is contained in:
choi.jh 2025-09-02 20:31:40 +09:00
parent 757df14d47
commit a9eb211f41
33 changed files with 808 additions and 227 deletions

View File

@ -179,6 +179,19 @@ $routes->group('admin', ['namespace' => 'App\Controllers\Admin', 'filter' => 'au
$routes->post('batchjob_delete', 'ServerController::batchjob_delete');
$routes->get('download/(:alpha)', 'ServerController::download/$1');
});
$routes->group('serverpart', ['namespace' => 'App\Controllers\Admin\Equipment'], function ($routes) {
$routes->get('/', 'ServerPartController::index');
$routes->get('create', 'ServerPartController::create_form');
$routes->post('create', 'ServerPartController::create');
$routes->get('modify/(:num)', 'ServerPartController::modify_form/$1');
$routes->post('modify/(:num)', 'ServerPartController::modify/$1');
$routes->get('view/(:num)', 'ServerPartController::view/$1');
$routes->get('delete/(:num)', 'ServerPartController::delete/$1');
$routes->get('toggle/(:num)/(:any)', 'ServerPartController::toggle/$1/$2');
$routes->post('batchjob', 'ServerPartController::batchjob');
$routes->post('batchjob_delete', 'ServerPartController::batchjob_delete');
$routes->get('download/(:alpha)', 'ServerPartController::download/$1');
});
$routes->group('line', ['namespace' => 'App\Controllers\Admin\Equipment'], function ($routes) {
$routes->get('/', 'LineController::index');
$routes->get('create', 'LineController::create_form');
@ -231,7 +244,7 @@ $routes->group('admin', ['namespace' => 'App\Controllers\Admin', 'filter' => 'au
$routes->post('batchjob_delete', 'PartController::batchjob_delete');
$routes->get('download/(:alpha)', 'PartController::download/$1');
});
$routes->group('cs', ['namespace' => 'App\Controllers\Admin\Equipment'], function ($routes) {
$routes->group('onetime', ['namespace' => 'App\Controllers\Admin\Equipment'], function ($routes) {
$routes->get('/', 'OnetimeController::index');
$routes->get('create', 'OnetimeController::create_form');
$routes->post('create', 'OnetimeController::create');

View File

@ -35,4 +35,28 @@ class PartController extends EquipmentController
return $this->_helper;
}
//Index,FieldForm관
// protected function index_process(array $entities = []): array
// {
// $where = null;
// $columns = [
// "uid",
// "code",
// "CASE
// WHEN code LIKE 'CPU%' THEN 'CPU'
// WHEN code LIKE 'RAM%' THEN 'RAM'
// WHEN code LIKE 'DISK%' THEN 'DISK'
// WHEN code LIKE 'OS%' THEN 'OS'
// WHEN code LIKE 'DB%' THEN 'DB'
// WHEN code LIKE 'SOFTWARE%' THEN 'SOFTWARE'
// ELSE 'UNKNOWN'
// END AS type",
// "title",
// "price",
// "status",
// ];
// foreach ($this->getService()->getEntities($where, $columns) as $entity) {
// $entities[] = $entity;
// }
// return $entities;
// }
}

View File

@ -42,6 +42,7 @@ class ServerController extends EquipmentController
switch ($this->getAction()) {
case 'create_form':
case 'modify_form':
case 'view':
case 'index':
$this->control = $this->getControlDatas();
$this->getHelper()->setViewDatas($this->getViewDatas());

View File

@ -0,0 +1,40 @@
<?php
namespace App\Controllers\Admin\Equipment;
use App\Entities\Equipment\ServerPartEntity;
use App\Helpers\Equipment\ServerPartHelper;
use App\Services\Equipment\ServerPartService;
use CodeIgniter\HTTP\RedirectResponse;
use CodeIgniter\HTTP\RequestInterface;
use CodeIgniter\HTTP\ResponseInterface;
use Psr\Log\LoggerInterface;
class ServerPartController extends EquipmentController
{
public function initController(RequestInterface $request, ResponseInterface $response, LoggerInterface $logger)
{
parent::initController($request, $response, $logger);
$this->content_title = lang("{$this->getService()->getClassName()}.title");
$this->class_path .= $this->getService()->getClassName();
$this->uri_path .= strtolower($this->getService()->getClassName('/')) . '/';
// $this->view_path .= strtolower($this->getService()->getClassName()) . DIRECTORY_SEPARATOR;
$this->serverinfopartinfo_cnt_options = array_combine(range(1, 10), range(1, 10));
}
public function getService(): ServerPartService
{
if (!$this->_service) {
$this->_service = new ServerPartService();
}
return $this->_service;
}
public function getHelper(): ServerPartHelper
{
if (!$this->_helper) {
$this->_helper = new ServerPartHelper();
}
return $this->_helper;
}
//Index,FieldForm관련
}

View File

@ -249,8 +249,7 @@ abstract class CommonController extends BaseController
//Process Result처리
protected function getResultFail(string $message = MESSAGES["FAILED"]): RedirectResponse
{
LogCollector::debug($message);
$this->getMyLogService()->save($this->getService()->getClassName(), $this->getAction(), $message, $this->getMyAuth()->getUIDByAuthInfo());
// $this->getMyLogService()->save($this->getService()->getClassName(), $this->getAction(), $message, $this->getMyAuth()->getUIDByAuthInfo());
if ($this->request->getMethod() === 'POST') {
return redirect()->back()->withInput()->with('error', $message);
}
@ -262,7 +261,7 @@ abstract class CommonController extends BaseController
switch ($this->getControlDatas('action')) {
case 'create':
case 'modify':
$this->getMyLogService()->save($this->getService()->getClassName(), $this->getAction(), $message, $this->getMyAuth()->getUIDByAuthInfo());
// $this->getMyLogService()->save($this->getService()->getClassName(), $this->getAction(), $message, $this->getMyAuth()->getUIDByAuthInfo());
$result = $this->view($this->entity->getPK());
break;
case 'create_form':

View File

@ -4,8 +4,8 @@
"settings": {
"width": 3000,
"height": 3000,
"scrollTop": -1512.3031,
"scrollLeft": -1646.9114,
"scrollTop": -1108.3031,
"scrollLeft": -588,
"zoomLevel": 0.76,
"show": 511,
"database": 4,
@ -337,7 +337,8 @@
"comment": "PART정보",
"columnIds": [
"2HB01q46-mugMjuOz85YG",
"TsfQy78jcI0ref_kE7OV9",
"InO1oDu66d2I2e84cDrpF",
"OGYYobEerCY_Fsb8dqU0D",
"1q8jG5dQKdD35_XYimkSk",
"HYB03rpc8hol5HFnZGtAi",
"VycsOgeM1SXkcq_5XYUMS",
@ -350,7 +351,9 @@
"4acJag7ORjUzX7FP-gnhZ",
"vYX0n1Zr9y259z_DMJm7s",
"62_dxuBdQszhGOVZkzL9f",
"InO1oDu66d2I2e84cDrpF",
"TsfQy78jcI0ref_kE7OV9",
"OGYYobEerCY_Fsb8dqU0D",
"1q8jG5dQKdD35_XYimkSk",
"D7Q_X02LvMZbBtg71_hCK",
"lwe5PLEmpyTipKEVSCHRJ",
@ -373,7 +376,7 @@
"color": ""
},
"meta": {
"updateAt": 1756279418325,
"updateAt": 1756778060089,
"createAt": 1745819764138
}
},
@ -853,7 +856,6 @@
"l2g7xess8DY86_ZOm7Ca1",
"IbWdZlEEF70bGqUDkU5ub",
"eu4eV0U7BRaP7Zk-oyBhV",
"czO0QNJkidvlfvj3hL6xs",
"mYEan5gjLS5bBthtFCc6w",
"tmSvn-3Kqlf7oUbiedFDh",
"SioEINPlR0iyL87vqa4N-",
@ -879,7 +881,8 @@
"NdvFKvSSsZJ3s1sEMgXzt",
"e65_vbZsM9k8Cn5lwGjt5",
"JP9PTSr956CAPbXosCtEq",
"kDyVwSigBBYnp_F9MyRAw"
"kDyVwSigBBYnp_F9MyRAw",
"IMTeN4-Evbpr5MMraE__C"
],
"ui": {
"x": 698.2708,
@ -890,7 +893,7 @@
"color": ""
},
"meta": {
"updateAt": 1756279409021,
"updateAt": 1756772659816,
"createAt": 1755476453282
}
},
@ -8215,6 +8218,66 @@
"updateAt": 1756279042574,
"createAt": 1756279042572
}
},
"IMTeN4-Evbpr5MMraE__C": {
"id": "IMTeN4-Evbpr5MMraE__C",
"tableId": "8GYAVBvZGaMFeq3QuXk_B",
"name": "code",
"comment": "서비스코드",
"dataType": "VARCHAR(20)",
"default": "",
"options": 12,
"ui": {
"keys": 0,
"widthName": 60,
"widthComment": 62,
"widthDataType": 75,
"widthDefault": 60
},
"meta": {
"updateAt": 1756772613764,
"createAt": 1756772613762
}
},
"InO1oDu66d2I2e84cDrpF": {
"id": "InO1oDu66d2I2e84cDrpF",
"tableId": "ZMGIWLFEswObjH2Sx0NlW",
"name": "code",
"comment": "서비스코드",
"dataType": "VARCHAR(20)",
"default": "",
"options": 12,
"ui": {
"keys": 0,
"widthName": 60,
"widthComment": 62,
"widthDataType": 75,
"widthDefault": 60
},
"meta": {
"updateAt": 1756772685250,
"createAt": 1756772685250
}
},
"OGYYobEerCY_Fsb8dqU0D": {
"id": "OGYYobEerCY_Fsb8dqU0D",
"tableId": "ZMGIWLFEswObjH2Sx0NlW",
"name": "type",
"comment": "부품구분",
"dataType": "VARCHAR(20)",
"default": "",
"options": 8,
"ui": {
"keys": 0,
"widthName": 60,
"widthComment": 60,
"widthDataType": 75,
"widthDefault": 60
},
"meta": {
"updateAt": 1756778069722,
"createAt": 1756778058760
}
}
},
"relationshipEntities": {
@ -8424,8 +8487,8 @@
"columnIds": [
"2HB01q46-mugMjuOz85YG"
],
"x": 563.565,
"y": 2249.8862,
"x": 565.565,
"y": 2261.8862,
"direction": 2
},
"end": {
@ -8434,7 +8497,7 @@
"l2g7xess8DY86_ZOm7Ca1"
],
"x": 698.2708,
"y": 2407.9865,
"y": 2395.9865,
"direction": 1
},
"meta": {
@ -8826,7 +8889,7 @@
"IbWdZlEEF70bGqUDkU5ub"
],
"x": 1292.2708,
"y": 2487.9865,
"y": 2469.9865,
"direction": 2
},
"meta": {
@ -8938,7 +9001,7 @@
"eu4eV0U7BRaP7Zk-oyBhV"
],
"x": 1292.2708,
"y": 2327.9865,
"y": 2321.9865,
"direction": 2
},
"meta": {

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

File diff suppressed because one or more lines are too long

View File

@ -35,12 +35,12 @@ abstract class CommonEntity extends Entity
{
return $this->attributes['updated_at'];
}
final public function setUpdatedAt(string $value): void
{
$this->attributes['updated_at'] = $value;
}
final public function getCreatedAt(): string
{
return $this->attributes['created_at'];
}
final public function getDeletedAt(): string
{
return $this->attributes['deleted_at'];
}
}

View File

@ -2,7 +2,8 @@
namespace App\Entities\Customer;
use App\Entities\Customer\ClientEntity;
use App\Entities\Equipment\ServerEntity;
use App\Entities\Equipment\SwitchEntity;
use App\Models\Customer\ServiceModel;
class ServiceEntity extends CustomerEntity
@ -13,6 +14,28 @@ class ServiceEntity extends CustomerEntity
const STATUS_PAUSE = "pause";
const STATUS_TERMINATED = "terminated";
const DEFAULT_STATUS = self::STATUS_NORMAL;
public function setServerEntity(ServerEntity|null $entity): void
{
$this->attributes['serverEntity'] = $entity;
}
public function getServerEntity(): ServerEntity|null
{
if (!array_key_exists('serverEntity', $this->attributes)) {
return null;
}
return $this->attributes['serverEntity'];
}
public function setSwitchEntity(SwitchEntity|null $entity): void
{
$this->attributes['switchEntity'] = $entity;
}
public function getSwitchEntity(): SwitchEntity|null
{
if (!array_key_exists('switchEntity', $this->attributes)) {
return null;
}
return $this->attributes['switchEntity'];
}
public function getCode(): string
{
return $this->attributes['code'] ?? "null";
@ -21,6 +44,10 @@ class ServiceEntity extends CustomerEntity
{
return intval($this->attributes['user_uid']);
}
final public function getClientInfoUID(): int
{
return intval($this->attributes['clientinfo_uid']);
}
public function getSwitchCode(): string
{
return $this->attributes['switchinfo_code'];

View File

@ -2,6 +2,7 @@
namespace App\Entities\Equipment;
use App\Entities\Equipment\ServerPartEntity;
use App\Models\Equipment\ServerModel;
class ServerEntity extends EquipmentEntity
@ -13,14 +14,14 @@ class ServerEntity extends EquipmentEntity
const STATUS_FORBIDDEN = "forbidden";
const DEFAULT_STATUS = self::STATUS_AVAILABLE;
public function addServerPartEntity(string $partType, ServerPartENtity $entity): void
public function addServerPartEntity(string $partType, ServerPartEntity $entity): void
{
if (!array_key_exists('serverPartEntities', $this->attributes)) {
$this->attributes['serverPartEntities'] = [];
}
$this->attributes['serverPartEntities'][$partType] = $entity;
}
public function getServerPartEntity(string $partType): ServerPartENtity|null
public function getServerPartEntity(string $partType): ServerPartEntity|null
{
if (!array_key_exists('serverPartEntities', $this->attributes)) {
return null;

View File

@ -8,7 +8,7 @@ class ServerPartEntity extends EquipmentEntity
{
const PK = ServerPartModel::PK;
const TITLE = ServerPartModel::TITLE;
const DEFAULT_BILLING = PAYMENT['BILLING']['MONTH'];
const DEFAULT_STATUS = null;
public function setPartEntity(PartEntity $entity): void
{

View File

@ -223,6 +223,7 @@ class CommonHelper
// $formOptions는 필터 옵션 배열로, key는 필터 엔티티의 PK, value는 필터 엔티티 객체
$html = sprintf("<select name=\"%s\" %s>", $field, $extra);
$html .= "<option value=\"\">" . lang("{$viewDatas['class_path']}.label.{$field}") . " 선택" . "</option>";
// echo "{$field}->{$value}";
foreach ($viewDatas['control']['field_optons'][$field] as $key => $entity) {
$isSelected = $key == $value ? ' selected' : '';
$isDisabled = $entity->getStatus() === $entity::DEFAULT_STATUS ? '' : ' disabled';
@ -280,6 +281,7 @@ class CommonHelper
case 'old_clientinfo_uid':
case 'clientinfo_uid':
case 'serviceinfo_uid':
case 'switchinfo_uid':
case 'serverinfo_uid':
$extras['class'] = array_key_exists('class', $extras) ? $extras['class'] . ' select-field' : 'select-field';
$form = $this->form_dropdown_custom($field, $value, $viewDatas, $extras);

View File

@ -2,7 +2,6 @@
namespace App\Helpers\Customer;
use App\Entities\Equipment\CodeEntity;
use App\Models\Customer\ServiceModel;
class ServiceHelper extends CustomerHelper
@ -20,7 +19,8 @@ class ServiceHelper extends CustomerHelper
case "SERVER":
case "CPU":
case "RAM":
case "STORAGE":
case "DISK":
case "OS":
case "SOFTWARE":
case "DEFENCE":
case "DOMAIN":
@ -46,9 +46,9 @@ class ServiceHelper extends CustomerHelper
public function getFieldForm(string $field, mixed $value, array $viewDatas, array $extras = []): string
{
switch ($field) {
case 'switchinfo_uid':
case 'serverinfo_uid':
$extras['class'] = array_key_exists('class', $extras) ? $extras['class'] . ' select-field' : 'select-field';
$form = $this->form_dropdown_custom($field, $value, $viewDatas, $extras);
$form = $this->form_dropdown_custom($field, array_key_exists('entity', $viewDatas) ? $viewDatas['entity']->getServerEntity()->getPK() : $value, $viewDatas, $extras);
break;
default:
$form = parent::getFieldForm($field, $value, $viewDatas, $extras);
@ -59,21 +59,20 @@ class ServiceHelper extends CustomerHelper
public function getFieldView(string $field, mixed $value, array $viewDatas, array $extras = []): string|null
{
switch ($field) {
case 'clientinfo_uid':
case 'ownerinfo_uid':
$temp = parent::getFieldForm($field, $value, $viewDatas, $extras);
$value = $temp . form_label(
ICONS['HISTORY'],
'client_history',
[
"data-src" => "/admin/customer/clienthistory?clientinfo_uid={$value}",
"data-bs-toggle" => "modal",
"data-bs-target" => "#index_action_form",
"class" => "btn btn-outline btn-primary btn-circle",
"target" => "_self"
]
);
break;
// case 'clientinfo_uid':
// $temp = parent::getFieldForm($field, $value, $viewDatas, $extras);
// $value = $temp . form_label(
// ICONS['HISTORY'],
// 'client_history',
// [
// "data-src" => "/admin/customer/clienthistory?clientinfo_uid={$value}",
// "data-bs-toggle" => "modal",
// "data-bs-target" => "#index_action_form",
// "class" => "btn btn-outline btn-primary btn-circle",
// "target" => "_self"
// ]
// );
// break;
case "LINE":
case "IP":
case "SERVER":

View File

@ -0,0 +1,159 @@
<?php
namespace App\Helpers\Equipment;
use App\Models\Equipment\ServerPartModel;
class ServerPartHelper extends EquipmentHelper
{
public function __construct()
{
parent::__construct();
$this->setTitleField(field: ServerPartModel::TITLE);
}
private function getServerPartForm(string $field, mixed $value, array $viewDatas, array $extras, string $partType): string
{
//Type별로 부품연결정보가 있는지 확인
$serverpartEntity = null;
if (array_key_exists('entity', $viewDatas)) {
$serverpartEntity = $viewDatas['entity']->getServerPartEntity($partType);
}
$form = "";
//수정시 Type별 사용할 hidden serverinfopartinfo_uid
if ($serverpartEntity !== null) {
$form .= form_hidden("serverinfopartinfo_uid_{$partType}", $serverpartEntity->getPK());
}
//기존 입력화면에서 return 된것인지?
if ($value === null && $serverpartEntity !== null) {
$value = $serverpartEntity->getPartInfoUID();
}
$form .= $this->form_dropdown_custom($field, $value, $viewDatas, $extras);
return $form;
}
public function getFieldForm(string $field, mixed $value, array $viewDatas, array $extras = []): string
{
switch ($field) {
case 'code':
// $extras['readonly'] = in_array($viewDatas['control']['action'], ['modify_form']) ? ' readonly' : '';
$form = parent::getFieldForm($field, $value, $viewDatas, $extras);
break;
case 'manufactur_at':
case 'format_at':
$extras['class'] = array_key_exists('class', $extras) ? $extras['class'] . ' calender' : 'calender';
$form = form_input($field, $value ?? "", $extras);
break;
case 'partinfo_uid_CPU':
$form = $this->getServerPartForm($field, $value, $viewDatas, $extras, 'CPU');
break;
case 'serverinfopartinfo_uid_CPU_cnt':
$form = form_dropdown($field, $viewDatas['serverinfopartinfo_cnt_options'], $value, $extras) . "";
break;
case 'partinfo_uid_RAM':
$form = $this->getServerPartForm($field, $value, $viewDatas, $extras, 'RAM',);
break;
case 'serverinfopartinfo_uid_RAM_cnt':
$form = form_dropdown($field, $viewDatas['serverinfopartinfo_cnt_options'], $value, $extras) . "";
break;
case 'partinfo_uid_DISK':
$form = $this->getServerPartForm($field, $value, $viewDatas, $extras, 'DISK');
break;
case 'serverinfopartinfo_uid_DISK_cnt':
$form = form_dropdown($field, $viewDatas['serverinfopartinfo_cnt_options'], $value, $extras) . "";
break;
case 'serverinfopartinfo_uid_DISK_extra':
$form = $this->form_dropdown_custom($field, $value, $viewDatas, $extras);
break;
case 'partinfo_uid_OS':
$form = $this->getServerPartForm($field, $value, $viewDatas, $extras, 'OS');
break;
case 'serverinfopartinfo_uid_OS_cnt':
$form = form_dropdown($field, $viewDatas['serverinfopartinfo_cnt_options'], $value, $extras) . "";
break;
case 'partinfo_uid_DB':
$form = $this->getServerPartForm($field, $value, $viewDatas, $extras, 'DB');
break;
case 'serverinfopartinfo_uid_DB_cnt':
$form = form_dropdown($field, $viewDatas['serverinfopartinfo_cnt_options'], $value, $extras) . "";
break;
case 'partinfo_uid_SOFTWARE':
$form = $this->getServerPartForm($field, $value, $viewDatas, $extras, 'SOFTWARE');
break;
case 'serverinfopartinfo_uid_SOFTWARE_cnt':
$form = form_dropdown($field, $viewDatas['serverinfopartinfo_cnt_options'], $value, $extras) . "";
break;
case 'ipinfo_uid':
case 'csinfo_uid':
$extras['class'] = array_key_exists('class', $extras) ? $extras['class'] . ' select-field' : 'select-field';
$form = $this->form_dropdown_custom($field, $value, $viewDatas, $extras);
break;
default:
$form = parent::getFieldForm($field, $value, $viewDatas, $extras);
break;
}
return $form;
}
private function getServerPartView(string $field, mixed $value, array $viewDatas, array $extras, string $partType): string
{
$serverPartEntity = $viewDatas['entity']->getServerPartEntity($partType);
if ($serverPartEntity !== null) {
$value .= sprintf(
"<div>%s%s %s</div>",
$serverPartEntity->getTitle(),
$serverPartEntity->getCnt() >= 1 ? "*" . $serverPartEntity->getCnt() . "" : "",
$serverPartEntity->getExtra() ?? ""
);
}
return $value;
}
public function getFieldView(string $field, mixed $value, array $viewDatas, array $extras = []): string|null
{
switch ($field) {
case 'manufactur_at':
case 'format_at':
$value = $value ? date("Y-m-d", strtotime($value)) : "";
break;
case 'CPU':
case 'RAM':
case 'DISK':
case 'OS':
case 'DB':
case 'SOFTWARE':
$value = $this->getServerPartView($field, $value, $viewDatas, $extras, $field);
break;
case 'ipinfo_uid':
$value = "";
foreach ($viewDatas['entity']->getIPEntities() as $ipEntity) {
$value .= sprintf("<div>%s%s %s</div>", $ipEntity->getTitle(), $ipEntity->getAmount());
}
break;
case 'csinfo_uid':
$value = "";
foreach ($viewDatas['entity']->getCSEntities() as $csEntity) {
$value .= sprintf("<div>%s%s %s</div>", $csEntity->getTitle(), $csEntity->getAmount());
}
break;
default:
$value = parent::getFieldView($field, $value, $viewDatas, $extras);
break;
}
if (is_array($value)) {
echo __METHOD__ . "에서 오류: {$field}의 값이 Array형태입니다";
exit;
}
return $value;
}
public function getListFilter(string $field, mixed $value, array $viewDatas, array $extras = []): string
{
switch ($field) {
case 'csinfo_uid':
case 'ipinfo_uid':
$extras['class'] = array_key_exists('class', $extras) ? $extras['class'] . ' select-field' : 'select-field';
$form = parent::getListFilter($field, $value, $viewDatas, $extras);
break;
default:
$form = parent::getListFilter($field, $value, $viewDatas, $extras);
break;
}
return $form;
}
}

View File

@ -4,6 +4,7 @@ return [
'label' => [
'user_uid' => "관리자",
'clientinfo_uid' => "고객",
'switchinfo_uid' => "스위치포트",
'serverinfo_uid' => "서버",
'site' => "사이트",
'code' => "코드",

View File

@ -0,0 +1,37 @@
<?php
return [
'title' => "서버장비정보",
'label' => [
'partinfo_uid' => "부품정보",
'clientinfo_uid' => "고객번호",
'serviceinfo_uid' => "서비스번호",
'serverinfo_uid' => "서버번호",
'type' => "항목형식",
'billing' => "결제방식",
'amount' => "제공가",
'cnt' => "갯수",
'extra' => "추가정보",
'updated_at' => "수정일",
'created_at' => "작성일",
'deleted_at' => "삭제일",
],
"BILLING" => [
"month" => "매월",
"onetime" => "일회성",
],
"TYPE" => [
"CPU" => "CPU",
"RAM" => "메모리",
"DISK" => "저장장치",
"OS" => "운영체제",
"DB" => "데이터베이스",
"SOFTWARE" => "소프트웨어",
],
"EXTRA" => [
'RAID0' => "RAID0",
'RAID1' => "RAID1",
'RAID5' => "RAID5",
'RAID6' => "RAID6",
'RAID10' => "RAID10",
],
];

View File

@ -14,18 +14,38 @@ class PartCodeProcess implements MigrationProcessInterface
}
public function process(array $row, int $cnt): void
{
try {
if (count($row) < 2) {
echo "{$cnt} {$row[0]}:{$row[1]}-> SKIP PARTCODE\n";
return;
throw new \Exception("{$cnt} {$row[0]}:{$row[1]} -> SKIP PARTCODE\n");
}
$temps = [];
$temps['type'] = trim($row[0]);
$temps['title'] = trim($row[1]);
$temps['price'] = trim($row[2]);
$temps['status'] = PartEntity::DEFAULT_STATUS; // Assuming SwitchEntity has a STATUS_DEFAULT constant
if (!$this->db->table('partinfo')->insert($temps)) {
$temps['status'] = PartEntity::DEFAULT_STATUS;
// INSERT
$result = $this->db->table('partinfo')->insert($temps);
if (!$result) {
throw new \Exception($this->db->error()['message']);
}
echo "{$cnt} -> {$temps['title']} PARTCODE 완료.\n";
// 방금 insert된 uid 가져오기
$insertId = $this->db->insertID();
// code 값 생성 (예: CPU123)
$code = $row[0] . $insertId;
// code 업데이트
$this->db->table('partinfo')
->where('uid', $insertId)
->update(['code' => $code]);
echo "{$cnt} -> {$temps['title']} ({$code}) PARTCODE 완료.\n";
} catch (\Exception $e) {
echo $e->getMessage();
}
}
}

View File

@ -136,12 +136,7 @@ abstract class CommonModel extends Model
case "content":
case "discription":
case "history":
// textarea 계열은 XSS 방지
if ($value === '' || $value === null) {
//값이 없거나 빈데이터면 아무것도 하지 않음
} elseif ($value === ' ') {
$value = ''; // 공백 하나를 넣어서 의도적인 빈칸 저장
} else {
if ($value !== '' && $value !== null) {
$value = htmlentities($value, ENT_QUOTES, 'UTF-8');
}
break;
@ -150,8 +145,6 @@ abstract class CommonModel extends Model
}
public function create(array $formDatas): mixed
{
// LogCollector::debug("입력내용");
// LogCollector::debug(var_export($formDatas, true));
$convertedFormDatas = [];
foreach ($this->allowedFields as $field) {
$value = $this->convertFormDatas(
@ -184,32 +177,22 @@ abstract class CommonModel extends Model
$pkField = $this->getPKField();
$entity->$pkField = $this->getInsertID();
}
$debug = sprintf("debug.%s.%s", str_replace("\\", ".", get_class($this)), __FUNCTION__);
if (env($debug, false)) {
echo var_dump($formDatas);
dd($entity->toArray());
}
return $entity;
}
public function modify(mixed $entity, array $formDatas): mixed
{
// 저장하기 전에 데이터 값 변경이 필요한 Field
// LogCollector::debug("[{$entity->getPK()}/{$entity->getTitle()}] 변경 전 내용");
// LogCollector::debug(var_export($formDatas, true));
// LogCollector::debug(var_export($entity->toArray(), true));
foreach ($this->allowedFields as $field) {
//수정일추가
$formDatas['updated_at'] = date("Y-m-d H:i:s");
foreach (array_keys($formDatas) as $field) {
$value = $this->convertFormDatas(
__FUNCTION__,
$field,
$formDatas
);
if ($value !== null) {
if ($entity->$field !== $value) {
$entity->$field = $value;
}
}
//수정일추가
$entity->setUpdatedAt(date("Y-m-d H:i:s"));
// 최종 저장 시 오류 발생하면
if (!$this->save($entity)) {
$message = sprintf(
@ -220,11 +203,6 @@ abstract class CommonModel extends Model
LogCollector::debug($message);
throw new \Exception($message);
}
$debug = sprintf("debug.%s.%s", str_replace("\\", ".", get_class($this)), __FUNCTION__);
if (env($debug, false)) {
echo var_dump($formDatas);
dd($entity->toArray());
}
return $entity;
}
}

View File

@ -19,9 +19,9 @@ class ServiceModel extends CustomerModel
"clientinfo_uid",
"code",
"site",
"type",
"location",
"billing",
"type",
"billing_at",
"amount",
"start_at",
"end_at",
@ -67,9 +67,9 @@ class ServiceModel extends CustomerModel
return $rule;
}
//입력전 코드처리
protected function create_process(array $formDatas): string|int
public function create(array $formDatas): ServiceEntity
{
$formDatas['code'] = "s" . time();
return parent::create_process($formDatas);
return parent::create($formDatas);
}
}

View File

@ -63,7 +63,6 @@ class ServerModel extends EquipmentModel
}
return $rule;
}
//create용 장비코드 마지막번호 가져오기
final public function getLastestCode(string $format, int $default): string
{

View File

@ -46,6 +46,9 @@ class ServerPartModel extends EquipmentModel
case "type":
$rule = "required|trim|string";
break;
case "extra":
$rule = "permit_empty|string";
break;
default:
$rule = parent::getFormRule($action, $field);
break;

View File

@ -31,6 +31,11 @@ abstract class CommonService
}
return $this->_model;
}
//Entity별로 작업처리시
protected function getEntity_process(mixed $entity): mixed
{
return $entity;
}
final public function getEntity(mixed $where, ?string $message = null): mixed
{
try {
@ -49,6 +54,24 @@ abstract class CommonService
throw new \Exception($message);
}
}
//entities를 가져오는 조건
protected function getEntities_process(mixed $where = null, array $columns = ['*']): array
{
if ($where) {
$this->getModel()->where($where);
}
//출력순서 정의
$this->setOrderBy();
$entities = [];
foreach ($this->getModel()->select(implode(',', $columns))->findAll() as $entity) {
$entities[$entity->getPK()] = $this->getEntity_process($entity);
}
$debug = sprintf("debug.%s.%s", str_replace("\\", ".", get_class($this)), __FUNCTION__);
if (env($debug, false)) {
echo $debug . "=>" . $this->getModel()->getLastQuery() . "<BR>";
}
return $entities;
}
final public function getEntities(mixed $where = null, array $columns = ['*']): array
{
try {
@ -68,29 +91,6 @@ abstract class CommonService
throw new \Exception($message);
}
} //
//Entity별로 작업처리시
protected function getEntity_process(mixed $entity): mixed
{
return $entity;
}
//entities를 가져오는 조건
protected function getEntities_process(mixed $where = null, array $columns = ['*']): array
{
if ($where) {
$this->getModel()->where($where);
}
//출력순서 정의
$this->setOrderBy();
$entities = [];
foreach ($this->getModel()->select(implode(',', $columns))->findAll() as $entity) {
$entities[$entity->getPK()] = $this->getEntity_process($entity);
}
$debug = sprintf("debug.%s.%s", str_replace("\\", ".", get_class($this)), __FUNCTION__);
if (env($debug, false)) {
echo $debug . "=>" . $this->getModel()->getLastQuery() . "<BR>";
}
return $entities;
}
//FieldForm관련용
public function getViewFields(): array
{
@ -161,6 +161,7 @@ abstract class CommonService
public function modify(mixed $entity, array $formDatas): mixed
{
$entity = $this->getModel()->modify($entity, $formDatas);
// dd($entity);
LogCollector::info("[{$entity->getTitle()}]" . MESSAGES["UPDATED"] . ":");
return $entity;
}

View File

@ -7,6 +7,7 @@ use App\Services\CommonService;
use App\Services\Customer\ClientService;
use App\Services\Equipment\ServerService;
use App\Services\Equipment\SwitchService;
use App\Services\UserService;
use CodeIgniter\Model;
@ -15,6 +16,7 @@ abstract class CustomerService extends CommonService
private ?UserService $_userService = null;
private ?ClientService $_clientService = null;
private ?ServiceService $_serviceService = null;
private ?SwitchService $_switchService = null;
private ?ServerService $_serverService = null;
private $_equipmentService = [];
@ -44,6 +46,13 @@ abstract class CustomerService extends CommonService
}
return $this->_serviceService;
}
final public function getSwitchService(): SwitchService
{
if (!$this->_switchService) {
$this->_switchService = new SwitchService();
}
return $this->_switchService;
}
final public function getServerService(): ServerService
{
if (!$this->_serverService) {
@ -66,6 +75,9 @@ abstract class CustomerService extends CommonService
case 'serviceinfo_uid':
$options = $this->getServiceService()->getEntities();
break;
case 'switchinfo_uid':
$options = $this->getSwitchService()->getEntities();
break;
case 'serverinfo_uid':
$options = $this->getServerService()->getEntities();
break;

View File

@ -3,13 +3,14 @@
namespace App\Services\Customer;
use App\Entities\Customer\ServiceEntity;
use App\Entities\Equipment\ServerEntity;
use App\Entities\Equipment\SwitchEntity;
use App\Models\Customer\ServiceModel;
use App\Traits\IPTrait;
class ServiceService extends CustomerService
{
use IPTrait;
private ?string $_searchIP = null;
public function __construct()
{
parent::__construct(new ServiceModel());
@ -18,26 +19,28 @@ class ServiceService extends CustomerService
public function getFormFields(): array
{
return [
"clientinfo_uid",
"type",
"site",
"location",
"type",
"clientinfo_uid",
"switchinfo_uid",
"serverinfo_uid",
"billing_at",
"amount",
"start_at",
"end_at",
"history",
"status",
"history",
];
}
public function getFormFilters(): array
{
return [
'site',
'clientinfo_uid',
'serverinfo_uid',
'type',
'location',
'type',
'clientinfo_uid',
"switchinfo_uid",
'serverinfo_uid',
'status',
];
}
@ -45,45 +48,69 @@ class ServiceService extends CustomerService
{
return [
'site',
'clientinfo_uid',
'type',
'location',
'type',
'clientinfo_uid',
"switchinfo_uid",
'serverinfo_uid',
'billing_at',
'amount',
'start_at',
'end_at',
'updated_at',
'status',
'user_uid'
'user_uid',
'start_at',
'updated_at',
];
}
public function getIndexFilters(): array
{
return [
'site',
'location',
'type',
'clientinfo_uid',
"switchinfo_uid",
'serverinfo_uid',
'user_uid',
'status',
];
}
public function getBatchjobFields(): array
{
return ['site', 'clientinfo_uid', 'status'];
return ['site', 'location', 'type', 'clientinfo_uid', 'status'];
}
//기본 기능부분
//검색용
public function setSearchIp(string $ip): void
public function getFormRule(string $action, string $field): string
{
$this->_searchIP = $ip;
if (is_array($field)) {
throw new \Exception(__FUNCTION__ . "=> field가 array 입니다.\n" . var_export($field, true));
}
public function getSearchIp(): string|null
switch ($field) {
case "serverinfo_uid":
case "switchinfo_uid":
$rule = "required|numeric";
break;;
default:
$rule = parent::getFormRule($action, $field);
break;
}
return $rule;
}
protected function getEntity_process(mixed $entity): ServiceEntity
{
return $this->_searchIP;
//서버정보 정의
$serverEntityy = $this->getServerService()->getEntity(['serviceinfo_uid' => $entity->getPK()]);
if ($serverEntityy) {
$entity->setServerEntity($serverEntityy);
}
// protected function getEntities_process(mixed $where = null,array $columns = ['*']): mixed
// {
// $ip = $this->getSearchIp();
// if ($ip) {
// $sql = "SELECT serviceinfo.* FROM serviceinfo
// LEFT JOIN serviceinfo_items ON serviceinfo.uid = serviceinfo_items.serviceinfo_uid
// WHERE serviceinfo_items.item_type = ?
// AND serviceinfo_items.item_uid IN (SELECT uid FROM ipinfo WHERE ip = ?)";
// return $this->getModel()->query($sql, ['IP', $ip])->getResult(ServiceEntity::class);
// //IP정보 정의
// foreach ($this->getIPService()->getEntities(['serverinfo_uid' => $entity->getPK()]) as $ipEntity) {
// $entity->addIPEntity($ipEntity);
// }
// return parent::getEntities_process($where,$columns);
// //CS정보 정의
// foreach ($this->getCSService()->getEntities(['serverinfo_uid' => $entity->getPK()]) as $csEntity) {
// $entity->addCSEntity($csEntity);
// }
return $entity;
}
//기본 기능부분
//FieldForm관련용
//interval을 기준으로 최근 신규 서비스정보 가져오기
@ -131,21 +158,83 @@ class ServiceService extends CustomerService
) WHERE billing_at = ? AND status = ?";
return $this->getModel()->query($sql, [$billing_at, $status]);
}
//다른장치 설정용
private function disableSetServiceToEquipments(ServiceEntity $entity): ServiceEntity
{
//기존 Server정보와 다른경우 사용가능상태로 변경
$serverEntity = $entity->getServerEntity();
if ($serverEntity !== null) {
$serverEntity = $this->getServerService()->setService(
$entity,
$serverEntity->getPK(),
ServerEntity::STATUS_AVAILABLE
);
$entity->setServerEntity(null);
}
//기존 Switch정보와 다른경우 사용가능상태로 변경
$switchEntity = $entity->getSwitchEntity();
if ($switchEntity !== null) {
$switchEntity = $this->getSwitchService()->setService(
$entity,
$switchEntity->getPK(),
SwitchEntity::STATUS_AVAILABLE
);
$entity->setSwitchEntity(null);
}
return $entity;
}
private function enableServiceToEquipments(ServiceEntity $entity, array $formDatas): ServiceEntity
{
//서버경우 서비스중으로 설정
$serverEntity = $this->getServerService()->setService(
$entity,
$formDatas['serverinfo_uid'],
ServerEntity::STATUS_OCCUPIED
);
$entity->setServerEntity($serverEntity);
//Switch경우 서비스중으로 설정
$serverEntity = $this->getSwitchService()->setService(
$entity,
$formDatas['switchinfo_uid'],
SwitchEntity::STATUS_OCCUPIED
);
$entity->setSwitchEntity($serverEntity);
return $entity;
}
//생성
public function create(array $formDatas): ServiceEntity
{
$entity = parent::create($formDatas);
//서버경우 서비스중으로 설정작업
// $this->getServerService()->setService($entity)ServerEntity::STATUS_OCCUPIED);
return parent::create($formDatas);
if (!array_key_exists('serverinfo_uid', $formDatas)) {
throw new \Exception("서버가 지정되지 않았습니다.");
}
//List 검색용
//검색어조건절처리
public function index_condition_filterWord(string $word): void
if (!array_key_exists('switchinfo_uid', $formDatas)) {
throw new \Exception("스위치정보가 지정되지 않았습니다.");
}
//신규정보 Enable
return $this->enableServiceToEquipments($entity, $formDatas);
}
//수정
public function modify(mixed $entity, array $formDatas): ServiceEntity
{
if ($this->isIPAddressTrait($word, 'ipv4')) {
$this->setSearchIp($word);
} else {
parent::index_condition_filterWord($word);
}
$entity = parent::modify($entity, $formDatas);
if (!array_key_exists('serverinfo_uid', $formDatas)) {
throw new \Exception("서버가 지정되지 않았습니다.");
}
if (!array_key_exists('switchinfo_uid', $formDatas)) {
throw new \Exception("스위치정보가 지정되지 않았습니다.");
}
//기존정보 Disable
$entity = $this->disableSetServiceToEquipments($entity);
//신규정보 Enable
return $this->enableServiceToEquipments($entity, $formDatas);
}
//삭제
public function delete(mixed $entity): ServiceEntity
{
//기존정보 Disable
$entity = $this->disableSetServiceToEquipments($entity);
return parent::delete($entity);
}
}

View File

@ -2,6 +2,7 @@
namespace App\Services\Equipment;
use App\Entities\Equipment\PartEntity;
use App\Models\Equipment\PartModel;
class PartService extends EquipmentService
@ -23,21 +24,35 @@ class PartService extends EquipmentService
public function getFormFilters(): array
{
return [
"type",
'type',
'status',
];
}
public function getIndexFields(): array
{
return [
"type",
"title",
"price",
"status",
];
}
public function getBatchjobFields(): array
{
return ['status'];
return ['type', 'status'];
}
//기본 기능부분
//FieldForm관련용
//List 검색용
//OrderBy 처리
public function setOrderBy(mixed $field = null, mixed $value = null): void
{
$this->getModel()->orderBy('type ASC');
$this->getModel()->orderBy('code ASC');
parent::setOrderBy($field, $value);
}
public function create(array $formDatas): PartEntity
{
$entity = parent::create($formDatas);
return $this->modify($entity, ['code' => $entity->getType() . $entity->getPK()]);
}
}

View File

@ -18,10 +18,10 @@ class ServerPartService extends EquipmentService
public function getFormFields(): array
{
return [
"partinfo_uid",
"serverinfo_uid",
"serviceinfo_uid",
"serverinfo_uid",
"type",
"partinfo_uid",
"billing",
"amount",
"cnt",
@ -31,15 +31,16 @@ class ServerPartService extends EquipmentService
public function getFormFilters(): array
{
return [
"partinfo_uid",
"serverinfo_uid",
"serviceinfo_uid",
"type"
"serverinfo_uid",
"type",
"partinfo_uid",
"billing",
];
}
public function getBatchjobFields(): array
{
return ['partinfo_uid', "serverinfo_uid", "serviceinfo_uid",];
return ['billing', 'type', 'partinfo_uid'];
}
final public function getPartService(): PartService
{

View File

@ -2,6 +2,7 @@
namespace App\Services\Equipment;
use App\Entities\Customer\ServiceEntity;
use App\Entities\Equipment\ServerEntity;
use App\Models\Equipment\ServerModel;
use App\Services\Equipment\EquipmentService;
@ -71,7 +72,7 @@ class ServerService extends EquipmentService
'amount',
'manufactur_at',
"format_at",
'status'
'status',
];
}
public function getIndexFilters(): array
@ -80,9 +81,6 @@ class ServerService extends EquipmentService
'clientinfo_uid',
'serviceinfo_uid',
'type',
"ipinfo_uid",
"csinfo_uid",
'partinfo_uid_SOFTWARE',
'status'
];
}
@ -116,9 +114,9 @@ class ServerService extends EquipmentService
{
//부품연결정보 정의
foreach (SERVER['PARTTYPES'] as $partType) {
$serverPartEnty = $this->getServerPartService()->getEntity(['serverinfo_uid' => $entity->getPK(), 'type' => $partType]);
if ($serverPartEnty) {
$entity->addServerPartEntity($partType, $serverPartEnty);
$serverPartEntity = $this->getServerPartService()->getEntity(['serverinfo_uid' => $entity->getPK(), 'type' => $partType]);
if ($serverPartEntity) {
$entity->addServerPartEntity($partType, $serverPartEntity);
}
}
//IP정보 정의
@ -224,4 +222,23 @@ class ServerService extends EquipmentService
$this->getModel()->orderBy("code ASC,title ASC");
parent::setOrderBy($field, $value);
}
public function setService(ServiceEntity $serviceEntity, mixed $uid, string $status): ServerEntity
{
$entity = $this->getEntity($uid);
if (!$entity) {
throw new \Exception("{$uid}에 대한 서버정보를 찾을수 없습니다.");
}
$formDatas = ['status' => $status];
if ($status === ServerEntity::STATUS_OCCUPIED) {
$formDatas["clientinfo_uid"] = $serviceEntity->getClientInfoUID();
$formDatas["serviceinfo_uid"] = $serviceEntity->getPK();
} elseif ($status === ServerEntity::STATUS_AVAILABLE) {
$formDatas["clientinfo_uid"] = null;
$formDatas["serviceinfo_uid"] = null;
} else {
throw new \Exception(__METHOD__ . "에서 오류발생: {$status}는 지정되지 않은 상태값입니다.");
}
return parent::modify($entity, $formDatas);
}
}

View File

@ -2,6 +2,7 @@
namespace App\Services\Equipment;
use App\Entities\Customer\ServiceEntity;
use App\Entities\Equipment\SwitchEntity;
use App\Models\Equipment\SwitchModel;
use App\Services\Equipment\EquipmentService;
@ -62,4 +63,25 @@ class SwitchService extends EquipmentService
$this->getModel()->orderBy('code', 'ASC');
parent::setOrderBy($field, $value);
}
public function setService(ServiceEntity $serviceEntity, mixed $uid, string $status): SwitchEntity
{
$entity = $this->getEntity($uid);
if (!$entity) {
throw new \Exception("{$uid}에 대한 서버정보를 찾을수 없습니다.");
}
$formDatas = ['status' => $status];
if ($status === SwitchEntity::STATUS_OCCUPIED) {
$formDatas["clientinfo_uid"] = $serviceEntity->getClientInfoUID();
$formDatas["serviceinfo_uid"] = $serviceEntity->getPK();
$formDatas["serverinfo_uid"] = $serviceEntity->getServerEntity()->getPK();
} elseif ($status === SwitchEntity::STATUS_AVAILABLE) {
$formDatas["clientinfo_uid"] = null;
$formDatas["serviceinfo_uid"] = null;
$formDatas["serverinfo_uid"] = null;
} else {
throw new \Exception(__METHOD__ . "에서 오류발생: {$status}는 지정되지 않은 상태값입니다.");
}
return parent::modify($entity, $formDatas);
}
}

View File

@ -62,6 +62,7 @@ class MyLogService extends CommonService
'user_uid' => $user_uid,
'title' => sprintf("%s->%s %s", $class, $method, $title),
'content' => LogCollector::dump(),
'status' => MyLogEntity::DEFAULT_STATUS
];
// dd($formDatas);
LogCollector::clear();

View File

@ -7,8 +7,8 @@
<div class="action_form">
<table class="table table-bordered">
<tr>
<th>서버정보</th>
<th>추가정보</th>
<th>기본 서버정보</th>
<th>기본 추가정보(서버 비용에 포함)</th>
</tr>
<tr>
<td>

View File

@ -0,0 +1,50 @@
<?= $this->extend(LAYOUTS[$viewDatas['layout']]['path']) ?>
<?= $this->section('content') ?>
<?php if ($error = session('error')): echo $viewDatas['helper']->alert($error) ?><?php endif ?>
<div id="container" class="content">
<div class="form_top"><?= $this->include("templates/{$viewDatas['layout']}/form_content_top"); ?></div>
<?= form_open(current_url(), $viewDatas['forms']['attributes'], $viewDatas['forms']['hiddens']) ?>
<div class="action_form">
<table class="table table-bordered">
<tr>
<th>서버정보</th>
<th>추가정보</th>
</tr>
<tr>
<td>
<table class="table table-bordered">
<?php foreach (["code", "type", "title", "price", "amount", "manufactur_at", "format_at", "status",] as $field): ?>
<tr>
<th nowrap class="text-end"><?= $viewDatas['helper']->getFieldLabel($field, lang("{$viewDatas['class_path']}.label.{$field}"), $viewDatas) ?></th>
<td nowrap class="text-start">
<?= $viewDatas['helper']->getFieldView($field, $viewDatas['entity']->$field ?? null, $viewDatas) ?>
<span><?= validation_show_error($field); ?></span>
</td>
</tr>
<?php endforeach; ?>
</table>
</td>
<td>
<table class="table table-bordered">
<?php foreach (SERVER['PARTTYPES'] as $partType): ?>
<tr>
<th nowrap class="text-end"><?= $viewDatas['helper']->getFieldLabel("partinfo_uid_{$partType}", lang("{$viewDatas['class_path']}.label.partinfo_uid_{$partType}"), $viewDatas) ?></th>
<td nowrap class="text-start">
<?= $viewDatas['helper']->getFieldView("partinfo_uid_{$partType}", old("partinfo_uid_{$partType}") ?? ($viewDatas['entity']->getServerPartEntity($partType) ? $viewDatas['entity']->getServerPartEntity($partType)->getPartInfoUID() : ($viewDatas['control']['form_datas']["partinfo_uid_{$partType}"] ?? null)), $viewDatas) ?>
<?= $viewDatas['helper']->getFieldView("serverinfopartinfo_uid_{$partType}_cnt", old("serverinfopartinfo_uid_{$partType}_cnt") ?? ($viewDatas['entity']->getServerPartEntity($partType) ? $viewDatas['entity']->getServerPartEntity($partType)->getCnt() : ($viewDatas['control']['form_datas']["serverinfopartinfo_uid_{$partType}_cnt"] ?? null)), $viewDatas) ?>
<?php if ($partType === "DISK"): ?>
<?= $viewDatas['helper']->getFieldView("serverinfopartinfo_uid_{$partType}_extra", old("serverinfopartinfo_uid_{$partType}_extra") ?? ($viewDatas['entity']->getServerPartEntity($partType) ? $viewDatas['entity']->getServerPartEntity($partType)->getExtra() : ($viewDatas['control']['form_datas']["serverinfopartinfo_uid_{$partType}_extra"] ?? null)), $viewDatas) ?>
<?php endif ?>
</td>
</tr>
<?php endforeach; ?>
</table>
</td>
</tr>
</table>
<div class="text-center"><?= form_submit('', '수정', array("class" => "btn btn-outline btn-primary")); ?></div>
<?= form_close(); ?>
</div>
<div class="form_bottom"><?= $this->include("templates/{$viewDatas['layout']}/form_content_bottom"); ?></div>
</div>
<?= $this->endSection() ?>