f49aPNR0T^FdZCqA*EyetBa^=XdRU0}QK`=u>3?CZr0d0yXlX|AHd;B~{8I-KiUQuZ#}p&oqN>y<
zZztU#T$YTvo^7H(zoXGRN1A?&S=
zfEPE6lh3Og~;9HrO={g+*X<*P2M$&9Gl
z9hIrW^`m!=M#FM?a(4*(
zjgRk{N@bb0m5+CFD?Z*nftLjYlK4?yOJf;NyH;M+hPYeFV98hfNA#z*+a*bGJ%O82
z!$KkcP5F9tmd#hhMp|#GA756tffp%dl=(TS03W&!bT3tH5W1t|=}law9!nRw1p4m(
z_$^fL1REJg&w;weep
z*#04lE@Y0J7psIcn?zI16DA;e79l?_DS_-@u_+JCc0Ray@-jlmSHlV0JJhm7{8Bmo
zMdg$4BXXyAPhH;K&?6f9(Jw@4SA1n2v1Y95&iJD4;NwA>K$?-#!HVHC(Z-6_C5v{_
ziVUpzt~?()*DR4c%g&{%SsUJ>!ilL`aYDw#a_3V+0DcVA$8$-g?{p91Glv><(z5$W
z8i5=T=Q>ZcTP;7nQh(Lov~Z#w%yC%yNPa|YXeawo^uc`n4p);BE;rT82EN>iGhXnt
z*FkpLT4pa38f@;ZwW#M5kHn}8xa~76x^!qe5!c~}ffyyFtRmGxQt&gKclk!d9S@;;
z=OnG1)#C|;7%3-9Vwst1cNI<5OkTx4v8>2+SRPk32a8}+JU-(AdcCg8x7aDj=4|65
zZ#%JoD{^fuzA^DUm`g6WP%cB_X-*Hn=q7w%g1<1y%h(1l`WKGY^;fkZYh$H7u=7u(
zqq(e~(QD|9GwM)&pL6wlV@cZay)l(gU)gDbZnP;m8@e|7O((6U&wZw^wipIO6h+1l
z-6#|?am@pMj~Ff;J_>)kTc>r;Q*_{Kv#)fM5Nwvm!hm
zZiVzCoz+pq$k#(i_4{JSDN{@qquicJdv(55T)y&!llA7KunpGbvKQ&F?+I5HpN{0*
z;~^VWtc6CCs-Z4in`?bBubvu^icfN6%UI6!rk1LoTn8Snrnt7foLxeT>*;+NtY*A`
zf=4}ade3N?(13;F(rY%CH-)2>Q#v2O?zjr(hzZPHp)eU&O%CQ{EI68C5ZAAyiiFvjmH8@1;)s)*
zPPdj
z6Fwl@<6(k-AlDPW-!e8EMmhFBoF1dj+2UYTl^sos7OwAo4m)sDPRL>g$VJId1DvLh
zp6!gaDC*YJ4}8aueCHq4NjTZ05FH1~Wji~PeP4!GLl4Wwa%DX+WgB+=!Foo~D-8F7
z$z3j*!~SPQSMP2vrg=a@^JI1G=uktYkbbk2SfV3v=O`^}LD}!K5*3*DfNYL-e`EdC
zdAQKBm$%t=#?5%+VjFx6t)W(-h__ozfuMHxvU6ZMY+uSwV_|HT2dS7ghT(<~<_!B*
zX|anRJv)^Kxkg&N)j?l|Th!x?N#)YZi7}sISN+%0sp%xi0@_ce4T?EhT`lc(2v~Z(
z8JHk%loC|dx-z`l2+0>VCk!tBGc;ZqNbDEJVvm
zC@4>GBI;ew?U4TS$fxn08yxtB8#L0c@Pke}%_&jVXV&TARU3O*?8gTjG8@&cz^54?ANd@Iyzd-vXYN}+
z(nc}#l_}&PFO?yHxjL&Tr8;LjnIB8ml_Z&*l)XS>g@#A+YYxN_OSsl<=fvPPJfuYb
zz28$IfA=zI&jqD|JtHN(8Mh>u-QZnqPiB*n{MBkz(?jQWNlM?6#C%`dB1$u^v>$T+
zR(a(g0t$$Bp=|qU&-|?rSKvu}z+6wJjefYP-8GZ+#lodxoK%=kYC&b+<4lvHwWRs9
zfUaT45099ay(Vmn%R@flT(v@^~4O
zF47?DJ!57deYn5K==w>;eN~a@gkh19rd#4oC?+jQ9$b__a%P&p*(rQWp!(Mf|n7WVmU{j=pIVB4kb_x*Ez&d6~eBH_iS1
zc!pDzIfgAK+m(TuS8m8%P5+*b$nYt-+#TLmaU;#vm?gFBWt1l*Fk$g$^>lK$Bz&9@
z8lR6>8mhXDS1}RmH89wbxqiHL#^a9%+CixAJJ^a&18-Salp{(__cz_TtKMr8tc}b<
z!X%ra$8McfGt>;kBp>jeO)+1iMyXND$&Ph!`0;YH8I(ZlaHM0+@%8ebZt3s(%@_jW
zJv;nds)X_07+CAzB^(wuwJ+?t^ikz!h{qi5K;L%b+Yun8F)ZQUX;3NWxP@pkXm)bt
zLX$=M;3?y&v6Az4CFY?{o|om3d~!_mCf^e`u$+vw-c(dPq)=(_MKuM=t_h2#v1Z{boOWImqsgf^qXj
z{)RqpN%ty~$o86!8>cE{l_Ps|!+D+dhLLE?qIe~RV)=Y}6T&2i6Ey9ruc5!E^t_$8
zWkP{cv1`hg+1xds0@t4t1*B;a2dS)-0Q?%_fbIVC56orOB^Q)daEF9P@j&GO;Shr>
z`LU)11QFiT%bf*URD?Ufpd0RhvF7HiEim^#8Q>&rlyC%G%cvOM!v(nf%w%4guKuHGnFq#M4)$aVVWEB}~Wb$0!7_j=F6c}6(2Sn?DzfJM0
z>BN3-@9fXAV*b2!`UG(6QyQ1Yk8c%zmbQ)7*hb^xPn~Y9mbJdrG2+ij`YxHH^SNeDUBmRH3{QpOxJX(ww2lN?eda9ImmQaKousPcoH_!QC
zz`CxQ+6OuRwJe8NSv8w_M~uCL!>!)4%IC|O0co~IZ4<)#HBHuC
z8nED$^VNUxVw>|Sz=h5Y#K|e^{UkFaR9Q+&sy;2j5?pGS)Q#SvH3|l~~fS*-4+YE>M+~m6g<_a@G0FEtbC;
zIJ8dGyWHSRtq)2$N7MAtvAIqbpxhlH;A;?GN-y_v`brVZqcNfq@R{RZ@s^2tw;P(V
zQBkzAF*$GTLh?jyD%Se}eH(ro!Hx8xq@=Hq>esx~0lNLwj4m4KH$0=sP;>bie0Hfl
zj?HgntRHqBFoBBUls~;6Rh^Q!&$G0nlLh+rwjfkC3XsfyWy<+0~{ovv(ybP23p)
zRYDdP7BF)Qvs1xn^D6+IvTx>C2
zwS3K^d61Ts3*fSCUtS@)&P^SOzQAA2NS}~?qnG2kCOH6Ex+_c)s}c-=DrZteIw_R~
zFj4v9W4Z`z=Ou1SQr(LB`s#m|Som}*@i(#oE|*2pcD7#lrd4w?0Ny=TFwIZ6AwV@k
z$W_pptmR>mkrA^f2xL9>+-U6=j
z$IK3Gsy~?#2IT%bQha%Jj3w`K+~;f3ie~`vkuBYG7GBh^C29X!Os>588};kwows=C
z0e&+wx*5fKOw`6V{%xEMw3_oiflH?`0C3f9xuwrH{|w-~wm?k21Rda(`Cx1R3q8mf
z>&v}LAP3;{-McT+GT*k1H=h9X$&-^M_lG81n!WBDiV0bHcxTL&Cx0f1#~X1#>ybAa43*BRGJe&Cv$5Pn5ir;<88
zQC7{8vxjt%Cn?kbUcNnYR(VjH3&gHXl~SnX1}Hc4Mdo$1odFD_2*dci{<$Y_I#E947+bk`0kB^=o5!iAvnvC&1-w$CuG@%JD*RH9c3k9|Sy
zRepxjO{L5RZpNm*5cVtWC4H;}^j-ZML&xPKn?4~k1_u?VqzVK_DLK7#?-{
z)wc{KLp){B;Cg<;gJYUQQrY6_yhqsz_sM=Z(2`T$e@OMFO;+aQ5!!FURR;|Oe2ziQ
zll|OAIsBIT45+iTvpWjUoBd!ox{`V$!bSBb{LWuf-2mCJveN1C*L3A#V!_8Z*F&9S
zL$@d;Nl8ggvB|t}>pDv+OdMhlwug|bg1asN7ylwpdU*LQTbaN_V7o)-Tts}X0JCVd
zdQhUfxd+49SN#3V4sh4Oe6-uoUjioOXv6p+I23`%JjB-fPV>d*(r_O}o5C$~Jg0m}
zIqdwa@!Fyl$pCoE-|g5i$JkHfHRwmulzqFM
z4uQGY??{JDI)(lL?2LwLM&503-Kev
zUNB59l_0e@qbtM3@i`Rw2?rK|igdr{;~fk@KWY~)Vg2}2|NBg
z@)Gb*f`9r>p#5+A8}wYmS?JZ{12s*<#oqBlj8apz*=hcjj08gQCYfNE2Sbc(4OW`e
zD-T`!`MUYcEn!Rbft=q`rYmcW+lPEZ6NRgpcKn=xH0u!i7aneuvzX5%7X}3MAskOSC;PKS1#!0)L
z8Gfc>(3jIxEhDK~o`T`8nKV#n);cc0t;?=vBByG;%nBJo?tNENb)Jsq)qPh^Fxbn@
zZ|>zb$=Bw~0?ulH)bgtpLLDAn6p*Fa3aQ%|Ge~8PKv@ffgt-sY#l?r*+Z0T?{tTa_AGw0w0dFyt^^OMu*kQTHDtpDAXjs%Cj=Usk(
zbL79i^}sHe_&zjv8-2G7vwYaYb7BTEEz|G#FsykpQfm8+pztSbm{R3gKQC~SFNRhq
z#DU4>n^d=5`CFwavv1p>Z3-P?fu`uM+dibt07Q)9p$jzrygGMC)#0AJ+391>kezb_>xkCD&EF!7SMCbjpZ1w^nH8Vt5lY08+wpb_2Hbd)re>U7qyMV
z;u7?Cno->AbHk@|VeKc?Fv7HB1Ww|7?}5o#KZfYNAA{NiEK7r=Ppv1#pqE7Xe73{xjSC#|!>bGb{anUjDif
zG-H7bAZ7oXPS9h~k+Quprs_u2wrGsU>`>C~*j)l8;)L!?%_yw73wF{ryn8)9*F>6M
zRDRtL;1b4myV}v&uFPbY7SPwr7oC2l{GmNEKW)(V&v(P*X;a(GTKdX0XAA^uw<>IR
z&V_rzW58iJ+9q)-?1R?&HKAb}iqX{FiTnXpN<7|oSFvFXs*o&Nvi(?XIVyB{O6E)z
zd-OG{-1$S5&PNJ>TQ8Ptr^UxRoh)C39^>qRO!|sZd>WsUaXf%59hVf%SQBageuiW<
zrC^^Jf739;$_m!R24$_f@kASgT(`V3o1(tA>|nX0@
zv@!#^?bZgqX)$W5nyKu7As{881B0-C0BP!EZOB@Xc|hu=*c4BL*s*p4%dIw!8&8yy
zdTTKPvVF{?K0RA;Chji36iVNB=l8H9tGP^7pBc=vaqdBiiC^LdY_^vVRo=DPb}4Jh
z^`(299>l^q?r%hkU?RoE5faW=dJ7qW~ZNDhxgDiKs7jX0Va^
znIS$E9yy!_BWoZROC9$NBLznHiRL!?_|D2fwmUe2YO>O~v%VulGkwm0r8+8}Z6
z{8=7OKfkVD^59vYV4)kSRBn@a{MCRm38xIqc1E}wKaTZ3Oq)_2R~yKG*6Tgtan?oI
zo#@P;dj`Ot^K`*qCao{Z3O~U<8!2fS-*){#+DkBm2Y<=$gFK%=2aA>m^|qr
z;pVbaswcIhAz)dxem+YrTI3or4PtnLZ(#-eW10m`nYhH@y4lED&Rz7WX>}L-eCJGj
zU&{r+L=&~U`z7i$B*Uql3#*0>2R)tA4q$%Q?lg9aui4JciD|c`5q9RKRCeX3kL@G5
zEAwq%9~v#61JL%1Ta-QyMc0sm2>Hm;yS7X`cwXFH?)0AQ)i1fafzZgQGeQ8#oYVGk
zA{V8&iT)GDj>xx9pN+u2mmCM#hT{fahn0l_?;S%b%>4hdv=9DYhpqC=`5r?$yKWDLx=|3Q!bH--AE&
zl6-|%LT=WLN3~YDn+C%INghR6daq4X`!=F{sX?4$r=G9lLB%07BE}AJq2Dp)0JfX$
zt)cEHvC*^zl-{(v^dwV2HRXq)bXr=52>dR=YX
zttKLpw18%%NdC|bE^SowVgXc%uZu0;cHIH@{7`(n*d}NBrzvt$hnDyL!UHJg_;Hn3
zWWSP63A38#RbtH7!)1iplE!dp49h`fiP!|E1}pf(!2-v6)Uc$cNl9xkRiEN-=UfPE
zY*yV1_icPV*Lw5~`^D4x&nSE29a}51SCO5ARjr#;77d4t;um$`l9pSq=|ZX%6ao4^
zA-i(JhaM{hb&&HDYunk);{Dnzs=D`+3>8rhdyT5N?x?zNE~eU)N30&JuAT)Jl*#p<
zIQxe*S`BP+uXf>r_S#h;fzQO*09Tzy+(*1A&whoqq*tGpye3INI6XYG>9uMK*15`n
zK7ScdCHj}Z`jP((!Oz3Pvs+g^VgNTP;R$D0ZH`qmh;7_xvxZ~vK{qj>9>SJtKiQSH
zasRtW_BVc^M%~bs;N{7$_mbk_$dj)9M>2Gjn-Ev^0EQ965>$MdT$hI;u>3JEQ)H<
z*>ET+N1Gd6Bov73zRa>nTDtjGefehk+HW0~u=0G`CR@Gr8uh9(J$38p8CoHcm5U7b@ot19ro%(pqL7;#M5?
zTVVHoX4^y6e3IZt_j;`5hm(3<*J+y)6K}I`z}lpH{oqAyX)zmk`~{{&Q1q1dW?{93
zzT3Aqe0{>ZH$hr9@ywS9;g2Z6&2E(7&(6gcKk^#Hw{>nX?X-Nr_~`^Vm_PQY7lS)`
zyp?LLF31ra!C7NU1*KZO&e#XfSSXJ_c$$_^3rgx|>Ks}KDYDkn(b+v`J=fUMnM;n8
z;(KYSv_983f(-7vv*yz;Gf#R*?jHDnY|d5Z)t~y-U{dkiZ*B8Tk1k_ln);?|tbnJ{
zuauG}=!~#@wHVuy;ZPO(s&YFY>=4iF`T?$9V)*SZp1v3E7F8NRHHN_}t5!y@J-%?=
zxA*86cy0-Vo&D!kb^9mhXc(;vCQ6+2$F;#PT!8qw0B@N~I81E4mm)fFW%q}i1a@_{
zJ_x&J3gakj7_m^i?_RI>{;jjNPtTu6FjFH_m-MeM46Ur#$r4K3vWBx9a=~M=fm>Nd
z)d876tDKU%uoc?0%6_gjnOUtOA>-xQTGCEqJIXrt**|DyO!n-iHr#Eko(>nxqOt$YfoJjG}
zUa`##s5?WpFS-k3!wGEqvS(PN==dck3w!Z5%)&jkyFuU@*UWO-?Xe4V0bj@JBEdLo
z=SnYxG&UmE2MeAN=h@zm;3(lEI!HR_?0vByJ0P&Op1-{ABNAFD;tQJ9+^}tDk60|p
zC5E7Yu}lu4tJ_vn55l6Qf_vkaWVe)Jevaz05s+EibCuvwjM&r8-3=dlE`_DPrtr??
zznwoaG$bP>7597Nd-BIhuTuqk{2pSCK}7455kEHh%>MlfY>ZV*`O!by@{GYE=iMWN
zP*4PA=`fN9w;(G0yTN@cD!rm5Xv&AePN?Jc>R}4VKWaM=n?1gsDcu^H8}#%|6E33L
zoC#>xM9f}}u~;!TjCEiRWO({;atwWPr1Q($VQ=T1A7mDJf}F02_QFG7`vJ+K7^|iT
z9ciZsqiZs;SfZ9UYGhq8iMLJ9V#b~RE`wA-H52IEjD_*DAYO=PiW*uE?=#P9JzMS?
z#p2P+#PWC&baz^jQ^wBS_GI-}<4s;$C<)b6Dqd-mFPgea>y4J!sA~1E!$o8yAqywww>HCIF5L-0bv^D=H|9jKZ0Cg;ku4F
zTP?UG)2fO-C%AXJNu;Qg5I38+mfEV=`?D*cj9e{hQYu9y&ZvdS{^UO0!iDRXV5VD@
zO>1~DOW&{LyzT4fr{>QK+;05YJ$ZL^dau0j@EHAY-@=NX|!X5|Ix9=Xzdo1)6)7#a_ix)F!IlL-Pix2TM0hpI$Rpbc?{n9G4!Dzv#2+8i2w5rccXC
z$9{S!IBs03E~zP9@6p|G({0G20VzGgAN+;uWywu{v7tihDG>3T++>
zXUjKu%Uh(Mqm}|9eV7(9P11H=y+$`!6aSE=!zdOufd4Z+uQ3lV^wm
z%haxF7Zo8QczH#!hs!@S6LO{a)Qm)CAyHg|HZbCH`=C@n5cXSmkT7td&i@S>RD?C+
z2_5Zg&t44Gm^-57m_cn+m+sl#tec(MG-ez*AXMOOLU$UZ1w%8!Ku>Hx)xL;qc@!4Z
zR*}$J?uRTm^QW-jx9!U$BgjZhCNRqB5Zqu$+suVcjjwXQ*Yku
zfGK!ff0%%kZeO{^!&t$LRjJ{S&P{XvQZ)Jelzfk(x`row+6Ym$0atXn0mJP9fH@&(_{n03_c9YGe_!NdW_D+3U
z@3uK29nN5Idol-0sf#{hpNc^T@)_dAbquZ|+(*|RWk*8F)z&d`aAcv7tzJi<4Z
zZ89JDz#@?#vH$H3K`usY($)8@@8ZOdH-W#1SggclH@YF99mxzFVQ>$YTR$&;fR#6)Ka}C6^SL_&Knn#|hcF^IJI{Lx~%gin3
z?fIKW$co%Seco4cte8a%8F+rqYFV~v$oJ;Sn5uL=h;7Zc2M!G0wWjHD&>Y)!94!gS
z)bbW)N{*EKv%5@uvUaysewK^7)L!Sn1jhzU
zdsXm8fa9^i2d)PVTuwuBBHTq)mAUG3qbw(B=jIQ)(!5FSSN6rnFW5_5RXbtZTt6!+
z!NfMMh)p@{MGoLh1+*6Y^WwHXQfJ$hJFoqQ(pJyOX=%|~J3-?)#f)s{qVFvbFOOBf
z3r}?XiF~~l@@T^+FOf^jc+Eq%SQ87ND*Sr@gK2iK_X@+68<;YQY|L^_eY2K_!sjN8OgT_)9Aws%q=Tmv^Z
zvS`BXCu%uxRJMTlgM>BrzFe3*x9Xi4%XdSoO3su=!r+%|td>%*1;#C`ZkLVwZ3@$Y
zDundGJLiLOaZn>;HE@~amXXej8L;(CMR5%!P*BBI_R=1H5x4WNZ%d8%^_zEHLe%LO
zvKOq6IB09{3^6q%4E=d|p(R~8sQ$$+uWP8+(Qk#0y$nbE(
zsLx|2te+1VJ$2qPYgx)ehmirz6;$yP
zt6)TAXP(+?(Nt<{b;VE6Qw|SJJ`MqhyQOwC=^IABGa67PKhN<+x<)*B)@6uZUSZw5
zc%vATW>4|&Nfj*46S(ZQ62BWD&jy;&+-0QrH-(h_Gr)ooCZ-W1`7W*ac1J;(T1hN&>4*Iuma+p$6kYN
z!c@Uo>Xv$4TQC&~#)Lq3h91xC34K=>PTTdj8~o!9VOKi{zX^c@*kj3d$s
z`H+_sRrcz^v6_EE{(MZ5Fly~pxKZ1)Hy;|{psksxzaiXjq`k^0VU)xWJQIEG-rEla
zr(Tu+u3$?I3+kSAjjbyhZH|7qC+&35a3&3MupT$np>9+z&*NIBoB7pz@jemevrg|j
z*=rvq?LU@5tmPc44Qt{IQ*DtyuVr0UFlvi^3C76#hf61_1$UL+Q>3B;%Wq;AfbDa7cJVo39)D8?FhKDOhQVR^B8TX=`1;l6Pp~v
z1Q(<tG&wHpjc@-5$#QjZwjv%DUi_WgLu3${$VYpVAxtcX9>4PheBH
zY?O{YioVp6wF$KRKT#ho7DH3XP<2<*)f1uSEzAQDgsxr>`KV=Lq@cVB6OH5m(4|oK
zAH>D)G_z+;`o^5FHCkE^@%{A$yYvCZvx}sP)6Cf?rVWwQtecR5C=Tdd;zWwbS7*)1haz
z_M2|lxJ$L9avpDRJZj2BHC-X|0oTDNl+-i?h$L_==O6~9^C_)qhMT11rJL~I@>B1K
z<8~3D4+0ZI%R9L6yU3P+njQ}rtA=?
zcw2L@B5hL1&iZq<;jawqfV3a?f#07awI-F&EvlgJ)OEpnYVLgbde>l&_AHK~j8(1g
z3hg7l1sqcpDP0cxA1BZOALwdNSJ+6GsUrIhF$#Op(A73
zrg*Xl{@T$NTpkp%Czde_rmflAEU)Xmg{}Lzwpz-V>GyDlBe2>PQCa7RaE1`(pVW*h
zGMD>2gPB3o-z2Zg>c&wrtQ-4fz<8p{ss@X*jTzTQ=oifWR>cX-Km$WRNMhVO=S`VS
z;`-DgheBZAUpvfc=sbD~FDmkKbGy?#^<0F>Il-nNj%BV*2t!2Y-=UH`*@TmKpxbOI
zR8HYU*FB@nSMk9uZ@6fLXG%jaFHxyO%9TD=tc%@&M&}?;V#>Pu2AZ)THfAq47PU$u
zgv;o4dnsX4S5dJ^EagKA$BG04@>n_RjDCC3|w(r==i6vd`@c{{`N!3AM)L0p`3<$c4oZZqzy}
z^H=qQNqWz6tp9V7+sn^GSWACds}kee(eU)g_P4w(ekvSZ_@{|AC}o!J!-67?T-R^G
zMhW;;J$AuRuMfF5u82^PW{1|l`hDrb%S`3DOSN&XK=RbI&ogid68pNVe6h0Zh666z
zi5KTjzQ}nAHsYB6qbgn4Z`8g{3Rg${*TW||@
zB!|4>9&y1kg-nSF!`f^F^a^W0ny_ac+%j~zUuGsR3Q2JQmy~1&7Vk~$MqI*gYWx9>
z%ZKpd&-Y~3GB9JSYYBRrdy>DooLeV%nsPRRcJb^-HMoZ3PcwDBjv(lZq%j;x+-pOCMl-$Pj{pK>25mYc`pr`_B>BrWl3Mst3K>sPUSXRH@c|>lsC5
zesmLM<6JpWus7rjGQ&Kbh25b!WRnn44)XDuBfR#)Zc~WljnwkH9lN|OHsnf9o@m$7
z&F>T&4M#D;bp_ESHU`o3F@ji)bw(gZH%lfK`Lx9@Xjnuq`<6{rO2SLsZld6B
z9$f2R>ZCV~N}Z_dxq|CV;2uWhT>ZRL@`|>|!0BAgfwXu@oW=a|f+lh0oz+O$aC@E7
z;E$!nNg|V^{(lG%KKx?KkK4^vAU*pV4V`(BJHM7RiMzv70!w(;j$$CgAYHkK7?mII
z8iOf>Q27PN%)JyBq_ff$zvyzTSHFkUt_oH5L;s5;SD(yiKaGA8?O+Y#M7V&`v2^`#
z>HlJEOq2R2(T}3pY!Cw#OBfwK$aCN4!SXq55PHUH&G&}~lh6Nh2wUYEGG%WsOZ{2*
zu4`b7>n%@#=r!QXd(TgCzOkNIe05Js%u>B>$A!^;6i3qt&V+g5
zQw`m%Z2Ccd)&1dpS(oa^%P#u^pEQ*Ouv1i@G=;$y1Q!&?F5YmP!}WVageYwfWFrbp?RtKL1J_4R}WgD0+fsL2CdP+Q<;%iD=e5e3(;>a3iki)@72<>@fv?ZQ~$1
zc&~d*>Sgfb!$;a>Pno^)A%XU$bzH2Qo_p@D)x+w&)P?&@vdB@|I;mT`d}`rOPm}JQ
z^1IbN7f(QwF;J4A8Ciq588{%~b0M)DUa^o&0`Ziq1POg?-Q`^iOxIVFhS5+B;`qzi
zXQKX}PYIg6;p+AZJ)B`Ro-wUk#$A^z!)CnKWjN89PZmfgqWoHS3oyMlGjb^M8(-=w
zJzR1Nfsu0SA+<%{?xcrJZ4dF7{OmHzy>Iau%n%#+TbBnws2dTeRomHMJ<8MQVPC@Z
zh{Xo8c6B1V@L1&t@@K-JSmBd7`iGaT*hjQ@E{BXV1s)M>bG^#bcS(@B^=V~=mmjS@
zijErTt?gd_!Na!5!E4QwoHhRiW8amny7K(IAUusT(|OAsH4T-}nA~;5;8FdpycX(j
z5hYX_G3HoeYC9thxvnxQ`sjzu=+qUdPMxdgnWr1OX^_+@QZ;H+_?<8I%%!!>de##f
z%F{0O(&!cey>JKrGm5phY`8BGhL03@3=%&PZ`rp{%zwIvMVO*Jz+qR(@@c_Mj<|J;
zFzh2637L47kJjgcI?bvETk1Y3w(u>F^(s1ZMJy@?(dx9VT_r+*f2x6sudaz1b=1UI
z^r84(8{9hXN|TUs3;w3oK`GsT@IBUqZ9d&*d;Pp=#pYSdhFxg1XCi1&t^8D`RNZ$Z|rIq2n
z#JG9Ec3Bi-8^$@~J00*q`5CL?aMP_M|CF7N!5wBLj*ofow=~V|w$`Jqq1aE%zgC3r
zvY4M4TQ~23J=NMDNV*VwiDHpqnfep|*TeeN1q!t}C@RnR7>hjYIyOd6T;w?E4}jK4
zTa@in@xj|9qMA3vTx;_9;|}(9NU2a)0DES~3O3|3lzuKDvb}ARySavGg1Hur#>V3_A1N&bCHxe*?x8lssChJCE2J%mwL^`Nm
zCEqtf48Y#A6)KRHSSjv!b|Y&-C>8juq&HJDwk}>ep}IExbgy#~rdbYhsVguo;A~)X
z={rBwSn$M3fng|lBWUG0g9L5ks%NydlfSu5_HaqA%{Dw-HGr-1p%u?Ix-B75XKmBW
zNTZ>9-mZ;H#x;HyAx12UU^%%%O;V2_a~rSDe!U&Ab)WR`?Fp60sP0U=tDk$-H{9+y?{g*XokTFhNCf%n_=i{N
z7DGR7JG+sx?cp1#x=Fy*{j#(Sg|4-0B1<9_mpdOs;Os_yrnyQ8ZPip1jCOK15)lv&
zC7seFo}&LDe+b6B1dl!W-G+sm?Bs{?rWYi~#~$gWT>OT@jju?nSYWw)8i&wO
zVSgO9>HU6IzNp}=&k9Q#%sZ*cgSTQg#l>$Lg?^A*U&GtEnOcC-6CS`Xm3^kBgUDe2
zGJ>2n!8XqBHMAS8c$;_|8}RLdEjS{vb2pJ4iRdJyNNvbIjk2*y&JRN!bPd+1t&OZe
zwGD@UXeYZ14q+EztT@q{qOW_u#SD3P2Y3D)PxyG=>Dz(dPWdNn0vzxedbCu$zey<+2``FJoqiab=q~l=g
zBmN5Pqa7hh`{wfdv3=hZhZ3u=^v9z7mqnWkCT`}oZp`Hrjb+4DJuT3Sqjx-l;G+F3
znJ5zSByW4pwtdoE;vZ$%?XfPP{utp+l>8J>gpIPT^pTNHBjSn8#^tW{u?y6+)
zFHlennd&7%Sst#TKac%QYoqInf9I6GI4pCKy5ChG
zA&gC@S(|109`nx2wGq|2-XHcE8*qno;IFV4Y#MQLASu76RjU?UR=Io6BwP<(;DeGx
z4CZD4>(_dx8RcI}lyQR>!N(7N93xcEV@`|-s?dW48Eil^W#fWxQ_6kR4W=HiWAd}e
z(3H~UJ7kB9E89>D%%)3mP0bkbTlQGNIdh*-y(6tZ6uoPiMj6tC7NyN``1&7dNY>r88c)=2De)63TBws!f
z6SuInzvnXYm3P#92kHRZ%bkCUHcx)Z$*&c~v%BNjedw?yl_Y8V1vgi7bQc;%dpug3
zaCL7$$SfWA&^gEXgvp`y#!Y)-&*Vk)X0@OuD^85cOI_KOt)77d%la#5|B=1VuU0$i
z=qSH7KjtMqey}B8Mrx6Uofi=pK72dt`wMkzIiO!4A2;gz!$*ClsY-`>&iA11n>Yu?
zYwd}K(S5UoxVUR%Ypd15k)q+a=5W$)^~^$b+s++6OE@FN{$+%k$9=iak8^PUvOz@i
zhNV0pt-|3h)fhom~oV6^m9f#5uor6zCQ$ytriNIJNyS#9VP1PTB8luN_rc}mrA<#~ZV1ldN0f1U}>QOO23v!G3L
zy3Lx-0w$7m_KIF^-JQCu?qRVo>E`gsNTpO5fJP9EFq
zum+=G6X4iWdBYNG2r6G#q=u%(GD*A4?74Q+8|nNf=qwJdLef`(s$A;f@{f(bI`%=y
zV*dwu?*Y}+*X@g9<*$g?uz-LHf`W+Bdr+E)bV7%ybV895dcclIlMX?82?R)_OIHz4
zdJP@K03m_U5?UbS?%@AB-#ufTao#u18~43??#&p{B<#KRDs#;>>u)Mory+B|O!Tq5cW>TH^b!&8S4#or2=QRM<|YV}Bkw9i_{zE=J-ekDbo
z_nI2#j>P681<}bgP?yCNBPK=D?K|G?5M2d8xk8z9NlS;2J4>;r$khJfXs%i(HFFa~=dBR7^@#zvK
z{!OLWG$UFk|7a*u@*zb!0+M5CRw&2utO%HgQTB9EWL3iRsztkm5_yRrYw}i{i_`?(
z)NZzKK>>6Ip`~9}@veS$?m=~pbZMYZP+6UHg^BIz&)CH4*>$sEpXz8HDO@_P-@h#h
zct|tHvJ5xuMmnNGyzb}mbQ~eOG_cA)>V_ej@21WaM>Mj2_TGZnM)xFIba^$L_JJUi
zFej;&(tInz0u*g~1R@r?5Oi}*c}>u9D9}xq@)~z()`u&pRb)$=85FVws^UBC>$07W
z$$;PE#EHj_j*bqeZ*K!hWB8uwrmnBAm{UvZcNRxDM*a@nITPTk0$8N%dp<@0Cf}|(
znZNB@H7SOoLqHG@5LbiayKT?V?&Vy8f7fhzt=mHby%WoZOl6x*@-hMaU98#{qaa;6
z$*_R|^1SExx~rF6@)%xw0X^hS{M-=HRWz??cur@1DZneZlOWZ7S21PB%`LH-mS#OK
z&EBjTZhfBTX8F{-vMq%xOnj8~G$ACy7GWz>=zQU(af+=%Vco@v#2=MAaqe*6
z_QGgV6{xoLTIP5y5Rf!-E1myx)OYwNRjeC`&39;dr|2=c2sAG*eQalj5%5rgljt*1
zn<=Xe2TTqJy2X08JM2R;p#0A!uwpN)m!o{@;9N=FR$muk0g1_5g@i}T~-1kgkX#Ou{mNUMYu*L{43^~n=r#EAx
z<$~@9!U6iu=gsaYkhf&$+|{#XfZw=V!FF)Ikqqd!W|Cp;Kv2b6!IKZjgH^kQXNo5Q
zOb`E>^mZ`n3Ds!RLt*`ORX7q5~USr=2Pm)(3`+!;AXtcGu0W&4YN?yvTgn8v#8Mv0f8-^A&fRC(b+m`tT%;{Md?_
z5%Lhwb~a5wzR&OET}&?D8FcM1uq5kKAE1YdAId%QKg`_Qwl+bW=wD_j8t%L@M^f$m
zb?%sMR2^5j1+<|?P-qC9=GPW)SpB5f`%-A=3*~Um6zJfh340N6GB|F(^zA88MP;ex
z)hmZ;1<7ZPo$3di|1V!YFJT2D=oXHUu#>de(OLoNX&}e=`BBl}TV!$d&sIS5T;uSU
zX-Ps8Pr%DOzC$>U3Vwaba4E4n2y^o`4^jDojkRvV5^^e0f&OPfK
zcrp<~xlb7f(w}m_$qgM9kUaWFlf8_zfwPP*Xm4DOdB40rG4F;^2CACEhRK|rPrD8;oIqnYF!$1yp#_8|e+PrQjZl#_P37c5lbHX@~Ua}T~MUB^{6=G^d!zt@d6RQe@smD
zrGBM75$Bk~>G`C=wHHh?0jrN6)cnLpagBQ8_$|=mvDwwQhm^3dVTPXuCf?Q-Be?U<
z4LurN=<4q*Sy!dU$j8n^M#)Rv;wdr0?Zzmqnfk=wKN!ADH`v9{TY#-wI%?X-JNg8V
z8ZkO5v35N;2dSs3)ra10Rtu3=Gl<@I4HpC$RaV|Ks}Sld^W1gYF3;f8=H)QVk9HI3
zvsA<12VyE>o~GVzo;}IU-
z&G?=EVqI7in)84)#w(?Uj}cy_Cs$*kGg1Gbb}{svmwe2f%_sfvnx+YSc{=-43=y6
za?HaO&-XWB1{bXQ$2Q7qf#6lo%YIyjbx!^3W(vPoUyq)wN6tFJyb$i>?tw!kw`?B=+&0MmZtiV@$WAEc-MZw26(r
z4KZ(E#NCdI)$d%?x-%OYEWhStv6+O{XDpz08)XQb^xOb
zl4`g1Nh}Q6DXibFOk9OZI1#$Vd;G;(xoXC4;8nRheAc~EOw_rZeQxeOc1>J8-kP}Z
zmQ{_1N3yogx5`VoNQZ6NT-+$?*=E6kqgp+k9w{ju33-p+OC4GR_*H_AI$P{gWLE&*
zbz-s0JjDJ;nW<_{;N=1NiQ7@#MvgHEaeW(}C5i5K|LX;W=oy4Y>C%f>evOtfbB|UK
zn%N(r74S0UhTmkk2Qu7VIJSO?uls7j@X*BLO_}SzsEngx&IUl58$OisvKkQ{9zKj8
zHB+z9E{?pcSi}aRswk}W&A-XJpIW?~m{
zl4O`_(4$#BCEc8M#6hxP(thdhPMb+Q6*d!lD*WxabQl(h!iCw|sJxXrtig80Y2s~S
zxzBRYI>9qRdm*iG5f>HD2R7yzXn6mS6i9ZN-JC~fz7i?1KY~!*Pwy)~^4+Z58+gOM
zo0cD8q>bh<_dH13?hlh)8n#~7Nu(GX85xydIeQ5&9lcPMm!}pCC$Pf(Rx;4ku4e(K
zm0~qvo*7pnv5_WWmCu29xO78*$$K{EB+tA(Gkb4o`veauDk-l01;9
zoFMB>%#Tc!MJZF>_LL}x{AjdpDidEx@9Lkd-vMv$sc-ydVp3$}W|Y4xQ@Rtw?JzVc
z2v>*ie9S#*YDxrBH)U;XZwiSSB=-sy?xt&^5BlvqyLWS5!TmD!IVSv~sWL$n!ka
zk4IicQSm5Ul|
z<PLFOiCXAxZY&pfj=Kz`=FK}Z^E|r
zq}(SNtrbHhv3#A5qHcL5-fP&b&H|nB{m)msvb3DuejbsH;Z|ZH^yQYF40P||{@C||
z_=*U8Q@F_V>lFhtB21d)FfZYScX2?K!TMywahb@o0X}}GTHOs7q&+UHFOx93o36;w
zSSF@G25^JpY5NzCi?0!$_>>+JPxL(Q?}+cRl=awp=agy|;B^qWpJv`0nOf_meNQAn
zyytHeik^$_Djc9hPB8$HqDL2?8`VyBF>^k`>5o2#5yneW+Imsk6BX|Ll7j;S`GAui
zaWx8(yM!MdH3NQdu>L8@pu%ytkH1aN_vr6FMNQqw$UOx;eKg2@(CuQ+nRjJ>h2^~~
z6po=VnZ*Lc+Is=QJy5eAJeb)O0yZ$`EIfa4JJ!hw3Y%YfQoPfyN&VgaibHnmOu${H
z=X`%J{_{p4GuE!Nlv%Rgm;Jodwu!lUp-AKI!;z8JW`RS9pCk1FPRjx8qq=LQPEJk(
z1=i{SceuxZ6`1Morc_mVLp#G#yncsTdTsw`UmSU1r$=i}l->Jm9iN(f0=#*)=8$<$y`Dt6Q|PF5%NK%-I3M4NF;y2M+Fh4FX>z&B;QdJvs;8G%X(^J
z_1PDgMg^y&lNXnifKyGD91+hTcf*DfAQ{i)xt$gOH^IL1G5YFHJv*a3rxZ-sX(k7;
z%K~S3uM2R9(X3HZpXNaT{=|oa`#r7!dMpm@Yih4Qt+Kc9K(?k|kGfk%RGYX5AeM-V
zic$zjW-l*fcKG4XQg5le03b=tA50J)=mO?QEcfbWvb_pDQf9+}OE&NUB+&0e%3&rI
zw-bYqz=9?K!y?H#DzaJg(p~XO3@{Qk#?Bw=F)@d9QrpZDw~1yyqjA!xf{41I-JZ-Q
z6ngJ|a&odP;rrRR_`xi{OH2-TB_t{s6k`aG*Ww}$U}^vz_1rT}PVT+$#rIaw|Lon<
z01}PDK9~k;Xa(!wH;t$tCjn#`U^8&Z=x6gvs2duX7h)QALx4pr8Xf(?3Sh^?0!Ndr
zogEN`8Yw&XIXgZ+x!|NJ7lQ$cW=k>4B_I~v889&_fA@Dx7r<$`BZjM}s6Z7I^hP7h
zWO{>#WZy?bb(~Kgq9Jk89y8w&bZL)k?cr$NQgrzI6}qL%xbpD~g_S7&-YZo=9Hw1WjPT=hNVYtB$}a8KFW$=+=Cr;7kfCDROy-ji$Wgjss>_
zBbtttjdX%KS@$XiSwAbo#hjy8$!V_{MTFY?WH(iJ&NpV^I>_W=qN@~n0bH*qAPS$U
zuvl98aV7po!K`Uz`f3
zyAe#rP6;PabnicoWDH)^kh3#ps0OpNewaQ#E#-Q$L}Prmrd3duhe=#S%D0*xK6Ut-
z-p{&wH#iRAq)xR)i)LS1`@#CPU?}2+G|QFoeHu1XFDk~I*Yf|-pkd=XCR~HNEZ{+Y
z7aZ9VNcM~iDEkyLX69RU;Pr!2CYN!Zq7&7tY&gZ3)Ae_4Y*d~as+AKVful83jQRO?
z#k7MLKvuy$I8QcH20&l1@sxL5Nn4+`8pXmFt6;b5ZKUR>W1sFe%AVTgNsadj^`>aV6uajP+?W?z)5NH8%s1`eOAjgQk#
zce41o9-Py<7BlP3rt@ugN&HyTfegRzhdu{C_OY?+IqP;}l{1XK3yVL+1|S^Wf6h4U
zFcl1FCkYLq5Udu
z$3>U;u%BB#T$Ez8aO$ax3eK6IX$$biOL7(8CR~-vXjPe7<&;*uHX_aBpz-r%t=#Q1
z-_GDnO8pj^Kt^Zm50t}y{=N?IG!FGr-;wbW$#|n=%Cl`Zvl*sb&oZXx*p2{Y-LUa<
zyVf_{&nx-vqbgOrHQ~$w3n;{`9X+MsU{u>WLuOJUi@mBly94S5oe>|3xa!vdAW=EU
z{h=4nqV;}aEH|1W*)RQJHGr9^{4e@ex@Ou19B+R5A#Sy9P(|J3hW&nv_C|0dBoDw$4MIr|L&3u~#E7h>STXXa9Z}8
z1s~rt+%blss5P
z^}z-MrTH>BrN#-+JsqUe7AU}Y%SMQ$p-qk#-RQzP{
zAS#(d%vOU}N@OHQ=FJ;H#K!aU=&4L1W^q-9Lk_N1{#Hi-wzHvt@D5dA-EZ!6u@GT(
z@;J@4epN;YVvWDuA9fu;oJ2@t@GGx@9dZZZUFZg3=El${wACC@6;+
zCwz~jl~!BFyK!$;%{h*~k_$h;x(P$^J=`-<*g_VM)>NqIbaND6M(=|QDm@1{-i@7F
z`C=orDb%GVay-eKr}w70O#M-ZahE734w|%h)*sa1h}X(rwc5)Ur&>{01pHUzY=wfi
zP6!7)Ek)8}QMPQ3+aWFcU1u^21={>nPpQMg?bse=0YLBFUHw|PR)?)GTbyQZgY8jv
z=!YAT2~H#vc}vx%Z1M@7?1D`U%Tn3z$H`a)uh{o$?EXU~zUJTL*~0`{rp|e;HY2L_
z`t0S(XOODBF1H3&Zn8N{1oTQ?mjFlGwpQjokfIIogLjw?z73V9r<;3eTp&v_M06qUv)jO3*`)X!(A1KG>w$Ki71IJEd7zgKV)BYE)6du^MAbDV
zjc;VGcLivQ_e!f@=pLO3=H^~&{@$|?BNxA+kE1Ik
z*iON|fsmnsj?S}*VE#dC-ndA^A=Pz5;)IpcWT6hXI&v=T&M(n?70Wzr`PMiT=Fu
zdb?CznTkQ97?_MrRIOV5fbzLLM9CT}&nkVSnHL^|U8m=JrYZxRhHav%Ee^$qb6$EDT7}ReL~@0O
zzRr&t>Nf0+V=i~H2kdCds37~)^OK_dBvN4*3M?jJ*P+sRb26`#E#jMl=kv9ipLh5O+llmqaytqc?)j^MN#i9UMt^*=f
zMYK2><98sHV5C5Mo#tM(U4I?1eFt-z!3UpXQLyU@e6u=%hAep-@naF{kF+Wt((kCB
zZ4K}308h5gbI~Q#=Q6bGTL^o(A}AYR+fV3c#na&-YCaP96~QD*zEOhnAT|amVf}8z
zEBk&5Bur{zxbj(AWixlar?}UgXuR_Xs`$Fl`uulajtpwI#+h>h;aHlGW;qNRnlLc~
zsME&Ag^zz9tp99VSc$gEfCi*kS2@<=w`*c+EIo>sk{TZgLBhQy0d^s>w<*qhwM2PA
zlG)|K_@1a+MA*lVm%H&te_ldeYR?+03QD#+A(cpyjJT8&Q0Y2|EoO5nziTuVbf*Sl
z4(qm^`wNt7wjxw!ryY58;*0{uyb5JAa)MRD$a0+$>{Jcuzo>z_+eIQCK?Fw1c!X5a
zg{eA)Y>3PJ@Z+*PFACS(6`soGIDki%ffrt`Doa}QY!;((U5
z0R2n99`dP1B$rv$s6*qOU1SZuEfCfgGjLP=5P!HBVs7}@`_GwGodZ2T+TuWjU}#Zw
zuxa*sqZ^TP1b>$5H2OWW<-tNHKQgMH#x{j2^iafZ46=yh6UAWtTi3Mea6W0wt3)Cu
zLT68w$Bo}V2Zb64jiGq;SFnv^O168|>DFY4jg6Z`=p#Lm
zecmsA;AU{q65U5ES09C!I!YmX5X3v5b(4<4C0t4c*t1JFv&gnS34Sx!34@#zZnMlj
zw%o<>gAu7gQ7x&ij~J82UD^4;!qiBK;2n^%Jw;S;L)P5>
z;@DCuc5Q^elM|BvEh|Nww)e(tl_Cgmto!VCp!1GxggKWk{TjI|mwuH_m3rDWNa>yH
zH$K!=aTG?HOZE0i)-MuPSZ-Jt$vcop(JZo!c9Up7Cao@ewKafsW;4#M3XQicylE%=
z0U_ujl$ISjb<=Qq6A9I@l#SgtF^bn10g(ZO0j*a-l#I0P)DdUpz5qExv+IP%6^Pm1
z(rRpM!g1m1ZEs;efzf4^J(G#Mn|i|L)%rrlQ#hAvF>hV*5Tb^PAtrFrp(WN~Y_2n{
z`%stM7`a-zCbcM*^rTqJNPx?hE%urO06$u=BXB}jN~pJg-XY
zU9(&Y3DnvFiHW;zG0oy^cyMQoD2pkP`H5!A5!Y1O#tj}yyJ*m
zOZfaw%v02hkG4QDu#
zs(UXk6)J)1T*~pgMYYHWO)R|R3+Fp~WpO=TDHMYU%{8_3@&Q8!^VLH&j=L*c6=o(m
z+j6+rnG^FDdZvys*h5A^MO%)#piK61uku`z_g;lRCEC3Wqsg4N?mo$d2u|r<@JbmY
zBtkz5n4U6z)?N%->Tik%xxYwDlNlw7V|4`9Q)`sk?O4~ADH3@p$GeU>P-Da%h|O6*
zuOFroM++vuYg*bsyrbsmJ6Cif*g-PJQD+E@C?I(?ABIJFN?W~--de3=?Z$!t}(0AbRq=uOF*9{z-!A4H2ho?5f
za|(dt&M(TS;qxQ5Nl~Li{<9Y`Czf&+#~V0gVgCRhPq{Xo`G6b`xz+#D{H@?rsSm3;xs}G6`slag
z;`+2j4JHUrfz8i{_0;Nt%$;T`zOW1Hz5#HAD{%m7yaNET&xoXKI9a!uXEo7azFbFt
z)395^FIm^5m+Ix5xK#7_yDib@lepmTMKhf>m8nPKxDF>3*vdea#!VBggd;vlcF0C!^UEl4UCY$#-paxpZG;DhxZIg8exKDME9?+ny`rjh*KYIk93eG(td&&pLZ
zgPO{HBPfr%7+|N-_hPdW+OAm(Hd=o(ep^NMGOSK}Q7_~46fxW2Wzb*w=z(^T`Yfr<
zAoQW7aMRQQ8DuS$wZZU$*Sh0t1IvO$DYwCmweI!YfHA_bMyigyc~kJSH0>&W&`Ot(
z|0>3A
zZ2TtGZrYZkZ((cLVwHnCXq@9-XnR*hUJ<#XgnWeNubj(QK(4kHcYK^+Wm&6-iHD;_
zpnSGm+2fwKd*{E&!{(4YK!C&}&q2x$gaj0OE8wwaL2+>f^8qGA(~=bB_fj`lNW-$b
zcbG*R%p8DFVg^^js}!aAG)CGK?4r^jwd(0`uI_@NAle(j&A5faCH##k@`t_nhsKJ<
zpt^D$Foat_BKj?+SSIHcIDT}SDyK-+fGn9|nuVf
zsnj9fNrUf0ZkVB95E-!%xK;t6E`1#3fYWUA8r=0nn$009RW9alP6k?LoB6N39+
zxGhtrZbNw724mYH2HSYZ!Y6xkF0MVIXFRRb3foHEY2V>>laL`EhS7G}X@vMFN>o#?
zAD4Pay7ALgG3l;W&KSH7sYeiFy62oSWYqErY@u4{lBT
z9bdc~=1(x}F4Zwg-W@CZF}yW3&M|^%%kRM0-g8o^p(6l=0Vhcd1|VHO1$Dd%|3+oVlnJ9^!5%H<5^b
ziYqhI;~1&L`CH@{2H(-=J(^ZHDG-=hTG~y4k*>l&(V??`+yjRUmxmT|At-2im_#7u
zN`zpYQsT!%%-NIhoO+(1Tr>O!#eBtwi67w}UPpN^J)1cj50A^;4Lb_$_&}D(!0S;n
z7U6I`-hz$iitRs)>HSd~=x&|*$mF^)eRA~%{F#c3JzIEJ0K(&BaNefk-ouKRhP^G`
z!8E^0ZID^p&xKq?cvtUTo`zgFU_P8o=_}i_8
z5=ORX@F0l;~ZsVeFVg;L-(J1@9pcfW)&MQ=$j
z+EGV-LDX`vQPaj^o!ez{
zqQbO|i^3Jb^$ej+@TimZSw^}yt$7)GQII>Ef-&fac@3={`Ucr&MYhxKx}m8jb|M>g
zIvvUqM!Uf^G+qt;5bG#oV3-T}CgAtCxL|=cCcrm7%oDw3Xj6>)`?u#<`&G9E3Oo~W
zFzWNW9PVnAtp(5e&919ZptkBMN!DAV2bmtrTGdn2=D57>r)m2HH_(YZt09DXo_tZW
zugl*(MT{D)Cr-O>AM$TG!=G-n7`9hvv2(3^urc+d+7)i)F8&%w!xHC0aXfEm0
z>>1pb^+t!#xChOh+!d9L@N<4-Ix&dBR7BYa@*44~LTJhbRT;os#J~`@r9tkK<76D3
z@C6CR4*TbCR!k3GU0!_c7XXU_Kj|HUa4g#aquZ~hnlXMB$5zT3;LwTHaBPSvUu)`q
zN>@~rGxPlB{muP7EMmL)#RK7JHpO0nr9<29tE=eIqpTyZwf<`D}~8`ht3KBWNihrSQYq57KwJ0*$+An`eZ5?Xn+Q
z1sK}~fO=nGP7n;CN?CtF=*^K0`c)D&;)!SI@_jO&AxUSVXen?P(&O~rPV5Z2#
zcdfZ&vdu;CzE!^UOY-`$L0-jqR`tD@z&cB47F;=L%$xcPcyP)~IzOx8b;)8(
zTh+QYMVMbbRYupEIW4ol_A(DiM+M~=qY{>z+1deyVngmO(jM@r(MP5~FPa4Nu7j7M
zfVbq!eW0VK9I5VlRz;pad3UOa1^CGU^^oG9d>Rte`G^Yt)#Z&9*|zqG&7Ysh?D5p1
z!o}GtYqt67iM4C=AM#qrYVa||om$DIHAkz`O$k~jY5sSd0W42K_L^oZY&p9myF2{)
zVMRD-RO&my(t2!Ta;i$|)&awHTj#x#Tt!|=vt$04dn`Hz)?8&Gn>$|P)cDFqGwy{)
z5}OpUqSbZXseg9U9eWDCIqu8z7i0;pstFWD&6>gtQC-}KgHn}H8VcmtYpq%C)vw6)
z*H$mc#j>lv*GC8JtZC##n-YZmB8zza!omHwt7pwhgv{2j>^QThEjPe$zN~dU
zT0H~#&Ln#O8fz^eT|wr*;M4P+$IOIHwq5ypKls&A**8M5^25d8=7n{S5dmr+{M{ba
zGrnOv=+;g5-%?qrpVE4aX|?KAq^6T_wh_#-rM(?nxRFCW
z?h!1OFRQ~m#!kaCONXWg)zgDBOSLeC19Hj60A&M`Bj!(;Crz2aVLb9OU{|J6;^WOW
z*3_x8s%2sQ%n;;qTH%9q_Aq0ofC|1@ryp9pgWY1bF{>5n3$yk{PMWqc#v$A($X-=t
z!^ib+cxS!sxU;RA8nT7PjZ=urR9v?CdYXjkBS2X7AvL$bf=^0sq0`JO^_D+ls@MBz
zPiZr#GE!y&hO)Mt2n`$CYwF3|86mp=TJD__nJc+lDY4@mk>Xo27|1*58w>;4m11EC
zf36Ch;@T1*GL)?!VtyQ?h?ri|>y2d;NA#m3O;9cxEU7Tk?NYAQ0bfehIHws{Z;BP}h5R*gHUl#X+Q1
zKCn_jQW=z1rnaoPE*<5lO(#C3ZB;gp+OaV+U72A#gwJJYcg$|S6$|k{c9JoA7^7Il
zJDJTI8EU6;Z{x!8a;{_A33eKR${PZj#`;J~W*LnLBuhKWucjEO@
z4&)t>0)Da!?~!6udd~RDXnxo7j$Z7}138EztCked{PUXjf3M+oKCPXbs(e(_Wgd&8
z;e&DmtQIiIVrui8@ldZ#n%jI9fsPXLtS6JgJKeKxr|)5EL^pXAQldJ9Tc1PsA1d~NW;EKn7JD5dCLbvB0FEE&zCN`98+YACi(AKTYso-cujV_ym@6~
zd*zl$P_gRPt?slbSy1SrOE^#ea0M=Ts%DS0zU|`Xd?|D)b%u=en=B?HWmA=zm^dJ<
zkzAyETGyahAnJ1Qg>Y_VC6@azlf!u)hcU9-Ls|&o8g6=JIe5Fw3bgl>hGEf(Zy3&o
zr6}rde$xbh;DVn@+5XsY(XVh1Ctyr`-yTBvhVU_r9)lbiVXlBSX`+761XxM%kCVYm
z#)!=!Zp3a6sYdYElMNc)Xd%qKYGK2@$*Xy`$%`1!Uh&Mf`1a*-gH}!bS#R2Qgnqph
z0u#J5yH159vh}}_zz{Zr1J#jMlaPtUBWf-I&T7sRQWlDjj4dXOD}>T}FjC(WEmw(V
z^?P$ERC4q*wbK%py;G{HBVVmrK@$PrbJbz3ufsT1)#vCit8Vx>EaUk6Hp|cp0cAr`
zS*>W`FAB)1#Iz!z+wy~xZ}LfIyNOm*Kd&A1Jfsk&vlq2DIjCSC?J`nAzHVLJi~H;w
zym+ymK8_KmML~#b1hL<(HI!qWp2(kF*b8IW1>5xqQY8UM@YSq0|wmJu=kU
z+by6Tu(2oQrRPk~#tZx`(eZZK=o-d=Fxy`O
zSR1Hx%7U=K0wVo{p_Im0+Gx(p+VF)ZP4xL=)^K(VdJrfbM_csNx}FNECv$J_J-~Ag
z-J{}9F+Fcd1S)m`1|EhzWXqpk4RM@K5g@KDZ_y7nkaQNngUBBSP1Bslj~;EkQCx$T
zdTmo?DlRViFc>oujJOs+(l=`b)p1;DzMrEj)2=k)p+t0Cb#r==RqyWsQx2~0bRIC
zP;sJ~mHlEc(K?+nT9*<0P2w{tUcW$xJ}hzP*U{zmXT9434|xKUyy^Uoo#~XiF^=WS
z2bp?C_l;4DfuehJ2?18~sGn>{B*eBJ#PdABTg|7R3iTuXboj>WAY-)*+AQ1}v+kI?
zaMvN&6&FPYe5npbkzC}^P!zI_Zb>pdq-BZi(
zew{iQjhdI3%mWwB^C=G0dZ;@%r_WPK#z%~eP!Ds>=KWZr{XSk>DDr=jwyCAsFoZB(
zsTcvyLBFi%Tf^u?c+8tIZm~vlwSJ^{E&@dGtCAR%In0!?&dXrps{l&C5_1+eif{IZ
z|L`WeUs5B!Vh`b1r*PCgI%MfVqfj*2v+y=(Bn?$U=~so1kDlfs%nm75#GE~XxLm6p
z-k3vsDxP*gN@bJ&$~KzWTWs5X?ZcLY&2DnVmAawooeN&|$Og$qphDH`X9-m+xUyX5
zcjH-(3AlOrPc5WL_OgN4lXho^7C%LBMkiVOWKp!JaH`!HreU2-$^{8
zPf^5-KZ4dyNcmr+vHL>SIf8MmHo{_gWWPb6-o;NV)08EueCt;q`lHFAyt(jOeX1B?
zF)WFj{A0!B{-`)R{=wijX-jwTFM>=hJ2D9?{?7#zXvd*M2HT_Q&5hhk8
zfI1nk|4J58=ORNWc^ecsc7nE5Lh36FTgQzB<=P982xhVKlAy{7?%tzs93epSF^s+G
zU^E7(0(c$aJ~wVe_SAS!H#bAa5J&u*lCkwk;V-6Bf;@x~88T&UyUJ;U9XZTv9$NV+
zf-s8St`d$#rvUQUFb=rQO#6?-@bcf>cKM9`|9;?^?;dXJgJ&nlLCkF|L&%Ae_j_m8
zburWJb2`MbhzE32D=n>%eG_90_Il=g36Qy}?#fGQ_il3|@((Qi1s(kuty(i*VXH<8
zBO!vvSY%zOjl{O`EdahrQkeyO&P5W39e&rbv)j7rGO{szLO4)N5mM^Xu`fVfof_o<
zc&g9@`5SUIbm#LzrN<7-G*rpMbdAYEY`bUob2-r;S7=H~ISybEo6?M+mg6=B$l
zo|9Q06-#+hsnDpN$^ytS-hm>5R+fcBgX+c>zNnm6qZQNFNyDa@Vs4?%J~nVDrQ?Dz
z0S~GctxOL~v&bIZOGI6fa_8h-2)k8yZOAg1@7SGXjDq-f<`}FA5WSjb;o#b}V}L>a
zkN8zPMxIOY2V^1&5735aXC5^#mFGHbkMODQn)%>-y>
zfHrV6zi-zu+9tc9pcE6UIH7d7hCQ6H*zVn#zWuS(8efcY(gf*lvhcP7QD$G_{wZP1
z)9_Y3U9lk!c_StBN6uz9Qr!OSPzT=yPWjYAeLyY5^A)(QosGS@=|P4V7KbhUlZbMD&YE!x06x=O9nFqe!qjY
zV+#AJF(l2|5FkWKR@l2pr#D_ow;kBW<+m6fZ&KkFgVS#YD;4kR#tZhS9^-nl0i1L>
zZEaEEPb}l1{1=Ifyx^cKsR2)L^@G=uDcwiG49!Xvk`gc`N-A$f>YEmzVtFeb%kN7$
z#fRGpENM~D=NX=>5iC?8JnkV$?Ctd>bF{YHh@!yHL0h=S=5?RfEgRdw0pGpw3{a&P
z7`FQ!v~z$nz#r(GH4fB|KcJpGf_>E+D*1`~N)vYtI5GIstr*>F+W_gC0jY0H&$Sok
z`s2RFkAbTjwD>C*W~Fk+$6JDn7rKlWLuP@e%8rD8O36`i3gx>nVpm(BojMDgp4QPh
z`)8ru*{B*8*$ew3hj!PXBlcO;JXNIT3eB@GV|`mz)wnAud&(lQ?h+7P&Pag;xCNzt
zb=7~udQTKk5<7#zF;qe=ug*Z1Kya>oM98j7lyE;l4fD0fI;}Xqkp!NadQF@j<1S0d
zP(ff9cgcw1ChAVN0>N+RUE}vTp3rth)oSEJFuS)}(J(g5dibBCE&Z>%$aX*5-@L8Xc4zV4{$sA#bo~Hzau4vCf&Ui2
zGD`kmr-T0o^4|YnL*K8Jr&O-}1Ox^$r2h`=Ar^!A6;O>^`phQ{7ZxyVZ;1Cmyu8Zl
zT!R{^a`r+yTe!vE7nfUm1C~j~rXyBxD#0EF_}B#;`+?GVu-~BqH$aUc+Ms&5pZg1{
zlTE|`~7kJ`vuwP0Q3d6w7qzQ9$Sr^eZ>Uc5mUv7OsyYgVsew<;CC_olC
zV1^2mjXon>4--BN-h%|ge{f&MNk;+`giH_0!^I99J(hxt0%@lQQ7`>jXQfvasGJa-
zbX%JfIAy@5v{W=!aaayW69wQUDk>P$qaa%j#LMI}lBlt2F^c=NIAFZ<<4(CAX*;=5
zVHt>t0eH6ipR&dOPIdTKNJ;-k4EMf&$E^HuXb^2amb#v;L+n-MT#r;RtzAn?pv@m=
z<>IDu((2P4tbQ_YyoPNI?Vx*lrrG8(8-I9!*$dt43W{)oj#-Ukdc%^(+oLCIbl<$9
z=Bo=3cs5>>dJ7VX*xKcu#ag733f_l8>0Sn^n2#d>`sX6BxZ8|P+Rqj?O$K>ev6h(CJ4Ac8PYa8C{
zj3r#As&LXvwPXo$)Q#u!8T6^iiB==6o2seqkR8TGk7%3*K&I?K4#`0u>vv9e7eM^`c}ZLe?Kb5ABcuzR`O*=Ad0&K*956Oo#%jw8rPKjx0Zo30x+KMk*Wa+=(7kojc)f$vpCxMtsQ
z^8|$--wH)Cohawd-$vZ~9}7Kq>Eqk}PY2Rw?0VyvxAJ7B2gubWe5~4E7&xW}7XK_Y
z`B$UITbf!Td*k4>uwVDyZ0hB$ub6h=|?c$s6&S!G=B|2N3AHFyk_H9e8L)HrkwQCG>
z+*2(Dq|cxI{QT04&&J=o5_f9z_^5B&v}a={@7>^tU$fmSU)>bFWBARd`pXHc2ez~R
zznvYYw&BIR?2flFCu95H9(!v8bbyLytCGXQ>jwbF!l>hY^6PVa
zeatG>H@2qoyL-}ntlHh|IN^O?0!9tuhT*{vq8wKtNKUEX{l>Z
zS!6=5pGio1GJj2EmHg`e-{fT3%QsYARkJFZ*5?~{NO}9!!i>YUe~Ru-oYMz(?sLBe
zr+&u}KCjP#r>%49OVw}3-}SEkSfCbXKRNqcd*bw1uUJc&+H7NgyX})FFLwJf{|kfH
z@vBC2R62zZOZ@-ab@}VV@Uu%ES{vGB-#ys2^>yW^^Z5k^F^+5Q$BXZ1e!cVcGggy(
zzcpUZ(%zYQlWST`Ak*{n55CD?Kaj1R`RC-@KYDhpnU<5~YO2NfZR^Z~&)+`3D_;NE
zwcE2QRO6h0%c2+-KeIjIeED=nZH?jS_~LuucrJO@y6I+)+5U=kZ|eUGC}-=P&}YB)
zP+306JT0V7vcX5qS!?RUR`Ix`Yip!G-EQ1g_&7czV}@s8VM~C5^_K7Z-Wd0|OA
zI1DaHw#k7~kBa659$TR;PMhrUr~b|Zbs^717eDy%gcolXZQ0V2e^l!;zoqW%vy)Dycq|PvF@OJf^LammvNsZ^PM_A)
z(>rBfHvWJjTRa7c)Yh0MR8eg<#|d~xN{`@-|Z1Q>OEt%%871`Q!w@<(^9~ZP{M$Q2o1IMTpaAX2RQQA-?ub
zx5Xjh@eZY5Il8)(T$Cm{u*QLXkRRvRCiki|>z4A|a}!Q3`E6(H@czqT2l*z8;-{&c
z?T1~I5)VD}xW7CY99c`&AG@&lz+5i7b1Vw!e%Bq&vlOl0mdKI;Vst0H@j+_5c6?
literal 0
HcmV?d00001
From fe37083546c79c0c9ddd51251ae0ceea14b195de Mon Sep 17 00:00:00 2001
From: Sarah Chavis <62406755+schavis@users.noreply.github.com>
Date: Mon, 17 Nov 2025 13:51:40 -0800
Subject: [PATCH 05/18] save
---
content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx | 8 +++-----
...crets-plugin copy.mdx => configure-secrets-plugin.mdx} | 0
2 files changed, 3 insertions(+), 5 deletions(-)
rename content/vault/v1.21.x/content/partials/gui-instructions/{configure-secrets-plugin copy.mdx => configure-secrets-plugin.mdx} (100%)
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
index 3d85070fb7..d967d7a723 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
@@ -208,10 +208,9 @@ For example:
-## Step 3: Connect Vault and your LDAP server
+## Step 3: Configure the LDAP plugin
-Save the plugin configuration so that Vault can communicate with your LDAP
-server to generate passwords.
+Apply your configuration details so Vault can communicate with your LDAP server.
@@ -252,7 +251,7 @@ TBD
- Select your LDAP schema.
- Provide the required information according to your configuration file.
-- Click *Save*.
+- Click **Save**.
@@ -260,7 +259,6 @@ TBD
-
## Step 4: Rotate the root password
Once you connect Vault and your LDAP server, rotate the root password so only
diff --git a/content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin copy.mdx b/content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin.mdx
similarity index 100%
rename from content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin copy.mdx
rename to content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin.mdx
From e18d19970059bb556bb4c8e51ca9635697a67b54 Mon Sep 17 00:00:00 2001
From: Sarah Chavis <62406755+schavis@users.noreply.github.com>
Date: Tue, 18 Nov 2025 13:58:50 -0800
Subject: [PATCH 06/18] save
---
.../ldap/cookbook/basic-racf-config.mdx | 74 ++----------------
.../content/docs/secrets/ldap/setup.mdx | 75 +------------------
.../partials/examples/ldap/ad-config.mdx | 24 ++++++
.../examples/ldap/openldap-config.mdx | 25 +++++++
.../partials/examples/ldap/racf-config.mdx | 26 +++++++
.../password-policies/default-password.mdx | 31 ++++++++
.../examples/password-policies/passphrase.mdx | 31 ++++++++
7 files changed, 146 insertions(+), 140 deletions(-)
create mode 100644 content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx
create mode 100644 content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx
create mode 100644 content/vault/v1.21.x/content/partials/examples/ldap/racf-config.mdx
create mode 100644 content/vault/v1.21.x/content/partials/examples/password-policies/default-password.mdx
create mode 100644 content/vault/v1.21.x/content/partials/examples/password-policies/passphrase.mdx
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx
index 1adfd96844..465e9d45d4 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx
@@ -7,12 +7,8 @@ description: >-
# Configure LDAP for Resource access control facility (RACF)
-configures the LDAP
-secrets engine plugin to:
-
-- Use the RACF schema (`racf`).
-- Automatically manage password phrases.
-- Refer to a Vault password policy to enforce password length and complexity.
+A basic RACF configuration for LDAP automatically manages password phrases and
+uses a Vault password policy to enforce password length and complexity.
@@ -24,76 +20,18 @@ secrets engine plugin to:
-
-
-1. Create a JSON file called `racf-config.json` with the basic configuration
- settings:
-
-1. Use `vault write` with the `/config` path to configure the plugin:
-
- ```shell-session
- $ vault write /config \
- binddn= \
- bindpass= \
- url= \
- schema="racf" \
- credential_type="phrase" \
- password_policy=""
- ```
+
- For example:
-
-
-
- ```shell-session
- $ vault write devcreds/config \
- binddn="cn=admin,dc=abc,dc=com" \
- bindpass="iamabadpassword" \
- url=ldaps://138.91.247.105 \
- schema="racf" \
- credential_type="phrase" \
- password_policy="racf_password_policy"
- ```
-
-
+@include '/examples/password-policies/passphrase.mdx'
-
-
-1. Create a JSON file called `racf-config.json` with the basic configuration
- settings:
+
-
-Make a `POST` call to
-[`/{mount_path}/config`](/vault/api-docs/secret/ldap#configuration-management)
-to configure the plugin:
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys//config
-```
-
-For example:
-
-
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys/devcreds/rotate-root
-```
-
-
+@include '/examples/ldap/racf-config.mdx'
-
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
index d967d7a723..702a7e963d 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
@@ -109,31 +109,7 @@ configuration details.
Use the schema enum `openldap` to create a basic configuration file called
`ldap.json`:
-```json
-{
- "schema": "openldap",
- "binddn": "",
- "bindpass": "",
- "url": "",
- "credential_type": ""
-}
-```
-
-For example:
-
-
-
-```json
-{
- "schema": "openldap",
- "binddn": "cn=admin,dc=abc,dc=com",
- "bindpass": "iamabadpassword",
- "url": "ldaps://138.91.247.105",
- "credential_type": "password"
-}
-```
-
-
+@include '/examples/ldap/openldap-config.mdx'
@@ -142,29 +118,8 @@ For example:
Use the schema enum `ad` to create a basic configuration file called
`ldap.json`:
-```json
-{
- "schema": "ad",
- "binddn": "",
- "bindpass": "",
- "url": "",
- "credential_type": ""
-}
-```
-
-For example:
-
-
+@include '/examples/ldap/ad-config.mdx'
-```json
-{
- "schema": "ad",
- "binddn": "cn=admin,dc=abc,dc=com",
- "bindpass": "iamabadpassword",
- "url": "ldaps://138.91.247.105",
- "credential_type": "password"
-}
-```
@@ -175,31 +130,7 @@ For example:
Use the schema enum `racf` and the name of your password policy to create a
basic configuration file called `ldap.json`:
-```json
-{
- "schema": "racf",
- "binddn": "",
- "bindpass": "",
- "url": "",
- "credential_type": "",
- "password_policy": ""
-}
-```
-
-For example:
-
-
-
-```json
-{
- "schema": "racf",
- "binddn": "cn=admin,dc=abc,dc=com",
- "bindpass": "iamabadpassword",
- "url": "ldaps://138.91.247.105",
- "credential_type": "phrase",
- "password_policy": "racf_password_policy"
-}
-```
+@include '/examples/ldap/racf-config.mdx'
diff --git a/content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx b/content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx
new file mode 100644
index 0000000000..edd8ccd72f
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx
@@ -0,0 +1,24 @@
+```json
+{
+ "schema": "ad",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "credential_type": ""
+}
+```
+
+For example:
+
+
+
+```json
+{
+ "schema": "ad",
+ "binddn": "cn=admin,dc=abc,dc=com",
+ "bindpass": "iamabadpassword",
+ "url": "ldaps://138.91.247.105",
+ "credential_type": "password"
+}
+```
+
diff --git a/content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx b/content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx
new file mode 100644
index 0000000000..c0da77e628
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx
@@ -0,0 +1,25 @@
+```json
+{
+ "schema": "openldap",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "credential_type": ""
+}
+```
+
+For example:
+
+
+
+```json
+{
+ "schema": "openldap",
+ "binddn": "cn=admin,dc=abc,dc=com",
+ "bindpass": "iamabadpassword",
+ "url": "ldaps://138.91.247.105",
+ "credential_type": "password"
+}
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/examples/ldap/racf-config.mdx b/content/vault/v1.21.x/content/partials/examples/ldap/racf-config.mdx
new file mode 100644
index 0000000000..349473ebec
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/examples/ldap/racf-config.mdx
@@ -0,0 +1,26 @@
+```json
+{
+ "schema": "racf",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "credential_type": "",
+ "password_policy": ""
+}
+```
+
+For example:
+
+
+
+```json
+{
+ "schema": "racf",
+ "binddn": "cn=admin,dc=abc,dc=com",
+ "bindpass": "iamabadpassword",
+ "url": "ldaps://138.91.247.105",
+ "credential_type": "phrase",
+ "password_policy": "racf_password_policy"
+}
+```
+
diff --git a/content/vault/v1.21.x/content/partials/examples/password-policies/default-password.mdx b/content/vault/v1.21.x/content/partials/examples/password-policies/default-password.mdx
new file mode 100644
index 0000000000..48caf69180
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/examples/password-policies/default-password.mdx
@@ -0,0 +1,31 @@
+The following password policy requires password strings to have:
+
+- 20 characters.
+- at least one lowercase character.
+- at least one uppercase character.
+- at least one number.
+- at least two special characters.
+
+```hcl
+length=20
+
+rule "charset" {
+ charset = "abcdefghijklmnopqrstuvwxyz"
+ min-chars = 1
+}
+
+rule "charset" {
+ charset = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
+ min-chars = 1
+}
+
+rule "charset" {
+ charset = "0123456789"
+ min-chars = 1
+}
+
+rule "charset" {
+ charset = "!@#$%^&*"
+ min-chars = 2
+}
+```
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/examples/password-policies/passphrase.mdx b/content/vault/v1.21.x/content/partials/examples/password-policies/passphrase.mdx
new file mode 100644
index 0000000000..2cd6aa958e
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/examples/password-policies/passphrase.mdx
@@ -0,0 +1,31 @@
+The following password policy requires password strings to have:
+
+- 20 characters.
+- at least 2 spaces (to encourage three-word phrases).
+- at least one lowercase character.
+- at least one uppercase character.
+- any number of basic punctuation marks.
+
+```hcl
+length=20
+
+rule "charset" {
+ charset = " "
+ min-chars = 2
+}
+
+rule "charset" {
+ charset = "abcdefghijklmnopqrstuvwxyz"
+ min-chars = 1
+}
+
+rule "charset" {
+ charset = "ABCDEFGHIJKLMNOPQRSTUVWXYZ"
+ min-chars = 1
+}
+
+rule "charset" {
+ charset = "!.,?"
+ min-chars = 0
+}
+```
\ No newline at end of file
From feb1df343bd62870b68e4dd0ba540d1524bdb093 Mon Sep 17 00:00:00 2001
From: Sarah Chavis <62406755+schavis@users.noreply.github.com>
Date: Thu, 20 Nov 2025 16:17:37 -0800
Subject: [PATCH 07/18] save progress
---
.../ldap/cookbook/basic-racf-config.mdx | 37 --
.../ldap/cookbook/create-static-roles.mdx | 92 +---
.../ldap/cookbook/delete-static-roles.mdx | 61 +++
.../ldap/cookbook/disable-root-rotation.mdx | 71 +++
.../ldap/cookbook/rotate-root-creds.mdx | 53 +-
.../ldap/cookbook/rotate-static-roles.mdx | 34 ++
.../ldap/cookbook/schedule-based-rotation.mdx | 76 +++
.../docs/secrets/ldap/dynamic-credentials.mdx | 130 +++++
.../ldap/examples/basic-racf-config.mdx | 39 ++
.../secrets/ldap/examples/hash-passwords.mdx | 65 +++
.../content/docs/secrets/ldap/ibm-racf.mdx | 316 ++++++++++++
.../content/docs/secrets/ldap/index2.mdx | 455 ++----------------
.../secrets/ldap/service-account-checkout.mdx | 159 ++++++
.../content/docs/secrets/ldap/setup.mdx | 87 +---
.../configure-secrets-plugin.mdx | 6 +-
.../partials/ldap/apply-config/api.mdx | 27 ++
.../partials/ldap/apply-config/cli.mdx | 17 +
.../partials/ldap/apply-config/gui.mdx | 5 +
.../partials/ldap/create-static-role/api.mdx | 28 ++
.../partials/ldap/create-static-role/cli.mdx | 18 +
.../partials/ldap/delete-static-role/api.mdx | 28 ++
.../partials/ldap/delete-static-role/cli.mdx | 18 +
.../content/partials/ldap/enable/api.mdx | 28 ++
.../content/partials/ldap/enable/cli.mdx | 13 +
.../content/partials/ldap/enable/gui.mdx | 5 +
.../example-config/ad/basic.mdx} | 3 +-
.../example-config/ad/disable-rotation.mdx | 25 +
.../example-config/ad/period-rotation.mdx | 29 ++
.../example-config/ad/scheduled-rotation.mdx | 31 ++
.../example-config/openldap/basic.mdx} | 2 +-
.../openldap/disable-rotation.mdx | 25 +
.../openldap/period-rotation.mdx | 29 ++
.../openldap/scheduled-rotation.mdx | 31 ++
.../example-config/racf/basic.mdx} | 5 +-
.../example-config/racf/disable-rotation.mdx | 25 +
.../ldap/example-config/racf/ibm-setup.mdx | 27 ++
.../example-config/racf/period-rotation.mdx | 31 ++
.../racf/scheduled-rotation.mdx | 33 ++
.../ldap/example-config/static-role/basic.mdx | 23 +
.../example-config/static-role/ibm-racf.mdx | 23 +
.../example-config/static-role/minimal.mdx | 21 +
.../partials/ldap/get-role-creds/api.mdx | 25 +
.../partials/ldap/get-role-creds/cli.mdx | 17 +
.../partials/ldap/rotate-creds/api.mdx | 25 +
.../partials/ldap/rotate-creds/cli.mdx | 19 +
.../content/partials/ldap/rotate-root/api.mdx | 25 +
.../content/partials/ldap/rotate-root/cli.mdx | 17 +
.../example-config}/default-password.mdx | 0
.../example-config/ibm-racf-passphrase.mdx | 32 ++
.../example-config/ibm-racf-password.mdx | 26 +
.../example-config}/passphrase.mdx | 0
.../example-config/traditional-ldap.mdx | 10 +
.../password-policies/read-policy/api.mdx | 25 +
.../password-policies/read-policy/cli.mdx | 17 +
.../password-policies/save-policy/api.mdx | 27 ++
.../password-policies/save-policy/cli.mdx | 19 +
content/vault/v1.21.x/data/docs-nav-data.json | 47 +-
57 files changed, 1909 insertions(+), 653 deletions(-)
delete mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/delete-static-roles.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/disable-root-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-static-roles.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/schedule-based-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/dynamic-credentials.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/examples/basic-racf-config.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/examples/hash-passwords.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/ibm-racf.mdx
create mode 100644 content/vault/v1.21.x/content/docs/secrets/ldap/service-account-checkout.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/apply-config/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/apply-config/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/apply-config/gui.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/create-static-role/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/create-static-role/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/delete-static-role/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/delete-static-role/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/enable/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/enable/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/enable/gui.mdx
rename content/vault/v1.21.x/content/partials/{examples/ldap/ad-config.mdx => ldap/example-config/ad/basic.mdx} (89%)
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/ad/disable-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/ad/period-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/ad/scheduled-rotation.mdx
rename content/vault/v1.21.x/content/partials/{examples/ldap/openldap-config.mdx => ldap/example-config/openldap/basic.mdx} (92%)
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/openldap/disable-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/openldap/period-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/openldap/scheduled-rotation.mdx
rename content/vault/v1.21.x/content/partials/{examples/ldap/racf-config.mdx => ldap/example-config/racf/basic.mdx} (84%)
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/racf/disable-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/racf/ibm-setup.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/racf/period-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/racf/scheduled-rotation.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/static-role/basic.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/static-role/ibm-racf.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/example-config/static-role/minimal.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/get-role-creds/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/get-role-creds/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/rotate-creds/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/rotate-creds/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/rotate-root/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/ldap/rotate-root/cli.mdx
rename content/vault/v1.21.x/content/partials/{examples/password-policies => password-policies/example-config}/default-password.mdx (100%)
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/example-config/ibm-racf-passphrase.mdx
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/example-config/ibm-racf-password.mdx
rename content/vault/v1.21.x/content/partials/{examples/password-policies => password-policies/example-config}/passphrase.mdx (100%)
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/example-config/traditional-ldap.mdx
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/read-policy/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/read-policy/cli.mdx
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/save-policy/api.mdx
create mode 100644 content/vault/v1.21.x/content/partials/password-policies/save-policy/cli.mdx
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx
deleted file mode 100644
index 465e9d45d4..0000000000
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/basic-racf-config.mdx
+++ /dev/null
@@ -1,37 +0,0 @@
----
-layout: docs
-page_title: Configure LDAP for Resource access control facility (RACF)
-description: >-
- TBD
----
-
-# Configure LDAP for Resource access control facility (RACF)
-
-A basic RACF configuration for LDAP automatically manages password phrases and
-uses a Vault password policy to enforce password length and complexity.
-
-
-
-- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
-- You have a Vault [password policy](/vault/docs/concepts/password-policies)
- defined for your RACF schema.
-
-
-
-
-
-
-
-@include '/examples/password-policies/passphrase.mdx'
-
-
-
-
-
-@include '/examples/ldap/racf-config.mdx'
-
-
-
-
-
-
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/create-static-roles.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/create-static-roles.mdx
index c02c18de18..1c7987a64f 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/create-static-roles.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/create-static-roles.mdx
@@ -1,98 +1,58 @@
---
layout: docs
-page_title: Create static roles
+page_title: Create static LDAP roles
description: >-
- TBD
+ Map a named Vault role to an entry in your LDAP server.
---
# Create static LDAP roles
-TBD
+Configure static roles to map names in Vault to LDAP entries and use the
+rotation settings to manage credentials automatically with the role.
- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
-- TBD
+- You have permission to update roles in Vault.
+- You have permission to make `POST` calls to the `ldap` plugin.
-
+1. Create a configuration file, `ldap-role.json` with your role settings:
+ @include 'ldap/example-config/static-role/basic.mdx'
+1. Save the new role.
+
---------------------------------------------------------------------------------
+
-Setup :
+ @include 'ldap/create-static-role/cli.mdx'
-1. Configure a static role that maps a name in Vault to an entry in LDAP.
- Password rotation settings will be managed by this role.
+
- ```shell-session
- $ vault write ldap/static-role/hashicorp \
- dn='uid=hashicorp,ou=users,dc=hashicorp,dc=com' \
- username='hashicorp' \
- rotation_period="24h"
- ```
+
-2. Request credentials for the "hashicorp" role:
+ @include 'ldap/create-static-role/api.mdx'
- ```shell-session
- $ vault read ldap/static-cred/hashicorp
- ```
+
+
+1. Confirm the role settings by requesting credentials from the plugin:
---------------------------------------------------------------------------------
+
-
+
-Use `vault read` with the `/subkeys` path to retrieve a list of secret data
-subkeys at the given path.
+ @include 'ldap/get-role-creds/cli.mdx'
-```shell-session
-$ vault write -f /rotate-root
-```
+
-For example:
+
-
+ @include 'ldap/get-role-creds/api.mdx'
-```shell-session
-$ vault write -f devcreds/rotate-root
-```
+
-
-
-
-
-
-
-Make a `POST` call to
-[`/{mount_path}/rotate-root`](/vault/api-docs/secret/ldap#rotate-root-password)
-to rotate the credential::
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys//rotate-root
-```
-
-For example:
-
-
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys/devcreds/rotate-root
-```
-
-
-
-
-
-
\ No newline at end of file
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/delete-static-roles.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/delete-static-roles.mdx
new file mode 100644
index 0000000000..2538b2f74c
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/delete-static-roles.mdx
@@ -0,0 +1,61 @@
+---
+layout: docs
+page_title: Delete static LDAP roles
+description: >-
+ Delete a named Vault role currently mapped to an entry in your LDAP server.
+---
+
+# Delete static LDAP roles
+
+Vault does not rotate passwords when you delete a static role. We recommend
+manually rotating the mapped credentials before deleting the role or revoking
+access to the static role.
+
+
+
+- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
+- You have permission to update roles in Vault.
+- You have permission to make `POST` calls to the `ldap` plugin.
+
+
+
+1. Even for delete requests, the plugin expects all required parameters. You
+ can use the existing configuration file (if you created one) or create a
+ minimal version for the delete request.
+
+ @include 'ldap/example-config/static-role/minimal.mdx'
+
+1. Update the role.
+
+
+
+
+ @include 'ldap/delete-static-role/cli.mdx'
+
+
+
+
+
+ @include 'ldap/delete-static-role/api.mdx'
+
+
+
+
+
+1. Confirm the role deletion by requesting credentials from the plugin:
+
+
+
+
+
+ @include 'ldap/get-role-creds/cli.mdx'
+
+
+
+
+
+ @include 'ldap/get-role-creds/api.mdx'
+
+
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/disable-root-rotation.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/disable-root-rotation.mdx
new file mode 100644
index 0000000000..ae22b15601
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/disable-root-rotation.mdx
@@ -0,0 +1,71 @@
+---
+layout: docs
+page_title: Disable LDAP root credential rotation
+description: >-
+ temporarily disable root credential rotation in the LDAP secrets plugin.
+---
+
+# Disable LDAP root credential rotation
+
+You can temporarily disable root rotation with the
+[`disable_automated_rotation`](/vault/api-docs/secret/ldap#disable_automated_rotation)
+paramter in your plugin configuration.
+
+If you use `rotation_period`, disabling rotation also resets the credential
+TTL.
+
+
+
+- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
+- You have permission to update the plugin configuration.
+
+
+
+1. Update your configuration to disable rotation:
+
+
+
+
+
+ @include 'ldap/example-config/ad/disable-rotation.mdx'
+
+
+
+
+
+ @include 'ldap/example-config/openldap/disable-rotation.mdx'
+
+
+
+
+
+ @include 'ldap/example-config/racf/disable-rotation.mdx'
+
+
+
+
+
+
+1. Apply the changes.
+
+
+
+
+
+ @include 'ldap/apply-config/cli.mdx'
+
+
+
+
+
+ @include 'ldap/apply-config/api.mdx'
+
+
+
+
+
+ @include 'ldap/apply-config/gui.mdx'
+
+
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-root-creds.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-root-creds.mdx
index 7c2b77ea4b..9d65c675af 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-root-creds.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-root-creds.mdx
@@ -1,13 +1,13 @@
---
layout: docs
-page_title: Rotate root LDAP credentials
+page_title: Manually rotate root LDAP credentials
description: >-
- TBD
+ Manually rotate root credentials in the LDAP secrets plugin.
---
-# Rotate root LDAP credentials
+# Manually rotate root LDAP credentials
-Mounts can rotate root credential keys configured directly within the mount.
+You can rotate root credential keys configured directly within the plugin.
Rotating to a Vault-generated key makes the key value inaccessible to the
operator and ensures only Vault can operate as a root user to manipulate dynamic
and static credentials.
@@ -15,7 +15,7 @@ and static credentials.
- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
-- TBD
+- You have permission to update LDAP credentials in Vault.
@@ -23,52 +23,13 @@ and static credentials.
-Use `vault read` with the `/subkeys` path to retrieve a list of secret data
-subkeys at the given path.
-
-```shell-session
-$ vault write -f /rotate-root
-```
-
-For example:
-
-
-
-```shell-session
-$ vault write -f devcreds/rotate-root
-```
-
-
+@include 'ldap/rotate-root/cli.mdx'
-Make a `POST` call to
-[`/{mount_path}/rotate-root`](/vault/api-docs/secret/ldap#rotate-root-password)
-to rotate the credential::
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys//rotate-root
-```
-
-For example:
-
-
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys/devcreds/rotate-root
-```
-
-
+@include 'ldap/rotate-root/api.mdx'
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-static-roles.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-static-roles.mdx
new file mode 100644
index 0000000000..10c5e5c0cf
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/rotate-static-roles.mdx
@@ -0,0 +1,34 @@
+---
+layout: docs
+page_title: Manually rotate static role credentials
+description: >-
+ Manually rotate credentials for static roles using the LDAP secrets plugin.
+---
+
+# Manually rotate static role credentials
+
+The LDAP secrets plugin can rotate LDAP credential for static roles configured
+the plugin.
+
+
+
+- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
+- You have permission to update LDAP credentials in Vault.
+
+
+
+
+
+
+
+@include 'ldap/rotate-creds/cli.mdx'
+
+
+
+
+
+@include 'ldap/rotate-creds/api.mdx'
+
+
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/schedule-based-rotation.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/schedule-based-rotation.mdx
new file mode 100644
index 0000000000..7bea1cb92b
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/cookbook/schedule-based-rotation.mdx
@@ -0,0 +1,76 @@
+---
+layout: docs
+page_title: Rotate root LDAP credentials on a schedule
+description: >-
+ Configure schedule-based, automatic credential rotation for root credentials
+ in the LDAP secrets plugin.
+---
+
+# Rotate root LDAP credentials on a schedule
+
+@include 'alerts/enterprise-only.mdx'
+
+You can set the `rotation_schedule` parameter with an optional rotation window
+in your LDAP configuration to rotate root credentials on a fixed schedule.
+
+If you set the rotation window, Vault stops trying to rotate the credential once
+the window expires. If Vault cannot rotate the credential within the defined
+window (e.g., due to a network failure) it waits until the next scheduled
+rotation to try again.
+
+
+
+- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
+- You have permission to update the LDAP plugin configuration.
+
+
+
+1. You cannot set `rotation_period` and `rotation_schedule` for the same plugin.
+ If you previously set a rotation period, you must disable period rotation in
+ your configuration:
+
+
+
+
+
+ @include 'ldap/example-config/ad/scheduled-rotation.mdx'
+
+
+
+
+
+ @include 'ldap/example-config/openldap/scheduled-rotation.mdx'
+
+
+
+
+
+ @include 'ldap/example-config/racf/scheduled-rotation.mdx'
+
+
+
+
+
+1. Apply the changes.
+
+
+
+
+
+ @include 'ldap/apply-config/cli.mdx'
+
+
+
+
+
+ @include 'ldap/apply-config/api.mdx'
+
+
+
+
+
+ @include 'ldap/apply-config/gui.mdx'
+
+
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/dynamic-credentials.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/dynamic-credentials.mdx
new file mode 100644
index 0000000000..342ebe8232
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/dynamic-credentials.mdx
@@ -0,0 +1,130 @@
+## Dynamic credentials
+
+### Setup
+
+Dynamic credentials can be configured by calling the `/role/:role_name` endpoint:
+
+```bash
+$ vault write ldap/role/dynamic-role \
+ creation_ldif=@/path/to/creation.ldif \
+ deletion_ldif=@/path/to/deletion.ldif \
+ rollback_ldif=@/path/to/rollback.ldif \
+ default_ttl=1h \
+ max_ttl=24h
+```
+
+-> Note: The `rollback_ldif` argument is optional, but recommended. The statements within `rollback_ldif` will be
+executed if the creation fails for any reason. This ensures any entities are removed in the event of a failure.
+
+To generate credentials:
+
+```bash
+$ vault read ldap/creds/dynamic-role
+Key Value
+--- -----
+lease_id ldap/creds/dynamic-role/HFgd6uKaDomVMvJpYbn9q4q5
+lease_duration 1h
+lease_renewable true
+distinguished_names [cn=v_token_dynamic-role_FfH2i1c4dO_1611952635,ou=users,dc=learn,dc=example]
+password xWMjkIFMerYttEbzfnBVZvhRQGmhpAA0yeTya8fdmDB3LXDzGrjNEPV2bCPE9CW6
+username v_token_testrole_FfH2i1c4dO_1611952635
+```
+
+The `distinguished_names` field is an array of DNs that are created from the `creation_ldif` statements. If more than
+one LDIF entry is included, the DN from each statement will be included in this field. Each entry in this field
+corresponds to a single LDIF statement. No de-duplication occurs and order is maintained.
+
+### LDIF entries
+
+User account management is provided through LDIF entries. The LDIF entries may be a base64-encoded version of the
+LDIF string. The string will be parsed and validated to ensure that it adheres to LDIF syntax. A good reference
+for proper LDIF syntax can be found [here](https://ldap.com/ldif-the-ldap-data-interchange-format/).
+
+Some important things to remember when crafting your LDIF entries:
+
+- There should not be any trailing spaces on any line, including empty lines
+- Each `modify` block needs to be preceded with an empty line
+- Multiple modifications for a `dn` can be defined in a single `modify` block. Each modification needs to close
+ with a single dash (`-`)
+
+### Active directory (AD)
+
+
+
+ Windows Servers hosting Active Directory include a
+ `lifetime period of an old password` configuration setting that lets clients
+ authenticate with old passwords for a specified amount of time.
+
+ For more information, refer to the
+ [NTLM network authentication behavior](https://learn.microsoft.com/en-us/troubleshoot/windows-server/windows-security new-setting-modifies-ntlm-network-authentication)
+ guide by Microsoft.
+
+
+
+For Active Directory, there are a few additional details that are important to remember:
+
+To create a user programmatically in AD, you first `add` a user object and then `modify` that user to provide a
+password and enable the account.
+
+- Passwords in AD are set using the `unicodePwd` field. This must be proceeded by two (2) colons (`::`).
+- When setting a password programmatically in AD, the following criteria must be met:
+
+ - The password must be enclosed in double quotes (`" "`)
+ - The password must be in [`UTF16LE` format](https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-adts/6e803168-f140-4d23-b2d3-c3a8ab5917d2)
+ - The password must be `base64`-encoded
+ - Additional details can be found [here](https://docs.microsoft.com/en-us/troubleshoot/windows-server/identity/set-user-password-with-ldifde)
+
+- Once a user's password has been set, it can be enabled. AD uses the `userAccountControl` field for this purpose:
+ - To enable the account, set `userAccountControl` to `512`
+ - You will likely also want to disable AD's password expiration for this dynamic user account. The
+ `userAccountControl` value for this is: `65536`
+ - `userAccountControl` flags are cumulative, so to set both of the above two flags, add up the two values
+ (`512 + 65536 = 66048`): set `userAccountControl` to `66048`
+ - See [here](https://docs.microsoft.com/en-us/troubleshoot/windows-server/identity/useraccountcontrol-manipulate-account-properties#property-flag-descriptions)
+ for details on `userAccountControl` flags
+
+`sAMAccountName` is a common field when working with AD users. It is used to provide compatibility with legacy
+Windows NT systems and has a limit of 20 characters. Keep this in mind when defining your `username_template`.
+See [here](https://docs.microsoft.com/en-us/windows/win32/adschema/a-samaccountname) for additional details.
+
+Since the default `username_template` is longer than 20 characters which follows the template of `v_{{.DisplayName}}_{{.RoleName}}_{{random 10}}_{{unix_time}}`, we recommend customising the `username_template` on the role configuration to generate accounts with names less than 20 characters. Please refer to the [username templating document](/vault/docs/concepts/username-templating) for more information.
+
+With regard to adding dynamic users to groups, AD doesn't let you directly modify a user's `memberOf` attribute.
+The `member` attribute of a group and `memberOf` attribute of a user are
+[linked attributes](https://docs.microsoft.com/en-us/windows/win32/ad/linked-attributes). Linked attributes are
+forward link/back link pairs, with the forward link able to be modified. In the case of AD group membership, the
+group's `member` attribute is the forward link. In order to add a newly-created dynamic user to a group, we also
+need to issue a `modify` request to the desired group and update the group membership with the new user.
+
+#### Active directory LDIF example
+
+The various `*_ldif` parameters are templates that use the [go template](https://golang.org/pkg/text/template/)
+language. A complete LDIF example for creating an Active Directory user account is provided here for reference:
+
+```ldif
+dn: CN={{.Username}},OU=HashiVault,DC=adtesting,DC=lab
+changetype: add
+objectClass: top
+objectClass: person
+objectClass: organizationalPerson
+objectClass: user
+userPrincipalName: {{.Username}}@adtesting.lab
+sAMAccountName: {{.Username}}
+
+dn: CN={{.Username}},OU=HashiVault,DC=adtesting,DC=lab
+changetype: modify
+replace: unicodePwd
+unicodePwd::{{ printf "%q" .Password | utf16le | base64 }}
+-
+replace: userAccountControl
+userAccountControl: 66048
+-
+
+dn: CN=test-group,OU=HashiVault,DC=adtesting,DC=lab
+changetype: modify
+add: member
+member: CN={{.Username}},OU=HashiVault,DC=adtesting,DC=lab
+-
+```
+
+
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/examples/basic-racf-config.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/examples/basic-racf-config.mdx
new file mode 100644
index 0000000000..b4c7379066
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/examples/basic-racf-config.mdx
@@ -0,0 +1,39 @@
+---
+layout: docs
+page_title: Example LDAP config for RACF
+description: >-
+ Basic RACF configuration for the LDAP secrets plugin
+---
+
+# Example LDAP configuration for RACF
+
+You can use the following Resource access control facility (RACF) configuration
+for the LDAP secrets plugin and password policy configuration as a starting
+point for connecting Vault with your RACF deployment to automatically manage
+password phrases with Vault.
+
+
+
+- You have [set up an `ldap` plugin](/vault/docs/secrets/ldap/setup).
+- You have permission to create Vault
+ [password policy](/vault/docs/concepts/password-policies) passwords.
+
+
+
+
+
+
+
+@include 'password-policies/example-config/passphrase.mdx'
+
+
+
+
+
+@include 'ldap/example-config/racf/basic.mdx'
+
+
+
+
+
+
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/examples/hash-passwords.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/examples/hash-passwords.mdx
new file mode 100644
index 0000000000..cc65a26913
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/examples/hash-passwords.mdx
@@ -0,0 +1,65 @@
+---
+layout: docs
+page_title: Hash LDAP passwords
+description: >-
+ Hash LDAP passwords
+---
+
+# Hash LDAP passwords
+
+The LDAP secret engine does not hash or encrypt passwords before modifying
+values in LDAP, which can lead to plaintext passwords on your LDAP server.
+
+
+
+- You have permission to update your LDAP server.
+- You know the data information tree (DIT) assocaited with your `ldap` plugin.
+
+
+
+We recommend configuring your LDAP server with an LDAP password policy that
+hashes passwords by default on the DIT used by your plugin:
+
+
+
+```
+dn: cn=module{0},cn=config
+changetype: modify
+add: olcModuleLoad
+olcModuleLoad: ppolicy
+
+dn: olcOverlay={2}ppolicy,olcDatabase={1}mdb,cn=config
+changetype: add
+objectClass: olcPPolicyConfig
+objectClass: olcOverlayConfig
+olcOverlay: {2}ppolicy
+olcPPolicyDefault: cn=default,ou=pwpolicies,
+olcPPolicyForwardUpdates: FALSE
+olcPPolicyHashCleartext: TRUE
+olcPPolicyUseLockout: TRUE
+```
+
+
+
+For example, to hash data on the `dc=hashicorp,dc=com` DIT:
+
+
+
+```
+dn: cn=module{0},cn=config
+changetype: modify
+add: olcModuleLoad
+olcModuleLoad: ppolicy
+
+dn: olcOverlay={2}ppolicy,olcDatabase={1}mdb,cn=config
+changetype: add
+objectClass: olcPPolicyConfig
+objectClass: olcOverlayConfig
+olcOverlay: {2}ppolicy
+olcPPolicyDefault: cn=default,ou=pwpolicies,dc=hashicorp,dc=com
+olcPPolicyForwardUpdates: FALSE
+olcPPolicyHashCleartext: TRUE
+olcPPolicyUseLockout: TRUE
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/ibm-racf.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/ibm-racf.mdx
new file mode 100644
index 0000000000..244cb8551a
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/ibm-racf.mdx
@@ -0,0 +1,316 @@
+---
+layout: docs
+page_title: Manage IBM RACF LDAP credentials
+description: >-
+ Automatically manage Manage IBM RACF LDAP credentials with the LDAP secrets
+ plugin.
+
+---
+
+# Manage IBM RACF LDAP credentials
+
+IBM RACF is a widely used mainframe security system for managing authentication and access control in enterprise environments.
+
+The LDAP secrets engine in HashiCorp Vault provides a secure and automated workflow for managing IBM RACF LDAP credentials.
+It enables centralized storage and controlled access to credentials while offering automatic password rotation to enhance security and reduce operational overhead.
+
+
+Password Policy in IBM RACF is defined as 1 - 8 characters length.
+A password is a traditional one to eight character alphanumeric valu
+
+A RACF password phrase is a secure alternative to a traditional password in IBM's Resource Access Control Facility (RACF).
+Unlike standard passwords, which are short and limited in complexity, a password phrase is a longer character string that may include
+mixed-case letters, numbers, spaces, and special characters.
+Due to its length and complexity, it provides stronger protection against unauthorized access and brute-force attacks.
+When the new-password-phrase exit (ICHPWX11) is present and allows it, the password phrase can be 9 - 100 characters.
+When ICHPWX11 is not present, the password phrase must be 14 - 100 characters.
+
+A password phrase is a character string that consists of mixed-case letters, numbers, and special characters including blanks.
+Password phrases have security advantages over passwords as they are long enough to withstand most hacking attempts and are unlikely to be written down because they are easy to remember.
+A user can be assigned a password, a password phrase, both, or neither.
+
+You can now define a more complex password policy by including special characters to enhance security and meet RACF compliance requirements
+
+
+For more details refer to [RACF password-phrase policy](https://www.ibm.com/docs/en/zos/2.4.0?topic=syntax-password-phrase-specify-user-password-password-phrase)
+
+
+
+
+
+## Before you start
+
+- **Check your Vault permissions**. You must have permission to enable and
+ configure plugins in Vault.
+- **Create a RACF-enabled LDAP user account for Vault**. You must have a
+ RACF-enabled LDAP user account with sufficient privileges to manage user
+ credentials.
+- **Decide on a password policy**. We recommend using passphrases over passwords
+ for better security, but z/OS supports both.
+
+
+## Step 1: Create a Vault password policy
+
+To securely manage z/OS LDAP credentials in Vault you must create a password
+policy in Vault to control how the plugin rotates LDAP credentials. You can use
+traditional passwords or a passphrase, but we strongly recommend using
+passphrases.
+
+
+1. Create a policy configuration file `racf-policy.hcl`.
+
+
+
+
+
+ @include 'password-policies/example-config/ibm-racf-passphrase.mdx'
+
+
+
+
+
+ @include 'password-policies/example-config/ibm-racf-password.mdx'
+
+
+
+
+
+1. Save the policy to Vault.
+
+
+
+
+
+ @include 'password-policies/save-policy/cli.mdx'
+
+
+
+
+
+ @include 'password-policies/save-policy/api.mdx'
+
+
+
+
+
+1. Verify the password policy saved correctly.
+
+
+
+
+
+ @include 'password-policies/read-policy/cli.mdx'
+
+
+
+
+
+ @include 'password-policies/read-policy/api.mdx'
+
+
+
+
+
+
+## Step 2: Enable the LDAP secrets plugin
+
+
+
+
+
+@include 'ldap/enable/cli.mdx'
+
+
+
+
+
+@include 'ldap/enable/api.mdx'
+
+
+
+
+
+@include 'ldap/enable/gui.mdx'
+
+
+
+
+
+
+
+## Step 3: Create your plugin configuration file
+
+For easier maintenance and reuse, create a JSON file with your preferred
+configuration details. Use the schema enum `racf` and the name of your Vault
+password policy to create a basic configuration file called `ldap.json`:
+
+
+@include 'ldap/example-config/racf/ibm-setup.mdx'
+
+
+## Step 4: Configure the LDAP plugin
+
+Configure the LDAP plugin with your RACF-enabled LDAP user and connect Vault to
+your IBM RACF LDAP server.
+
+
+
+
+
+@include 'ldap/apply-config/cli.mdx'
+
+
+
+
+
+@include 'ldap/apply-config/api.mdx'
+
+
+
+
+
+
+
+@include 'ldap/apply-config/gui.mdx'
+
+
+
+
+
+
+
+## Step 5: Rotate the root password
+
+Once you connect Vault and your LDAP server, rotate the root password for the
+`binddn` account so that only Vault knows the credential.
+
+
+
+
+
+@include 'ldap/rotate-root/cli.mdx'
+
+
+
+
+
+@include 'ldap/rotate-root/api.mdx'
+
+
+
+
+
+
+
+Once you rotate the root credential you cannot retrieve the newly generated
+password.
+
+
+
+
+
+## Step 6: Create a static role
+
+
+1. Create a configuration file, `ldap-role.json` with your role settings:
+
+ @include 'ldap/example-config/static-role/ibm-racf.mdx'
+
+1. Save the new role.
+
+
+
+
+ @include 'ldap/create-static-role/cli.mdx'
+
+
+
+
+
+ @include 'ldap/create-static-role/api.mdx'
+
+
+
+
+
+1. Confirm the role settings by requesting credentials from the plugin:
+
+
+
+
+
+ @include 'ldap/get-role-creds/cli.mdx'
+
+
+
+
+
+ @include 'ldap/get-role-creds/api.mdx'
+
+
+
+
+
+
+
+## Step 7: Test the static role
+
+Vault automatically rotates passwords based on the rotation period you set in
+the static role configured.
+
+1. Fetch credentials for the static role. The response includes the time before
+ the next rotation (ttl) in addition to the current credential.
+
+
+
+
+
+ @include 'ldap/get-role-creds/cli.mdx'
+
+
+
+
+
+ @include 'ldap/get-role-creds/api.mdx'
+
+
+
+
+
+
+1. Use the provided credential to SSH into your mainframe z/OS system:
+
+ ```shell-session
+ $ ssh @
+ ```
+
+ For example:
+
+
+
+ ```shell-session
+ $ ssh vault@pksthc4.pok.stglabs.ibm.com
+ ```
+
+
+
+## Additional resources
+
+
+
+
+
+- [Full LDAP plugin API reference](/vault/api-docs/secret/ldap)
+- [Use dynamic credentials](/vault/docs/secrets/ldap/dynamic-credentials)
+- [Let clients check out service accounts](/vault/docs/secrets/ldap/service-account-checkout)
+
+
+
+
+
+- [Passwords and password phrases overview](https://www.ibm.com/docs/en/zos/2.5.0?topic=users-passwords-password-phrases)
+- [Resource access control facility overview](https://www.ibm.com/docs/en/zos-basic-skills?topic=zos-what-is-racf
+
+
+
+
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/index2.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/index2.mdx
index ee7cb375c4..82baed4a8d 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/index2.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/index2.mdx
@@ -19,12 +19,17 @@ Current version | Edition | Runtime | Code source
## Feature summary
- Use OpenLDAP, RACF, and Active Directory schemas.
-- Map static Vault roles to LDAP credentials.
-- Manually rotate LDAP passwords.
-- Automatically rotate LDAP passwords.
-- Manage LDAP user accounts through LDIF.
+- Use traditional 8-character passwords and modern, longer password phrases.
+- Use dynamic LDAP credentials and manage LDAP user accounts through LDIF.
- Check-out service accounts with automatic password rotation.
+- Map static Vault roles to LDAP credentials.
+- Manually rotate LDAP passwords and root credentials.
+- Automatically rotate LDAP passwords for static credentials.
+
+
+## Overview
+@include 'rotation-manager-logging.mdx'
## Static credentials
@@ -42,9 +47,6 @@ Passwords will automatically be rotated based on the `rotation_period` configure
in the static role (minimum of 5 seconds). When requesting credentials for a static
role, the response will include the time before the next rotation (`ttl`).
-The `binddn` account used by Vault should be rotated using the `rotate-root` endpoint to generate a password
-only Vault will know.
-
As with the rotation manager, Vault logs rotations with reference to the
`name` of the role and `error` if the rotation failed. The logs also indicate
if the rotation was part of a `periodic function`.
@@ -56,12 +58,7 @@ rotated the rotation period will start over.
Logging for manual rotation records the same information as other rotation
logging with an additional reference that the rotation happened `on user request`.
-
-### Deleting static roles
-
-Passwords are not rotated upon deletion of a static role. The password should be manually
-rotated prior to deleting the role or revoking access to the static role.
-
+\
---------------------------------------------------------------------------------
### OpenLDAP
@@ -78,407 +75,19 @@ There are many object classes that provide `userPassword` including for example:
- `person`
- `posixAccount`
-### Password vs. password phrase credentials
-
-The LDAP plugin supports traditional 8-character passwords and modern,
-longer password phrases through th
-[`credential_type`](/vault/api-docs/secret/ldap#credential_type) parameter:
-
-- `password` (Default): Configure the plugin to generate and manage standard RACF passwords.
-- `phrase`: Configure the plugin to generate and manage case-sensitive password phrases.
-
-### Active directory (AD)
+## Root credential rotation
-- `ad`
-
-For managing Active Directory instances, the secret engine must be configured to use the
-schema `ad`.
-
-```bash
-$ vault write ldap/config \
- binddn=$USERNAME \
- bindpass=$PASSWORD \
- url=ldaps://138.91.247.105 \
- schema=ad
-```
+Mounts can rotate root credential keys configured directly within the mount.
+Rotating to a Vault-generated key makes the key value inaccessible to the
+operator and ensures only Vault can operate as a root user to manipulate dynamic
+and static credentials.
+- Schedule-based root credential rotation
-### Schedule-based root credential rotation
-
-@include 'alerts/enterprise-only.mdx'
-
-Use the [`rotation_schedule`](/vault/api-docs/secret/ldap#rotation_schedule) field
-to configure schedule-based, automatic credential rotation for root credentials in
-the LDAP secrets engine. For example, the following command set the rotation to
-occur every Saturday at midnight (00:00):
-
-```shell-session
-$ vault write ldap/config \
- ...
- rotation_schedule="0 * * * SAT"
- ...
-```
-
-This configuration will set the role's credential rotation to occur on Saturday
-at 00:00.
-
-Scheduled root credential rotation can also set a
-[rotation_window](/vault/api-docs/secret/ldap#rotation_window) during which the
-scheduled rotation is allowed to occur. Vault will stop trying to rotate the
-credential once the window expires. For example, the following command tells
-Vault to rotate the credential on Saturday at midnight, but only within the span
-of an hour. If Vault cannot rotate the credential by 1:00, due to a failure
-or otherwise, Vault will stop trying to rotate the credential until the next
-scheduled rotation.
-
-```shell-session
-$ vault write ldap/config \
- ...
- rotation_window="1h" \
- rotation_schedule="0 * * * SAT"
- ...
-```
-
-You can temporarily disable root rotation by setting
-[`disable_automated_rotation`](/vault/api-docs/secret/ldap#disable_automated_rotation)
-to `true`. Setting the `disable_automated_rotation` field prevent any rotation
-of the root credential until the field is reset to `false`. If you use
-`rotation_period`, setting `disable_automated_rotation` also resets the credential
-TTL.
-
-For more details on rotating root credentials in the LDAP plugin, refer to the
-[Root credential rotation](/vault/api-docs/secret/ldap#rotate-root) API docs.
-
-@include 'rotation-manager-logging.mdx'
-## Dynamic credentials
-
-### Setup
-
-Dynamic credentials can be configured by calling the `/role/:role_name` endpoint:
-
-```bash
-$ vault write ldap/role/dynamic-role \
- creation_ldif=@/path/to/creation.ldif \
- deletion_ldif=@/path/to/deletion.ldif \
- rollback_ldif=@/path/to/rollback.ldif \
- default_ttl=1h \
- max_ttl=24h
-```
-
--> Note: The `rollback_ldif` argument is optional, but recommended. The statements within `rollback_ldif` will be
-executed if the creation fails for any reason. This ensures any entities are removed in the event of a failure.
-
-To generate credentials:
-
-```bash
-$ vault read ldap/creds/dynamic-role
-Key Value
---- -----
-lease_id ldap/creds/dynamic-role/HFgd6uKaDomVMvJpYbn9q4q5
-lease_duration 1h
-lease_renewable true
-distinguished_names [cn=v_token_dynamic-role_FfH2i1c4dO_1611952635,ou=users,dc=learn,dc=example]
-password xWMjkIFMerYttEbzfnBVZvhRQGmhpAA0yeTya8fdmDB3LXDzGrjNEPV2bCPE9CW6
-username v_token_testrole_FfH2i1c4dO_1611952635
-```
-
-The `distinguished_names` field is an array of DNs that are created from the `creation_ldif` statements. If more than
-one LDIF entry is included, the DN from each statement will be included in this field. Each entry in this field
-corresponds to a single LDIF statement. No de-duplication occurs and order is maintained.
-
-### LDIF entries
-
-User account management is provided through LDIF entries. The LDIF entries may be a base64-encoded version of the
-LDIF string. The string will be parsed and validated to ensure that it adheres to LDIF syntax. A good reference
-for proper LDIF syntax can be found [here](https://ldap.com/ldif-the-ldap-data-interchange-format/).
-
-Some important things to remember when crafting your LDIF entries:
-
-- There should not be any trailing spaces on any line, including empty lines
-- Each `modify` block needs to be preceded with an empty line
-- Multiple modifications for a `dn` can be defined in a single `modify` block. Each modification needs to close
- with a single dash (`-`)
-
-### Active directory (AD)
-
-
-
- Windows Servers hosting Active Directory include a
- `lifetime period of an old password` configuration setting that lets clients
- authenticate with old passwords for a specified amount of time.
-
- For more information, refer to the
- [NTLM network authentication behavior](https://learn.microsoft.com/en-us/troubleshoot/windows-server/windows-security new-setting-modifies-ntlm-network-authentication)
- guide by Microsoft.
-
-
-
-For Active Directory, there are a few additional details that are important to remember:
-
-To create a user programmatically in AD, you first `add` a user object and then `modify` that user to provide a
-password and enable the account.
-
-- Passwords in AD are set using the `unicodePwd` field. This must be proceeded by two (2) colons (`::`).
-- When setting a password programmatically in AD, the following criteria must be met:
-
- - The password must be enclosed in double quotes (`" "`)
- - The password must be in [`UTF16LE` format](https://docs.microsoft.com/en-us/openspecs/windows_protocols/ms-adts/6e803168-f140-4d23-b2d3-c3a8ab5917d2)
- - The password must be `base64`-encoded
- - Additional details can be found [here](https://docs.microsoft.com/en-us/troubleshoot/windows-server/identity/set-user-password-with-ldifde)
-
-- Once a user's password has been set, it can be enabled. AD uses the `userAccountControl` field for this purpose:
- - To enable the account, set `userAccountControl` to `512`
- - You will likely also want to disable AD's password expiration for this dynamic user account. The
- `userAccountControl` value for this is: `65536`
- - `userAccountControl` flags are cumulative, so to set both of the above two flags, add up the two values
- (`512 + 65536 = 66048`): set `userAccountControl` to `66048`
- - See [here](https://docs.microsoft.com/en-us/troubleshoot/windows-server/identity/useraccountcontrol-manipulate-account-properties#property-flag-descriptions)
- for details on `userAccountControl` flags
-
-`sAMAccountName` is a common field when working with AD users. It is used to provide compatibility with legacy
-Windows NT systems and has a limit of 20 characters. Keep this in mind when defining your `username_template`.
-See [here](https://docs.microsoft.com/en-us/windows/win32/adschema/a-samaccountname) for additional details.
-
-Since the default `username_template` is longer than 20 characters which follows the template of `v_{{.DisplayName}}_{{.RoleName}}_{{random 10}}_{{unix_time}}`, we recommend customising the `username_template` on the role configuration to generate accounts with names less than 20 characters. Please refer to the [username templating document](/vault/docs/concepts/username-templating) for more information.
-
-With regard to adding dynamic users to groups, AD doesn't let you directly modify a user's `memberOf` attribute.
-The `member` attribute of a group and `memberOf` attribute of a user are
-[linked attributes](https://docs.microsoft.com/en-us/windows/win32/ad/linked-attributes). Linked attributes are
-forward link/back link pairs, with the forward link able to be modified. In the case of AD group membership, the
-group's `member` attribute is the forward link. In order to add a newly-created dynamic user to a group, we also
-need to issue a `modify` request to the desired group and update the group membership with the new user.
-
-#### Active directory LDIF example
-
-The various `*_ldif` parameters are templates that use the [go template](https://golang.org/pkg/text/template/)
-language. A complete LDIF example for creating an Active Directory user account is provided here for reference:
-
-```ldif
-dn: CN={{.Username}},OU=HashiVault,DC=adtesting,DC=lab
-changetype: add
-objectClass: top
-objectClass: person
-objectClass: organizationalPerson
-objectClass: user
-userPrincipalName: {{.Username}}@adtesting.lab
-sAMAccountName: {{.Username}}
-
-dn: CN={{.Username}},OU=HashiVault,DC=adtesting,DC=lab
-changetype: modify
-replace: unicodePwd
-unicodePwd::{{ printf "%q" .Password | utf16le | base64 }}
--
-replace: userAccountControl
-userAccountControl: 66048
--
-
-dn: CN=test-group,OU=HashiVault,DC=adtesting,DC=lab
-changetype: modify
-add: member
-member: CN={{.Username}},OU=HashiVault,DC=adtesting,DC=lab
--
-```
-
-## Service account Check-Out
-
-Service account check-out provides a library of service accounts that can be checked out
-by a person or by machines. Vault will automatically rotate the password each time a
-service account is checked in. Service accounts can be voluntarily checked in, or Vault
-will check them in when their lending period (or, "ttl", in Vault's language) ends.
-
-The service account check-out functionality works with various [schemas](/vault/api-docs/secret/ldap#schema),
-including OpenLDAP, Active Directory, and RACF. In the following usage example, the secrets
-engine is configured to manage a library of service accounts in an Active Directory instance.
-
-First we'll need to enable the LDAP secrets engine and tell it how to securely connect
-to an AD server.
-
-```shell-session
-$ vault secrets enable ldap
-Success! Enabled the ad secrets engine at: ldap/
-
-$ vault write ldap/config \
- binddn=$USERNAME \
- bindpass=$PASSWORD \
- url=ldaps://138.91.247.105 \
- userdn='dc=example,dc=com'
-```
-
-Our next step is to designate a set of service accounts for check-out.
-
-```shell-session
-$ vault write ldap/library/accounting-team \
- service_account_names=fizz@example.com,buzz@example.com \
- ttl=10h \
- max_ttl=20h \
- disable_check_in_enforcement=false
-```
-
-In this example, the service account names of `fizz@example.com` and `buzz@example.com` have
-already been created on the remote AD server. They've been set aside solely for Vault to handle.
-The `ttl` is how long each check-out will last before Vault checks in a service account,
-rotating its password during check-in. The `max_ttl` is the maximum amount of time it can live
-if it's renewed. These default to `24h`, and both use [duration format strings](/vault/docs/concepts/duration-format).
-Also by default, a service account must be checked in by the same Vault entity or client token that
-checked it out. However, if this behavior causes problems, set `disable_check_in_enforcement=true`.
-
-When a library of service accounts has been created, view their status at any time to see if they're
-available or checked out.
-
-```shell-session
-$ vault read ldap/library/accounting-team/status
-Key Value
---- -----
-buzz@example.com map[available:true]
-fizz@example.com map[available:true]
-```
-
-To check out any service account that's available, simply execute:
-
-```shell-session
-$ vault write -f ldap/library/accounting-team/check-out
-Key Value
---- -----
-lease_id ldap/library/accounting-team/check-out/EpuS8cX7uEsDzOwW9kkKOyGW
-lease_duration 10h
-lease_renewable true
-password ?@09AZKh03hBORZPJcTDgLfntlHqxLy29tcQjPVThzuwWAx/Twx4a2ZcRQRqrZ1w
-service_account_name fizz@example.com
-```
-
-If the default `ttl` for the check-out is higher than needed, set the check-out to last
-for a shorter time by using:
-
-```shell-session
-$ vault write ldap/library/accounting-team/check-out ttl=30m
-Key Value
---- -----
-lease_id ldap/library/accounting-team/check-out/gMonJ2jB6kYs6d3Vw37WFDCY
-lease_duration 30m
-lease_renewable true
-password ?@09AZerLLuJfEMbRqP+3yfQYDSq6laP48TCJRBJaJu/kDKLsq9WxL9szVAvL/E1
-service_account_name buzz@example.com
-```
-
-This can be a nice way to say, "Although I _can_ have a check-out for 24 hours, if I
-haven't checked it in after 30 minutes, I forgot or I'm a dead instance, so you can just
-check it back in."
-
-If no service accounts are available for check-out, Vault will return a 400 Bad Request.
-
-```shell-session
-$ vault write -f ldap/library/accounting-team/check-out
-Error writing data to ldap/library/accounting-team/check-out: Error making API request.
-
-URL: POST http://localhost:8200/v1/ldap/library/accounting-team/check-out
-Code: 400. Errors:
-
-* No service accounts available for check-out.
-```
-
-To extend a check-out, renew its lease.
-
-```shell-session
-$ vault lease renew ldap/library/accounting-team/check-out/0C2wmeaDmsToVFc0zDiX9cMq
-Key Value
---- -----
-lease_id ldap/library/accounting-team/check-out/0C2wmeaDmsToVFc0zDiX9cMq
-lease_duration 10h
-lease_renewable true
-```
-
-Renewing a check-out means its current password will live longer, since passwords are rotated
-anytime a password is _checked in_ either by a caller, or by Vault because the check-out `ttl`
-ends.
-
-To check a service account back in for others to use, call:
-
-```shell-session
-$ vault write -f ldap/library/accounting-team/check-in
-Key Value
---- -----
-check_ins [fizz@example.com]
-```
-
-Most of the time this will just work, but if multiple service accounts are checked out by the same
-caller, Vault will need to know which one(s) to check in.
-
-```shell-session
-$ vault write ldap/library/accounting-team/check-in service_account_names=fizz@example.com
-Key Value
---- -----
-check_ins [fizz@example.com]
-```
-
-To perform a check-in, Vault verifies that the caller _should_ be able to check in a given service account.
-To do this, Vault looks for either the same [entity ID](/vault/tutorials/auth-methods/identity)
-used to check out the service account, or the same client token.
-
-If a caller is unable to check in a service account, or simply doesn't try,
-Vault will check it back in automatically when the `ttl` expires. However, if that is too long,
-service accounts can be forcibly checked in by a highly privileged user through:
-
-```shell-session
-$ vault write -f ldap/library/manage/accounting-team/check-in
-Key Value
---- -----
-check_ins [fizz@example.com]
-```
-
-Or, alternatively, revoking the secret's lease has the same effect.
-
-```shell-session
-$ vault lease revoke ldap/library/accounting-team/check-out/PvBVG0m7pEg2940Cb3Jw3KpJ
-All revocation operations queued successfully!
-```
-
-## Password generation
-
-This engine previously allowed configuration of the length of the password that is generated
-when rotating credentials. This mechanism was deprecated in Vault 1.5 in favor of
-[password policies](/vault/docs/concepts/password-policies). This means the `length` field should
-no longer be used. The following password policy can be used to mirror the same behavior
-that the `length` field provides:
-
-```hcl
-length=
-rule "charset" {
- charset = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789"
-}
-```
-
-## LDAP password policy
-
-The LDAP secret engine does not hash or encrypt passwords prior to modifying
-values in LDAP. This behavior can cause plaintext passwords to be stored in LDAP.
-
-To avoid having plaintext passwords stored, the LDAP server should be configured
-with an LDAP password policy (ppolicy, not to be confused with a Vault password
-policy). A ppolicy can enforce rules such as hashing plaintext passwords by default.
-
-The following is an example of an LDAP password policy to enforce hashing on the
-data information tree (DIT) `dc=hashicorp,dc=com`:
-
-```
-dn: cn=module{0},cn=config
-changetype: modify
-add: olcModuleLoad
-olcModuleLoad: ppolicy
-
-dn: olcOverlay={2}ppolicy,olcDatabase={1}mdb,cn=config
-changetype: add
-objectClass: olcPPolicyConfig
-objectClass: olcOverlayConfig
-olcOverlay: {2}ppolicy
-olcPPolicyDefault: cn=default,ou=pwpolicies,dc=hashicorp,dc=com
-olcPPolicyForwardUpdates: FALSE
-olcPPolicyHashCleartext: TRUE
-olcPPolicyUseLockout: TRUE
-```
## Hierarchical paths
@@ -547,20 +156,9 @@ Since [Vault policies](/vault/docs/concepts/policies) are also path-based,
hierarchical names also let you define policies that map 1-1 to LDAP secrets
engine roles and set paths.
-The following Vault API endpoints support hierarchical path handling:
-
-- [Static roles](/vault/api-docs/secret/ldap#static-roles)
-- [Static role passwords](/vault/api-docs/secret/ldap#static-role-passwords)
-- [Manually rotate static role password](/vault/api-docs/secret/ldap#manually-rotate-static-role-password)
-- [Dynamic roles](/vault/api-docs/secret/ldap#dynamic-roles)
-- [Dynamic role passwords](/vault/api-docs/secret/ldap#dynamic-role-passwords)
-- [Library set management](/vault/api-docs/secret/ldap#library-set-management)
-- [Library set status check](/vault/api-docs/secret/ldap#library-set-status-check)
-- [Check-Out management](/vault/api-docs/secret/ldap#check-out-management)
-- [Check-In management](/vault/api-docs/secret/ldap#check-in-management)
-
+---------------------------------------------------------------------------
@@ -569,17 +167,32 @@ The following Vault API endpoints support hierarchical path handling:
Step-by-step instructions:
- [Set up the `ldap` plugin](/vault/docs/secrets/ldap/setup)
+- [Use dynamic credentials](/vault/docs/secrets/ldap/dynamic-credentials)
+- [Check out service accounts](/vault/docs/secrets/ldap/service-account-checkout)
-Basic examples:
+Short explanations for common problems:
-- [Rotate root credentials](/vault/docs/secrets/ldap/cookbook/rotate-root-cred)
+- [Manually rotate root credentials](/vault/docs/secrets/ldap/cookbook/rotate-root-cred)
+- [Schedule root credential rotation](/vault/docs/secrets/ldap/cookbook/schedule-based-rotation)
+- [Disable root credential rotation](/vault/docs/secrets/ldap/cookbook/disable-root-rotation)
+- [Create static roles](/vault/docs/secrets/ldap/cookbook/create-static-roles)
+
+
+Configuration and code templates:
+
+- [Basic RACF configuration](/vault/docs/secrets/ldap/examples/basic-racf-config)
+- [Hash policy for LDAP passwords](/vault/docs/secrets/ldap/examples/hash-passwords)
+
+
+
+
Technical references:
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/service-account-checkout.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/service-account-checkout.mdx
new file mode 100644
index 0000000000..d6893beeea
--- /dev/null
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/service-account-checkout.mdx
@@ -0,0 +1,159 @@
+## Service account Check-Out
+
+Service account check-out provides a library of service accounts that can be checked out
+by a person or by machines. Vault will automatically rotate the password each time a
+service account is checked in. Service accounts can be voluntarily checked in, or Vault
+will check them in when their lending period (or, "ttl", in Vault's language) ends.
+
+The service account check-out functionality works with various [schemas](/vault/api-docs/secret/ldap#schema),
+including OpenLDAP, Active Directory, and RACF. In the following usage example, the secrets
+engine is configured to manage a library of service accounts in an Active Directory instance.
+
+First we'll need to enable the LDAP secrets engine and tell it how to securely connect
+to an AD server.
+
+```shell-session
+$ vault secrets enable ldap
+Success! Enabled the ad secrets engine at: ldap/
+
+$ vault write ldap/config \
+ binddn=$USERNAME \
+ bindpass=$PASSWORD \
+ url=ldaps://138.91.247.105 \
+ userdn='dc=example,dc=com'
+```
+
+Our next step is to designate a set of service accounts for check-out.
+
+```shell-session
+$ vault write ldap/library/accounting-team \
+ service_account_names=fizz@example.com,buzz@example.com \
+ ttl=10h \
+ max_ttl=20h \
+ disable_check_in_enforcement=false
+```
+
+In this example, the service account names of `fizz@example.com` and `buzz@example.com` have
+already been created on the remote AD server. They've been set aside solely for Vault to handle.
+The `ttl` is how long each check-out will last before Vault checks in a service account,
+rotating its password during check-in. The `max_ttl` is the maximum amount of time it can live
+if it's renewed. These default to `24h`, and both use [duration format strings](/vault/docs/concepts/duration-format).
+Also by default, a service account must be checked in by the same Vault entity or client token that
+checked it out. However, if this behavior causes problems, set `disable_check_in_enforcement=true`.
+
+When a library of service accounts has been created, view their status at any time to see if they're
+available or checked out.
+
+```shell-session
+$ vault read ldap/library/accounting-team/status
+Key Value
+--- -----
+buzz@example.com map[available:true]
+fizz@example.com map[available:true]
+```
+
+To check out any service account that's available, simply execute:
+
+```shell-session
+$ vault write -f ldap/library/accounting-team/check-out
+Key Value
+--- -----
+lease_id ldap/library/accounting-team/check-out/EpuS8cX7uEsDzOwW9kkKOyGW
+lease_duration 10h
+lease_renewable true
+password ?@09AZKh03hBORZPJcTDgLfntlHqxLy29tcQjPVThzuwWAx/Twx4a2ZcRQRqrZ1w
+service_account_name fizz@example.com
+```
+
+If the default `ttl` for the check-out is higher than needed, set the check-out to last
+for a shorter time by using:
+
+```shell-session
+$ vault write ldap/library/accounting-team/check-out ttl=30m
+Key Value
+--- -----
+lease_id ldap/library/accounting-team/check-out/gMonJ2jB6kYs6d3Vw37WFDCY
+lease_duration 30m
+lease_renewable true
+password ?@09AZerLLuJfEMbRqP+3yfQYDSq6laP48TCJRBJaJu/kDKLsq9WxL9szVAvL/E1
+service_account_name buzz@example.com
+```
+
+This can be a nice way to say, "Although I _can_ have a check-out for 24 hours, if I
+haven't checked it in after 30 minutes, I forgot or I'm a dead instance, so you can just
+check it back in."
+
+If no service accounts are available for check-out, Vault will return a 400 Bad Request.
+
+```shell-session
+$ vault write -f ldap/library/accounting-team/check-out
+Error writing data to ldap/library/accounting-team/check-out: Error making API request.
+
+URL: POST http://localhost:8200/v1/ldap/library/accounting-team/check-out
+Code: 400. Errors:
+
+* No service accounts available for check-out.
+```
+
+To extend a check-out, renew its lease.
+
+```shell-session
+$ vault lease renew ldap/library/accounting-team/check-out/0C2wmeaDmsToVFc0zDiX9cMq
+Key Value
+--- -----
+lease_id ldap/library/accounting-team/check-out/0C2wmeaDmsToVFc0zDiX9cMq
+lease_duration 10h
+lease_renewable true
+```
+
+Renewing a check-out means its current password will live longer, since passwords are rotated
+anytime a password is _checked in_ either by a caller, or by Vault because the check-out `ttl`
+ends.
+
+To check a service account back in for others to use, call:
+
+```shell-session
+$ vault write -f ldap/library/accounting-team/check-in
+Key Value
+--- -----
+check_ins [fizz@example.com]
+```
+
+Most of the time this will just work, but if multiple service accounts are checked out by the same
+caller, Vault will need to know which one(s) to check in.
+
+```shell-session
+$ vault write ldap/library/accounting-team/check-in service_account_names=fizz@example.com
+Key Value
+--- -----
+check_ins [fizz@example.com]
+```
+
+To perform a check-in, Vault verifies that the caller _should_ be able to check in a given service account.
+To do this, Vault looks for either the same [entity ID](/vault/tutorials/auth-methods/identity)
+used to check out the service account, or the same client token.
+
+If a caller is unable to check in a service account, or simply doesn't try,
+Vault will check it back in automatically when the `ttl` expires. However, if that is too long,
+service accounts can be forcibly checked in by a highly privileged user through:
+
+```shell-session
+$ vault write -f ldap/library/manage/accounting-team/check-in
+Key Value
+--- -----
+check_ins [fizz@example.com]
+```
+
+Or, alternatively, revoking the secret's lease has the same effect.
+
+```shell-session
+$ vault lease revoke ldap/library/accounting-team/check-out/PvBVG0m7pEg2940Cb3Jw3KpJ
+All revocation operations queued successfully!
+```
+
+
+
+- [Library set management](/vault/api-docs/secret/ldap#library-set-management)
+- [Library set status check](/vault/api-docs/secret/ldap#library-set-status-check)
+- [Check-Out management](/vault/api-docs/secret/ldap#check-out-management)
+- [Check-In management](/vault/api-docs/secret/ldap#check-in-management)
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx b/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
index 702a7e963d..0e8456c6cd 100644
--- a/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
+++ b/content/vault/v1.21.x/content/docs/secrets/ldap/setup.mdx
@@ -22,7 +22,7 @@ Use `vault secrets enable` to enable an instance of the `ldap` plugin.
have a Vault [password policy](/vault/docs/concepts/password-policies) defined.
-## Step 1: Enable the plugin
+## Step 1: Enable the LDAP secrets plugin
@@ -60,7 +60,7 @@ $ curl \
For example:
-
+
```shell-session
$ curl \
@@ -68,7 +68,7 @@ $ curl \
--header "X-Vault-Token: ${VAULT_TOKEN}" \
--namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
--data '{"type": "ldap"}' \
- ${VAULT_ADDR}/v1/sys/mounts/devcreds | jq
+ ${VAULT_ADDR}/v1/sys/mounts/devcreds
```
@@ -83,8 +83,7 @@ $ curl \
- Select the "LDAP" plugin.
-- Enter a unique path for the plugin and provide the relevant configuration
- data.
+- Enter a unique path for the plugin and set your basic plugin settings.
@@ -109,7 +108,7 @@ configuration details.
Use the schema enum `openldap` to create a basic configuration file called
`ldap.json`:
-@include '/examples/ldap/openldap-config.mdx'
+@include 'ldap/example-config/openldap/basic.mdx'
@@ -118,11 +117,9 @@ Use the schema enum `openldap` to create a basic configuration file called
Use the schema enum `ad` to create a basic configuration file called
`ldap.json`:
-@include '/examples/ldap/ad-config.mdx'
+@include 'ldap/example-config/ad/basic.mdx'
-
-
@@ -130,9 +127,7 @@ Use the schema enum `ad` to create a basic configuration file called
Use the schema enum `racf` and the name of your password policy to create a
basic configuration file called `ldap.json`:
-@include '/examples/ldap/racf-config.mdx'
-
-
+@include 'ldap/example-config/racf/basic.mdx'
@@ -147,35 +142,19 @@ Apply your configuration details so Vault can communicate with your LDAP server.
-Use `vault write` with the `{mount_path}/config` endpoint to apply your
-configuration file:
-
-```shell-session
-$ vault write /config @ldap.json
-```
-
-For example:
-
-
-
-```shell-session
-$ vault write devcreds/config @ldap.json
-```
-
-
+@include 'ldap/apply-config/cli.mdx'
-TBD
+@include 'ldap/apply-config/api.mdx'
-
-
+
@include 'gui-instructions/configure-secrets-plugin.mdx'
@@ -192,58 +171,20 @@ TBD
## Step 4: Rotate the root password
-Once you connect Vault and your LDAP server, rotate the root password so only
-Vault knows the credentials.
+Once you connect Vault and your LDAP server, rotate the root password for the
+`binddn` account so that only Vault knows the credentials.
-Use `vault write` with the `rotate-root` endpoint to rotate the credential:
-
-```shell-session
-$ vault write -f /rotate-root
-```
-
-For example:
-
-
-
-```shell-session
-$ vault write -f devcreds/rotate-root
-```
-
-
+@include 'ldap/rotate-root/cli.mdx'
-Make a `POST` call to
-[`/{mount_path}/rotate-root`](/vault/api-docs/secret/ldap#rotate-root-password)
-to rotate the credential::
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys//rotate-root
-```
-
-For example:
-
-
-
-```shell-session
-$ curl \
- --request POST \
- --header "X-Vault-Token: ${VAULT_TOKEN}" \
- --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
- ${VAULT_ADDR}/v1/sys/devcreds/rotate-root
-```
-
-
+@include 'ldap/rotate-root/api.mdx'
diff --git a/content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin.mdx b/content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin.mdx
index 1edee56d75..fc7b5e5659 100644
--- a/content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin.mdx
+++ b/content/vault/v1.21.x/content/partials/gui-instructions/configure-secrets-plugin.mdx
@@ -1,5 +1,5 @@
-- If you just enabled a plugin, click "Configure ". Otherwise, open
- the **Configure** page for the plugin:
+- If you have the plugin landing page open, click **Configure {plugin_type} >**.
+ Otherwise:
1. Open the GUI for your Vault instance.
@@ -10,4 +10,4 @@
1. Click the plugin mount you want to configure.
- 1. Click "Configure ".
\ No newline at end of file
+ 1. Click **Configure {plugin_type} >**.
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/apply-config/api.mdx b/content/vault/v1.21.x/content/partials/ldap/apply-config/api.mdx
new file mode 100644
index 0000000000..7fa9817c25
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/apply-config/api.mdx
@@ -0,0 +1,27 @@
+Make a `POST` call to
+[`/{mount_path}/config`](/vault/api-docs/secret/ldap#configuration-management)
+to apply your configuration file, `ldap-config.json`:
+
+```shell-session
+$ curl \
+ --request POST \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data @ldap.json \
+ ${VAULT_ADDR}/v1//config
+```
+
+For example:
+
+
+
+```shell-session
+$ curl \
+ --request POST \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data @ldap.json \
+ ${VAULT_ADDR}/v1/devcreds/config
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/apply-config/cli.mdx b/content/vault/v1.21.x/content/partials/ldap/apply-config/cli.mdx
new file mode 100644
index 0000000000..3dec29b59b
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/apply-config/cli.mdx
@@ -0,0 +1,17 @@
+Use `vault write` with the
+[`{mount_path}/config`](/vault/api-docs/secret/ldap#configuration-management)
+path to apply your `ldap.json` configuration file:
+
+```shell-session
+$ vault write /config @ldap.json
+```
+
+For example:
+
+
+
+```shell-session
+$ vault write devcreds/config @ldap.json
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/apply-config/gui.mdx b/content/vault/v1.21.x/content/partials/ldap/apply-config/gui.mdx
new file mode 100644
index 0000000000..a1d6090995
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/apply-config/gui.mdx
@@ -0,0 +1,5 @@
+@include 'gui-instructions/configure-secrets-plugin.mdx'
+
+- Select your LDAP schema.
+- Update the rotation details according to your configuration file.
+- Click **Save**.
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/create-static-role/api.mdx b/content/vault/v1.21.x/content/partials/ldap/create-static-role/api.mdx
new file mode 100644
index 0000000000..1dd3e428b9
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/create-static-role/api.mdx
@@ -0,0 +1,28 @@
+Make a `POST` call to
+[`/{mount_path}/static-role`](/vault/api-docs/secret/ldap#static-roles)
+with your static role configuration, `ldap-role.json`, to create a new static
+role:
+
+```shell-session
+$ curl \
+ --request POST \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data @ldap-role.json \
+ ${VAULT_ADDR}/v1//static-role
+```
+
+For example:
+
+
+
+```shell-session
+$ curl \
+ --request POST \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data @ldap-role.json \
+ ${VAULT_ADDR}/v1/devcreds/static-role
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/create-static-role/cli.mdx b/content/vault/v1.21.x/content/partials/ldap/create-static-role/cli.mdx
new file mode 100644
index 0000000000..4561c5b150
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/create-static-role/cli.mdx
@@ -0,0 +1,18 @@
+Use `vault write` with the
+[`/{mount_path}/static-role`](/vault/api-docs/secret/ldap#static-roles)
+path and your static role configuration, `ldap-role.json`, to create a new
+static role:
+
+```shell-session
+$ vault write /static-role @ldap-role.json
+```
+
+For example:
+
+
+
+```shell-session
+$ vault write devcreds/static-role @ldap-role.json
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/delete-static-role/api.mdx b/content/vault/v1.21.x/content/partials/ldap/delete-static-role/api.mdx
new file mode 100644
index 0000000000..c2f181938d
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/delete-static-role/api.mdx
@@ -0,0 +1,28 @@
+Make a `DELETE` call to
+[`/{mount_path}/static-role`](/vault/api-docs/secret/ldap#static-roles)
+with your static role configuration, `ldap-role.json`, to delete the static
+role:
+
+```shell-session
+$ curl \
+ --request DELETE \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data @ldap-role.json \
+ ${VAULT_ADDR}/v1//static-role
+```
+
+For example:
+
+
+
+```shell-session
+$ curl \
+ --request DELETE \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data @ldap-role.json \
+ ${VAULT_ADDR}/v1/devcreds/static-role
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/delete-static-role/cli.mdx b/content/vault/v1.21.x/content/partials/ldap/delete-static-role/cli.mdx
new file mode 100644
index 0000000000..4561c5b150
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/delete-static-role/cli.mdx
@@ -0,0 +1,18 @@
+Use `vault write` with the
+[`/{mount_path}/static-role`](/vault/api-docs/secret/ldap#static-roles)
+path and your static role configuration, `ldap-role.json`, to create a new
+static role:
+
+```shell-session
+$ vault write /static-role @ldap-role.json
+```
+
+For example:
+
+
+
+```shell-session
+$ vault write devcreds/static-role @ldap-role.json
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/enable/api.mdx b/content/vault/v1.21.x/content/partials/ldap/enable/api.mdx
new file mode 100644
index 0000000000..267935dee7
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/enable/api.mdx
@@ -0,0 +1,28 @@
+Make a `POST` call to
+[`/sys/mounts/{mount_path}`](/vault/api-docs/system/mounts#enable-secrets-engine):
+
+```shell-session
+$ curl \
+ --request POST \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data '{"type": "ldap"}' \
+ ${VAULT_ADDR}/v1/sys/mounts/
+```
+
+For example:
+
+
+
+```shell-session
+$ curl \
+ --request POST \
+ --header "X-Vault-Token: ${VAULT_TOKEN}" \
+ --namespace "X-Vault-Namespace: ${VAULT_NAMESPACE}" \
+ --data '{"type": "ldap"}' \
+ ${VAULT_ADDR}/v1/sys/mounts/devcreds
+```
+
+
+
+`/sys/mounts/{mount_path}` does not return data on success.
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/enable/cli.mdx b/content/vault/v1.21.x/content/partials/ldap/enable/cli.mdx
new file mode 100644
index 0000000000..a635f421b1
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/enable/cli.mdx
@@ -0,0 +1,13 @@
+Use `vault secrets enable` to establish a new instance of the `ldap` plugin. By
+default, Vault uses the plugin name as the mount path. To configure a custom
+mount path, use the `-path` flag:
+
+```shell-session
+$ vault secrets enable -path ldap
+```
+
+For example:
+
+```shell-session
+$ vault secrets enable -path devcreds ldap
+```
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/enable/gui.mdx b/content/vault/v1.21.x/content/partials/ldap/enable/gui.mdx
new file mode 100644
index 0000000000..203ecb3d78
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/enable/gui.mdx
@@ -0,0 +1,5 @@
+@include 'gui-instructions/enable-secrets-plugin.mdx'
+
+- Select the "LDAP" plugin.
+
+- Enter a unique path for the plugin and set your basic plugin settings.
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/basic.mdx
similarity index 89%
rename from content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx
rename to content/vault/v1.21.x/content/partials/ldap/example-config/ad/basic.mdx
index edd8ccd72f..0be735c4ca 100644
--- a/content/vault/v1.21.x/content/partials/examples/ldap/ad-config.mdx
+++ b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/basic.mdx
@@ -10,7 +10,7 @@
For example:
-
+
```json
{
@@ -22,3 +22,4 @@ For example:
}
```
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/example-config/ad/disable-rotation.mdx b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/disable-rotation.mdx
new file mode 100644
index 0000000000..daf367a02e
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/disable-rotation.mdx
@@ -0,0 +1,25 @@
+```json
+{
+ "schema": "ad",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "disable_automated_rotation": "true"
+}
+```
+
+For example:
+
+
+
+```json
+{
+ "schema": "ad",
+ "binddn": "cn=admin,dc=abc,dc=com",
+ "bindpass": "iamabadpassword",
+ "url": "ldaps://138.91.247.105",
+ "disable_automated_rotation": "true"
+}
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/example-config/ad/period-rotation.mdx b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/period-rotation.mdx
new file mode 100644
index 0000000000..05c2cef77d
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/period-rotation.mdx
@@ -0,0 +1,29 @@
+```json
+{
+ "schema": "ad",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "credential_type": "",
+ "rotation_schedule": "",
+ "rotation_period": ""
+}
+```
+
+For example:
+
+
+
+```json
+{
+ "schema": "ad",
+ "binddn": "cn=admin,dc=abc,dc=com",
+ "bindpass": "iamabadpassword",
+ "url": "ldaps://138.91.247.105",
+ "credential_type": "password",
+ "rotation_schedule": "",
+ "rotation_period": "24h"
+}
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/ldap/example-config/ad/scheduled-rotation.mdx b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/scheduled-rotation.mdx
new file mode 100644
index 0000000000..078aff5270
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/example-config/ad/scheduled-rotation.mdx
@@ -0,0 +1,31 @@
+```json
+{
+ "schema": "ad",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "credential_type": "",
+ "rotation_schedule": "",
+ "rotation_window": "",
+ "rotation_period": "0"
+}
+```
+
+For example:
+
+
+
+```json
+{
+ "schema": "ad",
+ "binddn": "cn=admin,dc=abc,dc=com",
+ "bindpass": "iamabadpassword",
+ "url": "ldaps://138.91.247.105",
+ "credential_type": "password",
+ "rotation_schedule": "0 0 * * SAT",
+ "rotation_window": "1hr",
+ "rotation_period": "0"
+}
+```
+
+
\ No newline at end of file
diff --git a/content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx b/content/vault/v1.21.x/content/partials/ldap/example-config/openldap/basic.mdx
similarity index 92%
rename from content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx
rename to content/vault/v1.21.x/content/partials/ldap/example-config/openldap/basic.mdx
index c0da77e628..7f36e7ae50 100644
--- a/content/vault/v1.21.x/content/partials/examples/ldap/openldap-config.mdx
+++ b/content/vault/v1.21.x/content/partials/ldap/example-config/openldap/basic.mdx
@@ -10,7 +10,7 @@
For example:
-
+
```json
{
diff --git a/content/vault/v1.21.x/content/partials/ldap/example-config/openldap/disable-rotation.mdx b/content/vault/v1.21.x/content/partials/ldap/example-config/openldap/disable-rotation.mdx
new file mode 100644
index 0000000000..986a24e3e8
--- /dev/null
+++ b/content/vault/v1.21.x/content/partials/ldap/example-config/openldap/disable-rotation.mdx
@@ -0,0 +1,25 @@
+```json
+{
+ "schema": "openldap",
+ "binddn": "",
+ "bindpass": "",
+ "url": "",
+ "disable_automated_rotation": "true"
+}
+```
+
+For example:
+
+