Rapikan tampilan nilai, ganti NPM->NIM, fitur ganti password, kunci RPS view-only
- Tampilan "Isi Per Komponen Penilaian" diganti dari tombol bertumpuk teks jadi tabel (Komponen/Sub-CPMK/Bobot/Status/Aksi) dengan status berupa stempel, lebih mudah dipindai. - Filter pencarian MK (ketik kode/nama) di kotak penugasan dosen /admin. - Istilah NPM diseragamkan jadi NIM di seluruh aplikasi (label, header, template Excel, dokumen portofolio), termasuk migrasi kolom database mahasiswa.npm -> nim yang aman (ALTER TABLE RENAME COLUMN, otomatis saat startup, tanpa kehilangan data; parser Excel tetap terima file lama berheader NPM). - Fitur ganti password mandiri (/akun): verifikasi password lama, sesi lain otomatis keluar setelah berhasil, sesi yang dipakai tetap aktif. - RPS: dosen RPS+MK kini bisa menyesuaikan redaksi kalimat Sub-CPMK (bagian D) untuk MK yang diampu -- kode & kaitan CPMK/CPL tetap dari kurikulum, hanya teksnya yang bisa disesuaikan. Penyesuaian otomatis konsisten di dropdown mingguan (F), checklist komponen (G), serta unduhan RPS & portofolio, tanpa menyentuh data kurikulum induk atau halaman nilai/ dashboard prodi. - Form RPS dibungkus <fieldset disabled> untuk dosen tanpa hak edit -- seluruh field benar-benar terkunci (bukan cuma tombol simpan hilang).
This commit is contained in:
@@ -138,6 +138,13 @@ def _migrasi_role_pengguna(conn: sqlite3.Connection) -> None:
|
||||
conn.execute("DROP TABLE pengguna_lama")
|
||||
|
||||
|
||||
def _migrasi_nim_mahasiswa(conn: sqlite3.Connection) -> None:
|
||||
"""Kolom lama bernama 'npm' — istilah baku adalah NIM, bukan NPM."""
|
||||
kolom = {r["name"] for r in conn.execute("PRAGMA table_info(mahasiswa)")}
|
||||
if "npm" in kolom and "nim" not in kolom:
|
||||
conn.execute("ALTER TABLE mahasiswa RENAME COLUMN npm TO nim")
|
||||
|
||||
|
||||
def _migrasi_kelas_penugasan(conn: sqlite3.Connection) -> None:
|
||||
"""Skema lama penugasan hanya (user_id, mk_kode) — tambah kolom kelas
|
||||
(kosong = seluruh kelas MK ini, dipakai dosen_rps_mk; terisi = dosen_mk
|
||||
@@ -207,14 +214,15 @@ def init_db() -> None:
|
||||
_migrasi_kelas_penugasan(conn)
|
||||
conn.execute(
|
||||
"""CREATE TABLE IF NOT EXISTS mahasiswa (
|
||||
npm TEXT NOT NULL,
|
||||
nim TEXT NOT NULL,
|
||||
nama TEXT NOT NULL,
|
||||
mk_kode TEXT NOT NULL,
|
||||
kelas TEXT NOT NULL DEFAULT '',
|
||||
tahun TEXT NOT NULL,
|
||||
PRIMARY KEY (npm, mk_kode, tahun)
|
||||
PRIMARY KEY (nim, mk_kode, tahun)
|
||||
)"""
|
||||
)
|
||||
_migrasi_nim_mahasiswa(conn)
|
||||
|
||||
|
||||
# ── pengaturan prodi ─────────────────────────────────────────────────────────
|
||||
@@ -507,9 +515,9 @@ def ganti_mahasiswa(baris: list[dict], tahun: str | None = None) -> None:
|
||||
with get_conn() as conn:
|
||||
conn.execute("DELETE FROM mahasiswa WHERE tahun=?", (tahun,))
|
||||
conn.executemany(
|
||||
"INSERT OR REPLACE INTO mahasiswa (npm, nama, mk_kode, kelas, tahun) "
|
||||
"INSERT OR REPLACE INTO mahasiswa (nim, nama, mk_kode, kelas, tahun) "
|
||||
"VALUES (?,?,?,?,?)",
|
||||
[(b["npm"], b["nama"], b["mk_kode"], b.get("kelas", ""), tahun)
|
||||
[(b["nim"], b["nama"], b["mk_kode"], b.get("kelas", ""), tahun)
|
||||
for b in baris],
|
||||
)
|
||||
|
||||
@@ -518,8 +526,8 @@ def mahasiswa_mk(mk_kode: str, tahun: str | None = None) -> list[dict]:
|
||||
tahun = tahun or tahun_aktif()
|
||||
with get_conn() as conn:
|
||||
rows = conn.execute(
|
||||
"SELECT npm, nama, kelas FROM mahasiswa WHERE mk_kode=? AND tahun=? "
|
||||
"ORDER BY kelas, npm",
|
||||
"SELECT nim, nama, kelas FROM mahasiswa WHERE mk_kode=? AND tahun=? "
|
||||
"ORDER BY kelas, nim",
|
||||
(mk_kode, tahun),
|
||||
).fetchall()
|
||||
return [dict(r) for r in rows]
|
||||
|
||||
Reference in New Issue
Block a user