javascript - 未捕获的类型错误 : Cannot read property of 'send' undefined

标签 javascript java websocket socketserver typeerror

我试图以 json 的形式向我的 websocket 发送消息,但是当我运行 web 应用程序时,我在开发人员控制台中收到了这个错误。我知道当找不到元素时会发生此错误。但是,“发送”不是 websocket 的默认成员吗?怎么会找不到呢?错误发生在我的最后一行代码。我的.js文件的代码如下:

// to keep the session id
var sessionId = '';

// name of the client
var name = '';


$(document).ready(function() {

    $("#form_submit, #form_send_message").submit(function(e) {
        e.preventDefault();
        join();
    });
});

var webSocket;

/**
 * Connecting to socket
 */
function join() {
    // Checking person name
    if ($('#input_name').val().trim().length <= 0) {
        alert('Enter your name');
    } else {
        name = $('#input_name').val().trim();

        $('#prompt_name_container').fadeOut(1000, function() {
            // opening socket connection
            openSocket();
        });
    }

    return false;
}

/**
 * Will open the socket connection
 */
function openSocket() {
    // Ensures only one connection is open at a time
    if (webSocket !== undefined && webSocket.readyState !== WebSocket.CLOSED) {
        return;
    }

    var wsUrl;
    if (window.location.protocol == 'http:') {
        wsUrl = 'ws://' + window.location.host + ':8000/chat'+'?name='+name;
    } else {
        wsUrl = 'wss://' + window.location.host + ':8443/chat'+'?name='+name;
    }
    console.log('WebSockets Url : ' + wsUrl);
    var webSocket = new WebSocket(wsUrl);

    // Create a new instance of the websocket
    //webSocket = new WebSocket("ws://jbosslew-weihao.rhcloud.com:8000/" );

    /**
     * Binds functions to the listeners for the websocket.
     */
    webSocket.onopen = function(event) {
        $('#message_container').fadeIn();

        if (event.data === undefined)
            return;

    };

    webSocket.onmessage = function(event) {

        // parsing the json data
        parseMessage(event.data);
    };

    webSocket.onclose = function(event) {

    };
}

/**
 * Sending the chat message to server
 */
function send() {
    var message = $('#input_message').val();

    if (message.trim().length > 0) {
        sendMessageToServer('message', message);
    } else {
        alert('Please enter message to send!');
    }

}

/**
 * Closing the socket connection
 */
function closeSocket() {
    webSocket.close();

    $('#message_container').fadeOut(600, function() {
        $('#prompt_name_container').fadeIn();
        // clearing the name and session id
        sessionId = '';
        name = '';

        // clear the ul li messages
        $('#messages').html('');
        $('p.online_count').hide();
    });
}

/**
 * Parsing the json message. The type of message is identified by 'flag' node
 * value flag can be self, new, message, exit
 */
function parseMessage(message) {

    var jObj = $.parseJSON(message);

    // if the flag is 'self' message contains the session id
    if (jObj.flag == 'self') {

        sessionId = jObj.sessionId;

    } else if (jObj.flag == 'new') {
        // if the flag is 'new', a client joined the chat room
        var new_name = 'You';

        // number of people online
        var online_count = jObj.onlineCount;

        $('p.online_count').html(
                'Hello, <span class="green">' + name + '</span>. <b>'
                        + online_count + '</b> people online right now')
                .fadeIn();

        if (jObj.sessionId != sessionId) {
            new_name = jObj.name;
        }

        var li = '<li class="new"><span class="name">' + new_name + '</span> '
                + jObj.message + '</li>';
        $('#messages').append(li);

        $('#input_message').val('');

    } else if (jObj.flag == 'message') {
        // if the json flag is 'message', it means somebody sent the chat
        // message

        var from_name = 'You';

        if (jObj.sessionId != sessionId) {
            from_name = jObj.name;
        }

        var li = '<li><span class="name">' + from_name + '</span> '
                + jObj.message + '</li>';

        // appending the chat message to list
        appendChatMessage(li);

        $('#input_message').val('');

    } else if (jObj.flag == 'exit') {
        // if the json flag is 'exit', it means somebody left the chat room
        var li = '<li class="exit"><span class="name red">' + jObj.name
                + '</span> ' + jObj.message + '</li>';

        var online_count = jObj.onlineCount;

        $('p.online_count').html(
                'Hello, <span class="green">' + name + '</span>. <b>'
                        + online_count + '</b> people online right now');

        appendChatMessage(li);
    }
}

/**
 * Appending the chat message to list
 */
function appendChatMessage(li) {
    $('#messages').append(li);

    // scrolling the list to bottom so that new message will be visible
    $('#messages').scrollTop($('#messages').height());
}

/**
 * Sending message to socket server message will be in json format
 */
function sendMessageToServer(flag, message) {
    var json = '{""}';

    // preparing json object
    var myObject = new Object();
    myObject.sessionId = sessionId;
    myObject.message = message;
    myObject.flag = flag;

    // converting json object to json string
    json = JSON.stringify(myObject);

    // sending message to server
    webSocket.send(json); // Uncaught type error occurs here
}

如果它也相关,我的服务器套接字的java代码如下:

package info.androidhive.webmobilegroupchat;

import java.io.IOException;
import java.io.UnsupportedEncodingException;
import java.net.URLDecoder;
import java.util.Collections;
import java.util.HashMap;
import java.util.HashSet;
import java.util.Map;
import java.util.Set;

import javax.websocket.OnClose;
import javax.websocket.OnMessage;
import javax.websocket.OnOpen;
import javax.websocket.Session;
import javax.websocket.server.ServerEndpoint;

import org.json.JSONException;
import org.json.JSONObject;

import com.google.common.collect.Maps;

@ServerEndpoint("/chat")
public class SocketServer {

    // set to store all the live sessions
    private static final Set<Session> sessions = Collections
            .synchronizedSet(new HashSet<Session>());

    // Mapping between session and person name
    private static final HashMap<String, String> nameSessionPair = new HashMap<String, String>();

    private JSONUtils jsonUtils = new JSONUtils();

    // Getting query params
    public static Map<String, String> getQueryMap(String query) {
        Map<String, String> map = Maps.newHashMap();
        if (query != null) {
            String[] params = query.split("&");
            for (String param : params) {
                String[] nameval = param.split("=");
                map.put(nameval[0], nameval[1]);
            }
        }
        return map;
    }

    /**
     * Called when a socket connection opened
     * */
    @OnOpen
    public void onOpen(Session session) {

        System.out.println(session.getId() + " has opened a connection");

        Map<String, String> queryParams = getQueryMap(session.getQueryString());

        String name = "";

        if (queryParams.containsKey("name")) {

            // Getting client name via query param
            name = queryParams.get("name");
            try {
                name = URLDecoder.decode(name, "UTF-8");
            } catch (UnsupportedEncodingException e) {
                e.printStackTrace();
            }

            // Mapping client name and session id
            nameSessionPair.put(session.getId(), name);
        }

        // Adding session to session list
        sessions.add(session);

        try {
            // Sending session id to the client that just connected
            session.getBasicRemote().sendText(
                    jsonUtils.getClientDetailsJson(session.getId(),
                            "Your session details"));
        } catch (IOException e) {
            e.printStackTrace();
        }

        // Notifying all the clients about new person joined
        sendMessageToAll(session.getId(), name, " joined conversation!", true,
                false);

    }

    /**
     * method called when new message received from any client
     * 
     * @param message
     *            JSON message from client
     * */
    @OnMessage
    public void onMessage(String message, Session session) {

        System.out.println("Message from " + session.getId() + ": " + message);

        String msg = null;

        // Parsing the json and getting message
        try {
            JSONObject jObj = new JSONObject(message);
            msg = jObj.getString("message");
        } catch (JSONException e) {
            e.printStackTrace();
        }

        // Sending the message to all clients
        sendMessageToAll(session.getId(), nameSessionPair.get(session.getId()),
                msg, false, false);
    }

    /**
     * Method called when a connection is closed
     * */
    @OnClose
    public void onClose(Session session) {

        System.out.println("Session " + session.getId() + " has ended");

        // Getting the client name that exited
        String name = nameSessionPair.get(session.getId());

        // removing the session from sessions list
        sessions.remove(session);

        // Notifying all the clients about person exit
        sendMessageToAll(session.getId(), name, " left conversation!", false,
                true);

    }

    /**
     * Method to send message to all clients
     * 
     * @param sessionId
     * @param message
     *            message to be sent to clients
     * @param isNewClient
     *            flag to identify that message is about new person 
     * @param isExit
     *            flag to identify that a person left the conversation
     * */
    private void sendMessageToAll(String sessionId, String name,
            String message, boolean isNewClient, boolean isExit) {

        // Looping through all the sessions and sending the message individually
        for (Session s : sessions) {
            String json = null;

            // Checking if the message is about new client joined
            if (isNewClient) {
                json = jsonUtils.getNewClientJson(sessionId, name, message,
                        sessions.size());

            } else if (isExit) {
                // Checking if the person left the conversation
                json = jsonUtils.getClientExitJson(sessionId, name, message,
                        sessions.size());
            } else {
                // Normal chat conversation message
                json = jsonUtils
                        .getSendAllMessageJson(sessionId, name, message);
            }

            try {
                System.out.println("Sending Message To: " + sessionId + ", "
                        + json);

                s.getBasicRemote().sendText(json);
            } catch (IOException e) {
                System.out.println("error in sending. " + s.getId() + ", "
                        + e.getMessage());
                e.printStackTrace();
            }
        }
    }
}

最佳答案

根据 Tiny Giant 的说法,我不小心重新声明了我的变量 webSocket,而不是使用它的全局版本,导致我的 webSocket 当时未定义。

关于javascript - 未捕获的类型错误 : Cannot read property of 'send' undefined,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/34734400/

相关文章:

javascript - 根据父元素属性更改元素的 CSS 属性

javascript - 为什么在扩展 Ember.Object 时省略了 var 语句?

java - 在 JavaFX 中使用 onMouseEntered 事件重新填充 SVG 路径

html - 移动网络应用程序的推送通知工具

python - 高速公路网络套接字

node.js - 发送 200 个响应 header 后 http 请求失败的方法

javascript - 将本地存储中的元素添加到 html 下拉菜单的建议

javascript - 执行与正则表达式拆分相反的操作

java - 访问父类(super class)构造函数中的局部变量

java - Wicket 如何向 AjaxEditableLabel 添加双输入验证