Commit 05c0278c by iqbal

"Penambahan import dan csv by iqbal"

1 parent 1d523b8b
kode,nama,pangkat,ruang,tunjangan,status
"VII/A","Eselon VII A",2,"A",4000000,1
"VII/B","Eselon VII B",2,"B",8000000,1
"VIII/A","Eselon VIII A",3,"A",5500000,1
"VIII/B","Eselon VIII B",3,"B",5000000,1
"VIV/A","Eselon VIV A",4,"A",3500000,1
"VIV/B","Eselon VIV B",4,"B",2250000,1
"VV/A","Eselon VV A",5,"A",1500000,1
\ No newline at end of file \ No newline at end of file
urut,kode,nama,ibu_kota,kategori,provinsi_id/res_provinsi.kode,status
01,ID-JT.01,Kabupaten Karanganyar,Karanganyar,kabupaten,ID-JT,0
02,ID-JT.02,Kabupaten Sukoharjo,Sukoharjo,kabupaten,ID-JB,0
03,ID-JT.03,Kota Surakarta,Surakarta,kota,ID-JT,0
\ No newline at end of file \ No newline at end of file
kode,nama,kecamatan_id/res_kecamatan.kode,status,,,,,,,,,,
32.76.01.01,Depok,32.76.01,0,,,,,,,,,,
32.76.01.02,Depok Jaya,32.76.01,0,,,,,,,,,,
32.76.01.03,Mampang,32.76.01,0,,,,,,,,,,
\ No newline at end of file \ No newline at end of file
group_name,description,member_count
"Sritex","Superuser",1
"Djarum","Webservice",2
"Shopee","Pindah Departemen",3
"Grab","Guest",4
\ No newline at end of file \ No newline at end of file
kode,nama,email,idcard,status,created,is_vendor,is_customer
1245678,Muhammad Sasuke, sasuke@gmail.com,[null],1,2024-03-12 13:10:17.833045,1,1
2456789,Uzumaki Firaun, firaun@gmail.com,[null],1,2024-02-10 17:04:17.399242,1,1
4567891,Uzumaki heimdell, heimdell@gmail.com,[null],1,2023-02-10 17:04:17.376627,1,1
\ No newline at end of file \ No newline at end of file
user_id/public.users.id,desa_id/public.res_desa.id
1,70
2,66
...@@ -42,14 +42,16 @@ group-add,/group/add,Tambah group, ...@@ -42,14 +42,16 @@ group-add,/group/add,Tambah group,
group-edit,/group/{id}/edit,Edit group, group-edit,/group/{id}/edit,Edit group,
group-view,/group/{id}/view,View group, group-view,/group/{id}/view,View group,
group-delete,/group/{id}/delete,Hapus group, group-delete,/group/{id}/delete,Hapus group,
group-upload,/group/upload,Upload group,
group-act,/group/{act}/act,Act Groups, group-act,/group/{act}/act,Act Groups,
group-rpt,/group/{rpt}/rpt,Groups Report, group-rpt,/group/{rpt}/rpt,Groups Report,
user-group,/user/group,Daftar User groups, user-group,/user/group,Daftar User groups,1,0,
user-group-add,/user/group/add,Tambah user groups, user-group-add,/user/group/add,Tambah user groups,1,0,
user-group-edit,/user/group/{id}/edit,Edit user groups, user-group-edit,/user/group/{id}/edit,Edit user groups,1,0,
user-group-view,/user/group/{id}/view,View user groups, user-group-view,/user/group/{id}/view,View user groups,1,0,
user-group-delete,/user/group/{id}/delete,Hapus user groups, user-group-delete,/user/group/{id}/delete,Hapus user groups,1,0,
user-group-act,/user/group/{act}/act,Act User-Groups, user-group-upload,/user/group/{id}/upload,Upload user groups,1,0,
user-group-act,/user/group/{act}/act,Act User-Groups,1,0,
routes,/routes,Routes, routes,/routes,Routes,
routes-add,/routes/add,Tambah route, routes-add,/routes/add,Tambah route,
routes-edit,/routes/{id}/edit,Edit route, routes-edit,/routes/{id}/edit,Edit route,
...@@ -60,6 +62,7 @@ group-routes,/group/routes,Group Permission, ...@@ -60,6 +62,7 @@ group-routes,/group/routes,Group Permission,
group-routes-add,/group/routes/add,Tambah group permission, group-routes-add,/group/routes/add,Tambah group permission,
group-routes-edit,/group/routes/{group_id}/{route_id}/edit,Edit group permission, group-routes-edit,/group/routes/{group_id}/{route_id}/edit,Edit group permission,
group-routes-delete,/group/routes/{group_id}/{route_id}/delete,Hapus group permission, group-routes-delete,/group/routes/{group_id}/{route_id}/delete,Hapus group permission,
group-routes-upload,/group/routes/{group_id}/{route_id}/upload,Upload group permission,
group-routes-act,/group/routes/{act}/act,Act grouppermission, group-routes-act,/group/routes/{act}/act,Act grouppermission,
parameter,/parameter,Parameter, parameter,/parameter,Parameter,
parameter-add,/parameter/add,Tambah paramater, parameter-add,/parameter/add,Tambah paramater,
...@@ -78,6 +81,7 @@ partner-rpt,/partner/{rpt}/rpt,Partner Report, ...@@ -78,6 +81,7 @@ partner-rpt,/partner/{rpt}/rpt,Partner Report,
partner-edit,/partner/{id}/edit,Partner Edt, partner-edit,/partner/{id}/edit,Partner Edt,
partner-view,/partner/{id}/view,Partner view, partner-view,/partner/{id}/view,Partner view,
partner-delete,/partner/{id}/delete,Partner Del, partner-delete,/partner/{id}/delete,Partner Del,
partner-upload,/partner/upload,Partner Upload,
departemen,/departemen,Organisasi, departemen,/departemen,Organisasi,
departemen-act,/departemen/{act}/act,Organisasi Act, departemen-act,/departemen/{act}/act,Organisasi Act,
departemen-add,/departemen/add,Organisasi Tambah, departemen-add,/departemen/add,Organisasi Tambah,
...@@ -109,6 +113,7 @@ eselon-edit,/eselon/{id}/edit,Edit Eselon, ...@@ -109,6 +113,7 @@ eselon-edit,/eselon/{id}/edit,Edit Eselon,
eselon-view,/eselon/{id}/view,View Eselon, eselon-view,/eselon/{id}/view,View Eselon,
eselon-delete,/eselon/{id}/delete,Hapus Eselon, eselon-delete,/eselon/{id}/delete,Hapus Eselon,
eselon-act,/eselon/{act}/act,Act Eselon, eselon-act,/eselon/{act}/act,Act Eselon,
eselon-upload,/eselon/upload,Upload Eselon,
jabatan,/jabatan,Daftar Jabatan, jabatan,/jabatan,Daftar Jabatan,
jabatan-add,/jabatan/add,Tambah Jabatan, jabatan-add,/jabatan/add,Tambah Jabatan,
jabatan-edit,/jabatan/{id}/edit,Edit Jabatan, jabatan-edit,/jabatan/{id}/edit,Edit Jabatan,
......
...@@ -2,7 +2,7 @@ import logging ...@@ -2,7 +2,7 @@ import logging
from datetime import timedelta from datetime import timedelta
import colander import colander
from deform import ( from deform import (
Form, ValidationFailure, widget, Button, FileData) Form, ValidationFailure, widget, FileData)
from pyramid.httpexceptions import ( from pyramid.httpexceptions import (
HTTPFound, HTTPForbidden, HTTPNotFound, HTTPInternalServerError, HTTPFound, HTTPForbidden, HTTPNotFound, HTTPInternalServerError,
HTTPSeeOther) HTTPSeeOther)
...@@ -10,7 +10,7 @@ from pyramid.i18n import TranslationStringFactory ...@@ -10,7 +10,7 @@ from pyramid.i18n import TranslationStringFactory
from pyramid.interfaces import IRoutesMapper from pyramid.interfaces import IRoutesMapper
from pyramid.renderers import render_to_response from pyramid.renderers import render_to_response
from pyramid.view import view_config from pyramid.view import view_config
from deform.form import Button
from opensipkd.base import get_params, get_urls from opensipkd.base import get_params, get_urls
from opensipkd.models import ( from opensipkd.models import (
DBSession, UserService, ) DBSession, UserService, )
...@@ -22,6 +22,8 @@ log = logging.getLogger(__name__) ...@@ -22,6 +22,8 @@ log = logging.getLogger(__name__)
from datatables import ColumnDT from datatables import ColumnDT
# , DataTables, get_urls) # , DataTables, get_urls)
btn_upload = Button('upload', title=_('import'), css_class="btn-info")
def no_action(): def no_action():
test = ColumnDT test = ColumnDT
......
...@@ -2,7 +2,7 @@ import colander ...@@ -2,7 +2,7 @@ import colander
from deform import (widget, ) from deform import (widget, )
from pyramid.i18n import TranslationStringFactory from pyramid.i18n import TranslationStringFactory
from pyramid.view import (view_config, ) from pyramid.view import (view_config, )
from . import BaseView, btn_upload
from . import widget_os from . import widget_os
from .provinsi import provinsi_widget from .provinsi import provinsi_widget
from opensipkd.models import DBSession, ResDati2, kategori_dati2, ResProvinsi from opensipkd.models import DBSession, ResDati2, kategori_dati2, ResProvinsi
...@@ -69,6 +69,7 @@ class ViewDati2(BaseView): ...@@ -69,6 +69,7 @@ class ViewDati2(BaseView):
self.edit_schema = EditSchema self.edit_schema = EditSchema
self.table = ResDati2 self.table = ResDati2
self.list_schema = ListSchema self.list_schema = ListSchema
self.list_buttons = self.list_buttons + (btn_upload,)
def form_validator(self, form, value): def form_validator(self, form, value):
def err_kode(): def err_kode():
...@@ -151,4 +152,4 @@ class ViewDati2(BaseView): ...@@ -151,4 +152,4 @@ class ViewDati2(BaseView):
@view_config(route_name='dati2-upload', @view_config(route_name='dati2-upload',
renderer='templates/form.pt', permission='wilayah') renderer='templates/form.pt', permission='wilayah')
def view_upload(self): def view_upload(self):
return super(ViewDati2, self).view_upload(exts=(".csv",)) return super(ViewDati2,self).view_upload(exts=('.csv', ".tsv"))
\ No newline at end of file \ No newline at end of file
import colander import colander
from deform import (widget, ) from deform import (widget, )
from opensipkd.models import DBSession, ResDesa, kategori_desa, ResKecamatan, ResProvinsi, ResDati2 from opensipkd.models import DBSession, ResDesa, kategori_desa, ResKecamatan, ResProvinsi, ResDati2
from opensipkd.tools.buttons import btn_upload, btn_close, btn_add from . import BaseView, btn_upload
from opensipkd.tools.buttons import btn_close, btn_add
from pyramid.i18n import TranslationStringFactory from pyramid.i18n import TranslationStringFactory
from pyramid.view import (view_config, ) from pyramid.view import (view_config, )
...@@ -15,6 +16,14 @@ _ = TranslationStringFactory("opensipkd") ...@@ -15,6 +16,14 @@ _ = TranslationStringFactory("opensipkd")
SESS_ADD_FAILED = 'Tambah desa gagal' SESS_ADD_FAILED = 'Tambah desa gagal'
SESS_EDIT_FAILED = 'Edit desa gagal' SESS_EDIT_FAILED = 'Edit desa gagal'
def get_desa_list():
# r = [("", "--Pilih Desa--")]
r = []
q = DBSession.query(ResDesa).order_by(ResDesa.nama)
for row in q:
g = (str(row.id), (f"{row.kode}/ {row.nama}"))
r.append(g)
return r
@colander.deferred @colander.deferred
def desa_widget(node, kw): def desa_widget(node, kw):
...@@ -178,8 +187,8 @@ class ViewDesa(BaseView): ...@@ -178,8 +187,8 @@ class ViewDesa(BaseView):
renderer='templates/form.pt', permission='wilayah') renderer='templates/form.pt', permission='wilayah')
def view_delete(self): def view_delete(self):
return super(ViewDesa, self).view_delete() return super(ViewDesa, self).view_delete()
@view_config(route_name='desa-upload', @view_config(route_name='desa-upload',
renderer='templates/form.pt', permission='wilayah') renderer='templates/form.pt', permission='wilayah')
def view_upload(self): def view_upload(self):
return super(ViewDesa, self).view_upload(exts=('.csv', ".tsv")) return super().view_upload(exts=('.csv', ".tsv"))
...@@ -11,6 +11,7 @@ from opensipkd.models import ( ...@@ -11,6 +11,7 @@ from opensipkd.models import (
Eselon Eselon
) )
from ..views import BaseView from ..views import BaseView
from . import BaseView, btn_upload
SESS_ADD_FAILED = 'Tambah eselon gagal' SESS_ADD_FAILED = 'Tambah eselon gagal'
SESS_EDIT_FAILED = 'Edit eselon gagal' SESS_EDIT_FAILED = 'Edit eselon gagal'
...@@ -66,11 +67,18 @@ class Views(BaseView): ...@@ -66,11 +67,18 @@ class Views(BaseView):
self.edit_schema = EditSchema self.edit_schema = EditSchema
self.table = Eselon self.table = Eselon
self.list_schema = ListSchema self.list_schema = ListSchema
self.list_buttons = self.list_buttons + (btn_upload,)
@view_config(route_name='eselon', renderer='templates/table.pt', @view_config(route_name='eselon', renderer='templates/table.pt',
permission='eselon') permission='eselon')
def view_list(self): def view_list(self):
return super(Views, self).view_list() return super(Views, self).view_list()
@view_config(route_name='eselon-upload',
renderer='templates/form.pt', permission='user-upload')
def view_upload(self):
self.upload_keys = ["kode"]
return super().view_upload(exts=('.csv', ".tsv"))
@view_config(route_name='eselon-act', renderer='json', @view_config(route_name='eselon-act', renderer='json',
permission='read') permission='read')
......
...@@ -2,7 +2,7 @@ import colander ...@@ -2,7 +2,7 @@ import colander
from deform import widget from deform import widget
from pyramid.i18n import TranslationStringFactory from pyramid.i18n import TranslationStringFactory
from pyramid.view import view_config from pyramid.view import view_config
from . import BaseView, btn_upload
from . import BaseView from . import BaseView
from opensipkd.models import ( from opensipkd.models import (
DBSession, DBSession,
...@@ -58,6 +58,7 @@ class Views(BaseView): ...@@ -58,6 +58,7 @@ class Views(BaseView):
self.table = Group self.table = Group
self.add_schema = AddSchema self.add_schema = AddSchema
self.edit_schema = EditSchema self.edit_schema = EditSchema
self.list_buttons = self.list_buttons + (btn_upload,)
def get_bindings(self, row=None): def get_bindings(self, row=None):
return dict(group=row, return dict(group=row,
...@@ -132,7 +133,13 @@ class Views(BaseView): ...@@ -132,7 +133,13 @@ class Views(BaseView):
permission='user-view') permission='user-view')
def view_view(self): def view_view(self):
return super(Views, self).view_view() return super(Views, self).view_view()
@view_config(route_name='group-upload',
renderer='templates/form.pt', permission='user-upload')
def view_upload(self):
self.upload_keys = ["group_name"]
return super().view_upload(exts=('.csv', ".tsv"))
@view_config( @view_config(
route_name='group-edit', renderer='templates/form.pt', route_name='group-edit', renderer='templates/form.pt',
permission='user-edit') permission='user-edit')
......
...@@ -13,7 +13,7 @@ from pyramid.i18n import TranslationStringFactory ...@@ -13,7 +13,7 @@ from pyramid.i18n import TranslationStringFactory
from pyramid.view import ( from pyramid.view import (
view_config, view_config,
) )
from . import BaseView, btn_upload
from .company import company_widget from .company import company_widget
from .partner_base import PartnerSchema from .partner_base import PartnerSchema
# from .. import partner_idcard_url # from .. import partner_idcard_url
...@@ -106,6 +106,7 @@ class ViewPartner(BaseView): ...@@ -106,6 +106,7 @@ class ViewPartner(BaseView):
self.table = Partner self.table = Partner
self.list_schema = ListSchema self.list_schema = ListSchema
self.save_state = True self.save_state = True
self.list_buttons = self.list_buttons + (btn_upload,)
######## ########
# List # # List #
...@@ -213,6 +214,12 @@ class ViewPartner(BaseView): ...@@ -213,6 +214,12 @@ class ViewPartner(BaseView):
permission='user-edit') permission='user-edit')
def view_view(self): def view_view(self):
return super().view_view() return super().view_view()
@view_config(route_name='partner-upload',
renderer='templates/upload.pt', permission='user-upload')
def view_upload(self):
self.upload_keys = ["kode"]
return super(ViewPartner,self).view_upload(exts=('.csv', ".tsv"))
@view_config(route_name='partner-delete', renderer='templates/form.pt', @view_config(route_name='partner-delete', renderer='templates/form.pt',
permission='user-edit') permission='user-edit')
......
import colander import colander
import logging
from deform import widget from deform import widget
from pyramid.view import view_config from pyramid.view import view_config
from . import BaseView, btn_upload
from ...models import DBSession,ResDesa, User, UserArea
from .desa import desa_widget, get_desa_list
from pyramid.i18n import TranslationStringFactory
from . import BaseView _ = TranslationStringFactory('myapp')
from ...models import ResDesa, User, UserArea log = logging.getLogger(__name__)
class ListSchema(colander.Schema): class ListSchema(colander.Schema):
id = colander.SchemaNode( id = colander.SchemaNode(
...@@ -23,17 +27,21 @@ class ListSchema(colander.Schema): ...@@ -23,17 +27,21 @@ class ListSchema(colander.Schema):
colander.String(), colander.String(),
field=ResDesa.nama) field=ResDesa.nama)
@colander.deferred
def desa_checkbox_widget(node, kw):
values = kw.get('desa_list', [])
return widget.CheckboxChoiceWidget(values=values)
class AddSchema(colander.Schema): class AddSchema(colander.Schema):
user_id = colander.SchemaNode( user_id = colander.SchemaNode(
colander.Integer(), colander.Integer(),
widget=widget.RadioChoiceWidget(values=User.get_list()), widget=widget.SelectWidget(values=User.get_list()),
oid="user_id", oid="user_id",
title="User", title="User",
) )
desa_id = colander.SchemaNode( desa_id = colander.SchemaNode(
colander.Integer(), colander.Set(),
widget=widget.SelectWidget(values=ResDesa.get_list()), widget=desa_checkbox_widget,
oid="desa_id", oid="desa_id",
title="Kelurahan/Desa", ) title="Kelurahan/Desa", )
...@@ -52,10 +60,11 @@ class Views(BaseView): ...@@ -52,10 +60,11 @@ class Views(BaseView):
self.edit_schema = EditSchema self.edit_schema = EditSchema
self.list_route = 'user-area' self.list_route = 'user-area'
self.table = UserArea self.table = UserArea
self.list_buttons = self.list_buttons + (btn_upload,)
def list_join(self, query, **kwargs): def list_join(self, query, **kwargs):
return query.outerjoin(ResDesa, ResDesa.id == self.table.desa_id) \ return query.outerjoin(ResDesa, ResDesa.id == self.table.desa_id) \
.outerjoin(User, User.id == self.table.user_id) .outerjoin(User, User.id == self.table.user_id) \
@view_config(route_name='user-area', renderer='templates/table.pt', @view_config(route_name='user-area', renderer='templates/table.pt',
permission='user-view') permission='user-view')
...@@ -66,7 +75,11 @@ class Views(BaseView): ...@@ -66,7 +75,11 @@ class Views(BaseView):
permission='user-view') permission='user-view')
def view_act(self): def view_act(self):
return super().view_act() return super().view_act()
def get_bindings(self, row=None):
return {
"desa_list": get_desa_list()
}
@view_config(route_name='user-area-add', renderer='templates/form.pt', @view_config(route_name='user-area-add', renderer='templates/form.pt',
permission='user-edit') permission='user-edit')
def view_add(self): def view_add(self):
...@@ -81,8 +94,77 @@ class Views(BaseView): ...@@ -81,8 +94,77 @@ class Views(BaseView):
permission='user-edit') permission='user-edit')
def view_delete(self): def view_delete(self):
return super().view_delete() return super().view_delete()
@view_config(route_name='user-area-upload',
renderer='templates/upload.pt', permission='user-upload')
def view_upload(self):
self.upload_keys = ["user_id"]
return super(Views,self).view_upload(exts=('.csv', ".tsv"))
@view_config(route_name='user-area-edit', renderer='templates/form.pt', @view_config(route_name='user-area-edit', renderer='templates/form.pt',
permission='user-edit') permission='user-edit')
def view_edit(self): def view_edit(self):
return super().view_edit() return super().view_edit()
def save_request(self, values, row=None):
# Ambil user_id dari values
user_id = values.get("user_id")
if not user_id:
return None # Tidak ada user_id, kembalikan None atau tangani sesuai kebutuhan
# Jika ada departemen_id dalam values
if "desa_id" in values:
# Ambil departemen yang sudah ada untuk user ini
existing_desa = self.get_existing_desa(user_id)
# Konversi departemen_id dari set ke set of strings, filter None
selected_desa = set(
str(desa_id) for desa_id in values["desa_id"]
if desa_id is not None and str(desa_id) != "None"
)
# Departemen yang tidak dipilih lagi (akan dihapus)
unused_desa = existing_desa - selected_desa
# Hapus departemen yang tidak dipilih lagi, pastikan hanya integer yang valid
if unused_desa:
valid_unused = [int(d) for d in unused_desa if d.isdigit()]
if valid_unused:
DBSession.query(UserArea).filter_by(user_id=user_id) \
.filter(UserArea.desa_id.in_(valid_unused)) \
.delete(synchronize_session=False)
# Departemen baru yang dipilih (akan ditambahkan)
new_desa = selected_desa - existing_desa
log.debug(f"get_values new_desa: {new_desa}")
#sys.exit("Age less than 18")
# Tambahkan departemen baru, periksa duplikat sebelum insert
for desa_id in new_desa:
if desa_id.isdigit(): # Pastikan hanya angka yang diproses
# Cek apakah kombinasi user_id dan departemen_id sudah ada
exists = DBSession.query(UserArea).filter_by(
user_id=user_id,
desa_id=int(desa_id)
).first()
if not exists: # Hanya tambahkan jika belum ada
new_row = UserArea(
user_id=user_id,
desa_id=int(desa_id) # Konversi ke integer
)
DBSession.add(new_row)
# Commit semua perubahan
DBSession.flush()
return row # Kembalikan row jika ada, atau None jika tidak digunakan
def get_existing_desa(self, user_id):
q = DBSession.query(UserArea).filter_by(user_id=user_id)
r = []
for ug in q:
r.append(str(ug.desa_id))
return set(r)
def get_values(self, row, istime=False):
d = super(Views, self).get_values(row, istime)
d["desa_id"] = self.get_existing_desa(row.user_id)
return d
Markdown is supported
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!