2016-07-29 78 views
0

我正在使用docxtpl生成一个word文档,并想知道如何用户可以下载此文件一旦生成使用cherrypy,请参阅下面我的代码。下载docxtpl生成的文件与cherrypy

我想出的唯一解决方案是将其保存到www文件夹并创建一个链接到位置,但我相信这可以简化。

代码:

import os, os.path 
import random 
import string 
import cherrypy 
from docxtpl import DocxTemplate 
import sys 
from auth import AuthController, require, member_of, name_is 
import socket 

reload(sys) 
sys.setdefaultencoding('utf8') 
cherrypy.config.update({'server.socket_port': 8000}) 
cherrypy.server.socket_host = '0.0.0.0' 
cherrypy.engine.restart() 

class Root(object): 

    _cp_config = { 
     'tools.sessions.on': True, 
     'tools.auth.on': True } 

    @cherrypy.expose() 
    def default(self, **kwargs): 
     print kwargs  
     if kwargs.get('csa_no'): 
#    print kwargs.get('csa_no') 
      tpl=DocxTemplate('csa_tpl.docx')    
      sd = tpl.new_subdoc() 
      p = sd.add_paragraph('This 1st insert') 
      sd2 = tpl.new_subdoc() 
      p = sd2.add_paragraph('This 2nd insert') 
      context1 = { 
        'date': 'jkh', 
        'company_name' : 'Test Footer', 
        'cost' : '10,000', 
        'project_description': kwargs['project_description'], 
        'site': kwargs['site'], 
        'sp': kwargs['sp'], 
        'wo': kwargs['WO'], 
        'contract_manager': kwargs['contract_manager'], 
        'csa_no': kwargs['csa_no'], 
        'variation_reason': kwargs['variation_reason'], 
        'variation_scope_of_works': kwargs['variation_scope_of_works'], 

        'Initial_Contract_Value': '$300,000', 
        'variation_total': '$20,000', 
        'Ammended_Contract_Value': '$320,000', 
        'project_manager': kwargs['project_manager'], 
        'construction_manager': 'Dane Wilson', 
        'date': '30/04/2016',  
       } 
      tpl.render(context1) 
      file_name_with_path = '/var/www/html/csa_documents/' + kwargs['sp'] + '-'+ kwargs['WO'] + '_' + kwargs['site'] + '_-_' + 'CSA' + kwargs['csa_no'] +'.docx' 
      file_name = kwargs['sp'] + '-'+ kwargs['WO'] + '_' + kwargs['site'] + '_-_' + 'CSA' + kwargs['csa_no'] +'.docx' 
      print file_name 
      print file_name_with_path 
      tpl.save(file_name_with_path) 
      return ''' 

      <!DOCTYPE html> 
      <html> 
      <head> 
      <meta name="viewport" content="width=device-width, initial-scale=1"> 
      <meta charset="utf-8" http-equiv="X-UA-Compatible" content="IE=9" /> 
      <link href="//ajax.googleapis.com/ajax/libs/jquerymobile/1.4.2/jquery.mobile.min.css" rel="stylesheet"> 
      <script src="//ajax.googleapis.com/ajax/libs/jquery/1.10.2/jquery.min.js"></script> 
      <script src="//ajax.googleapis.com/ajax/libs/jquerymobile/1.4.2/jquery.mobile.min.js"></script> 
      <title>Broadspectrum</title> 
      </head> 
      <body> 
      <div data-role="header" data-theme="b"> 
      <h1>TCSS Gateway</h1> 
      </div> 
      <h2>Success</h2> 
      <a href="http://192.168.1.7">another submission</a> 
      <a href="http://192.168.1.7/csa_documents/%s">Download & Review CSA Document</a> 
      </body> 

      ''' % file_name 

回答

1

简短的回答是,基本上你需要写一些内存流(例如BytesIO),预先设定的HTTP标头并返回file_generator。 您的问题与一个月前询问的问题几乎相同,here是我的答案。

我在python3起草了小片段为您:

from io import BytesIO 

import cherrypy 
from cherrypy.lib import file_generator 

from docxtpl import DocxTemplate 


class GenerateDocx: 
    @cherrypy.expose 
    def build_docx(self, *args, **kwargs): 
     iostream = BytesIO() 

     tpl = DocxTemplate('csa_tpl.docx') 
     ... 
     # build your tpl here 
     ... 
     tpl.get_docx().save(iostream) 

     cherrypy.response.headers['Content-Type'] = (
      # set the correct MIME type for docx 
      'application/vnd.openxmlformats-officedocument' 
      '.wordprocessingml.document' 
     ) 
     cherrypy.response.headers['Content-Disposition'] = (
      'attachment; filename={fname}.docx'.format(
       fname='put your file name here' 
      ) 
     ) 

     iostream.seek(0) 
     return file_generator(iostream) 

UPD:我刚刚检查了the response body gets automatically wrapped with file_generator if the return value of a handler has read() method support

+0

感谢,我得到一个文件,但似乎DOCX,该Content-Disposition似乎设置在zip.please帮助 – Ossama

+0

我设法得到docx使用,cherrypy.response.headers ['Content-Disposition'] =( 'attachment; filename =“file.docx”' )但该文件为空 – Ossama

+0

哦,我错过了,确定扩展名应该是docx – webKnjaZ