我实际上是反应 - 还原的新手,所以我只需要一些帮助,试图理解我在这里犯的任何语法或逻辑错误......
基本上,我想显示从其他服务器获取的报告。函数'fetchNames'处理它,函数'fetchdownloadable'创建一个返回链接,允许通过身份验证并以pdf onClick下载报告。
所以我在控制台上调试了,我相信代码的执行顺序有问题...当我调试时...我注意到: 首先执行fetchnames以获取json数组中的所有报告数据... 然后为reports数组中的每个对象调用fetchDownloadable,并在SampleChild上返回'undefined'值... 然后使用未定义的值执行SampleChild ... 然后我们回来执行fetchDownloadable函数,该函数在控制台上打印链接值,并在reducer上调度操作,在reducer中返回'state'而不是'action.reports_uri'...
提前致谢!
SampleParent.js
12
SampleChild.js
import React, {Component} from 'react'
import { connect } from 'react-redux'
import { fetchNames, fetchDownloadable } from '../../actions/actions'
import SampleChild from '../ui/SampleChild'
class SampleParent extends Component {
constructor(props) {
super(props);
this.fetchDownloadLink = this.fetchDownloadLink.bind(this)
}
componentDidMount() {
const { dispatch } = this.props
dispatch(fetchNames())
}
fetchDownloadLink(uri){
this.props.dispatch(fetchDownloadable(uri))
}
render() {
return (<div><ul id="myUL">
{this.props.reports.map((report) => (
<li><SampleChild
key={report.id}
label={report.label}
uri={this.fetchDownloadLink("http://localhost:8080/sample"+report.uri+".pdf")}
/></li>))}
</ul></div>
)}
}
function mapStateToProps(state) {
const { reports } = state
return {
reports
}}
export default connect(mapStateToProps)(SampleParent)
Action.js
import React, { Component } from 'react'
export default class SampleChild extends Component {
render() {
const { key, label, uri } = this.props
return (
<div className="inside_SampleChild" id={label}>
{label}
<a href={uri}><img src="../images/pdf-file_128.png" height="25px" width="25px"></img></a>
</div>
)}}
Reducers.js
import C from '../constants'
import fetch from 'isomorphic-fetch'
export const fetchNames = value => dispatch => {
var obj = { method: 'GET', headers: { 'Authorization': 'Basic ***', 'Accept': 'application/json' },
'credentials': 'include'};
fetch('http://localhost:8080/samplelink', obj)
.then(response => {
if (response.status !== 200) {
throw Error(response.status);
}return response;})
.then((response) => response.json())
.then(resourceLookup => {
var arr = [];
var length = resourceLookup.resourceLookup.length;
for(var i = 0 ; i< length ; i++){
arr.push(resourceLookup.resourceLookup[i]);}
dispatch({
type: C.FETCH_LIST_REPORTS,
reports: arr})}).
catch(error => {
console.log("There was this error" + error);});}
export const fetchReportDownloadable = (uri) => dispatch => {
var obj = {
method: 'GET',
headers: {
'Authorization': 'Basic ***=',
'Accept': 'application/json'
},
'credentials': 'include'
};
fetch(uri, obj)
.then(response => {
if (response.status !== 200) {
throw Error(response.status);
}
return response ;
})
.then((response) => response)
.then(resourceLookup => {
console.log(`resourceLookup URL: ${resourceLookup.url}`)
dispatch({
type: C.FETCH_DOWNLOADABLE,
report_uri: resourceLookup.url
})
}).
catch(error => {
console.log("There was this error" + error);
});}
答案 0 :(得分:1)
我会尝试解释发生的事情。
首先,您遇到的第一个问题是您传递的错误值或uri
的未定义值:
<li>
<SampleChild key={report.id} label={report.label}
uri={this.fetchDownloadLink("http://localhost:8080/sample"+report.uri+".pdf")}
/>
</li>
这里uri
是一个函数,它在第一个渲染时触发,它调度fetchDownloadable(uri)
动作,但它不会返回任何值。因此uri
未定义。
其次,您的减速器中使用C.FETCH_REPORT_DOWNLOADABLE
常量。但是,您从不调度该类型的操作,操作将调度C.FETCHING_DOWNLOADABLE
。因此减速器没有做任何事情,所以状态不会改变。我的第二条评论是C.FETCH_LIST_REPORTS
,这对你来说无关紧要,所以我错了。
我要做的是从服务器端创建下载链接。使用报告对象将其发回。这样,您就不需要发送两个操作来列出您的报告。然后,我将在componentWillMount()
中发送我的操作,一旦完成获取数据,状态将会更改 - 如果您再次发送了正确的操作 - 并且您将使用在同一个对象中下载URL。
<强>更新强>
好的,我想我现在明白了。我要做的是将uri
作为字符串发送到SampleChild
,然后当它安装时,我将触发fetchDownloadable
函数。
<强> SampleParent 强>
import React, {Component} from 'react'
import { connect } from 'react-redux'
import { fetchNames, fetchReportDownloadable } from '../../actions/actions'
import SampleChild from '../ui/SampleChild'
class SampleParent extends Component {
constructor(props) {
super(props);
this.fetchDownloadLink = this.fetchDownloadLink.bind(this)
}
componentDidMount() {
const { dispatch } = this.props
dispatch(fetchNames())
}
fetchDownloadLink(uri){
this.props.dispatch(fetchReportDownloadable(uri))
}
render() {
return (<div><ul id="myUL">
{this.props.reports.map((report) => (
<li><SampleChild
key={report.id}
label={report.label}
uri={"http://localhost:8080/sample"+report.uri+".pdf"}
download={this.fetchDownloadLink}
/></li>))}
</ul></div>
)}
}
function mapStateToProps(state) {
const { reports } = state
return {
reports
}}
export default connect(mapStateToProps)(SampleParent)
<强> SampleChild 强>
import React, { Component } from 'react'
export default class SampleChild extends Component {
componentDidMount() {
this.props.download(this.props.uri);
}
render() {
const { key, label, uri } = this.props
return (
<div className="inside_SampleChild" id={label}>
{label}
<a href={uri}><img src="../images/pdf-file_128.png" height="25px" width="25px"></img></a>
</div>
)}}
现在应该发生的是,您将首先在SampleParent
中获取报告,然后将信息传递给SampleChild
。每当安装SampleChild
时,它都会触发fetchDownloadable
操作,该操作会在返回时下载发送给它的uri
。