თუ იყენებთ WHMCS-ს, მის ნაცვლად გამოიყენეთ WHMCS მოდული — ეს გვერდი განკუთვნილია ყველაფერი დანარჩენისთვის. არსებობს ორი ვარიანტი, ორივე უფასო და ორივე GPL-2.0-or-later ლიცენზიით.
HostBill
ჰოსტინგის მოდული იგივე ექვსი მოქმედებით, რაც WHMCS-ის ვერსიაში.
- ჩამოტვირთეთ და განარქივეთ.
- ატვირთეთ
zinn დირექტორია includes/modules/Hosting/ გზაზე, რათა ფაილები განთავსდეს აქ:
includes/modules/Hosting/zinn/class.zinn.php და includes/modules/Hosting/zinn/ZinnHostBillClient.php.
- Settings → Modules → Hosting, გააქტიურეთ Zinn Digital® და დაამატეთ კავშირი:
- API address:
https://api.zinndigital.com
- API key: თქვენი Zinn® API გასაღები (
password ველი, შესაბამისად HostBill ინახავს მას დაშიფრულად)
- პროდუქტზე მიუთითეთ Product line (მაგ.
mainstream), Stack (ნაგულისხმევად wordpress), და სურვილისამებრ Application და PHP version.
- დააჭირეთ Test connection.
⛔ არ გადაარქვათ სახელი zinn დირექტორიას. HostBill-ის ჩამტვირთავი ეძებს კლასს დირექტორიის სახელის მიხედვით, ამიტომ სახელის გადარქმევის შემთხვევაში მიიღებთ მოდულს, რომელსაც პანელი აჩვენებს, მაგრამ არასოდეს იძახებს.
ყველაფერი დანარჩენი — PHP კლიენტი
ერთი ფაილი, არანაირი დამოკიდებულება, არანაირი წინასწარი მოთხოვნა პანელზე. ჩასვით ZinnProvisioning.php თქვენს კოდში და გამოიძახეთ ექვსი მეთოდი.
require_once 'ZinnProvisioning.php';
$zinn = new ZinnProvisioning(getenv('ZINN_API_KEY'));
// When an order is paid — once per CUSTOMER, then once per SERVICE:
$orgId = $zinn->account('customer-4211', 'Acme Ltd');
$siteId = $zinn->provision('service-9915', $orgId, 'acme.com', 'mainstream', 'wordpress');
// Store $orgId against your customer and $siteId against your service.
$zinn->suspend($siteId, 'INV-2026-114 unpaid'); // an invoice goes unpaid
$zinn->unsuspend($siteId); // they pay
$zinn->terminate($siteId); // they cancel — schedules a deletion
// When they click "log in to my hosting" — mint it on the CLICK, never on page render:
header('Location: ' . $zinn->signInLink($siteId));
არ წერთ PHP-ზე? იგივე გამოძახებები ხელმისაწვდომია API ცნობარში და შეგიძლიათ შეასრულოთ ისინი ნებისმიერი პლატფორმიდან.
API გასაღები
შვიდი ნებართვა და მეტი არაფერი: org.create, org.read, sites.create, sites.view, sites.delete, reseller.view, reseller.provision.
⛔ არა reseller.manage. გასაღებს, რომელსაც ბილინგის პანელში ათავსებთ, უნდა შეეძლოს კლიენტის შეჩერება გადაუხდელობის გამო და მისი ავტორიზაცია; მას არ უნდა შეეძლოს თქვენი გადახდის შლუზის მონაცემების გადაწერა.
ორი წესი, რომელთა დარღვევაც ფული ჯდება
- დააკავშირეთ ანგარიში თქვენს კლიენტთან (CUSTOMER), ხოლო საიტი თქვენს სერვისთან (SERVICE). კლიენტის მეორე შეკვეთა უნდა მოხვდეს იმ ანგარიშში, რომელიც მას უკვე აქვს. თუ ორივეს სერვისთან დააკავშირებთ, ერთი კლიენტი მიიღებს სამ დაუკავშირებელ ანგარიშს და სამ ცალკეულ მართვის პანელს.
- გაგზავნეთ იდემპოტენტურობის გასაღები (idempotency key) ყოველ შექმნაზე, მიღებული ობიექტის თქვენივე იდენტიფიკატორიდან. ბილინგის ყველა სისტემა აკეთებს განმეორებით მცდელობას — შლუზის შეტყობინება ორჯერ მოდის, ადმინისტრატორი თავიდან უშვებს წარუმატებელ პროვიჟენინგს, კლიენტი ორჯერ აჭერს ღილაკს. მის გარეშე მეორე მცდელობა ქმნის მეორე საიტს და ამისთვის თქვენ გერიცხებათ გადასახადი. ორივე მოდული და PHP კლიენტი ამას თქვენს მაგივრად აკეთებს; თუ API-ს პირდაპირ იძახებთ, გაგზავნეთ
Idempotency-Key.
სამი ველი, რომელთა გამოტოვებაც ადვილია
თითოეული მათგანი არღვევს მთლიან ოპერაციას და არცერთი არ ვლინდება სხვაგვარად, თუ არა ვალიდაციის შეცდომით — გარდა პირველისა, რომელიც ჩანს, როგორც საერთოდ არაფერი:
- ⛔⛔ კლიენტი უნდა დაემატოს გეგმას მისი პირველი საიტის მომზადებამდე,
POST /v1/reseller/clients/{orgId}/plan მოთხოვნით, ხოლო მისი subscription_id უნდა გადაეცეს POST /v1/sites-ს. ეს არის შემთხვევა, როდესაც შეცდომის შეტყობინება არ ჩნდება. ახალი კლიენტის ანგარიშს არ გააჩნია გამოწერა, ხოლო POST /v1/sites-ს არ აქვს გეგმის ველი, ამიტომ მის გარეშე მომზადებულ საიტს საერთოდ არ ექნება გეგმა: თქვენი საბითუმო ამონაწერი იქმნება თქვენი კლიენტების აქტიური გამოწერებიდან, შესაბამისად, ახალი ჩანაწერი არ იქმნება და Zinn® არაფერს დაგაკისრებთ ჰოსტინგის მუშაობის მანძილზე; თქვენი კლიენტი ვერ მიიღებს ლიმიტებს, ამიტომ მის საიტზე კვოტა არ გავრცელდება; და განახლებისთვის შესაცვლელიც არაფერი იქნება. შეკვეთა აბრუნებს 201-ს, საიტი მზადდება და გამართულად ფუნქციონირებს. არცერთი მხარე ამის შესახებ არაფერს ატყობინებს.
თანმიმდევრობას მნიშვნელობა აქვს: POST /v1/sites აღრიცხავს იმ გამოწერას, რომელიც არსებობს მისი გაშვების მომენტში, ამიტომ მოგვიანებით დაყენებული გეგმა რეტროსპექტიულად არ მიებმება.
POST /v1/sites მოითხოვს stack_type-ს. გამოტოვების შემთხვევაში ვერცერთი შეკვეთა ვერ შესრულდება წარმატებით.
DELETE /v1/sites/{siteId} მოითხოვს ტანს {"confirm_domain": "<the site's own domain>"} — აკრეფით დადასტურებას, რადგან ეს არის დესტრუქციული ზმნა. გამოტოვების შემთხვევაში ვერცერთი გაუქმება ვერ შესრულდება წარმატებით, ამიტომ სერვისი გააგრძელებს მუშაობას და თქვენ კვლავ დაგერიცხებათ საფასური. წაიკითხეთ დომენი GET /v1/reseller/services/{siteId}-დან თქვენი ჩანაწერის გამოყენების ნაცვლად: იგი შედარდება საიტის ძირითად დომენთან და არასდროს მეორად სახელთან (alias).
წაიკითხეთ მთლიანი შეცდომა და არა მხოლოდ წინადადება
ვალიდაციის უარყოფის შეტყობინება გამიზნულად ზოგადია — "The request was well-formed but failed validation." — რადგან ქმედითი ნაწილი მოცემულია details-ში, სადაც მითითებულია ველი და მიზეზი. ორივე მოდული და PHP კლიენტი მას ურთავენ იმ შეტყობინებას, რომელსაც აჩვენებენ თქვენს ადმინისტრატორს. თუ თავად იძახებთ API-ს, წაიკითხეთ error.details; ზოგიერთი ჩანაწერი შეიცავს მხოლოდ მნიშვნელობას წინადადების ნაცვლად, სწორედ ასე მიიღებთ max_sites: 0-ს, როდესაც თქვენს გადამყიდველის გეგმაში ადგილი აღარ არის.
თქვენს პირველ შეკვეთამდე
საიტები, რომლებსაც თქვენი კლიენტები ყიდულობენ, ითვლება თქვენი გადამყიდველის გეგმის საიტების ლიმიტში, ამიტომ გჭირდებათ გეგმა თავისუფალი ადგილით. კავშირის ტესტს არ შეუძლია ამის აღმოჩენა — ის კითხულობს თქვენს პროგრამას და არაფერს ამზადებს — ამიტომ ის ასახავს გამართულ ანგარიშს, რომელსაც ჯერ არ შეუძლია გაყიდვა. ლიმიტის გარეშე განთავსებული შეკვეთა უარყოფილი იქნება ზუსტად ამ შინაარსის შეტყობინებით.
გადაამოწმეთ თქვენი ჩამოტვირთვა
ორივე არქივი მიეწოდება TLS-ით ჩვენი საკუთარი ჰოსტის სახელიდან, სხვაგან გადამისამართების გარეშე, მათი SHA-256 საკონტროლო ჯამები კი დაბეჭდილია ჩამოტვირთვის ბმულების გვერდით ჩამოტვირთვების გვერდზე.