2012-03-21 2 views
2

私はこれを何時間も試してきたので、おそらく新しい目が助けになるでしょう。GWTでGAEにファイルをアップロードするには?

Google App EngineでGWT(UiBinderを使用)を使用してファイルをサーバーにアップロードしようとしています。私が見つけることができるすべての例に続いて、が動作するように、のように見えますが、サーバーの「投稿」メソッドには0個のアイテムがアップロードされています。

ここでは、クライアントコードです:

FormUploader.ui.xml:

<g:FormPanel action="/formImageUploader" ui:field="formPanel"> 
    <g:VerticalPanel> 
     <g:FileUpload ui:field="uploader"></g:FileUpload> 
     <g:Button ui:field="submit">Submit</g:Button> 
    </g:VerticalPanel> 
</g:FormPanel> 

FormUploader.java:

@UiField 
    FormPanel formPanel; 

    @UiField 
    FileUpload uploader; 

    @UiField 
    Button submit; 

public FormUploader() { 
    initWidget(uiBinder.createAndBindUi(this)); 

    formPanel.setEncoding(FormPanel.ENCODING_MULTIPART); 
    formPanel.setMethod(FormPanel.METHOD_POST); 
    addSubmitHandlers(); 
    } 

    private void addSubmitHandlers() {  
    formPanel.addSubmitCompleteHandler(new SubmitCompleteHandler() { 
     @Override 
     public void onSubmitComplete(SubmitCompleteEvent event) { 
     Core.log("Inside submitComplete"); 
     Window.alert(event.getResults()); 
     } 
    }); 
    } 

のweb.xml:

は、
<servlet> 
    <servlet-name>formImageUploader</servlet-name> 
    <servlet-class>com.company.server.FormImageUploader</servlet-class> 
    </servlet> 
    <servlet-mapping> 
    <servlet-name>formImageUploader</servlet-name> 
    <url-pattern>/formImageUploader</url-pattern> 
    </servlet-mapping> 

FormImageUploader.java:

public class FormImageUploader extends HttpServlet { 

    protected void doPost(HttpServletRequest request, HttpServletResponse resp) throws ServletException, IOException { 
    log.info("Request.getContentLength(): " + request.getContentLength()); 
    log.info("Content type: " + request.getContentType()); 

    log.info("Parm names: "); 
    for (Object paramName : request.getParameterMap().keySet()) { 
     log.info("__Param name: " + paramName.toString()); 
    } 
    log.info("Attribtue names: "); 
    Enumeration enu = request.getAttributeNames(); 
    while (enu.hasMoreElements()) { 
     log.info("__Attribute name: " + enu.nextElement().toString()); 
    } 
    log.info("Header names: "); 
    enu = request.getHeaderNames(); 
    while (enu.hasMoreElements()) { 
     log.info("__Header name: " + enu.nextElement().toString()); 
    } 
    resp.getWriter().println("Post Code has finished executing"); 
} 

このすべてがうまく実行し、クライアントが郵便番号がの実行を終了しましたが、私が取得する方法を見つけ出すことはできませんを含む警告ボックスが表示さアップロードしたいファイルの内容。

ここでは、サーバー側のログです:

Request.getContentLength(): 63 
Content type: multipart/form-data; boundary=---------------------------194272772210834546661 
Parm names: 
Attribtue names: 
__Attribute name: com.google.apphosting.runtime.jetty.APP_VERSION_REQUEST_ATTR 

誰もが、私は、クライアント上で「送信」をクリックした後、サーバー上の任意のファイルを見ていないよ、なぜ私を見るのを助けることができますか?事前に

おかげ

編集:私は、サーバー上のフォームデータを取得することができない理由

はまだ把握することはできません。私はthis exampleに従っているだけで、クライアントに応答を書き出そうとしていますが、サーバーはクライアントからのコンテンツを見ていません。

Serverコード:

try { 
     log.info("Inside try block"); 
     ServletFileUpload upload = new ServletFileUpload(); 
     log.info("created the servlet file upload"); 
     res.setContentType("text/plain"); 
     log.info("set the content type to text/plain"); 
     FileItemIterator iterator = upload.getItemIterator(req); 
     log.info("Got the iterator for items"); 
     while (iterator.hasNext()) { 
     log.info("__inside iterator.hasNext"); 
     FileItemStream item = iterator.next(); 
     log.info("__assigned the file item stream"); 
     InputStream stream = item.openStream(); 
     log.info("__opened said stream"); 
     if (item.isFormField()) { 
      log.warning("Got a form field: " + item.getFieldName()); 
     } else { 
      log.warning("Got an uploaded file: " + item.getFieldName() + 
       ", name = " + item.getName()); 

      int len; 
      byte[] buffer = new byte[8192]; 
      while ((len = stream.read(buffer, 0, buffer.length)) != -1) { 
      res.getOutputStream().write(buffer, 0, len); 
      } 
      log.info("Done writing the input to the output stream"); 
     } 
     } 
    } catch (Exception ex) { 
     log.severe("Exception; " + ex); 
     throw new ServletException(ex); 
    } 
    log.info("Done parseInput3"); 

ログ:

Inside parseInput3 
Inside try block 
created the servlet file upload 
set the content type to text/plain 
Got the iterator for items 
Done parseInput3 

は再び、それは間違いなく、サーバー上のファイルの項目を反復することはできません...任意のアイデアなぜですか?

答えて

2

GAEは、ファイル(ブロブ)をアップロードする全く異なる方法があり、判明: http://code.google.com/appengine/docs/java/blobstore/overview.html#Uploading_a_Blob

あなたはサーバーからブロブストアのアップロードURL(タイムアウトする)と、フォームのクライアント上を指定する必要があり、取得しました使用:

blobstoreService.createUploadUrl('urlToRedirectToAfterUploadComplete') 

フォームのアクションにそのアップロードURLを設定した後、フォームが送信され、ブロブストアサービスは、Googleが格納されたオブジェクトのBlobKeyにアクセスすることができます提供されたURLにリダイレクトします。

だからこれで、私は私のGWT FileUploadに次のChangeHandlerを追加しました:

private void addChangeListener() { 
    Core.log("Selected file: " + uploader.getFilename()); 
    uploader.addChangeHandler(new ChangeHandler() { 
     @Override 
     public void onChange(ChangeEvent event) { 
     MyApp.SERVICES.getUploadUrl(new SuccessAsyncCallback<String>() { 
      @Override 
      public void onSuccess(String uploadUrl) { 
      form.setAction(uploadUrl); 
      form.submit(); 
      Core.log("Submitted form with upload url: " + uploadUrl); 
      } 
     }); 
     } 
    }); 
    } 

を次にサーブレットで、私はGAEは、アップロード後にリダイレクトがあります。

@Override 
    protected void doPost(HttpServletRequest req, HttpServletResponse resp) throws Exception { 
    BlobstoreService blobstoreService = BlobstoreServiceFactory.getBlobstoreService(); 
    Map<String, List<BlobKey>> blobs = blobstoreService.getUploads(req); 
    // where 'uploader' is the name of the FileUploader (<input type='file'>) control on the client 
    List<BlobKey> blobKeys = blobs.get("uploader"); 
    resp.getOutputStream().print(blobKeys.get(0).getKeyString()); 
    } 

注意を!

アップロードされたブロブの値を取得しようとしたときFileUpload制御はidがui:field="nameofControl"

0

ローカルファイルシステムに書き込むことはできません。files apiをご覧ください。

+0

ことができていること(UiBinderサンプルメッセージを使用して)あなたがそれを教えてくれていても、定義されたname="whateveryouwantthenametobe"属性を持っていない場合、GAEはのOutOfMemory例外がスローされますあなたは、クライアントからGAE上のアップロードされたファイルを抽出する方法に関するアドバイスをしますか?そのブロブストアのリンクは、ファイルを作成してブロブストアに保存する方法を示しているだけで、アップロードされたファイルを抽出する方法は示されていません。 – Cuga

関連する問題