Can't find room extension

Post here your questions about SFS2X. Here we discuss all server-side matters. For client API questions see the dedicated forums.

Moderators: Lapo, Bax

Fenlena
Posts: 6
Joined: 26 Dec 2018, 03:14

Can't find room extension

Postby Fenlena » 06 Nov 2021, 18:48

I have an Eclipse workspace with two projects: one for the zone extension and one for the room extension. I tried at first to put both extensions in the same project but SFS could not find the room extension when I created the room server-side. Everything was working just fine with two separate projects until I decided I wanted to be able to use classes from the zone extension in the room extension. So, for the room extension, I clicked Project->Properties->Java Build Path->Projects and selected the zone extension project. When I exported the room extension, suddenly SFS can't find the room extension.

I've went so far as to start the entire project over from scratch several times using a variety of configurations but SFS just refuses to find my room extension ever again. I can't possibly imagine why not.

Both exported extensions are in separate .jar files in SFS2X/extensions/BattlefieldExtension
The zone extension is called BFCampaignRoomExtension.jar The room extension is called BFSoneExtension.jar

In the project, the zone extension class is in a package called battlefieldZone. The zone extension class is called ZoneExtension. The room extension is in a package called battlefieldCampaignRoom. (I have tried using the same package for both projects. Doesn't seem to make a difference.) The room extension class is called CampaignRoomExtension. Here are the relevant lines of code in the class that handles the SFSEventType.USER_JOIN_ZONE event.

CreateRoomSettings cfg = new CreateRoomSettings();
cfg.setExtension(new CreateRoomSettings.RoomExtensionSettings("BattlefieldExtension", "CampaignRoomExtension"));

Here is the error from SFS.

Exception: com.smartfoxserver.v2.exceptions.SFSExtensionException
Message: Class not found: CampaignRoomExtension
Description: Failure while creating room extension.
Possible Causes: If the CreateRoom request was sent from client make sure that the extension name matches the name of an existing extension
+--- --- ---+
Stack Trace:
+--- --- ---+
com.smartfoxserver.v2.entities.managers.SFSExtensionManager.createJavaExtension(SFSExtensionManager.java:358)
com.smartfoxserver.v2.entities.managers.SFSExtensionManager.createExtension(SFSExtensionManager.java:260)
com.smartfoxserver.v2.entities.managers.SFSRoomManager.createRoomExtension(SFSRoomManager.java:247)
com.smartfoxserver.v2.entities.managers.SFSRoomManager.createRoom(SFSRoomManager.java:194)
com.smartfoxserver.v2.entities.SFSZone.createRoom(SFSZone.java:261)
com.smartfoxserver.v2.api.SFSApi.createRoom(SFSApi.java:739)
com.smartfoxserver.v2.api.SFSApi.createRoom(SFSApi.java:706)
battlefieldZone.JoinZoneEvent.handleServerEvent(JoinZoneEvent.java:77)
com.smartfoxserver.v2.extensions.SFSExtension.handleServerEvent(SFSExtension.java:259)
com.smartfoxserver.v2.entities.managers.SFSExtensionManager.dispatchEvent(SFSExtensionManager.java:769)
com.smartfoxserver.v2.entities.managers.SFSExtensionManager.dispatchZoneLevelEvent(SFSExtensionManager.java:690)
com.smartfoxserver.v2.entities.managers.SFSExtensionManager.handleServerEvent(SFSExtensionManager.java:891)
com.smartfoxserver.v2.core.SFSEventManager$SFSEventRunner.run(SFSEventManager.java:66)
java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1149)
java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:624)
java.lang.Thread.run(Thread.java:748)
::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::::

I've been banging my head on this one for two days. I'm sure it is something stupid and minor I have overlooked. A fresh set of eyes would be greatly appreciated.

EDIT: I've now completely uninstalled SFS from my Windows 10 machine, rebooted, re-installed and re-configured SFS then re-created the projects in Eclipse from scratch and... SFS still can't find my room extension. I don't know if it matters but the zone extension is loading properly, allowing me to login from the Unity client and showing via trace() that it is connecting to the database and performing queries without exceptions. I am using the signup and login assistant. The database queries are for other stuff.

2nd Edit: I probably should have mentioned that the room extension shows up in the SFS Admin Tool. I can assign it to a static room and it works fine. It only gives me fits when I try to assign it dynamically.
Fenlena
Posts: 6
Joined: 26 Dec 2018, 03:14

Re: Can't find room extension

Postby Fenlena » 07 Nov 2021, 17:04

I've boiled my code down as much as possible while still keeping the basic logic in tact. I added a DeleteAllRooms function to make sure the room gets created from scratch since I removed the logic that checks to see if the room exists. So, for the zone extension, I have

Code: Select all

package Battlefield;

import java.util.Arrays;
import com.smartfoxserver.v2.components.login.ILoginAssistantPlugin;
import com.smartfoxserver.v2.components.login.LoginAssistantComponent;
import com.smartfoxserver.v2.components.login.LoginData;
import com.smartfoxserver.v2.components.signup.PasswordMode;
import com.smartfoxserver.v2.components.signup.SignUpAssistantComponent;
import com.smartfoxserver.v2.core.SFSEventType;
import com.smartfoxserver.v2.db.IDBManager;
import com.smartfoxserver.v2.entities.data.ISFSObject;
import com.smartfoxserver.v2.extensions.SFSExtension;
import com.smartfoxserver.v2.persistence.room.DBRoomStorageConfig;
import com.smartfoxserver.v2.persistence.room.RoomStorageMode;

public class ZoneExtension extends SFSExtension 
{
   IDBManager sfs2xDBManager;
   private SignUpAssistantComponent suac;
   private LoginAssistantComponent lac;   
   
   void InitRoomPersistence()
   {
      DBRoomStorageConfig dbsc = new DBRoomStorageConfig();
      dbsc.tableName = "BG_rooms";
      
      dbsc.storeInactiveRooms = true;
      dbsc.storeRoomVariables = true;
       
       getParentZone().initRoomPersistence(RoomStorageMode.DB_STORAGE, dbsc);      
   }
   
   public void InitSUAC()
   {
      suac = new SignUpAssistantComponent();
      
        suac.getConfig().minUserNameLength = 3;
        suac.getConfig().maxUserNameLength = 30;
        suac.getConfig().maxEmailLength = 50;
        suac.getConfig().maxPasswordLength = 33;
        suac.getConfig().checkForDuplicateEmails = true;
        suac.getConfig().checkForDuplicateUserNames = true;
        suac.getConfig().passwordMode = PasswordMode.MD5;
   }
   
   
   public void InitLAC()
   {
      lac = new LoginAssistantComponent(this);
      lac.getConfig().userNameField = "username";
      
      lac.getConfig().extraFields = Arrays.asList("id");
        
       lac.getConfig().postProcessPlugin = new ILoginAssistantPlugin ()
       {          
          @Override
           public void execute(LoginData loginData)
           {
               ISFSObject fields = loginData.extraFields;
               loginData.session.setProperty("dbID", fields.getInt("id"));
           }
       };
   }
   
   void DeleteAllRooms()
   {
      try
          {
         getParentZone().getRoomPersistenceApi().removeAllRooms();
      }
          catch (SFSStorageException e)
          {
         e.printStackTrace();
      }
   }
   
   @Override
   public void init()
   {
      sfs2xDBManager = getParentZone().getDBManager();
      
       InitRoomPersistence();
       DeleteAllRooms();
       
       InitSUAC();
       InitLAC();
       
       addRequestHandler(SignUpAssistantComponent.COMMAND_PREFIX, suac);
       addEventHandler(SFSEventType.ROOM_REMOVED, RoomRemovedEvent.class);
       addEventHandler(SFSEventType.USER_JOIN_ZONE, JoinZoneEvent.class);
   }
   
   @Override
    public void destroy()
    {
        super.destroy();
    }
}

Since I am using room persistence, I need to save the room when nobody is in it.

Code: Select all

 
package Battlefield;

import com.smartfoxserver.v2.core.ISFSEvent;
import com.smartfoxserver.v2.core.SFSEventParam;
import com.smartfoxserver.v2.entities.Room;
import com.smartfoxserver.v2.exceptions.SFSException;
import com.smartfoxserver.v2.extensions.BaseServerEventHandler;
import com.smartfoxserver.v2.persistence.room.SFSStorageException;

public class RoomRemovedEvent extends BaseServerEventHandler
{
   @Override
   public void handleServerEvent(ISFSEvent event) throws SFSException
   {
      Room room = (Room) event.getParameter(SFSEventParam.ROOM);
      
      try
      {
         getParentExtension().getParentZone().getRoomPersistenceApi().saveRoom(room);
      }
      catch (SFSStorageException a)
      {
         trace("catch" + a);
      }
   }
}

Once the user joins the zone, the room is created. I had logic to determine if the room had already been created but it isn't relative to this issue, so I took it out.

Code: Select all

package Battlefield;

import com.smartfoxserver.v2.api.CreateRoomSettings;
import com.smartfoxserver.v2.core.ISFSEvent;
import com.smartfoxserver.v2.core.SFSEventParam;
import com.smartfoxserver.v2.entities.Room;
import com.smartfoxserver.v2.entities.SFSRoomRemoveMode;
import com.smartfoxserver.v2.entities.User;
import com.smartfoxserver.v2.exceptions.SFSCreateRoomException;
import com.smartfoxserver.v2.exceptions.SFSException;
import com.smartfoxserver.v2.exceptions.SFSJoinRoomException;
import com.smartfoxserver.v2.extensions.BaseServerEventHandler;

public class JoinZoneEvent extends BaseServerEventHandler
{
   @Override
   public void handleServerEvent(ISFSEvent event) throws SFSException
   {
      User user = (User) event.getParameter(SFSEventParam.USER);
      
      CreateRoomSettings cfg = new CreateRoomSettings();
      cfg.setName(user.getName() + "Campaign");
      cfg.setMaxUsers(1);
      cfg.setMaxVariablesAllowed(10);
      cfg.setGame(false);
      cfg.setExtension(new CreateRoomSettings.RoomExtensionSettings("Battlefield", "SinglePlayerRoom"));
      cfg.setDynamic(true);
      cfg.setAutoRemoveMode(SFSRoomRemoveMode.WHEN_EMPTY);
             
      try
      {
         Room myNewRoom = getApi().createRoom(getParentExtension().getParentZone(), cfg, user);
         getApi().joinRoom(user, myNewRoom);
      }
      catch (SFSCreateRoomException b)
      {
          trace("Exception " + b);
      }
      catch (SFSJoinRoomException c)
      {
         trace("Excemption " + c);
      }
   }
}

Finally, we have the room extension that I can't seem to assign dynamically to save my life. I have stripped it down to a basic extension and it still won't work. I changed the name just to make sure I get the same error.

Code: Select all

package Battlefield;


import com.smartfoxserver.v2.extensions.SFSExtension;

public class SinglePlayerRoom extends SFSExtension
{
   @Override
   public void init()
   {
      trace("init room");
   }
   
   @Override
    public void destroy()
    {
        super.destroy();
    }
}
User avatar
Lapo
Site Admin
Posts: 23027
Joined: 21 Mar 2005, 09:50
Location: Italy

Re: Can't find room extension

Postby Lapo » 08 Nov 2021, 08:40

Hi,
the important part of your code to check is only this line:

Code: Select all

cfg.setExtension(new CreateRoomSettings.RoomExtensionSettings("Battlefield", "SinglePlayerRoom"));

where you reference the Extension that you'd like to load.

There are however several issues:

1) You need to specify the fully qualified name of your class, which means the complete package name + class name of the class.
2) The package name should always be lower case. No upper cases in Java package names.

So I recommend changing the current package name from Battlefield to --> battlefield and re-export the jar file.
Then in your code use this:

Code: Select all

cfg.setExtension(new CreateRoomSettings.RoomExtensionSettings("Battlefield", "battlefield.SinglePlayerRoom"));


Cheers
Lapo
--
gotoAndPlay()
...addicted to flash games
Fenlena
Posts: 6
Joined: 26 Dec 2018, 03:14

Re: Can't find room extension

Postby Fenlena » 08 Nov 2021, 16:14

You are a lifesaver. Thanks so much. I don't know how it worked before because I'm pretty sure I didn't have the package name in there but that fixed my issue.

EDIT: Thinking back, I think I may have just used the default package to begin with. Perhaps this is why it worked before.

Return to “SFS2X Questions”

Who is online

Users browsing this forum: Baidu [Spider] and 129 guests