editing license

This commit is contained in:
Flatlogic Bot 2026-02-20 15:02:03 +00:00
parent 590f247c08
commit 2ab1263a06
3 changed files with 99 additions and 14 deletions

View File

@ -5,7 +5,10 @@ CREATE TABLE IF NOT EXISTS licenses (
id INT AUTO_INCREMENT PRIMARY KEY,
license_key VARCHAR(255) UNIQUE NOT NULL,
max_activations INT DEFAULT 1,
max_counters INT DEFAULT 1,
status ENUM('active', 'suspended', 'expired') DEFAULT 'active',
owner VARCHAR(255),
address TEXT,
created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP
) ENGINE=InnoDB;
@ -21,6 +24,6 @@ CREATE TABLE IF NOT EXISTS activations (
) ENGINE=InnoDB;
-- Seed some test data
INSERT INTO licenses (license_key, max_activations) VALUES ('FLAT-8822-1192-3301', 1);
INSERT INTO licenses (license_key, max_activations) VALUES ('FLAT-TEST-KEY-0001', 5);
INSERT INTO licenses (license_key, max_activations) VALUES ('FLAT-DEV-UNLIMITED', 999);
INSERT INTO licenses (license_key, max_activations, max_counters, owner) VALUES ('FLAT-8822-1192-3301', 1, 1, 'Client A');
INSERT INTO licenses (license_key, max_activations, max_counters, owner) VALUES ('FLAT-TEST-KEY-0001', 5, 10, 'Test User');
INSERT INTO licenses (license_key, max_activations, max_counters, owner) VALUES ('FLAT-DEV-UNLIMITED', 999, 999, 'Developer');

View File

@ -81,11 +81,13 @@ if ($endpoint === 'activate') {
$stmt->execute([$license['id'], $fingerprint, $domain, $product]);
}
// Success: Return signed token
// Success: Return signed token and license info
$token = hash_hmac('sha256', $key . $fingerprint, SERVER_SECRET);
echo json_encode([
'success' => true,
'activation_token' => $token
'activation_token' => $token,
'max_activations' => (int)$license['max_activations'],
'max_counters' => (int)$license['max_counters']
]);
exit;
}
@ -103,12 +105,17 @@ if ($endpoint === 'verify') {
exit;
}
$stmt = $pdo->prepare("SELECT status FROM licenses WHERE license_key = ?");
$stmt = $pdo->prepare("SELECT * FROM licenses WHERE license_key = ?");
$stmt->execute([$key]);
$status = $stmt->fetchColumn();
$license = $stmt->fetch();
$status = $license['status'] ?? 'suspended';
if ($status === 'active') {
echo json_encode(['success' => true]);
echo json_encode([
'success' => true,
'max_activations' => (int)$license['max_activations'],
'max_counters' => (int)$license['max_counters']
]);
} else {
echo json_encode(['success' => false, 'error' => 'License is no longer active.']);
}
@ -154,6 +161,7 @@ if ($endpoint === 'issue') {
}
$max_activations = (int)($input['max_activations'] ?? 1);
$max_counters = (int)($input['max_counters'] ?? 1);
$prefix = strtoupper(trim($input['prefix'] ?? 'FLAT'));
$owner = $input['owner'] ?? null;
$address = $input['address'] ?? null;
@ -163,13 +171,14 @@ if ($endpoint === 'issue') {
$key = strtoupper($key);
try {
$stmt = $pdo->prepare("INSERT INTO licenses (license_key, max_activations, owner, address) VALUES (?, ?, ?, ?)");
$stmt->execute([$key, $max_activations, $owner, $address]);
$stmt = $pdo->prepare("INSERT INTO licenses (license_key, max_activations, max_counters, owner, address) VALUES (?, ?, ?, ?, ?)");
$stmt->execute([$key, $max_activations, $max_counters, $owner, $address]);
echo json_encode([
'success' => true,
'license_key' => $key,
'max_activations' => $max_activations,
'max_counters' => $max_counters,
'owner' => $owner,
'address' => $address
]);
@ -214,6 +223,8 @@ if ($endpoint === 'update') {
$status = $input['status'] ?? null;
$owner = $input['owner'] ?? null;
$address = $input['address'] ?? null;
$max_activations = isset($input['max_activations']) ? (int)$input['max_activations'] : null;
$max_counters = isset($input['max_counters']) ? (int)$input['max_counters'] : null;
if (!$id) {
echo json_encode(['success' => false, 'error' => 'ID is required.']);
@ -226,6 +237,8 @@ if ($endpoint === 'update') {
if ($status !== null) { $fields[] = "status = ?"; $params[] = $status; }
if ($owner !== null) { $fields[] = "owner = ?"; $params[] = $owner; }
if ($address !== null) { $fields[] = "address = ?"; $params[] = $address; }
if ($max_activations !== null) { $fields[] = "max_activations = ?"; $params[] = $max_activations; }
if ($max_counters !== null) { $fields[] = "max_counters = ?"; $params[] = $max_counters; }
if (empty($fields)) {
echo json_encode(['success' => false, 'error' => 'No fields to update.']);

View File

@ -81,10 +81,13 @@ if ($_SERVER['REQUEST_METHOD'] === 'POST') {
case 'issue':
$prefix = strtoupper(trim($_POST['prefix'] ?? 'FLAT'));
$max_activations = (int)($_POST['max_activations'] ?? 1);
$max_counters = (int)($_POST['max_counters'] ?? 1);
$owner = trim($_POST['owner'] ?? '');
$address = trim($_POST['address'] ?? '');
$key = $prefix . '-' . strtoupper(bin2hex(random_bytes(2))) . '-' . strtoupper(bin2hex(random_bytes(2))) . '-' . strtoupper(bin2hex(random_bytes(2)));
$stmt = $pdo->prepare("INSERT INTO licenses (license_key, max_activations, status) VALUES (?, ?, 'active')");
$stmt->execute([$key, $max_activations]);
$stmt = $pdo->prepare("INSERT INTO licenses (license_key, max_activations, max_counters, owner, address, status) VALUES (?, ?, ?, ?, ?, 'active')");
$stmt->execute([$key, $max_activations, $max_counters, $owner, $address]);
$message = "New license issued: $key";
break;
}
@ -140,9 +143,21 @@ $licenses = $pdo->query("SELECT * FROM licenses ORDER BY created_at DESC")->fetc
<input type="text" name="prefix" class="form-control" value="FLAT" maxlength="10">
</div>
<div class="mb-3">
<label class="form-label">Max Activations</label>
<label class="form-label">Machines Limit</label>
<input type="number" name="max_activations" class="form-control" value="1" min="1">
</div>
<div class="mb-3">
<label class="form-label">Counters Limit</label>
<input type="number" name="max_counters" class="form-control" value="1" min="1">
</div>
<div class="mb-3">
<label class="form-label">Owner Name</label>
<input type="text" name="owner" class="form-control" placeholder="Optional client name">
</div>
<div class="mb-3">
<label class="form-label">Address / Notes</label>
<textarea name="address" class="form-control" rows="2" placeholder="Optional details"></textarea>
</div>
<button type="submit" class="btn btn-primary w-100">Issue Key</button>
</form>
</div>
@ -160,7 +175,9 @@ $licenses = $pdo->query("SELECT * FROM licenses ORDER BY created_at DESC")->fetc
<thead>
<tr>
<th>Key</th>
<th>Activations</th>
<th>Owner</th>
<th>Machines</th>
<th>Counters</th>
<th>Status</th>
<th>Created</th>
<th class="text-end">Actions</th>
@ -170,6 +187,7 @@ $licenses = $pdo->query("SELECT * FROM licenses ORDER BY created_at DESC")->fetc
<?php foreach ($licenses as $l): ?>
<tr>
<td><code><?= htmlspecialchars($l['license_key']) ?></code></td>
<td class="small"><?= htmlspecialchars($l['owner'] ?? '-') ?></td>
<td>
<?php
$stmt = $pdo->prepare("SELECT COUNT(*) FROM activations WHERE license_id = ?");
@ -178,6 +196,9 @@ $licenses = $pdo->query("SELECT * FROM licenses ORDER BY created_at DESC")->fetc
?>
<span class="fw-bold"><?= $count ?></span> / <?= $l['max_activations'] ?>
</td>
<td>
<span class="fw-bold"><?= $l['max_counters'] ?? 0 ?></span>
</td>
<td>
<span class="status-<?= $l['status'] ?>">
<i class="bi bi-circle-fill small me-1"></i> <?= ucfirst($l['status']) ?>
@ -186,6 +207,9 @@ $licenses = $pdo->query("SELECT * FROM licenses ORDER BY created_at DESC")->fetc
<td class="small text-muted"><?= date('M d, Y', strtotime($l['created_at'])) ?></td>
<td class="text-end">
<div class="btn-group">
<button type="button" class="btn btn-outline-info btn-sm" data-bs-toggle="modal" data-bs-target="#modal-<?= $l['id'] ?>" title="View Activations">
<i class="bi bi-laptop"></i>
</button>
<form method="POST" class="d-inline" onsubmit="return confirm('Change status?');">
<input type="hidden" name="action" value="toggle_status">
<input type="hidden" name="id" value="<?= $l['id'] ?>">
@ -204,6 +228,51 @@ $licenses = $pdo->query("SELECT * FROM licenses ORDER BY created_at DESC")->fetc
</div>
</td>
</tr>
<!-- Activations Modal -->
<div class="modal fade" id="modal-<?= $l['id'] ?>" tabindex="-1">
<div class="modal-dialog modal-lg">
<div class="modal-content">
<div class="modal-header">
<h5 class="modal-title">Activations for <?= htmlspecialchars($l['license_key']) ?></h5>
<button type="button" class="btn-close" data-bs-dismiss="modal"></button>
</div>
<div class="modal-body">
<?php
$stmt = $pdo->prepare("SELECT * FROM activations WHERE license_id = ? ORDER BY activated_at DESC");
$stmt->execute([$l['id']]);
$acts = $stmt->fetchAll();
if ($acts):
?>
<div class="table-responsive">
<table class="table table-sm">
<thead>
<tr>
<th>Fingerprint</th>
<th>Domain</th>
<th>Product</th>
<th>Activated At</th>
</tr>
</thead>
<tbody>
<?php foreach ($acts as $a): ?>
<tr>
<td><code><?= htmlspecialchars($a['fingerprint']) ?></code></td>
<td><?= htmlspecialchars($a['domain'] ?? '-') ?></td>
<td><?= htmlspecialchars($a['product'] ?? '-') ?></td>
<td><?= $a['activated_at'] ?></td>
</tr>
<?php endforeach; ?>
</tbody>
</table>
</div>
<?php else: ?>
<p class="text-center text-muted my-3">No active machine activations found.</p>
<?php endif; ?>
</div>
</div>
</div>
</div>
<?php endforeach; ?>
<?php if (empty($licenses)): ?>
<tr><td colspan="5" class="text-center py-4 text-muted">No licenses found.</td></tr>