-version 2.x -
+version 2.x - Dragon Chapel ()
+
+ + Add top 5 tag or category relation stats in the tag and category overview
version 2.8.1 - Deathwind Chapel (2022-12-31)
home.input.search.found = "Results found."
home.last.added = "Last added"
+view.nav.all.tags = "Tags"
+view.nav.all.categories = "Categories"
+view.nav.back.home = "back home"
+view.nav.random = "Random link"
+
view.name = "Name"
view.new.name = "New name"
view.deletion = "Deletion"
view.image.link = "Image Link"
view.categories = "Categories"
view.category = "Category"
+view.category.topcombination = "Top category combinations"
view.tag.help = "Enter a new one or select an existing from the suggested and press enter."
view.tag = "Tag"
view.tags = "Tags"
+view.tag.topcombination = "Top tag combinations"
view.private = "Private"
view.url = "URL"
view.image = "Image"
stats.import.xml.file = "Choose a file"
stats.import.xml.overwrite = "Overwrite existing"
stats.import.xml.import = "Import"
-
-view.nav.all.tags = "Tags"
-view.nav.all.categories = "Categories"
-view.nav.back.home = "back home"
-view.nav.random = "Random link"
-
stats.storage.clean.fail = "Something went wrong while storage cleaning"
stats.import.missing.file = "Please provide a import file"
stats.search.index.fail = "Something went wrong while search index update"
home.input.search.found = "Ergebnisse gefunden."
home.last.added = "Zuletzt hinzugefügt"
+view.nav.all.tags = "Tags"
+view.nav.all.categories = "Kategorien"
+view.nav.back.home = "zurück nach Hause"
+view.nav.random = "Zufallslink"
+
view.name = "Name"
view.new.name = "Neuer Name"
view.deletion = "Löschung"
view.image.link = "Bildverweis"
view.categories = "Kategorien"
view.category = "Kategorie"
+view.category.topcombination = "Top Kategorie Kombinationen"
view.tag.help = "Eingabe eines Neuen oder Auswahl eines Bestehenden und danach Enter drücken."
view.tag = "Tag"
view.tags = "Tags"
+view.tag.topcombination = "Top Tag Kombinationen"
view.private = "Privat"
view.url = "URL"
view.image = "Bild"
return $ret;
}
+ /**
+ * Top 5 combinations of either tag or category
+ *
+ * array(
+ * array(
+ * amount => number
+ * rel => array(rel, name)
+ * )
+ * )
+ *
+ * @param string $type
+ * @return array
+ */
+ public function linkRelationStats(string $type='tag'): array {
+ $ret = array();
+
+ // build the digit string which describes the tag/cat combination
+ $_relCombination = array();
+ if($type == 'category') {
+ $queryStr = "SELECT `linkid`, `categoryid` AS rel
+ FROM `".DB_PREFIX."_categoryrelation`
+ ORDER BY `linkid`, rel ASC";
+ } else {
+ $queryStr = "SELECT `linkid`, `tagid` AS rel
+ FROM `".DB_PREFIX."_tagrelation`
+ ORDER BY `linkid`, rel ASC";
+ }
+ $query = $this->DB->query($queryStr);
+ if(!empty($query) && $query->num_rows > 0) {
+ while($result = $query->fetch_assoc()) {
+ if(isset($_relCombination[$result['linkid']])) {
+ $_relCombination[$result['linkid']] .= ",".$result['rel'];
+ } else {
+ // https://www.php.net/manual/en/language.types.array.php "Strings containing valid decimal ints ... will be cast to the int type
+ // if not not done the arsort results are messed up
+ $_relCombination[$result['linkid']] = "0".$result['rel'];
+ }
+ }
+ }
+
+ // now count the unique digit strings
+ $_relCombination_amount = array();
+ if(!empty($_relCombination)) {
+ foreach($_relCombination as $k=>$v) {
+ if(isset($_relCombination_amount[$v])) {
+ $_relCombination_amount[$v]++;
+ } else {
+ $_relCombination_amount[$v] = 1;
+ }
+ }
+ }
+
+ // now sort and return top 5 combinations
+ // also resolve tag/cat name
+ if(!empty($_relCombination_amount)) {
+ arsort($_relCombination_amount);
+ $_top5 = array_splice($_relCombination_amount,0,5);
+
+ foreach($_top5 as $k=>$v) {
+ $_t = array();
+ if($k[0] === "0") {
+ $k = substr($k,1);
+ }
+
+ $_t['amount'] = $v;
+ $_rel = explode(",",$k);
+
+ $_existingRelInfo = array(); // avoid duplicate queries
+ foreach($_rel as $t) {
+ if(!isset($_existingRelInfo[$t])) {
+ if($type == 'category') {
+ $queryStr = "SELECT `name` FROM `".DB_PREFIX."_category`
+ WHERE `id` = '".$this->DB->real_escape_string($t)."'";
+ } else {
+ $queryStr = "SELECT `name` FROM `".DB_PREFIX."_tag`
+ WHERE `id` = '".$this->DB->real_escape_string($t)."'";
+ }
+ $query = $this->DB->query($queryStr);
+ if(!empty($query) && $query->num_rows > 0) {
+ $relinfo = $query->fetch_assoc();
+ $_existingRelInfo[$t] = $relinfo['name'];
+ $_t['rel'][$t] = $relinfo['name'];
+ }
+ } else {
+ $_t['rel'][$t] = $_existingRelInfo[$t];
+ }
+ }
+ $ret[] = $_t;
+ }
+
+ }
+
+ return $ret;
+ }
+
/**
* Return the query string for the correct status type
*
$displayEditButton = false;
$isAwm = false;
$sortLink = array();
+$colInfo = array();
if(Summoner::simpleAuthCheck() === true) {
$displayEditButton = true;
# show all the tags we have
$tagCollection = $Management->tags(0, true);
$subHeadline = $T->t('view.tags').' <i class="ion-md-pricetags"></i>';
+ $colInfo = $Management->linkRelationStats();
}
break;
case 'category':
# show all the categories we have
$categoryCollection = $Management->categories(0, true);
$subHeadline = $T->t('view.categories').' <i class="ion-md-filing"></i>';
+ $colInfo = $Management->linkRelationStats('category');
}
break;
case 'awm':
</div>
<?php } if(!empty($tagCollection)) { ?>
<div class="columns">
- <div class="column">
+ <div class="column is-half">
+ <?php if($displayEditButton === true) { ?>
+ <div class="column">
+ <div class="content">
+ <a href="index.php?p=edittags" class="button is-small is-danger">
+ <span class="icon"><i class="ion-md-create"></i></span>
+ <span><?php echo $T->t('view.edit.tags'); ?></span>
+ </a>
+ </div>
+ </div>
+ <?php } ?>
+ <div class="column">
+ <table class="table">
+ <tr>
+ <th><?php echo $T->t('view.name'); ?></th>
+ <th><?php echo $T->t('view.num.links'); ?></th>
+ </tr>
+ <?php foreach ($tagCollection as $k=>$v) { ?>
+ <tr>
+ <td><a href="index.php?p=overview&m=tag&id=<?php echo urlencode($k); ?>"><?php echo $v['name']; ?></a></td>
+ <td><?php echo $v['amount']; ?></td>
+ </tr>
+ <?php } ?>
+ </table>
+ </div>
+ </div>
+ <div class="column is-half">
+ <?php if(!empty($colInfo)) { ?>
+ <?php echo $T->t('view.tag.topcombination'); ?>
<table class="table">
<tr>
- <th><?php echo $T->t('view.name'); ?></th>
- <th><?php echo $T->t('view.num.links'); ?></th>
+ <th>#</th>
+ <th><?php echo $T->t('view.tags'); ?></th>
</tr>
- <?php foreach ($tagCollection as $k=>$v) { ?>
- <tr>
- <td><a href="index.php?p=overview&m=tag&id=<?php echo urlencode($k); ?>"><?php echo $v['name']; ?></a></td>
- <td><?php echo $v['amount']; ?></td>
- </tr>
- <?php } ?>
+ <?php foreach ($colInfo as $k=>$v) { ?>
+ <tr>
+ <td><?php echo $v['amount']; ?></td>
+ <td>
+ <?php foreach ($v['rel'] as $tid=>$tname) { ?>
+ <a href="index.php?p=overview&m=tag&id=<?php echo urlencode($tid); ?>"><?php echo $tname; ?></a>
+ <?php } ?>
+ </td>
+ </tr>
+ <?php } ?>
</table>
+ <?php } ?>
</div>
- <?php if($displayEditButton === true) { ?>
- <div class="column">
- <div class="content">
- <a href="index.php?p=edittags" class="button is-small is-danger">
- <span class="icon"><i class="ion-md-create"></i></span>
- <span><?php echo $T->t('view.edit.tags'); ?></span>
- </a>
- </div>
- </div>
- <?php } ?>
</div>
<?php } if(!empty($categoryCollection)) { ?>
<div class="columns">
- <div class="column">
- <table class="table">
- <tr>
- <th><?php echo $T->t('view.name'); ?></th>
- <th><?php echo $T->t('view.num.links'); ?></th>
- </tr>
- <?php foreach ($categoryCollection as $k=>$v) { ?>
- <tr>
- <td><a href="index.php?p=overview&m=category&id=<?php echo urlencode($k); ?>"><?php echo $v['name']; ?></a></td>
- <td><?php echo $v['amount']; ?></td>
- </tr>
+ <div class="column is-half">
+ <?php if($displayEditButton === true) { ?>
+ <div class="column">
+ <div class="content">
+ <a href="index.php?p=editcategories" class="button is-small is-danger">
+ <span class="icon"><i class="ion-md-create"></i></span>
+ <span><?php echo $T->t('view.edit.categories'); ?></span>
+ </a>
+ </div>
+ </div>
<?php } ?>
- </table>
- </div>
- <?php if($displayEditButton === true) { ?>
- <div class="column">
- <div class="content">
- <a href="index.php?p=editcategories" class="button is-small is-danger">
- <span class="icon"><i class="ion-md-create"></i></span>
- <span><?php echo $T->t('view.edit.categories'); ?></span>
- </a>
+ <div class="column">
+ <table class="table">
+ <tr>
+ <th><?php echo $T->t('view.name'); ?></th>
+ <th><?php echo $T->t('view.num.links'); ?></th>
+ </tr>
+ <?php foreach ($categoryCollection as $k=>$v) { ?>
+ <tr>
+ <td><a href="index.php?p=overview&m=category&id=<?php echo urlencode($k); ?>"><?php echo $v['name']; ?></a></td>
+ <td><?php echo $v['amount']; ?></td>
+ </tr>
+ <?php } ?>
+ </table>
</div>
</div>
- <?php } ?>
+ <div class="column is-half">
+ <?php if(!empty($colInfo)) { ?>
+ <?php echo $T->t('view.category.topcombination'); ?>
+ <table class="table">
+ <tr>
+ <th>#</th>
+ <th><?php echo $T->t('view.categories'); ?></th>
+ </tr>
+ <?php foreach ($colInfo as $k=>$v) { ?>
+ <tr>
+ <td><?php echo $v['amount']; ?></td>
+ <td>
+ <?php foreach ($v['rel'] as $cid=>$cname) { ?>
+ <a href="index.php?p=overview&m=category&id=<?php echo urlencode($cid); ?>"><?php echo $cname; ?></a>
+ <?php } ?>
+ </td>
+ </tr>
+ <?php } ?>
+ </table>
+ <?php } ?>
+ </div>
</div>
<?php } ?>
</section>
echo 'mysqldump-php error: ' . $e->getMessage();
}
- /*
- require_once 'lib/Mysqldump.php';
- $backupTmpFile = tempnam(sys_get_temp_dir(),'inspid');
-
- // mysqldump was modifed to make this work
- // include-views was not working while using include-tables
- $dumpSettings = array(
- 'include-tables' => array(
- DB_PREFIX.'_category',
- DB_PREFIX.'_categoryrelation',
- DB_PREFIX.'_link',
- DB_PREFIX.'_tag',
- DB_PREFIX.'_tagrelation'
- ),
- 'include-views' => array(
- DB_PREFIX.'_combined'
- ),
- 'default-character-set' => \Ifsnop\Mysqldump\Mysqldump::UTF8MB4
- );
- $dump = new Ifsnop\Mysqldump\Mysqldump(
- 'mysql:host='.DB_HOST.';dbname='.DB_NAME,
- DB_USERNAME,
- DB_PASSWORD,
- $dumpSettings
- );
-
- $dump->start($backupTmpFile);
- */
-
header('Content-Type: application/octet-stream');
header("Content-Transfer-Encoding: Binary");
header("Content-disposition: attachment; filename=inspid-db-backup-full.sql");
}
if(isset($_POST['statsUpdateSearchIndex'])) {
-
if($Management->updateSearchIndex() === true) {
$TemplateData['refresh'] = 'index.php?p=stats';
}