Help with csm needed
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Help with csm needed
I make a csm mod for someone and I follow the instructions on the minetest modding book and as CSM my code doesn't work, but as a normal mod it does work.
Does anyone know how to solve this problem??
P.S. Things as "minetest.register_privilege", "minetest.register_on_joinplayer" and "minetest.register_globalstep" doesn't work in my code and I think also "minetest.register_chatcommand"
All the "minetest." functions doesn't work
Does anyone know how to solve this problem??
P.S. Things as "minetest.register_privilege", "minetest.register_on_joinplayer" and "minetest.register_globalstep" doesn't work in my code and I think also "minetest.register_chatcommand"
All the "minetest." functions doesn't work
Last edited by Miniontoby on Sun Nov 10, 2019 11:23, edited 1 time in total.
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
Client-side mods use a completely different API that has little in common with the server-side API. I'm not sure what you're expecting functions such as minetest.register_privilege to even mean in a client-side context but many of the server-side API functions aren't relevant to client-side mods at all, or the equivalent client-side functions need different parameters.
Read https://github.com/minetest/minetest/bl ... ua_api.txt for the client-side API documentation. It's highly unlikely that you'll be able to simply convert a server-side mod to a client-side mod. Many of the things that you'd normally do in a server-side mod, such as adding new node types or changing game mechanics, are not applicable to client-side mods (as the server controls those aspects of the game) and impossible to do in a client-side mod, and client-side mods often focus on modifying the UI of the game rather than the game world itself (such as adding extra features via chat commands or with a GUI form).
Read https://github.com/minetest/minetest/bl ... ua_api.txt for the client-side API documentation. It's highly unlikely that you'll be able to simply convert a server-side mod to a client-side mod. Many of the things that you'd normally do in a server-side mod, such as adding new node types or changing game mechanics, are not applicable to client-side mods (as the server controls those aspects of the game) and impossible to do in a client-side mod, and client-side mods often focus on modifying the UI of the game rather than the game world itself (such as adding extra features via chat commands or with a GUI form).
Re: Help with csm needed
It would be nice if that was actually included in the doc folder.
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
Is there an "minetest" depend or something else??
Re: Help with csm needed
Minetest requires that clientmods have a file called mod.conf, and where is this documented indeed. That file is not present, and requires the user to create it.
Ideally the management of CSM mods could be managed via the GUI. At the very least, mods.conf could be present by default.
It frustrates me that so much effort was made to restrict and really neuter CSM.
Ideally the management of CSM mods could be managed via the GUI. At the very least, mods.conf could be present by default.
It frustrates me that so much effort was made to restrict and really neuter CSM.
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
It actually is. In the Minetest source tree, you will have doc/client_lua_api.txt alongside doc/lua_api.txt (the latter being the documentation for the server-side mod API). If you don't have this documentation file it's possible that you're using an old version of Minetest that doesn't support client-side mods or you're using a pre-built Linux package that for some reason doesn't include this file.zing269 wrote:It would be nice if that was actually included in the doc folder.
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
To clarify, the file is called mods.conf, not mod.conf, and there is one of these files for each Minetest installation located directly inside the clientmods directory. This file specifies which client-side mods should be loaded, and should not be confused with the individual mod.conf files that each server-side mod should provide (and which do not currently seem to exist in the context of client-side mods).jas wrote:Minetest requires that clientmods have a file called mod.conf, and where is this documented indeed. That file is not present, and requires the user to create it.
The clientmods/mods.conf file should contain one line for each client-side mod that you want to load, as follows: load_mod_modname = true. In this case, modname is the name of the directory containing the client-side mod (so for example if you installed the friendly_chat mod then the line would be load_mod_friendly_chat = true). You can also change true to false and in that case the mod won't be loaded (the same as if the line was missing altogether). If I remember correctly, once the file exists, Minetest will add lines (with the value set to false) for any mods that it finds but which aren't already listed in the file.
Re: Help with csm needed
I'm using the official windows 64-bit download from minetest.net and that file is not included.micheal65536 wrote:It actually is. In the Minetest source tree, you will have doc/client_lua_api.txt alongside doc/lua_api.txt (the latter being the documentation for the server-side mod API). If you don't have this documentation file it's possible that you're using an old version of Minetest that doesn't support client-side mods or you're using a pre-built Linux package that for some reason doesn't include this file.zing269 wrote:It would be nice if that was actually included in the doc folder.
Re: Help with csm needed
I don't see it: https://github.com/minetest/minetest/tr ... lientmods/there is one of these files for each Minetest installation located directly inside the clientmods directory
It's not there.
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
You have to create it yourself. When I said "there is", I meant "there is expected to be". As in "there is one mods.conf file directly inside the clientmods directory, as opposed to individual mod.conf files for each mod". I was trying to distinguish this clearly from the similarly-named mod.conf files used for server-side mods.jas wrote:I don't see it: https://github.com/minetest/minetest/tr ... lientmods/there is one of these files for each Minetest installation located directly inside the clientmods directory
It's not there.
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
I have a "/clientmods/mods.conf" with the mod enabled and I got an error of the code
- Attachments
-
- The error
- Minetest 5.1.0 [Main Menu] 11-11-2019 14_33_55.png (123.13 KiB) Viewed 994 times
Last edited by Miniontoby on Thu Nov 14, 2019 13:39, edited 1 time in total.
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
The error is because client-side mods use a different API to server-side mods. Please re-read this post where I already explained this:Miniontoby wrote:I have a "/clientmods/mods.conf" with the mod enabled and I got an error of the code
Think about it logically: minetest.register_privilege registers a privilege that the server uses to control what commands players can use or what actions they can take. What would you expect minetest.register_privilege to do in a client-side mod and why would you want to call it? Privileges make no sense in the context of a client-side mod.micheal65536 wrote:Client-side mods use a completely different API that has little in common with the server-side API. I'm not sure what you're expecting functions such as minetest.register_privilege to even mean in a client-side context but many of the server-side API functions aren't relevant to client-side mods at all, or the equivalent client-side functions need different parameters.
Read https://github.com/minetest/minetest/bl ... ua_api.txt for the client-side API documentation. It's highly unlikely that you'll be able to simply convert a server-side mod to a client-side mod. Many of the things that you'd normally do in a server-side mod, such as adding new node types or changing game mechanics, are not applicable to client-side mods (as the server controls those aspects of the game) and impossible to do in a client-side mod, and client-side mods often focus on modifying the UI of the game rather than the game world itself (such as adding extra features via chat commands or with a GUI form).
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
That error I solved and now have an other error.
I have an question: How to check if an player is on the server and then check the file if it needs to be kicked and then that it kicked that player?
Please help me with that and make an code that I can use as an CSM
I have an question: How to check if an player is on the server and then check the file if it needs to be kicked and then that it kicked that player?
Please help me with that and make an code that I can use as an CSM
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
For kicking you will need to make the CSM send the same kick command that you would use if you were kicking the player manually (there is no minetest.kick_player function in the client-side API). minetest.run_server_chatcommand("kick", player_name) will probably work. If you want to include a reason, you can use minetest.run_server_chatcommand("kick", player_name .. " " .. reason). Obviously you will need to have the kick privilege on whatever server you want to use this on.Miniontoby wrote:I have an question: How to check if an player is on the server and then check the file if it needs to be kicked and then that it kicked that player?
I don't know how to check if a player is on the server but I know there is a client-side API function for it. I'm too lazy to look it up though because you can read the documentation that I linked to and find it yourself.
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
Thanks for that, micheal65536.
And for the player (because there is no "minetest.register_on_joinplayer") I need an solution
And for the player (because there is no "minetest.register_on_joinplayer") I need an solution
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
Please read the documentation that I have linked to, it provides a list of all the client-side API functions. There is an API function that will return a list of the players connected to the server. There is also an API function that lets you process incoming chat messages (including messages such as players joining/leaving and responses to chat commands), so you could also send the /status command to the server and extract the list of players from the response (the same information is normally also sent when you join the server). You could also monitor for player join/leave messages, although this will only tell you about players that have joined or left after you joined so you will need to use another approach for getting the initial list of players.Miniontoby wrote:And for the player (because there is no "minetest.register_on_joinplayer") I need an solution
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
But how exactly (please with code)
And my code need to kick players who join and need to be kicked (from the file information that did been created with the rest of the code and a chatcommand I already have done)
And my code need to kick players who join and need to be kicked (from the file information that did been created with the rest of the code and a chatcommand I already have done)
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
I will not write the code for you. I have directed you to the documentation that you need. Please read the documentation and figure out what code you need to write in order to do what you're trying to do. You cannot always rely on other people to write the code for you. You need to be able to read documentation and write the code yourself - it's not that hard to do, and that's all that I would be doing if I wrote the code for you. From your first post it sounds like you already know how to write simple code, so you should have no problem writing the code again as a client-side mod once you find the correct API functions to use.Miniontoby wrote:But how exactly (please with code)
One more time, here is the link to the client-side API documentation which lists all of the available API functions. Please look at the documentation and find the functions that you need to use (hint: you can search the documentation with keywords such as "player", "chat", or "message" using your web browser's "find" function to find functions that might be relevant). https://github.com/minetest/minetest/bl ... ua_api.txt
EDIT: I've already given you a hint in my previous post for a way that you can find out when players are joining the game.
Last edited by micheal65536 on Fri Nov 15, 2019 20:29, edited 1 time in total.
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
I amn't the best modder (I have only made the doorbell mod) and I don't know how to use /status in a CSM code
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
I've already told you how to use /kick from a client-side mod (minetest.run_server_chatcommand("kick", player_name)). From this you should be able to figure out how to run the /status command.Miniontoby wrote:I don't know how to use /status in a CSM code
If you want to watch for player join/leave messages (similar to minetest.register_on_joinplayer and minetest.register_on_leaveplayer) then you will need to use another client-side API function that will tell you every time a chat message is received and let you do something in response to it. You can also use the same API function to watch for the server's response after you send the /status command (if you decide to use that method, although from your description it sounds like you're more interested in doing something in response to a player joining the game). You can find the correct API function by going to the API documentation that I linked to and searching for the word "chat" or "message" (you can search for text on a page by using your browser's "find" option which can usually be accessed by pressing ctrl+f).
Once you are able to respond to incoming chat messages, you will need to find the correct messages to respond to and extract the relevant information from them. Lua provides a function that will let you see if text strings match an expected format (called a "pattern") and let you extract parts of them according to a particular format.
To get the name of a player that joins the server, you would use string.match(message, "^*** (%S*) joins the game$"). The ^ and $ symbols make sure that the entire message matches, not just a part somewhere in the middle. The %S* part means "this part can be anything that isn't a space", and the brackets around it mean "I want to get whatever text was in this part of the original string". Altogether this means "check that the entire string starts with '*** ', followed by anything that isn't a space, followed by ' joins the game', and tell me what actual text was in the part after the asterisks". If you pass each chat message to this function, you'll either get the name of the player that joined the game or nil (which means that the chat message isn't a player join message). (You can find more information about patterns in Lua here: https://www.lua.org/manual/5.3/manual.html#6.4.1.)
Getting the list of players from the server status message (which is received directly after joining the game and after running the /status command) is a bit more complicated. For this, you would use the pattern ^# Server: .*clients={([^}]*)}. The ^ symbol means "match from the beginning of the string, don't start somewhere in the middle". Following this is the text # Server: which will always appear at the start of the server status message. After this, .* means "this part can be anything, I don't care what characters there are or how many of them there are". In this case, that means "the next part should appear somewhere in the string but I don't care where". Then there's the text clients={ which indicates the start of the list of player names. Then [^}]* means "this part is anything except a } character" (because the } marks the end of the list). As with the previous example, this part is surrounded by brackets so we'll be given whatever text was in here. Finally there's the closing } symbol to mark the end of the list. We don't care what (if anything) comes after the list of player names so we can end the pattern here. Altogether this means "check that the string starts with '# Server: ', then find the list of player names starting with 'clients={' somewhere inside the string, and tell me what's between the opening and closing curly bracket". As before, you'll either get the list of player names or you'll get a nil value meaning that the chat message isn't the server status message.
However, once you have the list of players from the server status message you'll still need to split it into a list of individual names (right now it's just a single string with all the names separated by commas). To do this, you can use another Lua function called string.gmatch. This function also takes a pattern but instead of checking once if the string matches the pattern and then giving you some part of it it will let you use a pattern to split a string into multiple sections. It's used in a for loop and on the first iteration of the loop it will give you the first part of the string that matches the pattern, then on the next iteration it will give you the next matching part, and so on until there's nothing left. To split the list of players, you would use
Code: Select all
for player in string.gmatch(list, "[^, ][^, ]*") do
-- do something with the player's name here
end
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
Can you please put that in a good working csm code for me (also because I cant make it working and I don't know everything about csm's and that lua_api file I also don't know how to use the commands)
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
Do you have any code so far? If you post your code so far I can help you figure out why it isn't working.Miniontoby wrote:Can you please put that in a good working csm code for me (also because I cant make it working and I don't know everything about csm's and that lua_api file I also don't know how to use the commands)
I have given you all the building blocks to make your CSM. Even if you have limited programming knowledge, you should be able to put them together from the information that I've given you.
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
I don't know how to make a one really, but this is what is tried (with the rest of the code)
Code: Select all
print("Load 'kick2' CSM [kick2]")
print("")
minetest.register_chatcommand("kick2", {
params = "<playername> | <playername> <reason>",
privs = {
kick = true,
},
func = function(name, param)
local can_kick = minetest.check_player_privs(name, {kick=true})
if can_kick then
if string.find(param, "^[^ ]+%s+.+") then
player_name, reason = string.match(param, "^([^ ]+)%s+(.+)")
minetest.run_server_chatcommand("kick", player_name .. " " .. reason)
t = io.open(minetest.get_worldpath().."/" .. player_name .. "_players.txt", "w")
t:write("true")
else
player_name = param
reason = ""
minetest.run_server_chatcommand("kick", player_name)
t = io.open(minetest.get_worldpath().."/" .. player_name .. "_players.txt", "w")
t:write("true")
end
else
minetest.log("info", name .. " don't have the kick priv")
end
end,
})
minetest.register_chatcommand("unkick2", {
params = "<playername>",
privs = {
kick = true,
},
func = function(name, param)
local can_kick = minetest.check_player_privs(name, {kick=true})
if can_kick then
t = io.open(minetest.get_worldpath().."/" .. param .. "_players.txt", "w")
t:write("false")
else
minetest.log("info", "You don't have the kick priv")
end
end,
})
minetest.register_on_receiving_chat_message(function(message)
if string.find(message, "^*** (%S*) joined the game$") then
player_name = string.match(message, "^*** (%S*) joined the game$")
local p = io.open(minetest.get_worldpath().."/" .. player_name .. "_players.txt", "r")
if p ~= nil then
local kick_message = p:read("*line")
p:close()
if kick_message ~= nil then
if kick_message == "true" then
minetest.run_server_chatcommand("kick", player_name)
end
end
end
end
end)
-
- Member
- Posts: 167
- Joined: Mon May 22, 2017 20:27
Re: Help with csm needed
Thanks for posting the code. There are a few things that I can comment on here.
You don't need this and it is more likely to cause confusion. Minetest already lists each CSM in the terminal/console as it's loaded.
Take out the privs section. It doesn't apply to client-side mods and will be ignored. Remember, privileges are a server-side thing.
In client-side mods, there's no name parameter to the command handler function because the command will always be run by yourself. You should only have the param parameter in your function definition.
This is probably unnecessary because running the command without the required server-side privileges won't do anything anyway (because the server won't allow it) but the equivalent client-side API function is minetest.get_privilege_list(), which will return a table listing your own privileges. You would use it like this: local can_kick = minetest.get_privilege_list().kick. (In the case of removing players from the list, I would strongly recommend skipping the privilege check because you're only removing someone that you've already added yourself and you might want to do this even if you don't have kick privileges for some reason.)
You should probably use minetest.display_chat_message("You don't have the kick priv") instead. That will show the message in your chat (but only for you, it won't send it to anyone else on the server). Also, you can't use name in the string because it isn't passed to the client-side command handler function (as previously explained).
There is no io.open function for client-side mods. There's also no minetest.get_worldpath() function because the world is stored on the server. The closest equivalent is minetest.get_mod_storage() however this won't give you per-world/per-server storage (so you could end up kicking the same player from a different server if you have kick privileges on multiple servers - although I do wonder if there's any particular reason why you need to save the list after you leave and re-join the game and if you can't just re-add a player to the list if you see them again later (note in particular that this code won't automatically kick the player if they're already in the game when you join, only if they join after you)). This is a bit of a difficult API function to use because you have to call it at load-time rather than at run-time (you can't call it from your command handler function), and the correct way to use this would be to add the line local storage = minetest.get_mod_storage() at the top of your code and then later you'll useto add the player to the kick list,to remove the player from the list (using an empty string deletes the value entirely which is better than leaving a "false" value in storage), andto kick the player when they later join the game (note that storage:get_string will return an empty string, not nil, if the value is unset or has been deleted).
If you make these changes and then post the code again I can check if there are any other issues.
Code: Select all
print("Load 'kick2' CSM [kick2]")
print("")
Code: Select all
minetest.register_chatcommand("kick2", {
params = "<playername> | <playername> <reason>",
privs = {
kick = true,
},
Code: Select all
minetest.register_chatcommand("unkick2", {
params = "<playername>",
privs = {
kick = true,
},
Code: Select all
func = function(name, param)
Code: Select all
local can_kick = minetest.check_player_privs(name, {kick=true})
Code: Select all
minetest.log("info", name .. " don't have the kick priv")
Code: Select all
t = io.open(minetest.get_worldpath().."/" .. player_name .. "_players.txt", "w")
t:write("true")
Code: Select all
t = io.open(minetest.get_worldpath().."/" .. param .. "_players.txt", "w")
t:write("false")
Code: Select all
local p = io.open(minetest.get_worldpath().."/" .. player_name .. "_players.txt", "r")
if p ~= nil then
local kick_message = p:read("*line")
p:close()
if kick_message ~= nil then
if kick_message == "true" then
minetest.run_server_chatcommand("kick", player_name)
end
end
end
Code: Select all
storage:set_string("kick_" .. player_name, "true")
storage:set_string("reason_" .. player_name, reason)
Code: Select all
storage:set_string("kick_" .. param, "")
storage:set_string("reason_" .. param, "")
Code: Select all
if storage:get_string("kick_" .. player_name) == "true" then
local reason = storage:get_string("reason_" .. player_name)
if reason ~= "" then
minetest.run_server_chatcommand("kick", player_name .. " " .. reason)
else
minetest.run_server_chatcommand("kick", player_name)
end
end
If you make these changes and then post the code again I can check if there are any other issues.
- Miniontoby
- Member
- Posts: 616
- Joined: Fri Mar 01, 2019 19:25
- GitHub: Miniontoby
- IRC: Miniontoby
- In-game: Miniontoby
- Location: The Netherlands
Re: Help with csm needed
Thank you for this help
But the reason don't needed to posted everytime ;)
And I add the server info for the kicking a player on a specific server and not kicking at an other server
I have made changes and this is my code now:
And I did try to test it but it doesn't got loaded
I runned a server from the commandline, I joined it and mod doesn't got loaded (and I have put the client-side-modding on) so that is also an problem
But the reason don't needed to posted everytime ;)
And I add the server info for the kicking a player on a specific server and not kicking at an other server
I have made changes and this is my code now:
Code: Select all
local storage = minetest.get_mod_storage()
local server_info = minetest.get_server_info()
local server_id = server_info.address .. ':' .. server_info.port
minetest.register_chatcommand("kick2", {
params = "<playername> | <playername> <reason>",
func = function(name, param)
if string.find(param, "^[^ ]+%s+.+") then
player_name, reason = string.match(param, "^([^ ]+)%s+(.+)")
minetest.run_server_chatcommand("kick", player_name .. " " .. reason)
storage:set_string(server_id .. "kick_" .. player_name, "true")
else
player_name = param
minetest.run_server_chatcommand("kick", player_name)
storage:set_string(server_id .. "kick_" .. player_name, "true")
end
end,
})
minetest.register_chatcommand("unkick2", {
params = "<playername>",
privs = {
kick = true,
},
func = function(name, param)
storage:set_string(server_id .. "kick_" .. param, "")
end,
})
minetest.register_on_receiving_chat_message(function(message)
if string.find(message, "^*** (%S*) joined the game$") then
player_name = string.match(message, "^*** (%S*) joined the game$")
if storage:get_string(server_id .. "kick_" .. player_name) == "true" then
minetest.run_server_chatcommand("kick", player_name)
end
end
end)
I runned a server from the commandline, I joined it and mod doesn't got loaded (and I have put the client-side-modding on) so that is also an problem
Who is online
Users browsing this forum: No registered users and 4 guests