diff --git a/README.md b/README.md
index 5a9f328..d3ad551 100644
--- a/README.md
+++ b/README.md
@@ -9,6 +9,8 @@ This module is designed for use with the following DNS providers:
- [Vultr](https://www.vultr.com/)
+- [BIND](https://www.isc.org/bind/)
+
## FOSSBilling Module Installation instructions
### 1. Download and Install FOSSBilling:
@@ -21,13 +23,19 @@ First, download this repository. After successfully downloading the repository,
Go to `[FOSSBilling]/modules/Servicedns/Providers` directory and run the `composer install` command.
-### 3. Addition of Synchronization Scripts:
+### (BIND Module only) 3. Addition of Synchronization Scripts:
+
+The BIND provider has an additional synchronization script which can be found at `[FOSSBilling]/modules/Servicedns/Crons/Bind.php`. It needs to be configured with your BIND installation parameters, so it can generate the zones regularly.
+
+### (BIND Module only) 4. Setting Up the Cron Job:
+
+You need to set up a hourly cron job that runs the sync module. Open crontab using the command `crontab -e` in your terminal.
-**not yet implemented**
+Add the following cron job:
-### 4. Setting Up the Cron Job:
+`0 * * * * php [FOSSBilling]/modules/Servicedns/Crons/Bind.php`
-**not yet implemented**
+This command schedules the synchronization script to run hourly.
### 5. Activate the DNS hosting module:
diff --git a/Servicedns/Crons/Bind.php b/Servicedns/Crons/Bind.php
new file mode 100644
index 0000000..5bf1200
--- /dev/null
+++ b/Servicedns/Crons/Bind.php
@@ -0,0 +1,117 @@
+setAttribute(PDO::ATTR_ERRMODE, PDO::ERRMODE_EXCEPTION);
+
+ // Fetch domain names and IDs from service_dns table
+ $domainsStmt = $pdo->query("SELECT id, domain_name FROM service_dns");
+ $domains = $domainsStmt->fetchAll(PDO::FETCH_ASSOC);
+ $timestamp = time();
+
+ foreach ($domains as $domain) {
+ $domainName = $domain['domain_name'];
+ $domainId = $domain['id'];
+
+ $stmt = $pdo->prepare("SELECT * FROM service_dns_records WHERE domain_id = :domainId");
+ $stmt->execute(['domainId' => $domainId]);
+
+ $zone = new Zone($domainName.'.');
+ $zone->setDefaultTtl(3600);
+
+ $soa = new ResourceRecord;
+ $soa->setName('@');
+ $soa->setClass(Classes::INTERNET);
+ $soa->setRdata(Factory::Soa(
+ 'example.com.',
+ 'post.example.com.',
+ $timestamp,
+ 3600,
+ 14400,
+ 604800,
+ 3600
+ ));
+ $zone->addResourceRecord($soa);
+
+ $ns1 = new ResourceRecord;
+ $ns1->setName('@');
+ $ns1->setClass(Classes::INTERNET);
+ $ns1->setRdata(Factory::Ns('ns1.nameserver.com.'));
+ $zone->addResourceRecord($ns1);
+
+ $ns2 = new ResourceRecord;
+ $ns2->setName('@');
+ $ns2->setClass(Classes::INTERNET);
+ $ns2->setRdata(Factory::Ns('ns2.nameserver.com.'));
+ $zone->addResourceRecord($ns2);
+
+ while ($row = $stmt->fetch(PDO::FETCH_ASSOC)) {
+ $recordType = $row['type'];
+ $host = $row['host'];
+ $value = $row['value'];
+ $ttl = $row['ttl'] ?? 3600; // Default TTL
+
+ $record = new ResourceRecord();
+ $record->setName($host);
+ $record->setTtl($ttl);
+
+ switch ($recordType) {
+ case 'A':
+ $record->setRdata(Factory::A($value));
+ break;
+ case 'AAAA':
+ $record->setRdata(Factory::Aaaa($value));
+ break;
+ case 'MX':
+ $priority = $row['priority'] ?? 0;
+ $record->setRdata(Factory::Mx($priority, $value));
+ break;
+ case 'CNAME':
+ $record->setRdata(Factory::Cname($value));
+ break;
+ case 'TXT':
+ $formattedValue = trim($value, '"');
+ $record->setRdata(Factory::Txt($formattedValue));
+ break;
+ case 'SPF':
+ $formattedValue = trim($value, '"');
+ $record->setRdata(Factory::Spf($formattedValue));
+ break;
+ case 'DS':
+ // DS record typically requires key tag, algorithm, digest type, and digest
+ // Assuming these are provided in a formatted string or individual columns
+ // $value format should be "keyTag algorithm digestType digest"
+ list($keyTag, $algorithm, $digestType, $digest) = explode(' ', $value);
+ $record->setRdata(Factory::Ds($keyTag, $algorithm, $digestType, $digest));
+ break;
+ // ... Other record types
+ }
+
+ $zone->addResourceRecord($record);
+ }
+
+ // Generate zone file content for each domain
+ $builder = new AlignedBuilder();
+ $zoneFileContent = $builder->build($zone);
+
+ // Generate zone for each domain and reload BIND
+ file_put_contents("/var/lib/bind/db.$domainName", $zoneFileContent);
+
+ exec("rndc reload {$domainName}.", $output, $return_var);
+ exec("rndc notify {$domainName}.", $output, $return_var);
+ }
+
+} catch (PDOException $e) {
+ echo "Connection failed: " . $e->getMessage();
+}
diff --git a/Servicedns/Providers/Bind.php b/Servicedns/Providers/Bind.php
new file mode 100644
index 0000000..e16dedc
--- /dev/null
+++ b/Servicedns/Providers/Bind.php
@@ -0,0 +1,86 @@
+dnsProvider = new Providers\Vultr($apiToken);
break;
+ case 'Bind':
+ $this->dnsProvider = new Providers\Bind();
+ break;
// Add more cases for additional providers
default:
throw new \FOSSBilling\Exception("Unknown DNS provider: {$providerName}");
diff --git a/Servicedns/html_admin/mod_servicedns_config.html.twig b/Servicedns/html_admin/mod_servicedns_config.html.twig
index 56d53b0..a83d98c 100644
--- a/Servicedns/html_admin/mod_servicedns_config.html.twig
+++ b/Servicedns/html_admin/mod_servicedns_config.html.twig
@@ -11,6 +11,7 @@
+