1
0
mirror of https://github.com/Anuken/Mindustry.git synced 2024-09-11 08:15:35 +03:00

Added unit tests

This commit is contained in:
Anuken 2018-10-03 20:58:35 -04:00
parent 34715b1e06
commit c82fd9ead5
11 changed files with 233 additions and 88 deletions

4
.gitignore vendored
View File

@ -14,8 +14,10 @@
/core/assets-raw/sprites/generated/
/annotations/build/
/kryonet/build/
/packer/build/
/tools/build/
/tests/build/
/server/build/
/test_files/
/annotations/build/
/android/assets/mindustry-maps/
/android/assets/mindustry-saves/

View File

@ -27,7 +27,7 @@ allprojects {
appName = 'Mindustry'
gdxVersion = '1.9.8'
roboVMVersion = '2.3.0'
uCoreVersion = '00d05bd7d3e943c8a454ccf2cb69cdffb23afbb7'
uCoreVersion = '220916714cbe63664c34f95a9dc50a362feca732'
getVersionString = {
String buildVersion = getBuildVersion()
@ -119,20 +119,6 @@ project(":html") {
}
}
project(":tests"){
apply plugin: "java"
dependencies {
compile project(":core")
testImplementation('org.junit.jupiter:junit-jupiter-api:5.1.0')
testRuntimeOnly('org.junit.jupiter:junit-jupiter-engine:5.1.0')
}
test {
useJUnitPlatform()
}
}
project(":ios") {
apply plugin: "java"
apply plugin: "robovm"
@ -218,6 +204,23 @@ project(":server") {
}
}
project(":tests"){
apply plugin: "java"
dependencies {
testImplementation project(":core")
testImplementation('org.junit.jupiter:junit-jupiter-api:5.1.0')
testRuntimeOnly('org.junit.jupiter:junit-jupiter-engine:5.1.0')
testImplementation "com.badlogicgames.gdx:gdx-backend-headless:$gdxVersion"
testImplementation "com.badlogicgames.gdx:gdx-platform:$gdxVersion:natives-desktop"
}
test {
useJUnitPlatform()
workingDir = new File("../core/assets")
}
}
project(":tools") {
apply plugin: "java"

Binary file not shown.

Before

Width:  |  Height:  |  Size: 598 B

After

Width:  |  Height:  |  Size: 607 B

Binary file not shown.

Before

Width:  |  Height:  |  Size: 102 KiB

After

Width:  |  Height:  |  Size: 102 KiB

View File

@ -11,6 +11,7 @@ import io.anuke.mindustry.type.ItemStack;
import io.anuke.ucore.util.Bits;
import static io.anuke.mindustry.Vars.control;
import static io.anuke.mindustry.Vars.headless;
@Serialize
public class Sector{
@ -46,11 +47,11 @@ public class Sector{
}
public SaveSlot getSave(){
return control.getSaves().getByID(saveID);
return !hasSave() ? null : control.getSaves().getByID(saveID);
}
public boolean hasSave(){
return control.getSaves().getByID(saveID) != null;
return !headless && control.getSaves().getByID(saveID) != null;
}
public int packedPosition(){

View File

@ -47,7 +47,9 @@ public class Sectors{
}
world.loadSector(sector);
logic.play();
sector.saveID = control.getSaves().addSave("sector-" + sector.packedPosition()).index;
if(!headless){
sector.saveID = control.getSaves().addSave("sector-" + sector.packedPosition()).index;
}
world.sectors().save();
world.setSector(sector);
sector.currentMission().onBegin();

View File

@ -1,7 +1,6 @@
package io.anuke.mindustry.net;
import com.badlogic.gdx.utils.Array;
import com.badlogic.gdx.utils.IntMap;
import com.badlogic.gdx.utils.ObjectMap;
import io.anuke.annotations.Annotations.Serialize;
import io.anuke.ucore.core.Settings;
@ -16,8 +15,6 @@ public class Administration{
private ObjectMap<String, PlayerInfo> playerInfo = new ObjectMap<>();
/**Maps UUIDs to trace infos. This is wiped when a player logs off.*/
private ObjectMap<String, TraceInfo> traceInfo = new ObjectMap<>();
/** Maps packed coordinates to logs for that coordinate*/
private IntMap<Array<EditLog>> editLogs = new IntMap<>();
private Array<String> bannedIPs = new Array<>();
public Administration(){
@ -46,16 +43,6 @@ public class Administration{
Settings.save();
}
public void setAntiGriefParams(int maxBreak, int cooldown){
Settings.putInt("antigrief-max", maxBreak);
Settings.putInt("antigrief-cooldown", cooldown);
Settings.save();
}
public IntMap<Array<EditLog>> getEditLogs(){
return editLogs;
}
/**
* Call when a player joins to update their information here.
*/

View File

@ -1,21 +0,0 @@
package io.anuke.mindustry.net;
import io.anuke.mindustry.world.Block;
public class EditLog{
public String playername;
public Block block;
public int rotation;
public EditAction action;
EditLog(String playername, Block block, int rotation, EditAction action){
this.playername = playername;
this.block = block;
this.rotation = rotation;
this.action = action;
}
public enum EditAction{
PLACE, BREAK
}
}

View File

@ -1,7 +1,6 @@
package io.anuke.mindustry.server;
import com.badlogic.gdx.ApplicationListener;
import com.badlogic.gdx.ApplicationLogger;
import com.badlogic.gdx.Files.FileType;
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.Preferences;
@ -13,6 +12,7 @@ import io.anuke.kryonet.KryoClient;
import io.anuke.kryonet.KryoServer;
import io.anuke.mindustry.net.Net;
import io.anuke.ucore.io.BinaryPreferences;
import io.anuke.ucore.util.EmptyLogger;
import io.anuke.ucore.util.OS;
import java.io.File;
@ -24,31 +24,7 @@ public class ServerLauncher extends HeadlessApplication{
super(listener, config);
//don't do anything at all for GDX logging: don't want controller info and such
Gdx.app.setApplicationLogger(new ApplicationLogger(){
@Override
public void log(String tag, String message){
}
@Override
public void log(String tag, String message, Throwable exception){
}
@Override
public void error(String tag, String message){
}
@Override
public void error(String tag, String message, Throwable exception){
}
@Override
public void debug(String tag, String message){
}
@Override
public void debug(String tag, String message, Throwable exception){
}
});
Gdx.app.setApplicationLogger(new EmptyLogger());
}
public static void main(String[] args){

View File

@ -0,0 +1,204 @@
import com.badlogic.gdx.Gdx;
import com.badlogic.gdx.backends.headless.HeadlessApplication;
import com.badlogic.gdx.backends.headless.HeadlessApplicationConfiguration;
import io.anuke.mindustry.Vars;
import io.anuke.mindustry.content.Items;
import io.anuke.mindustry.content.blocks.Blocks;
import io.anuke.mindustry.content.blocks.StorageBlocks;
import io.anuke.mindustry.core.GameState.State;
import io.anuke.mindustry.core.Logic;
import io.anuke.mindustry.core.NetServer;
import io.anuke.mindustry.core.World;
import io.anuke.mindustry.game.Content;
import io.anuke.mindustry.game.Team;
import io.anuke.mindustry.io.BundleLoader;
import io.anuke.mindustry.io.SaveIO;
import io.anuke.mindustry.maps.Map;
import io.anuke.mindustry.world.Tile;
import io.anuke.ucore.core.Timers;
import io.anuke.ucore.modules.ModuleCore;
import io.anuke.ucore.util.EmptyLogger;
import io.anuke.ucore.util.Log;
import org.junit.jupiter.api.BeforeAll;
import org.junit.jupiter.api.BeforeEach;
import org.junit.jupiter.api.Test;
import java.io.File;
import static io.anuke.mindustry.Vars.*;
import static org.junit.jupiter.api.Assertions.*;
public class ApplicationTests{
@BeforeAll
static void launchApplication(){
try{
boolean[] begins = {false};
Throwable[] exceptionThrown = {null};
Log.setUseColors(false);
ModuleCore core = new ModuleCore(){
@Override
public void init(){
Vars.init();
headless = true;
BundleLoader.load();
content.load();
content.initialize(Content::init);
module(logic = new Logic());
module(world = new World());
module(netServer = new NetServer());
}
@Override
public void postInit(){
super.postInit();
begins[0] = true;
}
};
HeadlessApplicationConfiguration config = new HeadlessApplicationConfiguration();
config.preferencesDirectory = "test_files/";
new File("tests_files/").delete();
new HeadlessApplication(core, config){{
Gdx.app.setApplicationLogger(new EmptyLogger());
}};
for(Thread thread : Thread.getAllStackTraces().keySet()){
if(thread.getName().equals("HeadlessApplication")){
thread.setUncaughtExceptionHandler((t, throwable) -> exceptionThrown[0] = throwable);
break;
}
}
while(!begins[0]){
if(exceptionThrown[0] != null){
fail(exceptionThrown[0]);
}
Thread.sleep(10);
}
}catch(Throwable r){
fail(r);
}
}
@BeforeEach
void resetWorld(){
Timers.setDeltaProvider(() -> 1f);
logic.reset();
state.set(State.menu);
}
@Test
void initialization(){
assertTrue(logic != null);
assertTrue(world != null);
assertTrue(content.getContentMap().length > 0);
}
@Test
void loadSector(){
world.sectors().createSector(0, 0);
world.sectors().playSector(world.sectors().get(0, 0));
}
@Test
void playMap(){
assertTrue(world.maps().all().size > 0);
world.loadMap(world.maps().all().first());
}
@Test
void spawnWaves(){
world.loadMap(world.maps().all().first());
logic.runWave();
unitGroups[waveTeam.ordinal()].updateEvents();
assertFalse(unitGroups[waveTeam.ordinal()].isEmpty());
}
@Test
void createMap(){
assertTrue(world.maps().all().size > 0);
Tile[][] tiles = world.createTiles(8, 8);
world.beginMapLoad();
for(int x = 0; x < tiles.length; x++){
for(int y = 0; y < tiles[0].length; y++){
tiles[x][y] = new Tile(x, y, (byte)0, (byte)0);
}
}
world.endMapLoad();
}
@Test
void multiblock(){
createMap();
int bx = 4;
int by = 4;
world.setBlock(world.tile(bx, by), StorageBlocks.core, Team.blue);
assertTrue(world.tile(bx, by).getTeam() == Team.blue);
for(int x = bx-1; x <= bx + 1; x++){
for(int y = by-1; y <= by + 1; y++){
if(x == bx && by == y){
assertTrue(world.tile(x, y).block() == StorageBlocks.core);
}else{
assertTrue(world.tile(x, y).block() == Blocks.blockpart && world.tile(x, y).getLinked() == world.tile(bx, by));
}
}
}
}
@Test
void blockInventories(){
multiblock();
Tile tile = world.tile(4, 4);
tile.entity.items.add(Items.coal, 5);
tile.entity.items.add(Items.titanium, 50);
assertTrue(tile.entity.items.total() == 55);
tile.entity.items.remove(Items.phasematter, 10);
tile.entity.items.remove(Items.titanium, 10);
assertTrue(tile.entity.items.total() == 45);
}
@Test
void timers(){
boolean[] ran = {false};
Timers.run(1.9999f, () -> ran[0] = true);
Timers.update();
assertFalse(ran[0]);
Timers.update();
assertTrue(ran[0]);
}
@Test
void save(){
assertTrue(world.maps().all().size > 0);
world.loadMap(world.maps().all().first());
SaveIO.saveToSlot(0);
}
@Test
void load(){
assertTrue(world.maps().all().size > 0);
world.loadMap(world.maps().all().first());
Map map = world.getMap();
SaveIO.saveToSlot(0);
resetWorld();
SaveIO.loadFromSlot(0);
assertTrue(world.getMap() == map);
assertTrue(world.width() == map.meta.width);
assertTrue(world.height() == map.meta.height);
}
}

View File

@ -1,9 +0,0 @@
import org.junit.jupiter.api.BeforeEach;
public class Tests{
@BeforeEach
void launchApplication(){
}
}