【问题标题】:Error: Could not find action or result No result defined for action action.Part and result {"col1":"col1","col2":"col2"}错误:找不到操作或结果没有为操作操作定义结果。部分和结果 {"col1":"col1","col2":"col2"}
【发布时间】:2013-06-10 05:45:04
【问题描述】:

我没有收到来自服务器的 JSON 类型数据的响应。

我正在使用 JSON 插件。

jQuery( "#dialog-form" ).dialog({ 
    autoOpen: false,
    height: 500,
    width: 750,
    modal: true,
    buttons :{
        "Search" : function(){
            jQuery.ajax({type : 'POST',
            dataType : 'json',
             url : '<s:url action="part" method="finder" />',
         success : handledata})
        }
    }
});
var handledata = function(data)
{
    alert(data);
}

如果dataType = 'json' 我没有收到任何回复,但如果我没有提及任何dataType,我将获得页面的 HTML 格式。

public String list(){
    JSONObject jo = new JSONObject();
    try {
        Iterator it = findList.iterator();
        while(it.hasNext()){
             SearchResult part = (SearchResult) it.next();
             jo.put("col1",part.getcol1());
             jo.put("col2",part.getcol2());
        }
        log.debug("--------->:"+jo.toString());
    } catch (Exception e) {
        log.error(e);
    }
    return jo.toString();
}

struts.xml:

<package name="default" namespace="/ajax" extends="json-default">
  <action name="finder" 
       class="action.Part" method="finder" name="finder">
       <result type="json" />
  </action>
</package>

JSP 页面:

<div id="dialog-form" >
    <form action="" id="channelfinder">
        <textarea id="products" name="prodnbr"<s:property value='prodNbr'/>   
    </form>
</div>

控制台错误:

org.apache.struts2.dispatcher.Dispatcher - 找不到操作或结果 没有为动作 action.Part 定义结果 结果 {"col1":"col1","col2":"col2"}

web.xml:

    <?xml version="1.0" encoding="ISO-8859-1"?>
     <web-app version="2.4" xmlns="http://java.sun.com/xml/ns/j2ee"      xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
            xsi:schemaLocation="http://java.sun.com/xml/ns/j2ee/web-app_2_4.xsd">
      <display-name>/parts</display-name>
      <description>Parts List Web App</description>

    <filter>
          <filter-name>struts-cleanup</filter-name>
          <filter-class>org.apache.struts2.dispatcher.ActionContextCleanUp</filter-class>
        </filter>

        <filter>
        <filter-name>sitemesh</filter-name>
        <filter-class>com.opensymphony.module.sitemesh.filter.PageFilter</filter-class>
        </filter>

       <filter>
        <filter-name>struts2</filter-name>
        <filter-class>org.apache.struts2.dispatcher.ng.filter.StrutsPrepareAndExecuteFilter</filter-class>
        <init-param>
            <param-name>actionPackages</param-name>
            <param-value>com.action</param-value>
        </init-param>
    </filter>


    <filter-mapping>
        <filter-name>struts-cleanup</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>

    <filter-mapping>
        <filter-name>sitemesh</filter-name>
        <url-pattern>/*</url-pattern>
        <dispatcher>REQUEST</dispatcher>
        <dispatcher>FORWARD</dispatcher>
        <dispatcher>INCLUDE</dispatcher>
    </filter-mapping>

    <filter-mapping>
        <filter-name>struts2</filter-name>
        <url-pattern>/*</url-pattern>
    </filter-mapping>
    <error-page>
        <exception-type>java.lang.Throwable</exception-type>
        <location>/errorPage.jsp</location>
    </error-page>
    <error-page>
        <error-code>404</error-code>
        <location>/errorPage.jsp</location>
    </error-page>

  <!-- Spring -->
  <context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>/WEB-INF/applicationContext.xml</param-value>
  </context-param>
  <listener>
    <listener-class>org.springframework.web.context.ContextLoaderListener</listener-class>
  </listener>

  </web-app>

我没有获取 jQuery 成功的数据。 请纠正我,这里有什么问题?

【问题讨论】:

  • 请立即查看问题。
  • 已更新问题。还是不行……
  • 您不应该返回 json 字符串,无论是 ruturn void 还是返回 SUCESS。当您返回 json 字符串时,您会遇到控制台错误
  • 请注意,您的 textarea 会自行关闭,然后再次关闭 :)
  • 尝试使用 GET 而不是 POST

标签: java jquery ajax json struts2


【解决方案1】:

关于 Struts2-JSON 插件

Struts2 JSON Plugin 以特定方式工作:

JSON 插件提供“json”结果类型,将动作序列化为 JSON。

它将整个 Action序列化为 JSON,除了

  • 瞬态属性
  • 没有 Getter 的属性

如果您不想序列化整个 Action,而只希望您选择一个对象,则可以指定一个 Root Object:

使用“root”属性(OGNL表达式)指定要序列化的根对象。

可以像这样在struts.xml 中完成:

<result type="json">
    <param name="root">
        objectToBeSerialized
    </param>
</result>

虽然动作应该有:

private CustomObject objectToBeSerialized;

public CustomObject getObjectToBeSerialized(){
    return this.objectToBeSerialized;
}

CustomObject 可以是 Primitive、String、Array 等...

以这种方式使用它(它的构建方式),您可以像在任何其他 AJAX Struts2 Action 中一样返回SUCCESSERROR,而不会破坏框架约定,并从回调函数访问序列化的 JSON 对象像任何其他字段一样的 AJAX jQuery 调用(如果使用 rootObject,var handledata = function(data) 的“数据”将是您的对象,否则它将是您的操作)。


关于您的具体情况

在您的情况下,假设您的对象结构如下所示

row1 [col1, col2], 
row2 [col1, col2], 
rowN [col1, col2]

您可以创建一个包含两列的对象列表:

值对象

public class MyRow implements Serializable {
    private static final long serialVersionUID = 1L;

    private String col1; 
    private String col2;

    // Getters
    public String getCol1(){ 
        return this.col1; 
    }
    public String getCol2(){ 
        return this.col2; 
    }
}

动作类

public class PartAction implements Serializable {
    private static final long serialVersionUID = 1L;
    
    private List<MyRow> rows;   

    // Getter
    public  List<MyRow> getRows() { 
        return this.rows; 
    } 

    public String finder() {
        String result = Action.SUCCESS;
        rows = new ArrayList<MyRow>();

        try {
            Iterator it = findList.iterator();
            while(it.hasNext()) {
                SearchResult part = (SearchResult) it.next();
                MyRow row = new MyRow();
                row.setCol1(part.getcol1());
                row.setCol2(part.getcol2());
                rows.add(row);
            }
        } catch (Exception e) {
            result = Action.ERROR;
            log.error(e);
        }
        return result;
    }  
} 

Struts.xml

<package name="default" namespace="/ajax" extends="json-default">
    <action name="finder" class="action.Part" method="finder" name="finder">
        <result type="json" >
            <param name="root">
                rows
            </param>
        </result>
  </action>
</package>

要在 AJAX 回调函数中测试它,只需使用 $.each

var handledata = function(data) {
    $.each(data, function(index) {
        alert(data[index].col1);
        alert(data[index].col2);
    });     
}

当然,您可以使用 List&lt;List&lt;String&gt;&gt; 代替自定义对象,或者您更喜欢的任何其他对象结构:这只是为了让您了解。

【讨论】:

    【解决方案2】:

    jQuery Ajax 使用dataType : 'json' 指定在执行操作和结果时应由success 回调函数返回的数据类型,以及从服务器返回的响应。

    dataType(默认:智能猜测(xmljsonscript,或html))

    输入:String

    您期望从服务器返回的数据类型。如果没有指定,jQuery 将尝试根据响应的 MIME 类型推断它(XML MIME 类型将产生 XML,在 1.4 中 JSON 将产生一个 JavaScript 对象,在 1.4 中脚本将执行脚本,其他任何东西都会以字符串形式返回)。

    网址应正确指向操作映射。假设它将在默认命名空间中,否则您应该修改 URL 和映射以添加 namespace attribute。

    <script type="text/javascript">
      $(function() {
        $("#dialog-form").dialog ({
          autoOpen: true,
          height: 500,
          width: 750,
          modal: true,
          buttons : {
            "Search" : function() {
              $.ajax({
                url : '<s:url action="part" />',
                success : function(data) {
                  //var obj = $.parseJSON(data);
                  var obj = data;
                  alert(JSON.stringify(obj));
                }
              });
            }
          }
        });
      });
    </script>
    

    如果您手动构建JSONObject,则不需要返回json 结果类型。您可以将文本返回为stream result,然后根据需要将字符串转换为 JSON。

    struts.xml:

    <package name="default" extends="struts-default">
      <action name="part" class="action.PartAction" method="finder">    
        <result type="stream">
          <param name="contentType">text/html</param>
          <param name="inputName">stream</param>
        </result>
      </action>
    </package>
    

    行动:

    public class PartAction extends ActionSupport {
    
      public class SearchResult {
        private String col1;
        private String col2;
    
        public String getCol1() {
          return col1;
        }
    
        public void setCol1(String col1) {
          this.col1 = col1;
        }
    
        public String getCol2() {
          return col2;
        }
    
        public void setCol2(String col2) {
          this.col2 = col2;
        }
    
        public SearchResult(String col1, String col2) {
          this.col1 = col1;
          this.col2 = col2;
        }
      }
    
      private InputStream stream;
    
      //getter here
      public InputStream getStream() {
        return stream;
      }
    
      private List<SearchResult> findList = new ArrayList<>();
    
      public List<SearchResult> getFindList() {
        return findList;
      }
    
      public void setFindList(List<SearchResult> findList) {
        this.findList = findList;
      }
    
      private String list() {
        JSONObject jo = new JSONObject();
        try {
          for (SearchResult part : findList) {
            jo.put("col1", part.getCol1());
            jo.put("col2", part.getCol2());
          }
          System.out.println("--------->:"+jo.toString());
        } catch (Exception e) {
          e.printStackTrace();
          System.out.println(e.getMessage());
        }
        return jo.toString();
      }
    
      @Action(value="part", results = {
        @Result(name="stream", type="stream", params = {"contentType", "text/html", "inputName", "stream"}),
        @Result(name="stream2", type="stream", params = {"contentType", "application/json", "inputName", "stream"}),
        @Result(name="json", type="json", params={"root", "findList"})
      })
      public String finder() {
        findList.add(new SearchResult("val1", "val2"));
        stream = new ByteArrayInputStream(list().getBytes());
        return "stream2";
      }
    }
    

    我已经使用结果类型和内容类型放置了不同的结果,以更好地描述这个想法。您可以返回这些结果中的任何一个,并返回字符串化或未字符串化的 JSON 对象。字符串化版本需要解析返回的数据以获取 JSON 对象。您还可以选择更好地序列化哪种结果类型以满足您的需求,但我的目标是表明,如果您需要序列化简单对象,则不需要 json 插件即可使其正常工作。

    参考资料:

    【讨论】:

    • 那么,将 jsonarray 转换为明文?如果从 jsonarray 转换为 jsonobject,可以吗?
    • 您是否已经在操作中获得了 json 字符串?然后你就可以把它作为成功函数的数据。
    • 公共字符串列表() { JSONObject jo = new JSONObject();字符串部分;部分 = 构建(); jo.put("数组",jo); return jo.toString();} - 仍然无法正常工作。
    • 你没有建立一个有效的 jo。试试这个 myString = new JSONObject().put("JSON", "Hello, World!").toString();
    • 非常感谢您的努力。无论来自动作类的数据是什么,我都需要使用数据表来显示。这就是我试图通过 ajax 放入数组或 JSON 数据的原因。但是这些文本格式的数据也可以用于数据表吗?
    猜你喜欢
    • 2014-09-21
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-03-03
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2012-09-21
    相关资源
    最近更新 更多