Why does my NPC go to a different place I wanted?

I am trying to get my NPC to go to the locations indicated for him.Unfortunately he goes to location 2 before he has even completed location 1.

NPC walk script
local MovePoint1 = game.Workspace.MovePoints.Part1
local MovePoint2 = game.Workspace.MovePoints.Part2
local NPC = script.Parent

wait(3)
NPC.Humanoid:MoveTo(MovePoint1.Position)
NPC.Humanoid.MoveToFinished:Wait()
NPC.Humanoid:MoveTo(MovePoint2.Position)
NPC.Humanoid.MoveToFinished:Wait()

Screen Recording.mp4

The output shows no error.I tried to add wait() manually, but it also didn’t work
Has anyone had a similar problem?

I actually have no idea, it could be a bug. Could you maybe try

NPC.Humanoid:MoveTo(MovePoint1.Position)
NPC.Humanoid.MoveToFinished:Wait()
task.wait(1.7) -- estimate
NPC.Humanoid:MoveTo(MovePoint2.Position)
NPC.Humanoid.MoveToFinished:Wait()

Ditto, also reckon it could be a bug.

I’d recommend using a Raycast to see when the BasePart is beneath the NPC and when their movement has stopped. Bit long winded but same result.

The issue might be the move to function stopping if the NPC hasn’t gotten to the destination after 8 seconds. Here is the documentation on it and a solution to the issue: Humanoid:MoveTo

Here is the solution to the issue on the page I linked above:

local function moveTo(humanoid, targetPoint, andThen)
	local targetReached = false
 
	-- listen for the humanoid reaching its target
	local connection
	connection = humanoid.MoveToFinished:Connect(function(reached)
		targetReached = true
		connection:Disconnect()
		connection = nil
		if andThen then
			andThen()
		end
	end)
 
	-- start walking
	humanoid:MoveTo(targetPoint)
 
	-- execute on a new thread so as to not yield function
	spawn(function()
		while not targetReached do
			-- does the humanoid still exist?
			if not (humanoid and humanoid.Parent) then
				break
			end
			-- has the target changed?
			if humanoid.WalkToPoint ~= targetPoint then
				break
			end
			-- refresh the timeout
			humanoid:MoveTo(targetPoint)
			wait(6)
		end
		
		-- disconnect the connection if it is still connected
		if connection then
			connection:Disconnect()
			connection = nil
		end
	end)
end

You might want to clean it up though.

If a humanoid takes more than 8 seconds to get to it’s target (set by :MoveTo), it’ll automatically fire .MoveToFinished passing false (it’ll normally pass true if it reached the goal) and cancel the :MoveTo because it’s possible the NPC might have gotten stuck. Of course, that’s not the case in your situation, it’s just that there’s a lot of distance to cover, all Roblox knows is it just took too much time to reach it’s destination. You can try changing your code to this:

local MovePoint1 = game.Workspace.MovePoints.Part1
local MovePoint2 = game.Workspace.MovePoints.Part2
local NPC = script.Parent

local function GoTo(Position)
    NPC.Humanoid:MoveTo(Position)
    local Reached = NPC.Humanoid.MoveToFinished:Wait()
    if not Reached then
        GoTo(Position)
    end
end

GoTo(MovePoint1.Position)
GoTo(MovePoint2.Position)

I’ve made a function to reduce code repetition. The function makes it so that the NPC re-tries the :MoveTo when it doesn’t reach the goal within 8 seconds.
[edited script because I realized there’s a simpler way]