From cbb6dcec8a020c6bc13c33e560a58b51fb2e2ddf Mon Sep 17 00:00:00 2001 From: Marco Wende Date: Thu, 18 Jun 2026 12:02:59 +0200 Subject: [PATCH 1/2] e --- .DS_Store | Bin 8196 -> 10244 bytes Active-Directory/.DS_Store | Bin 0 -> 6148 bytes Intune/.DS_Store | Bin 0 -> 8196 bytes 3 files changed, 0 insertions(+), 0 deletions(-) create mode 100644 Active-Directory/.DS_Store create mode 100644 Intune/.DS_Store diff --git a/.DS_Store b/.DS_Store index bda96e18601c67964f72519bf165ef5f761ed6a8..c9f1432030e0c40d2bbb3af06c676ebee4bff15b 100644 GIT binary patch delta 1491 zcmeHHU2GIp6uuutIwP0t-DX+`JCrR*K;7a_x1~Q21WF?YOAGCW9}RVOXM_p6vp+N4 zs--D05Fq@eOu_?#Z$_dqu{IWzN7NAF6DhAe_&~yg@zMC^xjRc@h^7y|dXvey-?``9 zd*=Ic&gmVeM|8#*c1_qOV+q%ywW@BPnTxbp^6|W19f%%p=+2h%t{?&E}mk&nh@^Bvo~>NyNjB zCf#V$`Fpk%I73BSrrP2=MO}=Ec+iQPxr{s zl*#o>-pV?8VXI2b)xCx52dhrScZ;6bTX*(rTtAd677A3SU-xZ)Q`e8m0^YIwV7TOX zRKk5Fx@16}9r2G_6=!(Tb1HTBTjU-Wv6^3I4ccx{l!x?BF}+P6Qk28;#+|n9*tKeg zM`VU@y{a2n0hKgLX2KT_m9VGfZRZht%$~B}*`EMbK*ft#2@TD72|C*G8hX%&er&~V zj9@Km`FNP{j<+;4IGJJg(w8Zr~<9!x#7lbNCi_@c_Ss(Av=zuGiA- zODa8|)A}&8hOd1l-1CBFh<@ioMM^0e7xmRIw;JpCD+<=z(rif70ePjpAtQioLl%3U*T&k;5P2y2i(Jt z_&NNoCEc+kLDkWUmoIw9sBI8((TZ9(?xAk%G<%bYbgK71b>sZ6VgpTv&*KeIgC3%c3E(Nd{0?r=$%_#-;Fyw(!4l|2{$gS-IGA%KZgSI#rPX delta 176 zcmZn(XmOBWU|?W$DortDU;r^WfEYvza8E20o2aKK3KC!h@);QN7*dnUiwlx+@{=|e zPGg_gz`L29gM~vDq=JpX6DVK8P>QSyD86g5jX)ufRCTqXiMhFsf}y$jBncVDp2@Nj x@{GNkZ6#FM1(|`$fIxy9NVtM5-dOmZc{0CBAP3M|kl75A<9ViTj*wwz1_06TBFF#$ diff --git a/Active-Directory/.DS_Store b/Active-Directory/.DS_Store new file mode 100644 index 0000000000000000000000000000000000000000..5008ddfcf53c02e82d7eee2e57c38e5672ef89f6 GIT binary patch literal 6148 zcmeH~Jr2S!425mzP>H1@V-^m;4Wg<&0T*E43hX&L&p$$qDprKhvt+--jT7}7np#A3 zem<@ulZcFPQ@L2!n>{z**++&mCkOWA81W14cNZlEfg7;MkzE(HCqgga^y>{tEnwC%0;vJ&^%eQ zLs35+`xjp>T01JtX(=mSr_s6-!(#{bNjZES%=5+o$fY36+A z{OA1V%>VEIowNUzF@|)}Xk=_YV@#%pqoz`ImBPpQb48ItNjV`%pD~A-tbsMNVfu?o z`Dda4UL%?rdJ~BGdVrq~33@oDLYxp7934~zDF7i) z0fItp$^!zOM2M*nCjS`djsoYI!Sc4pR)P_<@J4px!kBXoU`2=>7B_9 z+m`1iljk9omCu-2QK3|*6}vMB+|i7$`$aFU7k2VqkL%jGQd`gMu*}h{R@34-zHT{Y zAyBXklcwzIvmC=6O}j-yEx>~NL609^F^9$HrsZ_dPvO9 z7hK!k=6aTIxz0epZyxsf7++}0Q2(Ik7W|fAv3`rz7qhDQ9^J!S+1p_jJVHe|IeXrs zC3mh^wPyY1mis%p&sAzw)v7wTwr|AptekBQ=w9A*49nTyJ8BvJfkAS+<6HYIv!Ezd z(&ZjUA2QEXS80{=7sO)y#hi7hX!%F9I$0KL#o`G?)=up*$e1qI;F?A-5{t#}kma3R z-cm5B7GgEFY&j|DJsz1BzD~nkilTWv2Pp=Gs@k+#Ry3p6)^nyEitbrQqK>{1VOc2L zxJg#3P~V?-hlc3AJt2-Yr)63DbPwOVQ}_JtVbhs>tLFP;dC)tc7tHQa3c`{`yDSHv z7|FRxn_>BGAuzl%9*Yg|rJ4=HG(x*$vF#b!<1BsfmNQ~e*ps_O^viXnu&Yb05Y4&| z4^9NFz@2req!8B#n5_9_cson7G;3#j=%=(J>==8Ry~y5Sr`T!sG5d<0XBXKe_A~p1 z{mOo0f1n(*PzeoHh+!cXVKG)>4c6jrq|t#+bfFtP*o{5NLdQP17{(!ZID$v<7#_zH zcnZ(pS)9Q0cnK%*2HwP5_z0il3w()ha1lS?M_k6AQiUW-ic~Glk!qw`X}PpQS}kpq z+N5?VBi>&sv2N$2JwZb<2(Ig>A=ZUQjr8`_Sr>m`OM6FW*DcGsZ)bC!&8eANJ1@b> zw{BBb+PA^I)xwz$UWC;wMO_>7%p7l;Ty5fT1E8Dz{u0!xvku-}Xnn$e0jY{fP_h)fXv zS?om)dDw7>0*6q*7{>81Ch!Q3;y9iRXmA405e;6z%XkH^;x)XE(|8wW@E+dB2lxbE z;{v|NrD@^5b!xcd_v;P!kxap{U1vY(l_)fI$s64(6ARAg`G4EBfB(PH+eYg}9*8_} z3wZ$Lt(n#|z0kFe9iD3^=-EpTFMQsFz(9qnARQ+R(s9Dce;86bK~uR-D#QtaB%yNC Xe+aml-@2pwKf3?_b!L5Y@BhC6X>Fa& literal 0 HcmV?d00001 From 0ff20b95737322fd428ce4a5be57ad70cd99e177 Mon Sep 17 00:00:00 2001 From: Marco Wende Date: Fri, 19 Jun 2026 09:03:49 +0200 Subject: [PATCH 2/2] =?UTF-8?q?group=20remove=20hinzugef=C3=BCgt?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .DS_Store | Bin 10244 -> 10244 bytes Intune/.DS_Store | Bin 8196 -> 8196 bytes Intune/Intune-App-Manager-Web/www/app.js | 86 +++++++++++++++++++ Intune/Intune-App-Manager-Web/www/styles.css | 32 ++++++- 4 files changed, 116 insertions(+), 2 deletions(-) diff --git a/.DS_Store b/.DS_Store index c9f1432030e0c40d2bbb3af06c676ebee4bff15b..f234f688ebc29f7ef84c142b441c36eeb1431c04 100644 GIT binary patch delta 20 acmZn(XbITxLwxcE0gufN5T3?2Yq0|+z# delta 33 icmZn(XbITxL!86N&_YMS*uY|w#1DQR7^hZ8p&9_RdkK{Q diff --git a/Intune/.DS_Store b/Intune/.DS_Store index a56c8ef5a461836f7face22e88e70169bb6266b1..c797a86d5b963579910bc9c1bd264e74e6a396db 100644 GIT binary patch literal 8196 zcmeHMU2GIp6u#fI&>0xoDHIrFv5WNwu$65A+XCu#TNEtN%C__eWZB&rVZwB#?96V_ zTGJSfCP0jDia&`jqA~tN@i&_I0%Fu?44B{p560ibL=&Tli4UGTca}(j2NHr9=Wgbn zd(OG%%-l2QyLZnnV+^UH(af067?bJZRGUfNc^cRA>zpQql1ic=d&V4QvL@ESM(Go^ zC<0Lgq6kD0h$0Y0;7W`Do!Pv}7dZEYHtM4YL=pI3Mu6`Rak@B7hICTUVC$eRC;^D_ z5+G3M$MQggHZaXM`0Bg1eJl zJebaq6g29i2t*M$Hv$|!^VkNe+f?yyE(FZ zH#cfqo}Wm31*xKP+VrX_rD|r?-Ra%#SlZ9}MK6^tY~x&?>)N^UIGfvQnPVBPuG4k= ztmT-6z`!z0nzDVsatwDYo3vAOup(wJF(H4x4uV`M?7;kQCnP`lUH?K@IH^$o& zEfW)pJhx%_nk|_<_K4%|7wbg0SFl-A)_ve&7j1i`PO<2U_VS{?4i_yeGiIu@^!}{_ zgF|XYn_Z&S^^E$K>v&tuf=4u?)p!(z4SCn;Etp(Ckaz9kh~s6n+I-f|7wxQXcGz~> zy3Zt8jh8RDw%zM`7I!l==$rd|t~*CHIPAFvzcX+)Xpw(0ODlTj7L%M>C9{iMdv#L+ z0OghH`LV^w zo|UuBJ|{b3D%xS?#OzwFMqi*Wl(hzVu$Z&<7A^nYz||tXUfpictv9&_cV@`in@XU$ zMz7bmaZP8zq~4I_KzzNvMD6ovjk1;%6K_jtgBE>4v@C*@D?K zMj07C)OwNzFOTHhXq{pCE>{K%uh%!r@(_2}VHl#zz#P+HrYY! zVT}cBEVk};a&%m~WH>m*zF|MIU)f)TgK9#6jvJ6b8&X)0%|Y&`(T^Qr_8S<11D6os z;eJdI0w(bw_TvB!;xR(OAv{GWcov880$#*Rco}cuZM=i`@IH>>7(T+s_=IqA5~uM4 ze#Y-2ug_%r=5n43ia#zk+e_(!W4q2SvMVF#Y?qgws}L@AUjMJV@bCYZ{>G8VC<0Lg zu9yg*vMb${qQ|+=#=~pvI9)sG;*HOn6f`iQj!)t8pd2T9<_|*}$3tB*q?3Y@hT3KS YA>d#9(jA@u(fLnx^m*&*%YFX;4UFTQb^rhX literal 8196 zcmeHMTWl0n7(U;$&>1JtX(=mSr_s6-!(#{bNjZES%=5+o$fY36+A z{OA1V%>VEIowNUzF@|)}Xk=_YV@#%pqoz`ImBPpQb48ItNjV`%pD~A-tbsMNVfu?o z`Dda4UL%?rdJ~BGdVrq~33@oDLYxp7934~zDF7i) z0fItp$^!zOM2M*nCjS`djsoYI!Sc4pR)P_<@J4px!kBXoU`2=>7B_9 z+m`1iljk9omCu-2QK3|*6}vMB+|i7$`$aFU7k2VqkL%jGQd`gMu*}h{R@34-zHT{Y zAyBXklcwzIvmC=6O}j-yEx>~NL609^F^9$HrsZ_dPvO9 z7hK!k=6aTIxz0epZyxsf7++}0Q2(Ik7W|fAv3`rz7qhDQ9^J!S+1p_jJVHe|IeXrs zC3mh^wPyY1mis%p&sAzw)v7wTwr|AptekBQ=w9A*49nTyJ8BvJfkAS+<6HYIv!Ezd z(&ZjUA2QEXS80{=7sO)y#hi7hX!%F9I$0KL#o`G?)=up*$e1qI;F?A-5{t#}kma3R z-cm5B7GgEFY&j|DJsz1BzD~nkilTWv2Pp=Gs@k+#Ry3p6)^nyEitbrQqK>{1VOc2L zxJg#3P~V?-hlc3AJt2-Yr)63DbPwOVQ}_JtVbhs>tLFP;dC)tc7tHQa3c`{`yDSHv z7|FRxn_>BGAuzl%9*Yg|rJ4=HG(x*$vF#b!<1BsfmNQ~e*ps_O^viXnu&Yb05Y4&| z4^9NFz@2req!8B#n5_9_cson7G;3#j=%=(J>==8Ry~y5Sr`T!sG5d<0XBXKe_A~p1 z{mOo0f1n(*PzeoHh+!cXVKG)>4c6jrq|t#+bfFtP*o{5NLdQP17{(!ZID$v<7#_zH zcnZ(pS)9Q0cnK%*2HwP5_z0il3w()ha1lS?M_k6AQiUW-ic~Glk!qw`X}PpQS}kpq z+N5?VBi>&sv2N$2JwZb<2(Ig>A=ZUQjr8`_Sr>m`OM6FW*DcGsZ)bC!&8eANJ1@b> zw{BBb+PA^I)xwz$UWC;wMO_>7%p7l;Ty5fT1E8Dz{u0!xvku-}Xnn$e0jY{fP_h)fXv zS?om)dDw7>0*6q*7{>81Ch!Q3;y9iRXmA405e;6z%XkH^;x)XE(|8wW@E+dB2lxbE z;{v|NrD@^5b!xcd_v;P!kxap{U1vY(l_)fI$s64(6ARAg`G4EBfB(PH+eYg}9*8_} z3wZ$Lt(n#|z0kFe9iD3^=-EpTFMQsFz(9qnARQ+R(s9Dce;86bK~uR-D#QtaB%yNC Xe+aml-@2pwKf3?_b!L5Y@BhC6X>Fa& diff --git a/Intune/Intune-App-Manager-Web/www/app.js b/Intune/Intune-App-Manager-Web/www/app.js index dbb1662..0bd0828 100644 --- a/Intune/Intune-App-Manager-Web/www/app.js +++ b/Intune/Intune-App-Manager-Web/www/app.js @@ -1094,6 +1094,14 @@ function renderAppRow(app) { + `; + const removableReq = app.RequiredGroups.filter(g => !g.IsNative); + const removableAvail = app.AvailableGroups.filter(g => !g.IsNative); + const mkRemoveBtn = (groups, type, label) => groups.length > 0 + ? `` + : ``; + const removeReqBtn = mkRemoveBtn(removableReq, 'required', 'R'); + const removeAvailBtn = mkRemoveBtn(removableAvail, 'available', 'A'); + const hasNoAssignments = app.AvailableGroups.length === 0 && app.RequiredGroups.length === 0; // Direkt-Link in das Intune Admin Center fuer diese App (dezentes Icon, NICHT der Name selbst) const intuneIcon = intuneAppLink(app.AppId, app.AppName); @@ -1137,6 +1145,8 @@ function renderAppRow(app) {
${availBtn || '—'}
${reqBtn || '—'}
${createBtn}
+
${removeReqBtn}
+
${removeAvailBtn}
${deleteBtn}
${detailHtml} @@ -1688,6 +1698,26 @@ function attachAppRowEvents(wrap) { openCreateGroupModal(btn.dataset.appId, btn.dataset.appName); }); }); + wrap.querySelectorAll('[data-remove-group]').forEach(btn => { + btn.addEventListener('click', e => { + e.stopPropagation(); + const app = State.apps.find(a => a.AppId === btn.dataset.appId); + if (!app) return; + const type = btn.dataset.removeType; // 'required' | 'available' + const src = type === 'required' ? app.RequiredGroups : app.AvailableGroups; + const groups = src.filter(g => !g.IsNative).map(g => ({ ...g, _type: type })); + if (groups.length === 0) return; + if (groups.length === 1) { + removeAssignmentWithConfirm({ + appId: app.AppId, appName: app.AppName, + groupId: groups[0].GroupId, groupName: groups[0].GroupName, + type, + }); + return; + } + showRemoveGroupPicker(btn, app, groups); + }); + }); wrap.querySelectorAll('[data-delete-app]').forEach(btn => { btn.addEventListener('click', e => { e.preventDefault(); @@ -1893,6 +1923,62 @@ function showGroupPicker(anchorEl, app, groups, type) { }, 0); } +function showRemoveGroupPicker(anchorEl, app, groups) { + closeGroupPicker(); + + pickerEl = document.createElement('div'); + pickerEl.className = 'group-picker picker-remove'; + pickerEl.innerHTML = ` +
Gruppe entfernen — ${escapeHtml(app.AppName)}
+
+ ${groups.map(g => { + const badge = g._type === 'required' + ? `Req` + : `Avail`; + return ` +
+ +
`; + }).join('')} +
+ `; + document.body.appendChild(pickerEl); + + const r = anchorEl.getBoundingClientRect(); + const pw = pickerEl.offsetWidth; + const ph = pickerEl.offsetHeight; + let left = r.left; + let top = r.bottom + 4; + if (left + pw > window.innerWidth - 8) left = window.innerWidth - pw - 8; + if (top + ph > window.innerHeight - 8) top = r.top - ph - 4; + pickerEl.style.left = left + 'px'; + pickerEl.style.top = top + 'px'; + + pickerEl.querySelectorAll('.picker-remove-item').forEach(item => { + item.addEventListener('click', e => { + e.stopPropagation(); + const ctx = { + appId: app.AppId, appName: app.AppName, + groupId: item.dataset.groupId, groupName: item.dataset.groupName, + type: item.dataset.type, + }; + closeGroupPicker(); + removeAssignmentWithConfirm(ctx); + }); + }); + + setTimeout(() => { + document.addEventListener('click', onPickerOutsideClick, true); + document.addEventListener('keydown', onPickerEscape); + }, 0); +} + // ============================================================= // Membership // ============================================================= diff --git a/Intune/Intune-App-Manager-Web/www/styles.css b/Intune/Intune-App-Manager-Web/www/styles.css index 57bf071..afe42d3 100644 --- a/Intune/Intune-App-Manager-Web/www/styles.css +++ b/Intune/Intune-App-Manager-Web/www/styles.css @@ -1330,6 +1330,8 @@ html[data-theme="dark"] .entra-link.teams-link:hover { 98px /* available */ 98px /* required */ 26px /* + */ + 32px /* −R */ + 32px /* −A */ 26px; /* delete */ column-gap: 8px; padding: 6px 12px; @@ -1610,7 +1612,9 @@ html[data-theme="dark"] .entra-link.teams-link:hover { .col-version { justify-content: flex-start; } .col-avail { justify-content: stretch; } .col-req { justify-content: stretch; } -.col-create { justify-content: stretch; } +.col-create { justify-content: stretch; } +.col-remove-req { justify-content: stretch; } +.col-remove-avail { justify-content: stretch; } /* Buttons fuellen ihre Spalte komplett — saubere vertikale Linien. Available/Required: Label klebt links, Count-Badge rechts, damit die @@ -1621,7 +1625,11 @@ html[data-theme="dark"] .entra-link.teams-link:hover { justify-content: flex-start; padding: 0 10px; } -.col-create .type-btn { +.col-create .type-btn, +.col-remove-req .type-btn, +.col-remove-req .type-remove, +.col-remove-avail .type-btn, +.col-remove-avail .type-remove { width: 100%; justify-content: center; padding: 0; @@ -1891,6 +1899,26 @@ a.app-name:hover { border-color: var(--ink); border-style: solid; } +.type-remove { + width: 100%; + padding: 0; + font-size: 11px; + font-weight: 600; + color: var(--muted); + border-style: dashed; + justify-content: center; + letter-spacing: -0.5px; +} +.type-remove:hover:not(:disabled) { + color: var(--danger, #e55); + border-color: var(--danger, #e55); + border-style: solid; +} +.type-remove--empty { + visibility: hidden; + pointer-events: none; + border: none; +} /* Anzahl-Hinweis (z.B. "Available 3" wenn 3 Available-Gruppen existieren) */ .type-btn-count {