diff --git a/_developer_data/structure.sql b/_developer_data/structure.sql
index e960d29..4cd3a44 100644
--- a/_developer_data/structure.sql
+++ b/_developer_data/structure.sql
@@ -5,9 +5,7 @@ SET time_zone = '+00:00';
SET foreign_key_checks = 0;
SET sql_mode = 'NO_AUTO_VALUE_ON_ZERO';
-DROP DATABASE IF EXISTS `sakura`;
-CREATE DATABASE `sakura` /*!40100 DEFAULT CHARACTER SET utf8 COLLATE utf8_bin */;
-USE `sakura`;
+USE `flashiidev`;
DROP TABLE IF EXISTS `fii_actioncodes`;
CREATE TABLE `fii_actioncodes` (
@@ -17,7 +15,7 @@ CREATE TABLE `fii_actioncodes` (
`actkey` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'The URL key for using this code.',
`instruction` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Things the backend should do upon using this code',
PRIMARY KEY (`id`)
-) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
+) ENGINE=InnoDB AUTO_INCREMENT=7 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
DROP TABLE IF EXISTS `fii_apikeys`;
@@ -50,34 +48,6 @@ CREATE TABLE `fii_config` (
`config_value` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'The value, obviously.'
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
-TRUNCATE `fii_config`;
-INSERT INTO `fii_config` (`config_name`, `config_value`) VALUES
-('recaptcha_public', ''),
-('recaptcha_private', ''),
-('charset', 'utf-8'),
-('cookie_prefix', ''),
-('cookie_domain', ''),
-('cookie_path', '/'),
-('site_style', 'yuuno'),
-('manage_style', 'Manage'),
-('allow_registration', '0'),
-('smtp_server', ''),
-('smtp_auth', ''),
-('smtp_secure', ''),
-('smtp_port', ''),
-('smtp_username', ''),
-('smtp_password', ''),
-('smtp_replyto_mail', ''),
-('smtp_replyto_name', ''),
-('smtp_from_email', ''),
-('smtp_from_name', 'Sakura Noreply'),
-('sitename', 'Sakura'),
-('recaptcha', '1'),
-('require_activation', '1'),
-('require_registration_code', '0'),
-('disable_registration', '1'),
-('max_reg_keys', '5'),
-('mail_signature', 'Team Flashii');
DROP TABLE IF EXISTS `fii_infopages`;
CREATE TABLE `fii_infopages` (
@@ -117,24 +87,26 @@ CREATE TABLE `fii_profilefields` (
`id` int(64) unsigned NOT NULL AUTO_INCREMENT COMMENT 'ID used for ordering on the userpage.',
`name` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Name of the field.',
`formtype` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Type attribute in the input element.',
+ `islink` tinyint(1) unsigned NOT NULL COMMENT 'Set if this value should be put in a href.',
+ `linkformat` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'If the form is a link how should it be formatted? {{ VAL }} gets replace with the value.',
`description` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Description of the field displayed in the control panel.',
`additional` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Undocumented JSON array containing special options if needed (probably only going to be used for the YouTube field).',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=12 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
TRUNCATE `fii_profilefields`;
-INSERT INTO `fii_profilefields` (`id`, `name`, `formtype`, `description`, `additional`) VALUES
-(1, 'Website', 'url', 'URL to your website', ''),
-(2, 'Twitter', 'text', 'Your @twitter Username', ''),
-(3, 'GitHub', 'text', 'Your GitHub Username', ''),
-(4, 'Skype', 'text', 'Your Skype Username', ''),
-(5, 'YouTube', 'text', 'ID or Username excluding http://youtube.com/*/', '{\"youtubetype\": [\"checkbox\", \"I don\'t have a Channel Username (url looks like https://www.youtube.com/channel/UCXZcw5hw5C7Neto-T_nRXBQ).\"]}'),
-(6, 'SoundCloud', 'text', 'Your SoundCloud username', ''),
-(7, 'Steam', 'text', 'Your Steam Community Username (may differ from login username)', ''),
-(8, 'osu!', 'text', 'Your osu! Username', ''),
-(9, 'Origin', 'text', 'Your Origin User ID', ''),
-(10, 'Xbox Live', 'text', 'Your Xbox User ID', ''),
-(11, 'PSN', 'text', 'Your PSN User ID', '');
+INSERT INTO `fii_profilefields` (`id`, `name`, `formtype`, `islink`, `linkformat`, `description`, `additional`) VALUES
+(1, 'Website', 'url', 1, '{{ VAL }}', 'URL to your website', ''),
+(2, 'Twitter', 'text', 1, 'https://twitter.com/{{ VAL }}', 'Your @twitter Username', ''),
+(3, 'GitHub', 'text', 1, 'https://github.com/{{ VAL }}', 'Your GitHub Username', ''),
+(4, 'Skype', 'text', 1, 'skype:{{ VAL }}?userinfo', 'Your Skype Username', ''),
+(5, 'YouTube', 'text', 0, '', 'ID or Username excluding http://youtube.com/*/', '{\"youtubetype\": [\"checkbox\", \"I don\'t have a Channel Username (url looks like https://www.youtube.com/channel/UCXZcw5hw5C7Neto-T_nRXBQ).\"]}'),
+(6, 'SoundCloud', 'text', 1, 'https://soundcloud.com/{{ VAL }}', 'Your SoundCloud username', ''),
+(7, 'Steam', 'text', 1, 'https://steamcommunity.com/id/{{ VAL }}', 'Your Steam Community Username (may differ from login username)', ''),
+(8, 'osu!', 'text', 1, 'https://osu.ppy.sh/u/{{ VAL }}', 'Your osu! Username', ''),
+(9, 'Origin', 'text', 0, '', 'Your Origin User ID', ''),
+(10, 'Xbox Live', 'text', 1, 'https://account.xbox.com/en-GB/Profile?Gamertag={{ VAL }}', 'Your Xbox User ID', ''),
+(11, 'PSN', 'text', 1, 'http://psnprofiles.com/{{ VAL }}', 'Your PSN User ID', '');
DROP TABLE IF EXISTS `fii_ranks`;
CREATE TABLE `fii_ranks` (
@@ -144,20 +116,21 @@ CREATE TABLE `fii_ranks` (
`colour` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Colour used for the username of a member of this rank.',
`description` text COLLATE utf8_bin NOT NULL COMMENT 'A description of what a user of this rank can do/is supposed to do.',
`title` varchar(255) COLLATE utf8_bin NOT NULL COMMENT 'Default user title if user has none set.',
+ `is_premium` tinyint(1) unsigned NOT NULL DEFAULT '0' COMMENT 'Flag to set if the user group is a premium group.',
PRIMARY KEY (`id`)
) ENGINE=InnoDB AUTO_INCREMENT=10 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
TRUNCATE `fii_ranks`;
-INSERT INTO `fii_ranks` (`id`, `name`, `multi`, `colour`, `description`, `title`) VALUES
-(1, 'Deactivated', 0, '#555', 'Users that are yet to be activated or that deactivated their own account.', 'Deactivated'),
-(2, 'Regular user', 1, 'inherit', 'Regular users with regular permissions.', 'Regular user'),
-(3, 'Site moderator', 1, '#0A0', 'Users with special permissions like being able to ban and modify users if needed.', 'Staff'),
-(4, 'Administrator', 1, '#C00', 'Users that manage the server and everything around that.', 'Administrator'),
-(5, 'Developer', 1, '#824CA0', 'Users that either create or test new features of the site.', 'Staff'),
-(6, 'Bot', 1, '#9E8DA7', 'Reserved user accounts for services.', 'Bot'),
-(7, 'Chat moderator', 1, '#09F', 'Moderators of the chat room.', 'Staff'),
-(8, 'Tenshi', 0, '#EE9400', 'Users that donated $5.00 or more in order to keep the site and it\'s services alive!', 'Tenshi'),
-(9, 'Alumnii', 0, '#FF69B4', 'People who have contributed to the community but have moved on or resigned.', 'Alumnii');
+INSERT INTO `fii_ranks` (`id`, `name`, `multi`, `colour`, `description`, `title`, `is_premium`) VALUES
+(1, 'Deactivated', 0, '#555', 'Users that are yet to be activated or that deactivated their own account.', 'Deactivated', 0),
+(2, 'Regular user', 1, 'inherit', 'Regular users with regular permissions.', 'Regular user', 0),
+(3, 'Site moderator', 1, '#0A0', 'Users with special permissions like being able to ban and modify users if needed.', 'Staff', 1),
+(4, 'Administrator', 1, '#C00', 'Users that manage the server and everything around that.', 'Administrator', 1),
+(5, 'Developer', 1, '#824CA0', 'Users that either create or test new features of the site.', 'Staff', 1),
+(6, 'Bot', 1, '#9E8DA7', 'Reserved user accounts for services.', 'Bot', 0),
+(7, 'Chat moderator', 1, '#09F', 'Moderators of the chat room.', 'Staff', 1),
+(8, 'Tenshi', 0, '#EE9400', 'Users that donated $5.00 or more in order to keep the site and it\'s services alive!', 'Tenshi', 1),
+(9, 'Alumnii', 0, '#FF69B4', 'People who have contributed to the community but have moved on or resigned.', 'Alumnii', 1);
DROP TABLE IF EXISTS `fii_regcodes`;
CREATE TABLE `fii_regcodes` (
@@ -181,7 +154,7 @@ CREATE TABLE `fii_sessions` (
`expire` int(64) unsigned NOT NULL COMMENT 'The timestamp for when this session should end, -1 for permanent. ',
`remember` tinyint(1) unsigned NOT NULL DEFAULT '0' COMMENT 'If set to 1 session will be extended each time a page is loaded.',
PRIMARY KEY (`id`)
-) ENGINE=InnoDB AUTO_INCREMENT=18 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
+) ENGINE=InnoDB AUTO_INCREMENT=59 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
DROP TABLE IF EXISTS `fii_tenshi`;
@@ -223,7 +196,7 @@ CREATE TABLE `fii_users` (
`profile_data` text COLLATE utf8_bin NOT NULL COMMENT 'Modular array containing profile data.',
PRIMARY KEY (`id`),
UNIQUE KEY `username_clean` (`username_clean`)
-) ENGINE=InnoDB AUTO_INCREMENT=4 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
+) ENGINE=InnoDB AUTO_INCREMENT=6 DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
DROP TABLE IF EXISTS `fii_warnings`;
@@ -238,4 +211,4 @@ CREATE TABLE `fii_warnings` (
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
--- 2015-04-19 12:58:09
+-- 2015-04-27 00:38:20
diff --git a/_sakura/changelog.json b/_sakura/changelog.json
index 24ed867..32a8c7d 100644
--- a/_sakura/changelog.json
+++ b/_sakura/changelog.json
@@ -2,10 +2,22 @@
"versions": {
+ "Heliotrope": {
+
+ "colour": "#DF73FF",
+
+ "builds": [
+
+ "20150427"
+
+ ]
+
+ },
+
"Cyan": {
-
+
"colour": "#4EC9B0",
-
+
"builds": [
"20150221",
@@ -34,7 +46,7 @@
"20150426"
]
-
+
}
},
@@ -594,10 +606,6 @@
"20150426": [
- {
- "type": "ADD",
- "change": "Begin work on profile system."
- },
{
"type": "FIX",
"change": "The system thinking 0 is the rank ID for deactivated while it's 1."
@@ -611,6 +619,59 @@
"change": "Add changelog page."
}
+ ],
+
+ "20150427": [
+
+ {
+ "type": "ADD",
+ "change": "Begin work on profile system."
+ },
+ {
+ "type": "ADD",
+ "change": "Created function to get profile data from a user."
+ },
+ {
+ "type": "UPD",
+ "change": "Made profile data display properly."
+ },
+ {
+ "type": "FIX",
+ "change": "Fix rank title not displaying on profiles."
+ },
+ {
+ "type": "ADD",
+ "change": "Show country name on profile."
+ },
+ {
+ "type": "ADD",
+ "change": "Show tenshi tag on user's profile if they're tenshi."
+ },
+ {
+ "type": "FIX",
+ "change": "Actually update last online date."
+ },
+ {
+ "type": "FIX",
+ "change": "Activation broken methods in the activation process."
+ },
+ {
+ "type": "ADD",
+ "change": "Add glow around a user's avatar on their profile if they're online or offline (active in the last 5 minutes)."
+ },
+ {
+ "type": "ADD",
+ "change": "Show all online users on the frontpage."
+ },
+ {
+ "type": "FIX",
+ "change": "Fix JavaScript forms not submitting on hitting enter."
+ },
+ {
+ "type": "FIX",
+ "change": "Fix chat redirect."
+ }
+
]
}
diff --git a/_sakura/components/Main.php b/_sakura/components/Main.php
index fb9c6f7..f92d5da 100644
--- a/_sakura/components/Main.php
+++ b/_sakura/components/Main.php
@@ -199,14 +199,22 @@ class Main {
}
// Cleaning strings
- public static function cleanString($string, $lower = false) {
+ public static function cleanString($string, $lower = false, $nospecial = false) {
+ // Run common sanitisation function over string
$string = htmlentities($string, ENT_QUOTES | ENT_IGNORE, Configuration::getConfig('charset'));
$string = stripslashes($string);
$string = strip_tags($string);
+
+ // If set also make the string lowercase
if($lower)
$string = strtolower($string);
+ // If set remove all characters that aren't a-z or 0-9
+ if($nospecial)
+ $string = preg_replace('/[^a-z0-9]/', '', $string);
+
+ // Return clean string
return $string;
}
@@ -481,4 +489,18 @@ class Main {
}
+ // Get country name from ISO 3166 code
+ public static function getCountryName($code) {
+
+ // Parse JSON file
+ $iso3166 = json_decode(file_get_contents(Configuration::getLocalConfig('etc', 'iso3166')), true);
+
+ // Check if key exists
+ if(array_key_exists($code, $iso3166))
+ return $iso3166[$code]; // If entry found return the full name
+ else
+ return 'Unknown'; // Else return unknown
+
+ }
+
}
diff --git a/_sakura/components/Users.php b/_sakura/components/Users.php
index d2d49c6..09cd539 100644
--- a/_sakura/components/Users.php
+++ b/_sakura/components/Users.php
@@ -32,7 +32,8 @@ class Users {
'lastdate' => 0,
'lastunamechange' => 0,
'birthday' => '',
- 'profile_data' => '[]'
+ 'country' => 'EU',
+ 'profile_data' => ''
];
// Empty rank template
@@ -41,7 +42,8 @@ class Users {
'rankname' => 'Non-existent Rank',
'multi' => 0,
'colour' => '#444',
- 'description' => 'A hardcoded dummy rank for fallback.'
+ 'description' => 'A hardcoded dummy rank for fallback.',
+ 'is_premium' => 0
];
// Check if a user is logged in
@@ -69,6 +71,16 @@ class Users {
}
+ // Update last online
+ Database::update('users', [
+ [
+ 'lastdate' => time()
+ ],
+ [
+ 'id' => [Session::$userId, '=']
+ ]
+ ]);
+
// Redirect people that need to change their password to the new format
if(self::getUser(Session::$userId)['password_algo'] == 'legacy' && $_SERVER['PHP_SELF'] != '/authenticate.php' && $_SERVER['PHP_SELF'] != '/imageserve.php')
header('Location: /authenticate.php?legacy=true');
@@ -235,7 +247,7 @@ class Users {
'lastdate' => 0,
'lastunamechange' => time(),
'country' => Main::getCountryCode(),
- 'profile_data' => '[]'
+ 'profile_data' => ''
]);
// Get userid of the new user
@@ -435,7 +447,7 @@ class Users {
return [0, 'USER_NOT_EXIST'];
// Check if a user is activated
- if($user['rank_main'])
+ if(!in_array(1, json_decode($user['ranks'], true)) || !in_array(0, json_decode($user['ranks'], true)) || $user['rank_main'] > 1)
return [0, 'USER_ALREADY_ACTIVE'];
// Send activation e-mail
@@ -453,7 +465,7 @@ class Users {
$user = Database::fetch('users', false, ['id' => [$uid, '=']]);
// User is already activated or doesn't even exist
- if(!count($user) > 1 || !in_array(1, json_decode($user['ranks'], true)) || !in_array(0, json_decode($user['ranks'], true)) || $user['rank_main'] > 1)
+ if(count($user) < 2 || (!in_array(1, json_decode($user['ranks'], true)) || !in_array(0, json_decode($user['ranks'], true))) || $user['rank_main'] > 1)
return false;
// Generate activation key
@@ -642,6 +654,125 @@ class Users {
}
+ // Get user's profile fields
+ public static function getUserProfileData($id) {
+
+ // Get profile fields
+ $profileFields = Database::fetch('profilefields');
+
+ // If there's nothing just return null
+ if(!count($profileFields))
+ return null;
+
+ // Get the profile data JSON from the specified user's profile
+ $profileData = Database::fetch('users', false, ['id' => [$id, '=']]);
+
+ // Once again if nothing was returned just return null
+ if(count($profileData) < 2 || $profileData['profile_data'] == null || !count(json_decode($profileData['profile_data'], true)))
+ return null;
+
+ // Decode the profile_data json
+ $profileData = json_decode($profileData['profile_data'], true);
+
+ // Create output array
+ $profile = [];
+
+ // Check if profile fields aren't fake
+ foreach($profileFields as $field) {
+
+ // Completely strip all special characters from the field name
+ $fieldName = Main::cleanString($field['name'], true, true);
+
+ // Check if the user has the current field set otherwise continue
+ if(!array_key_exists($fieldName, $profileData))
+ continue;
+
+ // Assign field to output with value
+ $profile[$fieldName] = array();
+ $profile[$fieldName]['name'] = $field['name'];
+ $profile[$fieldName]['value'] = $profileData[$fieldName];
+ $profile[$fieldName]['islink'] = $field['islink'];
+
+ // If the field is set to be a link add a value for that as well
+ if($field['islink'])
+ $profile[$fieldName]['link'] = str_replace('{{ VAL }}', $profileData[$fieldName], $field['linkformat']);
+
+ // Check if we have additional options as well
+ if($field['additional'] != null) {
+
+ // Decode the json of the additional stuff
+ $additional = json_decode($field['additional'], true);
+
+ // Go over all additional forms
+ foreach($additional as $subName => $subField) {
+
+ // Check if the user has the current field set otherwise continue
+ if(!array_key_exists($subName, $profileData))
+ continue;
+
+ // Assign field to output with value
+ $profile[$fieldName][$subName] = $profileData[$subName];
+
+ }
+
+ }
+
+ }
+
+ // Return appropiate profile data
+ return $profile;
+
+ }
+
+ // Check if a user is online
+ public static function checkUserOnline($id) {
+
+ // Get user
+ $user = self::getUser($id);
+
+ // Return false if the user doesn't exist because a user that doesn't exist can't be online
+ if(empty($user))
+ return false;
+
+ // Return true if the user was online in the last 5 minutes
+ return ($user['lastdate'] > (time() - 500));
+
+ }
+
+ // Get all online users
+ public static function checkAllOnline() {
+
+ // Assign time - 500 to a variable
+ $time = time() - 500;
+
+ // Get all online users in the past 5 minutes
+ $getAll = Database::fetch('users', true, ['lastdate' => [$time, '>']]);
+
+ // Return all the online users
+ return $getAll;
+
+ }
+
+ // Check if user has Tenshi
+ public static function checkUserTenshi($id) {
+
+ // Get user's ranks
+ $ranks = json_decode(self::getUser($id)['ranks'], true);
+
+ // Check premium flag
+ foreach($ranks as $rank) {
+
+ // If premium rank was found return true
+ if(self::getRank($rank)['is_premium'])
+ return true;
+
+ }
+
+ // Else return false
+ return false;
+
+ }
+
// Get user data by id
public static function getUser($id) {
diff --git a/_sakura/config/config.example.php b/_sakura/config/config.example.php
index 7a960e4..4939615 100644
--- a/_sakura/config/config.example.php
+++ b/_sakura/config/config.example.php
@@ -23,3 +23,4 @@ $sakuraConf['urls']['manage'] = 'manage.flashii.net'; // Moderator panel url
// Errata
$sakuraConf['etc']['cfhosts'] = ROOT .'_sakura/config/cloudflare.hosts'; // Cloudflare IP subnets file
$sakuraConf['etc']['whoisservers'] = ROOT .'_sakura/config/whois.json'; // JSON with Whois servers
+$sakuraConf['etc']['iso3166'] = ROOT .'_sakura/config/iso3166.json'; // JSON with country codes
diff --git a/_sakura/config/iso3166.json b/_sakura/config/iso3166.json
new file mode 100644
index 0000000..17f4bdc
--- /dev/null
+++ b/_sakura/config/iso3166.json
@@ -0,0 +1,250 @@
+{
+ "_CONTRIB": "List of ISO 3166-1 alpha-2 country codes by Flashwave http://flash.moe",
+ "AD": "Andorra",
+ "AE": "United Arab Emirates",
+ "AF": "Afghanistan",
+ "AG": "Antigua and Barbuda",
+ "AI": "Anguilla",
+ "AL": "Albania",
+ "AM": "Armenia",
+ "AO": "Angola",
+ "AQ": "Antarctica",
+ "AR": "Argentina",
+ "AS": "American Samoa",
+ "AT": "Austria",
+ "AU": "Australia",
+ "AW": "Aruba",
+ "AX": "Åland Islands",
+ "AZ": "Azerbaijan",
+ "BA": "Bosnia and Herzegovina",
+ "BB": "Barbados",
+ "BD": "Bangladesh",
+ "BE": "Belgium",
+ "BF": "Burkina Faso",
+ "BG": "Bulgaria",
+ "BH": "Bahrain",
+ "BI": "Burundi",
+ "BJ": "Benin",
+ "BL": "Saint Barthélemy",
+ "BM": "Bermuda",
+ "BN": "Brunei Darussalam",
+ "BO": "Bolivia, Plurinational State of",
+ "BQ": "Bonaire, Sint Eustatius and Saba",
+ "BR": "Brazil",
+ "BS": "Bahamas",
+ "BT": "Bhutan",
+ "BV": "Bouvet Island",
+ "BW": "Botswana",
+ "BY": "Belarus",
+ "BZ": "Belize",
+ "CC": "Cocos (Keeling) Islands",
+ "CD": "Congo, the Democratic Republic of the",
+ "CF": "Central African Republic",
+ "CG": "Congo",
+ "CH": "Switzerland",
+ "CI": "Côte d'Ivoire",
+ "CK": "Cook Islands",
+ "CL": "Chile",
+ "CM": "Cameroon",
+ "CN": "China",
+ "CO": "Colombia",
+ "CR": "Costa Rica",
+ "CU": "Cuba",
+ "CV": "Cabo Verde",
+ "CW": "Curaçao",
+ "CX": "Christmas Island",
+ "CY": "Cyprus",
+ "CZ": "Czech Republic",
+ "DE": "Germany",
+ "DJ": "Djibouti",
+ "DK": "Denmark",
+ "DM": "Dominica",
+ "DO": "Dominican Republic",
+ "DZ": "Algeria",
+ "EC": "Ecuador",
+ "EE": "Estonia",
+ "EG": "Egypt",
+ "EH": "Western Sahara",
+ "ER": "Eritrea",
+ "ES": "Spain",
+ "ET": "Ethiopia",
+ "FI": "Finland",
+ "FJ": "Fiji",
+ "FK": "Falkland Islands (Malvinas)",
+ "FM": "Micronesia, Federated States of",
+ "FO": "Faroe Islands",
+ "FR": "France",
+ "GA": "Gabon",
+ "GB": "United Kingdom",
+ "GD": "Grenada",
+ "GE": "Georgia",
+ "GF": "French Guiana",
+ "GG": "Guernsey",
+ "GH": "Ghana",
+ "GI": "Gibraltar",
+ "GL": "Greenland",
+ "GM": "Gambia",
+ "GN": "Guinea",
+ "GP": "Guadeloupe",
+ "GQ": "Equatorial Guinea",
+ "GR": "Greece",
+ "GS": "South Georgia and the South Sandwich Islands",
+ "GT": "Guatemala",
+ "GU": "Guam",
+ "GW": "Guinea-Bissau",
+ "GY": "Guyana",
+ "HK": "Hong Kong",
+ "HM": "Heard Island and McDonald Islands",
+ "HN": "Honduras",
+ "HR": "Croatia",
+ "HT": "Haiti",
+ "HU": "Hungary",
+ "ID": "Indonesia",
+ "IE": "Ireland",
+ "IL": "Israel",
+ "IM": "Isle of Man",
+ "IN": "India",
+ "IO": "British Indian Ocean Territory",
+ "IQ": "Iraq",
+ "IR": "Iran, Islamic Republic of",
+ "IS": "Iceland",
+ "IT": "Italy",
+ "JE": "Jersey",
+ "JM": "Jamaica",
+ "JO": "Jordan",
+ "JP": "Japan",
+ "KE": "Kenya",
+ "KG": "Kyrgyzstan",
+ "KH": "Cambodia",
+ "KI": "Kiribati",
+ "KM": "Comoros",
+ "KN": "Saint Kitts and Nevis",
+ "KP": "Korea, Democratic People's Republic of",
+ "KR": "Korea, Republic of",
+ "KW": "Kuwait",
+ "KY": "Cayman Islands",
+ "KZ": "Kazakhstan",
+ "LA": "Lao People's Democratic Republic",
+ "LB": "Lebanon",
+ "LC": "Saint Lucia",
+ "LI": "Liechtenstein",
+ "LK": "Sri Lanka",
+ "LR": "Liberia",
+ "LS": "Lesotho",
+ "LT": "Lithuania",
+ "LU": "Luxembourg",
+ "LV": "Latvia",
+ "LY": "Libya",
+ "MA": "Morocco",
+ "MC": "Monaco",
+ "MD": "Moldova, Republic of",
+ "ME": "Montenegro",
+ "MF": "Saint Martin",
+ "MG": "Madagascar",
+ "MH": "Marshall Islands",
+ "MK": "Macedonia, the former Yugoslav Republic of",
+ "ML": "Mali",
+ "MM": "Myanmar",
+ "MN": "Mongolia",
+ "MO": "Macao",
+ "MP": "Northern Mariana Islands",
+ "MQ": "Martinique",
+ "MR": "Mauritania",
+ "MS": "Montserrat",
+ "MT": "Malta",
+ "MU": "Mauritius",
+ "MV": "Maldives",
+ "MW": "Malawi",
+ "MX": "Mexico",
+ "MY": "Malaysia",
+ "MZ": "Mozambique",
+ "NA": "Namibia",
+ "NC": "New Caledonia",
+ "NE": "Niger",
+ "NF": "Norfolk Island",
+ "NG": "Nigeria",
+ "NI": "Nicaragua",
+ "NL": "The Netherlands",
+ "NO": "Norway",
+ "NP": "Nepal",
+ "NR": "Nauru",
+ "NU": "Niue",
+ "NZ": "New Zealand",
+ "OM": "Oman",
+ "PA": "Panama",
+ "PE": "Peru",
+ "PF": "French Polynesia",
+ "PG": "Papua New Guinea",
+ "PH": "Philippines",
+ "PK": "Pakistan",
+ "PL": "Poland",
+ "PM": "Saint Pierre and Miquelon",
+ "PN": "Pitcairn",
+ "PR": "Puerto Rico",
+ "PS": "Palestine, State of",
+ "PT": "Portugal",
+ "PW": "Palau",
+ "PY": "Paraguay",
+ "QA": "Qatar",
+ "RE": "Réunion",
+ "RO": "Romania",
+ "RS": "Serbia",
+ "RU": "Russian Federation",
+ "RW": "Rwanda",
+ "SA": "Saudi Arabia",
+ "SB": "Solomon Islands",
+ "SC": "Seychelles",
+ "SD": "Sudan",
+ "SE": "Sweden",
+ "SG": "Singapore",
+ "SH": "Saint Helena, Ascension and Tristan da Cunha",
+ "SI": "Slovenia",
+ "SJ": "Svalbard and Jan Mayen",
+ "SK": "Slovakia",
+ "SL": "Sierra Leone",
+ "SM": "San Marino",
+ "SN": "Senegal",
+ "SO": "Somalia",
+ "SR": "Suriname",
+ "SS": "South Sudan",
+ "ST": "Sao Tome and Principe",
+ "SV": "El Salvador",
+ "SX": "Sint Maarten",
+ "SY": "Syrian Arab Republic",
+ "SZ": "Swaziland",
+ "TC": "Turks and Caicos Islands",
+ "TD": "Chad",
+ "TF": "French Southern Territories",
+ "TG": "Togo",
+ "TH": "Thailand",
+ "TK": "Tokelau",
+ "TL": "Timor-Leste",
+ "TM": "Turkmenistan",
+ "TN": "Tunisia",
+ "TO": "Tonga",
+ "TR": "Turkey",
+ "TT": "Trinidad and Tobago",
+ "TV": "Tuvalu",
+ "TW": "Taiwan, Province of China",
+ "TZ": "Tanzania, United Republic of",
+ "UA": "Ukraine",
+ "UG": "Uganda",
+ "UM": "United States Minor Outlying Islands",
+ "US": "United States",
+ "UY": "Uruguay",
+ "UZ": "Uzbekistan",
+ "VA": "Holy See (Vatican City State)",
+ "VC": "Saint Vincent and the Grenadines",
+ "VE": "Venezuela, Bolivarian Republic of",
+ "VG": "Virgin Islands, British",
+ "VI": "Virgin Islands, U.S.",
+ "VN": "Viet Nam",
+ "VU": "Vanuatu",
+ "WF": "Wallis and Futuna",
+ "WS": "Samoa",
+ "YE": "Yemen",
+ "YT": "Mayotte",
+ "ZA": "South Africa",
+ "ZM": "Zambia",
+ "ZW": "Zimbabwe"
+}
diff --git a/_sakura/sakura.php b/_sakura/sakura.php
index 95552a1..250610d 100644
--- a/_sakura/sakura.php
+++ b/_sakura/sakura.php
@@ -8,10 +8,10 @@
namespace Sakura;
// Define Sakura version
-define('SAKURA_VERSION', '20150426');
-define('SAKURA_VLABEL', 'Cyan');
+define('SAKURA_VERSION', '20150427');
+define('SAKURA_VLABEL', 'Heliotrope');
define('SAKURA_VTYPE', 'Development');
-define('SAKURA_COLOUR', '#4EC9B0');
+define('SAKURA_COLOUR', '#DF73FF');
// Define Sakura Path
define('ROOT', str_replace(basename(__DIR__), '', dirname(__FILE__)));
diff --git a/_sakura/templates/versionInfo.tpl b/_sakura/templates/changeLog.tpl
similarity index 100%
rename from _sakura/templates/versionInfo.tpl
rename to _sakura/templates/changeLog.tpl
diff --git a/_sakura/templates/yuuno/global/header.tpl b/_sakura/templates/yuuno/global/header.tpl
index 1c19611..e7b8c08 100644
--- a/_sakura/templates/yuuno/global/header.tpl
+++ b/_sakura/templates/yuuno/global/header.tpl
@@ -11,11 +11,11 @@
{% endif %}
-
-
+
+
-
+