这是其中的代码 actions.js
export function exportRecordToExcel(record) {
return ({fetch}) => ({
type: EXPORT_RECORD_TO_EXCEL,
payload: {
promise: fetch('/records/export', {
credentials: 'same-origin',
method: 'post',
headers: {'Content-Type': 'application/json'},
body: JSON.stringify(data)
}).then(function(response) {
return response;
})
}
});
}
返回的响应是一个.xlsx
文件。我希望用户能够将其保存为文件,但是什么也没有发生。我认为服务器返回的响应类型正确,因为在控制台中它说
Content-Disposition:attachment; filename="report.xlsx"
我想念的是什么?我应该在减速器中做什么?
浏览器技术当前不支持直接从Ajax请求下载文件。解决方法是添加一个隐藏的表单并将其提交到幕后,以使浏览器触发“保存”对话框。
我正在运行标准的Flux实现,因此不确定确切的Redux(Reducer)代码应该是什么,但是我刚刚为文件下载创建的工作流是这样的…
FileDownload
。该组件所做的全部工作就是呈现一个隐藏的表单,然后在内部componentDidMount
立即提交表单并将其称为onDownloadComplete
prop。Widget
下载按钮/图标(实际上很多…一个用于表中的每个项目)。Widget
具有相应的操作和存储文件。Widget
进口FileDownload
。Widget
有两种与下载相关的方法:handleDownload
和handleDownloadComplete
。Widget
商店有一个名为的属性downloadPath
。null
默认设置为。如果将其值设置为null
,则不会进行任何文件下载,并且该Widget
组件不会呈现该FileDownload
组件。Widget
将调用handleDownload
触发downloadFile
动作的方法。该downloadFile
操作不会发出Ajax请求。它将DOWNLOAD_FILE
事件分发给商店,并随事件一起发送downloadPath
文件下载。商店保存downloadPath
并发出更改事件。downloadPath
,Widget
将呈现FileDownload
传递必要的道具包括downloadPath
以及所述handleDownloadComplete
方法作为值onDownloadComplete
。FileDownload
被渲染和表单被提交method="GET"
(POST应太)和action={downloadPath}
,服务器的响应现在将触发浏览器的保存对话框目标下载文件(在IE 9/10测试,最新的Firefox和Chrome)。onDownloadComplete
/ handleDownloadComplete
。这将触发另一个调度DOWNLOAD_FILE
事件的动作。但是,这次downloadPath
设置为null
。商店将另存为downloadPath
,null
并发出更改事件。downloadPath
,FileDownload
因此不会渲染组件Widget
,因此世界是一个快乐的地方。Widget.js-仅部分代码
import FileDownload from './FileDownload';
export default class Widget extends Component {
constructor(props) {
super(props);
this.state = widgetStore.getState().toJS();
}
handleDownload(data) {
widgetActions.downloadFile(data);
}
handleDownloadComplete() {
widgetActions.downloadFile();
}
render() {
const downloadPath = this.state.downloadPath;
return (
// button/icon with click bound to this.handleDownload goes here
{downloadPath &&
<FileDownload
actionPath={downloadPath}
onDownloadComplete={this.handleDownloadComplete}
/>
}
);
}
widgetActions.js-仅部分代码
export function downloadFile(data) {
let downloadPath = null;
if (data) {
downloadPath = `${apiResource}/${data.fileName}`;
}
appDispatcher.dispatch({
actionType: actionTypes.DOWNLOAD_FILE,
downloadPath
});
}
widgetStore.js-仅部分代码
let store = Map({
downloadPath: null,
isLoading: false,
// other store properties
});
class WidgetStore extends Store {
constructor() {
super();
this.dispatchToken = appDispatcher.register(action => {
switch (action.actionType) {
case actionTypes.DOWNLOAD_FILE:
store = store.merge({
downloadPath: action.downloadPath,
isLoading: !!action.downloadPath
});
this.emitChange();
break;
FileDownload.js-
完整,功能齐全的代码,可供复制和粘贴
-带Babel 6.x的React 0.14.7 [“ es2015”,“ react”,“ stage-0”]
-表单必须display: none
是“隐藏的”形式“ className
是为了
import React, {Component, PropTypes} from 'react';
import ReactDOM from 'react-dom';
function getFormInputs() {
const {queryParams} = this.props;
if (queryParams === undefined) {
return null;
}
return Object.keys(queryParams).map((name, index) => {
return (
<input
key={index}
name={name}
type="hidden"
value={queryParams[name]}
/>
);
});
}
export default class FileDownload extends Component {
static propTypes = {
actionPath: PropTypes.string.isRequired,
method: PropTypes.string,
onDownloadComplete: PropTypes.func.isRequired,
queryParams: PropTypes.object
};
static defaultProps = {
method: 'GET'
};
componentDidMount() {
ReactDOM.findDOMNode(this).submit();
this.props.onDownloadComplete();
}
render() {
const {actionPath, method} = this.props;
return (
<form
action={actionPath}
className="hidden"
method={method}
>
{getFormInputs.call(this)}
</form>
);
}
}
问题内容: 我正在使用AngularJS和Spring编写应用程序。我想将请求发送到服务器,并将控制器返回的响应下载为文件。在控制器中,我有csv文件的内容(作为字符串),即(1行4列)。将此响应下载为文件的最简单方法是什么? 下面,我发布了我的简化代码。在Spring控制器中: 在javascript(AngularJS)中 我也在尝试(在下面)写入响应流,设置标头,但是在客户端,我总是以字符串
返回的响应是文件。我希望用户能够将其保存为一个文件,但什么也没有发生。我假设服务器正在返回正确类型的响应,因为在控制台中它说 我错过了什么?我在减速机里该怎么办?
我正在使用AngularJS和Spring编写应用程序。我想向服务器发送请求,并下载控制器返回的响应作为文件。在控制器中,我有csv文件的内容(作为字符串),即<代码>1;2.3.4(1行4列)。将此响应下载为文件的最简单方法是什么? 下面,我发布了我的简化代码。Spring控制器: 在javascript中(AngularJS) 我还试图写入响应流(如下所示),设置标题,但在客户端,我总是以字符
我有一个API可以返回excel文档作为响应。请求将是一个简单的JSON。 我搜索了谷歌,找到了一些代码库下载文件,我已经在我的应用程序中使用了它,但我得到了一些错误,无法找到它的解决方案。下面是我的代码库。 NameService.ts HTTPService.ts 使用上面的代码库,我得到了以下两个错误,文件没有下载。 null
问题内容: 我正在尝试使浏览器下载从ajax响应接收到的pdf文件。 受jquery ajax下载pdf文件启发,我模拟了如下单击/下载事件: 不幸的是,这仅适用于Chrome,不适用于Firefox + IE。当我尝试在最后两个浏览器中触发它时,没有任何反应。 由于从CMS继承,脚本和标记被放置在iframe中,但是我不确定这是否有影响。 关于如何针对所有现代浏览器进行优化的想法? 问题答案:
当用户点击下载按钮时,文件应该被下载,而不会在新标签中打开文件预览。如何实现这在反应js?