Utilitarul keytool livrat împreună cu Java Development Kit (JDK) creează o pereche de chei într-un keystore Java și o transformă într-un CSR (Certificate Signing Request), blocul codificat pe care o Autoritate de Certificare (CA) îl citește pentru a vă identifica înainte de a emite un certificat. Pentru semnarea codului, ceea ce keytool poate fi folosit în mod legitim s-a schimbat la 1 iunie 2023. Acest ghid stabilește mai întâi regula, apoi parcurge comenzile keytool care sunt încă corecte: împotriva unui keystore software pentru semnarea internă, și împotriva unui token hardware sau HSM prin PKCS#11.
Cheile de semnare a codului trebuie generate pe hardware
Din 1 iunie 2023, Cerințele de bază pentru semnarea codului ale CA/Browser Forum impun ca cheia privată pentru fiecare certificat de semnare a codului de încredere publică să fie generată și stocată într-un modul criptografic hardware care îndeplinește standardul FIPS 140-2 Nivel 2, Common Criteria EAL4+ sau un standard echivalent. Cheia trebuie să fie neexportabilă. Acest lucru se aplică atât certificatelor standard (Validare a Organizației), cât și celor cu Validare Extinsă. Semnarea codului EV a necesitat întotdeauna hardware; schimbarea din 2023 a extins aceeași regulă și la certificatele standard. Aceleași cerințe stabilesc o dimensiune minimă a cheii de RSA 3072 pentru certificatele de semnare a codului, în vigoare de la 1 iunie 2021.
Consecința pentru această pagină este directă. Un fișier keystore pe care keytool îl creează pe laptopul sau serverul dvs., fie că este PKCS12 sau formatul mai vechi JKS, deține o cheie software. Un CSR generat din acesta nu este acceptat de o Autoritate de Certificare publică pentru un certificat de semnare a codului. Autoritățile de Certificare au încetat să mai susțină generarea de chei bazată pe browser și fișierele de chei descărcabile pentru aceste produse. Cheia dvs. provine acum din unul dintre următoarele două locuri:
- Un token preconfigurat pe care CA vi-l livrează. CA generează perechea de chei și CSR-ul pe un token USB certificat de partea sa, încarcă certificatul emis pe acesta și vă trimite prin poștă tokenul. Nu există niciun CSR pe care să trebuiască să-l creați.
- Propriul dvs. HSM sau token, cu atestare a cheii. Generați cheia în interiorul dispozitivului, produceți un CSR din aceasta și trimiteți un fișier de atestare care dovedește CA-ului că cheia a fost creată pe hardware conform și nu poate fi exportată. Ambele părți sunt necesare; un CSR fără atestare validă este respins.
Care rută se aplică este decis la comandă. Pentru comparație, consultați metodele de livrare a certificatelor de semnare a codului. Dacă dețineți deja hardware conform, urmați ghidul pentru dispozitivul dvs.: generarea CSR și atestarea YubiKey 5 FIPS sau ghidul CSR și atestare pentru Luna Network Attached HSM v7.x.
Unde se mai potrivește keytool
Nimic din cele de mai sus nu îl scoate din uz pe keytool. Acesta rămâne instrumentul potrivit în trei situații, iar doar prima dintre ele produce un CSR pe care îl puteți trimite unei CA publice:
- Ca interfață PKCS#11 pentru tokenul sau HSM-ul dvs. keytool vorbește nativ PKCS#11. Îndreptați-l către biblioteca PKCS#11 a furnizorului dvs., iar cheia nu părăsește niciodată dispozitivul, în timp ce familiara comandă -certreq produce în continuare CSR-ul. Comenzile se află în secțiunea hardware de mai jos.
- Pentru semnarea internă sau la nivel de întreprindere. Dacă semnați software intern cu propria CA a organizației dvs., politica dvs. internă guvernează stocarea cheilor, nu Cerințele de bază publice. Un keystore software este o alegere normală în acest caz.
- Pentru repetiție. Obținerea corectă a numelui subiectului din prima încercare este mai ușoară dacă ați parcurs deja o dată solicitările împotriva unui keystore de unică folosință.
O limitare pe care merită să o cunoașteți înainte de a începe: keytool nu generează atestarea cheii. Atestarea este produsă de instrumentele proprii ale furnizorului tokenului sau HSM-ului, astfel încât chiar și pe calea PKCS#11 veți folosi utilitarul furnizorului pentru acel fișier, iar keytool doar pentru CSR.
Generați CSR-ul cu keytool
Dacă ați creat deja CSR-ul și Autoritatea de Certificare a emis certificatul, treceți direct la importul răspunsului CA, pasul care eșuează silențios atunci când aliasul nu se potrivește.
keytool vine împreună cu JDK, așa că instalați mai întâi un JDK actual dacă nu aveți unul. JDK 25 este versiunea curentă de suport pe termen lung, iar JDK 26 este versiunea curentă pe termen scurt. Comenzile de mai jos rulează pe JDK 17 și versiuni ulterioare, iar diferențele de versiune care contează sunt notate acolo unde apar. Confirmați că instrumentul este pe calea dvs.:
java -version
keytool -help
jarsigner -version
Un Java Runtime Environment de sine stătător nu este suficient, iar un keytool funcțional nu este dovada că aveți un JDK: vechiul Oracle JRE 8 livrează keytool, dar nu și jarsigner. Rulați toate cele trei comenzi acum. Dacă primele două răspund, iar a treia nu, vă aflați pe un JRE, iar instalarea unui JDK în acest moment este mai ușoară decât descoperirea acestui lucru atunci când mergeți să semnați.
Pasul 1: Creați keystore-ul și perechea de chei
Rulați acest lucru într-un terminal, sau în Command Prompt sau PowerShell pe Windows, din directorul în care doriți ca fișierul keystore să se afle:
keytool -genkeypair -alias codesign -keyalg RSA -keysize 3072 -storetype PKCS12 -keystore codesign.p12
Patru detalii din acea comandă diferă de instrucțiunile mai vechi, și fiecare dintre ele contează:
- -genkeypair, nu -genkey. Vechea formă -genkey încă rulează, iar keytool nu afișează niciun avertisment despre aceasta, dar este păstrată în sursă doar ca alias vechi și nu mai apare nicăieri în documentația JDK. Scrieți -genkeypair.
- -storetype PKCS12, nu JKS. JKS este formatul de keystore proprietar al Oracle. PKCS12 este cel standard în industrie și este implicit în JDK încă din Java 9. Dacă totuși creați un keystore JKS, keytool vă avertizează la fiecare comandă care îl atinge: „The JKS keystore uses a proprietary format. It is recommended to migrate to PKCS12 which is an industry standard format.”
- Numele fișierului nu stabilește formatul. Denumirea unui fișier keystore.jks nu îl transformă într-un keystore JKS. keytool preia tipul din -storetype, sau din proprietatea keystore.type din fișierul de securitate al JDK-ului atunci când îl omiteți. Pe JDK 9 și versiuni ulterioare, acea proprietate este pkcs12, astfel încât o comandă care scrie în keystore.jks fără -storetype produce în tăcere un fișier PKCS12 cu un nume înșelător.
- -keysize 3072, nu 2048. Cerințele de bază stabilesc RSA 3072 ca minim pentru semnarea codului, astfel încât o solicitare pe 2048 de biți este respinsă. JDK-urile actuale au implicit valoarea 3072 pentru RSA, dar JDK 17 și versiunile anterioare au implicit 2048, așa că treceți opțiunea explicit, iar comanda se comportă la fel peste tot.
Aliasul, codesign în exemplu, este eticheta pentru această intrare din interiorul keystore-ului. Alegeți ceva pe care îl veți recunoaște și notați-l: fiecare comandă ulterioară are nevoie de el, iar o nepotrivire este ceea ce strică importul certificatului descris mai jos.
O cheie ECDSA este de asemenea permisă. Înlocuiți -keyalg EC -groupname secp256r1 pentru opțiunile RSA dacă preferați P-256, și confirmați cu CA-ul dvs. că produsul pe care l-ați comandat susține ECDSA.
Pasul 2: Răspundeți la solicitările care construiesc numele dvs. distinctiv
keytool solicită o parolă pentru keystore de două ori, apoi pune șase întrebări în această ordine exactă. Ordinea contează: a doua solicitare cere unitatea organizațională, nu organizația, iar ghidurile mai vechi o listează greșit, astfel încât un cititor care introduce acolo numele companiei îl plasează în componenta greșită a numelui.
- Care este numele și prenumele dvs.? Acesta devine Numele Comun (CN), în ciuda formulării. Pentru un certificat de semnare a codului, CN-ul este identitatea editorului pe care utilizatorii o vor vedea, așa că introduceți numele legal exact al organizației dvs., sau propriul dvs. nume legal complet pentru un certificat individual. Nu introduceți aici un nume de domeniu.
- Care este numele unității dvs. organizaționale? Departamentul, de exemplu IT. Nu apăsați Enter pentru a-l omite: keytool va scrie atunci valoarea literală Unknown în nume, iar OU=Unknown ajunge în CSR-ul dvs. Dacă doriți deloc nicio unitate organizațională, folosiți forma -dname de mai jos și omiteți componenta OU din șir.
- Care este numele organizației dvs.? Numele legal înregistrat, scris așa cum apare în registrele oficiale. CA-ul verifică acest lucru în raport cu registrele publice.
- Care este numele orașului sau localității dvs.? Orașul de înregistrare, scris în întregime.
- Care este numele statului sau provinciei dvs.? Numele complet, nu o abreviere.
- Care este codul de țară din două litere pentru această unitate? Codul ISO, de exemplu US.
keytool afișează apoi numele asamblat și vă cere să îl confirmați:
Is CN=Example LLC, OU=IT, O=Example LLC, L=Miami, ST=Florida, C=US correct?
[no]:
Răspunsul implicit este no, așa că apăsarea Enter vă trimite înapoi prin toate cele șase întrebări. Tastați yes pentru a accepta. Citiți cu atenție linia mai întâi: aceasta este întregul nume distinctiv, nu doar Numele Comun, și fiecare componentă a acestuia intră în CSR.
Nu există o parolă separată pentru cheie pe un keystore PKCS12. Ghidurile mai vechi încheie acest pas cu „introduceți o parolă pentru cheie”, care este comportamentul JKS. Pe un keystore PKCS12, parola cheii este parola magazinului, iar dacă transmiteți -keypass cu o valoare diferită, keytool vă informează astfel: „Different store and key passwords not supported for PKCS12 KeyStores. Ignoring user-specified -keypass value.”
Pentru a evita complet solicitările, furnizați întregul nume cu -dname. Păstrați valoarea într-o singură pereche de ghilimele drepte:
keytool -genkeypair -alias codesign -keyalg RSA -keysize 3072 -storetype PKCS12 -keystore codesign.p12 -dname "CN=Example LLC, OU=IT, O=Example LLC, L=Miami, ST=Florida, C=US"
Nu includeți -storepass în linia de comandă și lăsați keytool să solicite parola. Transmiterea unei parole ca argument o scrie în istoricul shell-ului dvs. și o expune oricui poate lista procesele în rulare.
Pasul 3: Creați CSR-ul
Keystore-ul deține acum o cheie privată și un certificat auto-semnat temporar. Transformați acea intrare într-o solicitare de certificat:
keytool -certreq -alias codesign -keystore codesign.p12 -file codesign.csr
Introduceți parola keystore-ului atunci când vi se solicită. Nu aveți nevoie de -storetype aici: keytool detectează formatul unui fișier keystore care există deja. Aliasul trebuie să fie cel de la pasul 1, deoarece CSR-ul este semnat de cheia privată a acelei intrări.
Această comandă nu creează o cheie privată. Cheia a fost creată la pasul 1 și rămâne în interiorul keystore-ului, motiv pentru care fișierul keystore și parola sa sunt acum la fel de sensibile ca și cheia în sine. Oricine deține ambele poate semna software în numele dvs.
Pasul 4: Verificați CSR-ul înainte de a-l trimite
Un CSR respins costă un ciclu de validare, așa că decodați-l și recitiți-l:
keytool -printcertreq -file codesign.csr
Confirmați trei lucruri în rezultat. Linia Subject ar trebui să listeze detaliile dvs. în componentele corecte, cu numele legal al organizației în O și identitatea editorului în CN. Linia cheii publice ar trebui să indice 3072-bit RSA key sau mai mare. Algoritmul de semnătură ar trebui să fie un algoritm SHA-2: JDK-urile actuale semnează o solicitare RSA pe 3072 de biți cu SHA384withRSA, iar cele mai vechi folosesc SHA256withRSA, și oricare dintre ele este în regulă. Acel algoritm dovedește doar că dețineți cheia privată, și nu este algoritmul pe care CA-ul îl va folosi pentru a vă semna certificatul.
Puteți de asemenea să lipiți solicitarea în decodorul nostru de CSR pentru a citi aceleași câmpuri într-un browser.
Când trimiteți solicitarea, deschideți fișierul într-un editor de text simplu și copiați totul, inclusiv prima și ultima linie. keytool scrie aceste markere exacte, cu cinci cratime pe fiecare parte:
-----BEGIN NEW CERTIFICATE REQUEST-----
MIID3TCCAkUCAQAwaDELMAkGA1UEBhMCVVMxEDAOBgNVBAgTB0Zsb3JpZGExDjAM
...base64 encoded request...
-----END NEW CERTIFICATE REQUEST-----
Formularea NEW CERTIFICATE REQUEST este normală pentru rezultatul keytool, iar formularele de înscriere o acceptă. Dacă editorul dvs. a înlocuit orice succesiune de cratime cu o linie lungă, solicitarea va fi refuzată: retastați markerele ca cratime simple sau copiați fișierul cu un editor de cod în schimb.
Generați CSR-ul pe un token sau HSM cu keytool
Aceasta este calea care produce un CSR pe care o CA publică poate să îl proceseze. keytool comunică cu un token hardware prin furnizorul SunPKCS11, astfel încât perechea de chei este creată în interiorul dispozitivului și nu există niciodată ca fișier. Începeți prin a scrie un fișier mic de configurare, de exemplu token.cfg, care numește tokenul dvs. și indică biblioteca PKCS#11 pe care furnizorul dvs. a instalat-o:
name = token
library = /usr/local/lib/libeToken.so
Acele două linii, name și library, sunt singurele necesare. Calea bibliotecii este specifică furnizorului și diferă în funcție de sistemul de operare, așa că preluați-o din documentația tokenului dvs. mai degrabă decât din acest exemplu. Pe Windows este un DLL sub directorul de sistem. Fără o linie slot, furnizorul se atașează la primul slot pe care dispozitivul îl raportează, ceea ce este ceea ce doriți atunci când un singur token este conectat. Dacă aveți mai mult de un cititor sau token, adăugați fie slotListIndex cu poziția din acea listă, numărând de la zero, fie slot cu ID-ul numeric al slotului pe care utilitarul furnizorului dvs. îl afișează. Doar unul dintre cele două poate apărea în fișier, iar un ID de slot nu este același număr cu o poziție din listă, așa că nu ghiciți la slot = 0.
Listați ce se află pe dispozitiv. Tokenul furnizează aliasul, așa că aveți nevoie de acesta înaintea oricărui altceva:
keytool -list -keystore NONE -storetype PKCS11 -providerClass sun.security.pkcs11.SunPKCS11 -providerArg token.cfg
-keystore NONE este necesar ori de câte ori keystore-ul nu este un fișier, iar solicitarea de parolă cere PIN-ul tokenului. keytool acceptă de asemenea -addprovider SunPKCS11 -providerarg token.cfg în locul perechii -providerClass și -providerArg; ambele forme funcționează, iar documentația Autorității de Certificare arată de obicei forma mai veche.
Cu aliasul în mână, generați cheia pe dispozitiv și apoi solicitați CSR-ul pe baza acesteia:
keytool -genkeypair -alias codesign -keyalg RSA -keysize 3072 -keystore NONE -storetype PKCS11 -providerClass sun.security.pkcs11.SunPKCS11 -providerArg token.cfg -dname "CN=Example LLC, O=Example LLC, L=Miami, ST=Florida, C=US"
keytool -certreq -alias codesign -keystore NONE -storetype PKCS11 -providerClass sun.security.pkcs11.SunPKCS11 -providerArg token.cfg -file codesign.csr
Se aplică două avertismente. Unele tokenuri nu permit generarea de chei prin PKCS#11 și așteaptă să folosiți propriul utilitar al furnizorului, ceea ce este în regulă: keytool poate crea în continuare CSR-ul pe baza unei chei generate de instrumentul furnizorului. Și keytool nu poate produce fișierul de atestare pe care CA-ul dvs. îl va solicita, așa că generați-l cu instrumentele furnizorului în același timp cu cheia, urmând ghidul YubiKey sau Luna HSM.
Importați răspunsul CA în același alias
Când certificatul sosește, trebuie să meargă înapoi în intrarea care a generat CSR-ul. Importați-l oriunde altundeva, iar keytool va raporta în continuare succes în timp ce produce un keystore care nu poate semna, așa că citiți această secțiune înainte de a rula orice.
Importați mai întâi rădăcina CA-ului și orice certificate intermediare, fiecare sub propriul alias:
keytool -importcert -trustcacerts -alias caroot -file root.crt -keystore codesign.p12
keytool afișează certificatul pe care este pe cale să îl stocheze și întreabă Trust this certificate? cu no ca valoare implicită, așa că tastați yes. Verificați amprenta digitală în raport cu cea pe care Autoritatea dvs. de Certificare o publică înainte de a răspunde.
Omiteți importul rădăcinii, iar comanda următoare eșuează cu un mesaj care nu oferă niciun indiciu despre cauză:
keytool error: java.lang.Exception: Failed to establish chain from reply
Acum importați certificatul dvs. emis folosind același alias pe care l-ați folosit la pasul 1:
keytool -importcert -alias codesign -file codesign.crt -keystore codesign.p12
Mesajul pe care îl doriți este Certificate reply was installed in keystore. Acest lucru înseamnă că keytool a recunoscut o cheie privată existentă sub acel alias și a atașat certificatul emis și lanțul său la aceasta.
Dacă inventați în schimb un alias nou, keytool acceptă fișierul și afișează Certificate was added to keystore. Aceasta pare a fi un succes și nu este. keytool a stocat certificatul ca o intrare de încredere de sine stătătoare fără nicio cheie privată în spatele său, iar acea intrare nu poate semna niciodată nimic. Aliasul original, între timp, deține în continuare certificatul auto-semnat temporar din pasul 1. Verificați pe care dintre cele două îl aveți:
keytool -list -keystore codesign.p12
Aliasul dvs. de semnare trebuie să fie listat ca PrivateKeyEntry. Un alias afișat ca trustedCertEntry reprezintă greșeala descrisă mai sus. Ștergeți-l cu keytool -delete -alias wrongalias -keystore codesign.p12 și repetați importul pe aliasul corect. Adăugați -v la comanda de listare pentru a confirma că intrarea poartă acum un lanț complet de certificate, mai degrabă decât un singur certificat auto-semnat.
Pe un token hardware nu există nimic de importat în majoritatea cazurilor, deoarece CA-ul încarcă certificatul pe dispozitiv înainte de a-l expedia. Dacă CA-ul dvs. vă trimite un fișier de certificat pentru o cheie pe care ați generat-o pe propriul dvs. HSM, folosiți aceeași comandă -importcert cu opțiunile PKCS#11 din secțiunea anterioară.
Semnați un fișier JAR cu certificatul
Scopul plasării unui certificat de semnare a codului într-un keystore Java este semnarea fișierelor JAR cu jarsigner, care de asemenea vine livrat cu JDK. Cu certificatul instalat sub aliasul corect:
jarsigner -keystore codesign.p12 -tsa https://your-ca-timestamp-url application.jar codesign
Includeți întotdeauna -tsa cu adresa URL de marcare temporală pe care Autoritatea dvs. de Certificare o publică. O marcă temporală înregistrează faptul că JAR-ul a fost semnat în timp ce certificatul era încă valid, astfel încât semnătura continuă să funcționeze după expirarea certificatului. Fără una, fiecare copie a software-ului dvs. încetează să se mai valideze în ziua în care certificatul expiră.
Când cheia locuiește pe un token, îndreptați jarsigner către PKCS#11 exact așa cum face keytool:
jarsigner -keystore NONE -storetype PKCS11 -providerClass sun.security.pkcs11.SunPKCS11 -providerArg token.cfg -tsa https://your-ca-timestamp-url application.jar codesign
Dacă tokenul are prea puțin spațiu pentru lanțul complet de certificate, furnizați-l separat cu -certchain. Verificați rezultatul ulterior:
jarsigner -verify -verbose -certs application.jar
O rulare reușită afișează jar verified împreună cu numele distinctiv al semnatarului și detaliile marcajului temporal. JDK-urile actuale folosesc SHA-384 ca algoritm implicit de rezumat, astfel încât rareori aveți nevoie să setați manual -digestalg sau -sigalg.
Alte modalități de a crea această solicitare sunt acoperite în ghidurile OpenSSL, CertReq, Microsoft Management Console și macOS Keychain Access, iar aceeași regulă hardware se aplică tuturor acestora. Consultați de asemenea setul nostru complet de tutoriale de semnare a codului și prezentarea generală privind generarea CSR pentru certificatele de semnare a codului. Dacă aveți nevoie de un CSR keytool pentru un certificat de site web, mai degrabă decât unul de semnare a codului, urmați ghidul Tomcat sau JBoss în schimb.
Întrebări frecvente
Doar dacă keytool a generat cheia în interiorul unui token hardware sau HSM prin PKCS#11, și puteți furniza atestarea pe care Autoritatea de Certificare o solicită. Un CSR creat dintr-un fișier keystore obișnuit de pe calculatorul dvs. este o cheie software, iar din 1 iunie 2023 CA-urile publice nu emit certificate de semnare a codului pe baza cheilor software. Keystore-urile software rămân potrivite pentru semnarea cu o CA internă sau de întreprindere.
Folosiți -genkeypair. Forma -genkey este un alias vechi pe care JDK-ul îl acceptă în continuare fără niciun avertisment, dar a fost absent din documentație de-a lungul multor versiuni. Ambele fac același lucru astăzi; doar unul dintre ele este documentat.
Folosiți PKCS12. Este un format standard în industrie și a fost tipul implicit de keystore în JDK încă din Java 9, în timp ce JKS este proprietar Oracle și face ca keytool să afișeze un avertisment de migrare la fiecare comandă. Extensia fișierului nu are niciun efect: keytool decide formatul din -storetype, sau din proprietatea de securitate keystore.type atunci când o omiteți, astfel încât un fișier numit keystore.jks creat pe un JDK modern este de obicei un fișier PKCS12. Pentru a converti un keystore existent, rulați keytool -importkeystore -srckeystore keystore.jks -destkeystore keystore.p12 -deststoretype pkcs12.
RSA 3072 de biți sau mai mult, ceea ce Cerințele de bază pentru semnarea codului au impus din 1 iunie 2021, sau o cheie ECDSA echivalentă precum P-256. Treceți -keysize 3072 explicit, deoarece JDK 17 și versiunile anterioare au implicit 2048 de biți, iar acea solicitare este respinsă.
Aproape sigur ați importat răspunsul CA într-un alias nou, mai degrabă decât în aliasul care a generat CSR-ul. keytool îl stochează atunci ca un certificat de încredere de sine stătător fără nicio cheie privată atașată, și afișează Certificate was added to keystore, care se citește ca un succes. Rulați keytool -list -keystore codesign.p12: aliasul de semnare trebuie să apară ca PrivateKeyEntry, nu ca trustedCertEntry. Ștergeți intrarea greșită și importați din nou cu aliasul original, și ar trebui să vedeți Certificate reply was installed in keystore.
keytool nu poate construi o cale de la certificatul dvs. emis până la un certificat de care are deja încredere. Importați mai întâi rădăcina și certificatele intermediare ale CA-ului în același keystore, fiecare sub propriul alias cu -importcert -trustcacerts, apoi importați din nou certificatul dvs. Alternativ, importați un singur fișier care conține certificatul dvs. urmat de intermediari și de rădăcină.
Nu. Un certificat de semnare a codului este identificat prin utilizarea extinsă a cheii pentru semnarea codului, nu printr-un lanț de instrumente, astfel încât același certificat semnează fișiere JAR cu jarsigner și executabile Windows cu signtool. Ceea ce alegeți la comandă este metoda de livrare, care decide dacă CA-ul vă livrează un token preconfigurat sau generați cheia pe hardware pe care îl dețineți deja.
Cu un token sau HSM, cheia se află în interiorul dispozitivului și nu poate fi copiată în afara acestuia, ceea ce este întregul sens al cerinței. Cu un keystore software folosit pentru semnarea internă, cheia se află în fișierul keystore, astfel încât fișierul și parola sa împreună reprezintă secretul: păstrați-le într-o locație restricționată, nu le încărcați niciodată în controlul sursei, și lăsați keytool să solicite parola în loc să treceți -storepass pe linia de comandă, unde ar ajunge în istoricul shell-ului dvs.
Economisește 10% la certificatele SSL în momentul plasării comenzii!
Eliberare rapidă, criptare puternică, încredere în browser de 99,99%, suport dedicat și garanție de returnare a banilor în 25 de zile. Codul cuponului: SAVE10

