Pet Module won't work

Hello. I am creating a pet module, but, whenever I test, it errors from the script that I require ‘attempt to call a nil value’. Here is my code:

local Pet = {}
Pet.__index = Pet

function Pet.new(petName, petModel, playerFor)
	Pet = {Name = petName, Model = petModel, Owner = playerFor}
	return setmetatable({}, Pet);
end;

function Pet:Load()
	local clone = self.Model:Clone();
	clone.Name = self.Name;
	clone.Parent = self.Owner.Character;
end;

return Pet

I do from another script:

local pet = petsModule.new("Dragon", script.Pet, player)
pet:Load()

Could you post the entire server script?

Sure:

local petsModule = require(game:GetService("ServerScriptService").Pets);

function player_Added(player)
	local pet = petsModule.new("Dragon", script.Pet, player)
	pet:Load()
end;

game:GetService("Players").PlayerAdded:Connect(player_Added)
-- I know this is short, I am just practicing OOP.

Is there actually a model in the ServerScript (script.Pet)?

What line does it say the error is on?

Just to mention it errors in the line where it says

pet:Load()

And not in:

local pet = petsModule.new("Dragon", script.Pet, player)

Edit: Yes, there is.

I’m not really super experienced with metatables. However, it could possibly be that Pet is overwritten in the function Pet.new(), as a table: {Name = petName...}. Could it be overwriting all the pre-defined functions? Try re-writing it as:

local Pet = {}
Pet.__index = Pet

function Pet.new(petName, petModel, playerFor)
	local NewPet = {Name = petName, Model = petModel, Owner = playerFor}
	
	function NewPet:Load()
		local clone = self.Model:Clone();
		clone.Name = self.Name;
		clone.Parent = self.Owner.Character;
	end;
	
	return setmetatable({}, NewPet);
end;

I think it’s an issue with your metatable usage. Try this instead.

local Pet = {}
Pet.__index = Pet

function Pet.new(petName, petModel, playerFor)
	local NewPet = {Name = petName, Model = petModel, Owner = playerFor}
        setmetatable(NewPet, Pet)
	return NewPet
end;

function Pet:Load()
	local clone = self.Model:Clone();
	clone.Name = self.Name;
	clone.Parent = self.Owner.Character;
end;

return Pet

Why would you include one of the class functions inside the constructor? This would be inefficient. The use of metatables in OOP is to make creating classes possible without having to do this

Like I said, I am not experienced at all in metatables. What could I do better in that bit?

Did that but it still doesn’t work.

Is there anything new in the output?

p.s. Galactiq feel free to dm me and I’ll help you out, I don’t want to get off topic in this thread

Edit: Nevermind, it works! Thank you so much.
Thank you also @Galactiq for trying to help! :pray:

If there’s nothing in the output it may just be the pet model because I see no space for logic errors… here’s a less sugared approach just in case:


local Pet = {}
Pet.__index = Pet

function Pet.new(petName, petModel, playerFor)
	local NewPet = {};
	NewPet.Name = petName
	NewPet.Model = petModel
	NewPet.Owner = playerFor
        setmetatable(NewPet, Pet)
	return NewPet
end;

function Pet:Load()
	local clone = self.Model:Clone();
	clone.Name = self.Name;
	clone.Parent = self.Owner.Character;
end;

return Pet

Edit: Maybe send the place file if you don’t mind?

You were right, it did work. I put a print there and it worked. It was just an issue with the pet cloning. Thank you :pray:

1 Like