Skip to content

Commit

Permalink
Adds achievement metadata table (tgstation#48007)
Browse files Browse the repository at this point in the history
* Renames hub_id to database_id
Adds achievement_metadata table.

* Fixups

* enum
  • Loading branch information
AnturK authored and Jordie0608 committed Nov 30, 2019
1 parent f24450a commit f28b2d6
Show file tree
Hide file tree
Showing 10 changed files with 112 additions and 44 deletions.
17 changes: 15 additions & 2 deletions SQL/database_changelog.txt
Original file line number Diff line number Diff line change
Expand Up @@ -2,12 +2,25 @@ Any time you make a change to the schema files, remember to increment the databa

The latest database version is 5.4; The query to update the schema revision table is:

INSERT INTO `schema_revision` (`major`, `minor`) VALUES (5, 4);
INSERT INTO `schema_revision` (`major`, `minor`) VALUES (5, 5);
or
INSERT INTO `SS13_schema_revision` (`major`, `minor`) VALUES (5, 4);
INSERT INTO `SS13_schema_revision` (`major`, `minor`) VALUES (5, 5);

In any query remember to add a prefix to the table names if you use one.

-----------------------------------------------------

Version 5.5, 26 October 2019 by Anturke
Added achievement_metadata table.

DROP TABLE IF EXISTS `achievement_metadata`;
CREATE TABLE `achievement_metadata` (
`achievement_key` VARCHAR(32) NOT NULL,
`achievement_version` SMALLINT UNSIGNED NOT NULL DEFAULT 0,
`achievement_type` enum('achievement','score','award') NULL DEFAULT NULL,
PRIMARY KEY (`achievement_key`)
) ENGINE=InnoDB;


-----------------------------------------------------

Expand Down
8 changes: 8 additions & 0 deletions SQL/tgstation_schema.sql
Original file line number Diff line number Diff line change
Expand Up @@ -527,6 +527,14 @@ CREATE TABLE `achievements` (
PRIMARY KEY (`ckey`,`achievement_key`)
) ENGINE=InnoDB;

DROP TABLE IF EXISTS `achievement_metadata`;
CREATE TABLE `achievement_metadata` (
`achievement_key` VARCHAR(32) NOT NULL,
`achievement_version` SMALLINT UNSIGNED NOT NULL DEFAULT 0,
`achievement_type` enum('achievement','score','award') NULL DEFAULT NULL,
PRIMARY KEY (`achievement_key`)
) ENGINE=InnoDB;

/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;
Expand Down
8 changes: 8 additions & 0 deletions SQL/tgstation_schema_prefixed.sql
Original file line number Diff line number Diff line change
Expand Up @@ -527,6 +527,14 @@ CREATE TABLE `SS13_achievements` (
PRIMARY KEY (`ckey`,`achievement_key`)
) ENGINE=InnoDB;

DROP TABLE IF EXISTS `SS13_achievement_metadata`;
CREATE TABLE `SS13_achievement_metadata` (
`achievement_key` VARCHAR(32) NOT NULL,
`achievement_version` SMALLINT UNSIGNED NOT NULL DEFAULT 0,
`achievement_type` enum('achievement','score','award') NULL DEFAULT NULL,
PRIMARY KEY (`achievement_key`)
) ENGINE=InnoDB;

/*!40101 SET SQL_MODE=@OLD_SQL_MODE */;
/*!40014 SET FOREIGN_KEY_CHECKS=@OLD_FOREIGN_KEY_CHECKS */;
/*!40014 SET UNIQUE_CHECKS=@OLD_UNIQUE_CHECKS */;
Expand Down
2 changes: 1 addition & 1 deletion code/__DEFINES/subsystems.dm
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@
*
* make sure you add an update to the schema_version stable in the db changelog
*/
#define DB_MINOR_VERSION 4
#define DB_MINOR_VERSION 5


//! ## Timing subsystem
Expand Down
26 changes: 26 additions & 0 deletions code/controllers/subsystem/achievements.dm
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ SUBSYSTEM_DEF(achievements)
scores[T] = instance
awards[T] = instance

update_metadata()

for(var/i in GLOB.clients)
var/client/C = i
if(!C.player_details.achievements.initialized)
Expand All @@ -45,3 +47,27 @@ SUBSYSTEM_DEF(achievements)
cheevos_to_save += PD.achievements.get_changed_data()

SSdbcore.MassInsert(format_table_name("achievements"),cheevos_to_save,duplicate_key = TRUE)

//Update the metadata if any are behind
/datum/controller/subsystem/achievements/proc/update_metadata()
var/list/current_metadata = list()
//select metadata here
var/datum/DBQuery/Q = SSdbcore.NewQuery("SELECT achievement_key,achievement_version FROM [format_table_name("achievement_metadata")]")
if(!Q.Execute(async = TRUE))
qdel(Q)
return
else
while(Q.NextRow())
current_metadata[Q.item[1]] = text2num(Q.item[2])
qdel(Q)

var/list/to_update = list()
for(var/T in awards)
var/datum/award/A = awards[T]
if(!A.database_id)
continue
if(!current_metadata[A.database_id] || current_metadata[A.database_id] < A.achievement_version)
to_update += list(A.get_metadata_row())

if(to_update.len)
SSdbcore.MassInsert(format_table_name("achievement_metadata"),to_update,duplicate_key = TRUE)
2 changes: 1 addition & 1 deletion code/datums/achievements/_achievement_data.dm
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@
if(!A || !A.name) //Skip abstract achievements types
continue
if(!data[T])
data[T] = A.parse_value(kv[A.hub_id])
data[T] = A.parse_value(kv[A.database_id])
original_cached_data[T] = data[T]

///Updates local cache with db data for the given achievement type if it wasn't loaded yet.
Expand Down
27 changes: 20 additions & 7 deletions code/datums/achievements/_awards.dm
Original file line number Diff line number Diff line change
Expand Up @@ -6,8 +6,10 @@
var/icon = "default"
var/category = "Normal"

///What ID do we use on the hub?
var/hub_id
///What ID do we use in db, limited to 32 characters
var/database_id
//Bump this up if you're changing outdated table identifier and/or achievement type
var/achievement_version = 1

//Value returned on db connection failure, in case we want to differ 0 and nonexistent later on
var/default_value = FALSE
Expand All @@ -16,20 +18,23 @@
/datum/award/proc/load(key)
if(!SSdbcore.Connect())
return default_value
if(!key || !hub_id || !name)
if(!key || !database_id || !name)
return default_value
var/raw_value = get_raw_value(key)
return parse_value(raw_value)

///This saves the changed data to the hub.
/datum/award/proc/get_changed_rows(key, value)
if(!hub_id || !key || !name)
if(!database_id || !key || !name)
return
return list("ckey" = "'[sanitizeSQL(key)]'","achievement_key" = "'[sanitizeSQL(hub_id)]'", "value" = "'[sanitizeSQL(value)]'")
return list("ckey" = "'[sanitizeSQL(key)]'","achievement_key" = "'[sanitizeSQL(database_id)]'", "value" = "'[sanitizeSQL(value)]'")

/datum/award/proc/get_metadata_row()
return list("achievement_key" = "'[sanitizeSQL(database_id)]'", "achievement_version" = "'[sanitizeSQL(achievement_version)]'", "achievement_type" = "'award'")

///Get raw numerical achievement value from the database
/datum/award/proc/get_raw_value(key)
var/datum/DBQuery/Q = SSdbcore.NewQuery("SELECT value FROM [format_table_name("achievements")] WHERE ckey = '[sanitizeSQL(key)]' AND achievement_key = '[sanitizeSQL(hub_id)]'")
var/datum/DBQuery/Q = SSdbcore.NewQuery("SELECT value FROM [format_table_name("achievements")] WHERE ckey = '[sanitizeSQL(key)]' AND achievement_key = '[sanitizeSQL(database_id)]'")
if(!Q.Execute(async = TRUE))
qdel(Q)
return 0
Expand All @@ -51,6 +56,10 @@
/datum/award/achievement
desc = "Achievement for epic people"

/datum/award/achievement/get_metadata_row()
. = ..()
.["achievement_type"] = "'achievement'"

/datum/award/achievement/parse_value(raw_value)
return raw_value > 0

Expand All @@ -72,8 +81,12 @@
if(track_high_scores)
LoadHighScores()

/datum/award/score/get_metadata_row()
. = ..()
.["achievement_type"] = "'score'"

/datum/award/score/proc/LoadHighScores()
var/datum/DBQuery/Q = SSdbcore.NewQuery("SELECT ckey,value FROM [format_table_name("achievements")] WHERE achievement_key = '[sanitizeSQL(hub_id)]' ORDER BY value DESC LIMIT 50")
var/datum/DBQuery/Q = SSdbcore.NewQuery("SELECT ckey,value FROM [format_table_name("achievements")] WHERE achievement_key = '[sanitizeSQL(database_id)]' ORDER BY value DESC LIMIT 50")
if(!Q.Execute(async = TRUE))
qdel(Q)
return
Expand Down
32 changes: 16 additions & 16 deletions code/datums/achievements/boss_achievements.dm
Original file line number Diff line number Diff line change
Expand Up @@ -4,79 +4,79 @@
/datum/award/achievement/boss/tendril_exterminator
name = "Tendril Exterminator"
desc = "Watch your step"
hub_id = BOSS_MEDAL_TENDRIL
database_id = BOSS_MEDAL_TENDRIL

/datum/award/achievement/boss/boss_killer
name = "Boss Killer"
desc = "You've come a long ways from asking how to switch hands."
hub_id = "Boss Killer"
database_id = "Boss Killer"

/datum/award/achievement/boss/blood_miner_kill
name = "Blood-drunk Miner Killer"
desc = "I guess he couldn't handle his drink that well."
hub_id = BOSS_MEDAL_MINER
database_id = BOSS_MEDAL_MINER

/datum/award/achievement/boss/bubblegum_kill
name = "Bubblegum Killer"
desc = "I guess he wasn't made of candy after all"
hub_id = BOSS_MEDAL_BUBBLEGUM
database_id = BOSS_MEDAL_BUBBLEGUM

/datum/award/achievement/boss/colussus_kill
name = "Colussus Killer"
desc = "The bigger they are... the better the loot"
hub_id = BOSS_MEDAL_COLOSSUS
database_id = BOSS_MEDAL_COLOSSUS

/datum/award/achievement/boss/drake_kill
name = "Drake Killer"
desc = "Now I can wear Rune Platebodies!"
hub_id = BOSS_MEDAL_DRAKE
database_id = BOSS_MEDAL_DRAKE

/datum/award/achievement/boss/hierophant_kill
name = "Hierophant Killer"
desc = "Hierophant, but not triumphant."
hub_id = BOSS_MEDAL_HIEROPHANT
database_id = BOSS_MEDAL_HIEROPHANT

/datum/award/achievement/boss/legion_kill
name = "Legion Killer"
desc = "We were many..now we are none."
hub_id = BOSS_MEDAL_LEGION
database_id = BOSS_MEDAL_LEGION

/datum/award/achievement/boss/swarmer_beacon_kill
name = "Swarm Beacon Killer"
desc = "GET THEM OFF OF ME!"
hub_id = BOSS_MEDAL_SWARMERS
database_id = BOSS_MEDAL_SWARMERS

/datum/award/achievement/boss/blood_miner_crusher
name = "Blood-drunk Miner Crusher"
desc = "I guess he couldn't handle his drink that well."
hub_id = BOSS_MEDAL_MINER_CRUSHER
database_id = BOSS_MEDAL_MINER_CRUSHER

/datum/award/achievement/boss/bubblegum_crusher
name = "Bubblegum Crusher"
desc = "I guess he wasn't made of candy after all"
hub_id = BOSS_MEDAL_BUBBLEGUM_CRUSHER
database_id = BOSS_MEDAL_BUBBLEGUM_CRUSHER

/datum/award/achievement/boss/colussus_crusher
name = "Colussus Crusher"
desc = "The bigger they are... the better the loot"
hub_id = BOSS_MEDAL_COLOSSUS_CRUSHER
database_id = BOSS_MEDAL_COLOSSUS_CRUSHER

/datum/award/achievement/boss/drake_crusher
name = "Drake Crusher"
desc = "Now I can wear Rune Platebodies!"
hub_id = BOSS_MEDAL_DRAKE_CRUSHER
database_id = BOSS_MEDAL_DRAKE_CRUSHER

/datum/award/achievement/boss/hierophant_crusher
name = "Hierophant Crusher"
desc = "Hierophant, but not triumphant."
hub_id = BOSS_MEDAL_HIEROPHANT_CRUSHER
database_id = BOSS_MEDAL_HIEROPHANT_CRUSHER

/datum/award/achievement/boss/legion_crusher
name = "Legion Crusher"
desc = "We were many... now we are none."
hub_id = BOSS_MEDAL_LEGION_CRUSHER
database_id = BOSS_MEDAL_LEGION_CRUSHER

/datum/award/achievement/boss/swarmer_beacon_crusher
name = "Swarm Beacon Crusher"
desc = "GET THEM OFF OF ME!"
hub_id = BOSS_MEDAL_SWARMERS_CRUSHER
database_id = BOSS_MEDAL_SWARMERS_CRUSHER
18 changes: 9 additions & 9 deletions code/datums/achievements/boss_scores.dm
Original file line number Diff line number Diff line change
@@ -1,44 +1,44 @@
/datum/award/score/tendril_score
name = "Tendril Score"
desc = "Watch your step"
hub_id = TENDRIL_CLEAR_SCORE
database_id = TENDRIL_CLEAR_SCORE

/datum/award/score/boss_score
name = "Bosses Killed"
desc = "You've killed HOW many?"
hub_id = BOSS_SCORE
database_id = BOSS_SCORE

/datum/award/score/blood_miner_score
name = "Blood-Drunk Miners Killed"
desc = "You've killed HOW many?"
hub_id = MINER_SCORE
database_id = MINER_SCORE

/datum/award/score/bubblegum_score
name = "Bubblegums Killed"
desc = "You've killed HOW many?"
hub_id = BUBBLEGUM_SCORE
database_id = BUBBLEGUM_SCORE

/datum/award/score/colussus_score
name = "Colossus Killed"
desc = "You've killed HOW many?"
hub_id = COLOSSUS_SCORE
database_id = COLOSSUS_SCORE

/datum/award/score/drake_score
name = "Drakes Killed"
desc = "You've killed HOW many?"
hub_id = DRAKE_SCORE
database_id = DRAKE_SCORE

/datum/award/score/hierophant_score
name = "Hierophants Killed"
desc = "You've killed HOW many?"
hub_id = HIEROPHANT_SCORE
database_id = HIEROPHANT_SCORE

/datum/award/score/legion_score
name = "Legions Killed"
desc = "You've killed HOW many?"
hub_id = LEGION_SCORE
database_id = LEGION_SCORE

/datum/award/score/swarmer_beacon_score
name = "Swarmer Beacons Killed"
desc = "You've killed HOW many?"
hub_id = SWARMER_BEACON_SCORE
database_id = SWARMER_BEACON_SCORE
16 changes: 8 additions & 8 deletions code/datums/achievements/misc_achievements.dm
Original file line number Diff line number Diff line change
Expand Up @@ -4,39 +4,39 @@
/datum/award/achievement/misc/meteor_examine
name = "Your Life Before Your Eyes"
desc = "Take a close look at hurtling space debris"
hub_id = MEDAL_METEOR
database_id = MEDAL_METEOR

/datum/award/achievement/misc/pulse
name = "Jackpot"
desc = "Win a pulse rifle from an arcade machine"
hub_id = MEDAL_PULSE
database_id = MEDAL_PULSE

/datum/award/achievement/misc/time_waste
name = "Time waster"
desc = "Speak no evil, hear no evil, see just errors"
hub_id = MEDAL_TIMEWASTE
database_id = MEDAL_TIMEWASTE

/datum/award/achievement/misc/feat_of_strength
name = "Feat of Strength"
desc = "If the rod is immovable, is it passing you or are you passing it?"
hub_id = MEDAL_RODSUPLEX
database_id = MEDAL_RODSUPLEX

/datum/award/achievement/misc/round_and_full
name = "Round and Full"
desc = "Well at least you aren't down the river, I hear they eat people there."
hub_id = MEDAL_CLOWNCARKING
database_id = MEDAL_CLOWNCARKING

/datum/award/achievement/misc/the_best_driver
name = "The Best Driver"
desc = "100 honks later"
hub_id = MEDAL_THANKSALOT
database_id = MEDAL_THANKSALOT

/datum/award/achievement/misc/helbitaljanken
name = "Helbitaljanken"
desc = "You janked hard"
hub_id = MEDAL_HELBITALJANKEN
database_id = MEDAL_HELBITALJANKEN

/datum/award/achievement/misc/getting_an_upgrade
name = "Getting an upgrade"
desc = "Make your first unique material item!"
hub_id = MEDAL_MATERIALCRAFT
database_id = MEDAL_MATERIALCRAFT

0 comments on commit f28b2d6

Please sign in to comment.