2008-12-08 12 views
9

Tengo una aplicación flexible que carga archivos a un servidor. El servidor requiere autenticación para poder cargar. En IE, la carga funciona bien. Sin embargo, en FF y Safari, no se carga. He visto gente por todas partes con este mismo problema pero sin respuestas. No me falles ahora stackoverflowers.¿Cómo hago que la carga de archivos Flex funcione en Firefox y Safari?

+0

Voy a estar trabajando en solucionar este problema yo mismo en las próximas semanas e informaré sobre cualquier éxito o falla que tenga. –

+0

Sin más información, esta pregunta es casi imposible de responder. ¿Está utilizando un componente escrito por otra persona, o el suyo propio? ¿Funciona la autenticación en todos los navegadores? ¿Tiene un fragmento de código? ¿Alguna idea de dónde se detiene el código/bombardeo? –

Respuesta

3

Encontré esta pregunta al intentar encontrar la respuesta yo mismo. La solución fue bastante simple.

Basado en el flash player bug que otros han vinculado, y los comentarios en esa página, decidí agregar identificadores de sesión a mi URL de carga y darle una oportunidad. ¡Realmente fue así de fácil!

Para hacerlo funcionar, comencé agregando un parámetro flashVar llamado sessionParams. Esto me permitió pasar cualquier cadena que desee al reproductor flash como mi identificador de sesión, y luego se adjuntará a la URL utilizada para cargar.

//sessionParams - resolves firefox upload bug 
public var sessionParams:String = ""; 

//... 

public function initApp():void{ 
    sessionParams = Application.application.parameters.sessionParams; 
} 

En mi caso, estoy en ColdFusion con sesiones de Java permitió, por lo que mi sessionParams están configurados como lo siguiente antes de ser pasado en el reproductor de flash:

<cfset flashVars = "sessionParams=#urlEncodedFormat('jsessionid=' & session.sessionid)#" /> 

No se olvide de escapar caracteres especiales como =, &, etc. (que he hecho con urlEncodedFormat), para que sean tratados como parte del valor del parámetro "sessionParams", y no como puntos de interrupción para indicar otros parámetros. Está incorporando información de URL futura en la URL actual.

A continuación, utilice el valor de sessionParams en su código de carga.He aquí un fragmento de cómo me puse el mío:

// Set Up URLRequest 
_uploadURL = new URLRequest; 
_uploadURL.url = _url + "?" + _sessionParams; 
_uploadURL.method = "GET"; 
_uploadURL.data = _variables; 
_uploadURL.contentType = "multipart/form-data"; 

Los nombres de las variables son diferentes (pero similar), ya que esto es parte de una clase reutilizable.

Espero que eso te ayude. Si no, avíseme y trataré de proporcionarle más código o una explicación para ayudarlo.

+0

Lamentablemente estoy usando .net. Sin embargo, estoy usando un método similar que encontré en esta pregunta http://stackoverflow.com/questions/43324/can-i-put-an-asp-net-session-id-in-a-hidden-form-field – smartdirt

+1

Lamentablemente, esto no funciona si su cookie JSESSIONID está configurada en httponly, que es una configuración recomendada para resons de seguridad (para evitar XSS). –

+0

Sin mencionar que el envío de identificadores de sesión en la URL expone la sesión a intermediarios (por ejemplo, cachés) u otras personas (por ejemplo, a través de registros de solicitud, monitoreo, análisis). –

3

El problema al menos en Firefox es que las cookies de sesión no se envían en la solicitud cuando se invoca FileReference.upload(). Lo que debe hacer es agregar el token de autenticación como una variable de formulario o en la cadena de consulta. Este es un ejemplo en Java, donde la cookie de sesión se llama "jsessionid"

var request : URLRequset = new URLRequest(uploadUrl + ";jsessionid=" + jsessionid); 

Puede analizar el jsessionid las cookies utilizando Javascript y ExternalInterface para invocar la función Javascript. O bien, después de autenticarse, puede hacer que Flex invoque un método de backend que devuelva el ID de sesión actual.

El fallo relacionado Flex está aquí:

http://bugs.adobe.com/jira/browse/FP-201

+2

Para agregar a esto, la razón por la que las cookies de sesión no se envían en Firefox es porque Flash Player usa la pila de red del sistema operativo. Firefox tiene su propia pila de red, por lo que Flash Player no conoce la sesión. Funciona en IE porque IE también usa la pila del sistema operativo (obviamente). – joshtynjala

0

Parece que esto es bastante antiguo, pero recientemente me encontré con este problema, también. Mi solución (que está lejos de ser óptima) en una configuración de rieles autenticados Flex + era desactivar la autenticación basada en la sesión en el script de carga.

Como realmente hice quiero autenticación al menos básica, guardé el nombre de usuario y la contraseña con la que el usuario inició sesión, y escribí el código para enviar/validar manualmente en el lado de los rieles. Nunca pude hacer funcionar el truco "jsessionid", ya que el flash no tiene acceso a las sesiones del navegador.

Espero que esto ayude a alguien a ahorrar un poco de tiempo.

0

Esto es un flash player bug real. Tal vez este enlace te dará algunas ideas.

¿Qué tiene en el lado del servidor? Tal vez podría agregar el sessionid como parámetro en su solicitud.

1

He resuelto este problema. La carga de archivos utilizando flex funcionará en todos los navegadores. En la aplicación J2ee,

comente la restricción de seguridad o haga que la URL fileupload.do desprotegida en web.xml donde colocará el código real.

<security-constraint> 
    <display-name>Senusion Security Constraint</display-name> 
    <web-resource-collection> 
     <web-resource-name>Un Protected Area</web-resource-name> 
      <url-pattern>/fileupload.do</url-pattern> 
     </web-resource-collection> 
</security-constraint> 

Espero que esto ayude al próximo lector.

+0

lolz, esa es una forma. – Tom

1

FlashPlayer 10 proporciona una nueva API de Filereference que puede ayudar mucho. Aquí hay una entrada de blog que lo describe: http://www.flexpasta.com/index.php/2010/02/21/uploading-files-with-firefox-solution/.

De hecho en Flash 10 una mejora de flash.net.FileReference hace posible leer el contenido de un archivo antes de que se cargue. Lo que significa que el archivo se puede cargar de diferentes maneras y luego se puede hacer en Flash 9. El siguiente ejemplo muestra cómo la carga de archivos fácil puede ser y no está vinculada a SSL, Firefox, IE, Chrome, etc.

1

logré evitar este error usando filtro web Flex y java

Código Flex:

var urlVars:URLVariables = new URLVariables(); 
urlVars.jsessionid = sessionID; 

var uploadUrl:String = "http://localhost:8080/mywar;jsessionid="+sessionID; 
uploadUrl += "?"+getClientCookies(); //put all client cookies on the query string 
var urlRequest:URLRequest = new URLRequest(uploadUrl); 
urlRequest.method = URLRequestMethod.POST; 
urlRequest.data = urlVars; 

//will go first time and get the cookies set see flex docs 
var testUpload:Boolean = true; 
fileRef.upload(urlRequest,"Filedata",testUpload); 

jAVA CÓDIGO:

package com.mywar.fileupload; 

import java.io.IOException; 
import java.util.Enumeration; 

import javax.servlet.Filter; 
import javax.servlet.FilterChain; 
import javax.servlet.FilterConfig; 
import javax.servlet.ServletException; 
import javax.servlet.ServletRequest; 
import javax.servlet.ServletResponse; 
import javax.servlet.http.Cookie; 
import javax.servlet.http.HttpServletRequest; 
import javax.servlet.http.HttpServletResponse; 

/** 
* @author orasio - spieler 
* This filter comes to solve the Firefox ,Chrome and SAFARI file upload issue 
* The problem was that the file uploaded by the flex 
* FileReference came with a different session and no cookies 
* To solve this problem do the following : 
* 
* 
* don't forget to add this filter to the web.xml file 
*/ 
public class FileUploadFilter implements Filter { 

    private static final String CONTENT_LENGTH = "content-length"; 
    private static final String UPLOAD_SITE_PATH = "/"; 
    private static final String JSESSIONID = "JSESSIONID"; 


    @Override 
    public void init(FilterConfig filterConfig) throws ServletException { 
    } 

    @Override 
    public void doFilter(ServletRequest request, 
       ServletResponse response, 
       FilterChain filterChain) 
       throws IOException, ServletException { 
     if ((request instanceof HttpServletRequest) 
     && (response instanceof HttpServletResponse)) { 
      HttpServletRequest httpRequest = (HttpServletRequest) request; 

      //httpRequest.getHeader("user-agent"); //Shockwave Flash 
      String contentLength = httpRequest.getHeader(CONTENT_LENGTH); 
      boolean isFlexTest = (contentLength!=null 
         && Integer.parseInt(contentLength)==0); 
      if(isFlexTest){ 
       HttpServletResponse httpResponse = 
              (HttpServletResponse) response; 
       setAllClientCookie((HttpServletResponse)response, httpRequest); 
       PrintWriter out = httpResponse.getWriter(); 
       out.println("OK"); 
       out.close(); 
       return; 
      } 
     } 
     filterChain.doFilter(request, response); 
    } 

    /* 
    * write all cookies back to the flex test response 
    */ 
    @SuppressWarnings("unchecked") 
    private void setAllClientCookie(HttpServletResponse httpResponse, 
        HttpServletRequest httpRequest) { 
     Enumeration<String> parameterNames = 
       (Enumeration<String>)httpRequest.getParameterNames(); 
     while (parameterNames.hasMoreElements()) { 
      String cookieName = (String) parameterNames.nextElement(); 
    //since we get IllegalArgumentException: Cookie name "JSESSIONID" is a reserved token 

      if(!cookieName.contains(JSESSIONID)) { 
       Cookie cookie = 
          new Cookie(cookieName, httpRequest.getParameter(cookieName)); 
       cookie.setPath(UPLOAD_SITE_PATH); 
       httpResponse.addCookie(cookie); 
      } 
     } 
    } 

    @Override 
    public void destroy() { 
    } 

} 
1

Enfrenté el mismo problema ... La carga de archivos estaba funcionando en todos los navegadores excepto en firefox. En Firefox, el error # 2038 estaba siendo lanzado mientras se cargaba el archivo. La aplicación usó SSL ... En mi caso, incluso la solicitud de carga no se generaba desde Firefox, lo cual pude confirmar al ver en el panel Net de firebug, la URL de carga no estaba siendo golpeada. Eso significa que puede ser el tiempo de ejecución de flash en Firefox bloqueando la solicitud de carga. Sin embargo, cuando ejecuté la aplicación en IE, instalé el certificado autofirmado de la aplicación en IE, cargué el archivo de forma ambigua y, por supuesto, increíblemente, comencé a trabajar en firefox. Primero compruebe si la solicitud se está llegando al servidor u obteniendo bloqueado en el cliente.

Gracias

0

Algunas veces, incluso si enviamos las galletas a través de la URL no funcionará. Esto se debe a que Flex está bloqueando la solicitud de carga de archivos.

Para desbloquearlo, debe instalar el certificado SSL y luego probarlo.

Si alguien tiene alguna otra respuesta, por favor hágamelo saber.

0

Como estaba creando una aplicación Flash para Facebook, no tenía acceso a jsessionid.

He resuelto este problema por cargando en una dirección HTTPS en lugar de HTTP.

Una cosa que me causó problemas es que en OSX Firefox y Safari (no en Chrome), el (FileReferenceInstance) .type es nulo, y el (FileReferenceInstance) .name viene con la extensión completa (myimage.jpg).

Cuestiones relacionadas